2 * This file is part of the GROMACS molecular simulation package.
4 * Copyright (c) 2013,2014,2015, by the GROMACS development team, led by
5 * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
6 * and including many others, as listed in the AUTHORS file in the
7 * top-level source directory and at http://www.gromacs.org.
9 * GROMACS is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public License
11 * as published by the Free Software Foundation; either version 2.1
12 * of the License, or (at your option) any later version.
14 * GROMACS is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Lesser General Public License for more details.
19 * You should have received a copy of the GNU Lesser General Public
20 * License along with GROMACS; if not, see
21 * http://www.gnu.org/licenses, or write to the Free Software Foundation,
22 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
24 * If you want to redistribute modifications to GROMACS, please
25 * consider that scientific software is very special. Version
26 * control is crucial - bugs must be traceable. We will be happy to
27 * consider code for inclusion in the official distribution, but
28 * derived work must not be called official GROMACS. Details are found
29 * in the README & COPYING files - if they are missing, get the
30 * official version at http://www.gromacs.org.
32 * To help us fund GROMACS development, we humbly ask that you cite
33 * the research papers on the package. Check out http://www.gromacs.org.
37 * Implements gmx::analysismodules::Freevolume.
39 * \author Titov Anatoly <Wapuk-cobaka@yandex.ru>
40 * \ingroup module_trajectoryanalysis
51 #include <gromacs/trajectoryanalysis.h>
52 #include <gromacs/pbcutil/pbc.h>
53 #include <gromacs/utility/smalloc.h>
54 #include <gromacs/math/do_fit.h>
55 #include <gromacs/fileio/trxio.h>
56 #include <gromacs/trajectoryanalysis/topologyinformation.h>
62 double F (double aix, double aiy, double aiz, double bix_plus_x, double biy_plus_y, double biz_plus_z, double A, double B, double C) {
63 return sqrt( pow(aix + biy_plus_y * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B)) - biz_plus_z * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) - cos(B) * cos(C) * bix_plus_x, 2) +
64 pow(aiy - biy_plus_y * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C)) + biz_plus_z * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) - cos(B) * sin(C) * bix_plus_x, 2) +
65 pow(aiz + sin(B) * bix_plus_x - cos(A) * cos(B) * biz_plus_z - cos(B) * sin(A) * biy_plus_y, 2) );
68 void searchF0xyzabc (double &F, double &Fx, double &Fy, double &Fz, double &Fa, double &Fb, double &Fc, double aix, double aiy, double aiz, double bix_plus_x, double biy_plus_y, double biz_plus_z, double A, double B, double C) {
69 double t01, t02, t03, t04, t05, t06, t07;
70 t01 = pow(aix + biy_plus_y * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B)) - biz_plus_z * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) - cos(B) * cos(C) * bix_plus_x, 2);
71 t02 = pow(aiy - biy_plus_y * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C)) + biz_plus_z * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) - cos(B) * sin(C) * bix_plus_x, 2);
72 t03 = pow(aiz + sin(B) * bix_plus_x - cos(A) * cos(B) * biz_plus_z - cos(B) * sin(A) * biy_plus_y, 2);
73 t04 = sqrt(t01 + t02 + t03);
74 t05 = (aix + biy_plus_y * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B)) - biz_plus_z * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) - cos(B) * cos(C) * bix_plus_x);
75 t06 = (aiz + sin(B) * bix_plus_x - cos(A) * cos(B) * biz_plus_z - cos(B) * sin(A) * biy_plus_y);
76 t07 = (aiy - biy_plus_y * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C)) + biz_plus_z * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) - cos(B) * sin(C) * bix_plus_x);
78 //#pragma omp parallel sections
83 Fx += -(2 * cos(B) * cos(C) * t05 - 2 * sin(B) * t06 + 2 * cos(B) * sin(C) * t07) / (2 * t04);
85 Fy += -(2 * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C)) * t07 - 2 * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B)) * t05 + 2 * cos(B) * sin(A) * t06) / (2 * t04);
87 Fz += -(2 * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) * t05 - 2 * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) * t07 + 2 * cos(A) * cos(B) * t06) / (2 * t04);
89 Fa += -(2 * (cos(A) * cos(B) * biy_plus_y - cos(B) * sin(A) * biz_plus_z) * t06 -
90 2 * (biy_plus_y * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) + biz_plus_z * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C))) * t07 +
91 2 * (biy_plus_y * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) + biz_plus_z * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B))) * t05) / (2 * t04);
93 Fb += -(2 * (cos(A) * cos(B) * sin(C) * biz_plus_z - sin(B) * sin(C) * bix_plus_x + cos(B) * sin(A) * sin(C) * biy_plus_y) * t07 +
94 2 * (cos(A) * cos(B) * cos(C) * biz_plus_z - cos(C) * sin(B) * bix_plus_x + cos(B) * cos(C) * sin(A) * biy_plus_y) * t05 -
95 2 * (cos(B) * bix_plus_x + sin(A) * sin(B) * biy_plus_y + cos(A) * sin(B) * biz_plus_z) * t06) / (2 * t04);
97 Fc += (2 * (biy_plus_y * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C)) - biz_plus_z * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) + cos(B) * sin(C) * bix_plus_x) * t05 -
98 2 * (biz_plus_z * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) - biy_plus_y * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B)) + cos(B) * cos(C) * bix_plus_x) * t07) / (2 * t04);
102 /*void searchL (double &fLd, double &fLdd, double aix, double aiy, double aiz, double bix, double biy, double biz, double x, double y, double z, double A, double B, double C, double L, double fx, double fy, double fz, double fa, double fb, double fc) {
103 double AmLfa, BmLfb, CmLfc, BIXpXmLfx, BIYpYmLfy, BIZpZmLfz, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, t14, t15, t16, t17, t18, t19, t20;
107 BIXpXmLfx = bix + x - L * fx;
108 BIYpYmLfy = biy + y - L * fy;
109 BIZpZmLfz = biz + z - L * fz;
110 t1 = (cos(AmLfa) * cos(CmLfc) + sin(AmLfa) * sin(BmLfb) * sin(CmLfc));
111 t2 = (cos(CmLfc) * sin(AmLfa) - cos(AmLfa) * sin(BmLfb) * sin(CmLfc));
112 t3 = (cos(AmLfa) * sin(CmLfc) - cos(CmLfc) * sin(AmLfa) * sin(BmLfb));
113 t4 = (sin(AmLfa) * sin(CmLfc) + cos(AmLfa) * cos(CmLfc) * sin(BmLfb));
114 t5 = pow(aiz + sin(BmLfb) * BIXpXmLfx - cos(AmLfa) * cos(BmLfb) * BIZpZmLfz - cos(BmLfb) * sin(AmLfa) * BIYpYmLfy, 2);
115 t6 = pow(aix + t3 * BIYpYmLfy - t4 * BIZpZmLfz - cos(BmLfb) * cos(CmLfc) * BIXpXmLfx, 2);
116 t7 = pow(aiy - t1 * BIYpYmLfy + t2 * BIZpZmLfz - cos(BmLfb) * sin(CmLfc) * BIXpXmLfx, 2);
118 t8 = fc * sin(AmLfa) * sin(CmLfc);
119 t9 = fa * cos(AmLfa) * cos(CmLfc);
120 t10 = fb * cos(AmLfa) * cos(BmLfb) * sin(CmLfc);
121 t11 = fc * cos(AmLfa) * cos(CmLfc) * sin(BmLfb);
122 t12 = fa * sin(AmLfa) * sin(BmLfb) * sin(CmLfc);
124 t13 = fa * cos(AmLfa) * sin(BmLfb) * sin(CmLfc);
125 t14 = fc * cos(AmLfa) * sin(CmLfc);
126 t15 = fa * cos(CmLfc) * sin(AmLfa);
127 t16 = fb * cos(BmLfb) * sin(AmLfa) * sin(CmLfc);
128 t17 = fc * cos(CmLfc) * sin(AmLfa) * sin(BmLfb);
130 t18 = fx * cos(BmLfb) * sin(CmLfc);
131 t19 = fc * cos(BmLfb) * cos(CmLfc);
132 t20 = fb * sin(BmLfb) * sin(CmLfc);
134 fLd += (2 * (aiy - t1 * BIYpYmLfy + t2 * BIZpZmLfz - cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) *
135 ( BIZpZmLfz * (t8 - t9 + t10 + t11 - t12) + fy * t1 - fz * t2 + BIYpYmLfy * (t13 - t14 - t15 + t16 + t17) + t18 + t19 * BIXpXmLfx - t20 * BIXpXmLfx) -
136 2 * (aiz + sin(BmLfb) * BIXpXmLfx - cos(AmLfa) * cos(BmLfb) * BIZpZmLfz - cos(BmLfb) * sin(AmLfa) * BIYpYmLfy) *
137 (fx * sin(BmLfb) - fy * cos(BmLfb) * sin(AmLfa) + fb * cos(BmLfb) * BIXpXmLfx - fz * cos(AmLfa) * cos(BmLfb) -
138 fa * cos(AmLfa) * cos(BmLfb) * BIYpYmLfy + fa * cos(BmLfb) * sin(AmLfa) * BIZpZmLfz + fb * cos(AmLfa) * sin(BmLfb) * BIZpZmLfz + fb * sin(AmLfa) * sin(BmLfb) * BIYpYmLfy) +
139 2 * (aix + t3 * BIYpYmLfy - t4 * BIZpZmLfz - cos(BmLfb) * cos(CmLfc) * BIXpXmLfx) *
140 (BIZpZmLfz * (fa * cos(AmLfa) * sin(CmLfc) + fc * cos(CmLfc) * sin(AmLfa) + fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) - t15 * sin(BmLfb) - fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) +
141 BIYpYmLfy * (fa * sin(AmLfa) * sin(CmLfc) - fc * cos(AmLfa) * cos(CmLfc) + t9 * sin(BmLfb) +
142 fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) - fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) - fy * t3 +
143 fz * t4 + fx * cos(BmLfb) * cos(CmLfc) - fb * cos(CmLfc) * sin(BmLfb) * BIXpXmLfx - fc * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx)) /
144 (2 * sqrt( t5 + t6 + pow(aiy - t1 * BIYpYmLfy + t2 * BIZpZmLfz - cos(BmLfb) * sin(CmLfc) * BIXpXmLfx, 2)));
147 fLdd += ( (2 * aiz + 2 * sin(BmLfb) * BIXpXmLfx - 2 * cos(AmLfa) * cos(BmLfb) * BIZpZmLfz - 2 * cos(BmLfb) * sin(AmLfa) * BIYpYmLfy) *
148 (2 * fb * fx * cos(BmLfb) - pow(fb, 2) * sin(BmLfb) * BIXpXmLfx - 2 * fa * fy * cos(AmLfa) * cos(BmLfb) + 2 * fa * fz * cos(BmLfb) * sin(AmLfa) + 2 * fb * fz * cos(AmLfa) * sin(BmLfb) +
149 2 * fb * fy * sin(AmLfa) * sin(BmLfb) + pow(fa, 2) * cos(AmLfa) * cos(BmLfb) * BIZpZmLfz + pow(fb, 2) * cos(AmLfa) * cos(BmLfb) * BIZpZmLfz +
150 pow(fa, 2) * cos(BmLfb) * sin(AmLfa) * BIYpYmLfy + pow(fb, 2) * cos(BmLfb) * sin(AmLfa) * BIYpYmLfy + 2 * fa * fb * cos(AmLfa) * sin(BmLfb) * BIYpYmLfy -
151 2 * fa * fb * sin(AmLfa) * sin(BmLfb) * BIZpZmLfz) +
152 (BIZpZmLfz * (fa * cos(AmLfa) * sin(CmLfc) + fc * cos(CmLfc) * sin(AmLfa) +
153 fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) - t15 * sin(BmLfb) - fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) +
154 BIYpYmLfy * (fa * sin(AmLfa) * sin(CmLfc) - fc * cos(AmLfa) * cos(CmLfc) + t9 * sin(BmLfb) +
155 fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) - fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) - fy * (cos(AmLfa) * sin(CmLfc) -
156 cos(CmLfc) * sin(AmLfa) * sin(BmLfb)) + fz * t4 + fx * cos(BmLfb) * cos(CmLfc) -
157 fb * cos(CmLfc) * sin(BmLfb) * BIXpXmLfx - fc * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) *
158 (2 * BIZpZmLfz * (fa * cos(AmLfa) * sin(CmLfc) +
159 fc * cos(CmLfc) * sin(AmLfa) + fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) - t15 * sin(BmLfb) -
160 fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) + 2 * BIYpYmLfy * (fa * sin(AmLfa) * sin(CmLfc) - fc * cos(AmLfa) * cos(CmLfc) +
161 t9 * sin(BmLfb) + fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) - fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) -
162 2 * fy * t3 + 2 * fz * t4 +
163 2 * fx * cos(BmLfb) * cos(CmLfc) - 2 * fb * cos(CmLfc) * sin(BmLfb) * BIXpXmLfx - 2 * fc * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) +
164 (2 * aix + 2 * t3 * BIYpYmLfy - 2 * (sin(AmLfa) * sin(CmLfc) +
165 cos(AmLfa) * cos(CmLfc) * sin(BmLfb)) * BIZpZmLfz - 2 * cos(BmLfb) * cos(CmLfc) * BIXpXmLfx) *
166 (BIZpZmLfz * (pow(fa, 2) * sin(AmLfa) * sin(CmLfc) +
167 pow(fc, 2) * sin(AmLfa) * sin(CmLfc) - 2 * fa * fc * cos(AmLfa) * cos(CmLfc) + pow(fa, 2) * cos(AmLfa) * cos(CmLfc) * sin(BmLfb) +
168 pow(fb, 2) * cos(AmLfa) * cos(CmLfc) * sin(BmLfb) + pow(fc, 2) * cos(AmLfa) * cos(CmLfc) * sin(BmLfb) + 2 * fa * fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) +
169 2 * fb * fc * cos(AmLfa) * cos(BmLfb) * sin(CmLfc) - 2 * fa * fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) + BIYpYmLfy * (pow(fa, 2) * cos(CmLfc) * sin(AmLfa) * sin(BmLfb) -
170 pow(fc, 2) * cos(AmLfa) * sin(CmLfc) - 2 * fa * fc * cos(CmLfc) * sin(AmLfa) - pow(fa, 2) * cos(AmLfa) * sin(CmLfc) + pow(fb, 2) * cos(CmLfc) * sin(AmLfa) * sin(BmLfb) +
171 pow(fc, 2) * cos(CmLfc) * sin(AmLfa) * sin(BmLfb) - 2 * fa * fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) + 2 * fa * fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc) +
172 2 * fb * fc * cos(BmLfb) * sin(AmLfa) * sin(CmLfc)) - 2 * fz * (fa * cos(AmLfa) * sin(CmLfc) + fc * cos(CmLfc) * sin(AmLfa) +
173 fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) - t15 * sin(BmLfb) - fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) -
174 2 * fy * (fa * sin(AmLfa) * sin(CmLfc) - fc * cos(AmLfa) * cos(CmLfc) + t9 * sin(BmLfb) + fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) -
175 fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) + 2 * fb * fx * cos(CmLfc) * sin(BmLfb) + 2 * fc * t18 + pow(fb, 2) * cos(BmLfb) * cos(CmLfc) * BIXpXmLfx +
176 pow(fc, 2) * cos(BmLfb) * cos(CmLfc) * BIXpXmLfx - 2 * fb * fc * sin(BmLfb) * sin(CmLfc) * BIXpXmLfx) +
177 (BIZpZmLfz * (t8 - t9 + t10 + t11 - t12) + fy * t1 - fz * t2 + BIYpYmLfy * (t13 - t14 - t15 + t16 + t17) + t18 + t19 * BIXpXmLfx - t20 * BIXpXmLfx) *
178 (2 * BIZpZmLfz * (t8 - t9 + t10 + t11 - t12) + 2 * fy * t1 - 2 * fz * t2 + 2 * BIYpYmLfy * (t13 - t14 - t15 + t16 + t17) + 2 * t18 + 2 * t19 * BIXpXmLfx - 2 * t20 * BIXpXmLfx) +
179 (fx * sin(BmLfb) - fy * cos(BmLfb) * sin(AmLfa) + fb * cos(BmLfb) * BIXpXmLfx - fz * cos(AmLfa) * cos(BmLfb) - fa * cos(AmLfa) * cos(BmLfb) * BIYpYmLfy +
180 fa * cos(BmLfb) * sin(AmLfa) * BIZpZmLfz + fb * cos(AmLfa) * sin(BmLfb) * BIZpZmLfz + fb * sin(AmLfa) * sin(BmLfb) * BIYpYmLfy) *
181 (2 * fx * sin(BmLfb) - 2 * fy * cos(BmLfb) * sin(AmLfa) + 2 * fb * cos(BmLfb) * BIXpXmLfx - 2 * fz * cos(AmLfa) * cos(BmLfb) - 2 * fa * cos(AmLfa) * cos(BmLfb) * BIYpYmLfy +
182 2 * fa * cos(BmLfb) * sin(AmLfa) * BIZpZmLfz + 2 * fb * cos(AmLfa) * sin(BmLfb) * BIZpZmLfz + 2 * fb * sin(AmLfa) * sin(BmLfb) * BIYpYmLfy) +
183 (2 * aiy - 2 * t1 * BIYpYmLfy + 2 * (cos(CmLfc) * sin(AmLfa) - cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) * BIZpZmLfz - 2 * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) *
184 (BIZpZmLfz * (pow(fa, 2) * cos(AmLfa) * sin(BmLfb) * sin(CmLfc) -
185 pow(fc, 2) * cos(CmLfc) * sin(AmLfa) - 2 * fa * t14 - pow(fa, 2) * cos(CmLfc) * sin(AmLfa) + pow(fb, 2) * cos(AmLfa) * sin(BmLfb) * sin(CmLfc) +
186 pow(fc, 2) * cos(AmLfa) * sin(BmLfb) * sin(CmLfc) - 2 * fb * fc * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) + 2 * fa * t16 +
187 2 * fa * t17) + BIYpYmLfy * (pow(fa, 2) * cos(AmLfa) * cos(CmLfc) + pow(fc, 2) * cos(AmLfa) * cos(CmLfc) - 2 * fa * t8 +
188 pow(fa, 2) * sin(AmLfa) * sin(BmLfb) * sin(CmLfc) + pow(fb, 2) * sin(AmLfa) * sin(BmLfb) * sin(CmLfc) + pow(fc, 2) * sin(AmLfa) * sin(BmLfb) * sin(CmLfc) -
189 2 * fa * t10 - 2 * fa * t11 - 2 * fb * t19 * sin(AmLfa)) - 2 * fz * (t8 - t9 + t10 + t11 - t12) - 2 * fy * (t13 - t14 - t15 + t16 + t17) -
190 2 * fc * fx * cos(BmLfb) * cos(CmLfc) + 2 * fb * fx * sin(BmLfb) * sin(CmLfc) +
191 pow(fb, 2) * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx + pow(fc, 2) * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx + 2 * fb * fc * cos(CmLfc) * sin(BmLfb) * BIXpXmLfx)) /
192 (2 * sqrt( t5 + t6 + t7)) -
193 ( (2 * (aiy - t1 * BIYpYmLfy + t2 * BIZpZmLfz - cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) *
194 (BIZpZmLfz * (t8 - t9 + t10 + t11 - t12) + fy * t1 - fz * t2 + BIYpYmLfy * (t13 - t14 - t15 + t16 + t17) + t18 + t19 * BIXpXmLfx - t20 * BIXpXmLfx) -
195 2 * (aiz + sin(BmLfb) * BIXpXmLfx - cos(AmLfa) * cos(BmLfb) * BIZpZmLfz - cos(BmLfb) * sin(AmLfa) * BIYpYmLfy) *
196 (fx * sin(BmLfb) - fy * cos(BmLfb) * sin(AmLfa) + fb * cos(BmLfb) * BIXpXmLfx - fz * cos(AmLfa) * cos(BmLfb) - fa * cos(AmLfa) * cos(BmLfb) * BIYpYmLfy +
197 fa * cos(BmLfb) * sin(AmLfa) * BIZpZmLfz + fb * cos(AmLfa) * sin(BmLfb) * BIZpZmLfz + fb * sin(AmLfa) * sin(BmLfb) * BIYpYmLfy) +
198 2 * (aix + t3 * BIYpYmLfy - t4 * BIZpZmLfz - cos(BmLfb) * cos(CmLfc) * BIXpXmLfx) *
199 (BIZpZmLfz * (fa * cos(AmLfa) * sin(CmLfc) + fc * cos(CmLfc) * sin(AmLfa) + fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) - t15 * sin(BmLfb) - fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) +
200 BIYpYmLfy * (fa * sin(AmLfa) * sin(CmLfc) - fc * cos(AmLfa) * cos(CmLfc) + t9 * sin(BmLfb) + fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) - fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) -
201 fy * t3 + fz * t4 + fx * cos(BmLfb) * cos(CmLfc) - fb * cos(CmLfc) * sin(BmLfb) * BIXpXmLfx - fc * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx)) *
202 ( (2 * aix + 2 * t3 * BIYpYmLfy - 2 * t4 * BIZpZmLfz - 2 * cos(BmLfb) * cos(CmLfc) * BIXpXmLfx) *
203 (BIZpZmLfz * (fa * cos(AmLfa) * sin(CmLfc) + fc * cos(CmLfc) * sin(AmLfa) + fb * cos(AmLfa) * cos(BmLfb) * cos(CmLfc) - t15 * sin(BmLfb) - fc * cos(AmLfa) * sin(BmLfb) * sin(CmLfc)) +
204 BIYpYmLfy * (fa * sin(AmLfa) * sin(CmLfc) - fc * cos(AmLfa) * cos(CmLfc) + t9 * sin(BmLfb) + fb * cos(BmLfb) * cos(CmLfc) * sin(AmLfa) - fc * sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) -
205 fy * t3 + fz * t4 + fx * cos(BmLfb) * cos(CmLfc) - fb * cos(CmLfc) * sin(BmLfb) * BIXpXmLfx - fc * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) +
206 (2 * aiy - 2 * t1 * BIYpYmLfy + 2 * t2 * BIZpZmLfz - 2 * cos(BmLfb) * sin(CmLfc) * BIXpXmLfx) *
207 (BIZpZmLfz * (t8 - t9 + t10 + t11 - t12) + fy * (cos(AmLfa) * cos(CmLfc) + sin(AmLfa) * sin(BmLfb) * sin(CmLfc)) - fz * t2 + BIYpYmLfy * (t13 - t14 - t15 + t16 + t17) +
208 t18 + t19 * BIXpXmLfx - t20 * BIXpXmLfx) - (2 * aiz + 2 * sin(BmLfb) * BIXpXmLfx - 2 * cos(AmLfa) * cos(BmLfb) * BIZpZmLfz - 2 * cos(BmLfb) * sin(AmLfa) * BIYpYmLfy) *
209 (fx * sin(BmLfb) - fy * cos(BmLfb) * sin(AmLfa) + fb * cos(BmLfb) * BIXpXmLfx - fz * cos(AmLfa) * cos(BmLfb) - fa * cos(AmLfa) * cos(BmLfb) * BIYpYmLfy +
210 fa * cos(BmLfb) * sin(AmLfa) * BIZpZmLfz + fb * cos(AmLfa) * sin(BmLfb) * BIZpZmLfz + fb * sin(AmLfa) * sin(BmLfb) * BIYpYmLfy))) /
211 (4 * pow ( t5 + t6 + t7, 3 / 2));
215 void ApplyFit (std::vector< RVec > &b, double x, double y, double z, double A, double B, double C) {
218 #pragma omp for schedule(dynamic)
219 for (int i = 0; i < b.size(); i++) {
221 b[i][0] = (temp[2] + z) * (sin(A) * sin(C) + cos(A) * cos(C) * sin(B)) - (temp[1] + y) * (cos(A) * sin(C) - cos(C) * sin(A) * sin(B)) + cos(B) * cos(C) * (temp[0] + x);
222 b[i][1] = (temp[1] + y) * (cos(A) * cos(C) + sin(A) * sin(B) * sin(C)) - (temp[2] + z) * (cos(C) * sin(A) - cos(A) * sin(B) * sin(C)) + cos(B) * sin(C) * (temp[0] + x);
223 b[i][2] = cos(A) * cos(B) * (temp[2] + z) - sin(B) * (temp[0] + x) + cos(B) * sin(A) * (temp[1] + y);
228 void CalcMid (std::vector< RVec > a, std::vector< RVec > b, RVec &midA, RVec &midB, std::vector< std::pair< int, int > > pairs) {
237 for (int i = 0; i < pairs.size(); i++) {
238 rvec_inc(midA, a[pairs[i].first]);
239 rvec_inc(midB, b[pairs[i].second]);
241 midA[0] /= pairs.size();
242 midA[1] /= pairs.size();
243 midA[2] /= pairs.size();
245 midB[0] /= pairs.size();
246 midB[1] /= pairs.size();
247 midB[2] /= pairs.size();
250 /*float*/double FrameMidLength(std::vector< RVec > a) {
255 for (int i = 0; i < a.size(); i++) {
261 void reset_coord(std::vector< RVec > &frame, RVec move) {
262 for (int i = 0; i < frame.size(); i++) {
267 void MyFitNew (std::vector< RVec > a, std::vector< RVec > &b, std::vector< std::pair< int, int > > pairs, double FtCnst) {
268 double f1 = 0, f2 = 0, fx = 0, fy = 0, fz = 0, fa = 0, fb = 0, fc = 0, l = 1;
270 CalcMid(a, b, ma, mb, pairs);
277 double x = ma[0], y = ma[1], z = ma[2], A = 0, B = 0, C = 0;
278 for (int i = 0; i < pairs.size(); i++) {
279 f1 += F(a[pairs[i].first][0], a[pairs[i].first][1], a[pairs[i].first][2], b[pairs[i].second][0] + x, b[pairs[i].second][1] + y, b[pairs[i].second][2] + z, A, B, C);
288 while (f1 - f2 < 0 || f1 - f2 > FtCnst) {
289 f1 = 0; fx = 0; fy = 0; fz = 0; fa = 0; fb = 0; fc = 0;
290 for (int i = 0; i < pairs.size(); i++) {
291 searchF0xyzabc(f1, fx, fy, fz, fa, fb, fc, a[pairs[i].first][0], a[pairs[i].first][1], a[pairs[i].first][2], b[pairs[i].second][0] + x, b[pairs[i].second][1] + y, b[pairs[i].second][2] + z, A, B, C);
295 for (int i = 0; i < pairs.size(); i++) {
296 f2 += F(a[pairs[i].first][0], a[pairs[i].first][1], a[pairs[i].first][2], b[pairs[i].second][0] + (x - l * fx), b[pairs[i].second][1] + (y - l * fy), b[pairs[i].second][2] + (z - l * fz), A - l * fa, B - l * fb, C - l * fc);
300 x -= l * fx; y -= l * fy; z -= l * fz; A -= l * fa; B -= l * fb; C -= l * fc;
301 fx = 0; fy = 0; fz = 0; fa = 0; fb = 0; fc = 0;
304 l *= 0.99; // may be put somewhere l > 0
308 //std::cout << " " << count << "\n";
309 ApplyFit(b, x, y, z, A, B, C);
313 void printPDBtraj(const char* Fname, std::vector< std::vector < RVec > > trj, std::vector< std::vector< std::pair< int, int > > > prs, std::vector< int > ndx) {
314 FILE* a = fopen (Fname, "a");
315 for (int i = 1; i < trj.size(); i++) {
316 fprintf(a, "TITLE test t= %9.5f step= %5d\nMODEL %d\n", (/*float*/double)(i + 1), i + 1, i + 1);
317 for (int j = 0; j < prs.size(); j++) {
318 for (int k = 0; k < prs[j].size(); k++) {
319 fprintf(a, "ATOM %5d CA CA %5d %8.3f%8.3f%8.3f%6.2f%6.2f %4s%2s \n", ndx[prs[j][k].first], ndx[prs[j][k].first], (trj[i][prs[j][k].first][0] * 10), (trj[i][prs[j][k].first][1] * 10), (trj[i][prs[j][k].first][2] * 10), 1.0, 20.0, " ", " ");
322 fprintf(a, "TER\nENDMDL\n");
324 //fprintf(a, "END\n");
328 bool myfunction (const std::vector< std::pair< int, int > > i, const std::vector< std::pair< int, int > > j) {
329 return i.size() < j.size();
332 void domain_reading(SelectionList sList, std::vector< int > ind, std::vector< std::vector < std::pair< int, int > > > &d_ind_num) {
333 d_ind_num.resize(sList.size() - 1);
334 for (int i = 1; i < sList.size(); i++) {
335 d_ind_num[i - 1].resize(0);
336 for (ArrayRef< const int >::iterator ai = sList[i].atomIndices().begin(); (ai < sList[i].atomIndices().end()); ai++) {
337 d_ind_num[i - 1].push_back(std::make_pair(*ai, 0));
341 for (int i = 0; i < d_ind_num.size(); i++) {
343 for (int j = 0; j < d_ind_num[i].size(); j++) {
345 while (ind[k] != d_ind_num[i][j].first) {
348 d_ind_num[i][j].second = k;
352 // its a point of interest as we can either take biggest domains of the given set and work from those or we take them in given order
353 //std::sort(d_ind_num.begin(), d_ind_num.end(), myfunction);
355 for (int i = 0; i < d_ind_num.size(); i++) {
356 if (d_ind_num[i].size() >= 4) {
357 for (int k = 0; k < d_ind_num[i].size(); k++) {
358 for (int j = i + 1; j < d_ind_num.size(); j++) {
359 for (int x = 0; x < d_ind_num[j].size(); x++) {
360 if (d_ind_num[j][x].first == d_ind_num[i][k].first) {
361 d_ind_num[j].erase(d_ind_num[j].begin() + x);
371 void domain_expansion(std::vector< int > indx, std::vector< std::vector < std::pair< int, int > > > &d_ind_num, std::vector< RVec > frame) {
372 std::vector< bool > flag;
373 flag.resize(indx.size(), 1);
374 for (int i = 0; i < d_ind_num.size(); i++) {
375 for (int j = 0; j < d_ind_num[i].size(); j++) {
376 flag[d_ind_num[i][j].second] = 0;
379 /*float*/double dist;
381 for (int i = 0; i < indx.size(); i++) {
384 for (int x1 = 0; x1 < d_ind_num.size(); x1++) {
385 for (int x2 = 0; x2 < d_ind_num[x1].size(); x2++) {
387 dist = (frame[i] - frame[d_ind_num[0][0].first]).norm();
390 if ((frame[i] - frame[d_ind_num[x1][x2].first]).norm() < dist) {
392 dist = (frame[i] - frame[d_ind_num[x1][x2].first]).norm();
396 d_ind_num[x3].push_back(std::make_pair(indx[i], i));
401 void MakeDomainFitPairs(std::vector< std::vector< std::pair< int, int > > > &p, std::vector< std::vector< std::pair< int, int > > > d) {
403 for (int i = 0; i < d.size(); i++) {
405 for (int j = 0; j < d[i].size(); j++) {
406 p[i].push_back(std::make_pair(d[i][j].second, d[i][j].second));
411 void TrajFitting(std::vector< std::vector < RVec > > &trj, double FC, std::vector< std::vector< std::pair< int, int > > > prs) {
413 // its needed to be thought through on whats shared and whats private
414 //#pragma omp parallel for shared(trj, prs, FC)/* private(clone)*/
415 for (int i = 1; i < trj.size()/*2*/; i++) {
416 std::vector< std::vector < RVec > > clone;
418 clone.resize(prs.size(), trj[i]);
419 //std::chrono::time_point<std::chrono::system_clock> now1, now2;
420 for (int j = 0; j < prs.size(); j++) {
421 //now1 = std::chrono::system_clock::now();
422 MyFitNew(trj[0], clone[j], prs[j], FC);
423 //now2 = std::chrono::system_clock::now();
424 //std::cout << " " << std::chrono::duration_cast<std::chrono::milliseconds>(now2 - now1).count() << "\n";
425 for (int k = 0; k < prs[j].size(); k++) {
426 trj[i][prs[j][k].first] = clone[j][prs[j][k].first];
430 //std::cout << "frame " << i << " fitted\n";
434 class Fitng : public TrajectoryAnalysisModule
441 //! Set the options and setting
442 virtual void initOptions(IOptionsContainer *options,
443 TrajectoryAnalysisSettings *settings);
445 //! First routine called by the analysis framework
446 // virtual void initAnalysis(const t_trxframe &fr, t_pbc *pbc);
447 virtual void initAnalysis(const TrajectoryAnalysisSettings &settings,
448 const TopologyInformation &top);
450 virtual void initAfterFirstFrame(const TrajectoryAnalysisSettings &settings,
451 const t_trxframe &fr);
453 //! Call for each frame of the trajectory
454 // virtual void analyzeFrame(const t_trxframe &fr, t_pbc *pbc);
455 virtual void analyzeFrame(int frnr, const t_trxframe &fr, t_pbc *pbc,
456 TrajectoryAnalysisModuleData *pdata);
458 //! Last routine called by the analysis framework
459 // virtual void finishAnalysis(t_pbc *pbc);
460 virtual void finishAnalysis(int nframes);
462 //! Routine to write output, that is additional over the built-in
463 virtual void writeOutput();
468 std::vector< int > index;
470 std::vector< std::vector< std::pair< int, int > > > domains_index_number;
471 std::vector< std::vector < RVec > > trajectory;
472 std::vector< RVec > reference;
474 std::vector< t_trxframe > saved_traj;
476 std::vector< std::vector< std::pair< int, int > > > pairs;
480 std::string OutPutTrjName;
484 Fitng::Fitng(): TrajectoryAnalysisModule()
493 Fitng::initOptions(IOptionsContainer *options,
494 TrajectoryAnalysisSettings *settings)
496 static const char *const desc[] = {
497 "[THISMODULE] to be done"
499 // Add the descriptive text (program help text) to the options
500 settings->setHelpText(desc);
501 // Add option for selecting a subset of atoms
502 //options->addOption(SelectionOption("select")
503 // .store(&selec).required()
504 // .description("Atoms that are considered as part of the excluded volume"));
505 // Add option for selection list
506 options->addOption(SelectionOption("select_residue_and_domains").storeVector(&sel_)
507 .required().dynamicMask().multiValue()
508 .description("Selected group and domains based on it"));
509 // Add option for Fit constant
510 options->addOption(DoubleOption("FitConst")
512 .description("Fitting untill diff <= FitConst, by default == 0.00001"));
513 // Add option for output pdb traj (meh edition)
514 options->addOption(StringOption("trj_out")
515 .store(&OutPutTrjName)
516 .description("transformed trajectory"));
517 // Add option for trajectory Fit transformation
518 options->addOption(IntegerOption("method")
520 .description("1 - fitting all -> all | 2 - keep only domains, all -> all | 3 - keep only domains, domain -> domain | 4 - extend domains to full coverage, domain -> domain"));
521 // Control input settings
522 settings->setFlags(TrajectoryAnalysisSettings::efNoUserPBC);
523 settings->setFlag(TrajectoryAnalysisSettings::efUseTopX);
524 settings->setPBC(true);
527 // /home/toluk/Develop/samples/reca_test_ground/
528 // -s '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.tpr' -f '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.xtc' -sf '/home/toluk/Develop/samples/reca_test_ground/SL0' -n '/home/toluk/Develop/samples/reca_test_ground/t0.ndx' -pdb_out '/home/toluk/Develop/samples/reca_test_ground/FullCAFit.pdb' -e 1000
529 // -s '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.tpr' -f '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.xtc' -sf '/home/toluk/Develop/samples/reca_test_ground/SL2' -n '/home/toluk/Develop/samples/reca_test_ground/t2.ndx' -pdb_out '/home/toluk/Develop/samples/reca_test_ground/CAdomainsFit.pdb' -e 1000 -method 2
530 // -s '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.tpr' -f '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.xtc' -sf '/home/toluk/Develop/samples/reca_test_ground/SL2' -n '/home/toluk/Develop/samples/reca_test_ground/t2.ndx' -pdb_out '/home/toluk/Develop/samples/reca_test_ground/CAdomainsOnlyFit.pdb' -e 1000 -method 3
531 // -s '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.tpr' -f '/home/toluk/Develop/samples/reca_test_ground/reca_rd.mono.xtc' -sf '/home/toluk/Develop/samples/reca_test_ground/SL2' -n '/home/toluk/Develop/samples/reca_test_ground/t2.ndx' -pdb_out '/home/toluk/Develop/samples/reca_test_ground/CAdomainsWExtraOnlyFit.pdb' -e 1000 -method 4
533 // -s '/home/titov_ai/Develop/samples/reca_rd/reca_rd.mono.tpr' -f '/home/titov_ai/Develop/samples/reca_rd/reca_rd.mono.xtc' -sf '/home/titov_ai/Develop/samples/reca_rd/SLCa' -n '/home/titov_ai/Develop/samples/reca_rd/CA.ndx' -pdb_out '/home/titov_ai/Develop/samples/reca_rd/test.xtc' -method 1
535 // -s '/home/titov_ai/BioStore/titov_ai/trp_cage/kv1/trp-cage.pdb' -f '/home/titov_ai/BioStore/titov_ai/trp_cage/kv1/test.xtc' -sf '/home/titov_ai/BioStore/titov_ai/trp_cage/kv1/SLfull' -n '/home/titov_ai/BioStore/titov_ai/trp_cage/kv1/full.ndx' -pdb_out '/home/titov_ai/BioStore/titov_ai/trp_cage/kv1/testfit.xtc' -method 1
537 // -f '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/local_test_trjconvfit_time.xtc' -s '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/trp-cage.pdb' -sf '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/SLfull' -n '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/full.ndx' -pdb_out '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/local_test_prefit_time.xtc' -method 1 -e 500 -FitConst 0.000001
538 // -s '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/trp-cage.pdb' -f '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/test_Done.xtc' -sf '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/SLfull' -n '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/full.ndx' -pdb_out '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/testfit.xtc' -method 1
540 // -s '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/trp-cage.md_npt.tpr' -f '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/test_Done.xtc' -sf '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/SLfull' -n '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/full.ndx' -trj_out '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/testfit.xtc' -method 1 -h
543 // -s '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/trp-cage.md_npt.tpr' -f '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/test1k.xtc' -sf '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/SLfull' -n '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/full.ndx' -trj_out '/home/titov_ai/BioStore/titov_ai/trp_cage/new_try/kv1/local_test/testfit.xtc' -method 1 -h
547 Fitng::initAnalysis(const TrajectoryAnalysisSettings &settings, const TopologyInformation &top)
550 for (ArrayRef< const int >::iterator ai = sel_[0].atomIndices().begin(); (ai < sel_[0].atomIndices().end()); ai++) {
551 index.push_back(*ai);
555 if (top.hasFullTopology()) {
556 for (int i = 0; i < index.size(); i++) {
557 reference.push_back(top.x().at(index[i]));
560 //std::cout << reference.size() << "\n important \n";
562 saved_traj.resize(0);
564 if (sel_.size() > 1 && method >= 2) {
565 domain_reading(sel_, index, domains_index_number);
570 Fitng::initAfterFirstFrame(const TrajectoryAnalysisSettings &settings, const t_trxframe &fr)
572 trajectory.resize(0);
573 std::vector < RVec > a;
575 trajectory.push_back(reference);
576 /*for (int i = 0; i < index.size(); i++) {
577 trajectory[0].push_back(fr.x[index[i]]);
579 trajectory.push_back(a);
583 for (int i = 0; i < index.size(); i++) {
584 pairs[0].push_back(std::make_pair(i, i));
589 for (int i = 0; i < domains_index_number.size(); i++) {
590 for (int j = 0; j < domains_index_number[i].size(); j++) {
591 pairs[0].push_back(std::make_pair(domains_index_number[i][j].second, domains_index_number[i][j].second));
596 MakeDomainFitPairs(pairs, domains_index_number);
599 domain_expansion(index, domains_index_number, trajectory[0]);
600 MakeDomainFitPairs(pairs, domains_index_number);
604 op = open_trx(OutPutTrjName.c_str(), "w+");
608 Fitng::analyzeFrame(int frnr, const t_trxframe &fr, t_pbc *pbc,
609 TrajectoryAnalysisModuleData *pdata)
611 trajectory[1].resize(0);
612 for (int i = 0; i < index.size(); i++) {
613 trajectory[1].push_back(fr.x[index[i]]);
615 TrajFitting(trajectory, FitConst, pairs);
618 for (int i = 0; i < index.size(); i++) {
619 copy_rvec(trajectory[1][i].as_vec(), c.x[index[i]]);
621 //trajectory.push_back(trajectory[1]);
622 if (write_trxframe_indexed(op, static_cast<const t_trxframe *>(&c), index.size(), static_cast<const int *>(&index.front())/*saved_traj[i].index*/, NULL) != 0) {
623 std::cout << "\nFileOutPut error\nframe number = " << frnr << "\n";
626 //printPDBtraj((OutPutTrjName + ".pdb").c_str(), trajectory, pairs, index);
631 Fitng::finishAnalysis(int nframes)
633 std::cout << "\nGame Over\n";
639 //printPDBtraj((OutPutTrjName + ".pdb").c_str(), trajectory, pairs, index);
644 * The main function for the analysis template.
647 main(int argc, char *argv[])
649 return gmx::TrajectoryAnalysisCommandLineRunner::runAsMain<Fitng>(argc, argv);