ソースを参照

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

code for all matrices.
legacy
Sam Hocevar sam 12年前
コミット
eb51928415
7個のファイルの変更306行の追加106行の削除
  1. +23
    -18
      src/lol/math/vector.h
  2. +109
    -6
      src/math/vector.cpp
  3. +2
    -2
      test/Makefile.am
  4. +2
    -2
      test/benchmark/vector.cpp
  5. +167
    -0
      test/unit/matrix.cpp
  6. +1
    -77
      test/unit/vector.cpp
  7. +2
    -1
      win32/testsuite.vcxproj

+ 23
- 18
src/lol/math/vector.h ファイルの表示

@@ -1354,9 +1354,6 @@ template <typename T> struct Mat2
inline Vec2<T>& operator[](size_t n) { return (&v0)[n]; } inline Vec2<T>& operator[](size_t n) { return (&v0)[n]; }
inline Vec2<T> const& operator[](size_t n) const { return (&v0)[n]; } inline Vec2<T> const& operator[](size_t n) const { return (&v0)[n]; }


T det() const;
Mat2<T> invert() const;

/* Helpers for transformation matrices */ /* Helpers for transformation matrices */
static Mat2<T> rotate(T angle); static Mat2<T> rotate(T angle);


@@ -1436,9 +1433,6 @@ template <typename T> struct Mat3
inline Vec3<T>& operator[](size_t n) { return (&v0)[n]; } inline Vec3<T>& operator[](size_t n) { return (&v0)[n]; }
inline Vec3<T> const& operator[](size_t n) const { return (&v0)[n]; } inline Vec3<T> const& operator[](size_t n) const { return (&v0)[n]; }


T det() const;
Mat3<T> invert() const;

/* Helpers for transformation matrices */ /* Helpers for transformation matrices */
static Mat3<T> rotate(T angle, T x, T y, T z); static Mat3<T> rotate(T angle, T x, T y, T z);
static Mat3<T> rotate(T angle, Vec3<T> v); static Mat3<T> rotate(T angle, Vec3<T> v);
@@ -1521,9 +1515,6 @@ template <typename T> struct Mat4
inline Vec4<T>& operator[](size_t n) { return (&v0)[n]; } inline Vec4<T>& operator[](size_t n) { return (&v0)[n]; }
inline Vec4<T> const& operator[](size_t n) const { return (&v0)[n]; } inline Vec4<T> const& operator[](size_t n) const { return (&v0)[n]; }


T det() const;
Mat4<T> invert() const;

/* Helpers for transformation matrices */ /* Helpers for transformation matrices */
static Mat4<T> translate(T x, T y, T z); static Mat4<T> translate(T x, T y, T z);
static Mat4<T> translate(Vec3<T> v); static Mat4<T> translate(Vec3<T> v);
@@ -1531,16 +1522,18 @@ template <typename T> struct Mat4
static Mat4<T> rotate(T angle, Vec3<T> v); static Mat4<T> rotate(T angle, Vec3<T> v);
static Mat4<T> rotate(Quat<T> q); static Mat4<T> rotate(Quat<T> q);


static inline Mat4<T> translate(Mat4<T> mat, Vec3<T> v)
static inline Mat4<T> translate(Mat4<T> const &mat, Vec3<T> v)
{ {
return translate(v) * mat; return translate(v) * mat;
} }


static inline Mat4<T> rotate(Mat4<T> mat, T angle, Vec3<T> v)
static inline Mat4<T> rotate(Mat4<T> &mat, T angle, Vec3<T> v)
{ {
return rotate(angle, v) * mat; return rotate(angle, v) * mat;
} }


static Mat3<T> normal(Mat4<T> const &mat);

/* Helpers for view matrices */ /* Helpers for view matrices */
static Mat4<T> lookat(Vec3<T> eye, Vec3<T> center, Vec3<T> up); static Mat4<T> lookat(Vec3<T> eye, Vec3<T> center, Vec3<T> up);


@@ -1556,37 +1549,37 @@ template <typename T> struct Mat4
friend std::ostream &operator<<(std::ostream &stream, Mat4<U> const &m); friend std::ostream &operator<<(std::ostream &stream, Mat4<U> const &m);
#endif #endif


inline Mat4<T> operator +(Mat4<T> const m) const
inline Mat4<T> operator +(Mat4<T> const &m) const
{ {
return Mat4<T>(v0 + m[0], v1 + m[1], v2 + m[2], v3 + m[3]); return Mat4<T>(v0 + m[0], v1 + m[1], v2 + m[2], v3 + m[3]);
} }


