3 * This source code is part of
7 * GROningen MAchine for Chemical Simulations
10 * Written by David van der Spoel, Erik Lindahl, Berk Hess, and others.
11 * Copyright (c) 1991-2000, University of Groningen, The Netherlands.
12 * Copyright (c) 2001-2004, The GROMACS development team,
13 * check out http://www.gromacs.org for more information.
15 * This program is free software; you can redistribute it and/or
16 * modify it under the terms of the GNU General Public License
17 * as published by the Free Software Foundation; either version 2
18 * of the License, or (at your option) any later version.
20 * If you want to redistribute modifications, please consider that
21 * scientific software is very special. Version control is crucial -
22 * bugs must be traceable. We will be happy to consider code for
23 * inclusion in the official distribution, but derived work must not
24 * be called official GROMACS. Details are found in the README & COPYING
25 * files - if they are missing, get the official version at www.gromacs.org.
27 * To help us fund GROMACS development, we humbly ask that you cite
28 * the papers on the package - you can find them in the top README file.
30 * For more info, check our website at http://www.gromacs.org
33 * Green Red Orange Magenta Azure Cyan Skyblue
55 #include "gmx_fatal.h"
65 void print_stat(rvec
*x
,int natoms
,matrix box
)
69 for(m
=0;(m
<DIM
);m
++) {
73 for(i
=0;(i
<natoms
);i
++) {
75 xmin
[m
]=min(xmin
[m
],x
[i
][m
]);
76 xmax
[m
]=max(xmax
[m
],x
[i
][m
]);
80 fprintf(stderr
,"DIM %d XMIN %8.3f XMAX %8.3f BOX %8.3f\n",
81 m
,xmin
[m
],xmax
[m
],box
[m
][m
]);
85 static gmx_bool
in_box(t_pbc
*pbc
,rvec x
)
90 calc_box_center(ecenterTRIC
,pbc
->box
,box_center
);
92 shift
= pbc_dx_aiuc(pbc
,x
,box_center
,dx
);
94 return (shift
== CENTRAL
);
97 static void mk_vdw(t_atoms
*a
,real rvdw
[],gmx_atomprop_t aps
,
102 /* initialise van der waals arrays of configuration */
103 fprintf(stderr
,"Initialising van der waals distances...\n");
104 for(i
=0; (i
< a
->nr
); i
++)
105 if (!gmx_atomprop_query(aps
,epropVDW
,
106 *(a
->resinfo
[a
->atom
[i
].resind
].name
),
107 *(a
->atomname
[i
]),&(rvdw
[i
])))
108 rvdw
[i
] = r_distance
;
119 void sort_molecule(t_atoms
**atoms_solvt
,rvec
*x
,rvec
*v
,real
*r
)
121 int atnr
,i
,j
,moltp
=0,nrmoltypes
,resi_o
,resi_n
,resnr
;
122 t_moltypes
*moltypes
;
123 t_atoms
*atoms
,*newatoms
;
124 rvec
*newx
, *newv
=NULL
;
127 fprintf(stderr
,"Sorting configuration\n");
129 atoms
= *atoms_solvt
;
131 /* copy each residue from *atoms to a molecule in *molecule */
135 for (i
=0; i
<atoms
->nr
; i
++) {
136 if ( (i
==0) || (atoms
->atom
[i
].resind
!= atoms
->atom
[i
-1].resind
) ) {
137 /* see if this was a molecule type we haven't had yet: */
139 for (j
=0; (j
<nrmoltypes
) && (moltp
==NOTSET
); j
++)
140 if (strcmp(*(atoms
->resinfo
[atoms
->atom
[i
].resind
].name
),
141 moltypes
[j
].name
)==0)
146 srenew(moltypes
,nrmoltypes
);
147 moltypes
[moltp
].name
=*(atoms
->resinfo
[atoms
->atom
[i
].resind
].name
);
149 while ((i
+atnr
<atoms
->nr
) &&
150 (atoms
->atom
[i
].resind
== atoms
->atom
[i
+atnr
].resind
))
152 moltypes
[moltp
].natoms
=atnr
;
153 moltypes
[moltp
].nmol
=0;
155 moltypes
[moltp
].nmol
++;
159 fprintf(stderr
,"Found %d%s molecule type%s:\n",
160 nrmoltypes
,nrmoltypes
==1?"":" different",nrmoltypes
==1?"":"s");
161 for(j
=0; j
<nrmoltypes
; j
++) {
163 moltypes
[j
].res0
= 0;
165 moltypes
[j
].res0
= moltypes
[j
-1].res0
+moltypes
[j
-1].nmol
;
166 fprintf(stderr
,"%7s (%4d atoms): %5d residues\n",
167 moltypes
[j
].name
,moltypes
[j
].natoms
,moltypes
[j
].nmol
);
170 /* if we have only 1 moleculetype, we don't have to sort */
172 /* find out which molecules should go where: */
173 moltypes
[0].i
= moltypes
[0].i0
= 0;
174 for(j
=1; j
<nrmoltypes
; j
++) {
177 moltypes
[j
-1].i0
+moltypes
[j
-1].natoms
*moltypes
[j
-1].nmol
;
180 /* now put them there: */
182 init_t_atoms(newatoms
,atoms
->nr
,FALSE
);
183 newatoms
->nres
=atoms
->nres
;
184 snew(newatoms
->resinfo
,atoms
->nres
);
185 snew(newx
,atoms
->nr
);
186 if (v
) snew(newv
,atoms
->nr
);
187 snew(newr
,atoms
->nr
);
192 for(moltp
=0; moltp
<nrmoltypes
; moltp
++) {
194 while (i
< atoms
->nr
) {
195 resi_o
= atoms
->atom
[i
].resind
;
196 if (strcmp(*atoms
->resinfo
[resi_o
].name
,moltypes
[moltp
].name
) == 0) {
197 /* Copy the residue info */
198 newatoms
->resinfo
[resi_n
] = atoms
->resinfo
[resi_o
];
199 newatoms
->resinfo
[resi_n
].nr
= resnr
;
200 /* Copy the atom info */
202 newatoms
->atom
[j
] = atoms
->atom
[i
];
203 newatoms
->atomname
[j
] = atoms
->atomname
[i
];
204 newatoms
->atom
[j
].resind
= resi_n
;
205 copy_rvec(x
[i
],newx
[j
]);
207 copy_rvec(v
[i
],newv
[j
]);
212 } while (i
< atoms
->nr
&& atoms
->atom
[i
].resind
== resi_o
);
213 /* Increase the new residue counters */
217 /* Skip this residue */
220 } while (i
< atoms
->nr
&& atoms
->atom
[i
].resind
== resi_o
);
225 /* put them back into the original arrays and throw away temporary arrays */
226 sfree(atoms
->atomname
);
227 sfree(atoms
->resinfo
);
230 *atoms_solvt
= newatoms
;
231 for (i
=0; i
<(*atoms_solvt
)->nr
; i
++) {
232 copy_rvec(newx
[i
],x
[i
]);
233 if (v
) copy_rvec(newv
[i
],v
[i
]);
243 void rm_res_pbc(t_atoms
*atoms
, rvec
*x
, matrix box
)
251 for(n
=0; n
<atoms
->nr
; n
++) {
252 if (!is_hydrogen(*(atoms
->atomname
[n
]))) {
256 if ( (n
+1 == atoms
->nr
) ||
257 (atoms
->atom
[n
+1].resind
!= atoms
->atom
[n
].resind
) ) {
258 /* if nat==0 we have only hydrogens in the solvent,
259 we take last coordinate as cg */
264 svmul(1.0/nat
,xcg
,xcg
);
265 for(d
=0; d
<DIM
; d
++) {
267 for(i
=start
; i
<=n
; i
++)
271 while (xcg
[d
]>=box
[d
][d
]) {
272 for(i
=start
; i
<=n
; i
++)
284 static char *insert_mols(const char *mol_insrt
,int nmol_insrt
,int ntry
,int seed
,
285 t_atoms
*atoms
,rvec
**x
,real
**r
,int ePBC
,matrix box
,
286 gmx_atomprop_t aps
,real r_distance
,real rshell
,
287 const output_env_t oenv
)
290 static char *title_insrt
;
297 real alfa
,beta
,gamma
;
301 set_pbc(&pbc
,ePBC
,box
);
303 /* read number of atoms of insert molecules */
304 get_stx_coordnum(mol_insrt
,&atoms_insrt
.nr
);
305 if (atoms_insrt
.nr
== 0)
306 gmx_fatal(FARGS
,"No molecule in %s, please check your input\n",mol_insrt
);
307 /* allocate memory for atom coordinates of insert molecules */
308 snew(x_insrt
,atoms_insrt
.nr
);
309 snew(r_insrt
,atoms_insrt
.nr
);
310 snew(atoms_insrt
.resinfo
,atoms_insrt
.nr
);
311 snew(atoms_insrt
.atomname
,atoms_insrt
.nr
);
312 snew(atoms_insrt
.atom
,atoms_insrt
.nr
);
313 atoms_insrt
.pdbinfo
= NULL
;
314 snew(x_n
,atoms_insrt
.nr
);
315 snew(title_insrt
,STRLEN
);
317 /* read residue number, residue names, atomnames, coordinates etc. */
318 fprintf(stderr
,"Reading molecule configuration \n");
319 read_stx_conf(mol_insrt
,title_insrt
,&atoms_insrt
,x_insrt
,NULL
,
320 &ePBC_insrt
,box_insrt
);
321 fprintf(stderr
,"%s\nContaining %d atoms in %d residue\n",
322 title_insrt
,atoms_insrt
.nr
,atoms_insrt
.nres
);
323 srenew(atoms_insrt
.resinfo
,atoms_insrt
.nres
);
325 /* initialise van der waals arrays of insert molecules */
326 mk_vdw(&atoms_insrt
,r_insrt
,aps
,r_distance
);
328 srenew(atoms
->resinfo
,(atoms
->nres
+nmol_insrt
*atoms_insrt
.nres
));
329 srenew(atoms
->atomname
,(atoms
->nr
+atoms_insrt
.nr
*nmol_insrt
));
330 srenew(atoms
->atom
,(atoms
->nr
+atoms_insrt
.nr
*nmol_insrt
));
331 srenew(*x
,(atoms
->nr
+atoms_insrt
.nr
*nmol_insrt
));
332 srenew(*r
,(atoms
->nr
+atoms_insrt
.nr
*nmol_insrt
));
335 while ((mol
< nmol_insrt
) && (trial
< ntry
*nmol_insrt
)) {
336 fprintf(stderr
,"\rTry %d",trial
++);
337 for (i
=0;(i
<atoms_insrt
.nr
);i
++) {
338 copy_rvec(x_insrt
[i
],x_n
[i
]);
340 alfa
=2*M_PI
*rando(&seed
);
341 beta
=2*M_PI
*rando(&seed
);
342 gamma
=2*M_PI
*rando(&seed
);
343 rotate_conf(atoms_insrt
.nr
,x_n
,NULL
,alfa
,beta
,gamma
);
344 offset_x
[XX
]=box
[XX
][XX
]*rando(&seed
);
345 offset_x
[YY
]=box
[YY
][YY
]*rando(&seed
);
346 offset_x
[ZZ
]=box
[ZZ
][ZZ
]*rando(&seed
);
347 gen_box(0,atoms_insrt
.nr
,x_n
,box_insrt
,offset_x
,TRUE
);
348 if (!in_box(&pbc
,x_n
[0]) || !in_box(&pbc
,x_n
[atoms_insrt
.nr
-1]))
352 add_conf(atoms
,x
,NULL
,r
,FALSE
,ePBC
,box
,TRUE
,
353 &atoms_insrt
,x_n
,NULL
,r_insrt
,FALSE
,rshell
,0,oenv
);
355 if (atoms
->nr
==(atoms_insrt
.nr
+onr
)) {
357 fprintf(stderr
," success (now %d atoms)!",atoms
->nr
);
360 srenew(atoms
->resinfo
, atoms
->nres
);
361 srenew(atoms
->atomname
, atoms
->nr
);
362 srenew(atoms
->atom
, atoms
->nr
);
363 srenew(*x
, atoms
->nr
);
364 srenew(*r
, atoms
->nr
);
366 fprintf(stderr
,"\n");
367 /* print number of molecules added */
368 fprintf(stderr
,"Added %d molecules (out of %d requested) of %s\n",
369 mol
,nmol_insrt
,*atoms_insrt
.resinfo
[0].name
);
374 static void add_solv(const char *fn
,t_atoms
*atoms
,rvec
**x
,rvec
**v
,real
**r
,
376 gmx_atomprop_t aps
,real r_distance
,int *atoms_added
,
377 int *residues_added
,real rshell
,int max_sol
,
378 const output_env_t oenv
)
382 char filename
[STRLEN
];
383 char title_solvt
[STRLEN
];
384 t_atoms
*atoms_solvt
;
385 rvec
*x_solvt
,*v_solvt
=NULL
;
393 strncpy(filename
,lfn
,STRLEN
);
396 get_stx_coordnum(filename
,&(atoms_solvt
->nr
));
397 if (atoms_solvt
->nr
== 0)
398 gmx_fatal(FARGS
,"No solvent in %s, please check your input\n",filename
);
399 snew(x_solvt
,atoms_solvt
->nr
);
400 if (v
) snew(v_solvt
,atoms_solvt
->nr
);
401 snew(r_solvt
,atoms_solvt
->nr
);
402 snew(atoms_solvt
->resinfo
,atoms_solvt
->nr
);
403 snew(atoms_solvt
->atomname
,atoms_solvt
->nr
);
404 snew(atoms_solvt
->atom
,atoms_solvt
->nr
);
405 atoms_solvt
->pdbinfo
= NULL
;
406 fprintf(stderr
,"Reading solvent configuration%s\n",
407 v_solvt
?" and velocities":"");
408 read_stx_conf(filename
,title_solvt
,atoms_solvt
,x_solvt
,v_solvt
,
409 &ePBC_solvt
,box_solvt
);
410 fprintf(stderr
,"\"%s\"\n",title_solvt
);
411 fprintf(stderr
,"solvent configuration contains %d atoms in %d residues\n",
412 atoms_solvt
->nr
,atoms_solvt
->nres
);
413 fprintf(stderr
,"\n");
415 /* apply pbc for solvent configuration for whole molecules */
416 rm_res_pbc(atoms_solvt
,x_solvt
,box_solvt
);
418 /* initialise van der waals arrays of solvent configuration */
419 mk_vdw(atoms_solvt
,r_solvt
,aps
,r_distance
);
421 /* calculate the box multiplication factors n_box[0...DIM] */
423 for (i
=0; (i
< DIM
);i
++) {
425 while (n_box
[i
]*box_solvt
[i
][i
] < box
[i
][i
])
429 fprintf(stderr
,"Will generate new solvent configuration of %dx%dx%d boxes\n",
430 n_box
[XX
],n_box
[YY
],n_box
[ZZ
]);
432 /* realloc atoms_solvt for the new solvent configuration */
433 srenew(atoms_solvt
->resinfo
,atoms_solvt
->nres
*nmol
);
434 srenew(atoms_solvt
->atomname
,atoms_solvt
->nr
*nmol
);
435 srenew(atoms_solvt
->atom
,atoms_solvt
->nr
*nmol
);
436 srenew(x_solvt
,atoms_solvt
->nr
*nmol
);
437 if (v_solvt
) srenew(v_solvt
,atoms_solvt
->nr
*nmol
);
438 srenew(r_solvt
,atoms_solvt
->nr
*nmol
);
440 /* generate a new solvent configuration */
441 genconf(atoms_solvt
,x_solvt
,v_solvt
,r_solvt
,box_solvt
,n_box
);
444 print_stat(x_solvt
,atoms_solvt
->nr
,box_solvt
);
448 print_stat(x_solvt
,atoms_solvt
->nr
,box_solvt
);
450 /* Sort the solvent mixture, not the protein... */
451 sort_molecule(&atoms_solvt
,x_solvt
,v_solvt
,r_solvt
);
453 /* add the two configurations */
456 add_conf(atoms
,x
,v
,r
,TRUE
,ePBC
,box
,FALSE
,
457 atoms_solvt
,x_solvt
,v_solvt
,r_solvt
,TRUE
,rshell
,max_sol
,oenv
);
458 *atoms_added
=atoms
->nr
-onr
;
459 *residues_added
=atoms
->nres
-onres
;
464 fprintf(stderr
,"Generated solvent containing %d atoms in %d residues\n",
465 *atoms_added
,*residues_added
);
468 static char *read_prot(const char *confin
,t_atoms
*atoms
,rvec
**x
,rvec
**v
,
469 real
**r
, int *ePBC
,matrix box
,gmx_atomprop_t aps
,
476 get_stx_coordnum(confin
,&natoms
);
478 /* allocate memory for atom coordinates of configuration 1 */
480 if (v
) snew(*v
,natoms
);
482 init_t_atoms(atoms
,natoms
,FALSE
);
484 /* read residue number, residue names, atomnames, coordinates etc. */
485 fprintf(stderr
,"Reading solute configuration%s\n",v
?" and velocities":"");
486 read_stx_conf(confin
,title
,atoms
,*x
,v
?*v
:NULL
,ePBC
,box
);
487 fprintf(stderr
,"%s\nContaining %d atoms in %d residues\n",
488 title
,atoms
->nr
,atoms
->nres
);
490 /* initialise van der waals arrays of configuration 1 */
491 mk_vdw(atoms
,*r
,aps
,r_distance
);
496 static void update_top(t_atoms
*atoms
,matrix box
,int NFILE
,t_filenm fnm
[],
499 #define TEMP_FILENM "temp.top"
501 char buf
[STRLEN
],buf2
[STRLEN
],*temp
;
502 const char *topinout
;
504 gmx_bool bSystem
,bMolecules
,bSkip
;
509 for(i
=0; (i
<atoms
->nres
); i
++) {
510 /* calculate number of SOLvent molecules */
511 if ( (strcmp(*atoms
->resinfo
[i
].name
,"SOL")==0) ||
512 (strcmp(*atoms
->resinfo
[i
].name
,"WAT")==0) ||
513 (strcmp(*atoms
->resinfo
[i
].name
,"HOH")==0) )
517 for(i
=0; (i
<atoms
->nr
); i
++) {
518 gmx_atomprop_query(aps
,epropMass
,
519 *atoms
->resinfo
[atoms
->atom
[i
].resind
].name
,
520 *atoms
->atomname
[i
],&mm
);
526 fprintf(stderr
,"Volume : %10g (nm^3)\n",vol
);
527 fprintf(stderr
,"Density : %10g (g/l)\n",
528 (mtot
*1e24
)/(AVOGADRO
*vol
));
529 fprintf(stderr
,"Number of SOL molecules: %5d \n\n",nsol
);
531 /* open topology file and append sol molecules */
532 topinout
= ftp2fn(efTOP
,NFILE
,fnm
);
533 if ( ftp2bSet(efTOP
,NFILE
,fnm
) ) {
534 fprintf(stderr
,"Processing topology\n");
535 fpin
= ffopen(topinout
,"r");
536 fpout
= ffopen(TEMP_FILENM
,"w");
538 bSystem
= bMolecules
= FALSE
;
539 while (fgets(buf
, STRLEN
, fpin
)) {
543 if ((temp
=strchr(buf2
,'\n')) != NULL
)
548 if ((temp
=strchr(buf2
,'\n')) != NULL
)
551 if (buf2
[strlen(buf2
)-1]==']') {
552 buf2
[strlen(buf2
)-1]='\0';
555 bSystem
=(gmx_strcasecmp(buf2
,"system")==0);
556 bMolecules
=(gmx_strcasecmp(buf2
,"molecules")==0);
558 } else if (bSystem
&& nsol
&& (buf
[0]!=';') ) {
559 /* if sol present, append "in water" to system name */
561 if (buf2
[0] && (!strstr(buf2
," water")) ) {
562 sprintf(buf
,"%s in water\n",buf2
);
565 } else if (bMolecules
) {
566 /* check if this is a line with solvent molecules */
567 sscanf(buf
,"%s",buf2
);
568 if (strcmp(buf2
,"SOL")==0) {
569 sscanf(buf
,"%*s %d",&i
);
578 if ((temp
=strchr(buf
,'\n')) != NULL
)
580 fprintf(stdout
,"Removing line #%d '%s' from topology file (%s)\n",
583 fprintf(fpout
,"%s",buf
);
587 fprintf(stdout
,"Adding line for %d solvent molecules to "
588 "topology file (%s)\n",nsol
,topinout
);
589 fprintf(fpout
,"%-15s %5d\n","SOL",nsol
);
592 /* use ffopen to generate backup of topinout */
593 fpout
=ffopen(topinout
,"w");
595 rename(TEMP_FILENM
,topinout
);
600 int gmx_genbox(int argc
,char *argv
[])
602 const char *desc
[] = {
603 "Genbox can do one of 3 things:[PAR]",
605 "1) Generate a box of solvent. Specify -cs and -box. Or specify -cs and",
606 "-cp with a structure file with a box, but without atoms.[PAR]",
608 "2) Solvate a solute configuration, eg. a protein, in a bath of solvent ",
609 "molecules. Specify [TT]-cp[tt] (solute) and [TT]-cs[tt] (solvent). ",
610 "The box specified in the solute coordinate file ([TT]-cp[tt]) is used,",
611 "unless [TT]-box[tt] is set.",
612 "If you want the solute to be centered in the box,",
613 "the program [TT]editconf[tt] has sophisticated options",
614 "to change the box dimensions and center the solute.",
615 "Solvent molecules are removed from the box where the ",
616 "distance between any atom of the solute molecule(s) and any atom of ",
617 "the solvent molecule is less than the sum of the VanderWaals radii of ",
618 "both atoms. A database ([TT]vdwradii.dat[tt]) of VanderWaals radii is ",
619 "read by the program, atoms not in the database are ",
620 "assigned a default distance [TT]-vdwd[tt].",
621 "Note that this option will also influence the distances between",
622 "solvent molecules if they contain atoms that are not in the database.",
625 "3) Insert a number ([TT]-nmol[tt]) of extra molecules ([TT]-ci[tt]) ",
626 "at random positions.",
627 "The program iterates until [TT]nmol[tt] molecules",
628 "have been inserted in the box. To test whether an insertion is ",
629 "successful the same VanderWaals criterium is used as for removal of ",
630 "solvent molecules. When no appropriately ",
631 "sized holes (holes that can hold an extra molecule) are available the ",
632 "program tries for [TT]-nmol[tt] * [TT]-try[tt] times before giving up. ",
633 "Increase -try if you have several small holes to fill.[PAR]",
635 "The default solvent is Simple Point Charge water (SPC), with coordinates ",
636 "from [TT]$GMXLIB/spc216.gro[tt]. These coordinates can also be used",
637 "for other 3-site water models, since a short equibilibration will remove",
638 "the small differences between the models.",
639 "Other solvents are also supported, as well as mixed solvents. The",
640 "only restriction to solvent types is that a solvent molecule consists",
641 "of exactly one residue. The residue information in the coordinate",
642 "files is used, and should therefore be more or less consistent.",
643 "In practice this means that two subsequent solvent molecules in the ",
644 "solvent coordinate file should have different residue number.",
645 "The box of solute is built by stacking the coordinates read from",
646 "the coordinate file. This means that these coordinates should be ",
647 "equlibrated in periodic boundary conditions to ensure a good",
648 "alignment of molecules on the stacking interfaces.",
649 "The [TT]-maxsol[tt] option simply adds only the first [TT]-maxsol[tt]",
650 "solvent molecules and leaves out the rest would have fit into the box.",
653 "The program can optionally rotate the solute molecule to align the",
654 "longest molecule axis along a box edge. This way the amount of solvent",
655 "molecules necessary is reduced.",
656 "It should be kept in mind that this only works for",
657 "short simulations, as eg. an alpha-helical peptide in solution can ",
658 "rotate over 90 degrees, within 500 ps. In general it is therefore ",
659 "better to make a more or less cubic box.[PAR]",
661 "Setting -shell larger than zero will place a layer of water of",
662 "the specified thickness (nm) around the solute. Hint: it is a good",
663 "idea to put the protein in the center of a box first (using editconf).",
666 "Finally, genbox will optionally remove lines from your topology file in ",
667 "which a number of solvent molecules is already added, and adds a ",
668 "line with the total number of solvent molecules in your coordinate file."
671 const char *bugs
[] = {
672 "Molecules must be whole in the initial configurations.",
676 gmx_bool bSol
,bProt
,bBox
;
677 const char *conf_prot
,*confout
;
683 /* protein configuration data */
691 /* other data types */
692 int atoms_added
,residues_added
;
695 { efSTX
, "-cp", "protein", ffOPTRD
},
696 { efSTX
, "-cs", "spc216", ffLIBOPTRD
},
697 { efSTX
, "-ci", "insert", ffOPTRD
},
698 { efSTO
, NULL
, NULL
, ffWRITE
},
699 { efTOP
, NULL
, NULL
, ffOPTRW
},
701 #define NFILE asize(fnm)
703 static int nmol_ins
=0,nmol_try
=10,seed
=1997;
704 static real r_distance
=0.105,r_shell
=0;
705 static rvec new_box
={0.0,0.0,0.0};
706 static gmx_bool bReadV
=FALSE
;
707 static int max_sol
= 0;
710 { "-box", FALSE
, etRVEC
, {new_box
},
712 { "-nmol", FALSE
, etINT
, {&nmol_ins
},
713 "no of extra molecules to insert" },
714 { "-try", FALSE
, etINT
, {&nmol_try
},
715 "try inserting -nmol*-try times" },
716 { "-seed", FALSE
, etINT
, {&seed
},
717 "random generator seed"},
718 { "-vdwd", FALSE
, etREAL
, {&r_distance
},
719 "default vdwaals distance"},
720 { "-shell", FALSE
, etREAL
, {&r_shell
},
721 "thickness of optional water layer around solute" },
722 { "-maxsol", FALSE
, etINT
, {&max_sol
},
723 "maximum number of solvent molecules to add if they fit in the box. If zero (default) this is ignored" },
724 { "-vel", FALSE
, etBOOL
, {&bReadV
},
725 "keep velocities from input solute and solvent" }
728 CopyRight(stderr
,argv
[0]);
729 parse_common_args(&argc
,argv
, PCA_BE_NICE
,NFILE
,fnm
,asize(pa
),pa
,
730 asize(desc
),desc
,asize(bugs
),bugs
,&oenv
);
732 bInsert
= opt2bSet("-ci",NFILE
,fnm
) && (nmol_ins
> 0);
733 bSol
= opt2bSet("-cs",NFILE
,fnm
);
734 bProt
= opt2bSet("-cp",NFILE
,fnm
);
735 bBox
= opt2parg_bSet("-box",asize(pa
),pa
);
738 if (bInsert
&& nmol_ins
<=0)
739 gmx_fatal(FARGS
,"When specifying inserted molecules (-ci), "
740 "-nmol must be larger than 0");
742 gmx_fatal(FARGS
,"When no solute (-cp) is specified, "
743 "a box size (-box) must be specified");
745 aps
= gmx_atomprop_init();
748 /*generate a solute configuration */
749 conf_prot
= opt2fn("-cp",NFILE
,fnm
);
750 title
= read_prot(conf_prot
,&atoms
,&x
,bReadV
?&v
:NULL
,&r
,&ePBC
,box
,
753 fprintf(stderr
,"Note: no velocities found\n");
755 fprintf(stderr
,"Note: no atoms in %s\n",conf_prot
);
772 box
[XX
][XX
]=new_box
[XX
];
773 box
[YY
][YY
]=new_box
[YY
];
774 box
[ZZ
][ZZ
]=new_box
[ZZ
];
777 gmx_fatal(FARGS
,"Undefined solute box.\nCreate one with editconf "
778 "or give explicit -box command line option");
780 /* add nmol_ins molecules of atoms_ins
781 in random orientation at random place */
783 title_ins
= insert_mols(opt2fn("-ci",NFILE
,fnm
),nmol_ins
,nmol_try
,seed
,
784 &atoms
,&x
,&r
,ePBC
,box
,aps
,r_distance
,r_shell
,
787 title_ins
= strdup("Generated by genbox");
791 add_solv(opt2fn("-cs",NFILE
,fnm
),&atoms
,&x
,v
?&v
:NULL
,&r
,ePBC
,box
,
792 aps
,r_distance
,&atoms_added
,&residues_added
,r_shell
,max_sol
,
795 /* write new configuration 1 to file confout */
796 confout
= ftp2fn(efSTO
,NFILE
,fnm
);
797 fprintf(stderr
,"Writing generated configuration to %s\n",confout
);
799 write_sto_conf(confout
,title
,&atoms
,x
,v
,ePBC
,box
);
800 /* print box sizes and box type to stderr */
801 fprintf(stderr
,"%s\n",title
);
803 write_sto_conf(confout
,title_ins
,&atoms
,x
,v
,ePBC
,box
);
805 /* print size of generated configuration */
806 fprintf(stderr
,"\nOutput configuration contains %d atoms in %d residues\n",
807 atoms
.nr
,atoms
.nres
);
808 update_top(&atoms
,box
,NFILE
,fnm
,aps
);
810 gmx_atomprop_destroy(aps
);