opennurbs_quaternion.h
1 /* $NoKeywords: $ */
2 /*
3 //
4 // Copyright (c) 1993-2012 Robert McNeel & Associates. All rights reserved.
5 // OpenNURBS, Rhinoceros, and Rhino3D are registered trademarks of Robert
6 // McNeel & Associates.
7 //
8 // THIS SOFTWARE IS PROVIDED "AS IS" WITHOUT EXPRESS OR IMPLIED WARRANTY.
9 // ALL IMPLIED WARRANTIES OF FITNESS FOR ANY PARTICULAR PURPOSE AND OF
10 // MERCHANTABILITY ARE HEREBY DISCLAIMED.
11 //
12 // For complete openNURBS copyright information see <http://www.opennurbs.org>.
13 //
14 ////////////////////////////////////////////////////////////////
15 */
16 
17 #if !defined(ON_QUATERNION_INC_)
18 #define ON_QUATERNION_INC_
19 
20 class ON_CLASS ON_Quaternion
21 {
22 public:
23  // quaternion = a + bi + cj + dk
24  double a,b,c,d;
25 
26  static const ON_Quaternion Zero; // 0 = (0,0,0,0
27  static const ON_Quaternion Identity; // 1 = (1,0,0,0)
28  static const ON_Quaternion I; // "i" = (0,1,0,0)
29  static const ON_Quaternion J; // "j" = (0,0,1,0)
30  static const ON_Quaternion K; // "k" = (0,0,0,1)
31 
33 
34  ON_Quaternion(double qa, double qb, double qc, double qd);
35 
36  // (a,b,c,d) = (0,v.x,v.y,v.z)
37  ON_Quaternion(const ON_3dVector& v);
38 
39  // (a,b,c,d) = (0,v.x,v.y,v.z)
40  ON_Quaternion& operator=(const ON_3dVector& v);
41 
42  void Set(double qa, double qb, double qc, double qd);
43 
44  // arithmetic operators
45  ON_Quaternion operator*(int) const;
46  ON_Quaternion operator/(int) const;
47  ON_Quaternion operator*(float) const;
48  ON_Quaternion operator/(float) const;
49  ON_Quaternion operator*(double) const;
50  ON_Quaternion operator/(double) const;
51 
52  ON_Quaternion operator+(const ON_Quaternion&) const;
53  ON_Quaternion operator-(const ON_Quaternion&) const;
54 
55  // quaternion multiplication is not commutative
56  ON_Quaternion operator*(const ON_Quaternion&) const;
57 
58  /*
59  Returns:
60  True if a, b, c, and d are valid finite IEEE doubles.
61  */
62  bool IsValid() const;
63 
64  /*
65  Description:
66  Returns the conjugate of the quaternion = (a,-b,-c,-d).
67  */
68  ON_Quaternion Conjugate() const;
69 
70  /*
71  Description:
72  Sets the quaternion to a/L2, -b/L2, -c/L2, -d/L2,
73  where L2 = length squared = (a*a + b*b + c*c + d*d).
74  This is the multiplicative inverse, i.e.,
75  (a,b,c,d)*(a/L2, -b/L2, -c/L2, -d/L2) = (1,0,0,0).
76  Returns:
77  True if successful. False if the quaternion is zero
78  and cannot be inverted.
79  */
80  bool Invert();
81 
82  /*
83  Returns:
84  Sets the quaternion to a/L2, -b/L2, -c/L2, -d/L2,
85  where L2 = length squared = (a*a + b*b + c*c + d*d).
86  This is the multiplicative inverse, i.e.,
87  (a,b,c,d)*(a/L2, -b/L2, -c/L2, -d/L2) = (1,0,0,0).
88  If "this" is the zero quaternion, then the zero quaternion
89  is returned.
90  */
91  ON_Quaternion Inverse() const;
92 
93  /*
94  Returns:
95  Returns the length or norm of the quaternion
96  sqrt(a*a + b*b + c*c + d*d).
97  */
98  double Length() const;
99 
100  /*
101  Returns:
102  Returns a*a + b*b + c*c + d*d.
103  */
104  double LengthSquared() const;
105 
106  /*
107  Returns:
108  The distance or norm of the difference between the two quaternions.
109  = ("this" - q).Length().
110  */
111  double DistanceTo(const ON_Quaternion& q) const;
112 
113  /*
114  Returns:
115  The distance or norm of the difference between the two quaternions.
116  = (p - q).Length().
117  */
118  static double Distance(const ON_Quaternion& p, const ON_Quaternion& q);
119 
120  /*
121  Returns:
122  4x4 real valued matrix form of the quaternion
123 
124  a b c d
125  -b a -d c
126  -c d a -b
127  -d -c b a
128 
129  which has the same arithmetic properties in as the
130  quaternion.
131  Remarks:
132  Do not confuse this with the rotation defined
133  by the quaternion. This function will only be interesting
134  to math nerds and is not useful in rendering or animation
135  applications.
136  */
137  ON_Xform MatrixForm() const;
138 
139  /*
140  Description:
141  Scales the quaternion's coordinates so that
142  a*a + b*b + c*c + d*d = 1.
143  Returns:
144  True if successful. False if the quaternion is zero
145  and cannot be unitized.
146  */
147  bool Unitize();
148 
149  /*
150  Description:
151  Sets the quaternion to
152 
153  cos(angle/2), sin(angle/2)*x, sin(angle/2)*y, sin(angle/2)*z
154 
155  where (x,y,z) is the unit vector parallel to axis. This is
156  the unit quaternion that represents the rotation of angle
157  about axis.
158  Parameters:
159  angle - [in] in radians
160  axis - [in] axis of rotation
161  Returns:
162  */
163  void SetRotation(double angle, const ON_3dVector& axis);
164 
165  /*
166  Parameters:
167  angle - [in] in radians
168  axis - [in] axis of rotation
169  Returns:
170  The unit quaternion
171 
172  cos(angle/2), sin(angle/2)*x, sin(angle/2)*y, sin(angle/2)*z
173 
174  where (x,y,z) is the unit vector parallel to axis. This is the
175  unit quaternion that represents the rotation of angle about axis.
176  */
177  static ON_Quaternion Rotation(double angle, const ON_3dVector& axis);
178 
179  /*
180  Descriptin:
181  Sets the quaternion to the unit quaternion which rotates
182  plane0.xaxis to plane1.xaxis,
183  plane0.yaxis to plane1.yaxis, and
184  plane0.zaxis to plane1.zaxis.
185  Parameters:
186  plane0 - [in]
187  plane1 - [in]
188  Remarks:
189  The plane origins are ignored.
190  */
191  void SetRotation(const ON_Plane& plane0, const ON_Plane& plane1);
192 
193  /*
194  Parameters:
195  plane0 - [in]
196  plane1 - [in]
197  Returns:
198  The unit quaternion that represents the the rotation that maps
199  plane0.xaxis to plane1.xaxis,
200  plane0.yaxis to plane1.yaxis, and
201  plane0.zaxis to plane1.zaxis.
202  Remarks:
203  The plane origins are ignored.
204  */
205  static ON_Quaternion Rotation(const ON_Plane& plane0, const ON_Plane& plane1);
206 
207  /*
208  Parameters:
209  angle - [out]
210  in radians
211  axis - [out]
212  unit axis of rotation of 0 if (b,c,d) is the zero vector.
213  Returns:
214  The rotation defined by the quaternion.
215  Remarks:
216  If the quaternion is not unitized, the rotation of its
217  unitized form is returned.
218  */
219  bool GetRotation(double& angle, ON_3dVector& axis) const;
220 
221  /*
222  Description:
223  The transformation returned by this function has the property
224  that xform*V = q.Rotate(V).
225  Parameters:
226  xform - [out]
227  Returns:
228  A transformation matrix that performs the rotation defined
229  by the quaternion.
230  Remarks:
231  If the quaternion is not unitized, the rotation of its
232  unitized form is returned. Do not confuse the result of this
233  function the matrix returned by ON_Quaternion::MatrixForm().
234  The transformation returned by this function has the property
235  that xform*V = q.Rotate(V).
236  */
237  bool GetRotation(ON_Xform& xform) const;
238 
239  /*
240  Parameters:
241  plane - [out]
242  Returns:
243  The frame created by applying the quaternion's rotation
244  to the canonical world frame (1,0,0),(0,1,0),(0,0,1).
245  */
246  bool GetRotation(ON_Plane& plane) const;
247 
248  /*
249  Description
250  Rotate a 3d vector. This operation is also called
251  conjugation, because the result is the same as
252 
253  (q.Conjugate()*(0,x,y,x)*q/q.LengthSquared()).Vector()
254 
255  Parameters:
256  v - [in]
257  Returns:
258  R*v, where R is the rotation defined by the unit quaternion.
259  This is mathematically the same as the values
260  (Inverse(q)*(0,x,y,z)*q).Vector()
261  and
262  (q.Conjugate()*(0,x,y,x)*q/q.LengthSquared()).Vector()
263  Remarks:
264  If you need to rotate more than a dozen or so vectors, it will
265  be more efficient to call GetRotation(ON_Xform& xform)
266  and multiply the vectors by xform.
267  */
268  ON_3dVector Rotate(ON_3dVector v) const;
269 
270  /*
271  Returns:
272  The "vector" or "imaginary" part of the quaternion = (b,c,d)
273  */
274  ON_3dVector Vector() const;
275 
276  /*
277  Returns:
278  The "real" or "scalar" part of the quaternion = a.
279  */
280  double Scalar() const;
281 
282  /*
283  Returns:
284  True if a, b, c, and d are all zero.
285  */
286  bool IsZero() const;
287 
288  /*
289  Returns:
290  True if a, b, c, and d are all valid, finite and at least one is non-zero.
291  */
292  bool IsNotZero() const;
293 
294  /*
295  Returns:
296  True if b, c, and d are all zero.
297  */
298  bool IsScalar() const;
299 
300  /*
301  Returns:
302  True if a = 0 and at least one of b, c, or d is not zero.
303  */
304  bool IsVector() const;
305 
306 
307  /*
308  Returns:
309  exp(q) = e^a*( cos(|V|) + V/|V|*sin(|V|) ), where V = b*i + c*j + d*k.
310  */
311  static ON_Quaternion Exp(ON_Quaternion q);
312 
313  /*
314  Returns:
315  log(q) = log(|q|) + V/|V|*acos(a/|q|), where V = b*i + c*j + d*k.
316  */
317  static ON_Quaternion Log(ON_Quaternion q);
318 
319  /*
320  Returns:
321  q^t = Exp(t*Log(q))
322  */
323  static ON_Quaternion Pow(ON_Quaternion q, double t);
324 
325 
326  static ON_Quaternion Slerp(ON_Quaternion q0, ON_Quaternion q1, double t);
327 
328 };
329 
330 /*
331 Returns:
332  The quaternion product of p and q. This is the same value as p*q.
333 */
334 ON_DECL
335 ON_Quaternion ON_QuaternionProduct( const ON_Quaternion& p, const ON_Quaternion& q);
336 
337 /*
338 Returns:
339  The vector cross product of p and q = (0,x,y,z) where
340  (x,y,z) = ON_CrossProduct(p.Vector(),q.Vector())
341 
342  This is NOT the same as the quaternion product p*q.
343 */
344 ON_DECL
345 ON_Quaternion ON_CrossProduct( const ON_Quaternion& p, const ON_Quaternion& q);
346 
347 ON_DECL
348 ON_Quaternion operator*(int, const ON_Quaternion&);
349 
350 ON_DECL
351 ON_Quaternion operator*(float, const ON_Quaternion&);
352 
353 ON_DECL
354 ON_Quaternion operator*(double, const ON_Quaternion&);
355 
356 #endif
ON_Quaternion()
Definition: opennurbs_quaternion.h:32
static const ON_Quaternion J
Definition: opennurbs_quaternion.h:29
static const ON_Quaternion Identity
Definition: opennurbs_quaternion.h:27
static const ON_Quaternion Zero
Definition: opennurbs_quaternion.h:26
Definition: opennurbs_quaternion.h:20
static const ON_Quaternion I
Definition: opennurbs_quaternion.h:28
static const ON_Quaternion K
Definition: opennurbs_quaternion.h:30
Definition: opennurbs_xform.h:28
double d
Definition: opennurbs_quaternion.h:24
Definition: opennurbs_plane.h:20
Definition: opennurbs_point.h:1152