Ignore:
Timestamp:
Apr 21, 2012, 6:58:26 PM (8 years ago)
Author:
sam
Message:

math: add inversion code for 2×2 and 3×3 matrices, and transposition
code for all matrices.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/math/vector.cpp

    r1180 r1257  
    3737{
    3838
     39static inline float det2(float a, float b,
     40                         float c, float d)
     41{
     42    return a * d - b * c;
     43}
     44
    3945static inline float det3(float a, float b, float c,
    4046                         float d, float e, float f,
     
    4652}
    4753
    48 static inline float cofact3(mat4 const &mat, int i, int j)
     54static inline float cofact(mat2 const &mat, int i, int j)
     55{
     56    return mat[(i + 1) & 1][(j + 1) & 1] * (((i + j) & 1) ? -1.0f : 1.0f);
     57}
     58
     59static inline float cofact(mat3 const &mat, int i, int j)
     60{
     61    return det2(mat[(i + 1) % 3][(j + 1) % 3],
     62                mat[(i + 2) % 3][(j + 1) % 3],
     63                mat[(i + 1) % 3][(j + 2) % 3],
     64                mat[(i + 2) % 3][(j + 2) % 3]);
     65}
     66
     67static inline float cofact(mat4 const &mat, int i, int j)
    4968{
    5069    return det3(mat[(i + 1) & 3][(j + 1) & 3],
     
    5978}
    6079
    61 template<> float mat4::det() const
     80template<> float determinant(mat2 const &mat)
     81{
     82    return mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0];
     83}
     84
     85template<> mat2 transpose(mat2 const &mat)
     86{
     87    mat2 ret;
     88    for (int j = 0; j < 2; j++)
     89        for (int i = 0; i < 2; i++)
     90            ret[j][i] = mat[i][j];
     91    return ret;
     92}
     93
     94template<> mat2 inverse(mat2 const &mat)
     95{
     96    mat2 ret;
     97    float d = determinant(mat);
     98    if (d)
     99    {
     100        d = 1.0f / d;
     101        for (int j = 0; j < 2; j++)
     102            for (int i = 0; i < 2; i++)
     103                ret[j][i] = cofact(mat, i, j) * d;
     104    }
     105    return ret;
     106}
     107
     108template<> float determinant(mat3 const &mat)
     109{
     110    return det3(mat[0][0], mat[0][1], mat[0][2],
     111                mat[1][0], mat[1][1], mat[1][2],
     112                mat[2][0], mat[2][1], mat[2][2]);
     113}
     114
     115template<> mat3 transpose(mat3 const &mat)
     116{
     117    mat3 ret;
     118    for (int j = 0; j < 3; j++)
     119        for (int i = 0; i < 3; i++)
     120            ret[j][i] = mat[i][j];
     121    return ret;
     122}
     123
     124template<> mat3 inverse(mat3 const &mat)
     125{
     126    mat3 ret;
     127    float d = determinant(mat);
     128    if (d)
     129    {
     130        d = 1.0f / d;
     131        for (int j = 0; j < 3; j++)
     132            for (int i = 0; i < 3; i++)
     133                ret[j][i] = cofact(mat, i, j) * d;
     134    }
     135    return ret;
     136}
     137
     138template<> float determinant(mat4 const &mat)
    62139{
    63140    float ret = 0;
    64141    for (int n = 0; n < 4; n++)
    65         ret += (*this)[n][0] * cofact3(*this, n, 0);
    66     return ret;
    67 }
    68 
    69 template<> mat4 mat4::invert() const
     142        ret += mat[n][0] * cofact(mat, n, 0);
     143    return ret;
     144}
     145
     146template<> mat4 transpose(mat4 const &mat)
    70147{
    71148    mat4 ret;
    72     float d = det();
     149    for (int j = 0; j < 4; j++)
     150        for (int i = 0; i < 4; i++)
     151            ret[j][i] = mat[i][j];
     152    return ret;
     153}
     154
     155template<> mat4 inverse(mat4 const &mat)
     156{
     157    mat4 ret;
     158    float d = determinant(mat);
    73159    if (d)
    74160    {
     
    76162        for (int j = 0; j < 4; j++)
    77163            for (int i = 0; i < 4; i++)
    78                 ret[j][i] = cofact3(*this, i, j) * d;
     164                ret[j][i] = cofact(mat, i, j) * d;
    79165    }
    80166    return ret;
     
    119205{
    120206    Log::Debug("[ %6.6f %6.6f %6.6f %6.6f ]\n", x, y, z, w);
     207}
     208
     209template<> void mat2::printf() const
     210{
     211    mat2 const &p = *this;
     212
     213    Log::Debug("[ %6.6f %6.6f\n", p[0][0], p[1][0]);
     214    Log::Debug("  %6.6f %6.6f ]\n", p[0][1], p[1][1]);
     215}
     216
     217template<> void mat3::printf() const
     218{
     219    mat3 const &p = *this;
     220
     221    Log::Debug("[ %6.6f %6.6f %6.6f\n", p[0][0], p[1][0], p[2][0]);
     222    Log::Debug("  %6.6f %6.6f %6.6f\n", p[0][1], p[1][1], p[2][1]);
     223    Log::Debug("  %6.6f %6.6f %6.6f ]\n", p[0][2], p[1][2], p[2][2]);
    121224}
    122225
Note: See TracChangeset for help on using the changeset viewer.