inline Mat4<T> operator +=(Mat4<T> const m)
inline Mat4<T> operator +=(Mat4<T> const &m)
{ {
return *this = *this + m; return *this = *this + m;
} }


inline Mat4<T> operator -(Mat4<T> const m) const
inline Mat4<T> operator -(Mat4<T> const &m) const
{ {
return Mat4<T>(v0 - m[0], v1 - m[1], v2 - m[2], v3 - m[3]); return Mat4<T>(v0 - m[0], v1 - m[1], v2 - m[2], v3 - m[3]);
} }


inline Mat4<T> operator -=(Mat4<T> const m)
inline Mat4<T> operator -=(Mat4<T> const &m)
{ {
return *this = *this - m; return *this = *this - m;
} }


inline Mat4<T> operator *(Mat4<T> const m) const
inline Mat4<T> operator *(Mat4<T> const &m) const
{ {
return Mat4<T>(*this * m[0], *this * m[1], *this * m[2], *this * m[3]); return Mat4<T>(*this * m[0], *this * m[1], *this * m[2], *this * m[3]);
} }


inline Mat4<T> operator *=(Mat4<T> const m)
inline Mat4<T> operator *=(Mat4<T> const &m)
{ {
return *this = *this * m; return *this = *this * m;
} }


inline Vec4<T> operator *(Vec4<T> const m) const
inline Vec4<T> operator *(Vec4<T> const &m) const
{ {
Vec4<T> ret; Vec4<T> ret;
for (int j = 0; j < 4; j++) for (int j = 0; j < 4; j++)
@@ -1602,6 +1595,18 @@ template <typename T> struct Mat4
Vec4<T> v0, v1, v2, v3; Vec4<T> v0, v1, v2, v3;
}; };


template<typename T> T determinant(Mat2<T> const &);
template<typename T> T determinant(Mat3<T> const &);
template<typename T> T determinant(Mat4<T> const &);

template<typename T> Mat2<T> transpose(Mat2<T> const &);
template<typename T> Mat3<T> transpose(Mat3<T> const &);
template<typename T> Mat4<T> transpose(Mat4<T> const &);

template<typename T> Mat2<T> inverse(Mat2<T> const &);
template<typename T> Mat3<T> inverse(Mat3<T> const &);
template<typename T> Mat4<T> inverse(Mat4<T> const &);

