ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE-3.0/src/math/Quaternion.hpp
Revision: 1930
Committed: Wed Jan 12 22:41:40 2005 UTC (19 years, 5 months ago) by gezelter
File size: 12420 byte(s)
Log Message:
merging new_design branch into OOPSE-2.0

File Contents

# User Rev Content
1 gezelter 1930 /*
2     * Copyright (c) 2005 The University of Notre Dame. All Rights Reserved.
3 tim 1585 *
4 gezelter 1930 * The University of Notre Dame grants you ("Licensee") a
5     * non-exclusive, royalty free, license to use, modify and
6     * redistribute this software in source and binary code form, provided
7     * that the following conditions are met:
8     *
9     * 1. Acknowledgement of the program authors must be made in any
10     * publication of scientific results based in part on use of the
11     * program. An acceptable form of acknowledgement is citation of
12     * the article in which the program was described (Matthew
13     * A. Meineke, Charles F. Vardeman II, Teng Lin, Christopher
14     * J. Fennell and J. Daniel Gezelter, "OOPSE: An Object-Oriented
15     * Parallel Simulation Engine for Molecular Dynamics,"
16     * J. Comput. Chem. 26, pp. 252-271 (2005))
17     *
18     * 2. Redistributions of source code must retain the above copyright
19     * notice, this list of conditions and the following disclaimer.
20     *
21     * 3. Redistributions in binary form must reproduce the above copyright
22     * notice, this list of conditions and the following disclaimer in the
23     * documentation and/or other materials provided with the
24     * distribution.
25     *
26     * This software is provided "AS IS," without a warranty of any
27     * kind. All express or implied conditions, representations and
28     * warranties, including any implied warranty of merchantability,
29     * fitness for a particular purpose or non-infringement, are hereby
30     * excluded. The University of Notre Dame and its licensors shall not
31     * be liable for any damages suffered by licensee as a result of
32     * using, modifying or distributing the software or its
33     * derivatives. In no event will the University of Notre Dame or its
34     * licensors be liable for any lost revenue, profit or data, or for
35     * direct, indirect, special, consequential, incidental or punitive
36     * damages, however caused and regardless of the theory of liability,
37     * arising out of the use of or inability to use software, even if the
38     * University of Notre Dame has been advised of the possibility of
39     * such damages.
40 tim 1585 */
41 gezelter 1930
42 tim 1585 /**
43     * @file Quaternion.hpp
44     * @author Teng Lin
45     * @date 10/11/2004
46     * @version 1.0
47     */
48    
49     #ifndef MATH_QUATERNION_HPP
50     #define MATH_QUATERNION_HPP
51    
52 tim 1586 #include "math/Vector.hpp"
53 tim 1603 #include "math/SquareMatrix.hpp"
54 tim 1586
55 tim 1585 namespace oopse{
56    
57     /**
58     * @class Quaternion Quaternion.hpp "math/Quaternion.hpp"
59 tim 1586 * Quaternion is a sort of a higher-level complex number.
60     * It is defined as Q = w + x*i + y*j + z*k,
61     * where w, x, y, and z are numbers of type T (e.g. double), and
62     * i*i = -1; j*j = -1; k*k = -1;
63     * i*j = k; j*k = i; k*i = j;
64 tim 1585 */
65     template<typename Real>
66     class Quaternion : public Vector<Real, 4> {
67 tim 1586 public:
68 tim 1603 Quaternion() : Vector<Real, 4>() {}
69 tim 1585
70 tim 1586 /** Constructs and initializes a Quaternion from w, x, y, z values */
71     Quaternion(Real w, Real x, Real y, Real z) {
72     data_[0] = w;
73     data_[1] = x;
74     data_[2] = y;
75     data_[3] = z;
76     }
77    
78 tim 1603 /** Constructs and initializes a Quaternion from a Vector<Real,4> */
79 tim 1586 Quaternion(const Vector<Real,4>& v)
80     : Vector<Real, 4>(v){
81     }
82 tim 1585
83 tim 1603 /** copy assignment */
84 tim 1586 Quaternion& operator =(const Vector<Real, 4>& v){
85     if (this == & v)
86     return *this;
87    
88     Vector<Real, 4>::operator=(v);
89    
90     return *this;
91     }
92    
93     /**
94     * Returns the value of the first element of this quaternion.
95     * @return the value of the first element of this quaternion
96     */
97     Real w() const {
98     return data_[0];
99     }
100    
101     /**
102     * Returns the reference of the first element of this quaternion.
103     * @return the reference of the first element of this quaternion
104     */
105     Real& w() {
106     return data_[0];
107     }
108    
109     /**
110     * Returns the value of the first element of this quaternion.
111     * @return the value of the first element of this quaternion
112     */
113     Real x() const {
114     return data_[1];
115     }
116    
117     /**
118     * Returns the reference of the second element of this quaternion.
119     * @return the reference of the second element of this quaternion
120     */
121     Real& x() {
122     return data_[1];
123     }
124    
125     /**
126     * Returns the value of the thirf element of this quaternion.
127     * @return the value of the third element of this quaternion
128     */
129     Real y() const {
130     return data_[2];
131     }
132    
133     /**
134     * Returns the reference of the third element of this quaternion.
135     * @return the reference of the third element of this quaternion
136     */
137     Real& y() {
138     return data_[2];
139     }
140    
141     /**
142     * Returns the value of the fourth element of this quaternion.
143     * @return the value of the fourth element of this quaternion
144     */
145     Real z() const {
146     return data_[3];
147     }
148     /**
149     * Returns the reference of the fourth element of this quaternion.
150     * @return the reference of the fourth element of this quaternion
151     */
152     Real& z() {
153     return data_[3];
154     }
155    
156     /**
157 tim 1603 * Tests if this quaternion is equal to other quaternion
158     * @return true if equal, otherwise return false
159     * @param q quaternion to be compared
160     */
161     inline bool operator ==(const Quaternion<Real>& q) {
162    
163     for (unsigned int i = 0; i < 4; i ++) {
164     if (!equal(data_[i], q[i])) {
165     return false;
166     }
167     }
168    
169     return true;
170     }
171    
172     /**
173 tim 1586 * Returns the inverse of this quaternion
174     * @return inverse
175     * @note since quaternion is a complex number, the inverse of quaternion
176     * q = w + xi + yj+ zk is inv_q = (w -xi - yj - zk)/(|q|^2)
177     */
178 tim 1603 Quaternion<Real> inverse() {
179 tim 1586 Quaternion<Real> q;
180 tim 1603 Real d = this->lengthSquare();
181 tim 1586
182     q.w() = w() / d;
183     q.x() = -x() / d;
184     q.y() = -y() / d;
185     q.z() = -z() / d;
186    
187     return q;
188     }
189    
190     /**
191     * Sets the value to the multiplication of itself and another quaternion
192     * @param q the other quaternion
193     */
194     void mul(const Quaternion<Real>& q) {
195 tim 1603 Quaternion<Real> tmp(*this);
196 tim 1586
197 tim 1603 data_[0] = (tmp[0]*q[0]) -(tmp[1]*q[1]) - (tmp[2]*q[2]) - (tmp[3]*q[3]);
198     data_[1] = (tmp[0]*q[1]) + (tmp[1]*q[0]) + (tmp[2]*q[3]) - (tmp[3]*q[2]);
199     data_[2] = (tmp[0]*q[2]) + (tmp[2]*q[0]) + (tmp[3]*q[1]) - (tmp[1]*q[3]);
200     data_[3] = (tmp[0]*q[3]) + (tmp[3]*q[0]) + (tmp[1]*q[2]) - (tmp[2]*q[1]);
201     }
202 tim 1586
203 tim 1603 void mul(const Real& s) {
204     data_[0] *= s;
205     data_[1] *= s;
206     data_[2] *= s;
207     data_[3] *= s;
208 tim 1586 }
209    
210     /** Set the value of this quaternion to the division of itself by another quaternion */
211 tim 1603 void div(Quaternion<Real>& q) {
212 tim 1586 mul(q.inverse());
213     }
214 tim 1603
215     void div(const Real& s) {
216     data_[0] /= s;
217     data_[1] /= s;
218     data_[2] /= s;
219     data_[3] /= s;
220     }
221 tim 1586
222     Quaternion<Real>& operator *=(const Quaternion<Real>& q) {
223     mul(q);
224     return *this;
225     }
226 tim 1603
227     Quaternion<Real>& operator *=(const Real& s) {
228     mul(s);
229 tim 1586 return *this;
230     }
231    
232 tim 1603 Quaternion<Real>& operator /=(Quaternion<Real>& q) {
233     *this *= q.inverse();
234     return *this;
235     }
236    
237     Quaternion<Real>& operator /=(const Real& s) {
238     div(s);
239     return *this;
240     }
241 tim 1586 /**
242     * Returns the conjugate quaternion of this quaternion
243     * @return the conjugate quaternion of this quaternion
244     */
245     Quaternion<Real> conjugate() {
246     return Quaternion<Real>(w(), -x(), -y(), -z());
247     }
248    
249     /**
250     * Returns the corresponding rotation matrix (3x3)
251     * @return a 3x3 rotation matrix
252     */
253 tim 1592 SquareMatrix<Real, 3> toRotationMatrix3() {
254     SquareMatrix<Real, 3> rotMat3;
255 tim 1586
256     Real w2;
257     Real x2;
258     Real y2;
259     Real z2;
260    
261     if (!isNormalized())
262     normalize();
263    
264     w2 = w() * w();
265     x2 = x() * x();
266     y2 = y() * y();
267     z2 = z() * z();
268    
269     rotMat3(0, 0) = w2 + x2 - y2 - z2;
270     rotMat3(0, 1) = 2.0 * ( x() * y() + w() * z() );
271     rotMat3(0, 2) = 2.0 * ( x() * z() - w() * y() );
272    
273     rotMat3(1, 0) = 2.0 * ( x() * y() - w() * z() );
274     rotMat3(1, 1) = w2 - x2 + y2 - z2;
275     rotMat3(1, 2) = 2.0 * ( y() * z() + w() * x() );
276    
277     rotMat3(2, 0) = 2.0 * ( x() * z() + w() * y() );
278     rotMat3(2, 1) = 2.0 * ( y() * z() - w() * x() );
279     rotMat3(2, 2) = w2 - x2 -y2 +z2;
280 tim 1603
281     return rotMat3;
282 tim 1586 }
283    
284     };//end Quaternion
285    
286 tim 1603
287 tim 1586 /**
288 tim 1603 * Returns the vaule of scalar multiplication of this quaterion q (q * s).
289     * @return the vaule of scalar multiplication of this vector
290     * @param q the source quaternion
291     * @param s the scalar value
292     */
293     template<typename Real, unsigned int Dim>
294     Quaternion<Real> operator * ( const Quaternion<Real>& q, Real s) {
295     Quaternion<Real> result(q);
296     result.mul(s);
297     return result;
298     }
299    
300     /**
301     * Returns the vaule of scalar multiplication of this quaterion q (q * s).
302     * @return the vaule of scalar multiplication of this vector
303     * @param s the scalar value
304     * @param q the source quaternion
305     */
306     template<typename Real, unsigned int Dim>
307     Quaternion<Real> operator * ( const Real& s, const Quaternion<Real>& q ) {
308     Quaternion<Real> result(q);
309     result.mul(s);
310     return result;
311     }
312    
313     /**
314 tim 1586 * Returns the multiplication of two quaternion
315     * @return the multiplication of two quaternion
316     * @param q1 the first quaternion
317     * @param q2 the second quaternion
318     */
319     template<typename Real>
320     inline Quaternion<Real> operator *(const Quaternion<Real>& q1, const Quaternion<Real>& q2) {
321     Quaternion<Real> result(q1);
322     result *= q2;
323     return result;
324     }
325    
326     /**
327     * Returns the division of two quaternion
328     * @param q1 divisor
329     * @param q2 dividen
330     */
331    
332     template<typename Real>
333 tim 1603 inline Quaternion<Real> operator /( Quaternion<Real>& q1, Quaternion<Real>& q2) {
334 tim 1586 return q1 * q2.inverse();
335     }
336    
337     /**
338     * Returns the value of the division of a scalar by a quaternion
339     * @return the value of the division of a scalar by a quaternion
340     * @param s scalar
341     * @param q quaternion
342     * @note for a quaternion q, 1/q = q.inverse()
343     */
344     template<typename Real>
345 tim 1603 Quaternion<Real> operator /(const Real& s, Quaternion<Real>& q) {
346 tim 1586
347 tim 1603 Quaternion<Real> x;
348     x = q.inverse();
349     x *= s;
350     return x;
351 tim 1586 }
352 tim 1603
353     template <class T>
354     inline bool operator==(const Quaternion<T>& lhs, const Quaternion<T>& rhs) {
355     return equal(lhs[0] ,rhs[0]) && equal(lhs[1] , rhs[1]) && equal(lhs[2], rhs[2]) && equal(lhs[3], rhs[3]);
356     }
357    
358 tim 1586 typedef Quaternion<double> Quat4d;
359 tim 1585 }
360     #endif //MATH_QUATERNION_HPP

Properties

Name Value
svn:executable *