Matrix3.h 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308
  1. //
  2. // Copyright (c) 2008-2013 the Urho3D project.
  3. //
  4. // Permission is hereby granted, free of charge, to any person obtaining a copy
  5. // of this software and associated documentation files (the "Software"), to deal
  6. // in the Software without restriction, including without limitation the rights
  7. // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  8. // copies of the Software, and to permit persons to whom the Software is
  9. // furnished to do so, subject to the following conditions:
  10. //
  11. // The above copyright notice and this permission notice shall be included in
  12. // all copies or substantial portions of the Software.
  13. //
  14. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16. // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  17. // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  18. // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  19. // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  20. // THE SOFTWARE.
  21. //
  22. #pragma once
  23. #include "Vector3.h"
  24. namespace Urho3D
  25. {
  26. /// 3x3 matrix for rotation and scaling.
  27. class URHO3D_API Matrix3
  28. {
  29. public:
  30. /// Construct undefined.
  31. Matrix3()
  32. {
  33. }
  34. /// Copy-construct from another matrix.
  35. Matrix3(const Matrix3& matrix) :
  36. m00_(matrix.m00_),
  37. m01_(matrix.m01_),
  38. m02_(matrix.m02_),
  39. m10_(matrix.m10_),
  40. m11_(matrix.m11_),
  41. m12_(matrix.m12_),
  42. m20_(matrix.m20_),
  43. m21_(matrix.m21_),
  44. m22_(matrix.m22_)
  45. {
  46. }
  47. /// Construct from values.
  48. Matrix3(float v00, float v01, float v02,
  49. float v10, float v11, float v12,
  50. float v20, float v21, float v22) :
  51. m00_(v00),
  52. m01_(v01),
  53. m02_(v02),
  54. m10_(v10),
  55. m11_(v11),
  56. m12_(v12),
  57. m20_(v20),
  58. m21_(v21),
  59. m22_(v22)
  60. {
  61. }
  62. /// Construct from a float array.
  63. Matrix3(const float* data) :
  64. m00_(data[0]),
  65. m01_(data[1]),
  66. m02_(data[2]),
  67. m10_(data[3]),
  68. m11_(data[4]),
  69. m12_(data[5]),
  70. m20_(data[6]),
  71. m21_(data[7]),
  72. m22_(data[8])
  73. {
  74. }
  75. /// Assign from another matrix.
  76. Matrix3& operator = (const Matrix3& rhs)
  77. {
  78. m00_ = rhs.m00_;
  79. m01_ = rhs.m01_;
  80. m02_ = rhs.m02_;
  81. m10_ = rhs.m10_;
  82. m11_ = rhs.m11_;
  83. m12_ = rhs.m12_;
  84. m20_ = rhs.m20_;
  85. m21_ = rhs.m21_;
  86. m22_ = rhs.m22_;
  87. return *this;
  88. }
  89. /// Test for equality with another matrix without epsilon.
  90. bool operator == (const Matrix3& rhs) const
  91. {
  92. const float* leftData = Data();
  93. const float* rightData = rhs.Data();
  94. for (unsigned i = 0; i < 9; ++i)
  95. {
  96. if (leftData[i] != rightData[i])
  97. return false;
  98. }
  99. return true;
  100. }
  101. /// Test for inequality with another matrix without epsilon.
  102. bool operator != (const Matrix3& rhs) const { return !(*this == rhs); }
  103. /// Multiply a Vector3.
  104. Vector3 operator * (const Vector3& rhs) const
  105. {
  106. return Vector3(
  107. m00_ * rhs.x_ + m01_ * rhs.y_ + m02_ * rhs.z_,
  108. m10_ * rhs.x_ + m11_ * rhs.y_ + m12_ * rhs.z_,
  109. m20_ * rhs.x_ + m21_ * rhs.y_ + m22_ * rhs.z_
  110. );
  111. }
  112. /// Add a matrix.
  113. Matrix3 operator + (const Matrix3& rhs) const
  114. {
  115. return Matrix3(
  116. m00_ + rhs.m00_,
  117. m01_ + rhs.m01_,
  118. m02_ + rhs.m02_,
  119. m10_ + rhs.m10_,
  120. m11_ + rhs.m11_,
  121. m12_ + rhs.m12_,
  122. m20_ + rhs.m20_,
  123. m21_ + rhs.m21_,
  124. m22_ + rhs.m22_
  125. );
  126. }
  127. /// Subtract a matrix.
  128. Matrix3 operator - (const Matrix3& rhs) const
  129. {
  130. return Matrix3(
  131. m00_ - rhs.m00_,
  132. m01_ - rhs.m01_,
  133. m02_ - rhs.m02_,
  134. m10_ - rhs.m10_,
  135. m11_ - rhs.m11_,
  136. m12_ - rhs.m12_,
  137. m20_ - rhs.m20_,
  138. m21_ - rhs.m21_,
  139. m22_ - rhs.m22_
  140. );
  141. }
  142. /// Multiply with a scalar.
  143. Matrix3 operator * (float rhs) const
  144. {
  145. return Matrix3(
  146. m00_ * rhs,
  147. m01_ * rhs,
  148. m02_ * rhs,
  149. m10_ * rhs,
  150. m11_ * rhs,
  151. m12_ * rhs,
  152. m20_ * rhs,
  153. m21_ * rhs,
  154. m22_ * rhs
  155. );
  156. }
  157. /// Multiply a matrix.
  158. Matrix3 operator * (const Matrix3& rhs) const
  159. {
  160. return Matrix3(
  161. m00_ * rhs.m00_ + m01_ * rhs.m10_ + m02_ * rhs.m20_,
  162. m00_ * rhs.m01_ + m01_ * rhs.m11_ + m02_ * rhs.m21_,
  163. m00_ * rhs.m02_ + m01_ * rhs.m12_ + m02_ * rhs.m22_,
  164. m10_ * rhs.m00_ + m11_ * rhs.m10_ + m12_ * rhs.m20_,
  165. m10_ * rhs.m01_ + m11_ * rhs.m11_ + m12_ * rhs.m21_,
  166. m10_ * rhs.m02_ + m11_ * rhs.m12_ + m12_ * rhs.m22_,
  167. m20_ * rhs.m00_ + m21_ * rhs.m10_ + m22_ * rhs.m20_,
  168. m20_ * rhs.m01_ + m21_ * rhs.m11_ + m22_ * rhs.m21_,
  169. m20_ * rhs.m02_ + m21_ * rhs.m12_ + m22_ * rhs.m22_
  170. );
  171. }
  172. /// Set scaling elements.
  173. void SetScale(const Vector3& scale)
  174. {
  175. m00_ = scale.x_;
  176. m11_ = scale.y_;
  177. m22_ = scale.z_;
  178. }
  179. /// Set uniform scaling elements.
  180. void SetScale(float scale)
  181. {
  182. m00_ = scale;
  183. m11_ = scale;
  184. m22_ = scale;
  185. }
  186. /// Return the scaling part.
  187. Vector3 Scale() const
  188. {
  189. return Vector3(
  190. sqrtf(m00_ * m00_ + m10_ * m10_ + m20_ * m20_),
  191. sqrtf(m01_ * m01_ + m11_ * m11_ + m21_ * m21_),
  192. sqrtf(m02_ * m02_ + m12_ * m12_ + m22_ * m22_)
  193. );
  194. }
  195. /// Return transpose.
  196. Matrix3 Transpose() const
  197. {
  198. return Matrix3(
  199. m00_,
  200. m10_,
  201. m20_,
  202. m01_,
  203. m11_,
  204. m21_,
  205. m02_,
  206. m12_,
  207. m22_
  208. );
  209. }
  210. /// Return scaled by a vector.
  211. Matrix3 Scaled(const Vector3& scale) const
  212. {
  213. return Matrix3(
  214. m00_ * scale.x_,
  215. m01_ * scale.y_,
  216. m02_ * scale.z_,
  217. m10_ * scale.x_,
  218. m11_ * scale.y_,
  219. m12_ * scale.z_,
  220. m20_ * scale.x_,
  221. m21_ * scale.y_,
  222. m22_ * scale.z_
  223. );
  224. }
  225. /// Test for equality with another matrix with epsilon.
  226. bool Equals(const Matrix3& rhs) const
  227. {
  228. const float* leftData = Data();
  229. const float* rightData = rhs.Data();
  230. for (unsigned i = 0; i < 9; ++i)
  231. {
  232. if (!Urho3D::Equals(leftData[i], rightData[i]))
  233. return false;
  234. }
  235. return true;
  236. }
  237. /// Return inverse.
  238. Matrix3 Inverse() const;
  239. /// Return float data.
  240. const float* Data() const { return &m00_; }
  241. float m00_;
  242. float m01_;
  243. float m02_;
  244. float m10_;
  245. float m11_;
  246. float m12_;
  247. float m20_;
  248. float m21_;
  249. float m22_;
  250. /// Bulk transpose matrices.
  251. static void BulkTranspose(float* dest, const float* src, unsigned count)
  252. {
  253. for (unsigned i = 0; i < count; ++i)
  254. {
  255. dest[0] = src[0];
  256. dest[1] = src[3];
  257. dest[2] = src[6];
  258. dest[3] = src[1];
  259. dest[4] = src[4];
  260. dest[5] = src[7];
  261. dest[6] = src[2];
  262. dest[7] = src[5];
  263. dest[8] = src[8];
  264. dest += 9;
  265. src += 9;
  266. }
  267. }
  268. /// Zero matrix.
  269. static const Matrix3 ZERO;
  270. /// Identity matrix.
  271. static const Matrix3 IDENTITY;
  272. };
  273. /// Multiply a 3x3 matrix with a scalar.
  274. inline Matrix3 operator * (float lhs, const Matrix3& rhs) { return rhs * lhs; }
  275. }