matrix3.h 7.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275
  1. /*
  2. This program is free software: you can redistribute it and/or modify
  3. it under the terms of the GNU General Public License as published by
  4. the Free Software Foundation, either version 3 of the License, or
  5. (at your option) any later version.
  6. This program is distributed in the hope that it will be useful,
  7. but WITHOUT ANY WARRANTY; without even the implied warranty of
  8. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  9. GNU General Public License for more details.
  10. You should have received a copy of the GNU General Public License
  11. along with this program. If not, see <http://www.gnu.org/licenses/>.
  12. */
  13. // Copyright 2010 Michael Smith, all rights reserved.
  14. // Inspired by:
  15. /****************************************
  16. * 3D Vector Classes
  17. * By Bill Perone (billperone@yahoo.com)
  18. */
  19. //
  20. // 3x3 matrix implementation.
  21. //
  22. // Note that the matrix is organised in row-normal form (the same as
  23. // applies to array indexing).
  24. //
  25. // In addition to the template, this header defines the following types:
  26. //
  27. // Matrix3i 3x3 matrix of signed integers
  28. // Matrix3ui 3x3 matrix of unsigned integers
  29. // Matrix3l 3x3 matrix of signed longs
  30. // Matrix3ul 3x3 matrix of unsigned longs
  31. // Matrix3f 3x3 matrix of signed floats
  32. //
  33. #pragma once
  34. #include "vector3.h"
  35. #include "vector2.h"
  36. // 3x3 matrix with elements of type T
  37. template <typename T>
  38. class Matrix3 {
  39. public:
  40. // Vectors comprising the rows of the matrix
  41. Vector3<T> a, b, c;
  42. // trivial ctor
  43. // note that the Vector3 ctor will zero the vector elements
  44. constexpr Matrix3<T>() {}
  45. // setting ctor
  46. constexpr Matrix3<T>(const Vector3<T> &a0, const Vector3<T> &b0, const Vector3<T> &c0)
  47. : a(a0)
  48. , b(b0)
  49. , c(c0) {}
  50. // setting ctor
  51. constexpr Matrix3<T>(const T ax, const T ay, const T az,
  52. const T bx, const T by, const T bz,
  53. const T cx, const T cy, const T cz)
  54. : a(ax,ay,az)
  55. , b(bx,by,bz)
  56. , c(cx,cy,cz) {}
  57. // function call operator
  58. void operator () (const Vector3<T> &a0, const Vector3<T> &b0, const Vector3<T> &c0)
  59. {
  60. a = a0; b = b0; c = c0;
  61. }
  62. // test for equality
  63. bool operator == (const Matrix3<T> &m)
  64. {
  65. return (a==m.a && b==m.b && c==m.c);
  66. }
  67. // test for inequality
  68. bool operator != (const Matrix3<T> &m)
  69. {
  70. return (a!=m.a || b!=m.b || c!=m.c);
  71. }
  72. // negation
  73. Matrix3<T> operator - (void) const
  74. {
  75. return Matrix3<T>(-a,-b,-c);
  76. }
  77. // addition
  78. Matrix3<T> operator + (const Matrix3<T> &m) const
  79. {
  80. return Matrix3<T>(a+m.a, b+m.b, c+m.c);
  81. }
  82. Matrix3<T> &operator += (const Matrix3<T> &m)
  83. {
  84. return *this = *this + m;
  85. }
  86. // subtraction
  87. Matrix3<T> operator - (const Matrix3<T> &m) const
  88. {
  89. return Matrix3<T>(a-m.a, b-m.b, c-m.c);
  90. }
  91. Matrix3<T> &operator -= (const Matrix3<T> &m)
  92. {
  93. return *this = *this - m;
  94. }
  95. // uniform scaling
  96. Matrix3<T> operator * (const T num) const
  97. {
  98. return Matrix3<T>(a*num, b*num, c*num);
  99. }
  100. Matrix3<T> &operator *= (const T num)
  101. {
  102. return *this = *this * num;
  103. }
  104. Matrix3<T> operator / (const T num) const
  105. {
  106. return Matrix3<T>(a/num, b/num, c/num);
  107. }
  108. Matrix3<T> &operator /= (const T num)
  109. {
  110. return *this = *this / num;
  111. }
  112. // allow a Matrix3 to be used as an array of vectors, 0 indexed
  113. Vector3<T> & operator[](uint8_t i) {
  114. Vector3<T> *_v = &a;
  115. #if MATH_CHECK_INDEXES
  116. assert(i >= 0 && i < 3);
  117. #endif
  118. return _v[i];
  119. }
  120. const Vector3<T> & operator[](uint8_t i) const {
  121. const Vector3<T> *_v = &a;
  122. #if MATH_CHECK_INDEXES
  123. assert(i >= 0 && i < 3);
  124. #endif
  125. return _v[i];
  126. }
  127. // multiplication by a vector
  128. Vector3<T> operator *(const Vector3<T> &v) const;
  129. // multiplication of transpose by a vector
  130. Vector3<T> mul_transpose(const Vector3<T> &v) const;
  131. // multiplication by a vector giving a Vector2 result (XY components)
  132. Vector2<T> mulXY(const Vector3<T> &v) const;
  133. // extract x column
  134. Vector3<T> colx(void) const
  135. {
  136. return Vector3<T>(a.x, b.x, c.x);
  137. }
  138. // extract y column
  139. Vector3<T> coly(void) const
  140. {
  141. return Vector3<T>(a.y, b.y, c.y);
  142. }
  143. // extract z column
  144. Vector3<T> colz(void) const
  145. {
  146. return Vector3<T>(a.z, b.z, c.z);
  147. }
  148. // multiplication by another Matrix3<T>
  149. Matrix3<T> operator *(const Matrix3<T> &m) const;
  150. Matrix3<T> &operator *=(const Matrix3<T> &m)
  151. {
  152. return *this = *this * m;
  153. }
  154. // transpose the matrix
  155. Matrix3<T> transposed(void) const;
  156. void transpose(void)
  157. {
  158. *this = transposed();
  159. }
  160. /**
  161. * Calculate the determinant of this matrix.
  162. *
  163. * @return The value of the determinant.
  164. */
  165. T det() const;
  166. /**
  167. * Calculate the inverse of this matrix.
  168. *
  169. * @param inv[in] Where to store the result.
  170. *
  171. * @return If this matrix is invertible, then true is returned. Otherwise,
  172. * \p inv is unmodified and false is returned.
  173. */
  174. bool inverse(Matrix3<T>& inv) const WARN_IF_UNUSED;
  175. /**
  176. * Invert this matrix if it is invertible.
  177. *
  178. * @return Return true if this matrix could be successfully inverted and
  179. * false otherwise.
  180. */
  181. bool invert() WARN_IF_UNUSED;
  182. // zero the matrix
  183. void zero(void);
  184. // setup the identity matrix
  185. void identity(void) {
  186. a.x = b.y = c.z = 1;
  187. a.y = a.z = 0;
  188. b.x = b.z = 0;
  189. c.x = c.y = 0;
  190. }
  191. // check if any elements are NAN
  192. bool is_nan(void) WARN_IF_UNUSED
  193. {
  194. return a.is_nan() || b.is_nan() || c.is_nan();
  195. }
  196. // create a rotation matrix from Euler angles
  197. void from_euler(float roll, float pitch, float yaw);
  198. // create eulers from a rotation matrix.
  199. // roll is from -Pi to Pi
  200. // pitch is from -Pi/2 to Pi/2
  201. // yaw is from -Pi to Pi
  202. void to_euler(float *roll, float *pitch, float *yaw) const;
  203. // create matrix from rotation enum
  204. void from_rotation(enum Rotation rotation);
  205. /*
  206. calculate Euler angles (312 convention) for the matrix.
  207. See http://www.atacolorado.com/eulersequences.doc
  208. vector is returned in r, p, y order
  209. */
  210. Vector3<T> to_euler312() const;
  211. /*
  212. fill the matrix from Euler angles in radians in 312 convention
  213. */
  214. void from_euler312(float roll, float pitch, float yaw);
  215. // apply an additional rotation from a body frame gyro vector
  216. // to a rotation matrix.
  217. void rotate(const Vector3<T> &g);
  218. // create rotation matrix for rotation about the vector v by angle theta
  219. // See: https://en.wikipedia.org/wiki/Rotation_matrix#General_rotations
  220. // "Rotation matrix from axis and angle"
  221. void from_axis_angle(const Vector3<T> &v, float theta);
  222. // normalize a rotation matrix
  223. void normalize(void);
  224. };
  225. typedef Matrix3<int16_t> Matrix3i;
  226. typedef Matrix3<uint16_t> Matrix3ui;
  227. typedef Matrix3<int32_t> Matrix3l;
  228. typedef Matrix3<uint32_t> Matrix3ul;
  229. typedef Matrix3<float> Matrix3f;
  230. typedef Matrix3<double> Matrix3d;