Jpp test-rotations-new
the software that should make you happy
Loading...
Searching...
No Matches
JQuaternion3D.hh
Go to the documentation of this file.
1#ifndef __JQUATERNION3D__
2#define __JQUATERNION3D__
3
4#include <istream>
5#include <ostream>
6#include <limits>
7#include <cmath>
8
10#include "JLang/JEquals.hh"
11#include "JMath/JMath.hh"
12#include "JMath/JConstants.hh"
15
16
17/**
18 * \author mdejong
19 */
20
21namespace JGEOMETRY3D {}
22namespace JPP { using namespace JGEOMETRY3D; }
23
24namespace JGEOMETRY3D {
25
26 using JIO::JReader;
27 using JIO::JWriter;
28 using JMATH::JMath;
29 using JLANG::JEquals;
30
31
32 /**
33 * This class represents a rotation.
34 */
36 protected:
37 /**
38 * Default constructor.
39 * This constructor corresponds to the identity operation.
40 */
42 __a(1.0),
43 __u(0.0)
44 {}
45
46
47 /**
48 * Constructor.
49 *
50 * \param theta rotation angle [rad]
51 */
52 JQuaternion2D(const double theta) :
53 __a(cos(0.5*theta)),
54 __u(sin(0.5*theta))
55 {}
56
57
58 public:
59 /**
60 * Get a value.
61 *
62 * \return a value
63 */
64 double getA() const
65 {
66 return __a;
67 }
68
69
70 /**
71 * Raise quaternion to given power.
72 *
73 * \param y power
74 * \return this object
75 */
76 inline JQuaternion2D& pow(const double y)
77 {
78 const double theta = atan2(__u, __a) * y;
79
80 __a = cos(theta);
81 __u = sin(theta);
82
83 return *this;
84 }
85
86
87 /**
88 * Write quaternion from input.
89 *
90 * \param in input stream
91 * \param quaternion quaternion
92 * \return input stream
93 */
94 friend inline std::istream& operator>>(std::istream& in, JQuaternion2D& quaternion)
95 {
96 return in >> quaternion.__a >> quaternion.__u;
97 }
98
99
100 /**
101 * Write quaternion to output.
102 *
103 * \param out output stream
104 * \param quaternion quaternion
105 * \return output stream
106 */
107 friend inline std::ostream& operator<<(std::ostream& out, const JQuaternion2D& quaternion)
108 {
109 const JFormat format(out, getFormat<JQuaternion3D>(JFormat_t(9, 6, std::ios::fixed | std::ios::showpos)));
110
111 return out << format << quaternion.__a << ' '
112 << format << quaternion.__u;
113 }
114
115
116 /**
117 * Read quaternion from input.
118 *
119 * \param in reader
120 * \param quaternion quaternion
121 * \return reader
122 */
123 friend inline JReader& operator>>(JReader& in, JQuaternion2D& quaternion)
124 {
125 return in >> quaternion.__a >> quaternion.__u;
126 }
127
128
129 /**
130 * Write quaternion to output.
131 *
132 * \param out writer
133 * \param quaternion quaternion
134 * \return writer
135 */
136 friend inline JWriter& operator<<(JWriter& out, const JQuaternion2D& quaternion)
137 {
138 return out << quaternion.__a << quaternion.__u;
139 }
140
141
142 protected:
143 double __a;
144 double __u;
145 };
146
147
148 /**
149 * This class represents a rotation around the x-axis.
150 */
152 public JQuaternion2D
153 {
154 /**
155 * Default constructor.
156 */
159 {}
160
161
162 /**
163 * Constructor.
164 *
165 * \param theta rotation angle [rad]
166 */
167 JQuaternion3X(const double theta) :
168 JQuaternion2D(theta)
169 {}
170
171
172 /**
173 * Get b value.
174 *
175 * \return b value
176 */
177 double getB() const
178 {
179 return __u;
180 }
181
182
183 /**
184 * Raise quaternion to given power.
185 *
186 * \param y power
187 * \return this object
188 */
189 inline JQuaternion3X& pow(const double y)
190 {
192
193 return *this;
194 }
195 };
196
197
198 /**
199 * This class represents a rotation around the y-axis.
200 */
202 public JQuaternion2D
203 {
204 /**
205 * Default constructor.
206 */
209 {}
210
211
212 /**
213 * Constructor.
214 *
215 * \param theta rotation angle [rad]
216 */
217 JQuaternion3Y(const double theta) :
218 JQuaternion2D(theta)
219 {}
220
221
222 /**
223 * Get c value.
224 *
225 * \return c value
226 */
227 double getC() const
228 {
229 return __u;
230 }
231
232
233 /**
234 * Raise quaternion to given power.
235 *
236 * \param y power
237 * \return this object
238 */
239 inline JQuaternion3Y& pow(const double y)
240 {
242
243 return *this;
244 }
245 };
246
247
248 /**
249 * This class represents a rotation around the z-axis.
250 */
252 public JQuaternion2D
253 {
254 /**
255 * Default constructor.
256 */
259 {}
260
261
262 /**
263 * Constructor.
264 *
265 * \param theta rotation angle [rad]
266 */
267 JQuaternion3Z(const double theta) :
268 JQuaternion2D(theta)
269 {}
270
271
272 /**
273 * Get d value.
274 *
275 * \return d value
276 */
277 double getD() const
278 {
279 return __u;
280 }
281
282
283 /**
284 * Raise quaternion to given power.
285 *
286 * \param y power
287 * \return this object
288 */
289 inline JQuaternion3Z& pow(const double y)
290 {
292
293 return *this;
294 }
295 };
296
297
298 /**
299 * Data structure for unit quaternion in three dimensions.
300 *
301 * This class implements the JMATH::JMath and JLANG::JEquals interfaces.
302 */
304 public JMath <JQuaternion3D>,
305 public JMath <JQuaternion3D, JQuaternion3X>,
306 public JMath <JQuaternion3D, JQuaternion3Y>,
307 public JMath <JQuaternion3D, JQuaternion3Z>,
308 public JEquals<JQuaternion3D>
309 {
310 public:
311
316
317
318 struct decomposition; // forward declaration
319
320
321 /**
322 * Default constructor.
323 */
325 __a(1.0),
326 __b(0.0),
327 __c(0.0),
328 __d(0.0)
329 {}
330
331
332 /**
333 * Constructor.
334 *
335 * \param a a value
336 * \param b b value
337 * \param c c value
338 * \param d d value
339 */
340 JQuaternion3D(const double a,
341 const double b,
342 const double c,
343 const double d) :
344 __a(a),
345 __b(b),
346 __c(c),
347 __d(d)
348 {
349 normalise();
350 }
351
352
353 /**
354 * Constructor.
355 *
356 * This constructor represents a rotation around the given axis by the given angle.
357 *
358 * \param theta rotation angle [rad]
359 * \param dir rotation axis
360 */
361 JQuaternion3D(const double theta,
362 const JVersor3D& dir)
363 {
364 const double ct = cos(0.5*theta);
365 const double st = sin(0.5*theta);
366
367 __a = ct;
368 __b = st * dir.getDX();
369 __c = st * dir.getDY();
370 __d = st * dir.getDZ();
371 }
372
373
374 /**
375 * Constructor.
376 *
377 * \param w weight
378 * \param dir rotation axis
379 */
380 JQuaternion3D(const double w,
381 const JVector3D& dir)
382 {
383 __a = w;
384 __b = dir.getX();
385 __c = dir.getY();
386 __d = dir.getZ();
387
388 normalise();
389 }
390
391
392 /**
393 * Constructor.
394 *
395 * \param qx rotation around x-axis
396 */
398 __a(1.0),
399 __b(0.0),
400 __c(0.0),
401 __d(0.0)
402 {
403 mul(qx);
404 }
405
406
407 /**
408 * Constructor.
409 *
410 * \param qy rotation around y-axis
411 */
413 __a(1.0),
414 __b(0.0),
415 __c(0.0),
416 __d(0.0)
417 {
418 mul(qy);
419 }
420
421
422 /**
423 * Constructor.
424 *
425 * \param qz rotation around x-axis
426 */
428 __a(1.0),
429 __b(0.0),
430 __c(0.0),
431 __d(0.0)
432 {
433 mul(qz);
434 }
435
436
437 /**
438 * Constructor.
439 *
440 * \param qx rotation around x-axis
441 * \param qy rotation around y-axis
442 * \param qz rotation around z-axis
443 */
445 const JQuaternion3Y& qy,
446 const JQuaternion3Z& qz) :
447 __a(1.0),
448 __b(0.0),
449 __c(0.0),
450 __d(0.0)
451 {
452 mul(qz).mul(qy).mul(qx);
453
454 normalise();
455 }
456
457
458 /**
459 * Get identity quaternion
460 *
461 * \return identity quaternion
462 */
464 {
465 static const JQuaternion3D Q = JQuaternion3D().setIdentity();
466
467 return Q;
468 }
469
470
471 /**
472 * Get quaternion.
473 *
474 * \return quaternion
475 */
477 {
478 return static_cast<const JQuaternion3D&>(*this);
479 }
480
481
482 /**
483 * Get quaternion.
484 *
485 * \return quaternion
486 */
488 {
489 return static_cast<JQuaternion3D&>(*this);
490 }
491
492
493 /**
494 * Set quaternion.
495 *
496 * \param quaternion quaternion
497 */
498 void setQuaternion(const JQuaternion3D& quaternion)
499 {
500 static_cast<JQuaternion3D&>(*this) = quaternion;
501 }
502
503
504 /**
505 * Type conversion operator.
506 *
507 * \return position
508 */
509 operator JVector3D() const
510 {
511 return JVector3D(this->getB(), this->getC(), this->getD());
512 }
513
514
515 /**
516 * Type conversion operator.
517 *
518 * \return direction
519 */
520 operator JVersor3D() const
521 {
522 return JVersor3D(this->getB(), this->getC(), this->getD());
523 }
524
525
526 /**
527 * Get rotation angle.
528 *
529 * \return angle [rad]
530 */
531 inline double getAngle() const
532 {
533 return atan2(sqrt(this->getB()*this->getB() +
534 this->getC()*this->getC() +
535 this->getD()*this->getD()),
536 this->getA()) * 2.0;
537 }
538
539
540 /**
541 * Get a value.
542 *
543 * \return a value
544 */
545 double getA() const
546 {
547 return __a;
548 }
549
550
551 /**
552 * Get b value.
553 *
554 * \return b value
555 */
556 double getB() const
557 {
558 return __b;
559 }
560
561
562 /**
563 * Get c value.
564 *
565 * \return c value
566 */
567 double getC() const
568 {
569 return __c;
570 }
571
572
573 /**
574 * Get d value.
575 *
576 * \return d value
577 */
578 double getD() const
579 {
580 return __d;
581 }
582
583
584 /**
585 * Set to identity quaternion
586 *
587 * \return this quaternion
588 */
590 {
591 __a = 1.0;
592 __b = 0.0;
593 __c = 0.0;
594 __d = 0.0;
595
596 return *this;
597 }
598
599
600 /**
601 * Conjugate quaternion.
602 *
603 * \return this quaternion
604 */
606 {
607 __b = -__b;
608 __c = -__c;
609 __d = -__d;
610
611 return *this;
612 }
613
614
615 /**
616 * Negate quaternion.
617 *
618 * \return this quaternion
619 */
621 {
622 __a = -__a;
623 __b = -__b;
624 __c = -__c;
625 __d = -__d;
626
627 return *this;
628 }
629
630
631 /**
632 * Add quaternion.
633 *
634 * \param quaternion quaternion
635 * \return this quaternion
636 */
637 JQuaternion3D& add(const JQuaternion3D& quaternion)
638 {
639 __a += quaternion.getA();
640 __b += quaternion.getB();
641 __c += quaternion.getC();
642 __d += quaternion.getD();
643
644 return *this;
645 }
646
647
648 /**
649 * Subtract quaternion.
650 *
651 * \param quaternion quaternion
652 * \return this quaternion
653 */
654 JQuaternion3D& sub(const JQuaternion3D& quaternion)
655 {
656 __a -= quaternion.getA();
657 __b -= quaternion.getB();
658 __c -= quaternion.getC();
659 __d -= quaternion.getD();
660
661 return *this;
662 }
663
664
665 /**
666 * Scale quaternion.
667 *
668 * \param factor multiplication factor
669 * \return this quaternion
670 */
671 JQuaternion3D& mul(const double factor)
672 {
673 __a *= factor;
674 __b *= factor;
675 __c *= factor;
676 __d *= factor;
677
678 return *this;
679 }
680
681
682 /**
683 * Scale quaternion.
684 *
685 * \param factor division factor
686 * \return this quaternion
687 */
688 JQuaternion3D& div(const double factor)
689 {
690 __a /= factor;
691 __b /= factor;
692 __c /= factor;
693 __d /= factor;
694
695 return *this;
696 }
697
698
699 /**
700 * Quaternion multiplication.
701 *
702 * This method evaluates the Hamilton product (also called cross product).
703 *
704 * \param first first quaternion
705 * \param second second quaternion
706 * \return this quaternion
707 */
708 JQuaternion3D& mul(const JQuaternion3D& first, const JQuaternion3X& second)
709 {
710 __a = first.getA() * second.getA() - first.getB() * second.getB();
711 __b = first.getA() * second.getB() + first.getB() * second.getA();
712 __c = first.getC() * second.getA() + first.getD() * second.getB();
713 __d = -first.getC() * second.getB() + first.getD() * second.getA();
714
715 return *this;
716 }
717
718
719 /**
720 * Quaternion multiplication.
721 *
722 * This method evaluates the Hamilton product (or cross product).
723 *
724 * \param first first quaternion
725 * \param second second quaternion
726 * \return this quaternion
727 */
729 const JQuaternion3Y& second)
730 {
731 __a = first.getA() * second.getA() - first.getC() * second.getC();
732 __b = first.getB() * second.getA() - first.getD() * second.getC();
733 __c = first.getA() * second.getC() + first.getC() * second.getA();
734 __d = first.getB() * second.getC() + first.getD() * second.getA();
735
736 return *this;
737 }
738
739
740 /**
741 * Quaternion multiplication.
742 *
743 * This method evaluates the Hamilton product (or cross product).
744 *
745 * \param first first quaternion
746 * \param second second quaternion
747 * \return this quaternion
748 */
750 const JQuaternion3Z& second)
751 {
752 __a = first.getA() * second.getA() - first.getD() * second.getD();
753 __b = first.getB() * second.getA() + first.getC() * second.getD();
754 __c = -first.getB() * second.getD() + first.getC() * second.getA();
755 __d = first.getA() * second.getD() + first.getD() * second.getA();
756
757 return *this;
758 }
759
760
761 /**
762 * Quaternion multiplication.
763 *
764 * This method evaluates the Hamilton product (or cross product).
765 *
766 * \param first first quaternion
767 * \param second second quaternion
768 * \return this quaternion
769 */
771 const JQuaternion3D& second)
772 {
773 __a = first.getA() * second.getA() - first.getB() * second.getB() - first.getC() * second.getC() - first.getD() * second.getD();
774 __b = first.getA() * second.getB() + first.getB() * second.getA() + first.getC() * second.getD() - first.getD() * second.getC();
775 __c = first.getA() * second.getC() - first.getB() * second.getD() + first.getC() * second.getA() + first.getD() * second.getB();
776 __d = first.getA() * second.getD() + first.getB() * second.getC() - first.getC() * second.getB() + first.getD() * second.getA();
777
778 return *this;
779 }
780
781
782 /**
783 * Quaternion multiplication.
784 *
785 * \param qx rotation around x-axis
786 * \param qy rotation around y-axis
787 * \param qz rotation around x-axis
788 * \return this quaternion
789 */
791 const JQuaternion3Y& qy,
792 const JQuaternion3Z& qz)
793 {
794 return *this = JQuaternion3D().setIdentity().mul(qz).mul(qy).mul(qx);
795 }
796
797
798 /**
799 * Rotate.
800 *
801 * \param __x x value
802 * \param __y y value
803 * \param __z z value
804 */
805 void rotate(double& __x, double& __y, double& __z) const
806 {
807 const double qx = 2.0 * (__c*__z - __d*__y);
808 const double qy = 2.0 * (__d*__x - __b*__z);
809 const double qz = 2.0 * (__b*__y - __c*__x);
810
811 __x = __x + __c*qz - __d*qy + __a*qx;
812 __y = __y - __b*qz + __a*qy + __d*qx;
813 __z = __z + __a*qz + __b*qy - __c*qx;
814 }
815
816
817 /**
818 * Rotate back.
819 *
820 * \param __x x value
821 * \param __y y value
822 * \param __z z value
823 */
824 void rotate_back(double& __x, double& __y, double& __z) const
825 {
826 const double qx = 2.0 * (__d*__y - __c*__z);
827 const double qy = 2.0 * (__b*__z - __d*__x);
828 const double qz = 2.0 * (__c*__x - __b*__y);
829
830 __x = __x - __c*qz + __d*qy + __a*qx;
831 __y = __y + __b*qz + __a*qy - __d*qx;
832 __z = __z + __a*qz - __b*qy + __c*qx;
833 }
834
835
836 /**
837 * Check equality.
838 *
839 * \param quaternion quaternion
840 * \param precision numerical precision
841 * \return true if quaternions are equal; else false
842 */
843 bool equals(const JQuaternion3D& quaternion,
844 const double precision = std::numeric_limits<double>::min()) const
845 {
846 return (fabs(getA() - quaternion.getA()) <= precision &&
847 fabs(getB() - quaternion.getB()) <= precision &&
848 fabs(getC() - quaternion.getC()) <= precision &&
849 fabs(getD() - quaternion.getD()) <= precision);
850 }
851
852
853 /**
854 * Test identity.
855 *
856 * \param precision precision
857 * \return true if identity quaternion; else false
858 */
859 bool isIdentity(const double precision = std::numeric_limits<double>::min()) const
860 {
861 if (fabs(getA()) <= precision) {
862
863 if (fabs(getB()) <= precision)
864 return ((fabs(getC()) <= precision && fabs(fabs(getD()) - 1.0) <= precision) ||
865 (fabs(fabs(getC()) - 1.0) <= precision && fabs(getD()) <= precision));
866 else
867 return (fabs(fabs(getB()) - 1.0) <= precision &&
868 fabs(getC()) <= precision &&
869 fabs(getD()) <= precision);
870
871 } else {
872
873 return (fabs(fabs(getA()) - 1.0) <= precision &&
874 fabs(getB()) <= precision &&
875 fabs(getC()) <= precision &&
876 fabs(getD()) <= precision);
877 }
878 }
879
880
881 /**
882 * Get length squared.
883 *
884 * \return square of length
885 */
886 double getLengthSquared() const
887 {
888 return getA()*getA() + getB()*getB() + getC()*getC() + getD()*getD();
889 }
890
891
892 /**
893 * Get length.
894 *
895 * \return length
896 */
897 double getLength() const
898 {
899 return sqrt(getLengthSquared());
900 }
901
902
903 /**
904 * Get squared of distance to quaternion.
905 *
906 * \param quaternion quaternion
907 * \return square of distance
908 */
909 double getDistanceSquared(const JQuaternion3D& quaternion) const
910 {
911 return JQuaternion3D(quaternion).sub(*this).getLengthSquared();
912 }
913
914
915 /**
916 * Get distance to quaternion.
917 *
918 * \param quaternion quaternion
919 * \return distance
920 */
921 double getDistance(const JQuaternion3D& quaternion) const
922 {
923 return sqrt(getDistanceSquared(quaternion));
924 }
925
926
927 /**
928 * Get dot product.
929 *
930 * \param quaternion quaternion
931 * \return dot product
932 */
933 double getDot(const JQuaternion3D& quaternion) const
934 {
935 return
936 getA() * quaternion.getA() -
937 getB() * quaternion.getB() -
938 getC() * quaternion.getC() -
939 getD() * quaternion.getD();
940 }
941
942
943 /**
944 * Get conjugate of this quaternion.
945 *
946 * \return conjugate quaternion
947 */
949 {
950 return JQuaternion3D(*this).conjugate();
951 }
952
953
954 /**
955 * Normalise quaternion.
956 *
957 * \return this quaternion
958 */
960 {
961 const double v = getLength();
962
963 if (v != 0.0) {
964 mul(1.0 / v);
965 }
966
967 return *this;
968 }
969
970
971 /**
972 * Raise quaternion to given power.
973 *
974 * \param y power
975 * \return this object
976 */
977 inline JQuaternion3D& pow(const double y)
978 {
979 const double v = sqrt(getB() * getB() +
980 getC() * getC() +
981 getD() * getD());
982
983 if (v != 0.0) {
984
985 const JVersor3D u(getB(), getC(), getD());
986
987 const double theta = atan2(v, getA());
988
989 *this = JQuaternion3D(2.0 * theta * y, u);
990 }
991
992 return *this;
993 }
994
995
996 /**
997 * Interpolation between quaternions.
998 * The result is equal to <tt>*this = (1 - alpha) * (*this) + (alpha) * (object)</tt>.
999 *
1000 * \param object object
1001 * \param alpha interpolation factor <tt>[0, 1]</tt>
1002 * \return this object
1003 */
1005 const double alpha)
1006 {
1007 const double MAXIMAL_DOT_PRODUCT = 0.9995;
1008
1009 JQuaternion3D v0(*this);
1010 JQuaternion3D v1(object);
1011
1012 v0.normalise();
1013 v1.normalise();
1014
1015 double dot = v0.getDot(v1);
1016
1017 if (dot < 0.0) {
1018 v1 = -v1;
1019 dot = -dot;
1020 }
1021
1022 double s1 = alpha;
1023 double s0 = 1.0 - alpha;
1024
1025 if (dot <= MAXIMAL_DOT_PRODUCT) {
1026
1027 const double theta_0 = acos(dot);
1028 const double theta_1 = theta_0 * alpha;
1029
1030 s1 = sin(theta_1) / sin(theta_0);
1031 s0 = cos(theta_1) - dot * s1;
1032 }
1033
1034 *this = (s0 * v0) + (s1 * v1);
1035
1036 return normalise();
1037 }
1038
1039
1040 /**
1041 * Write quaternion from input.
1042 *
1043 * \param in input stream
1044 * \param quaternion quaternion
1045 * \return input stream
1046 */
1047 friend inline std::istream& operator>>(std::istream& in, JQuaternion3D& quaternion)
1048 {
1049 in >> quaternion.__a;
1050 in >> quaternion.__b;
1051 in >> quaternion.__c;
1052 in >> quaternion.__d;
1053
1054 quaternion.normalise();
1055
1056 return in;
1057 }
1058
1059
1060 /**
1061 * Write quaternion to output.
1062 *
1063 * \param out output stream
1064 * \param quaternion quaternion
1065 * \return output stream
1066 */
1067 friend inline std::ostream& operator<<(std::ostream& out, const JQuaternion3D& quaternion)
1068 {
1069 const JFormat format(out, getFormat<JQuaternion3D>(JFormat_t(9, 6, std::ios::fixed | std::ios::showpos)));
1070
1071 out << format << quaternion.getA() << ' '
1072 << format << quaternion.getB() << ' '
1073 << format << quaternion.getC() << ' '
1074 << format << quaternion.getD();
1075
1076 return out;
1077 }
1078
1079
1080 /**
1081 * Read quaternion from input.
1082 *
1083 * \param in reader
1084 * \param quaternion quaternion
1085 * \return reader
1086 */
1087 friend inline JReader& operator>>(JReader& in, JQuaternion3D& quaternion)
1088 {
1089 in >> quaternion.__a;
1090 in >> quaternion.__b;
1091 in >> quaternion.__c;
1092 in >> quaternion.__d;
1093
1094 return in;
1095 }
1096
1097
1098 /**
1099 * Write quaternion to output.
1100 *
1101 * \param out writer
1102 * \param quaternion quaternion
1103 * \return writer
1104 */
1105 friend inline JWriter& operator<<(JWriter& out, const JQuaternion3D& quaternion)
1106 {
1107 out << quaternion.__a;
1108 out << quaternion.__b;
1109 out << quaternion.__c;
1110 out << quaternion.__d;
1111
1112 return out;
1113 }
1114
1115
1116 protected:
1117 double __a;
1118 double __b;
1119 double __c;
1120 double __d;
1121 };
1122
1123
1124 /**
1125 * Auxiliary data structure for decomposition of quaternion in twist and swing quaternions.
1126 */
1128 /**
1129 * Constructor.
1130 *
1131 * \param Q quaternion
1132 * \param dir direction
1133 */
1135 const JVector3D& dir)
1136 {
1137 twist = JQuaternion3D(Q.getA(), dir * dir.getDot(Q)); // rotation around given axis
1139 }
1140
1141
1142 /**
1143 * Get quaternion.
1144 *
1145 * \return quaternion
1146 */
1148 {
1149 return swing * twist;
1150 }
1151
1152 JQuaternion3D twist; //!< rotation around parallel axis
1153 JQuaternion3D swing; //!< rotation around perpendicular axis
1154 };
1155
1156
1157
1158 /**
1159 * Get space angle between quanternions.
1160 *
1161 * \param first first quanternion
1162 * \param second second quanternion
1163 * \return angle [deg]
1164 */
1165 inline double getAngle(const JQuaternion3D& first,
1166 const JQuaternion3D& second)
1167 {
1168 double dot = (first.getA() * second.getA() +
1169 first.getB() * second.getB() +
1170 first.getC() * second.getC() +
1171 first.getD() * second.getD());
1172
1173 dot = 2.0 * dot * dot - 1.0;
1174
1175 if (dot > +1.0)
1176 return 0.0;
1177 else if (dot < -1.0)
1178 return 180.0;
1179 else
1180 return 0.5 * acos(dot) * 180.0 / JMATH::PI;
1181 }
1182}
1183
1184#endif
JFormat_t & getFormat()
Get format for given type.
Definition JManip.hh:682
Mathematical constants.
Base class for data structures with artithmetic capabilities.
Data structure for unit quaternion in three dimensions.
JQuaternion3D(const JQuaternion3Y &qy)
Constructor.
JQuaternion3D(const JQuaternion3X &qx, const JQuaternion3Y &qy, const JQuaternion3Z &qz)
Constructor.
const JQuaternion3D & getQuaternion() const
Get quaternion.
double getDistanceSquared(const JQuaternion3D &quaternion) const
Get squared of distance to quaternion.
JQuaternion3D & mul(const JQuaternion3D &first, const JQuaternion3Z &second)
Quaternion multiplication.
JQuaternion3D(const JQuaternion3Z &qz)
Constructor.
JQuaternion3D & sub(const JQuaternion3D &quaternion)
Subtract quaternion.
JQuaternion3D(const JQuaternion3X &qx)
Constructor.
JQuaternion3D & mul(const JQuaternion3D &first, const JQuaternion3D &second)
Quaternion multiplication.
JQuaternion3D()
Default constructor.
void setQuaternion(const JQuaternion3D &quaternion)
Set quaternion.
JQuaternion3D & normalise()
Normalise quaternion.
JQuaternion3D getConjugate() const
Get conjugate of this quaternion.
void rotate(double &__x, double &__y, double &__z) const
Rotate.
bool isIdentity(const double precision=std::numeric_limits< double >::min()) const
Test identity.
JQuaternion3D & interpolate(const JQuaternion3D &object, const double alpha)
Interpolation between quaternions.
double getAngle() const
Get rotation angle.
double getB() const
Get b value.
JQuaternion3D & getQuaternion()
Get quaternion.
double getD() const
Get d value.
JQuaternion3D & mul(const JQuaternion3D &first, const JQuaternion3Y &second)
Quaternion multiplication.
double getDistance(const JQuaternion3D &quaternion) const
Get distance to quaternion.
JQuaternion3D & conjugate()
Conjugate quaternion.
double getLength() const
Get length.
void rotate_back(double &__x, double &__y, double &__z) const
Rotate back.
double getC() const
Get c value.
JQuaternion3D(const double theta, const JVersor3D &dir)
Constructor.
JQuaternion3D & mul(const double factor)
Scale quaternion.
JQuaternion3D & pow(const double y)
Raise quaternion to given power.
friend std::istream & operator>>(std::istream &in, JQuaternion3D &quaternion)
Write quaternion from input.
JQuaternion3D(const double a, const double b, const double c, const double d)
Constructor.
JQuaternion3D & setIdentity()
Set to identity quaternion.
JQuaternion3D & div(const double factor)
Scale quaternion.
bool equals(const JQuaternion3D &quaternion, const double precision=std::numeric_limits< double >::min()) const
Check equality.
double getDot(const JQuaternion3D &quaternion) const
Get dot product.
static const JQuaternion3D & getIdentity()
Get identity quaternion.
friend std::ostream & operator<<(std::ostream &out, const JQuaternion3D &quaternion)
Write quaternion to output.
friend JWriter & operator<<(JWriter &out, const JQuaternion3D &quaternion)
Write quaternion to output.
friend JReader & operator>>(JReader &in, JQuaternion3D &quaternion)
Read quaternion from input.
double getA() const
Get a value.
JQuaternion3D & negate()
Negate quaternion.
double getLengthSquared() const
Get length squared.
JQuaternion3D & add(const JQuaternion3D &quaternion)
Add quaternion.
JQuaternion3D(const double w, const JVector3D &dir)
Constructor.
JQuaternion3D & mul(const JQuaternion3X &qx, const JQuaternion3Y &qy, const JQuaternion3Z &qz)
Quaternion multiplication.
JQuaternion3D & mul(const JQuaternion3D &first, const JQuaternion3X &second)
Quaternion multiplication.
Data structure for vector in three dimensions.
Definition JVector3D.hh:36
double getY() const
Get y position.
Definition JVector3D.hh:104
double getZ() const
Get z position.
Definition JVector3D.hh:115
double getDot(const JVector3D &vector) const
Get dot product.
Definition JVector3D.hh:282
double getX() const
Get x position.
Definition JVector3D.hh:94
Data structure for normalised vector in three dimensions.
Definition JVersor3D.hh:28
double getDY() const
Get y direction.
Definition JVersor3D.hh:106
double getDX() const
Get x direction.
Definition JVersor3D.hh:95
double getDZ() const
Get z direction.
Definition JVersor3D.hh:117
Interface for binary input.
Interface for binary output.
Auxiliary classes and methods for 3D geometrical objects and operations.
Definition JAngle3D.hh:19
double getAngle(const JQuaternion3D &first, const JQuaternion3D &second)
Get space angle between quanternions.
static const double PI
Mathematical constants.
This name space includes all other name spaces (except KM3NETDAQ, KM3NET and ANTARES).
Data structure for format specifications.
Definition JManip.hh:524
Auxiliary class to temporarily define format specifications.
Definition JManip.hh:636
This class represents a rotation.
friend JWriter & operator<<(JWriter &out, const JQuaternion2D &quaternion)
Write quaternion to output.
double getA() const
Get a value.
friend std::ostream & operator<<(std::ostream &out, const JQuaternion2D &quaternion)
Write quaternion to output.
friend std::istream & operator>>(std::istream &in, JQuaternion2D &quaternion)
Write quaternion from input.
JQuaternion2D & pow(const double y)
Raise quaternion to given power.
JQuaternion2D(const double theta)
Constructor.
JQuaternion2D()
Default constructor.
friend JReader & operator>>(JReader &in, JQuaternion2D &quaternion)
Read quaternion from input.
Auxiliary data structure for decomposition of quaternion in twist and swing quaternions.
JQuaternion3D getQuaternion() const
Get quaternion.
JQuaternion3D swing
rotation around perpendicular axis
JQuaternion3D twist
rotation around parallel axis
decomposition(const JQuaternion3D &Q, const JVector3D &dir)
Constructor.
This class represents a rotation around the x-axis.
JQuaternion3X(const double theta)
Constructor.
JQuaternion3X & pow(const double y)
Raise quaternion to given power.
double getB() const
Get b value.
JQuaternion3X()
Default constructor.
This class represents a rotation around the y-axis.
JQuaternion3Y()
Default constructor.
JQuaternion3Y & pow(const double y)
Raise quaternion to given power.
JQuaternion3Y(const double theta)
Constructor.
double getC() const
Get c value.
This class represents a rotation around the z-axis.
JQuaternion3Z & pow(const double y)
Raise quaternion to given power.
double getD() const
Get d value.
JQuaternion3Z()
Default constructor.
JQuaternion3Z(const double theta)
Constructor.
Template definition of auxiliary base class for comparison of data structures.
Definition JEquals.hh:84
Auxiliary base class for aritmetic operations of derived class types.
Definition JMath.hh:347