00001 #ifndef __MAT33_H__
00002 #define __MAT33_H__
00003
00004 #include <math/config.hpp>
00005 #include <math/vecbase.hpp>
00006
00007 namespace math {
00008 template<typename T> class mat33: public math::matsqu<T,3> {
00009 public:
00010
00011
00012 mat33(T e0, T e1, T e2, T e3, T e4, T e5, T e6, T e7, T e8) {
00013 matsqu<T,3>::v(0,0)=e0;
00014 matsqu<T,3>::v(0,1)=e1;
00015 matsqu<T,3>::v(0,2)=e2;
00016 matsqu<T,3>::v(1,0)=e3;
00017 matsqu<T,3>::v(1,1)=e4;
00018 matsqu<T,3>::v(1,2)=e5;
00019 matsqu<T,3>::v(2,0)=e6;
00020 matsqu<T,3>::v(2,1)=e7;
00021 matsqu<T,3>::v(2,2)=e8;
00022 }
00023 mat33(math::mat33<T> const & rhs): math::matsqu<T,3>(rhs) {}
00024 mat33(const T * rhs): math::matsqu<T,3>(rhs) {}
00025 mat33(vec3<T> const & rhs) {
00026 loadIdentity();
00027 matsqu<T,3>::v(0,0) = rhs.v[0];
00028 matsqu<T,3>::v(1,1) = rhs.v[1];
00029 matsqu<T,3>::v(2,2) = rhs.v[2];
00030 }
00031 void setDiagonal(T x, T y, T z) {
00032 matsqu<T,3>::loadZero();
00033 matsqu<T,3>::v(0,0) = x;
00034 matsqu<T,3>::v(1,1) = y;
00035 matsqu<T,3>::v(2,2) = z;
00036 }
00037 void setRotation(math::quat<T> const & q) {
00038 const T x = q.x;
00039 const T y = q.y;
00040 const T z = q.z;
00041 const T w = q.w;
00042
00043 const T x2 = x + x;
00044 const T y2 = y + y;
00045 const T z2 = z + z;
00046
00047 const T xx = x2*x;
00048 const T yy = y2*y;
00049 const T zz = z2*z;
00050
00051 const T xy = x2*y;
00052 const T xz = x2*z;
00053 const T xw = x2*w;
00054
00055 const T yz = y2*z;
00056 const T yw = y2*w;
00057 const T zw = z2*w;
00058
00059 matsqu<T,3>::v(0,0) = 1.0f - yy - zz;
00060 matsqu<T,3>::v(0,1) = xy + zw;
00061 matsqu<T,3>::v(0,2) = xz - yw;
00062
00063 matsqu<T,3>::v(1,0) = xy - zw;
00064 matsqu<T,3>::v(1,1) = 1.0f - xx - zz;
00065 matsqu<T,3>::v(1,2) = yz + xw;
00066
00067 matsqu<T,3>::v(2,0) = xz + yw;
00068 matsqu<T,3>::v(2,1) = yz - xw;
00069 matsqu<T,3>::v(2,2) = 1.0f - xx - yy;
00070 }
00071 math::vec3<T> getRow(int position) const {
00072 math::vec3<T> ret(matsqu<T,3>::getRow());
00073 return ret;
00074 }
00075 math::vec3<T> getColumn(int position) const {
00076 math::vec3<T> ret(matsqu<T,3>::getColumn());
00077 return ret;
00078 }
00079 void loadIdentity() {
00080 matsqu<T,3>::loadZero();
00081 matsqu<T,3>::v(0,0) = 1.0;
00082 matsqu<T,3>::v(1,1) = 1.0;
00083 matsqu<T,3>::v(2,2) = 1.0;
00084 }
00085 math::mat33<T> operator+(math::mat33<T> const & rhs) const {
00086 return matbase<T,3,3>::operator+(rhs);
00087 }
00088 math::mat33<T> operator-(math::mat33<T> const & rhs) const {
00089 return matbase<T,3,3>::operator-(rhs);
00090 }
00091 math::mat33<T> operator*(math::mat33<T> const & rhs) const {
00092 return math::matbase<T,3,3>::operator*(rhs);
00093 }
00094 math::mat33<T> operator*(T const & rhs) const {
00095 return vecbase<T,9>::operator*(rhs);
00096 }
00097 math::mat33<T> operator/(T const & rhs) const {
00098 if (rhs==0.0f || rhs==1.0f)
00099 return (*this);
00100
00101 T temp=1/rhs;
00102
00103 return (*this)*temp;
00104 }
00105 bool operator==(math::mat33<T> const & rhs) const {
00106 return math::vecbase<T,9>::operator==(rhs);
00107 }
00108 bool operator!=(const math::mat33<T> & rhs) const {
00109 return math::vecbase<T,9>::operator!=(rhs);
00110 }
00111 void operator+=(const math::mat33<T> & rhs) {
00112 math::matsqu<T,3>::operator+=(rhs);
00113 }
00114 void operator-=(const math::mat33<T> & rhs) {
00115 math::matsqu<T,3>::operator-=(rhs);
00116 }
00117 void operator*=(const math::mat33<T> & rhs) {
00118 (*this) = (*this) * rhs;
00119 }
00120 math::vec3<T> operator*(const vec3<T> rhs) const {
00121 return math::matsqu<T,3>::operator*(rhs);
00122 }
00123
00124
00125 math::vec3<T> getRotatedVector3D(const vec3<T> & rhs) const
00126 {
00127 return operator*(rhs);
00128
00129
00130
00131 }
00132 math::vec3<T> getInverseRotatedVector3D(const vec3<T> & rhs) const
00133 {
00134
00135 return getTranspose() * rhs;
00136 }
00137 void invert() {
00138 *this = getInverse();
00139 }
00140 math::mat33<T> getInverse() const {
00141 math::mat33<T> result = getInverseTranspose();
00142
00143 result.Transpose();
00144
00145 return result;
00146 }
00147 void transpose() {
00148 *this = getTranspose();
00149 }
00150 math::mat33<T> getTranspose(void) const {
00151 return math::mat33<T>(
00152 vecbase<T,9>::v[0], vecbase<T,9>::v[3], vecbase<T,9>::v[6],
00153 vecbase<T,9>::v[1], vecbase<T,9>::v[4], vecbase<T,9>::v[7],
00154 vecbase<T,9>::v[2], vecbase<T,9>::v[5], vecbase<T,9>::v[8]);
00155 }
00156 void invertTranspose(void) {
00157 *this = getInverseTranspose();
00158 }
00159 math::mat33<T> getInverseTranspose(void) const {
00160 math::mat33<T> result;
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257 return result;
00258 }
00259 void setRotationAxis(const T angle, const vec3<T> & axis) {
00260 vec3<T> u=axis.GetNormalized();
00261
00262 T sinAngle=(T)sin(M_PI*angle/180);
00263 T cosAngle=(T)cos(M_PI*angle/180);
00264 T oneMinusCosAngle=1.0f-cosAngle;
00265
00266 loadIdentity();
00267
00268 vecbase<T,9>::v[0] = (u.v[0])*(u.v[0]) + cosAngle*(1-(u.v[0])*(u.v[0]));
00269 vecbase<T,9>::v[4] = (u.v[0])*(u.v[1])*(oneMinusCosAngle) - sinAngle*u.v[2];
00270 vecbase<T,9>::v[8] = (u.v[0])*(u.v[2])*(oneMinusCosAngle) + sinAngle*u.v[1];
00271
00272 vecbase<T,9>::v[1] = (u.v[0])*(u.v[1])*(oneMinusCosAngle) + sinAngle*u.v[2];
00273 vecbase<T,9>::v[5] = (u.v[1])*(u.v[1]) + cosAngle*(1-(u.v[1])*(u.v[1]));
00274 vecbase<T,9>::v[9] = (u.v[1])*(u.v[2])*(oneMinusCosAngle) - sinAngle*u.v[0];
00275
00276 vecbase<T,9>::v[2] = (u.v[0])*(u.v[2])*(oneMinusCosAngle) - sinAngle*u.v[1];
00277 vecbase<T,9>::v[6] = (u.v[1])*(u.v[2])*(oneMinusCosAngle) + sinAngle*u.v[0];
00278 vecbase<T,9>::v[10] = (u.v[2])*(u.v[2]) + cosAngle*(1-(u.v[2])*(u.v[2]));
00279 }
00280 void setRotationX(const T angle) {
00281 loadIdentity();
00282
00283 vecbase<T,9>::v[4] = (T)cos(M_PI*angle/180);
00284 vecbase<T,9>::v[5] = (T)sin(M_PI*angle/180);
00285
00286 vecbase<T,9>::v[6] = -vecbase<T,9>::v[6];
00287 vecbase<T,9>::v[7]= vecbase<T,9>::v[5];
00288 }
00289 void setRotationY(const T angle) {
00290 loadIdentity();
00291
00292 vecbase<T,9>::v[0]=(T)cos(M_PI*angle/180);
00293 vecbase<T,9>::v[2]=-(T)sin(M_PI*angle/180);
00294
00295 vecbase<T,9>::v[6]=-vecbase<T,9>::v[2];
00296 vecbase<T,9>::v[8]=vecbase<T,9>::v[0];
00297 }
00298 void setRotationZ(const T angle) {
00299 loadIdentity();
00300
00301 vecbase<T,9>::v[0]=(T)cos(M_PI*angle/180);
00302 vecbase<T,9>::v[1]=(T)sin(M_PI*angle/180);
00303
00304 vecbase<T,9>::v[3]=-vecbase<T,9>::v[1];
00305 vecbase<T,9>::v[4]=vecbase<T,9>::v[0];
00306 }
00307 void setRotationEuler(const T angleX, const T angleY, const T angleZ) {
00308 T cr = cos( M_PI*angleX/180 );
00309 T sr = sin( M_PI*angleX/180 );
00310 T cp = cos( M_PI*angleY/180 );
00311 T sp = sin( M_PI*angleY/180 );
00312 T cy = cos( M_PI*angleZ/180 );
00313 T sy = sin( M_PI*angleZ/180 );
00314
00315 vecbase<T,9>::v[0] = ( T )( cp*cy );
00316 vecbase<T,9>::v[1] = ( T )( cp*sy );
00317 vecbase<T,9>::v[2] = ( T )( -sp );
00318
00319 T srsp = sr*sp;
00320 T crsp = cr*sp;
00321
00322 vecbase<T,9>::v[3] = ( T )( srsp*cy-cr*sy );
00323 vecbase<T,9>::v[4] = ( T )( srsp*sy+cr*cy );
00324 vecbase<T,9>::v[5] = ( T )( sr*cp );
00325
00326 vecbase<T,9>::v[6] = ( T )( crsp*cy+sr*sy );
00327 vecbase<T,9>::v[7] = ( T )( crsp*sy-sr*cy );
00328 vecbase<T,9>::v[8] = ( T )( cr*cp );
00329 }
00330 void rotateVector3D(math::vec3<T> & rhs) const {
00331 rhs = GetRotatedVector3D(rhs);
00332 }
00333 void inverseRotateVector3D(math::vec3<T> & rhs) const
00334 {
00335 rhs=GetInverseRotatedVector3D(rhs);
00336 }
00337
00338
00339 ~mat33() {}
00340
00341
00342 operator T* () const {return (T*) this;}
00343 operator const T* () const {return (const T*) this;}
00344
00345
00346
00347 };
00348 }
00349
00350 #endif //mat44_H