/* /*
* Arbitrarily-sized square matrices; for now this only supports * Arbitrarily-sized square matrices; for now this only supports
* naive inversion and is used for the Remez inversion method. * naive inversion and is used for the Remez inversion method.


+ 109
- 6
src/math/vector.cpp ファイルの表示

@@ -36,6 +36,12 @@ using namespace std;
namespace lol namespace lol
{ {


static inline float det2(float a, float b,
float c, float d)
{
return a * d - b * c;
}

static inline float det3(float a, float b, float c, static inline float det3(float a, float b, float c,
float d, float e, float f, float d, float e, float f,
float g, float h, float i) float g, float h, float i)
@@ -45,7 +51,20 @@ static inline float det3(float a, float b, float c,
+ c * (d * h - g * e); + c * (d * h - g * e);
} }


static inline float cofact3(mat4 const &mat, int i, int j)
static inline float cofact(mat2 const &mat, int i, int j)
{
return mat[(i + 1) & 1][(j + 1) & 1] * (((i + j) & 1) ? -1.0f : 1.0f);
}

static inline float cofact(mat3 const &mat, int i, int j)
{
return det2(mat[(i + 1) % 3][(j + 1) % 3],
mat[(i + 2) % 3][(j + 1) % 3],
mat[(i + 1) % 3][(j + 2) % 3],
mat[(i + 2) % 3][(j + 2) % 3]);
}

static inline float cofact(mat4 const &mat, int i, int j)
{ {
return det3(mat[(i + 1) & 3][(j + 1) & 3], return det3(mat[(i + 1) & 3][(j + 1) & 3],
mat[(i + 2) & 3][(j + 1) & 3], mat[(i + 2) & 3][(j + 1) & 3],
@@ -58,24 +77,91 @@ static inline float cofact3(mat4 const &mat, int i, int j)
mat[(i + 3) & 3][(j + 3) & 3]) * (((i + j) & 1) ? -1.0f : 1.0f); mat[(i + 3) & 3][(j + 3) & 3]) * (((i + j) & 1) ? -1.0f : 1.0f);
} }


template<> float mat4::det() const
template<> float determinant(mat2 const &mat)
{
return mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0];
}

template<> mat2 transpose(mat2 const &mat)
{
mat2 ret;
for (int j = 0; j < 2; j++)
for (int i = 0; i < 2; i++)
ret[j][i] = mat[i][j];
return ret;
}

template<> mat2 inverse(mat2 const &mat)
{
mat2 ret;
float d = determinant(mat);
if (d)
{
d = 1.0f / d;
for (int j = 0; j < 2; j++)
for (int i = 0; i < 2; i++)
ret[j][i] = cofact(mat, i, j) * d;
}
return ret;
}

template<> float determinant(mat3 const &mat)
{
return det3(mat[0][0], mat[0][1], mat[0][2],
mat[1][0], mat[1][1], mat[1][2],
mat[2][0], mat[2][1], mat[2][2]);
}

template<> mat3 transpose(mat3 const &mat)
{
mat3 ret;
for (int j = 0; j < 3; j++)
for (int i = 0; i < 3; i++)
ret[j][i] = mat[i][j];
return ret;
}

template<> mat3 inverse(mat3 const &mat)
{
mat3 ret;
float d = determinant(mat);
if (d)
{
d = 1.0f / d;
for (int j = 0; j < 3; j++)
for (int i = 0; i < 3; i++)
ret[j][i] = cofact(mat, i, j) * d;
}
return ret;
}

template<> float determinant(mat4 const &mat)
{ {
float ret = 0; float ret = 0;
for (int n = 0; n < 4; n++) for (int n = 0; n < 4; n++)
ret += (*this)[n][0] * cofact3(*this, n, 0);
ret += mat[n][0] * cofact(mat, n, 0);
return ret; return ret;
} }


template<> mat4 mat4::invert() const
template<> mat4 transpose(mat4 const &mat)
{ {
mat4 ret; mat4 ret;
float d = det();
for (int j = 0; j < 4; j++)
for (int i = 0; i < 4; i++)
ret[j][i] = mat[i][j];
return ret;
}

template<> mat4 inverse(mat4 const &mat)
{
mat4 ret;
float d = determinant(mat);
if (d) if (d)
{ {
d = 1.0f / d; d = 1.0f / d;
for (int j = 0; j < 4; j++) for (int j = 0; j < 4; j++)
for (int i = 0; i < 4; i++) for (int i = 0; i < 4; i++)
ret[j][i] = cofact3(*this, i, j) * d;
ret[j][i] = cofact(mat, i, j) * d;
} }
return ret; return ret;
} }
@@ -120,6 +206,23 @@ template<> void quat::printf() const
Log::Debug("[ %6.6f %6.6f %6.6f %6.6f ]\n", x, y, z, w); Log::Debug("[ %6.6f %6.6f %6.6f %6.6f ]\n", x, y, z, w);
} }


template<> void mat2::printf() const
{
mat2 const &p = *this;

Log::Debug("[ %6.6f %6.6f\n", p[0][0], p[1][0]);
Log::Debug(" %6.6f %6.6f ]\n", p[0][1], p[1][1]);
}

template<> void mat3::printf() const
{
mat3 const &p = *this;

Log::Debug("[ %6.6f %6.6f %6.6f\n", p[0][0], p[1][0], p[2][0]);
Log::Debug(" %6.6f %6.6f %6.6f\n", p[0][1], p[1][1], p[2][1]);
Log::Debug(" %6.6f %6.6f %6.6f ]\n", p[0][2], p[1][2], p[2][2]);
}

template<> void mat4::printf() const template<> void mat4::printf() const
{ {
mat4 const &p = *this; mat4 const &p = *this;


+ 2
- 2
test/Makefile.am ファイルの表示

@@ -22,8 +22,8 @@ noinst_PROGRAMS = quad benchsuite testsuite
TESTS = testsuite TESTS = testsuite


testsuite_SOURCES = testsuite.cpp \ testsuite_SOURCES = testsuite.cpp \
unit/vector.cpp unit/half.cpp unit/trig.cpp unit/build.cpp \
unit/real.cpp unit/image.cpp unit/quat.cpp unit/cmplx.cpp
unit/vector.cpp unit/matrix.cpp unit/half.cpp unit/trig.cpp \
unit/build.cpp unit/real.cpp unit/image.cpp unit/quat.cpp unit/cmplx.cpp
testsuite_CPPFLAGS = @LOL_CFLAGS@ @PIPI_CFLAGS@ testsuite_CPPFLAGS = @LOL_CFLAGS@ @PIPI_CFLAGS@
testsuite_LDFLAGS = $(top_builddir)/src/liblol.a @LOL_LIBS@ @PIPI_LIBS@ testsuite_LDFLAGS = $(top_builddir)/src/liblol.a @LOL_LIBS@ @PIPI_LIBS@
testsuite_DEPENDENCIES = $(top_builddir)/src/liblol.a testsuite_DEPENDENCIES = $(top_builddir)/src/liblol.a


+ 2
- 2
test/benchmark/vector.cpp ファイルの表示

@@ -52,7 +52,7 @@ void bench_matrix(int mode)
/* Determinant */ /* Determinant */
timer.GetMs(); timer.GetMs();
for (size_t i = 0; i < MATRIX_TABLE_SIZE; i++) for (size_t i = 0; i < MATRIX_TABLE_SIZE; i++)
pf[i] = pm[i].det();
pf[i] = determinant(pm[i]);
result[1] += timer.GetMs(); result[1] += timer.GetMs();


/* Multiply matrices */ /* Multiply matrices */
@@ -70,7 +70,7 @@ void bench_matrix(int mode)
/* Invert matrix */ /* Invert matrix */
timer.GetMs(); timer.GetMs();
for (size_t i = 0; i < MATRIX_TABLE_SIZE; i++) for (size_t i = 0; i < MATRIX_TABLE_SIZE; i++)
pm[i] = pm[i].invert();
pm[i] = inverse(pm[i]);
result[4] += timer.GetMs(); result[4] += timer.GetMs();
} }




+ 167
- 0
test/unit/matrix.cpp ファイルの表示

@@ -0,0 +1,167 @@
//
// Lol Engine
//
// Copyright: (c) 2010-2012 Sam Hocevar <sam@hocevar.net>
// This program is free software; you can redistribute it and/or
// modify it under the terms of the Do What The Fuck You Want To
// Public License, Version 2, as published by Sam Hocevar. See
// http://sam.zoy.org/projects/COPYING.WTFPL for more details.
//

#if defined HAVE_CONFIG_H
# include "config.h"
#endif

#include "core.h"
#include "lol/unit.h"

namespace lol
{

LOLUNIT_FIXTURE(MatrixTest)
{
void SetUp()
{
id2 = mat2(1.0f);
tri2 = mat2(vec2(1.0f, 0.0f),
vec2(7.0f, 2.0f));
inv2 = mat2(vec2(4.0f, 3.0f),
vec2(3.0f, 2.0f));

id3 = mat3(1.0f);
tri3 = mat3(vec3(1.0f, 0.0f, 0.0f),
vec3(7.0f, 2.0f, 0.0f),
vec3(1.0f, 5.0f, 3.0f));
inv3 = mat3(vec3(2.0f, 3.0f, 5.0f),
vec3(3.0f, 2.0f, 3.0f),
vec3(9.0f, 5.0f, 7.0f));

id4 = mat4(1.0f);
tri4 = mat4(vec4(1.0f, 0.0f, 0.0f, 0.0f),
vec4(7.0f, 2.0f, 0.0f, 0.0f),
vec4(1.0f, 5.0f, 3.0f, 0.0f),
vec4(8.0f, 9.0f, 2.0f, 4.0f));
inv4 = mat4(vec4( 1.0f, 1.0f, 2.0f, -1.0f),
vec4(-2.0f, -1.0f, -2.0f, 2.0f),
vec4( 4.0f, 2.0f, 5.0f, -4.0f),
vec4( 5.0f, -3.0f, -7.0f, -6.0f));
}

void TearDown() {}

LOLUNIT_TEST(Determinant)
{
float d1, d2;

d1 = determinant(tri2);
LOLUNIT_ASSERT_EQUAL(d1, 2.0f);
d2 = determinant(inv2);
LOLUNIT_ASSERT_EQUAL(d2, -1.0f);

d1 = determinant(tri3);
LOLUNIT_ASSERT_EQUAL(d1, 6.0f);
d2 = determinant(inv3);
LOLUNIT_ASSERT_EQUAL(d2, 1.0f);

d1 = determinant(tri4);
LOLUNIT_ASSERT_EQUAL(d1, 24.0f);
d2 = determinant(inv4);
LOLUNIT_ASSERT_EQUAL(d2, -1.0f);
}

LOLUNIT_TEST(Multiplication)
{
mat4 m0 = id4;
mat4 m1 = id4;
mat4 m2 = m0 * m1;

LOLUNIT_ASSERT_EQUAL(m2[0][0], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][0], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][1], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][1], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][2], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][2], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][3], 1.0f);
}

LOLUNIT_TEST(Inverse2x2)
{
mat2 m0 = inv2;
mat2 m1 = inverse(m0);

mat2 m2 = m0 * m1;

LOLUNIT_ASSERT_EQUAL(m2[0][0], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][0], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][1], 1.0f);
}

LOLUNIT_TEST(Inverse3x3)
{
mat3 m0 = inv3;
mat3 m1 = inverse(m0);

mat3 m2 = m0 * m1;

LOLUNIT_ASSERT_EQUAL(m2[0][0], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][0], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][1], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][1], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][2], 1.0f);
}

LOLUNIT_TEST(Inverse4x4)
{
mat4 m0 = inv4;
mat4 m1 = inverse(m0);

mat4 m2 = m0 * m1;

LOLUNIT_ASSERT_EQUAL(m2[0][0], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][0], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][1], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][1], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][2], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][2], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][3], 1.0f);
}

mat2 tri2, id2, inv2;
mat3 tri3, id3, inv3;
mat4 tri4, id4, inv4;
};

} /* namespace lol */


+ 1
- 77
test/unit/vector.cpp ファイルの表示

@@ -20,18 +20,7 @@ namespace lol


LOLUNIT_FIXTURE(VectorTest) LOLUNIT_FIXTURE(VectorTest)
{ {
void SetUp()
{
identity = mat4(1.0f);
triangular = mat4(vec4(1.0f, 0.0f, 0.0f, 0.0f),
vec4(7.0f, 2.0f, 0.0f, 0.0f),
vec4(1.0f, 5.0f, 3.0f, 0.0f),
vec4(8.0f, 9.0f, 2.0f, 4.0f));
invertible = mat4(vec4( 1.0f, 1.0f, 2.0f, -1.0f),
vec4(-2.0f, -1.0f, -2.0f, 2.0f),
vec4( 4.0f, 2.0f, 5.0f, -4.0f),
vec4( 5.0f, -3.0f, -7.0f, -6.0f));
}
void SetUp() {}


void TearDown() {} void TearDown() {}


@@ -135,71 +124,6 @@ LOLUNIT_FIXTURE(VectorTest)
LOLUNIT_ASSERT_EQUAL(c.w, 0.0f); LOLUNIT_ASSERT_EQUAL(c.w, 0.0f);
LOLUNIT_ASSERT_EQUAL(a3, a1); LOLUNIT_ASSERT_EQUAL(a3, a1);
} }

LOLUNIT_TEST(MatrixDeterminant)
{
float d1 = triangular.det();
LOLUNIT_ASSERT_EQUAL(d1, 24.0f);
float d2 = invertible.det();
LOLUNIT_ASSERT_EQUAL(d2, -1.0f);
}

LOLUNIT_TEST(MatrixMultiplication)
{
mat4 m0 = identity;
mat4 m1 = identity;
mat4 m2 = m0 * m1;

LOLUNIT_ASSERT_EQUAL(m2[0][0], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][0], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][1], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][1], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][2], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][2], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][3], 1.0f);
}

LOLUNIT_TEST(MatrixInverse)
{
mat4 m0 = invertible;
mat4 m1 = m0.invert();

mat4 m2 = m0 * m1;

LOLUNIT_ASSERT_EQUAL(m2[0][0], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][0], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][0], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][1], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][1], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][1], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][2], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][2], 1.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][2], 0.0f);

LOLUNIT_ASSERT_EQUAL(m2[0][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[1][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[2][3], 0.0f);
LOLUNIT_ASSERT_EQUAL(m2[3][3], 1.0f);
}

mat4 triangular, identity, invertible;
}; };


} /* namespace lol */ } /* namespace lol */


+ 2
- 1
win32/testsuite.vcxproj ファイルの表示

@@ -32,6 +32,7 @@
<ClCompile Include="..\test\unit\cmplx.cpp" /> <ClCompile Include="..\test\unit\cmplx.cpp" />
<ClCompile Include="..\test\unit\half.cpp" /> <ClCompile Include="..\test\unit\half.cpp" />
<ClCompile Include="..\test\unit\image.cpp" /> <ClCompile Include="..\test\unit\image.cpp" />
<ClCompile Include="..\test\unit\matrix.cpp" />
<ClCompile Include="..\test\unit\quat.cpp" /> <ClCompile Include="..\test\unit\quat.cpp" />
<ClCompile Include="..\test\unit\real.cpp" /> <ClCompile Include="..\test\unit\real.cpp" />
<ClCompile Include="..\test\unit\trig.cpp" /> <ClCompile Include="..\test\unit\trig.cpp" />
@@ -60,4 +61,4 @@
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" /> <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets"> <ImportGroup Label="ExtensionTargets">
</ImportGroup> </ImportGroup>
</Project>
</Project>

読み込み中…
キャンセル
保存