MASK to SWIZZLE in the vector templates, rename matrix<> to mat<> for consistency, implement transposition for all matrix sizes, make matrix columns private and only accessible through operator[].undefined
| @@ -1449,15 +1449,15 @@ void EasyMesh::AppendCapsule(int ndivisions, float h, float d) | |||||
| /* Fill in the icosahedron vertices, rotating them so that there | /* Fill in the icosahedron vertices, rotating them so that there | ||||
| * is a vertex at [0 1 0] and [0 -1 0] after normalisation. */ | * is a vertex at [0 1 0] and [0 -1 0] after normalisation. */ | ||||
| float phi = 0.5f + 0.5f * sqrt(5.f); | float phi = 0.5f + 0.5f * sqrt(5.f); | ||||
| mat3 mat = mat3::rotate(degrees(asin(1.f / sqrt(2.f + phi))), | |||||
| vec3(0.f, 0.f, 1.f)); | |||||
| mat3 m = mat3::rotate(degrees(asin(1.f / sqrt(2.f + phi))), | |||||
| vec3(0.f, 0.f, 1.f)); | |||||
| for (int i = 0; i < 4; i++) | for (int i = 0; i < 4; i++) | ||||
| { | { | ||||
| float x = (i & 1) ? 0.5f : -0.5f; | float x = (i & 1) ? 0.5f : -0.5f; | ||||
| float y = (i & 2) ? phi * 0.5f : phi * -0.5f; | float y = (i & 2) ? phi * 0.5f : phi * -0.5f; | ||||
| vertices << mat * vec3(x, y, 0.f); | |||||
| vertices << mat * vec3(0.f, x, y); | |||||
| vertices << mat * vec3(y, 0.f, x); | |||||
| vertices << m * vec3(x, y, 0.f); | |||||
| vertices << m * vec3(0.f, x, y); | |||||
| vertices << m * vec3(y, 0.f, x); | |||||
| } | } | ||||
| static int const trilist[] = | static int const trilist[] = | ||||
| @@ -42,6 +42,7 @@ | |||||
| * (planned for Visual Studion 14) */ | * (planned for Visual Studion 14) */ | ||||
| #define LOL_FEATURE_CXX11_RELAXED_UNIONS 0 | #define LOL_FEATURE_CXX11_RELAXED_UNIONS 0 | ||||
| #define LOL_FEATURE_CXX11_INHERIT_CONSTRUCTORS 0 | #define LOL_FEATURE_CXX11_INHERIT_CONSTRUCTORS 0 | ||||
| #define LOL_FEATURE_CXX11_ARRAY_INITIALIZERS 0 | |||||
| #define LOL_FEATURE_CXX11_CONSTEXPR 0 | #define LOL_FEATURE_CXX11_CONSTEXPR 0 | ||||
| #define LOL_FEATURE_CXX11_ISNAN 0 | #define LOL_FEATURE_CXX11_ISNAN 0 | ||||
| @@ -54,6 +55,8 @@ | |||||
| # define LOL_FEATURE_CXX11_CONSTEXPR 1 | # define LOL_FEATURE_CXX11_CONSTEXPR 1 | ||||
| # undef LOL_FEATURE_CXX11_ISNAN | # undef LOL_FEATURE_CXX11_ISNAN | ||||
| # define LOL_FEATURE_CXX11_ISNAN 1 | # define LOL_FEATURE_CXX11_ISNAN 1 | ||||
| # undef LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| # define LOL_FEATURE_CXX11_ARRAY_INITIALIZERS 1 | |||||
| # endif | # endif | ||||
| # if (__GNUC__ * 100 + __GNUC_MINOR__) < 470 | # if (__GNUC__ * 100 + __GNUC_MINOR__) < 470 | ||||
| # undef LOL_FEATURE_CXX11_TEMPLATE_ALIASES | # undef LOL_FEATURE_CXX11_TEMPLATE_ALIASES | ||||
| @@ -64,6 +67,8 @@ | |||||
| # undef LOL_FEATURE_CXX11_CONSTEXPR | # undef LOL_FEATURE_CXX11_CONSTEXPR | ||||
| # define LOL_FEATURE_CXX11_CONSTEXPR 1 | # define LOL_FEATURE_CXX11_CONSTEXPR 1 | ||||
| # endif | # endif | ||||
| # undef LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| # define LOL_FEATURE_CXX11_ARRAY_INITIALIZERS 1 | |||||
| #endif | #endif | ||||
| @@ -34,7 +34,10 @@ class half; | |||||
| * Forward declaration of vec and matrix | * Forward declaration of vec and matrix | ||||
| */ | */ | ||||
| template<int N, typename T, int MASK = -1> struct vec; | |||||
| int const FULL_SWIZZLE = 0xaaaa; | |||||
| int const NO_SWIZZLE = 0xbbbb; | |||||
| template<int N, typename T, int SWIZZLE = FULL_SWIZZLE> struct vec; | |||||
| template<int COLS, int ROWS, typename T> struct matrix; | template<int COLS, int ROWS, typename T> struct matrix; | ||||
| template<typename T> struct Cmplx; | template<typename T> struct Cmplx; | ||||
| template<typename T> struct Quat; | template<typename T> struct Quat; | ||||
| @@ -99,6 +102,19 @@ typedef mat3x4 float3x4; | |||||
| typedef mat4x2 float4x2; | typedef mat4x2 float4x2; | ||||
| typedef mat4x3 float4x3; | typedef mat4x3 float4x3; | ||||
| typedef f16vec2 half2; | |||||
| typedef f16vec3 half3; | |||||
| typedef f16vec4 half4; | |||||
| typedef f16mat2 half2x2; | |||||
| typedef f16mat3 half3x3; | |||||
| typedef f16mat4 half4x4; | |||||
| typedef f16mat2x3 half2x3; | |||||
| typedef f16mat2x4 half2x4; | |||||
| typedef f16mat3x2 half3x2; | |||||
| typedef f16mat3x4 half3x4; | |||||
| typedef f16mat4x2 half4x2; | |||||
| typedef f16mat4x3 half4x3; | |||||
| typedef ivec2 int2; | typedef ivec2 int2; | ||||
| typedef ivec3 int3; | typedef ivec3 int3; | ||||
| typedef ivec4 int4; | typedef ivec4 int4; | ||||
| @@ -28,7 +28,10 @@ namespace lol | |||||
| # define constexpr /* */ | # define constexpr /* */ | ||||
| #endif | #endif | ||||
| /* The generic "matrix" type, which is a fixed-size matrix */ | |||||
| /* | |||||
| * The generic "matrix" type, which is fixed-size | |||||
| */ | |||||
| template<int COLS, int ROWS, typename T> | template<int COLS, int ROWS, typename T> | ||||
| struct matrix | struct matrix | ||||
| { | { | ||||
| @@ -61,25 +64,42 @@ struct matrix<2, 2, T> | |||||
| typedef matrix<2,2,T> type; | typedef matrix<2,2,T> type; | ||||
| inline matrix() {} | inline matrix() {} | ||||
| inline matrix(vec<2,T> V0, vec<2,T> V1) | |||||
| : v0(V0), v1(V1) {} | |||||
| inline matrix(vec<2,T> v0, vec<2,T> v1) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ v0, v1 } {} | |||||
| #else | |||||
| : m_v0(v0), m_v1(v1) {} | |||||
| #endif | |||||
| explicit inline matrix(T const &val) | explicit inline matrix(T const &val) | ||||
| : v0(val, (T)0), | |||||
| v1((T)0, val) {} | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ vec<2,T>(val, T(0)), | |||||
| vec<2,T>(T(0), val) } {} | |||||
| #else | |||||
| : m_v0(val, T(0)), | |||||
| m_v1(T(0), val) {} | |||||
| #endif | |||||
| explicit inline matrix(matrix<4,4,T> const &mat) | |||||
| : v0(mat[0].xy), | |||||
| v1(mat[1].xy) {} | |||||
| explicit inline matrix(matrix<4,4,T> const &m) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ m[0].xy, m[1].xy } {} | |||||
| #else | |||||
| : m_v0(m[0].xy), m_v1(m[1].xy) {} | |||||
| #endif | |||||
| inline vec<2,T>& operator[](size_t n) { return (&v0)[n]; } | |||||
| inline vec<2,T> const& operator[](size_t n) const { return (&v0)[n]; } | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| inline vec<2,T>& operator[](size_t n) { return m_data[n]; } | |||||
| inline vec<2,T> const& operator[](size_t n) const { return m_data[n]; } | |||||
| #else | |||||
| inline vec<2,T>& operator[](size_t n) { return (&m_v0)[n]; } | |||||
| inline vec<2,T> const& operator[](size_t n) const { return (&m_v0)[n]; } | |||||
| #endif | |||||
| /* Helpers for transformation matrices */ | /* Helpers for transformation matrices */ | ||||
| static matrix<2,2,T> rotate(T degrees); | static matrix<2,2,T> rotate(T degrees); | ||||
| static inline matrix<2,2,T> rotate(matrix<2,2,T> mat, T degrees) | |||||
| static inline matrix<2,2,T> rotate(matrix<2,2,T> m, T degrees) | |||||
| { | { | ||||
| return rotate(degrees) * mat; | |||||
| return rotate(degrees) * m; | |||||
| } | } | ||||
| void printf() const; | void printf() const; | ||||
| @@ -89,9 +109,14 @@ struct matrix<2, 2, T> | |||||
| friend std::ostream &operator<<(std::ostream &stream, | friend std::ostream &operator<<(std::ostream &stream, | ||||
| matrix<2,2,U> const &m); | matrix<2,2,U> const &m); | ||||
| vec<2,T> v0, v1; | |||||
| static const matrix<2,2,T> identity; | static const matrix<2,2,T> identity; | ||||
| private: | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| vec<2,T> m_data[2]; | |||||
| #else | |||||
| vec<2,T> m_v0, m_v1; | |||||
| #endif | |||||
| }; | }; | ||||
| /* | /* | ||||
| @@ -104,33 +129,51 @@ struct matrix<3,3,T> | |||||
| typedef matrix<3,3,T> type; | typedef matrix<3,3,T> type; | ||||
| inline matrix() {} | inline matrix() {} | ||||
| inline matrix(vec<3,T> V0, vec<3,T> V1, vec<3,T> V2) | |||||
| : v0(V0), v1(V1), v2(V2) {} | |||||
| inline matrix(vec<3,T> v0, vec<3,T> v1, vec<3,T> v2) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ v0, v1, v2 } {} | |||||
| #else | |||||
| : m_v0(v0), m_v1(v1), m_v2(v2) {} | |||||
| #endif | |||||
| explicit inline matrix(T const &val) | explicit inline matrix(T const &val) | ||||
| : v0(val, (T)0, (T)0), | |||||
| v1((T)0, val, (T)0), | |||||
| v2((T)0, (T)0, val) {} | |||||
| explicit inline matrix(matrix<2,2,T> mat) | |||||
| : v0(mat[0], (T)0), | |||||
| v1(mat[1], (T)0), | |||||
| v2((T)0, (T)0, (T)0) {} | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ vec<3,T>(val, (T)0, (T)0), | |||||
| vec<3,T>((T)0, val, (T)0), | |||||
| vec<3,T>((T)0, (T)0, val) } {} | |||||
| #else | |||||
| : m_v0(val, (T)0, (T)0), | |||||
| m_v1((T)0, val, (T)0), | |||||
| m_v2((T)0, (T)0, val) {} | |||||
| #endif | |||||
| explicit inline matrix(matrix<2,2,T> mat, T const &val) | |||||
| : v0(vec<3,T>(mat[0], (T)0)), | |||||
| v1(vec<3,T>(mat[1], (T)0)), | |||||
| v2((T)0, (T)0, val) {} | |||||
| explicit inline matrix(matrix<2,2,T> m, T const &val = T(1)) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ vec<3,T>(m[0], (T)0), | |||||
| vec<3,T>(m[1], (T)0), | |||||
| vec<3,T>((T)0, (T)0, val) } {} | |||||
| #else | |||||
| : m_v0(m[0], (T)0), | |||||
| m_v1(m[1], (T)0), | |||||
| m_v2((T)0, (T)0, val) {} | |||||
| #endif | |||||
| explicit inline matrix(matrix<4,4,T> const &mat) | |||||
| : v0(mat[0].xyz), | |||||
| v1(mat[1].xyz), | |||||
| v2(mat[2].xyz) {} | |||||
| explicit inline matrix(matrix<4,4,T> const &m) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ m[0].xyz, m[1].xyz, m[2].xyz } {} | |||||
| #else | |||||
| : m_v0(m[0].xyz), m_v1(m[1].xyz), m_v2(m[2].xyz) {} | |||||
| #endif | |||||
| explicit matrix(Quat<T> const &q); | explicit matrix(Quat<T> const &q); | ||||
| inline vec<3,T>& operator[](size_t n) { return (&v0)[n]; } | |||||
| inline vec<3,T> const& operator[](size_t n) const { return (&v0)[n]; } | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| inline vec<3,T>& operator[](size_t n) { return m_data[n]; } | |||||
| inline vec<3,T> const& operator[](size_t n) const { return m_data[n]; } | |||||
| #else | |||||
| inline vec<3,T>& operator[](size_t n) { return (&m_v0)[n]; } | |||||
| inline vec<3,T> const& operator[](size_t n) const { return (&m_v0)[n]; } | |||||
| #endif | |||||
| /* Helpers for transformation matrices */ | /* Helpers for transformation matrices */ | ||||
| static matrix<3,3,T> scale(T x); | static matrix<3,3,T> scale(T x); | ||||
| @@ -165,9 +208,9 @@ struct matrix<3,3,T> | |||||
| static matrix<3,3,T> fromeuler_zxz(T phi, T theta, T psi); | static matrix<3,3,T> fromeuler_zxz(T phi, T theta, T psi); | ||||
| static matrix<3,3,T> fromeuler_zyz(T phi, T theta, T psi); | static matrix<3,3,T> fromeuler_zyz(T phi, T theta, T psi); | ||||
| static inline matrix<3,3,T> rotate(matrix<3,3,T> mat, T degrees, vec<3,T> v) | |||||
| static inline matrix<3,3,T> rotate(matrix<3,3,T> m, T degrees, vec<3,T> v) | |||||
| { | { | ||||
| return rotate(degrees, v) * mat; | |||||
| return rotate(degrees, v) * m; | |||||
| } | } | ||||
| void printf() const; | void printf() const; | ||||
| @@ -177,9 +220,14 @@ struct matrix<3,3,T> | |||||
| friend std::ostream &operator<<(std::ostream &stream, | friend std::ostream &operator<<(std::ostream &stream, | ||||
| matrix<3,3,U> const &m); | matrix<3,3,U> const &m); | ||||
| vec<3,T> v0, v1, v2; | |||||
| static const matrix<3,3,T> identity; | static const matrix<3,3,T> identity; | ||||
| private: | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| vec<3,T> m_data[3]; | |||||
| #else | |||||
| vec<3,T> m_v0, m_v1, m_v2; | |||||
| #endif | |||||
| }; | }; | ||||
| /* | /* | ||||
| @@ -192,43 +240,61 @@ struct matrix<4, 4, T> | |||||
| typedef matrix<4,4,T> type; | typedef matrix<4,4,T> type; | ||||
| inline matrix() {} | inline matrix() {} | ||||
| inline matrix(vec<4,T> V0, vec<4,T> V1, vec<4,T> V2, vec<4,T> V3) | |||||
| : v0(V0), v1(V1), v2(V2), v3(V3) {} | |||||
| inline matrix(vec<4,T> v0, vec<4,T> v1, vec<4,T> v2, vec<4,T> v3) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ v0, v1, v2, v3 } {} | |||||
| #else | |||||
| : m_v0(v0), m_v1(v1), m_v2(v2), m_v3(v3) {} | |||||
| #endif | |||||
| explicit inline matrix(T const &val) | explicit inline matrix(T const &val) | ||||
| : v0(val, (T)0, (T)0, (T)0), | |||||
| v1((T)0, val, (T)0, (T)0), | |||||
| v2((T)0, (T)0, val, (T)0), | |||||
| v3((T)0, (T)0, (T)0, val) {} | |||||
| explicit inline matrix(matrix<2,2,T> mat) | |||||
| : v0(mat[0], (T)0, (T)0), | |||||
| v1(mat[1], (T)0, (T)0), | |||||
| v2((T)0, (T)0, (T)0, (T)0), | |||||
| v3((T)0, (T)0, (T)0, (T)0) {} | |||||
| explicit inline matrix(matrix<2,2,T> mat, T const &val1, T const &val2) | |||||
| : v0(mat[0], (T)0, (T)0), | |||||
| v1(mat[1], (T)0, (T)0), | |||||
| v2((T)0, (T)0, val1, (T)0), | |||||
| v3((T)0, (T)0, (T)0, val2) {} | |||||
| explicit inline matrix(matrix<3,3,T> mat) | |||||
| : v0(mat[0], (T)0), | |||||
| v1(mat[1], (T)0), | |||||
| v2(mat[2], (T)0), | |||||
| v3((T)0, (T)0, (T)0, (T)0) {} | |||||
| explicit inline matrix(matrix<3,3,T> mat, T const &val) | |||||
| : v0(mat[0], (T)0), | |||||
| v1(mat[1], (T)0), | |||||
| v2(mat[2], (T)0), | |||||
| v3((T)0, (T)0, (T)0, val) {} | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ vec<4,T>(val, (T)0, (T)0, (T)0), | |||||
| vec<4,T>((T)0, val, (T)0, (T)0), | |||||
| vec<4,T>((T)0, (T)0, val, (T)0), | |||||
| vec<4,T>((T)0, (T)0, (T)0, val) } {} | |||||
| #else | |||||
| : m_v0(val, (T)0, (T)0, (T)0), | |||||
| m_v1((T)0, val, (T)0, (T)0), | |||||
| m_v2((T)0, (T)0, val, (T)0), | |||||
| m_v3((T)0, (T)0, (T)0, val) {} | |||||
| #endif | |||||
| explicit inline matrix(matrix<2,2,T> m, T const &val = T(1)) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ vec<4,T>(m[0], (T)0, (T)0), | |||||
| vec<4,T>(m[1], (T)0, (T)0), | |||||
| vec<4,T>((T)0, (T)0, val, (T)0), | |||||
| vec<4,T>((T)0, (T)0, (T)0, val) } {} | |||||
| #else | |||||
| : m_v0(m[0], (T)0, (T)0), | |||||
| m_v1(m[1], (T)0, (T)0), | |||||
| m_v2((T)0, (T)0, val, (T)0), | |||||
| m_v3((T)0, (T)0, (T)0, val) {} | |||||
| #endif | |||||
| explicit inline matrix(matrix<3,3,T> m, T const &val = T(1)) | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| : m_data{ vec<4,T>(m[0], (T)0), | |||||
| vec<4,T>(m[1], (T)0), | |||||
| vec<4,T>(m[2], (T)0), | |||||
| vec<4,T>((T)0, (T)0, (T)0, val) } {} | |||||
| #else | |||||
| : m_v0(m[0], (T)0), | |||||
| m_v1(m[1], (T)0), | |||||
| m_v2(m[2], (T)0), | |||||
| m_v3((T)0, (T)0, (T)0, val) {} | |||||
| #endif | |||||
| explicit matrix(Quat<T> const &q); | explicit matrix(Quat<T> const &q); | ||||
| inline vec<4,T>& operator[](size_t n) { return (&v0)[n]; } | |||||
| inline vec<4,T> const& operator[](size_t n) const { return (&v0)[n]; } | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| inline vec<4,T>& operator[](size_t n) { return m_data[n]; } | |||||
| inline vec<4,T> const& operator[](size_t n) const { return m_data[n]; } | |||||
| #else | |||||
| inline vec<4,T>& operator[](size_t n) { return (&m_v0)[n]; } | |||||
| inline vec<4,T> const& operator[](size_t n) const { return (&m_v0)[n]; } | |||||
| #endif | |||||
| /* Helpers for transformation matrices */ | /* Helpers for transformation matrices */ | ||||
| static matrix<4,4,T> translate(T x, T y, T z); | static matrix<4,4,T> translate(T x, T y, T z); | ||||
| @@ -249,9 +315,9 @@ struct matrix<4, 4, T> | |||||
| return matrix<4,4,T>(matrix<3,3,T>::scale(v), (T)1); | return matrix<4,4,T>(matrix<3,3,T>::scale(v), (T)1); | ||||
| } | } | ||||
| static inline matrix<4,4,T> translate(matrix<4,4,T> const &mat, vec<3,T> v) | |||||
| static inline matrix<4,4,T> translate(matrix<4,4,T> const &m, vec<3,T> v) | |||||
| { | { | ||||
| return translate(v) * mat; | |||||
| return translate(v) * m; | |||||
| } | } | ||||
| static inline matrix<4,4,T> rotate(T degrees, T x, T y, T z) | static inline matrix<4,4,T> rotate(T degrees, T x, T y, T z) | ||||
| @@ -264,9 +330,9 @@ struct matrix<4, 4, T> | |||||
| return matrix<4,4,T>(matrix<3,3,T>::rotate(degrees, v), (T)1); | return matrix<4,4,T>(matrix<3,3,T>::rotate(degrees, v), (T)1); | ||||
| } | } | ||||
| static inline matrix<4,4,T> rotate(matrix<4,4,T> &mat, T degrees, vec<3,T> v) | |||||
| static inline matrix<4,4,T> rotate(matrix<4,4,T> &m, T degrees, vec<3,T> v) | |||||
| { | { | ||||
| return rotate(degrees, v) * mat; | |||||
| return rotate(degrees, v) * m; | |||||
| } | } | ||||
| static matrix<4,4,T> fromeuler_xyz(vec<3,T> const &v); | static matrix<4,4,T> fromeuler_xyz(vec<3,T> const &v); | ||||
| @@ -312,23 +378,34 @@ struct matrix<4, 4, T> | |||||
| friend std::ostream &operator<<(std::ostream &stream, | friend std::ostream &operator<<(std::ostream &stream, | ||||
| matrix<4,4,U> const &m); | matrix<4,4,U> const &m); | ||||
| vec<4,T> v0, v1, v2, v3; | |||||
| static const matrix<4,4,T> identity; | static const matrix<4,4,T> identity; | ||||
| private: | |||||
| #if LOL_FEATURE_CXX11_ARRAY_INITIALIZERS | |||||
| vec<4,T> m_data[4]; | |||||
| #else | |||||
| vec<4,T> m_v0, m_v1, m_v2, m_v3; | |||||
| #endif | |||||
| }; | }; | ||||
| template<typename T> T determinant(matrix<2,2,T> const &); | template<typename T> T determinant(matrix<2,2,T> const &); | ||||
| template<typename T> T determinant(matrix<3,3,T> const &); | template<typename T> T determinant(matrix<3,3,T> const &); | ||||
| template<typename T> T determinant(matrix<4,4,T> const &); | template<typename T> T determinant(matrix<4,4,T> const &); | ||||
| template<typename T> matrix<2,2,T> transpose(matrix<2,2,T> const &); | |||||
| template<typename T> matrix<3,3,T> transpose(matrix<3,3,T> const &); | |||||
| template<typename T> matrix<4,4,T> transpose(matrix<4,4,T> const &); | |||||
| template<typename T> matrix<2,2,T> inverse(matrix<2,2,T> const &); | template<typename T> matrix<2,2,T> inverse(matrix<2,2,T> const &); | ||||
| template<typename T> matrix<3,3,T> inverse(matrix<3,3,T> const &); | template<typename T> matrix<3,3,T> inverse(matrix<3,3,T> const &); | ||||
| template<typename T> matrix<4,4,T> inverse(matrix<4,4,T> const &); | template<typename T> matrix<4,4,T> inverse(matrix<4,4,T> const &); | ||||
| template<int COLS, int ROWS, typename T> | |||||
| static inline matrix<ROWS, COLS, T> transpose(matrix<COLS, ROWS, T> const &m) | |||||
| { | |||||
| matrix<ROWS, COLS, T> ret; | |||||
| for (int i = 0; i < COLS; ++i) | |||||
| for (int j = 0; j < ROWS; ++j) | |||||
| ret[j][i] = m[i][j]; | |||||
| return ret; | |||||
| } | |||||
| /* | /* | ||||
| * Addition/subtraction/unary | * Addition/subtraction/unary | ||||
| */ | */ | ||||
| @@ -383,7 +460,7 @@ static inline matrix<COLS, ROWS, T> operator -(matrix<COLS, ROWS, T> const &m) | |||||
| } | } | ||||
| /* | /* | ||||
| * Matrix-vector multiplication | |||||
| * Matrix-vector and vector-matrix multiplication | |||||
| */ | */ | ||||
| template<int COLS, int ROWS, int MASK, typename T> | template<int COLS, int ROWS, int MASK, typename T> | ||||
| @@ -396,6 +473,16 @@ static inline vec<ROWS, T> operator *(matrix<COLS, ROWS, T> const &m, | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<int COLS, int ROWS, int MASK, typename T> | |||||
| static inline vec<COLS, T> operator *(vec<ROWS, T, MASK> const &v, | |||||
| matrix<COLS, ROWS, T> const &m) | |||||
| { | |||||
| vec<COLS, T> ret(T(0)); | |||||
| for (int i = 0; i < COLS; ++i) | |||||
| ret[i] = dot(v, m[i]); | |||||
| return ret; | |||||
| } | |||||
| /* | /* | ||||
| * Matrix-matrix multiplication | * Matrix-matrix multiplication | ||||
| */ | */ | ||||
| @@ -48,15 +48,15 @@ namespace lol | |||||
| * fuck it. | * fuck it. | ||||
| */ | */ | ||||
| template<int N, typename T, int MASK> | |||||
| template<int N, typename T, int SWIZZLE> | |||||
| struct vec | struct vec | ||||
| { | { | ||||
| typedef vec<N,T> type; | typedef vec<N,T> type; | ||||
| inline vec<N, T, MASK>& operator =(vec<N, T> that); | |||||
| inline vec<N, T, SWIZZLE>& operator =(vec<N, T> that); | |||||
| #if LOL_FEATURE_CXX11_RELAXED_UNIONS | #if LOL_FEATURE_CXX11_RELAXED_UNIONS | ||||
| inline vec<N, T, MASK>& operator =(vec<N, T, MASK> const &that) | |||||
| inline vec<N, T, SWIZZLE>& operator =(vec<N, T, SWIZZLE> const &that) | |||||
| { | { | ||||
| /* Pass by value in case this == &that */ | /* Pass by value in case this == &that */ | ||||
| return *this = (vec<N,T>)that; | return *this = (vec<N,T>)that; | ||||
| @@ -65,18 +65,19 @@ struct vec | |||||
| inline T& operator[](size_t n) | inline T& operator[](size_t n) | ||||
| { | { | ||||
| int i = (MASK >> (4 * (N - 1 - n))) & 3; | |||||
| int i = (SWIZZLE >> (4 * (N - 1 - n))) & 3; | |||||
| return static_cast<T*>(static_cast<void*>(this))[i]; | return static_cast<T*>(static_cast<void*>(this))[i]; | ||||
| } | } | ||||
| inline T const& operator[](size_t n) const | inline T const& operator[](size_t n) const | ||||
| { | { | ||||
| int i = (MASK >> (4 * (N - 1 - n))) & 3; | |||||
| int i = (SWIZZLE >> (4 * (N - 1 - n))) & 3; | |||||
| return static_cast<T const*>(static_cast<void const *>(this))[i]; | return static_cast<T const*>(static_cast<void const *>(this))[i]; | ||||
| } | } | ||||
| }; | }; | ||||
| /* The generic "vec" type, which is a fixed-size vector */ | |||||
| /* The generic "vec" type, which is a fixed-size vector with no | |||||
| * swizzling. There's an override for N=2, N=3, N=4 that has swizzling. */ | |||||
| template<int N, typename T> | template<int N, typename T> | ||||
| struct vec<N, T, -1> | struct vec<N, T, -1> | ||||
| { | { | ||||
| @@ -218,10 +219,41 @@ private: | |||||
| * 2-element vectors | * 2-element vectors | ||||
| */ | */ | ||||
| template <typename T> struct base_vec2 | |||||
| template <typename T> | |||||
| struct vec<2,T> | |||||
| { | { | ||||
| explicit inline constexpr base_vec2() {} | |||||
| explicit inline constexpr base_vec2(T X, T Y) : x(X), y(Y) {} | |||||
| typedef vec<2,T> type; | |||||
| /* Default constructor, copy constructor, and destructor */ | |||||
| inline constexpr vec() : x(), y() {} | |||||
| inline constexpr vec(vec<2,T> const &v) : x(v.x), y(v.y) {} | |||||
| inline ~vec() { x.~T(); y.~T(); } | |||||
| /* Implicit constructor for swizzling */ | |||||
| template<int SWIZZLE> | |||||
| inline constexpr vec(vec<2, T, SWIZZLE> const &v) | |||||
| : x(v[0]), y(v[1]) {} | |||||
| /* Explicit constructor for type conversion */ | |||||
| template<typename U, int SWIZZLE> | |||||
| explicit inline constexpr vec(vec<2, U, SWIZZLE> const &v) | |||||
| : x(v[0]), y(v[1]) {} | |||||
| /* Various explicit constructors */ | |||||
| explicit inline constexpr vec(T X, T Y) | |||||
| : x(X), y(Y) {} | |||||
| explicit inline constexpr vec(T X) | |||||
| : x(X), y(X) {} | |||||
| LOL_COMMON_MEMBER_OPS(x) | |||||
| LOL_VECTOR_MEMBER_OPS() | |||||
| static const vec<2,T> zero; | |||||
| static const vec<2,T> axis_x; | |||||
| static const vec<2,T> axis_y; | |||||
| template<typename U> | |||||
| friend std::ostream &operator<<(std::ostream &stream, vec<2,U> const &v); | |||||
| union | union | ||||
| { | { | ||||
| @@ -264,59 +296,86 @@ template <typename T> struct base_vec2 | |||||
| }; | }; | ||||
| }; | }; | ||||
| template <> struct base_vec2<half> | |||||
| { | |||||
| explicit inline base_vec2() {} | |||||
| explicit inline base_vec2(half X, half Y) : x(X), y(Y) {} | |||||
| half x, y; | |||||
| }; | |||||
| template <> struct base_vec2<real> | |||||
| { | |||||
| explicit inline base_vec2() {} | |||||
| explicit inline base_vec2(real X, real Y) : x(X), y(Y) {} | |||||
| real x, y; | |||||
| }; | |||||
| /* | |||||
| * 3-element vectors | |||||
| */ | |||||
| template <typename T> | template <typename T> | ||||
| struct vec<2,T> : base_vec2<T> | |||||
| struct vec<3,T> | |||||
| { | { | ||||
| typedef vec<2,T> type; | |||||
| typedef vec<3,T> type; | |||||
| inline constexpr vec() {} | |||||
| inline constexpr vec(T X, T Y) : base_vec2<T>(X, Y) {} | |||||
| /* Default constructor, copy constructor, and destructor */ | |||||
| inline constexpr vec() : x(), y(), z() {} | |||||
| inline constexpr vec(vec<3,T> const &v) : x(v.x), y(v.y), z(v.z) {} | |||||
| inline ~vec() { x.~T(); y.~T(); z.~T(); } | |||||
| /* Implicit constructor for swizzling */ | |||||
| template<int SWIZZLE> | |||||
| inline constexpr vec(vec<3, T, SWIZZLE> const &v) | |||||
| : x(v[0]), y(v[1]), z(v[2]) {} | |||||
| /* Explicit constructor for type conversion */ | |||||
| template<typename U, int SWIZZLE> | |||||
| explicit inline constexpr vec(vec<3, U, SWIZZLE> const &v) | |||||
| : x(v[0]), y(v[1]), z(v[2]) {} | |||||
| /* Various explicit constructors */ | |||||
| explicit inline constexpr vec(T X) | |||||
| : x(X), y(X), z(X) {} | |||||
| explicit inline constexpr vec(T X, T Y, T Z) | |||||
| : x(X), y(Y), z(Z) {} | |||||
| explicit inline constexpr vec(vec<2,T> XY, T Z) | |||||
| : x(XY.x), y(XY.y), z(Z) {} | |||||
| explicit inline constexpr vec(T X, vec<2,T> YZ) | |||||
| : x(X), y(YZ.x), z(YZ.y) {} | |||||
| explicit inline constexpr vec(T X) : base_vec2<T>(X, X) {} | |||||
| LOL_COMMON_MEMBER_OPS(x) | |||||
| LOL_VECTOR_MEMBER_OPS() | |||||
| template<int MASK> | |||||
| inline constexpr vec(vec<2, T, MASK> const &v) | |||||
| : base_vec2<T>(v[0], v[1]) {} | |||||
| static vec<3,T> toeuler_xyx(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_xzx(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yxy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yzy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zxz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zyz(Quat<T> const &q); | |||||
| template<typename U, int MASK> | |||||
| explicit inline constexpr vec(vec<2, U, MASK> const &v) | |||||
| : base_vec2<T>(v[0], v[1]) {} | |||||
| static vec<3,T> toeuler_xyz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_xzy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yxz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yzx(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zxy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zyx(Quat<T> const &q); | |||||
| LOL_COMMON_MEMBER_OPS(x) | |||||
| LOL_VECTOR_MEMBER_OPS() | |||||
| /* Return the cross product (vector product) of "a" and "b" */ \ | |||||
| friend inline type cross(type const &a, type const &b) | |||||
| { | |||||
| return type(a.y * b.z - a.z * b.y, | |||||
| a.z * b.x - a.x * b.z, | |||||
| a.x * b.y - a.y * b.x); | |||||
| } | |||||
| static const vec<2,T> zero; | |||||
| static const vec<2,T> axis_x; | |||||
| static const vec<2,T> axis_y; | |||||
| /* Return a vector that is orthogonal to "a" */ | |||||
| friend inline type orthogonal(type const &a) | |||||
| { | |||||
| return lol::abs(a.x) > lol::abs(a.z) | |||||
| ? type(-a.y, a.x, (T)0) | |||||
| : type((T)0, -a.z, a.y); | |||||
| } | |||||
| template<typename U> | |||||
| friend std::ostream &operator<<(std::ostream &stream, vec<2,U> const &v); | |||||
| }; | |||||
| /* Return a vector that is orthonormal to "a" */ | |||||
| friend inline type orthonormal(type const &a) | |||||
| { | |||||
| return normalize(orthogonal(a)); | |||||
| } | |||||
| /* | |||||
| * 3-element vectors | |||||
| */ | |||||
| static const vec<3,T> zero; | |||||
| static const vec<3,T> axis_x; | |||||
| static const vec<3,T> axis_y; | |||||
| static const vec<3,T> axis_z; | |||||
| template <typename T> struct base_vec3 | |||||
| { | |||||
| explicit inline constexpr base_vec3() {} | |||||
| explicit inline constexpr base_vec3(T X, T Y, T Z) : x(X), y(Y), z(Z) {} | |||||
| template<typename U> | |||||
| friend std::ostream &operator<<(std::ostream &stream, vec<3,U> const &v); | |||||
| union | union | ||||
| { | { | ||||
| @@ -448,100 +507,59 @@ template <typename T> struct base_vec3 | |||||
| }; | }; | ||||
| }; | }; | ||||
| template <> struct base_vec3<half> | |||||
| { | |||||
| explicit inline base_vec3() {} | |||||
| explicit inline base_vec3(half X, half Y, half Z) | |||||
| : x(X), y(Y), z(Z) {} | |||||
| half x, y, z; | |||||
| }; | |||||
| template <> struct base_vec3<real> | |||||
| { | |||||
| explicit inline base_vec3() {} | |||||
| explicit inline base_vec3(real X, real Y, real Z) : x(X), y(Y), z(Z) {} | |||||
| real x, y, z; | |||||
| }; | |||||
| /* | |||||
| * 4-element vectors | |||||
| */ | |||||
| template <typename T> | template <typename T> | ||||
| struct vec<3,T> : base_vec3<T> | |||||
| struct vec<4,T> | |||||
| { | { | ||||
| typedef vec<3,T> type; | |||||
| inline constexpr vec() {} | |||||
| inline constexpr vec(T X, T Y, T Z) : base_vec3<T>(X, Y, Z) {} | |||||
| inline constexpr vec(vec<2,T> XY, T Z) : base_vec3<T>(XY.x, XY.y, Z) {} | |||||
| inline constexpr vec(T X, vec<2,T> YZ) : base_vec3<T>(X, YZ.x, YZ.y) {} | |||||
| explicit inline constexpr vec(T X) : base_vec3<T>(X, X, X) {} | |||||
| template<int MASK> | |||||
| inline constexpr vec(vec<3, T, MASK> const &v) | |||||
| : base_vec3<T>(v[0], v[1], v[2]) {} | |||||
| typedef vec<4,T> type; | |||||
| template<typename U, int MASK> | |||||
| explicit inline constexpr vec(vec<3, U, MASK> const &v) | |||||
| : base_vec3<T>(v[0], v[1], v[2]) {} | |||||
| /* Default constructor, copy constructor, and destructor */ | |||||
| inline constexpr vec() : x(), y(), z(), w() {} | |||||
| inline constexpr vec(vec<4,T> const &v) : x(v.x), y(v.y), z(v.z), w(v.w) {} | |||||
| inline ~vec() { x.~T(); y.~T(); z.~T(); w.~T(); } | |||||
| /* Implicit constructor for swizzling */ | |||||
| template<int SWIZZLE> | |||||
| inline constexpr vec(vec<4, T, SWIZZLE> const &v) | |||||
| : x(v[0]), y(v[1]), z(v[2]), w(v[3]) {} | |||||
| /* Explicit constructor for type conversion */ | |||||
| template<typename U, int SWIZZLE> | |||||
| explicit inline constexpr vec(vec<4, U, SWIZZLE> const &v) | |||||
| : x(v[0]), y(v[1]), z(v[2]), w(v[3]) {} | |||||
| /* Various explicit constructors */ | |||||
| explicit inline constexpr vec(T X) | |||||
| : x(X), y(X), z(X), w(X) {} | |||||
| explicit inline constexpr vec(T X, T Y, T Z, T W) | |||||
| : x(X), y(Y), z(Z), w(W) {} | |||||
| explicit inline constexpr vec(vec<2,T> XY, T Z, T W) | |||||
| : x(XY.x), y(XY.y), z(Z), w(W) {} | |||||
| explicit inline constexpr vec(T X, vec<2,T> YZ, T W) | |||||
| : x(X), y(YZ.x), z(YZ.y), w(W) {} | |||||
| explicit inline constexpr vec(T X, T Y, vec<2,T> ZW) | |||||
| : x(X), y(Y), z(ZW.x), w(ZW.y) {} | |||||
| explicit inline constexpr vec(vec<2,T> XY, vec<2,T> ZW) | |||||
| : x(XY.x), y(XY.y), z(ZW.x), w(ZW.y) {} | |||||
| explicit inline constexpr vec(vec<3,T> XYZ, T W) | |||||
| : x(XYZ.x), y(XYZ.y), z(XYZ.z), w(W) {} | |||||
| explicit inline constexpr vec(T X, vec<3,T> YZW) | |||||
| : x(X), y(YZW.x), z(YZW.y), w(YZW.z) {} | |||||
| LOL_COMMON_MEMBER_OPS(x) | LOL_COMMON_MEMBER_OPS(x) | ||||
| LOL_VECTOR_MEMBER_OPS() | LOL_VECTOR_MEMBER_OPS() | ||||
| static vec<3,T> toeuler_xyx(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_xzx(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yxy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yzy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zxz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zyz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_xyz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_xzy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yxz(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_yzx(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zxy(Quat<T> const &q); | |||||
| static vec<3,T> toeuler_zyx(Quat<T> const &q); | |||||
| /* Return the cross product (vector product) of "a" and "b" */ \ | |||||
| friend inline type cross(type const &a, type const &b) | |||||
| { | |||||
| return type(a.y * b.z - a.z * b.y, | |||||
| a.z * b.x - a.x * b.z, | |||||
| a.x * b.y - a.y * b.x); | |||||
| } | |||||
| /* Return a vector that is orthogonal to "a" */ | |||||
| friend inline type orthogonal(type const &a) | |||||
| { | |||||
| return lol::abs(a.x) > lol::abs(a.z) | |||||
| ? type(-a.y, a.x, (T)0) | |||||
| : type((T)0, -a.z, a.y); | |||||
| } | |||||
| /* Return a vector that is orthonormal to "a" */ | |||||
| friend inline type orthonormal(type const &a) | |||||
| { | |||||
| return normalize(orthogonal(a)); | |||||
| } | |||||
| static const vec<3,T> zero; | |||||
| static const vec<3,T> axis_x; | |||||
| static const vec<3,T> axis_y; | |||||
| static const vec<3,T> axis_z; | |||||
| static const vec<4,T> zero; | |||||
| static const vec<4,T> axis_x; | |||||
| static const vec<4,T> axis_y; | |||||
| static const vec<4,T> axis_z; | |||||
| static const vec<4,T> axis_w; | |||||
| template<typename U> | template<typename U> | ||||
| friend std::ostream &operator<<(std::ostream &stream, vec<3,U> const &v); | |||||
| }; | |||||
| /* | |||||
| * 4-element vectors | |||||
| */ | |||||
| template <typename T> struct base_vec4 | |||||
| { | |||||
| explicit inline constexpr base_vec4() {} | |||||
| explicit inline constexpr base_vec4(T X, T Y, T Z, T W) | |||||
| : x(X), y(Y), z(Z), w(W) {} | |||||
| friend std::ostream &operator<<(std::ostream &stream, vec<4,U> const &v); | |||||
| union | union | ||||
| { | { | ||||
| @@ -892,77 +910,15 @@ template <typename T> struct base_vec4 | |||||
| }; | }; | ||||
| }; | }; | ||||
| template <> struct base_vec4<half> | |||||
| { | |||||
| explicit inline base_vec4() {} | |||||
| explicit inline base_vec4(half X, half Y, half Z, half W) | |||||
| : x(X), y(Y), z(Z), w(W) {} | |||||
| half x, y, z, w; | |||||
| }; | |||||
| template <> struct base_vec4<real> | |||||
| { | |||||
| explicit inline base_vec4() {} | |||||
| explicit inline base_vec4(real X, real Y, real Z, real W) | |||||
| : x(X), y(Y), z(Z), w(W) {} | |||||
| real x, y, z, w; | |||||
| }; | |||||
| template <typename T> | |||||
| struct vec<4,T> : base_vec4<T> | |||||
| { | |||||
| typedef vec<4,T> type; | |||||
| inline constexpr vec() {} | |||||
| inline constexpr vec(T X, T Y, T Z, T W) | |||||
| : base_vec4<T>(X, Y, Z, W) {} | |||||
| inline constexpr vec(vec<2,T> XY, T Z, T W) | |||||
| : base_vec4<T>(XY.x, XY.y, Z, W) {} | |||||
| inline constexpr vec(T X, vec<2,T> YZ, T W) | |||||
| : base_vec4<T>(X, YZ.x, YZ.y, W) {} | |||||
| inline constexpr vec(T X, T Y, vec<2,T> ZW) | |||||
| : base_vec4<T>(X, Y, ZW.x, ZW.y) {} | |||||
| inline constexpr vec(vec<2,T> XY, vec<2,T> ZW) | |||||
| : base_vec4<T>(XY.x, XY.y, ZW.x, ZW.y) {} | |||||
| inline constexpr vec(vec<3,T> XYZ, T W) | |||||
| : base_vec4<T>(XYZ.x, XYZ.y, XYZ.z, W) {} | |||||
| inline constexpr vec(T X, vec<3,T> YZW) | |||||
| : base_vec4<T>(X, YZW.x, YZW.y, YZW.z) {} | |||||
| explicit inline constexpr vec(T X) : base_vec4<T>(X, X, X, X) {} | |||||
| template<int MASK> | |||||
| inline constexpr vec(vec<4, T, MASK> const &v) | |||||
| : base_vec4<T>(v[0], v[1], v[2], v[3]) {} | |||||
| template<typename U, int MASK> | |||||
| explicit inline constexpr vec(vec<4, U, MASK> const &v) | |||||
| : base_vec4<T>(v[0], v[1], v[2], v[3]) {} | |||||
| LOL_COMMON_MEMBER_OPS(x) | |||||
| LOL_VECTOR_MEMBER_OPS() | |||||
| static const vec<4,T> zero; | |||||
| static const vec<4,T> axis_x; | |||||
| static const vec<4,T> axis_y; | |||||
| static const vec<4,T> axis_z; | |||||
| static const vec<4,T> axis_w; | |||||
| template<typename U> | |||||
| friend std::ostream &operator<<(std::ostream &stream, vec<4,U> const &v); | |||||
| }; | |||||
| /* | /* | ||||
| * Operators for swizzled vectors. Since template deduction cannot be | * Operators for swizzled vectors. Since template deduction cannot be | ||||
| * done for two arbitrary vec<> values, we help the compiler understand | * done for two arbitrary vec<> values, we help the compiler understand | ||||
| * the expected type. | * the expected type. | ||||
| */ | */ | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline bool operator ==(vec<N,T,MASK1> const &a, | |||||
| vec<N,T,MASK2> const &b) | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline bool operator ==(vec<N,T,SWIZZLE1> const &a, | |||||
| vec<N,T,SWIZZLE2> const &b) | |||||
| { | { | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| if (!(a[i] == b[i])) | if (!(a[i] == b[i])) | ||||
| @@ -970,9 +926,9 @@ static inline bool operator ==(vec<N,T,MASK1> const &a, | |||||
| return true; | return true; | ||||
| } | } | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline bool operator !=(vec<N,T,MASK1> const &a, | |||||
| vec<N,T,MASK2> const &b) | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline bool operator !=(vec<N,T,SWIZZLE1> const &a, | |||||
| vec<N,T,SWIZZLE2> const &b) | |||||
| { | { | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| if (a[i] != b[i]) | if (a[i] != b[i]) | ||||
| @@ -981,15 +937,15 @@ static inline bool operator !=(vec<N,T,MASK1> const &a, | |||||
| } | } | ||||
| #define LOL_SWIZZLE_V_VV_OP(op) \ | #define LOL_SWIZZLE_V_VV_OP(op) \ | ||||
| template<int N, int MASK1, int MASK2, typename T> \ | |||||
| inline vec<N,T> operator op(vec<N,T,MASK1> const &a, \ | |||||
| vec<N,T,MASK2> const &b) \ | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> \ | |||||
| inline vec<N,T> operator op(vec<N,T,SWIZZLE1> const &a, \ | |||||
| vec<N,T,SWIZZLE2> const &b) \ | |||||
| { \ | { \ | ||||
| return vec<N,T>(a) op vec<N,T>(b); \ | return vec<N,T>(a) op vec<N,T>(b); \ | ||||
| } \ | } \ | ||||
| \ | \ | ||||
| template<int N, int MASK, typename T> \ | |||||
| inline vec<N,T> operator op(vec<N,T,MASK> a, T const &b) \ | |||||
| template<int N, int SWIZZLE, typename T> \ | |||||
| inline vec<N,T> operator op(vec<N,T,SWIZZLE> a, T const &b) \ | |||||
| { \ | { \ | ||||
| return vec<N,T>(a) op b; \ | return vec<N,T>(a) op b; \ | ||||
| } | } | ||||
| @@ -1001,8 +957,8 @@ LOL_SWIZZLE_V_VV_OP(/) | |||||
| #undef LOL_SWIZZLE_V_VV_OP | #undef LOL_SWIZZLE_V_VV_OP | ||||
| template<int N, int MASK, typename T> | |||||
| static inline vec<N,T> operator *(T const &val, vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline vec<N,T> operator *(T const &val, vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| vec<N,T> ret; | vec<N,T> ret; | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| @@ -1016,8 +972,9 @@ static inline vec<N,T> operator *(T const &val, vec<N,T,MASK> const &a) | |||||
| */ | */ | ||||
| #define LOL_SWIZZLE_V_VV_FUN(fun) \ | #define LOL_SWIZZLE_V_VV_FUN(fun) \ | ||||
| template<int N, int MASK1, int MASK2, typename T> \ | |||||
| inline vec<N,T> fun(vec<N,T,MASK1> const &a, vec<N,T,MASK2> const &b) \ | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> \ | |||||
| inline vec<N,T> fun(vec<N,T,SWIZZLE1> const &a, \ | |||||
| vec<N,T,SWIZZLE2> const &b) \ | |||||
| { \ | { \ | ||||
| using lol::fun; \ | using lol::fun; \ | ||||
| vec<N,T> ret; \ | vec<N,T> ret; \ | ||||
| @@ -1026,8 +983,8 @@ static inline vec<N,T> operator *(T const &val, vec<N,T,MASK> const &a) | |||||
| return ret; \ | return ret; \ | ||||
| } \ | } \ | ||||
| \ | \ | ||||
| template<int N, int MASK, typename T> \ | |||||
| inline vec<N,T> fun(vec<N,T,MASK> const &a, T const &b) \ | |||||
| template<int N, int SWIZZLE, typename T> \ | |||||
| inline vec<N,T> fun(vec<N,T,SWIZZLE> const &a, T const &b) \ | |||||
| { \ | { \ | ||||
| using lol::fun; \ | using lol::fun; \ | ||||
| vec<N,T> ret; \ | vec<N,T> ret; \ | ||||
| @@ -1036,8 +993,8 @@ static inline vec<N,T> operator *(T const &val, vec<N,T,MASK> const &a) | |||||
| return ret; \ | return ret; \ | ||||
| } \ | } \ | ||||
| \ | \ | ||||
| template<int N, int MASK, typename T> \ | |||||
| inline vec<N,T> fun(T const &a, vec<N,T,MASK> const &b) \ | |||||
| template<int N, int SWIZZLE, typename T> \ | |||||
| inline vec<N,T> fun(T const &a, vec<N,T,SWIZZLE> const &b) \ | |||||
| { \ | { \ | ||||
| using lol::fun; \ | using lol::fun; \ | ||||
| vec<N,T> ret; \ | vec<N,T> ret; \ | ||||
| @@ -1059,32 +1016,32 @@ LOL_SWIZZLE_V_VV_FUN(fmod) | |||||
| * vec clamp(vec, scalar, scalar) | * vec clamp(vec, scalar, scalar) | ||||
| */ | */ | ||||
| template<int N, int MASK1, int MASK2, int MASK3, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,MASK1> const &x, | |||||
| vec<N,T,MASK2> const &a, | |||||
| vec<N,T,MASK3> const &b) | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, int SWIZZLE3, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,SWIZZLE1> const &x, | |||||
| vec<N,T,SWIZZLE2> const &a, | |||||
| vec<N,T,SWIZZLE3> const &b) | |||||
| { | { | ||||
| return max(min(x, b), a); | return max(min(x, b), a); | ||||
| } | } | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,MASK1> const &x, | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,SWIZZLE1> const &x, | |||||
| T const &a, | T const &a, | ||||
| vec<N,T,MASK2> const &b) | |||||
| vec<N,T,SWIZZLE2> const &b) | |||||
| { | { | ||||
| return max(min(x, b), a); | return max(min(x, b), a); | ||||
| } | } | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,MASK1> const &x, | |||||
| vec<N,T,MASK2> const &a, | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,SWIZZLE1> const &x, | |||||
| vec<N,T,SWIZZLE2> const &a, | |||||
| T const &b) | T const &b) | ||||
| { | { | ||||
| return max(min(x, b), a); | return max(min(x, b), a); | ||||
| } | } | ||||
| template<int N, int MASK1, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,MASK1> const &x, | |||||
| template<int N, int SWIZZLE1, typename T> | |||||
| static inline vec<N,T> clamp(vec<N,T,SWIZZLE1> const &x, | |||||
| T const &a, | T const &a, | ||||
| T const &b) | T const &b) | ||||
| { | { | ||||
| @@ -1096,17 +1053,17 @@ static inline vec<N,T> clamp(vec<N,T,MASK1> const &x, | |||||
| * vec mix(vec, vec, scalar) | * vec mix(vec, vec, scalar) | ||||
| */ | */ | ||||
| template<int N, int MASK1, int MASK2, int MASK3, typename T> | |||||
| static inline vec<N,T> mix(vec<N,T,MASK1> const &x, | |||||
| vec<N,T,MASK2> const &y, | |||||
| vec<N,T,MASK3> const &a) | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, int SWIZZLE3, typename T> | |||||
| static inline vec<N,T> mix(vec<N,T,SWIZZLE1> const &x, | |||||
| vec<N,T,SWIZZLE2> const &y, | |||||
| vec<N,T,SWIZZLE3> const &a) | |||||
| { | { | ||||
| return x + a * (y - x); | return x + a * (y - x); | ||||
| } | } | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline vec<N,T> mix(vec<N,T,MASK1> const &x, | |||||
| vec<N,T,MASK2> const &y, | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline vec<N,T> mix(vec<N,T,SWIZZLE1> const &x, | |||||
| vec<N,T,SWIZZLE2> const &y, | |||||
| T const &a) | T const &a) | ||||
| { | { | ||||
| return x + a * (y - x); | return x + a * (y - x); | ||||
| @@ -1116,8 +1073,8 @@ static inline vec<N,T> mix(vec<N,T,MASK1> const &x, | |||||
| * Some GLSL-like functions. | * Some GLSL-like functions. | ||||
| */ | */ | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline T dot(vec<N,T,MASK1> const &a, vec<N,T,MASK2> const &b) | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline T dot(vec<N,T,SWIZZLE1> const &a, vec<N,T,SWIZZLE2> const &b) | |||||
| { | { | ||||
| T ret(0); | T ret(0); | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| @@ -1125,22 +1082,22 @@ static inline T dot(vec<N,T,MASK1> const &a, vec<N,T,MASK2> const &b) | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline T sqlength(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline T sqlength(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| return dot(a, a); | return dot(a, a); | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline T length(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline T length(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| /* FIXME: this is not very nice */ | /* FIXME: this is not very nice */ | ||||
| return (T)sqrt((double)sqlength(a)); | return (T)sqrt((double)sqlength(a)); | ||||
| } | } | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline vec<N,T> lerp(vec<N,T,MASK1> const &a, | |||||
| vec<N,T,MASK2> const &b, | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline vec<N,T> lerp(vec<N,T,SWIZZLE1> const &a, | |||||
| vec<N,T,SWIZZLE2> const &b, | |||||
| T const &s) | T const &s) | ||||
| { | { | ||||
| vec<N,T> ret; | vec<N,T> ret; | ||||
| @@ -1149,14 +1106,14 @@ static inline vec<N,T> lerp(vec<N,T,MASK1> const &a, | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<int N, int MASK1, int MASK2, typename T> | |||||
| static inline T distance(vec<N,T,MASK1> const &a, vec<N,T,MASK2> const &b) | |||||
| template<int N, int SWIZZLE1, int SWIZZLE2, typename T> | |||||
| static inline T distance(vec<N,T,SWIZZLE1> const &a, vec<N,T,SWIZZLE2> const &b) | |||||
| { | { | ||||
| return length(a - b); | return length(a - b); | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline vec<N,T> fract(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline vec<N,T> fract(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| vec<N,T> ret; | vec<N,T> ret; | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| @@ -1164,15 +1121,15 @@ static inline vec<N,T> fract(vec<N,T,MASK> const &a) | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline vec<N,T> normalize(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline vec<N,T> normalize(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| T norm = (T)length(a); | T norm = (T)length(a); | ||||
| return norm ? a / norm : vec<N,T>(T(0)); | return norm ? a / norm : vec<N,T>(T(0)); | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline vec<N,T> abs(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline vec<N,T> abs(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| vec<N,T> ret; | vec<N,T> ret; | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| @@ -1180,8 +1137,8 @@ static inline vec<N,T> abs(vec<N,T,MASK> const &a) | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline vec<N,T> degrees(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline vec<N,T> degrees(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| vec<N,T> ret; | vec<N,T> ret; | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| @@ -1189,8 +1146,8 @@ static inline vec<N,T> degrees(vec<N,T,MASK> const &a) | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<int N, int MASK, typename T> | |||||
| static inline vec<N,T> radians(vec<N,T,MASK> const &a) | |||||
| template<int N, int SWIZZLE, typename T> | |||||
| static inline vec<N,T> radians(vec<N,T,SWIZZLE> const &a) | |||||
| { | { | ||||
| vec<N,T> ret; | vec<N,T> ret; | ||||
| for (size_t i = 0; i < N; ++i) | for (size_t i = 0; i < N; ++i) | ||||
| @@ -1203,8 +1160,8 @@ static inline vec<N,T> radians(vec<N,T,MASK> const &a) | |||||
| */ | */ | ||||
| #if LOL_FEATURE_CXX11_RELAXED_UNIONS | #if LOL_FEATURE_CXX11_RELAXED_UNIONS | ||||
| template<int N, typename T, int MASK> | |||||
| inline vec<N, T, MASK>& vec<N, T, MASK>::operator =(vec<N,T> that) | |||||
| template<int N, typename T, int SWIZZLE> | |||||
| inline vec<N, T, SWIZZLE>& vec<N, T, SWIZZLE>::operator =(vec<N,T> that) | |||||
| { | { | ||||
| for (int i = 0; i < N; ++i) | for (int i = 0; i < N; ++i) | ||||
| (*this)[i] = that[i]; | (*this)[i] = that[i]; | ||||
| @@ -46,125 +46,98 @@ static inline float det3(float a, float b, float c, | |||||
| /* | /* | ||||
| * Return the cofactor of the (i,j) entry in a 2×2 matrix. | * Return the cofactor of the (i,j) entry in a 2×2 matrix. | ||||
| */ | */ | ||||
| static inline float cofact(mat2 const &mat, int i, int j) | |||||
| static inline float cofact(mat2 const &m, int i, int j) | |||||
| { | { | ||||
| float tmp = mat[(i + 1) & 1][(j + 1) & 1]; | |||||
| float tmp = m[(i + 1) & 1][(j + 1) & 1]; | |||||
| return ((i + j) & 1) ? -tmp : tmp; | return ((i + j) & 1) ? -tmp : tmp; | ||||
| } | } | ||||
| /* | /* | ||||
| * Return the cofactor of the (i,j) entry in a 3×3 matrix. | * Return the cofactor of the (i,j) entry in a 3×3 matrix. | ||||
| */ | */ | ||||
| static inline float cofact(mat3 const &mat, int i, int j) | |||||
| static inline float cofact(mat3 const &m, 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]); | |||||
| return det2(m[(i + 1) % 3][(j + 1) % 3], | |||||
| m[(i + 2) % 3][(j + 1) % 3], | |||||
| m[(i + 1) % 3][(j + 2) % 3], | |||||
| m[(i + 2) % 3][(j + 2) % 3]); | |||||
| } | } | ||||
| /* | /* | ||||
| * Return the cofactor of the (i,j) entry in a 4×4 matrix. | * Return the cofactor of the (i,j) entry in a 4×4 matrix. | ||||
| */ | */ | ||||
| static inline float cofact(mat4 const &mat, int i, int j) | |||||
| static inline float cofact(mat4 const &m, int i, int j) | |||||
| { | { | ||||
| return det3(mat[(i + 1) & 3][(j + 1) & 3], | |||||
| mat[(i + 2) & 3][(j + 1) & 3], | |||||
| mat[(i + 3) & 3][(j + 1) & 3], | |||||
| mat[(i + 1) & 3][(j + 2) & 3], | |||||
| mat[(i + 2) & 3][(j + 2) & 3], | |||||
| mat[(i + 3) & 3][(j + 2) & 3], | |||||
| mat[(i + 1) & 3][(j + 3) & 3], | |||||
| mat[(i + 2) & 3][(j + 3) & 3], | |||||
| mat[(i + 3) & 3][(j + 3) & 3]) * (((i + j) & 1) ? -1.0f : 1.0f); | |||||
| return det3(m[(i + 1) & 3][(j + 1) & 3], | |||||
| m[(i + 2) & 3][(j + 1) & 3], | |||||
| m[(i + 3) & 3][(j + 1) & 3], | |||||
| m[(i + 1) & 3][(j + 2) & 3], | |||||
| m[(i + 2) & 3][(j + 2) & 3], | |||||
| m[(i + 3) & 3][(j + 2) & 3], | |||||
| m[(i + 1) & 3][(j + 3) & 3], | |||||
| m[(i + 2) & 3][(j + 3) & 3], | |||||
| m[(i + 3) & 3][(j + 3) & 3]) * (((i + j) & 1) ? -1.0f : 1.0f); | |||||
| } | } | ||||
| template<> float determinant(mat2 const &mat) | |||||
| template<> float determinant(mat2 const &m) | |||||
| { | { | ||||
| return det2(mat[0][0], mat[0][1], | |||||
| mat[1][0], mat[1][1]); | |||||
| return det2(m[0][0], m[0][1], | |||||
| m[1][0], m[1][1]); | |||||
| } | } | ||||
| template<> mat2 transpose(mat2 const &mat) | |||||
| template<> mat2 inverse(mat2 const &m) | |||||
| { | { | ||||
| mat2 ret; | 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); | |||||
| float d = determinant(m); | |||||
| if (d) | if (d) | ||||
| { | { | ||||
| d = 1.0f / d; | d = 1.0f / d; | ||||
| for (int j = 0; j < 2; j++) | for (int j = 0; j < 2; j++) | ||||
| for (int i = 0; i < 2; i++) | for (int i = 0; i < 2; i++) | ||||
| ret[j][i] = cofact(mat, i, j) * d; | |||||
| ret[j][i] = cofact(m, i, j) * d; | |||||
| } | } | ||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<> float determinant(mat3 const &mat) | |||||
| template<> float determinant(mat3 const &m) | |||||
| { | { | ||||
| 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]); | |||||
| return det3(m[0][0], m[0][1], m[0][2], | |||||
| m[1][0], m[1][1], m[1][2], | |||||
| m[2][0], m[2][1], m[2][2]); | |||||
| } | } | ||||
| template<> mat3 transpose(mat3 const &mat) | |||||
| template<> mat3 inverse(mat3 const &m) | |||||
| { | { | ||||
| mat3 ret; | 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); | |||||
| float d = determinant(m); | |||||
| if (d) | if (d) | ||||
| { | { | ||||
| d = 1.0f / d; | d = 1.0f / d; | ||||
| for (int j = 0; j < 3; j++) | for (int j = 0; j < 3; j++) | ||||
| for (int i = 0; i < 3; i++) | for (int i = 0; i < 3; i++) | ||||
| ret[j][i] = cofact(mat, i, j) * d; | |||||
| ret[j][i] = cofact(m, i, j) * d; | |||||
| } | } | ||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<> float determinant(mat4 const &mat) | |||||
| template<> float determinant(mat4 const &m) | |||||
| { | { | ||||
| float ret = 0; | float ret = 0; | ||||
| for (int n = 0; n < 4; n++) | for (int n = 0; n < 4; n++) | ||||
| ret += mat[n][0] * cofact(mat, n, 0); | |||||
| return ret; | |||||
| } | |||||
| template<> mat4 transpose(mat4 const &mat) | |||||
| { | |||||
| mat4 ret; | |||||
| for (int j = 0; j < 4; j++) | |||||
| for (int i = 0; i < 4; i++) | |||||
| ret[j][i] = mat[i][j]; | |||||
| ret += m[n][0] * cofact(m, n, 0); | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| template<> mat4 inverse(mat4 const &mat) | |||||
| template<> mat4 inverse(mat4 const &m) | |||||
| { | { | ||||
| mat4 ret; | mat4 ret; | ||||
| float d = determinant(mat); | |||||
| float d = determinant(m); | |||||
| 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] = cofact(mat, i, j) * d; | |||||
| ret[j][i] = cofact(m, i, j) * d; | |||||
| } | } | ||||
| return ret; | return ret; | ||||
| } | } | ||||
| @@ -419,17 +392,17 @@ template<> mat3::matrix(quat const &q) | |||||
| float s = 2.0f / n; | float s = 2.0f / n; | ||||
| v0[0] = 1.0f - s * (q.y * q.y + q.z * q.z); | |||||
| v0[1] = s * (q.x * q.y + q.z * q.w); | |||||
| v0[2] = s * (q.x * q.z - q.y * q.w); | |||||
| (*this)[0][0] = 1.0f - s * (q.y * q.y + q.z * q.z); | |||||
| (*this)[0][1] = s * (q.x * q.y + q.z * q.w); | |||||
| (*this)[0][2] = s * (q.x * q.z - q.y * q.w); | |||||
| v1[0] = s * (q.x * q.y - q.z * q.w); | |||||
| v1[1] = 1.0f - s * (q.z * q.z + q.x * q.x); | |||||
| v1[2] = s * (q.y * q.z + q.x * q.w); | |||||
| (*this)[1][0] = s * (q.x * q.y - q.z * q.w); | |||||
| (*this)[1][1] = 1.0f - s * (q.z * q.z + q.x * q.x); | |||||
| (*this)[1][2] = s * (q.y * q.z + q.x * q.w); | |||||
| v2[0] = s * (q.x * q.z + q.y * q.w); | |||||
| v2[1] = s * (q.y * q.z - q.x * q.w); | |||||
| v2[2] = 1.0f - s * (q.x * q.x + q.y * q.y); | |||||
| (*this)[2][0] = s * (q.x * q.z + q.y * q.w); | |||||
| (*this)[2][1] = s * (q.y * q.z - q.x * q.w); | |||||
| (*this)[2][2] = 1.0f - s * (q.x * q.x + q.y * q.y); | |||||
| } | } | ||||
| template<> mat4::matrix(quat const &q) | template<> mat4::matrix(quat const &q) | ||||
| @@ -285,8 +285,8 @@ void BtPhysTest::InitApp() | |||||
| { | { | ||||
| EasyConstraint* new_constraint = new EasyConstraint(); | EasyConstraint* new_constraint = new EasyConstraint(); | ||||
| vec3 A2B = .5f * (RopeElements[i]->GetPhysic()->GetTransform().v3.xyz - | |||||
| RopeElements[i - 1]->GetPhysic()->GetTransform().v3.xyz); | |||||
| vec3 A2B = .5f * (RopeElements[i]->GetPhysic()->GetTransform()[3].xyz - | |||||
| RopeElements[i - 1]->GetPhysic()->GetTransform()[3].xyz); | |||||
| new_constraint->SetPhysObjA(RopeElements[i - 1]->GetPhysic(), lol::mat4::translate(A2B)); | new_constraint->SetPhysObjA(RopeElements[i - 1]->GetPhysic(), lol::mat4::translate(A2B)); | ||||
| new_constraint->SetPhysObjB(RopeElements[i]->GetPhysic(), lol::mat4::translate(-A2B)); | new_constraint->SetPhysObjB(RopeElements[i]->GetPhysic(), lol::mat4::translate(-A2B)); | ||||
| new_constraint->InitConstraintToPoint2Point(); | new_constraint->InitConstraintToPoint2Point(); | ||||
| @@ -349,7 +349,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| PhysicsObject* PhysObj = m_physobj_list[i].m1; | PhysicsObject* PhysObj = m_physobj_list[i].m1; | ||||
| float &Timer = m_physobj_list[i].m2; | float &Timer = m_physobj_list[i].m2; | ||||
| vec3 obj_loc = PhysObj->GetPhysic()->GetTransform().v3.xyz; | |||||
| vec3 obj_loc = PhysObj->GetPhysic()->GetTransform()[3].xyz; | |||||
| if (m_cam_target == -1 || m_cam_target == i) | if (m_cam_target == -1 || m_cam_target == i) | ||||
| { | { | ||||
| @@ -371,7 +371,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| LocalPos = mat4::translate(vec3(4.f)) * LocalPos0; | LocalPos = mat4::translate(vec3(4.f)) * LocalPos0; | ||||
| LocalPos = cam_screen * LocalPos; | LocalPos = cam_screen * LocalPos; | ||||
| vpos = (LocalPos.v3 / LocalPos.v3.w).xyz; | |||||
| vpos = (LocalPos[3] / LocalPos[3].w).xyz; | |||||
| screen_min_max[0] = min(vpos.xy, screen_min_max[0]); | screen_min_max[0] = min(vpos.xy, screen_min_max[0]); | ||||
| screen_min_max[1] = max(vpos.xy, screen_min_max[1]); | screen_min_max[1] = max(vpos.xy, screen_min_max[1]); | ||||
| } | } | ||||
| @@ -427,7 +427,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| PhysicsObject* PhysObj = m_ground_list[i]; | PhysicsObject* PhysObj = m_ground_list[i]; | ||||
| mat4 GroundMat = PhysObj->GetTransform(); | mat4 GroundMat = PhysObj->GetTransform(); | ||||
| GroundBarycenter += GroundMat.v3.xyz; | |||||
| GroundBarycenter += GroundMat[3].xyz; | |||||
| factor += 1.f; | factor += 1.f; | ||||
| } | } | ||||
| @@ -438,7 +438,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| PhysicsObject* PhysObj = m_ground_list[i]; | PhysicsObject* PhysObj = m_ground_list[i]; | ||||
| mat4 GroundMat = PhysObj->GetTransform(); | mat4 GroundMat = PhysObj->GetTransform(); | ||||
| vec3 CenterToGround = GroundMat.v3.xyz - GroundBarycenter; | |||||
| vec3 CenterToGround = GroundMat[3].xyz - GroundBarycenter; | |||||
| vec3 CenterToCam = m_camera->GetPosition() - GroundBarycenter; | vec3 CenterToCam = m_camera->GetPosition() - GroundBarycenter; | ||||
| if (dot(normalize(CenterToCam - CenterToGround), | if (dot(normalize(CenterToCam - CenterToGround), | ||||
| @@ -462,7 +462,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| GroundMat = CenterMx * | GroundMat = CenterMx * | ||||
| mat4(quat::fromeuler_xyz(vec3(.0f, 20.f, 20.0f) * seconds)) | mat4(quat::fromeuler_xyz(vec3(.0f, 20.f, 20.0f) * seconds)) | ||||
| * GroundMat; | * GroundMat; | ||||
| PhysObj->SetTransform(GroundMat.v3.xyz, quat(GroundMat)); | |||||
| PhysObj->SetTransform(GroundMat[3].xyz, quat(GroundMat)); | |||||
| } | } | ||||
| } | } | ||||
| #endif //USE_ROTATION | #endif //USE_ROTATION | ||||
| @@ -477,14 +477,14 @@ void BtPhysTest::TickGame(float seconds) | |||||
| if (i == 0) | if (i == 0) | ||||
| { | { | ||||
| GroundMat = GroundMat * mat4(quat::fromeuler_xyz(vec3(20.f, .0f, .0f) * seconds)); | GroundMat = GroundMat * mat4(quat::fromeuler_xyz(vec3(20.f, .0f, .0f) * seconds)); | ||||
| PhysObj->SetTransform(GroundMat.v3.xyz, quat(GroundMat)); | |||||
| PhysObj->SetTransform(GroundMat[3].xyz, quat(GroundMat)); | |||||
| } | } | ||||
| else if (i == 1) | else if (i == 1) | ||||
| { | { | ||||
| GroundMat = | GroundMat = | ||||
| mat4::translate(vec3(-15.0f, 5.0f, lol::cos(m_loop_value) * 8.f)) * | mat4::translate(vec3(-15.0f, 5.0f, lol::cos(m_loop_value) * 8.f)) * | ||||
| mat4(quat::fromeuler_xyz(vec3(.0f, lol::cos(m_loop_value) * 20.f, .0f))); | mat4(quat::fromeuler_xyz(vec3(.0f, lol::cos(m_loop_value) * 20.f, .0f))); | ||||
| PhysObj->SetTransform(GroundMat.v3.xyz, quat(GroundMat)); | |||||
| PhysObj->SetTransform(GroundMat[3].xyz, quat(GroundMat)); | |||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| @@ -512,7 +512,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| Character->SetMovementForFrame(CharMove); | Character->SetMovementForFrame(CharMove); | ||||
| RayCastResult HitResult; | RayCastResult HitResult; | ||||
| if (m_simulation->RayHits(HitResult, ERT_Closest, Character->GetTransform().v3.xyz, (Character->GetTransform().v3.xyz + vec3(.0f, -1.f, .0f)), Character)) | |||||
| if (m_simulation->RayHits(HitResult, ERT_Closest, Character->GetTransform()[3].xyz, (Character->GetTransform()[3].xyz + vec3(.0f, -1.f, .0f)), Character)) | |||||
| Character->AttachTo(HitResult.m_collider_list[0], true, true); | Character->AttachTo(HitResult.m_collider_list[0], true, true); | ||||
| else | else | ||||
| Character->AttachTo(NULL); | Character->AttachTo(NULL); | ||||
| @@ -530,7 +530,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| PhysicsObject* PhysObj = m_character_list[i]; | PhysicsObject* PhysObj = m_character_list[i]; | ||||
| mat4 GroundMat = PhysObj->GetTransform(); | mat4 GroundMat = PhysObj->GetTransform(); | ||||
| PhysObjBarycenter += GroundMat.v3.xyz; | |||||
| PhysObjBarycenter += GroundMat[3].xyz; | |||||
| factor += 1.f; | factor += 1.f; | ||||
| } | } | ||||
| @@ -550,7 +550,7 @@ void BtPhysTest::TickGame(float seconds) | |||||
| PhysicsObject* PhysObj = m_physobj_list[i].m1; | PhysicsObject* PhysObj = m_physobj_list[i].m1; | ||||
| mat4 GroundMat = PhysObj->GetTransform(); | mat4 GroundMat = PhysObj->GetTransform(); | ||||
| PhysObjBarycenter += GroundMat.v3.xyz; | |||||
| PhysObjBarycenter += GroundMat[3].xyz; | |||||
| factor += 1.f; | factor += 1.f; | ||||
| } | } | ||||
| @@ -493,7 +493,7 @@ public: | |||||
| TargetCamera tc; | TargetCamera tc; | ||||
| if (m_meshes.Count() && m_mesh_id >= 0) | if (m_meshes.Count() && m_mesh_id >= 0) | ||||
| for (int i = 0; i < m_meshes[m_mesh_id].m1->GetVertexCount(); i++) | for (int i = 0; i < m_meshes[m_mesh_id].m1->GetVertexCount(); i++) | ||||
| tc.AddTarget((m_mat * mat4::translate(m_meshes[m_mesh_id].m1->GetVertexLocation(i))).v3.xyz); | |||||
| tc.AddTarget((m_mat * mat4::translate(m_meshes[m_mesh_id].m1->GetVertexLocation(i)))[3].xyz); | |||||
| tc.AddTarget(box3(vec3(0.f), vec3(1.f))); | tc.AddTarget(box3(vec3(0.f), vec3(1.f))); | ||||
| for (int k = 0; k < m_ssetup->m_lights.Count() && m_ssetup->m_show_lights; ++k) | for (int k = 0; k < m_ssetup->m_lights.Count() && m_ssetup->m_show_lights; ++k) | ||||
| { | { | ||||
| @@ -525,13 +525,13 @@ public: | |||||
| //Get location in cam coordinates | //Get location in cam coordinates | ||||
| target_mx = world_cam * target_mx; | target_mx = world_cam * target_mx; | ||||
| vpos = target_mx.v3.xyz; | |||||
| vpos = target_mx[3].xyz; | |||||
| local_min_max[0] = min(vpos.xyz, local_min_max[0]); | local_min_max[0] = min(vpos.xyz, local_min_max[0]); | ||||
| local_min_max[1] = max(vpos.xyz, local_min_max[1]); | local_min_max[1] = max(vpos.xyz, local_min_max[1]); | ||||
| //Get location in screen coordinates | //Get location in screen coordinates | ||||
| target_mx = cam_screen * target_mx; | target_mx = cam_screen * target_mx; | ||||
| vpos = (target_mx.v3 / target_mx.v3.w).xyz; | |||||
| vpos = (target_mx[3] / target_mx[3].w).xyz; | |||||
| screen_min_max[0] = min(screen_min_max[0], vpos.xy * vec2(RATIO_WH, 1.f)); | screen_min_max[0] = min(screen_min_max[0], vpos.xy * vec2(RATIO_WH, 1.f)); | ||||
| screen_min_max[1] = max(screen_min_max[1], vpos.xy * vec2(RATIO_WH, 1.f)); | screen_min_max[1] = max(screen_min_max[1], vpos.xy * vec2(RATIO_WH, 1.f)); | ||||
| @@ -846,7 +846,7 @@ public: | |||||
| { | { | ||||
| Light* ltmp = m_ssetup->m_lights[k]; | Light* ltmp = m_ssetup->m_lights[k]; | ||||
| mat4 world = mat4::translate(ltmp->GetPosition()); | mat4 world = mat4::translate(ltmp->GetPosition()); | ||||
| mat4 local = mat4::translate((inverse(m_mat) * world).v3.xyz); | |||||
| mat4 local = mat4::translate((inverse(m_mat) * world)[3].xyz); | |||||
| //dir light | //dir light | ||||
| if (ltmp->GetType() == LightType::Directional) | if (ltmp->GetType() == LightType::Directional) | ||||
| { | { | ||||
| @@ -873,14 +873,14 @@ public: | |||||
| m_meshes[i].m1->m_vert[m_meshes[i].m1->m_indices[j+2]] | m_meshes[i].m1->m_vert[m_meshes[i].m1->m_indices[j+2]] | ||||
| }; | }; | ||||
| for (int k = 0; k < 3; k++) | for (int k = 0; k < 3; k++) | ||||
| Debug::DrawLine((m_mat * mat4::translate(v[k].m_coord)).v3.xyz, | |||||
| (m_mat * mat4::translate(v[(k+1)%3].m_coord)).v3.xyz, vec4(vec3((v[k].m_coord.z + 1.f)*.5f),1.f)); | |||||
| Debug::DrawLine((m_mat * mat4::translate(v[k].m_coord))[3].xyz, | |||||
| (m_mat * mat4::translate(v[(k+1)%3].m_coord))[3].xyz, vec4(vec3((v[k].m_coord.z + 1.f)*.5f),1.f)); | |||||
| } | } | ||||
| for (int j = 0; j < m_meshes[i].m1->m_vert.Count(); j++) | for (int j = 0; j < m_meshes[i].m1->m_vert.Count(); j++) | ||||
| { | { | ||||
| VertexData &v = m_meshes[i].m1->m_vert[m_meshes[i].m1->m_indices[j]]; | VertexData &v = m_meshes[i].m1->m_vert[m_meshes[i].m1->m_indices[j]]; | ||||
| Debug::DrawLine((m_mat * mat4::translate(v.m_coord)).v3.xyz, | |||||
| (m_mat * mat4::translate(v.m_coord)).v3.xyz + | |||||
| Debug::DrawLine((m_mat * mat4::translate(v.m_coord))[3].xyz, | |||||
| (m_mat * mat4::translate(v.m_coord))[3].xyz + | |||||
| (m_mat * vec4(v.m_normal * 5.f, 0.f)).xyz, vec4(lol::abs(v.m_normal), 1.f)); | (m_mat * vec4(v.m_normal * 5.f, 0.f)).xyz, vec4(lol::abs(v.m_normal), 1.f)); | ||||
| } | } | ||||
| } | } | ||||
| @@ -107,10 +107,10 @@ void EasyCharacterController::SetTransform(const lol::vec3& base_location, const | |||||
| { | { | ||||
| if (m_base_is_updating) | if (m_base_is_updating) | ||||
| { | { | ||||
| m_base_cached_movement = base_location - m_local_to_world.v3.xyz; | |||||
| m_local_to_world = lol::mat4::translate(m_local_to_world.v3.xyz) * lol::mat4(base_rotation); | |||||
| m_base_cached_movement = base_location - m_local_to_world[3].xyz; | |||||
| m_local_to_world = lol::mat4::translate(m_local_to_world[3].xyz) * lol::mat4(base_rotation); | |||||
| if (m_ghost_object) | if (m_ghost_object) | ||||
| m_ghost_object->setWorldTransform(btTransform(LOL2BT_QUAT(base_rotation), LOL2BT_VEC3(LOL2BT_UNIT * m_local_to_world.v3.xyz))); | |||||
| m_ghost_object->setWorldTransform(btTransform(LOL2BT_QUAT(base_rotation), LOL2BT_VEC3(LOL2BT_UNIT * m_local_to_world[3].xyz))); | |||||
| } | } | ||||
| else | else | ||||
| EasyPhysic::SetTransform(base_location, base_rotation); | EasyPhysic::SetTransform(base_location, base_rotation); | ||||
| @@ -83,15 +83,15 @@ private: | |||||
| void CustomInitConstraintToPoint2Point() | void CustomInitConstraintToPoint2Point() | ||||
| { | { | ||||
| m_p2p_constraint = new btPoint2PointConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | m_p2p_constraint = new btPoint2PointConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | ||||
| LOL2BT_VEC3(m_a_transform.v3.xyz * LOL2BT_UNIT), LOL2BT_VEC3(m_b_transform.v3.xyz * LOL2BT_UNIT)); | |||||
| LOL2BT_VEC3(m_a_transform[3].xyz * LOL2BT_UNIT), LOL2BT_VEC3(m_b_transform[3].xyz * LOL2BT_UNIT)); | |||||
| m_typed_constraint = m_p2p_constraint; | m_typed_constraint = m_p2p_constraint; | ||||
| } | } | ||||
| void CustomInitConstraintToHinge() | void CustomInitConstraintToHinge() | ||||
| { | { | ||||
| m_hinge_constraint = new btHingeConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | m_hinge_constraint = new btHingeConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | ||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform[3].xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform[3].xyz * LOL2BT_UNIT)), | |||||
| m_using_ref_a); | m_using_ref_a); | ||||
| m_typed_constraint = m_hinge_constraint; | m_typed_constraint = m_hinge_constraint; | ||||
| } | } | ||||
| @@ -99,8 +99,8 @@ private: | |||||
| void CustomInitConstraintToSlider() | void CustomInitConstraintToSlider() | ||||
| { | { | ||||
| m_slider_constraint = new btSliderConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | m_slider_constraint = new btSliderConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | ||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform[3].xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform[3].xyz * LOL2BT_UNIT)), | |||||
| m_using_ref_a); | m_using_ref_a); | ||||
| m_typed_constraint = m_slider_constraint; | m_typed_constraint = m_slider_constraint; | ||||
| } | } | ||||
| @@ -108,16 +108,16 @@ private: | |||||
| void CustomInitConstraintToConeTwist() | void CustomInitConstraintToConeTwist() | ||||
| { | { | ||||
| m_cone_twist_constraint = new btConeTwistConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | m_cone_twist_constraint = new btConeTwistConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | ||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform.v3.xyz * LOL2BT_UNIT))); | |||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform[3].xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform[3].xyz * LOL2BT_UNIT))); | |||||
| m_typed_constraint = m_cone_twist_constraint; | m_typed_constraint = m_cone_twist_constraint; | ||||
| } | } | ||||
| void CustomInitConstraintTo6Dof() | void CustomInitConstraintTo6Dof() | ||||
| { | { | ||||
| m_6dof_constraint = new btGeneric6DofConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | m_6dof_constraint = new btGeneric6DofConstraint(*m_a_physobj->m_rigid_body, *m_b_physobj->m_rigid_body, | ||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform.v3.xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_a_transform)), LOL2BT_VEC3(m_a_transform[3].xyz * LOL2BT_UNIT)), | |||||
| btTransform(LOL2BT_QUAT(quat(m_b_transform)), LOL2BT_VEC3(m_b_transform[3].xyz * LOL2BT_UNIT)), | |||||
| m_using_ref_a); | m_using_ref_a); | ||||
| m_typed_constraint = m_6dof_constraint; | m_typed_constraint = m_6dof_constraint; | ||||
| } | } | ||||
| @@ -157,16 +157,16 @@ void EasyPhysic::SetTransform(const lol::vec3& base_location, const lol::quat& b | |||||
| //Internal callback when Base transform has changed. | //Internal callback when Base transform has changed. | ||||
| void EasyPhysic::BaseTransformChanged(const lol::mat4& PreviousMatrix, const lol::mat4& NewMatrix) | void EasyPhysic::BaseTransformChanged(const lol::mat4& PreviousMatrix, const lol::mat4& NewMatrix) | ||||
| { | { | ||||
| mat4 PreviousMatrixLoc = ((m_base_lock_location)?(PreviousMatrix):(lol::mat4::translate(PreviousMatrix.v3.xyz))); | |||||
| mat4 PreviousMatrixLoc = ((m_base_lock_location)?(PreviousMatrix):(lol::mat4::translate(PreviousMatrix[3].xyz))); | |||||
| mat4 PreviousMatrixRot = ((m_base_lock_rotation)?(lol::mat4(lol::quat(PreviousMatrix))):(lol::mat4(1.f))); | mat4 PreviousMatrixRot = ((m_base_lock_rotation)?(lol::mat4(lol::quat(PreviousMatrix))):(lol::mat4(1.f))); | ||||
| mat4 NewMatrixLoc = ((m_base_lock_location)?(NewMatrix):(lol::mat4::translate(NewMatrix.v3.xyz))); | |||||
| mat4 NewMatrixLoc = ((m_base_lock_location)?(NewMatrix):(lol::mat4::translate(NewMatrix[3].xyz))); | |||||
| mat4 NewMatrixRot = ((m_base_lock_rotation)?(lol::mat4(lol::quat(NewMatrix))):(lol::mat4(1.f))); | mat4 NewMatrixRot = ((m_base_lock_rotation)?(lol::mat4(lol::quat(NewMatrix))):(lol::mat4(1.f))); | ||||
| if (m_ghost_object || (m_rigid_body->getCollisionFlags() & btCollisionObject::CF_KINEMATIC_OBJECT)) | if (m_ghost_object || (m_rigid_body->getCollisionFlags() & btCollisionObject::CF_KINEMATIC_OBJECT)) | ||||
| { | { | ||||
| mat4 ThisMatrixLoc = NewMatrixLoc * inverse(PreviousMatrixLoc) * lol::mat4::translate(m_local_to_world.v3.xyz); | |||||
| mat4 ThisMatrixLoc = NewMatrixLoc * inverse(PreviousMatrixLoc) * lol::mat4::translate(m_local_to_world[3].xyz); | |||||
| mat4 ThisMatrixRot = NewMatrixRot * inverse(PreviousMatrixRot) * lol::mat4(lol::quat(m_local_to_world)); | mat4 ThisMatrixRot = NewMatrixRot * inverse(PreviousMatrixRot) * lol::mat4(lol::quat(m_local_to_world)); | ||||
| SetTransform(ThisMatrixLoc.v3.xyz, lol::mat4(lol::quat(ThisMatrixRot))); | |||||
| SetTransform(ThisMatrixLoc[3].xyz, lol::mat4(lol::quat(ThisMatrixRot))); | |||||
| } | } | ||||
| } | } | ||||
| @@ -247,7 +247,7 @@ void EasyPhysic::InitBodyToGhost() | |||||
| m_collision_object = m_ghost_object; | m_collision_object = m_ghost_object; | ||||
| m_collision_object->setUserPointer(this); | m_collision_object->setUserPointer(this); | ||||
| SetTransform(m_local_to_world.v3.xyz, lol::quat(m_local_to_world)); | |||||
| SetTransform(m_local_to_world[3].xyz, lol::quat(m_local_to_world)); | |||||
| m_ghost_object->setCollisionFlags(m_ghost_object->getCollisionFlags()); | m_ghost_object->setCollisionFlags(m_ghost_object->getCollisionFlags()); | ||||
| } | } | ||||
| @@ -17,38 +17,33 @@ using namespace lol; | |||||
| * naive inversion and is used for the Remez inversion method. | * naive inversion and is used for the Remez inversion method. | ||||
| */ | */ | ||||
| template<typename T> struct Matrix | |||||
| template<typename T> struct LinearSystem | |||||
| { | { | ||||
| inline Matrix<T>(int cols, int rows) | |||||
| : m_cols(cols), | |||||
| m_rows(rows) | |||||
| inline LinearSystem<T>(int cols) | |||||
| : m_cols(cols) | |||||
| { | { | ||||
| ASSERT(cols > 0); | ASSERT(cols > 0); | ||||
| ASSERT(rows > 0); | |||||
| m_data.Resize(m_cols * m_rows); | |||||
| m_data.Resize(m_cols * m_cols); | |||||
| } | } | ||||
| inline Matrix<T>(Matrix<T> const &other) | |||||
| inline LinearSystem<T>(LinearSystem<T> const &other) | |||||
| { | { | ||||
| m_cols = other.m_cols; | m_cols = other.m_cols; | ||||
| m_rows = other.m_rows; | |||||
| m_data = other.m_data; | m_data = other.m_data; | ||||
| } | } | ||||
| void Init(T const &x) | void Init(T const &x) | ||||
| { | { | ||||
| for (int j = 0; j < m_rows; j++) | |||||
| for (int j = 0; j < m_cols; j++) | |||||
| for (int i = 0; i < m_cols; i++) | for (int i = 0; i < m_cols; i++) | ||||
| m(i, j) = (i == j) ? x : (T)0; | m(i, j) = (i == j) ? x : (T)0; | ||||
| } | } | ||||
| /* Naive matrix inversion */ | /* Naive matrix inversion */ | ||||
| Matrix<T> inv() const | |||||
| LinearSystem<T> inv() const | |||||
| { | { | ||||
| ASSERT(m_cols == m_rows); | |||||
| Matrix a(*this), b(m_cols, m_rows); | |||||
| LinearSystem a(*this), b(m_cols); | |||||
| b.Init((T)1); | b.Init((T)1); | ||||
| @@ -100,10 +95,10 @@ template<typename T> struct Matrix | |||||
| return b; | return b; | ||||
| } | } | ||||
| inline T & m(int i, int j) { return m_data[m_rows * j + i]; } | |||||
| inline T const & m(int i, int j) const { return m_data[m_rows * j + i]; } | |||||
| inline T & m(int i, int j) { return m_data[m_cols * j + i]; } | |||||
| inline T const & m(int i, int j) const { return m_data[m_cols * j + i]; } | |||||
| int m_cols, m_rows; | |||||
| int m_cols; | |||||
| private: | private: | ||||
| array<T> m_data; | array<T> m_data; | ||||
| @@ -105,7 +105,7 @@ void RemezSolver::Init() | |||||
| /* We build a matrix of Chebishev evaluations: row i contains the | /* We build a matrix of Chebishev evaluations: row i contains the | ||||
| * evaluations of x_i for polynomial order n = 0, 1, ... */ | * evaluations of x_i for polynomial order n = 0, 1, ... */ | ||||
| Matrix<real> mat(m_order + 1, m_order + 1); | |||||
| LinearSystem<real> system(m_order + 1); | |||||
| for (int i = 0; i < m_order + 1; i++) | for (int i = 0; i < m_order + 1; i++) | ||||
| { | { | ||||
| /* Compute the powers of x_i */ | /* Compute the powers of x_i */ | ||||
| @@ -120,19 +120,19 @@ void RemezSolver::Init() | |||||
| real sum = 0.0; | real sum = 0.0; | ||||
| for (int k = 0; k < m_order + 1; k++) | for (int k = 0; k < m_order + 1; k++) | ||||
| sum += (real)Cheby(n, k) * powers[k]; | sum += (real)Cheby(n, k) * powers[k]; | ||||
| mat.m(i, n) = sum; | |||||
| system.m(i, n) = sum; | |||||
| } | } | ||||
| } | } | ||||
| /* Solve the system */ | /* Solve the system */ | ||||
| mat = mat.inv(); | |||||
| system = system.inv(); | |||||
| /* Compute interpolation coefficients */ | /* Compute interpolation coefficients */ | ||||
| for (int j = 0; j < m_order + 1; j++) | for (int j = 0; j < m_order + 1; j++) | ||||
| { | { | ||||
| m_coeff[j] = 0; | m_coeff[j] = 0; | ||||
| for (int i = 0; i < m_order + 1; i++) | for (int i = 0; i < m_order + 1; i++) | ||||
| m_coeff[j] += mat.m(j, i) * fxn[i]; | |||||
| m_coeff[j] += system.m(j, i) * fxn[i]; | |||||
| } | } | ||||
| } | } | ||||
| @@ -245,7 +245,7 @@ void RemezSolver::Step() | |||||
| /* We build a matrix of Chebishev evaluations: row i contains the | /* We build a matrix of Chebishev evaluations: row i contains the | ||||
| * evaluations of x_i for polynomial order n = 0, 1, ... */ | * evaluations of x_i for polynomial order n = 0, 1, ... */ | ||||
| Matrix<real> mat(m_order + 2, m_order + 2); | |||||
| LinearSystem<real> system(m_order + 2); | |||||
| for (int i = 0; i < m_order + 2; i++) | for (int i = 0; i < m_order + 2; i++) | ||||
| { | { | ||||
| /* Compute the powers of x_i */ | /* Compute the powers of x_i */ | ||||
| @@ -260,29 +260,29 @@ void RemezSolver::Step() | |||||
| real sum = 0.0; | real sum = 0.0; | ||||
| for (int k = 0; k < m_order + 1; k++) | for (int k = 0; k < m_order + 1; k++) | ||||
| sum += (real)Cheby(n, k) * powers[k]; | sum += (real)Cheby(n, k) * powers[k]; | ||||
| mat.m(i, n) = sum; | |||||
| system.m(i, n) = sum; | |||||
| } | } | ||||
| if (i & 1) | if (i & 1) | ||||
| mat.m(i, m_order + 1) = fabs(Weight(m_control[i])); | |||||
| system.m(i, m_order + 1) = fabs(Weight(m_control[i])); | |||||
| else | else | ||||
| mat.m(i, m_order + 1) = -fabs(Weight(m_control[i])); | |||||
| system.m(i, m_order + 1) = -fabs(Weight(m_control[i])); | |||||
| } | } | ||||
| /* Solve the system */ | /* Solve the system */ | ||||
| mat = mat.inv(); | |||||
| system = system.inv(); | |||||
| /* Compute interpolation coefficients */ | /* Compute interpolation coefficients */ | ||||
| for (int j = 0; j < m_order + 1; j++) | for (int j = 0; j < m_order + 1; j++) | ||||
| { | { | ||||
| m_coeff[j] = 0; | m_coeff[j] = 0; | ||||
| for (int i = 0; i < m_order + 2; i++) | for (int i = 0; i < m_order + 2; i++) | ||||
| m_coeff[j] += mat.m(j, i) * fxn[i]; | |||||
| m_coeff[j] += system.m(j, i) * fxn[i]; | |||||
| } | } | ||||
| /* Compute the error */ | /* Compute the error */ | ||||
| real error = 0; | real error = 0; | ||||
| for (int i = 0; i < m_order + 2; i++) | for (int i = 0; i < m_order + 2; i++) | ||||
| error += mat.m(m_order + 1, i) * fxn[i]; | |||||
| error += system.m(m_order + 1, i) * fxn[i]; | |||||
| } | } | ||||
| int RemezSolver::Cheby(int n, int k) | int RemezSolver::Cheby(int n, int k) | ||||
| @@ -28,7 +28,7 @@ au Syntax cpp | |||||
| " HLSL types | " HLSL types | ||||
| au Syntax cpp | au Syntax cpp | ||||
| \ syn match cType | \ syn match cType | ||||
| \ "\<\(int\|float\)[234]\(\|x[234]\)\>" | |||||
| \ "\<\(int\|half\|float\)[234]\(\|x[234]\)\>" | |||||
| " More GLSL-like types from the Lol Engine | " More GLSL-like types from the Lol Engine | ||||
| au Syntax cpp | au Syntax cpp | ||||