ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE-1.0/utils/sysbuilder/MoLocator.cpp
Revision: 1435
Committed: Thu Jul 29 18:16:16 2004 UTC (19 years, 11 months ago) by tim
File size: 4410 byte(s)
Log Message:
working version of simpleBuilder

File Contents

# Content
1 #include <iostream>
2
3 #include <cstdlib>
4 #include <cmath>
5
6 #include "simError.h"
7 #include "MoLocator.hpp"
8 #include "MatVec3.h"
9
10 MoLocator::MoLocator( MoleculeStamp* theStamp, ForceFields* theFF){
11
12 myStamp = theStamp;
13 myFF = theFF;
14 nIntegrableObjects = myStamp->getNIntegrable();
15 calcRefCoords();
16 }
17
18 void MoLocator::placeMol( const Vector3d& offset, const Vector3d& ort, Molecule* mol){
19 Vector3d newCoor;
20 Vector3d velocity(0.0, 0.0, 0.0);
21 Vector3d angMomentum(0.0, 0.0, 0.0);
22 double quaternion[4];
23 vector<StuntDouble*> myIntegrableObjects;
24 double rotMat[3][3];
25
26 quaternion[0] = 1.0;
27 quaternion[1] = 0.0;
28 quaternion[2] = 0.0;
29 quaternion[3] = 0.0;
30
31 latVec2RotMat(ort, rotMat);
32
33 myIntegrableObjects = mol->getIntegrableObjects();
34
35 if(myIntegrableObjects.size() != nIntegrableObjects){
36 sprintf( painCave.errMsg,
37 "MoLocator error.\n"
38 " The number of integrable objects of MoleculeStamp is not the same as that of Molecule\n");
39 painCave.isFatal = 1;
40 simError();
41
42 }
43
44 for(int i=0; i<nIntegrableObjects; i++) {
45
46 //calculate the reference coordinate for integrable objects after rotation
47 matVecMul3(rotMat, refCoords[i].vec, newCoor.vec);
48 newCoor += offset;
49
50 myIntegrableObjects[i]->setPos( newCoor.vec);
51 myIntegrableObjects[i]->setVel(velocity.vec);
52
53 if(myIntegrableObjects[i]->isDirectional()){
54 myIntegrableObjects[i]->setA(rotMat);
55 myIntegrableObjects[i]->setJ(angMomentum.vec);
56 }
57 }
58
59 }
60
61 void MoLocator::calcRefCoords( void ){
62 AtomStamp* currAtomStamp;
63 int nAtoms;
64 int nRigidBodies;
65 vector<double> mass;
66 Vector3d coor;
67 Vector3d refMolCom;
68 int nAtomsInRb;
69 double totMassInRb;
70 double currAtomMass;
71 double molMass;
72
73 nAtoms= myStamp->getNAtoms();
74 nRigidBodies = myStamp->getNRigidBodies();
75
76 for(size_t i=0; i<nAtoms; i++){
77
78 currAtomStamp = myStamp->getAtom(i);
79
80 if( !currAtomStamp->havePosition() ){
81 sprintf( painCave.errMsg,
82 "MoLocator error.\n"
83 " Component %s, atom %s does not have a position specified.\n"
84 " This means MoLocator cannot initalize it's position.\n",
85 myStamp->getID(),
86 currAtomStamp->getType() );
87
88 painCave.isFatal = 1;
89 simError();
90 }
91
92 //if atom belongs to rigidbody, just skip it
93 if(myStamp->isAtomInRigidBody(i))
94 continue;
95 //get mass and the reference coordinate
96 else{
97 currAtomMass = myFF->getAtomTypeMass(currAtomStamp->getType());
98 mass.push_back(currAtomMass);
99 coor.x = currAtomStamp->getPosX();
100 coor.y = currAtomStamp->getPosY();
101 coor.z = currAtomStamp->getPosZ();
102 refCoords.push_back(coor);
103
104 }
105 }
106
107 for(int i = 0; i < nRigidBodies; i++){
108 coor.x = 0;
109 coor.y = 0;
110 coor.z = 0;
111 totMassInRb = 0;
112
113 for(int j = 0; j < nAtomsInRb; j++){
114
115 currAtomMass = myFF->getAtomTypeMass(currAtomStamp->getType());
116 totMassInRb += currAtomMass;
117
118 coor.x += currAtomStamp->getPosX() * currAtomMass;
119 coor.y += currAtomStamp->getPosY() * currAtomMass;
120 coor.z += currAtomStamp->getPosZ() * currAtomMass;
121 }
122
123 mass.push_back(totMassInRb);
124 coor /= totMassInRb;
125 refCoords.push_back(coor);
126 }
127
128
129 //calculate the reference center of mass
130 molMass = 0;
131 refMolCom.x = 0;
132 refMolCom.y = 0;
133 refMolCom.z = 0;
134
135 for(int i = 0; i < nIntegrableObjects; i++){
136 refMolCom += refCoords[i] * mass[i];
137 molMass += mass[i];
138 }
139
140 refMolCom /= molMass;
141
142 //move the reference center of mass to (0,0,0) and adjust the reference coordinate
143 //of the integrabel objects
144 for(int i = 0; i < nIntegrableObjects; i++)
145 refCoords[i] -= refMolCom;
146 }
147
148
149 void latVec2RotMat(const Vector3d& lv, double rotMat[3][3]){
150
151 double theta, phi, psi;
152
153 theta =acos(lv.z);
154 phi = atan2(lv.y, lv.x);
155 psi = 0;
156
157 rotMat[0][0] = (cos(phi) * cos(psi)) - (sin(phi) * cos(theta) * sin(psi));
158 rotMat[0][1] = (sin(phi) * cos(psi)) + (cos(phi) * cos(theta) * sin(psi));
159 rotMat[0][2] = sin(theta) * sin(psi);
160
161 rotMat[1][0] = -(cos(phi) * sin(psi)) - (sin(phi) * cos(theta) * cos(psi));
162 rotMat[1][1] = -(sin(phi) * sin(psi)) + (cos(phi) * cos(theta) * cos(psi));
163 rotMat[1][2] = sin(theta) * cos(psi);
164
165 rotMat[2][0] = sin(phi) * sin(theta);
166 rotMat[2][1] = -cos(phi) * sin(theta);
167 rotMat[2][2] = cos(theta);
168 }
169