Main Page | Namespace List | Class Hierarchy | Class List | Directories | File List | Namespace Members | Class Members

mitkMatrix.h

00001 /*=========================================================================
00002 
00003   Program:   3DMed
00004   Date:      $Date: 2014-02-25 18:30:00 +0800 $
00005   Version:   $Version: 4.6.0 $
00006   Copyright: MIPG, Institute of Automation, Chinese Academy of Sciences
00007 
00008 =========================================================================*/
00009 
00010 
00011 #ifndef __mitkMatrix_h
00012 #define __mitkMatrix_h
00013 
00014 #include <math.h>
00015 //#include "mitkGlobal.h"
00016 #include "mitkSIMD.h"
00017 
00018 #ifdef USE_SIMD
00019 #pragma pack(push,16)    /* Must ensure class & union 16-B aligned */
00020 #endif
00021 
00027 class MITK_COMMON_API mitkMatrix
00028 {
00029 public:
00030 
00031 #ifdef USE_SIMD
00032     union
00033     {
00034         struct
00035         {
00036             __m128 r1, r2, r3, r4;
00037         };
00038         struct
00039         {
00040             float ele[16];
00041         };
00042     };
00043 
00044     static void* operator new(size_t size)
00045     {
00046         return _aligned_malloc(size, 16);
00047     }
00048 
00049     static void operator delete(void *p)
00050     {
00051         _aligned_free(p);
00052     }
00053 
00054     static void* operator new[](size_t size)
00055     {
00056         return _aligned_malloc(size, 16);
00057     }
00058 
00059     static void operator delete[](void *p)
00060     {
00061         _aligned_free(p);
00062     }
00063 #else
00064     float ele[16];
00065 #endif
00066 
00067     mitkMatrix() {}
00068     mitkMatrix(const mitkMatrix &m)
00069     {
00070     #ifdef USE_SIMD
00071         r1 = m.r1;
00072         r2 = m.r2;
00073         r3 = m.r3;
00074         r4 = m.r4;
00075     #else
00076         ele[0] =  m.ele[0]; 
00077         ele[1] =  m.ele[1]; 
00078         ele[2] =  m.ele[2]; 
00079         ele[3] =  m.ele[3]; 
00080         ele[4] =  m.ele[4]; 
00081         ele[5] =  m.ele[5]; 
00082         ele[6] =  m.ele[6]; 
00083         ele[7] =  m.ele[7]; 
00084         ele[8] =  m.ele[8]; 
00085         ele[9] =  m.ele[9]; 
00086         ele[10] = m.ele[10];
00087         ele[11] = m.ele[11];
00088         ele[12] = m.ele[12];
00089         ele[13] = m.ele[13];
00090         ele[14] = m.ele[14];
00091         ele[15] = m.ele[15];
00092     #endif
00093     }
00094 
00095     mitkMatrix(float e0, float e1, float e2, float e3,
00096                float e4, float e5, float e6, float e7,
00097                float e8, float e9, float e10, float e11,
00098                float e12, float e13, float e14, float e15)
00099     {
00100     #ifdef USE_SIMD
00101         r1 = _mm_setr_ps(e0, e1, e2, e3);
00102         r2 = _mm_setr_ps(e4, e5, e6, e7);
00103         r3 = _mm_setr_ps(e8, e9, e10, e11);
00104         r4 = _mm_setr_ps(e12, e13, e14, e15);
00105     #else
00106         ele[0] = e0;
00107         ele[1] = e1;
00108         ele[2] = e2;
00109         ele[3] = e3;
00110         ele[4] = e4;
00111         ele[5] = e5;
00112         ele[6] = e6;
00113         ele[7] = e7;
00114         ele[8] = e8;
00115         ele[9] = e9;
00116         ele[10] = e10;
00117         ele[11] = e11;
00118         ele[12] = e12;
00119         ele[13] = e13;
00120         ele[14] = e14;
00121         ele[15] = e15;
00122     #endif
00123     }   
00124 
00125     mitkMatrix& operator = (const mitkMatrix &m) 
00126     {
00127     #ifdef USE_SIMD
00128         r1 = m.r1;
00129         r2 = m.r2;
00130         r3 = m.r3;
00131         r4 = m.r4;
00132     #else
00133         ele[0] =  m.ele[0]; 
00134         ele[1] =  m.ele[1]; 
00135         ele[2] =  m.ele[2]; 
00136         ele[3] =  m.ele[3]; 
00137         ele[4] =  m.ele[4]; 
00138         ele[5] =  m.ele[5]; 
00139         ele[6] =  m.ele[6]; 
00140         ele[7] =  m.ele[7]; 
00141         ele[8] =  m.ele[8]; 
00142         ele[9] =  m.ele[9]; 
00143         ele[10] = m.ele[10];
00144         ele[11] = m.ele[11];
00145         ele[12] = m.ele[12];
00146         ele[13] = m.ele[13];
00147         ele[14] = m.ele[14];
00148         ele[15] = m.ele[15];
00149     #endif
00150         return *this;
00151     }
00152 
00153     friend mitkMatrix operator * (const mitkMatrix&, const mitkMatrix&);
00154     friend mitkMatrix operator + (const mitkMatrix&, const mitkMatrix&);
00155     friend mitkMatrix operator - (const mitkMatrix&, const mitkMatrix&);
00156     friend mitkMatrix operator + (const mitkMatrix&);
00157     friend mitkMatrix operator - (const mitkMatrix&);
00158     friend mitkMatrix operator * (const mitkMatrix&, const float);
00159     friend mitkMatrix operator * (const float, const mitkMatrix&);
00160 
00161     mitkMatrix& operator *= (const mitkMatrix &);
00162     mitkMatrix& operator *= (const float);
00163     mitkMatrix& operator += (const mitkMatrix &);
00164     mitkMatrix& operator -= (const mitkMatrix &);
00165 
00166     operator const float* () const { return ele; }  
00167     operator float* () { return ele; }
00168 
00172     void    Transpose();    
00173     
00177     float   Inverse();      
00178 
00182     float   Determinant();  
00183 
00187     void    Adjoint();
00188 
00192     float   MinValue();     
00193 
00197     float   MaxValue();     
00198 
00202     void ZeroMatrix();
00203 
00207     void IdentityMatrix();
00208 
00212     void TranslateMatrix(const float dx, const float dy, const float dz);
00213 
00217     void ScaleMatrix(const float a, const float b, const float c);
00218 
00222     void ScaleMatrix(const float a);
00223 
00227     void RotateXMatrix(const float angle);
00228 
00232     void RotateYMatrix(const float angle);
00233 
00237     void RotateZMatrix(const float angle);
00238 
00242     void Translate(const float dx, const float dy, const float dz);
00243 
00247     void Scale(const float a, const float b, const float c);
00248 
00252     void Rotate(const float angle, const float x, const float y, const float z);
00253 
00257     void RotateX(const float angle);
00258 
00262     void RotateY(const float angle);
00263 
00267     void RotateZ(const float angle);
00268 };
00269 
00273 class MITK_COMMON_API mitkVector
00274 {
00275 public:
00276 #ifdef USE_SIMD
00277     union
00278     {
00279         __m128 vec;
00280         struct
00281         { 
00282             float   ele[4];
00283         };
00284     };
00285 
00286     static void* operator new(size_t size)
00287     {
00288         return _aligned_malloc(size, 16);
00289     }
00290 
00291     static void operator delete(void *p)
00292     {
00293         _aligned_free(p);
00294     }
00295 
00296     static void* operator new[](size_t size)
00297     {
00298         return _aligned_malloc(size, 16);
00299     }
00300 
00301     static void operator delete[](void *p)
00302     {
00303         _aligned_free(p);
00304     }
00305 #else
00306     float ele[4];
00307 #endif
00308 
00309     mitkVector()
00310     {
00311     #ifdef USE_SIMD
00312             vec = _mm_setr_ps(0.0f, 0.0f, 0.0f, 1.0f);
00313     #else
00314             ele[0] = 0.0f;
00315             ele[1] = 0.0f;
00316             ele[2] = 0.0f;
00317             ele[3] = 1.0f;
00318     #endif
00319     }
00320 
00321     mitkVector(const mitkVector &v)
00322     {
00323     #ifdef USE_SIMD
00324             vec = v.vec;
00325     #else
00326             ele[0] = v.ele[0];
00327             ele[1] = v.ele[1];
00328             ele[2] = v.ele[2];
00329             ele[3] = v.ele[3];
00330     #endif
00331     }
00332 
00333     mitkVector(const float x, const float y, const float z, const float w = 1.0f)
00334     {
00335     #ifdef USE_SIMD
00336         vec = _mm_setr_ps(x, y, z, w);
00337     #else
00338             ele[0] = x;
00339             ele[1] = y;
00340             ele[2] = z;
00341             ele[3] = w;
00342     #endif
00343     }
00344 
00345     mitkVector(const float srcVector[4])
00346     {
00347         ele[0] = srcVector[0];
00348         ele[1] = srcVector[1];
00349         ele[2] = srcVector[2];
00350         ele[3] = srcVector[3];
00351     }   
00352 
00353     
00354     operator float* () { return ele; }  
00355     operator const float* () const { return ele; }
00356 
00357     mitkVector& operator = (const mitkVector &a)
00358     {
00359     #ifdef USE_SIMD
00360         vec = a.vec;
00361     #else
00362         ele[0] = a.ele[0];
00363         ele[1] = a.ele[1];
00364         ele[2] = a.ele[2];
00365         ele[3] = a.ele[3];
00366     #endif
00367         return *this; 
00368     }
00369     
00370     friend mitkVector operator * (const mitkVector&, const mitkMatrix&);
00371     friend float operator * (const mitkVector &, const mitkVector &);           // Dot Product
00372     friend mitkVector operator % (const mitkVector &, const mitkVector &);      // Cross Product
00373     friend mitkVector operator * (const mitkVector &, const float);
00374     friend mitkVector operator * (const float, const mitkVector &);
00375     friend mitkVector operator + (const mitkVector&);
00376     friend mitkVector operator + (const mitkVector&, const mitkVector&);
00377     friend mitkVector operator - (const mitkVector&);
00378     friend mitkVector operator - (const mitkVector&, const mitkVector&);
00379     friend mitkVector operator ~ (const mitkVector&);                           // Normalize
00380 
00381     mitkVector& operator *= (const mitkMatrix &);
00382     mitkVector& operator *= (const float);
00383     mitkVector& operator += (const mitkVector &);
00384     mitkVector& operator -= (const mitkVector &);
00385 
00386     float Length();
00387     float Length2();
00388     void Normalize();
00389 };
00390 
00391 #ifdef USE_SIMD
00392 #define _mm_ror_ps(vec,i)   \
00393     (((i)%4) ? (_mm_shuffle_ps(vec,vec, _MM_SHUFFLE((unsigned char)(i+3)%4,(unsigned char)(i+2)%4,(unsigned char)(i+1)%4,(unsigned char)(i+0)%4))) : (vec))
00394 #define _mm_rol_ps(vec,i)   \
00395     (((i)%4) ? (_mm_shuffle_ps(vec,vec, _MM_SHUFFLE((unsigned char)(7-i)%4,(unsigned char)(6-i)%4,(unsigned char)(5-i)%4,(unsigned char)(4-i)%4))) : (vec))
00396 const float _NEGMASK = 0.0f * -1.0f;
00397 const __m128 _MASKSIGN_ = _mm_set_ps(_NEGMASK, _NEGMASK, _NEGMASK, _NEGMASK);
00398 #define _mm_abs_ps(vec)     _mm_andnot_ps(_MASKSIGN_,vec)
00399 #define _mm_neg_ps(vec)     _mm_xor_ps(_MASKSIGN_,vec)
00400 
00401 #pragma pack(pop)
00402 #endif
00403 
00404 //----------------------------------------------------------------------------
00405 inline void mitkMatrix::ZeroMatrix() 
00406 {
00407 #ifdef USE_SIMD
00408     r1 = _mm_setzero_ps();
00409     r2 = _mm_setzero_ps();
00410     r3 = _mm_setzero_ps();
00411     r4 = _mm_setzero_ps();
00412 #else
00413     ele[0] = ele[1] = ele[2] = ele[3] = 0.0f;
00414     ele[4] = ele[5] = ele[6] = ele[7] = 0.0f;
00415     ele[8] = ele[9] = ele[10] = ele[11] = 0.0f;
00416     ele[12] = ele[13] = ele[14] = ele[15] = 0.0f;
00417 #endif
00418 }
00419 //----------------------------------------------------------------------------
00420 inline void mitkMatrix::IdentityMatrix() 
00421 {
00422 #ifdef USE_SIMD
00423     r1 = _mm_setr_ps(1.0f, 0.0f, 0.0f, 0.0f);
00424     r2 = _mm_setr_ps(0.0f, 1.0f, 0.0f, 0.0f);
00425     r3 = _mm_setr_ps(0.0f, 0.0f, 1.0f, 0.0f);
00426     r4 = _mm_setr_ps(0.0f, 0.0f, 0.0f, 1.0f);
00427 #else
00428     ele[0] = ele[5] = ele[10] = ele[15] = 1.0f;
00429     ele[1] = ele[2] = ele[3] = ele[4] = 0.0f;
00430     ele[6] = ele[7] = ele[8] = ele[9] = 0.0f;
00431     ele[11] = ele[12] = ele[13] = ele[14] = 0.0f;
00432 #endif
00433 }
00434 //----------------------------------------------------------------------------
00435 inline mitkMatrix operator * (const mitkMatrix &A, const mitkMatrix &B) 
00436 {
00437     mitkMatrix Res;
00438 
00439 #ifdef USE_SIMD
00440 
00441     __m128 Result;  
00442 
00443     Result = _mm_mul_ps(_mm_set_ps1(B.ele[0]), A.r1);
00444     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[1]), A.r2));
00445     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[2]), A.r3));
00446     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[3]), A.r4));
00447     Res.r1 = Result;
00448     
00449     Result = _mm_mul_ps(_mm_set_ps1(B.ele[4]), A.r1);
00450     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[5]), A.r2));
00451     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[6]), A.r3));
00452     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[7]), A.r4));
00453     Res.r2 = Result;
00454     
00455     Result = _mm_mul_ps(_mm_set_ps1(B.ele[8]), A.r1);
00456     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[9]), A.r2));
00457     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[10]), A.r3));
00458     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[11]), A.r4));
00459     Res.r3 = Result;
00460     
00461     Result = _mm_mul_ps(_mm_set_ps1(B.ele[12]), A.r1);
00462     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[13]), A.r2));
00463     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[14]), A.r3));
00464     Result = _mm_add_ps(Result, _mm_mul_ps(_mm_set_ps1(B.ele[15]), A.r4));
00465     Res.r4 = Result;    
00466         
00467     return Res;
00468     
00469 #else
00470     
00471     Res.ele[0]   = A.ele[0]*B.ele[0] + A.ele[4]*B.ele[1] + A.ele[8]*B.ele[2] + A.ele[12]*B.ele[3]; 
00472     Res.ele[1]   = A.ele[1]*B.ele[0] + A.ele[5]*B.ele[1] + A.ele[9]*B.ele[2] + A.ele[13]*B.ele[3]; 
00473     Res.ele[2]   = A.ele[2]*B.ele[0] + A.ele[6]*B.ele[1] + A.ele[10]*B.ele[2] + A.ele[14]*B.ele[3]; 
00474     Res.ele[3]   = A.ele[3]*B.ele[0] + A.ele[7]*B.ele[1] + A.ele[11]*B.ele[2] + A.ele[15]*B.ele[3]; 
00475 
00476     Res.ele[4]   = A.ele[0]*B.ele[4] + A.ele[4]*B.ele[5] + A.ele[8]*B.ele[6] + A.ele[12]*B.ele[7]; 
00477     Res.ele[5]   = A.ele[1]*B.ele[4] + A.ele[5]*B.ele[5] + A.ele[9]*B.ele[6] + A.ele[13]*B.ele[7]; 
00478     Res.ele[6]   = A.ele[2]*B.ele[4] + A.ele[6]*B.ele[5] + A.ele[10]*B.ele[6] + A.ele[14]*B.ele[7]; 
00479     Res.ele[7]   = A.ele[3]*B.ele[4] + A.ele[7]*B.ele[5] + A.ele[11]*B.ele[6] + A.ele[15]*B.ele[7]; 
00480 
00481     Res.ele[8]   = A.ele[0]*B.ele[8] + A.ele[4]*B.ele[9] + A.ele[8]*B.ele[10] + A.ele[12]*B.ele[11]; 
00482     Res.ele[9]   = A.ele[1]*B.ele[8] + A.ele[5]*B.ele[9] + A.ele[9]*B.ele[10] + A.ele[13]*B.ele[11]; 
00483     Res.ele[10]   = A.ele[2]*B.ele[8] + A.ele[6]*B.ele[9] + A.ele[10]*B.ele[10] + A.ele[14]*B.ele[11]; 
00484     Res.ele[11]   = A.ele[3]*B.ele[8] + A.ele[7]*B.ele[9] + A.ele[11]*B.ele[10] + A.ele[15]*B.ele[11]; 
00485 
00486     Res.ele[12]   = A.ele[0]*B.ele[12] + A.ele[4]*B.ele[13] + A.ele[8]*B.ele[14] + A.ele[12]*B.ele[15];     
00487     Res.ele[13]   = A.ele[1]*B.ele[12] + A.ele[5]*B.ele[13] + A.ele[9]*B.ele[14] + A.ele[13]*B.ele[15];     
00488     Res.ele[14]   = A.ele[2]*B.ele[12] + A.ele[6]*B.ele[13] + A.ele[10]*B.ele[14] + A.ele[14]*B.ele[15];    
00489     Res.ele[15]   = A.ele[3]*B.ele[12] + A.ele[7]*B.ele[13] + A.ele[11]*B.ele[14] + A.ele[15]*B.ele[15];        
00490     return Res; 
00491     
00492 #endif
00493 }
00494 //----------------------------------------------------------------------------
00495 inline mitkMatrix& mitkMatrix::operator *= (const mitkMatrix &B) 
00496 {
00497 #ifdef USE_SIMD
00498 
00499     __m128 Result1, Result2, Result3, Result4;  
00500 
00501     Result1 = _mm_mul_ps(_mm_set_ps1(B.ele[0]), r1);
00502     Result1 = _mm_add_ps(Result1, _mm_mul_ps(_mm_set_ps1(B.ele[1]), r2));
00503     Result1 = _mm_add_ps(Result1, _mm_mul_ps(_mm_set_ps1(B.ele[2]), r3));
00504     Result1 = _mm_add_ps(Result1, _mm_mul_ps(_mm_set_ps1(B.ele[3]), r4));
00505             
00506     Result2 = _mm_mul_ps(_mm_set_ps1(B.ele[4]), r1);
00507     Result2 = _mm_add_ps(Result2, _mm_mul_ps(_mm_set_ps1(B.ele[5]), r2));
00508     Result2 = _mm_add_ps(Result2, _mm_mul_ps(_mm_set_ps1(B.ele[6]), r3));
00509     Result2 = _mm_add_ps(Result2, _mm_mul_ps(_mm_set_ps1(B.ele[7]), r4));
00510             
00511     Result3 = _mm_mul_ps(_mm_set_ps1(B.ele[8]), r1);
00512     Result3 = _mm_add_ps(Result3, _mm_mul_ps(_mm_set_ps1(B.ele[9]), r2));
00513     Result3 = _mm_add_ps(Result3, _mm_mul_ps(_mm_set_ps1(B.ele[10]), r3));
00514     Result3 = _mm_add_ps(Result3, _mm_mul_ps(_mm_set_ps1(B.ele[11]), r4));
00515             
00516     Result4 = _mm_mul_ps(_mm_set_ps1(B.ele[12]), r1);
00517     Result4 = _mm_add_ps(Result4, _mm_mul_ps(_mm_set_ps1(B.ele[13]), r2));
00518     Result4 = _mm_add_ps(Result4, _mm_mul_ps(_mm_set_ps1(B.ele[14]), r3));
00519     Result4 = _mm_add_ps(Result4, _mm_mul_ps(_mm_set_ps1(B.ele[15]), r4));
00520 
00521     r1 = Result1;
00522     r2 = Result2;
00523     r3 = Result3;
00524     r4 = Result4;               
00525     return *this;
00526 
00527 #else
00528 
00529     mitkMatrix Res;
00530     Res.ele[0]   = ele[0]*B.ele[0] + ele[4]*B.ele[1] + ele[8]*B.ele[2] + ele[12]*B.ele[3]; 
00531     Res.ele[1]   = ele[1]*B.ele[0] + ele[5]*B.ele[1] + ele[9]*B.ele[2] + ele[13]*B.ele[3]; 
00532     Res.ele[2]   = ele[2]*B.ele[0] + ele[6]*B.ele[1] + ele[10]*B.ele[2] + ele[14]*B.ele[3]; 
00533     Res.ele[3]   = ele[3]*B.ele[0] + ele[7]*B.ele[1] + ele[11]*B.ele[2] + ele[15]*B.ele[3]; 
00534 
00535     Res.ele[4]   = ele[0]*B.ele[4] + ele[4]*B.ele[5] + ele[8]*B.ele[6] + ele[12]*B.ele[7]; 
00536     Res.ele[5]   = ele[1]*B.ele[4] + ele[5]*B.ele[5] + ele[9]*B.ele[6] + ele[13]*B.ele[7]; 
00537     Res.ele[6]   = ele[2]*B.ele[4] + ele[6]*B.ele[5] + ele[10]*B.ele[6] + ele[14]*B.ele[7]; 
00538     Res.ele[7]   = ele[3]*B.ele[4] + ele[7]*B.ele[5] + ele[11]*B.ele[6] + ele[15]*B.ele[7]; 
00539 
00540     Res.ele[8]   = ele[0]*B.ele[8] + ele[4]*B.ele[9] + ele[8]*B.ele[10] + ele[12]*B.ele[11]; 
00541     Res.ele[9]   = ele[1]*B.ele[8] + ele[5]*B.ele[9] + ele[9]*B.ele[10] + ele[13]*B.ele[11]; 
00542     Res.ele[10]   = ele[2]*B.ele[8] + ele[6]*B.ele[9] + ele[10]*B.ele[10] + ele[14]*B.ele[11]; 
00543     Res.ele[11]   = ele[3]*B.ele[8] + ele[7]*B.ele[9] + ele[11]*B.ele[10] + ele[15]*B.ele[11]; 
00544 
00545     Res.ele[12]   = ele[0]*B.ele[12] + ele[4]*B.ele[13] + ele[8]*B.ele[14] + ele[12]*B.ele[15];     
00546     Res.ele[13]   = ele[1]*B.ele[12] + ele[5]*B.ele[13] + ele[9]*B.ele[14] + ele[13]*B.ele[15];     
00547     Res.ele[14]   = ele[2]*B.ele[12] + ele[6]*B.ele[13] + ele[10]*B.ele[14] + ele[14]*B.ele[15];    
00548     Res.ele[15]   = ele[3]*B.ele[12] + ele[7]*B.ele[13] + ele[11]*B.ele[14] + ele[15]*B.ele[15];        
00549     *this = Res;
00550     return *this;
00551     
00552 #endif
00553 }
00554 //----------------------------------------------------------------------------
00555 inline mitkMatrix operator * (const mitkMatrix &A, const float s) 
00556 {
00557     mitkMatrix Res;
00558 
00559 #ifdef USE_SIMD
00560 
00561     __m128 S = _mm_set_ps1(s);
00562     Res.r1 = _mm_mul_ps(A.r1, S);
00563     Res.r2 = _mm_mul_ps(A.r2, S);
00564     Res.r3 = _mm_mul_ps(A.r3, S);
00565     Res.r4 = _mm_mul_ps(A.r4, S);   
00566     return Res;
00567 
00568 #else
00569 
00570     Res.ele[0] = A.ele[0] * s;
00571     Res.ele[1] = A.ele[1] * s;
00572     Res.ele[2] = A.ele[2] * s;
00573     Res.ele[3] = A.ele[3] * s;
00574     Res.ele[4] = A.ele[4] * s;
00575     Res.ele[5] = A.ele[5] * s;
00576     Res.ele[6] = A.ele[6] * s;
00577     Res.ele[7] = A.ele[7] * s;
00578     Res.ele[8] = A.ele[8] * s;
00579     Res.ele[9] = A.ele[9] * s;
00580     Res.ele[10] = A.ele[10] * s;
00581     Res.ele[11] = A.ele[11] * s;
00582     Res.ele[12] = A.ele[12] * s;
00583     Res.ele[13] = A.ele[13] * s;
00584     Res.ele[14] = A.ele[14] * s;
00585     Res.ele[15] = A.ele[15] * s;
00586     return Res; 
00587 
00588 #endif
00589 }
00590 //----------------------------------------------------------------------------
00591 inline mitkMatrix operator * (const float s, const mitkMatrix &A) 
00592 {
00593     mitkMatrix Res;
00594 
00595 #ifdef USE_SIMD
00596 
00597     __m128 S = _mm_set_ps1(s);
00598     Res.r1 = _mm_mul_ps(A.r1, S);
00599     Res.r2 = _mm_mul_ps(A.r2, S);
00600     Res.r3 = _mm_mul_ps(A.r3, S);
00601     Res.r4 = _mm_mul_ps(A.r4, S);   
00602     return Res;
00603 
00604 #else
00605 
00606     Res.ele[0] = A.ele[0] * s;
00607     Res.ele[1] = A.ele[1] * s;
00608     Res.ele[2] = A.ele[2] * s;
00609     Res.ele[3] = A.ele[3] * s;
00610     Res.ele[4] = A.ele[4] * s;
00611     Res.ele[5] = A.ele[5] * s;
00612     Res.ele[6] = A.ele[6] * s;
00613     Res.ele[7] = A.ele[7] * s;
00614     Res.ele[8] = A.ele[8] * s;
00615     Res.ele[9] = A.ele[9] * s;
00616     Res.ele[10] = A.ele[10] * s;
00617     Res.ele[11] = A.ele[11] * s;
00618     Res.ele[12] = A.ele[12] * s;
00619     Res.ele[13] = A.ele[13] * s;
00620     Res.ele[14] = A.ele[14] * s;
00621     Res.ele[15] = A.ele[15] * s;
00622     return Res; 
00623 
00624 #endif
00625 }
00626 //----------------------------------------------------------------------------
00627 inline mitkMatrix& mitkMatrix::operator *= (const float s) 
00628 {
00629 #ifdef USE_SIMD
00630     __m128 S = _mm_set_ps1(s);
00631     r1 = _mm_mul_ps(r1, S);
00632     r2 = _mm_mul_ps(r2, S);
00633     r3 = _mm_mul_ps(r3, S);
00634     r4 = _mm_mul_ps(r4, S); 
00635     return *this;
00636 #else
00637     ele[0] *= s;
00638     ele[1] *= s;
00639     ele[2] *= s;
00640     ele[3] *= s;
00641     ele[4] *= s;
00642     ele[5] *= s;
00643     ele[6] *= s;
00644     ele[7] *= s;
00645     ele[8] *= s;
00646     ele[9] *= s;
00647     ele[10] *= s;
00648     ele[11] *= s;
00649     ele[12] *= s;
00650     ele[13] *= s;
00651     ele[14] *= s;
00652     ele[15] *= s;
00653     return *this;
00654 #endif
00655 }
00656 //----------------------------------------------------------------------------
00657 inline mitkMatrix operator + (const mitkMatrix &A, const mitkMatrix &B) 
00658 {
00659     mitkMatrix Res;
00660 
00661 #ifdef USE_SIMD
00662 
00663     Res.r1 = _mm_add_ps(A.r1, B.r1);
00664     Res.r2 = _mm_add_ps(A.r2, B.r2);
00665     Res.r3 = _mm_add_ps(A.r3, B.r3);
00666     Res.r4 = _mm_add_ps(A.r4, B.r4);
00667     return Res;
00668 
00669 #else
00670 
00671     Res.ele[0] = A.ele[0] + B.ele[0];
00672     Res.ele[1] = A.ele[1] + B.ele[1];
00673     Res.ele[2] = A.ele[2] + B.ele[2];
00674     Res.ele[3] = A.ele[3] + B.ele[3];
00675     Res.ele[4] = A.ele[4] + B.ele[4];
00676     Res.ele[5] = A.ele[5] + B.ele[5];
00677     Res.ele[6] = A.ele[6] + B.ele[6];
00678     Res.ele[7] = A.ele[7] + B.ele[7];   
00679     Res.ele[8] = A.ele[8] + B.ele[8];
00680     Res.ele[9] = A.ele[9] + B.ele[9];
00681     Res.ele[10] = A.ele[10] + B.ele[10];
00682     Res.ele[11] = A.ele[11] + B.ele[11];
00683     Res.ele[12] = A.ele[12] + B.ele[12];
00684     Res.ele[13] = A.ele[13] + B.ele[13];
00685     Res.ele[14] = A.ele[14] + B.ele[14];
00686     Res.ele[15] = A.ele[15] + B.ele[15];
00687     return Res;
00688 
00689 #endif
00690 }
00691 //----------------------------------------------------------------------------
00692 inline mitkMatrix & mitkMatrix::operator += (const mitkMatrix &B) 
00693 {
00694 #ifdef USE_SIMD
00695     r1 = _mm_add_ps(r1, B.r1);
00696     r2 = _mm_add_ps(r2, B.r2);
00697     r3 = _mm_add_ps(r3, B.r3);
00698     r4 = _mm_add_ps(r4, B.r4);
00699     return *this;
00700 #else
00701     ele[0] += B.ele[0];
00702     ele[1] += B.ele[1];
00703     ele[2] += B.ele[2];
00704     ele[3] += B.ele[3];
00705     ele[4] += B.ele[4];
00706     ele[5] += B.ele[5];
00707     ele[6] += B.ele[6];
00708     ele[7] += B.ele[7];
00709     ele[8] += B.ele[8];
00710     ele[9] += B.ele[9];
00711     ele[10] += B.ele[10];
00712     ele[11] += B.ele[11];
00713     ele[12] += B.ele[12];
00714     ele[13] += B.ele[13];
00715     ele[14] += B.ele[14];
00716     ele[15] += B.ele[15];
00717     return *this;
00718 #endif
00719 }
00720 //----------------------------------------------------------------------------
00721 inline mitkMatrix operator - (const mitkMatrix &A, const mitkMatrix &B) 
00722 {
00723     mitkMatrix Res;
00724 
00725 #ifdef USE_SIMD
00726 
00727     Res.r1 = _mm_sub_ps(A.r1, B.r1);
00728     Res.r2 = _mm_sub_ps(A.r2, B.r2);
00729     Res.r3 = _mm_sub_ps(A.r3, B.r3);
00730     Res.r4 = _mm_sub_ps(A.r4, B.r4);
00731     return Res;
00732     
00733 #else
00734     
00735     Res.ele[0] = A.ele[0] - B.ele[0];
00736     Res.ele[1] = A.ele[1] - B.ele[1];
00737     Res.ele[2] = A.ele[2] - B.ele[2];
00738     Res.ele[3] = A.ele[3] - B.ele[3];
00739     Res.ele[4] = A.ele[4] - B.ele[4];
00740     Res.ele[5] = A.ele[5] - B.ele[5];
00741     Res.ele[6] = A.ele[6] - B.ele[6];
00742     Res.ele[7] = A.ele[7] - B.ele[7];   
00743     Res.ele[8] = A.ele[8] - B.ele[8];
00744     Res.ele[9] = A.ele[9] - B.ele[9];
00745     Res.ele[10] = A.ele[10] - B.ele[10];
00746     Res.ele[11] = A.ele[11] - B.ele[11];
00747     Res.ele[12] = A.ele[12] - B.ele[12];
00748     Res.ele[13] = A.ele[13] - B.ele[13];
00749     Res.ele[14] = A.ele[14] - B.ele[14];
00750     Res.ele[15] = A.ele[15] - B.ele[15];
00751     return Res;
00752 
00753 #endif
00754 }
00755 //----------------------------------------------------------------------------
00756 inline mitkMatrix operator - (const mitkMatrix &A)
00757 {
00758     mitkMatrix Res;
00759 
00760 #ifdef USE_SIMD
00761 
00762     Res.r1 = _mm_neg_ps(A.r1);
00763     Res.r2 = _mm_neg_ps(A.r2);
00764     Res.r3 = _mm_neg_ps(A.r3);
00765     Res.r4 = _mm_neg_ps(A.r4);
00766     return Res;
00767 
00768 #else
00769 
00770     Res.ele[0] = - A.ele[0];
00771     Res.ele[1] = - A.ele[1];
00772     Res.ele[2] = - A.ele[2];
00773     Res.ele[3] = - A.ele[3];
00774     Res.ele[4] = - A.ele[4];
00775     Res.ele[5] = - A.ele[5];
00776     Res.ele[6] = - A.ele[6];
00777     Res.ele[7] = - A.ele[7];    
00778     Res.ele[8] = - A.ele[8];
00779     Res.ele[9] = - A.ele[9];
00780     Res.ele[10] = - A.ele[10];
00781     Res.ele[11] = - A.ele[11];
00782     Res.ele[12] = - A.ele[12];
00783     Res.ele[13] = - A.ele[13];
00784     Res.ele[14] = - A.ele[14];
00785     Res.ele[15] = - A.ele[15];
00786     return Res;
00787 
00788 #endif
00789 }
00790 //----------------------------------------------------------------------------
00791 inline mitkMatrix & mitkMatrix::operator -= (const mitkMatrix &B) 
00792 {
00793 #ifdef USE_SIMD
00794     r1 = _mm_add_ps(r1, B.r1);
00795     r2 = _mm_add_ps(r2, B.r2);
00796     r3 = _mm_add_ps(r3, B.r3);
00797     r4 = _mm_add_ps(r4, B.r4);
00798     return *this;
00799 #else   
00800     ele[0] -= B.ele[0];
00801     ele[1] -= B.ele[1];
00802     ele[2] -= B.ele[2];
00803     ele[3] -= B.ele[3];
00804     ele[4] -= B.ele[4];
00805     ele[5] -= B.ele[5];
00806     ele[6] -= B.ele[6];
00807     ele[7] -= B.ele[7];
00808     ele[8] -= B.ele[8];
00809     ele[9] -= B.ele[9];
00810     ele[10] -= B.ele[10];
00811     ele[11] -= B.ele[11];
00812     ele[12] -= B.ele[12];
00813     ele[13] -= B.ele[13];
00814     ele[14] -= B.ele[14];
00815     ele[15] -= B.ele[15];
00816     return *this;
00817 #endif
00818 }
00819 //----------------------------------------------------------------------------
00820 inline mitkVector operator * (const mitkVector& Vec, const mitkMatrix& Mat) 
00821 {
00822     mitkVector Res;
00823 
00824 #ifdef USE_SIMD
00825 
00826         mitkVector temp;
00827 
00828         temp.vec = _mm_mul_ps(Vec.vec, Mat.r1);
00829         Res.ele[0] = temp.ele[0] + temp.ele[1] + temp.ele[2] + temp.ele[3];
00830 
00831         temp.vec = _mm_mul_ps(Vec.vec, Mat.r2);
00832         Res.ele[1] = temp.ele[0] + temp.ele[1] + temp.ele[2] + temp.ele[3];
00833 
00834         temp.vec = _mm_mul_ps(Vec.vec, Mat.r3);
00835         Res.ele[2] = temp.ele[0] + temp.ele[1] + temp.ele[2] + temp.ele[3];
00836 
00837         temp.vec = _mm_mul_ps(Vec.vec, Mat.r4);
00838         Res.ele[3] = temp.ele[0] + temp.ele[1] + temp.ele[2] + temp.ele[3];
00839         return Res;
00840 
00841 #else
00842     
00843     Res.ele[0] = Mat.ele[0]*Vec.ele[0] + Mat.ele[1]*Vec.ele[1] + Mat.ele[2]*Vec.ele[2] + Mat.ele[3]*Vec.ele[3]; 
00844     Res.ele[1] = Mat.ele[4]*Vec.ele[0] + Mat.ele[5]*Vec.ele[1] + Mat.ele[6]*Vec.ele[2] + Mat.ele[7]*Vec.ele[3]; 
00845     Res.ele[2] = Mat.ele[8]*Vec.ele[0] + Mat.ele[9]*Vec.ele[1] + Mat.ele[10]*Vec.ele[2] + Mat.ele[11]*Vec.ele[3]; 
00846     Res.ele[3] = Mat.ele[12]*Vec.ele[0] + Mat.ele[13]*Vec.ele[1] + Mat.ele[14]*Vec.ele[2] + Mat.ele[15]*Vec.ele[3]; 
00847     return Res; 
00848     
00849 #endif
00850 }
00851 //----------------------------------------------------------------------------
00852 inline mitkVector operator * (const mitkMatrix& Mat, mitkVector& Vec) 
00853 {
00854     mitkVector Res;
00855 
00856 #ifdef USE_SIMD
00857 
00858     Res.vec = _mm_mul_ps(Mat.r1, _mm_set_ps1(Vec.ele[0]));
00859     Res.vec = _mm_add_ps(Res.vec, _mm_mul_ps(Mat.r2, _mm_set_ps1(Vec.ele[1])));
00860     Res.vec = _mm_add_ps(Res.vec, _mm_mul_ps(Mat.r3, _mm_set_ps1(Vec.ele[2])));
00861     Res.vec = _mm_add_ps(Res.vec, _mm_mul_ps(Mat.r4, _mm_set_ps1(Vec.ele[3])));             
00862     return Res;
00863 
00864 #else
00865     
00866     Res.ele[0] = Mat.ele[0]*Vec.ele[0] + Mat.ele[4]*Vec.ele[1] + Mat.ele[8]*Vec.ele[2] + Mat.ele[12]*Vec.ele[3]; 
00867     Res.ele[1] = Mat.ele[1]*Vec.ele[0] + Mat.ele[5]*Vec.ele[1] + Mat.ele[9]*Vec.ele[2] + Mat.ele[13]*Vec.ele[3]; 
00868     Res.ele[2] = Mat.ele[2]*Vec.ele[0] + Mat.ele[6]*Vec.ele[1] + Mat.ele[10]*Vec.ele[2] + Mat.ele[14]*Vec.ele[3]; 
00869     Res.ele[3] = Mat.ele[3]*Vec.ele[0] + Mat.ele[7]*Vec.ele[1] + Mat.ele[11]*Vec.ele[2] + Mat.ele[15]*Vec.ele[3]; 
00870     return Res; 
00871     
00872 #endif
00873 }
00874 //----------------------------------------------------------------------------
00875 inline mitkVector& mitkVector::operator *= (const mitkMatrix& Mat) 
00876 {
00877 #ifdef USE_SIMD
00878 
00879         __m128 temp;
00880         temp = _mm_mul_ps(Mat.r1, _mm_set_ps1(ele[0]));
00881         temp = _mm_add_ps(temp, _mm_mul_ps(Mat.r2, _mm_set_ps1(ele[1])));
00882         temp = _mm_add_ps(temp, _mm_mul_ps(Mat.r3, _mm_set_ps1(ele[2])));
00883         temp = _mm_add_ps(temp, _mm_mul_ps(Mat.r4, _mm_set_ps1(ele[3])));               
00884         vec  = temp;
00885         return *this;
00886 
00887 #else
00888     
00889     float temp[4];
00890     temp[0] = Mat.ele[0]*ele[0] + Mat.ele[4]*ele[1] + Mat.ele[8]*ele[2] + Mat.ele[12]*ele[3]; 
00891     temp[1] = Mat.ele[1]*ele[0] + Mat.ele[5]*ele[1] + Mat.ele[9]*ele[2] + Mat.ele[13]*ele[3]; 
00892     temp[2] = Mat.ele[2]*ele[0] + Mat.ele[6]*ele[1] + Mat.ele[10]*ele[2] + Mat.ele[14]*ele[3]; 
00893     temp[3] = Mat.ele[3]*ele[0] + Mat.ele[7]*ele[1] + Mat.ele[11]*ele[2] + Mat.ele[15]*ele[3]; 
00894     ele[0] = temp[0];
00895     ele[1] = temp[1];
00896     ele[2] = temp[2];
00897     ele[3] = temp[3];   
00898     return *this;
00899 
00900 #endif
00901 }
00902 //----------------------------------------------------------------------------
00903 inline float operator * (const mitkVector& A, const mitkVector& B) 
00904 {
00905 #ifdef USE_SIMD
00906     mitkVector r;
00907     r.vec = _mm_mul_ps(A.vec, B.vec);
00908     return r.ele[0] + r.ele[1] + r.ele[2];
00909 #else
00910     return A.ele[0]*B.ele[0] + A.ele[1]*B.ele[1] + A.ele[2]*B.ele[2];
00911 #endif
00912 }
00913 
00914 //----------------------------------------------------------------------------
00915 inline mitkVector operator % (const mitkVector& A, const mitkVector& B) 
00916 {
00917     mitkVector Res;
00918 
00919 #ifdef USE_SIMD
00920     __m128 l1, l2, m1, m2;
00921     l1 = _mm_shuffle_ps(A.vec,A.vec, _MM_SHUFFLE(3,1,0,2));
00922     l2 = _mm_shuffle_ps(B.vec,B.vec, _MM_SHUFFLE(3,0,2,1));
00923     m2 = _mm_mul_ps(l1, l2);
00924 
00925     l1 = _mm_shuffle_ps(A.vec,A.vec, _MM_SHUFFLE(3,0,2,1));
00926     l2 = _mm_shuffle_ps(B.vec,B.vec, _MM_SHUFFLE(3,1,0,2));
00927     m1 = _mm_mul_ps(l1, l2);
00928 
00929     Res.vec = _mm_sub_ps(m1, m2);       
00930     return Res;
00931 #else
00932     Res.ele[0] = A.ele[1] * B.ele[2] - A.ele[2] * B.ele[1]; 
00933     Res.ele[1] = A.ele[2] * B.ele[0] - A.ele[0] * B.ele[2]; 
00934     Res.ele[2] = A.ele[0] * B.ele[1] - A.ele[1] * B.ele[0]; 
00935     Res.ele[3] = 0.0f;
00936     return Res;
00937 #endif
00938 }
00939 //----------------------------------------------------------------------------
00940 inline mitkVector operator * (const mitkVector &V, const float s) 
00941 {
00942     mitkVector Res;
00943 #ifdef USE_SIMD
00944     Res.vec = _mm_mul_ps(V.vec, _mm_set_ps1(s));
00945     return Res;
00946 #else
00947     Res.ele[0] = V.ele[0] * s;
00948     Res.ele[1] = V.ele[1] * s;
00949     Res.ele[2] = V.ele[2] * s;
00950     Res.ele[3] = V.ele[3] * s;  
00951     return Res;
00952 #endif
00953 }
00954 //----------------------------------------------------------------------------
00955 inline mitkVector operator * (const float s, const mitkVector &V) 
00956 {
00957     mitkVector Res;
00958 #ifdef USE_SIMD
00959     Res.vec = _mm_mul_ps(V.vec, _mm_set_ps1(s));
00960     return Res;
00961 #else
00962     Res.ele[0] = V.ele[0] * s;
00963     Res.ele[1] = V.ele[1] * s;
00964     Res.ele[2] = V.ele[2] * s;
00965     Res.ele[3] = V.ele[3] * s;  
00966     return Res;
00967 #endif
00968 }
00969 //----------------------------------------------------------------------------
00970 inline mitkVector& mitkVector::operator *= (const float s) 
00971 {
00972 #ifdef USE_SIMD
00973     vec = _mm_mul_ps(vec, _mm_set_ps1(s));
00974     return *this;
00975 #else
00976     ele[0] *= s;
00977     ele[1] *= s;
00978     ele[2] *= s;
00979     ele[3] *= s;    
00980     return *this;
00981 #endif
00982 }
00983 //----------------------------------------------------------------------------
00984 inline mitkVector operator + (const mitkVector& A, const mitkVector& B) 
00985 {
00986     mitkVector Res;
00987 #ifdef USE_SIMD
00988     Res.vec = _mm_add_ps(A.vec, B.vec);
00989     return Res;
00990 #else
00991     Res.ele[0] = A.ele[0] + B.ele[0];
00992     Res.ele[1] = A.ele[1] + B.ele[1];
00993     Res.ele[2] = A.ele[2] + B.ele[2];
00994     Res.ele[3] = A.ele[3] + B.ele[3];
00995     return Res;
00996 #endif
00997 }
00998 //----------------------------------------------------------------------------
00999 inline mitkVector operator - (const mitkVector& A, const mitkVector& B) 
01000 {
01001     mitkVector Res;
01002 #ifdef USE_SIMD
01003     Res.vec = _mm_sub_ps(A.vec, B.vec);
01004     return Res;
01005 #else
01006     Res.ele[0] = A.ele[0] - B.ele[0];
01007     Res.ele[1] = A.ele[1] - B.ele[1];
01008     Res.ele[2] = A.ele[2] - B.ele[2];
01009     Res.ele[3] = A.ele[3] - B.ele[3];
01010     return Res;
01011 #endif
01012 }
01013 //----------------------------------------------------------------------------
01014 inline mitkVector operator - (const mitkVector& A)
01015 {
01016     mitkVector Res;
01017 #ifdef USE_SIMD
01018     Res.vec = _mm_neg_ps(A.vec);
01019     return Res;
01020 #else
01021     Res.ele[0] = - A.ele[0];
01022     Res.ele[1] = - A.ele[1];
01023     Res.ele[2] = - A.ele[2];
01024     Res.ele[3] = - A.ele[3];
01025     return Res;
01026 #endif
01027 }
01028 //----------------------------------------------------------------------------
01029 inline mitkVector & mitkVector::operator += (const mitkVector &B) 
01030 {
01031 #ifdef USE_SIMD
01032     vec = _mm_add_ps(vec, B.vec);
01033     return *this;
01034 #else
01035     ele[0] += B.ele[0];
01036     ele[1] += B.ele[1];
01037     ele[2] += B.ele[2];
01038     ele[3] += B.ele[3];
01039     return *this;
01040 #endif
01041 }
01042 //----------------------------------------------------------------------------
01043 inline mitkVector & mitkVector::operator -= (const mitkVector &B) 
01044 {
01045 #ifdef USE_SIMD
01046     vec = _mm_sub_ps(vec, B.vec);
01047     return *this;
01048 #else
01049     ele[0] -= B.ele[0];
01050     ele[1] -= B.ele[1];
01051     ele[2] -= B.ele[2];
01052     ele[3] -= B.ele[3];
01053     return *this;
01054 #endif
01055 }
01056 //----------------------------------------------------------------------------
01057 inline float mitkVector::Length()
01058 {
01059 #ifdef USE_SIMD
01060     __m128 r = _mm_mul_ps(vec, vec);
01061     r = _mm_add_ss(_mm_movehl_ps(r, r), r);
01062     r = _mm_add_ss(_mm_shuffle_ps(r, r, 1), r);
01063     r = _mm_sqrt_ss(r);     
01064     return *(float *)&r;
01065 #else
01066     return sqrtf(ele[0]*ele[0] + ele[1]*ele[1] + ele[2]*ele[2]);
01067 #endif
01068 }
01069 //----------------------------------------------------------------------------
01070 inline float mitkVector::Length2()
01071 {
01072 #ifdef USE_SIMD
01073     __m128 r = _mm_mul_ps(vec, vec);
01074     r = _mm_add_ss(_mm_movehl_ps(r, r), r);
01075     r = _mm_add_ss(_mm_shuffle_ps(r, r, 1), r);
01076     return *(float *)&r;
01077 #else
01078     return (ele[0]*ele[0] + ele[1]*ele[1] + ele[2]*ele[2]);
01079 #endif
01080 }
01081 //----------------------------------------------------------------------------
01082 inline void mitkVector::Normalize() 
01083 {
01084 #ifdef USE_SIMD
01085     __m128 r = _mm_mul_ps(vec, vec);
01086     r = _mm_add_ps(_mm_movehl_ps(r, r), r);
01087     r = _mm_add_ss(_mm_shuffle_ps(r, r, 1), r);
01088     r = _mm_rsqrt_ps(r);
01089     vec = _mm_mul_ps(vec, _mm_shuffle_ps(r, r, 0)); 
01090 #else   
01091     float vecLenInv = 1.0f / sqrtf(ele[0]*ele[0] + ele[1]*ele[1] + ele[2]*ele[2]);
01092     ele[0] *= vecLenInv;
01093     ele[1] *= vecLenInv;
01094     ele[2] *= vecLenInv;
01095 #endif
01096 }
01097 //----------------------------------------------------------------------------
01098 #endif
01099 

Generated on Tue Feb 25 15:00:37 2014 for MITK (Medical Imaging ToolKit) by  doxygen 1.4.3