moab
HomXform.hpp
Go to the documentation of this file.
00001 
00016 #ifndef MOAB_HOMXFORM
00017 #define MOAB_HOMXFORM
00018 
00019 /*
00020  * \file HomXform.hpp
00021  *
00022  * \brief Representation and functions for homogeneous transforms
00023  *
00024  * A homogeneous transform is a 4x4 matrix for representing and manipulating
00025  * homogeneous coordinates, which are x' = (x/h, y/h, z/h, h).  See Mortenson,
00026  * Geometric Modeling, or other texts on geometric modeling for details of homogeneous
00027  * transforms.
00028  */
00029 
00030 #define XFORM(a,b) xForm[4*a+b]
00031 #define XFORM_INDEX(a,b) 4*a+b
00032 
00033 #include <math.h>
00034 #include <ostream>
00035 
00036 namespace moab {
00037 
00038 class HomXform;
00039 
00043 class HomCoord 
00044 {
00045 private:
00046 
00048 #if defined(__INTEL_COMPILER) && (__INTEL_COMPILER < 1310)
00049   // Hack Intel compiler 12 issues with -O2 optimization
00050   int homCoord[5];
00051 #else
00052   int homCoord[4];
00053 #endif
00054 
00055 public:
00056   friend class HomXform;
00057 
00058   static HomCoord unitv[3];
00059   static HomCoord IDENTITY;
00060 
00062   HomCoord();
00063   HomCoord(const int coords[], const int num_coords = 4);
00064   HomCoord(const int coord0, const int coord1, 
00065            const int coord2, const int coord3);
00066   HomCoord(const int coord0, const int coord1, 
00067            const int coord2);
00068   HomCoord(const HomCoord &coord);
00069 
00071   void set(const int coords[]);
00072   void set(const int i, const int j, const int k, 
00073            const int h = 1);
00074 
00076   const int *hom_coord() const {return homCoord;}
00077 
00079   int i() const {return homCoord[0];}
00080   int j() const {return homCoord[1];}
00081   int k() const {return homCoord[2];}
00082   int h() const {return homCoord[3];}
00083 
00085   int length_squared() const;
00086 
00088   int length() const;
00089 
00091   void normalize();
00092 
00094   HomCoord &operator*=(const HomXform &rhs2);
00095   HomCoord operator*(const HomXform &rhs2) const;
00096   HomCoord &operator*=(const int mult);
00097   HomCoord operator*(const int mult) const;
00098   inline HomCoord &operator/=(const HomXform &rhs2);
00099   HomCoord operator/(const HomXform &rhs2) const;
00100   inline HomCoord &operator/=(const int mult);
00101   HomCoord operator/(const int mult) const;
00102   inline HomCoord &operator+=(const HomCoord &rhs1);
00103   HomCoord operator+(const HomCoord &rhs1) const;
00104   inline HomCoord &operator-=(const HomCoord &rhs1);
00105   HomCoord operator-(const HomCoord &rhs1) const;
00106   HomCoord &operator=(const HomCoord &rhs);
00107 
00108     // dot product
00109   int operator%(const HomCoord &rhs) const;
00110   
00111     // cross product
00112   HomCoord operator*(const HomCoord &rhs) const;
00113   HomCoord &operator*=(const HomCoord &rhs);
00114   
00115   bool operator==(const HomCoord &rhs1) const;
00116   bool operator!=(const HomCoord &rhs1) const;
00117   bool operator>=(const HomCoord &rhs1) const;
00118   bool operator<=(const HomCoord &rhs1) const;
00119   bool operator>(const HomCoord &rhs1) const;
00120   bool operator<(const HomCoord &rhs1) const;
00121   inline int operator[](const int &param) const;
00122   int &operator[](const int &param);
00123 
00124 };
00125   
00129 class HomXform
00130 {
00131 
00132 private:
00133 
00136   int xForm[16];
00137 
00138 public:
00139 
00140   friend class HomCoord;
00141 
00142   static HomXform IDENTITY;
00143 
00145   HomXform(const int matrix[16]);
00146 
00148   HomXform();
00149   
00151   HomXform(const int rotate[9], const int scale[3], const int translate[3]);
00152 
00154   HomXform(int i1, int i2, int i3, int i4,
00155            int i5, int i6, int i7, int i8,
00156            int i9, int i10, int i11, int i12,
00157            int i13, int i14, int i15, int i16);
00158 
00160   inline HomXform inverse() const;
00161 
00163   void three_pt_xform(const HomCoord &p1, const HomCoord &q1,
00164                       const HomCoord &p2, const HomCoord &q2,
00165                       const HomCoord &p3, const HomCoord &q3);
00166 
00168   int operator[](const int &count) const;
00169   int &operator[](const int &count);
00170   bool operator==(const HomXform &rhs) const;
00171   bool operator!=(const HomXform &rhs) const;
00172 
00173   HomXform &operator=(const HomXform &rhs);
00174   HomXform &operator*=(const HomXform &rhs);
00175   HomXform operator*(const HomXform &rhs2) const;
00176 };
00177 
00178 inline HomCoord::HomCoord() 
00179 {
00180   homCoord[0] = 0;
00181   homCoord[1] = 0;
00182   homCoord[2] = 0;
00183   homCoord[3] = 0;
00184 }
00185   
00186 inline HomCoord::HomCoord(const int coords[], const int num_coords) 
00187 {
00188   for (int tmpj = 0; tmpj < num_coords; tmpj++) homCoord[tmpj] = coords[tmpj];
00189   if (num_coords != 4) homCoord[3] = 1;
00190 }
00191 
00192 inline HomCoord::HomCoord(const int coord0, const int coord1, 
00193                           const int coord2, const int coord3) 
00194 {
00195   homCoord[0] = coord0;
00196   homCoord[1] = coord1;
00197   homCoord[2] = coord2;
00198   homCoord[3] = coord3;
00199 }
00200   
00201 inline HomCoord::HomCoord(const int coord0, const int coord1, 
00202                           const int coord2) 
00203 {
00204   homCoord[0] = coord0;
00205   homCoord[1] = coord1;
00206   homCoord[2] = coord2;
00207   homCoord[3] = 1;
00208 }
00209 
00210 inline HomCoord::HomCoord(const HomCoord &coords) 
00211 {
00212 #if defined(__INTEL_COMPILER) && (__INTEL_COMPILER < 1310)
00213   // Hack Intel compiler 12 issues with -O2 optimization
00214   int coord0 = coords[0];
00215   int coord1 = coords[1];
00216   int coord2 = coords[2];
00217   int coord3 = coords[3];
00218   homCoord[0] = coord0;
00219   homCoord[1] = coord1;
00220   homCoord[2] = coord2;
00221   homCoord[3] = coord3;
00222 #else
00223   homCoord[0] = coords[0];
00224   homCoord[1] = coords[1];
00225   homCoord[2] = coords[2];
00226   homCoord[3] = coords[3];
00227 #endif
00228 }
00229   
00230 inline void HomCoord::set(const int coords[]) 
00231 {
00232     homCoord[0] = coords[0];
00233     homCoord[1] = coords[1];
00234     homCoord[2] = coords[2];
00235     homCoord[3] = coords[3];
00236 }
00237   
00238 inline void HomCoord::set(const int ip, const int jp, const int kp,
00239                           const int hp)
00240 {
00241     homCoord[0] = ip;
00242     homCoord[1] = jp;
00243     homCoord[2] = kp;
00244     homCoord[3] = hp;
00245 }
00246   
00247 inline HomCoord &HomCoord::operator=(const HomCoord &rhs1)
00248 {
00249   homCoord[0] = rhs1.homCoord[0];
00250   homCoord[1] = rhs1.homCoord[1];
00251   homCoord[2] = rhs1.homCoord[2];
00252   homCoord[3] = rhs1.homCoord[3];
00253   return *this;
00254 }
00255 
00257 inline int HomCoord::length_squared() const 
00258 {
00259   return homCoord[0]*homCoord[0] +
00260     homCoord[1]*homCoord[1] +
00261     homCoord[2]*homCoord[2];
00262 }
00263 
00264 
00266 inline int HomCoord::length() const 
00267 {
00268   return (int) sqrt((float)length_squared());
00269 }
00270 
00272 inline void HomCoord::normalize()
00273 {
00274   *this /= length();
00275 }
00276 
00277     // dot product
00278 inline int HomCoord::operator%(const HomCoord &rhs) const 
00279 {
00280   return homCoord[0]*rhs.homCoord[0] +
00281     homCoord[1]*rhs.homCoord[1] +
00282     homCoord[2]*rhs.homCoord[2];
00283 }
00284 
00285     // cross product
00286 inline HomCoord HomCoord::operator*(const HomCoord &rhs) const 
00287 {
00288   return HomCoord(
00289     homCoord[1]*rhs.homCoord[2] - homCoord[2]*rhs.homCoord[1],
00290     homCoord[2]*rhs.homCoord[0] - homCoord[0]*rhs.homCoord[2],
00291     homCoord[0]*rhs.homCoord[1] - homCoord[1]*rhs.homCoord[0]);
00292 }
00293 
00294 inline HomCoord &HomCoord::operator*=(const HomCoord &rhs) 
00295 {
00296   *this = HomCoord(
00297     homCoord[1]*rhs.homCoord[2] - homCoord[2]*rhs.homCoord[1],
00298     homCoord[2]*rhs.homCoord[0] - homCoord[0]*rhs.homCoord[2],
00299     homCoord[0]*rhs.homCoord[1] - homCoord[1]*rhs.homCoord[0]);
00300   
00301   return *this;
00302 }
00303   
00304 inline bool HomCoord::operator==(const HomCoord &rhs1) const 
00305 {
00306   return (homCoord[0] == rhs1.homCoord[0] &&
00307           homCoord[1] == rhs1.homCoord[1] &&
00308           homCoord[2] == rhs1.homCoord[2] &&
00309           homCoord[3] == rhs1.homCoord[3]);
00310 }
00311 
00312 inline bool HomCoord::operator!=(const HomCoord &rhs1) const 
00313 {
00314   return (homCoord[0] != rhs1.homCoord[0] ||
00315           homCoord[1] != rhs1.homCoord[1] ||
00316           homCoord[2] != rhs1.homCoord[2] ||
00317           homCoord[3] != rhs1.homCoord[3]);
00318 }
00319 
00320 inline bool HomCoord::operator>=(const HomCoord &rhs1) const 
00321 {
00322   return (homCoord[0] >= rhs1.homCoord[0] &&
00323           homCoord[1] >= rhs1.homCoord[1] &&
00324           homCoord[2] >= rhs1.homCoord[2] &&
00325           homCoord[3] == rhs1.homCoord[3]);
00326 }
00327 
00328 inline bool HomCoord::operator<=(const HomCoord &rhs1) const 
00329 {
00330   return (homCoord[0] <= rhs1.homCoord[0] &&
00331           homCoord[1] <= rhs1.homCoord[1] &&
00332           homCoord[2] <= rhs1.homCoord[2] &&
00333           homCoord[3] == rhs1.homCoord[3]);
00334 }
00335 
00336 inline bool HomCoord::operator<(const HomCoord &rhs1) const 
00337 {
00338   return (homCoord[0] < rhs1.homCoord[0] &&
00339           homCoord[1] < rhs1.homCoord[1] &&
00340           homCoord[2] < rhs1.homCoord[2] &&
00341           homCoord[3] == rhs1.homCoord[3]);
00342 }
00343 
00344 inline bool HomCoord::operator>(const HomCoord &rhs1) const 
00345 {
00346   return (homCoord[0] > rhs1.homCoord[0] &&
00347           homCoord[1] > rhs1.homCoord[1] &&
00348           homCoord[2] > rhs1.homCoord[2] &&
00349           homCoord[3] == rhs1.homCoord[3]);
00350 }
00351 
00352 inline HomCoord HomCoord::operator*(const HomXform &rhs2) const 
00353 {
00354   return HomCoord(
00355 //    homCoord[0]*rhs2[4*0+0] + homCoord[1]*rhs2[4*1+0] + 
00356 //    homCoord[2]*rhs2[4*2+0] + homCoord[3]*rhs2[4*3+0],
00357     homCoord[0]*rhs2.xForm[0] + homCoord[1]*rhs2.xForm[4] + 
00358     homCoord[2]*rhs2.xForm[8] + homCoord[3]*rhs2.xForm[12],
00359 
00360 //    homCoord[0]*rhs2.xForm[4*0+1] + homCoord[1]*rhs2.xForm[4*1+1] + 
00361 //    homCoord[2]*rhs2.xForm[4*2+1] + homCoord[3]*rhs2.xForm[4*3+1],
00362     homCoord[0]*rhs2.xForm[1] + homCoord[1]*rhs2.xForm[5] + 
00363     homCoord[2]*rhs2.xForm[9] + homCoord[3]*rhs2.xForm[13],
00364 
00365 //    homCoord[0]*rhs2.xForm[4*0+2] + homCoord[1]*rhs2.xForm[4*1+2] + 
00366 //    homCoord[2]*rhs2.xForm[4*2+2] + homCoord[3]*rhs2.xForm[4*3+2],
00367     homCoord[0]*rhs2.xForm[2] + homCoord[1]*rhs2.xForm[6] + 
00368     homCoord[2]*rhs2.xForm[10] + homCoord[3]*rhs2.xForm[14],
00369 
00370 //    homCoord[0]*rhs2.xForm[4*0+3] + homCoord[1]*rhs2.xForm[4*1+3] + 
00371 //    homCoord[2]*rhs2.xForm[4*2+3] + homCoord[3]*rhs2.xForm[4*3+3]
00372     homCoord[0]*rhs2.xForm[3] + homCoord[1]*rhs2.xForm[7] + 
00373     homCoord[2]*rhs2.xForm[11] + homCoord[3]*rhs2.xForm[15]
00374     );
00375 }
00376 
00377 inline HomCoord &HomCoord::operator*=(const HomXform &rhs2)
00378 {
00379   *this = HomCoord(
00380 //    homCoord[0]*rhs2.xForm[4*0+0] + homCoord[1]*rhs2.xForm[4*1+0] + 
00381 //    homCoord[2]*rhs2.xForm[4*2+0] + homCoord[3]*rhs2.xForm[4*3+0],
00382     homCoord[0]*rhs2.xForm[0] + homCoord[1]*rhs2.xForm[4] + 
00383     homCoord[2]*rhs2.xForm[8] + homCoord[3]*rhs2.xForm[12],
00384 
00385 //    homCoord[0]*rhs2.xForm[4*0+1] + homCoord[1]*rhs2.xForm[4*1+1] + 
00386 //    homCoord[2]*rhs2.xForm[4*2+1] + homCoord[3]*rhs2.xForm[4*3+1],
00387     homCoord[0]*rhs2.xForm[1] + homCoord[1]*rhs2.xForm[5] + 
00388     homCoord[2]*rhs2.xForm[9] + homCoord[3]*rhs2.xForm[13],
00389 
00390 //    homCoord[0]*rhs2.xForm[4*0+2] + homCoord[1]*rhs2.xForm[4*1+2] + 
00391 //    homCoord[2]*rhs2.xForm[4*2+2] + homCoord[3]*rhs2.xForm[4*3+2],
00392     homCoord[0]*rhs2.xForm[2] + homCoord[1]*rhs2.xForm[6] + 
00393     homCoord[2]*rhs2.xForm[10] + homCoord[3]*rhs2.xForm[14],
00394 
00395 //    homCoord[0]*rhs2.xForm[4*0+3] + homCoord[1]*rhs2.xForm[4*1+3] + 
00396 //    homCoord[2]*rhs2.xForm[4*2+3] + homCoord[3]*rhs2.xForm[4*3+3]
00397     homCoord[0]*rhs2.xForm[3] + homCoord[1]*rhs2.xForm[7] + 
00398     homCoord[2]*rhs2.xForm[11] + homCoord[3]*rhs2.xForm[15]
00399     );
00400   return *this;
00401 }
00402 
00403 inline HomCoord HomCoord::operator*(const int mult) const 
00404 {
00405   return HomCoord(mult*homCoord[0], mult*homCoord[1], mult*homCoord[2]);
00406 }
00407 
00408 inline HomCoord &HomCoord::operator*=(const int mult)
00409 {
00410   homCoord[0] *= mult;
00411   homCoord[1] *= mult;
00412   homCoord[2] *= mult;
00413   return *this;
00414 }
00415 
00416 inline HomCoord HomCoord::operator/(const int div) const 
00417 {
00418   return HomCoord(homCoord[0]/div, homCoord[1]/div, homCoord[2]/div);
00419 }
00420 
00421 inline HomCoord &HomCoord::operator/=(const int div)
00422 {
00423   homCoord[0] /= div;
00424   homCoord[1] /= div;
00425   homCoord[2] /= div;
00426   return *this;
00427 }
00428 
00429 inline HomCoord HomCoord::operator-(const HomCoord &rhs2) const 
00430 {
00431   return HomCoord(*this) -= rhs2;
00432 }
00433 
00434 inline HomCoord &HomCoord::operator-=(const HomCoord &rhs2)
00435 {
00436   homCoord[0] -= rhs2[0];
00437   homCoord[1] -= rhs2[1];
00438   homCoord[2] -= rhs2[2];
00439   return *this;
00440 }
00441 
00442 inline HomCoord HomCoord::operator+(const HomCoord &rhs2) const 
00443 {
00444   return HomCoord(*this) += rhs2;
00445 }
00446 
00447 inline HomCoord &HomCoord::operator+=(const HomCoord &rhs2)
00448 {
00449   homCoord[0] += rhs2[0];
00450   homCoord[1] += rhs2[1];
00451   homCoord[2] += rhs2[2];
00452   return *this;
00453 }
00454 
00455 inline HomCoord HomCoord::operator/(const HomXform &rhs2) const 
00456 {
00457   return HomCoord(*this) /= rhs2;
00458 }
00459 
00460 inline HomCoord &HomCoord::operator/=(const HomXform &rhs2)
00461 {
00462   HomXform inv = rhs2.inverse();
00463   *this *= inv;
00464   return *this;
00465 }
00466 
00467 inline int HomCoord::operator[](const int &param) const
00468 {
00469   return homCoord[param];
00470 }
00471 
00472 inline int &HomCoord::operator[](const int &param)
00473 {
00474   return homCoord[param];
00475 }
00476 
00477 inline std::ostream &operator<<(std::ostream &str, const HomCoord &hc)
00478 {
00479   str << "(" << hc.i() << "," << hc.j() << "," << hc.k() << ")";
00480   return str;
00481 }
00482 
00483 inline HomXform::HomXform(const int matrix[16]) 
00484 {
00485   for (int i = 0; i < 16; i++)
00486     xForm[i] = matrix[i];
00487 }
00488 
00489 inline HomXform::HomXform() 
00490 {
00491 }
00492 
00493 inline HomXform::HomXform(const int rotate[9], const int scale[3], 
00494                           const int translate[3]) 
00495 {
00496   int i, j;
00497   for (i = 0; i < 3; i++) {
00498     for (j = 0; j < 3; j++)
00499       xForm[i*4+j] = rotate[i*3+j]*scale[j];
00500 
00501     xForm[12+i] = translate[i];
00502   }
00503   xForm[3] = 0;
00504   xForm[7] = 0;
00505   xForm[11] = 0;
00506   xForm[15] = 1;
00507   
00508 }
00509 
00510 inline HomXform::HomXform(int i1, int i2, int i3, int i4,
00511                           int i5, int i6, int i7, int i8,
00512                           int i9, int i10, int i11, int i12,
00513                           int i13, int i14, int i15, int i16) 
00514 {
00515   xForm[0] = i1; xForm[1] = i2; xForm[2] = i3; xForm[3] = i4;
00516   xForm[4] = i5; xForm[5] = i6; xForm[6] = i7; xForm[7] = i8;
00517   xForm[8] = i9; xForm[9] = i10; xForm[10] = i11; xForm[11] = i12;
00518   xForm[12] = i13; xForm[13] = i14; xForm[14] = i15; xForm[15] = i16;
00519 }
00520 
00521 inline HomXform &HomXform::operator=(const HomXform &rhs) 
00522 {
00523   for (int i = 0; i < 16; i++)
00524     xForm[i] = rhs.xForm[i];
00525 
00526   return *this;
00527 }
00528 
00529 inline HomXform HomXform::operator*(const HomXform &rhs2) const
00530 {
00531   return HomXform(
00532 //  temp.XFORM(0,0)
00533     XFORM(0,0)*rhs2.XFORM(0,0) + XFORM(0,1)*rhs2.XFORM(1,0) + 
00534     XFORM(0,2)*rhs2.XFORM(2,0) + XFORM(0,3)*rhs2.XFORM(3,0),
00535 //  temp.XFORM(0,1)  
00536     XFORM(0,0)*rhs2.XFORM(0,1) + XFORM(0,1)*rhs2.XFORM(1,1) + 
00537     XFORM(0,2)*rhs2.XFORM(2,1) + XFORM(0,3)*rhs2.XFORM(3,1),
00538 //  temp.XFORM(0,2)  
00539     XFORM(0,0)*rhs2.XFORM(0,2) + XFORM(0,1)*rhs2.XFORM(1,2) + 
00540     XFORM(0,2)*rhs2.XFORM(2,2) + XFORM(0,3)*rhs2.XFORM(3,2),
00541 //  temp.XFORM(0,3)  
00542     XFORM(0,0)*rhs2.XFORM(0,3) + XFORM(0,1)*rhs2.XFORM(1,3) + 
00543     XFORM(0,2)*rhs2.XFORM(2,3) + XFORM(0,3)*rhs2.XFORM(3,3),
00544 
00545 //  temp.XFORM(1,0)  
00546     XFORM(1,0)*rhs2.XFORM(0,0) + XFORM(1,1)*rhs2.XFORM(1,0) + 
00547     XFORM(1,2)*rhs2.XFORM(2,0) + XFORM(1,3)*rhs2.XFORM(3,0),
00548 //  temp.XFORM(1,1)  
00549     XFORM(1,0)*rhs2.XFORM(0,1) + XFORM(1,1)*rhs2.XFORM(1,1) + 
00550     XFORM(1,2)*rhs2.XFORM(2,1) + XFORM(1,3)*rhs2.XFORM(3,1),
00551 //  temp.XFORM(1,2)  
00552     XFORM(1,0)*rhs2.XFORM(0,2) + XFORM(1,1)*rhs2.XFORM(1,2) + 
00553     XFORM(1,2)*rhs2.XFORM(2,2) + XFORM(1,3)*rhs2.XFORM(3,2),
00554 //  temp.XFORM(1,3)  
00555     XFORM(1,0)*rhs2.XFORM(0,3) + XFORM(1,1)*rhs2.XFORM(1,3) + 
00556     XFORM(1,2)*rhs2.XFORM(2,3) + XFORM(1,3)*rhs2.XFORM(3,3),
00557 
00558 //  temp.XFORM(2,0)  
00559     XFORM(2,0)*rhs2.XFORM(0,0) + XFORM(2,1)*rhs2.XFORM(1,0) + 
00560     XFORM(2,2)*rhs2.XFORM(2,0) + XFORM(2,3)*rhs2.XFORM(3,0),
00561 //  temp.XFORM(2,1)  
00562     XFORM(2,0)*rhs2.XFORM(0,1) + XFORM(2,1)*rhs2.XFORM(1,1) + 
00563     XFORM(2,2)*rhs2.XFORM(2,1) + XFORM(2,3)*rhs2.XFORM(3,1),
00564 //  temp.XFORM(2,2)  
00565     XFORM(2,0)*rhs2.XFORM(0,2) + XFORM(2,1)*rhs2.XFORM(1,2) + 
00566     XFORM(2,2)*rhs2.XFORM(2,2) + XFORM(2,3)*rhs2.XFORM(3,2),
00567 //  temp.XFORM(2,3)  
00568     XFORM(2,0)*rhs2.XFORM(0,3) + XFORM(2,1)*rhs2.XFORM(1,3) + 
00569     XFORM(2,2)*rhs2.XFORM(2,3) + XFORM(2,3)*rhs2.XFORM(3,3),
00570 
00571 //  temp.XFORM(3,0)  
00572 //  xForm[12]*rhs2.xForm[0] + xForm[13]*rhs2.xForm[4] + xForm[14]*rhs2.xForm[8] + xForm[15]*rhs2.xForm[12]
00573     XFORM(3,0)*rhs2.XFORM(0,0) + XFORM(3,1)*rhs2.XFORM(1,0) + 
00574     XFORM(3,2)*rhs2.XFORM(2,0) + XFORM(3,3)*rhs2.XFORM(3,0),
00575 //  temp.XFORM(3,1)  
00576 //  xForm[12]*rhs2.xForm[1] + xForm[13]*rhs2.xForm[5] + xForm[14]*rhs2.xForm[9] + xForm[15]*rhs2.xForm[13]
00577     XFORM(3,0)*rhs2.XFORM(0,1) + XFORM(3,1)*rhs2.XFORM(1,1) + 
00578     XFORM(3,2)*rhs2.XFORM(2,1) + XFORM(3,3)*rhs2.XFORM(3,1),
00579 //  temp.XFORM(3,2)  
00580 //  xForm[12]*rhs2.xForm[2] + xForm[13]*rhs2.xForm[6] + xForm[14]*rhs2.xForm[10] + xForm[15]*rhs2.xForm[14]
00581     XFORM(3,0)*rhs2.XFORM(0,2) + XFORM(3,1)*rhs2.XFORM(1,2) + 
00582     XFORM(3,2)*rhs2.XFORM(2,2) + XFORM(3,3)*rhs2.XFORM(3,2),
00583 //  temp.XFORM(3,3)  
00584 //  xForm[12]*rhs2.xForm[3] + xForm[13]*rhs2.xForm[7] + xForm[14]*rhs2.xForm[11] + xForm[15]*rhs2.xForm[15]
00585     XFORM(3,0)*rhs2.XFORM(0,3) + XFORM(3,1)*rhs2.XFORM(1,3) + 
00586     XFORM(3,2)*rhs2.XFORM(2,3) + XFORM(3,3)*rhs2.XFORM(3,3));
00587 }
00588 
00589 inline HomXform &HomXform::operator*=(const HomXform &rhs2)
00590 {
00591   *this =  HomXform(
00592 //  temp.XFORM(0,0)
00593     XFORM(0,0)*rhs2.XFORM(0,0) + XFORM(0,1)*rhs2.XFORM(1,0) + 
00594     XFORM(0,2)*rhs2.XFORM(2,0) + XFORM(0,3)*rhs2.XFORM(3,0),
00595 //  temp.XFORM(0,1)  
00596     XFORM(0,0)*rhs2.XFORM(0,1) + XFORM(0,1)*rhs2.XFORM(1,1) + 
00597     XFORM(0,2)*rhs2.XFORM(2,1) + XFORM(0,3)*rhs2.XFORM(3,1),
00598 //  temp.XFORM(0,2)  
00599     XFORM(0,0)*rhs2.XFORM(0,2) + XFORM(0,1)*rhs2.XFORM(1,2) + 
00600     XFORM(0,2)*rhs2.XFORM(2,2) + XFORM(0,3)*rhs2.XFORM(3,2),
00601 //  temp.XFORM(0,3)  
00602     XFORM(0,0)*rhs2.XFORM(0,3) + XFORM(0,1)*rhs2.XFORM(1,3) + 
00603     XFORM(0,2)*rhs2.XFORM(2,3) + XFORM(0,3)*rhs2.XFORM(3,3),
00604 
00605 //  temp.XFORM(1,0)  
00606     XFORM(1,0)*rhs2.XFORM(0,0) + XFORM(1,1)*rhs2.XFORM(1,0) + 
00607     XFORM(1,2)*rhs2.XFORM(2,0) + XFORM(1,3)*rhs2.XFORM(3,0),
00608 //  temp.XFORM(1,1)  
00609     XFORM(1,0)*rhs2.XFORM(0,1) + XFORM(1,1)*rhs2.XFORM(1,1) + 
00610     XFORM(1,2)*rhs2.XFORM(2,1) + XFORM(1,3)*rhs2.XFORM(3,1),
00611 //  temp.XFORM(1,2)  
00612     XFORM(1,0)*rhs2.XFORM(0,2) + XFORM(1,1)*rhs2.XFORM(1,2) + 
00613     XFORM(1,2)*rhs2.XFORM(2,2) + XFORM(1,3)*rhs2.XFORM(3,2),
00614 //  temp.XFORM(1,3)  
00615     XFORM(1,0)*rhs2.XFORM(0,3) + XFORM(1,1)*rhs2.XFORM(1,3) + 
00616     XFORM(1,2)*rhs2.XFORM(2,3) + XFORM(1,3)*rhs2.XFORM(3,3),
00617 
00618 //  temp.XFORM(2,0)  
00619     XFORM(2,0)*rhs2.XFORM(0,0) + XFORM(2,1)*rhs2.XFORM(1,0) + 
00620     XFORM(2,2)*rhs2.XFORM(2,0) + XFORM(2,3)*rhs2.XFORM(3,0),
00621 //  temp.XFORM(2,1)  
00622     XFORM(2,0)*rhs2.XFORM(0,1) + XFORM(2,1)*rhs2.XFORM(1,1) + 
00623     XFORM(2,2)*rhs2.XFORM(2,1) + XFORM(2,3)*rhs2.XFORM(3,1),
00624 //  temp.XFORM(2,2)  
00625     XFORM(2,0)*rhs2.XFORM(0,2) + XFORM(2,1)*rhs2.XFORM(1,2) + 
00626     XFORM(2,2)*rhs2.XFORM(2,2) + XFORM(2,3)*rhs2.XFORM(3,2),
00627 //  temp.XFORM(2,3)  
00628     XFORM(2,0)*rhs2.XFORM(0,3) + XFORM(2,1)*rhs2.XFORM(1,3) + 
00629     XFORM(2,2)*rhs2.XFORM(2,3) + XFORM(2,3)*rhs2.XFORM(3,3),
00630 
00631 //  temp.XFORM(3,0)  
00632     XFORM(3,0)*rhs2.XFORM(0,0) + XFORM(3,1)*rhs2.XFORM(1,0) + 
00633     XFORM(3,2)*rhs2.XFORM(2,0) + XFORM(3,3)*rhs2.XFORM(3,0),
00634 //  temp.XFORM(3,1)  
00635     XFORM(3,0)*rhs2.XFORM(0,1) + XFORM(3,1)*rhs2.XFORM(1,1) + 
00636     XFORM(3,2)*rhs2.XFORM(2,1) + XFORM(3,3)*rhs2.XFORM(3,1),
00637 //  temp.XFORM(3,2)  
00638     XFORM(3,0)*rhs2.XFORM(0,2) + XFORM(3,1)*rhs2.XFORM(1,2) + 
00639     XFORM(3,2)*rhs2.XFORM(2,2) + XFORM(3,3)*rhs2.XFORM(3,2),
00640 //  temp.XFORM(3,3)  
00641     XFORM(3,0)*rhs2.XFORM(0,3) + XFORM(3,1)*rhs2.XFORM(1,3) + 
00642     XFORM(3,2)*rhs2.XFORM(2,3) + XFORM(3,3)*rhs2.XFORM(3,3));
00643 
00644   return *this;
00645 }
00646 
00647 inline int HomXform::operator[](const int &count) const
00648 {
00649   return xForm[count];
00650 }
00651 
00652 inline int &HomXform::operator[](const int &count)
00653 {
00654   return xForm[count];
00655 }
00656 
00657 inline bool HomXform::operator==(const HomXform &rhs) const 
00658 {
00659   return (
00660     xForm[0] == rhs.xForm[0] && xForm[1] == rhs.xForm[1] &&
00661     xForm[2] == rhs.xForm[2] && xForm[3] == rhs.xForm[3] &&
00662     xForm[4] == rhs.xForm[4] && xForm[5] == rhs.xForm[5] &&
00663     xForm[6] == rhs.xForm[6] && xForm[7] == rhs.xForm[7] &&
00664     xForm[8] == rhs.xForm[8] && xForm[9] == rhs.xForm[9] &&
00665     xForm[10] == rhs.xForm[10] && xForm[11] == rhs.xForm[11] &&
00666     xForm[12] == rhs.xForm[12] && xForm[13] == rhs.xForm[13] &&
00667     xForm[14] == rhs.xForm[14] && xForm[15] == rhs.xForm[15]);
00668 }
00669 
00670 inline bool HomXform::operator!=(const HomXform &rhs) const 
00671 {
00672   return (
00673     xForm[0] != rhs.xForm[0] || xForm[1] != rhs.xForm[1] ||
00674     xForm[2] != rhs.xForm[2] || xForm[3] != rhs.xForm[3] ||
00675     xForm[4] != rhs.xForm[4] || xForm[5] != rhs.xForm[5] ||
00676     xForm[6] != rhs.xForm[6] || xForm[7] != rhs.xForm[7] ||
00677     xForm[8] != rhs.xForm[8] || xForm[9] != rhs.xForm[9] ||
00678     xForm[10] != rhs.xForm[10] || xForm[11] != rhs.xForm[11] ||
00679     xForm[12] != rhs.xForm[12] || xForm[13] != rhs.xForm[13] ||
00680     xForm[14] != rhs.xForm[14] || xForm[15] != rhs.xForm[15]);
00681 }
00682 
00683 inline HomXform HomXform::inverse() const 
00684 {
00685 
00686 /*
00687 // original code:
00688 
00689   HomXform tmp;
00690   
00691     // assign the diagonal
00692   tmp[0] = xForm[0];
00693   tmp[5] = xForm[5];
00694   tmp[10] = xForm[10];
00695   tmp[15] = xForm[15];
00696   
00697     // invert the rotation matrix
00698   tmp[XFORM_INDEX(0,1)] = XFORM(1,0);
00699   tmp[XFORM_INDEX(0,2)] = XFORM(2,0);
00700   tmp[XFORM_INDEX(1,0)] = XFORM(0,1);
00701   tmp[XFORM_INDEX(1,2)] = XFORM(2,1);
00702   tmp[XFORM_INDEX(2,0)] = XFORM(0,2);
00703   tmp[XFORM_INDEX(2,1)] = XFORM(1,2);
00704 
00705     // negative translate * Rinv
00706   tmp[XFORM_INDEX(3,0)] = -(XFORM(3,0)*tmp.XFORM(0,0) + XFORM(3,1)*tmp.XFORM(1,0) + XFORM(3,2)*tmp.XFORM(2,0));
00707   tmp[XFORM_INDEX(3,1)] = -(XFORM(3,0)*tmp.XFORM(0,1) + XFORM(3,1)*tmp.XFORM(1,1) + XFORM(3,2)*tmp.XFORM(2,1));
00708   tmp[XFORM_INDEX(3,2)] = -(XFORM(3,0)*tmp.XFORM(0,2) + XFORM(3,1)*tmp.XFORM(1,2) + XFORM(3,2)*tmp.XFORM(2,2));
00709   
00710     // zero last column
00711   tmp[XFORM_INDEX(0,3)] = 0;
00712   tmp[XFORM_INDEX(1,3)] = 0;
00713   tmp[XFORM_INDEX(2,3)] = 0;
00714 
00715     // h factor
00716   tmp[XFORM_INDEX(3,3)] = 1;
00717 
00718   return tmp;
00719 */
00720 
00721 // more efficient, but somewhat confusing (remember, column-major):
00722 
00723   return HomXform(
00724       // row 0
00725     xForm[0], XFORM(1,0), XFORM(2,0), 0,
00726       // row 1
00727     XFORM(0,1), xForm[5], XFORM(2,1), 0,
00728       // row 2
00729     XFORM(0,2), XFORM(1,2), xForm[10], 0,
00730       // row 3
00731     -(XFORM(3,0)*xForm[0] + XFORM(3,1)*XFORM(0,1) + XFORM(3,2)*XFORM(0,2)),
00732     -(XFORM(3,0)*XFORM(1,0) + XFORM(3,1)*xForm[5] + XFORM(3,2)*XFORM(1,2)),
00733     -(XFORM(3,0)*XFORM(2,0) + XFORM(3,1)*XFORM(2,1) + XFORM(3,2)*xForm[10]),
00734     1);
00735 }
00736 
00737 } // namespace moab 
00738 
00739 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines