00001
00011
00012
00013 #if (_MSC_VER > 1000) || defined(SGI_COMPILER)
00014 #pragma once
00015 #endif
00016
00017 #ifndef __XSIMATRIX4F_H__
00018 #define __XSIMATRIX4F_H__
00019
00020 #include "sicppsdk.h"
00021 #include "math.h"
00022
00023 namespace XSI {
00024 namespace MATH {
00025
00026
00031
00032 class SICPPSDKDECL CMatrix4f
00033 {
00034 public:
00035
00037 SICPPSDK_INLINE CMatrix4f();
00038
00057 SICPPSDK_INLINE CMatrix4f(float in_f00, float in_f01, float in_f02, float in_f03,
00058 float in_f10, float in_f11, float in_f12, float in_f13,
00059 float in_f20, float in_f21, float in_f22, float in_f23,
00060 float in_f30, float in_f31, float in_f32, float in_f33);
00061
00065 SICPPSDK_INLINE CMatrix4f( const CMatrix4f& in_matrix4 );
00066
00068 SICPPSDK_INLINE ~CMatrix4f();
00069
00074 SICPPSDK_INLINE CMatrix4f & operator=( const CMatrix4f & in_matrix4 );
00075
00081 SICPPSDK_INLINE CMatrix4f & operator*=(const CMatrix4f & in_matrix4);
00082
00086 SICPPSDK_INLINE CMatrix4f& SetIdentity();
00087
00091 SICPPSDK_INLINE bool InvertInPlace();
00092
00097 SICPPSDK_INLINE bool Invert(const CMatrix4f& in_matrix4);
00098
00103 SICPPSDK_INLINE bool TransposeInverseInPlace();
00104
00110 SICPPSDK_INLINE bool TransposeInverse(const CMatrix4f& in_matrix4);
00111
00114 SICPPSDK_INLINE void TransposeInPlace();
00115
00119 SICPPSDK_INLINE void Transpose(const CMatrix4f& in_matrix4);
00120
00126 SICPPSDK_INLINE CMatrix4f& MulInPlace(const CMatrix4f& in_matrix4);
00127
00134 SICPPSDK_INLINE CMatrix4f& Mul(const CMatrix4f& in_matrix4A, const CMatrix4f& in_matrix4B);
00135
00154 SICPPSDK_INLINE void Get
00155 (
00156 float& io_f00, float& io_f01, float& io_f02, float& io_f03,
00157 float& io_f10, float& io_f11, float& io_f12, float& io_f13,
00158 float& io_f20, float& io_f21, float& io_f22, float& io_f23,
00159 float& io_f30, float& io_f31, float& io_f32, float& io_f33
00160 ) const;
00161
00180 SICPPSDK_INLINE void Set( float in_f00, float in_f01, float in_f02, float in_f03,
00181 float in_f10, float in_f11, float in_f12, float in_f13,
00182 float in_f20, float in_f21, float in_f22, float in_f23,
00183 float in_f30, float in_f31, float in_f32, float in_f33);
00184
00188 SICPPSDK_INLINE float* Get();
00189
00193 SICPPSDK_INLINE void Set(const float in_vals[4][4]);
00194
00200 SICPPSDK_INLINE float GetValue(short in_sRow,short in_sCol )const;
00201
00207 SICPPSDK_INLINE void SetValue(short in_sRow, short in_sCol, float in_fVal );
00208
00214 SICPPSDK_INLINE bool EpsilonEquals
00215 (
00216 const CMatrix4f& in_matrix4,
00217 float in_fEpsilon
00218 ) const;
00219
00224 SICPPSDK_INLINE bool Equals(const CMatrix4f& in_matrix4) const;
00225
00231 SICPPSDK_INLINE bool operator ==(const CMatrix4f & in_matrix4 ) const;
00232
00238 SICPPSDK_INLINE bool operator !=(const CMatrix4f & in_matrix4 ) const;
00239
00246 SICPPSDK_INLINE bool operator < (const CMatrix4f& in_matrix4 )const;
00247
00248 private:
00249 float m_fMat[4][4];
00250
00251 SICPPSDK_INLINE bool ComputeInverse
00252 (
00253 const float in_fMat[4][4],
00254 float out_fInv[4][4],
00255 const bool bTransposeResult = false
00256 );
00257 };
00258
00259
00260 SICPPSDK_INLINE CMatrix4f::CMatrix4f()
00261 {
00262 m_fMat[0][0] = 0.0;
00263 m_fMat[0][1] = 0.0;
00264 m_fMat[0][2] = 0.0;
00265 m_fMat[0][3] = 0.0;
00266 m_fMat[1][0] = 0.0;
00267 m_fMat[1][1] = 0.0;
00268 m_fMat[1][2] = 0.0;
00269 m_fMat[1][3] = 0.0;
00270 m_fMat[2][0] = 0.0;
00271 m_fMat[2][1] = 0.0;
00272 m_fMat[2][2] = 0.0;
00273 m_fMat[2][3] = 0.0;
00274 m_fMat[3][0] = 0.0;
00275 m_fMat[3][1] = 0.0;
00276 m_fMat[3][2] = 0.0;
00277 m_fMat[3][3] = 0.0;
00278 }
00279
00280 SICPPSDK_INLINE CMatrix4f::CMatrix4f
00281 (
00282 float in_f00, float in_f01, float in_f02, float in_f03,
00283 float in_f10, float in_f11, float in_f12, float in_f13,
00284 float in_f20, float in_f21, float in_f22, float in_f23,
00285 float in_f30, float in_f31, float in_f32, float in_f33
00286 )
00287 {
00288 m_fMat[0][0] = in_f00;
00289 m_fMat[0][1] = in_f01;
00290 m_fMat[0][2] = in_f02;
00291 m_fMat[0][3] = in_f03;
00292 m_fMat[1][0] = in_f10;
00293 m_fMat[1][1] = in_f11;
00294 m_fMat[1][2] = in_f12;
00295 m_fMat[1][3] = in_f13;
00296 m_fMat[2][0] = in_f20;
00297 m_fMat[2][1] = in_f21;
00298 m_fMat[2][2] = in_f22;
00299 m_fMat[2][3] = in_f23;
00300 m_fMat[3][0] = in_f30;
00301 m_fMat[3][1] = in_f31;
00302 m_fMat[3][2] = in_f32;
00303 m_fMat[3][3] = in_f33;
00304 }
00305
00306 SICPPSDK_INLINE CMatrix4f::CMatrix4f(const CMatrix4f& in_matrix4)
00307 {
00308 m_fMat[0][0] = in_matrix4.m_fMat[0][0];
00309 m_fMat[0][1] = in_matrix4.m_fMat[0][1];
00310 m_fMat[0][2] = in_matrix4.m_fMat[0][2];
00311 m_fMat[0][3] = in_matrix4.m_fMat[0][3];
00312 m_fMat[1][0] = in_matrix4.m_fMat[1][0];
00313 m_fMat[1][1] = in_matrix4.m_fMat[1][1];
00314 m_fMat[1][2] = in_matrix4.m_fMat[1][2];
00315 m_fMat[1][3] = in_matrix4.m_fMat[1][3];
00316 m_fMat[2][0] = in_matrix4.m_fMat[2][0];
00317 m_fMat[2][1] = in_matrix4.m_fMat[2][1];
00318 m_fMat[2][2] = in_matrix4.m_fMat[2][2];
00319 m_fMat[2][3] = in_matrix4.m_fMat[2][3];
00320 m_fMat[3][0] = in_matrix4.m_fMat[3][0];
00321 m_fMat[3][1] = in_matrix4.m_fMat[3][1];
00322 m_fMat[3][2] = in_matrix4.m_fMat[3][2];
00323 m_fMat[3][3] = in_matrix4.m_fMat[3][3];
00324 }
00325
00326 SICPPSDK_INLINE CMatrix4f::~CMatrix4f()
00327 {}
00328
00329 SICPPSDK_INLINE CMatrix4f& CMatrix4f::operator=( const CMatrix4f & in_matrix4 )
00330 {
00331 m_fMat[0][0] = in_matrix4.m_fMat[0][0];
00332 m_fMat[0][1] = in_matrix4.m_fMat[0][1];
00333 m_fMat[0][2] = in_matrix4.m_fMat[0][2];
00334 m_fMat[0][3] = in_matrix4.m_fMat[0][3];
00335 m_fMat[1][0] = in_matrix4.m_fMat[1][0];
00336 m_fMat[1][1] = in_matrix4.m_fMat[1][1];
00337 m_fMat[1][2] = in_matrix4.m_fMat[1][2];
00338 m_fMat[1][3] = in_matrix4.m_fMat[1][3];
00339 m_fMat[2][0] = in_matrix4.m_fMat[2][0];
00340 m_fMat[2][1] = in_matrix4.m_fMat[2][1];
00341 m_fMat[2][2] = in_matrix4.m_fMat[2][2];
00342 m_fMat[2][3] = in_matrix4.m_fMat[2][3];
00343 m_fMat[3][0] = in_matrix4.m_fMat[3][0];
00344 m_fMat[3][1] = in_matrix4.m_fMat[3][1];
00345 m_fMat[3][2] = in_matrix4.m_fMat[3][2];
00346 m_fMat[3][3] = in_matrix4.m_fMat[3][3];
00347 return *this;
00348 }
00349
00350 SICPPSDK_INLINE CMatrix4f& CMatrix4f::operator*=(const CMatrix4f& in_matrix4)
00351 {
00352 return MulInPlace(in_matrix4);
00353 }
00354
00355 SICPPSDK_INLINE CMatrix4f& CMatrix4f::SetIdentity()
00356 {
00357 m_fMat[0][0] = 1.0;
00358 m_fMat[0][1] = 0.0;
00359 m_fMat[0][2] = 0.0;
00360 m_fMat[0][3] = 0.0;
00361 m_fMat[1][0] = 0.0;
00362 m_fMat[1][1] = 1.0;
00363 m_fMat[1][2] = 0.0;
00364 m_fMat[1][3] = 0.0;
00365 m_fMat[2][0] = 0.0;
00366 m_fMat[2][1] = 0.0;
00367 m_fMat[2][2] = 1.0;
00368 m_fMat[2][3] = 0.0;
00369 m_fMat[3][0] = 0.0;
00370 m_fMat[3][1] = 0.0;
00371 m_fMat[3][2] = 0.0;
00372 m_fMat[3][3] = 1.0;
00373 return *this;
00374 }
00375
00376 SICPPSDK_INLINE bool CMatrix4f::InvertInPlace()
00377 {
00378 return Invert(*this);
00379 }
00380
00381 SICPPSDK_INLINE bool CMatrix4f::Invert(const CMatrix4f& in_matrix4)
00382 {
00383 float fInv[4][4];
00384
00385 if (ComputeInverse(in_matrix4.m_fMat, fInv))
00386 {
00387 Set(fInv);
00388 return true;
00389 }
00390 else
00391 {
00392 return false;
00393 }
00394 }
00395
00396 SICPPSDK_INLINE bool CMatrix4f::TransposeInverseInPlace()
00397 {
00398 return TransposeInverse(*this);
00399 }
00400
00401 SICPPSDK_INLINE bool CMatrix4f::TransposeInverse(const CMatrix4f& in_matrix4)
00402 {
00403 float fTransInv[4][4];
00404
00405 if(ComputeInverse(in_matrix4.m_fMat, fTransInv, true))
00406 {
00407 Set(fTransInv);
00408 return true;
00409 }
00410 else
00411 {
00412 return false;
00413 }
00414 }
00415
00416 SICPPSDK_INLINE void CMatrix4f::TransposeInPlace()
00417 {
00418 Transpose(*this);
00419 }
00420
00421 SICPPSDK_INLINE void CMatrix4f::Transpose(const CMatrix4f& in_matrix4)
00422 {
00423 float dTempMat[4][4];
00424 for(int nR=0; nR<4; nR++)
00425 for(int nC=0; nC<4; nC++)
00426 dTempMat[nR][nC] = in_matrix4.m_fMat[nC][nR];
00427 Set(dTempMat);
00428 }
00429
00430 SICPPSDK_INLINE CMatrix4f& CMatrix4f::MulInPlace(const CMatrix4f& in_matrix4)
00431 {
00432 return Mul(*this,in_matrix4);
00433 }
00434
00435 SICPPSDK_INLINE CMatrix4f& CMatrix4f::Mul
00436 (
00437 const CMatrix4f& in_matrix4A,
00438 const CMatrix4f& in_matrix4B
00439 )
00440 {
00441 float dTempMat[4][4];
00442
00443 for(int nR=0; nR<4; nR++)
00444 for(int nC=0; nC<4; nC++)
00445 dTempMat[nR][nC] =
00446 in_matrix4A.m_fMat[nR][0] * in_matrix4B.m_fMat[0][nC] +
00447 in_matrix4A.m_fMat[nR][1] * in_matrix4B.m_fMat[1][nC] +
00448 in_matrix4A.m_fMat[nR][2] * in_matrix4B.m_fMat[2][nC] +
00449 in_matrix4A.m_fMat[nR][3] * in_matrix4B.m_fMat[3][nC];
00450
00451 Set(dTempMat);
00452 return (*this);
00453 }
00454
00455 SICPPSDK_INLINE void CMatrix4f::Get
00456 (
00457 float& io_f00, float& io_f01, float& io_f02, float& io_f03,
00458 float& io_f10, float& io_f11, float& io_f12, float& io_f13,
00459 float& io_f20, float& io_f21, float& io_f22, float& io_f23,
00460 float& io_f30, float& io_f31, float& io_f32, float& io_f33
00461 ) const
00462 {
00463
00464 io_f00 = m_fMat[0][0];
00465 io_f01 = m_fMat[0][1];
00466 io_f02 = m_fMat[0][2];
00467 io_f03 = m_fMat[0][3];
00468 io_f10 = m_fMat[1][0];
00469 io_f11 = m_fMat[1][1];
00470 io_f12 = m_fMat[1][2];
00471 io_f13 = m_fMat[1][3];
00472 io_f20 = m_fMat[2][0];
00473 io_f21 = m_fMat[2][1];
00474 io_f22 = m_fMat[2][2];
00475 io_f23 = m_fMat[2][3];
00476 io_f30 = m_fMat[3][0];
00477 io_f31 = m_fMat[3][1];
00478 io_f32 = m_fMat[3][2];
00479 io_f33 = m_fMat[3][3];
00480 }
00481
00482 SICPPSDK_INLINE void CMatrix4f::Set
00483 (
00484 float in_f00, float in_f01, float in_f02, float in_f03,
00485 float in_f10, float in_f11, float in_f12, float in_f13,
00486 float in_f20, float in_f21, float in_f22, float in_f23,
00487 float in_f30, float in_f31, float in_f32, float in_f33
00488 )
00489 {
00490 m_fMat[0][0] = in_f00;
00491 m_fMat[0][1] = in_f01;
00492 m_fMat[0][2] = in_f02;
00493 m_fMat[0][3] = in_f03;
00494 m_fMat[1][0] = in_f10;
00495 m_fMat[1][1] = in_f11;
00496 m_fMat[1][2] = in_f12;
00497 m_fMat[1][3] = in_f13;
00498 m_fMat[2][0] = in_f20;
00499 m_fMat[2][1] = in_f21;
00500 m_fMat[2][2] = in_f22;
00501 m_fMat[2][3] = in_f23;
00502 m_fMat[3][0] = in_f30;
00503 m_fMat[3][1] = in_f31;
00504 m_fMat[3][2] = in_f32;
00505 m_fMat[3][3] = in_f33;
00506 }
00507
00508 SICPPSDK_INLINE void CMatrix4f::Set(const float in_matrix4[4][4])
00509 {
00510 m_fMat[0][0] = in_matrix4[0][0];
00511 m_fMat[0][1] = in_matrix4[0][1];
00512 m_fMat[0][2] = in_matrix4[0][2];
00513 m_fMat[0][3] = in_matrix4[0][3];
00514 m_fMat[1][0] = in_matrix4[1][0];
00515 m_fMat[1][1] = in_matrix4[1][1];
00516 m_fMat[1][2] = in_matrix4[1][2];
00517 m_fMat[1][3] = in_matrix4[1][3];
00518 m_fMat[2][0] = in_matrix4[2][0];
00519 m_fMat[2][1] = in_matrix4[2][1];
00520 m_fMat[2][2] = in_matrix4[2][2];
00521 m_fMat[2][3] = in_matrix4[2][3];
00522 m_fMat[3][0] = in_matrix4[3][0];
00523 m_fMat[3][1] = in_matrix4[3][1];
00524 m_fMat[3][2] = in_matrix4[3][2];
00525 m_fMat[3][3] = in_matrix4[3][3];
00526 }
00527
00528 SICPPSDK_INLINE float* CMatrix4f::Get()
00529 {
00530 return &m_fMat[0][0];
00531 }
00532
00533 SICPPSDK_INLINE float CMatrix4f::GetValue(short in_sRow,short in_sCol ) const
00534 {
00535 bool l_bValidIndex = ( in_sRow >=0 && in_sCol >= 0 &&
00536 in_sRow <=3 && in_sCol <= 3);
00537 assert(l_bValidIndex);
00538
00539 if(l_bValidIndex)
00540 {
00541 return m_fMat[in_sRow][in_sCol];
00542 }
00543 return 0.0;
00544 }
00545
00546 SICPPSDK_INLINE void CMatrix4f::SetValue(short in_sRow, short in_sCol, float in_fVal )
00547 {
00548 bool l_bValidIndex = ( in_sRow >=0 && in_sCol >= 0 && in_sRow <=3 && in_sCol <= 3);
00549
00550 assert(l_bValidIndex);
00551 if(l_bValidIndex)
00552 {
00553 m_fMat[in_sRow][in_sCol] = in_fVal;
00554 }
00555 }
00556
00557 SICPPSDK_INLINE bool CMatrix4f::EpsilonEquals
00558 (
00559 const CMatrix4f& in_matrix4,
00560 float in_fEpsilon
00561 ) const
00562 {
00563 return (this == &in_matrix4) ? true :
00564 ::fabs(m_fMat[0][0] - in_matrix4.m_fMat[0][0]) < ::fabs(in_fEpsilon) &&
00565 ::fabs(m_fMat[0][1] - in_matrix4.m_fMat[0][1]) < ::fabs(in_fEpsilon) &&
00566 ::fabs(m_fMat[0][2] - in_matrix4.m_fMat[0][2]) < ::fabs(in_fEpsilon) &&
00567 ::fabs(m_fMat[0][3] - in_matrix4.m_fMat[0][3]) < ::fabs(in_fEpsilon) &&
00568 ::fabs(m_fMat[1][0] - in_matrix4.m_fMat[1][0]) < ::fabs(in_fEpsilon) &&
00569 ::fabs(m_fMat[1][1] - in_matrix4.m_fMat[1][1]) < ::fabs(in_fEpsilon) &&
00570 ::fabs(m_fMat[1][2] - in_matrix4.m_fMat[1][2]) < ::fabs(in_fEpsilon) &&
00571 ::fabs(m_fMat[1][3] - in_matrix4.m_fMat[1][3]) < ::fabs(in_fEpsilon) &&
00572 ::fabs(m_fMat[2][0] - in_matrix4.m_fMat[2][0]) < ::fabs(in_fEpsilon) &&
00573 ::fabs(m_fMat[2][1] - in_matrix4.m_fMat[2][1]) < ::fabs(in_fEpsilon) &&
00574 ::fabs(m_fMat[2][2] - in_matrix4.m_fMat[2][2]) < ::fabs(in_fEpsilon) &&
00575 ::fabs(m_fMat[2][3] - in_matrix4.m_fMat[2][3]) < ::fabs(in_fEpsilon) &&
00576 ::fabs(m_fMat[3][0] - in_matrix4.m_fMat[3][0]) < ::fabs(in_fEpsilon) &&
00577 ::fabs(m_fMat[3][1] - in_matrix4.m_fMat[3][1]) < ::fabs(in_fEpsilon) &&
00578 ::fabs(m_fMat[3][2] - in_matrix4.m_fMat[3][2]) < ::fabs(in_fEpsilon) &&
00579 ::fabs(m_fMat[3][3] - in_matrix4.m_fMat[3][3]) < ::fabs(in_fEpsilon);
00580 }
00581
00582 SICPPSDK_INLINE bool CMatrix4f::Equals(const CMatrix4f& in_matrix4) const
00583 {
00584 return (this == &in_matrix4) ? true :
00585 m_fMat[0][0] == in_matrix4.m_fMat[0][0] &&
00586 m_fMat[0][1] == in_matrix4.m_fMat[0][1] &&
00587 m_fMat[0][2] == in_matrix4.m_fMat[0][2] &&
00588 m_fMat[0][3] == in_matrix4.m_fMat[0][3] &&
00589 m_fMat[1][0] == in_matrix4.m_fMat[1][0] &&
00590 m_fMat[1][1] == in_matrix4.m_fMat[1][1] &&
00591 m_fMat[1][2] == in_matrix4.m_fMat[1][2] &&
00592 m_fMat[1][3] == in_matrix4.m_fMat[1][3] &&
00593 m_fMat[2][0] == in_matrix4.m_fMat[2][0] &&
00594 m_fMat[2][1] == in_matrix4.m_fMat[2][1] &&
00595 m_fMat[2][2] == in_matrix4.m_fMat[2][2] &&
00596 m_fMat[2][3] == in_matrix4.m_fMat[2][3] &&
00597 m_fMat[3][0] == in_matrix4.m_fMat[3][0] &&
00598 m_fMat[3][1] == in_matrix4.m_fMat[3][1] &&
00599 m_fMat[3][2] == in_matrix4.m_fMat[3][2] &&
00600 m_fMat[3][3] == in_matrix4.m_fMat[3][3];
00601 }
00602
00603 SICPPSDK_INLINE bool CMatrix4f::operator ==(const CMatrix4f & in_matrix4 ) const
00604 {
00605 return Equals( in_matrix4 );
00606 }
00607
00608 SICPPSDK_INLINE bool CMatrix4f::operator !=(const CMatrix4f & in_matrix4 ) const
00609 {
00610 return ! Equals( in_matrix4 );
00611 }
00612
00613 SICPPSDK_INLINE bool CMatrix4f::operator < (const CMatrix4f& in_matrix4 )const
00614 {
00615 if ( m_fMat[0][0] != in_matrix4.m_fMat[0][0] ) return m_fMat[0][0] < in_matrix4.m_fMat[0][0];
00616 if ( m_fMat[0][1] != in_matrix4.m_fMat[0][1] ) return m_fMat[0][1] < in_matrix4.m_fMat[0][1];
00617 if ( m_fMat[0][2] != in_matrix4.m_fMat[0][2] ) return m_fMat[0][2] < in_matrix4.m_fMat[0][2];
00618 if ( m_fMat[0][3] != in_matrix4.m_fMat[0][3] ) return m_fMat[0][3] < in_matrix4.m_fMat[0][3];
00619 if ( m_fMat[1][0] != in_matrix4.m_fMat[1][0] ) return m_fMat[1][0] < in_matrix4.m_fMat[1][0];
00620 if ( m_fMat[1][1] != in_matrix4.m_fMat[1][1] ) return m_fMat[1][1] < in_matrix4.m_fMat[1][1];
00621 if ( m_fMat[1][2] != in_matrix4.m_fMat[1][2] ) return m_fMat[1][2] < in_matrix4.m_fMat[1][2];
00622 if ( m_fMat[1][3] != in_matrix4.m_fMat[1][3] ) return m_fMat[1][3] < in_matrix4.m_fMat[1][3];
00623 if ( m_fMat[2][0] != in_matrix4.m_fMat[2][0] ) return m_fMat[2][0] < in_matrix4.m_fMat[2][0];
00624 if ( m_fMat[2][1] != in_matrix4.m_fMat[2][1] ) return m_fMat[2][1] < in_matrix4.m_fMat[2][1];
00625 if ( m_fMat[2][2] != in_matrix4.m_fMat[2][2] ) return m_fMat[2][2] < in_matrix4.m_fMat[2][2];
00626 if ( m_fMat[2][3] != in_matrix4.m_fMat[2][3] ) return m_fMat[2][3] < in_matrix4.m_fMat[2][3];
00627 if ( m_fMat[3][0] != in_matrix4.m_fMat[3][0] ) return m_fMat[3][0] < in_matrix4.m_fMat[3][0];
00628 if ( m_fMat[3][1] != in_matrix4.m_fMat[3][1] ) return m_fMat[3][1] < in_matrix4.m_fMat[3][1];
00629 if ( m_fMat[3][2] != in_matrix4.m_fMat[3][2] ) return m_fMat[3][2] < in_matrix4.m_fMat[3][2];
00630 if ( m_fMat[3][3] != in_matrix4.m_fMat[3][3] ) return m_fMat[3][3] < in_matrix4.m_fMat[3][3];
00631 return false;
00632 }
00633
00634 SICPPSDK_INLINE bool CMatrix4f::ComputeInverse
00635 (
00636 const float in_fMat[4][4],
00637 float out_fInv[4][4],
00638 const bool bTransposeResult
00639 )
00640 {
00641 int i, j, k;
00642 float fSys[4][8];
00643 float fTemp;
00644
00645
00646 for(i=0; i<4; i++)
00647 {
00648 for(j=0; j<4; j++)
00649 {
00650 fSys[i][j] = in_fMat[i][j];
00651 fSys[i][j+4] = (float) (i==j);
00652 }
00653 }
00654
00655 for(j=0; j<4; j++)
00656 {
00657 if(fabs(fSys[j][j]) < MicroEPS)
00658 {
00659 for(i=j + 1; (i<4) && (fabs(fSys[i][j]) < MicroEPS ); i++)
00660 {};
00661 if(i==4)
00662 {
00663 return(false);
00664 }
00665 else
00666 {
00667 for(k=0; k<8; k++)
00668 {
00669 fTemp = fSys[i][k];
00670 fSys[i][k] = fSys[j][k];
00671 fSys[j][k] = fTemp;
00672 }
00673 }
00674 }
00675 fTemp = 1.0f / fSys[j][j];
00676 for(i=0; i<8; i++)
00677 {
00678 fSys[j][i] *= fTemp;
00679 }
00680 for(i=0; i<4; i++)
00681 {
00682 if(i != j)
00683 {
00684 fTemp = - fSys[i][j];
00685 for(k=0; k<8; k++)
00686 {
00687 fSys[i][k] += fSys[j][k] * fTemp;
00688 }
00689 }
00690 }
00691 }
00692
00693
00694 if(bTransposeResult)
00695 {
00696 for(i=0; i<4; i++)
00697 {
00698 for(j=0; j<4; j++)
00699 {
00700 out_fInv[j][i] = fSys[i][j + 4];
00701 }
00702 }
00703 }
00704 else
00705 {
00706 for(i=0; i<4; i++)
00707 {
00708 for(j=0; j<4; j++)
00709 {
00710 out_fInv[i][j] = fSys[i][j + 4];
00711 }
00712 }
00713 }
00714 return(true);
00715 }
00716
00717 };
00718 };
00719
00720 #endif // __XSIMATRIX4_H__