Permalink
Browse files

Added rotation matrices from quaternions

- finally fixed the scale bug
- also ignoring .gch files (gcc precompiled header)
- added enable_if to some scalar function to allow code like 6*ntuple (istead of having to write 6.f*ntuple)
- fixed broken compile on using close
- added platform.h for some platform-specific defines
- added is_identity to matrices
- added a precompiled header in the test project
- added a header for test-specific defines in the test project
  • Loading branch information...
1 parent dea1a18 commit 9a981cdaba0498822983f5b14ac82a61d370ec86 @iboB committed Apr 13, 2012
View
@@ -10,6 +10,7 @@ test/ipch/
#code blocks stuff
*.depend
*.layout
+*.gch
test/bin/
test/obj/
View
@@ -8,6 +8,7 @@
#pragma once
#include <cmath>
+#include <utility>
namespace mathgp
{
@@ -43,8 +44,9 @@ _type deg_to_rad(const _type& degrees)
}
template <typename _type>
-bool close(const _type& a, const _type& b,
- const _type& epsilon = constants<_type>::EPSILON())
+typename std::enable_if<std::is_arithmetic<_type>::value,
+bool>::type close(const _type& a, const _type& b,
+ const _type& epsilon)
{
return !(std::abs(a - b) > epsilon);
}
View
@@ -9,6 +9,7 @@
//#define MATHGP_DISABLE_SWIZZLE
+#include "platform.h"
#include "defines.h"
#include "vector.h"
#include "complex.h"
View
@@ -150,6 +150,11 @@ class matrixnxnt : public ntuple<_n*_n, _type, _this_type>
////////////////////////////////////////////////////////
// functions
+ bool is_identity(_type e = constants<_type>::EPSILON()) const
+ {
+ return close(*this, identity(), e);
+ }
+
_this_type& transpose()
{
for(size_t r=0; r<order; ++r)
@@ -415,6 +420,26 @@ class matrix3x3t : public _internal::matrixnxnt<3, _type, matrix3x3t<_type>>
{
return _internal::rotation_from_vectors<matrix3x3t>(src, target);
}
+
+ static matrix3x3t rotation_quaternion(const quaterniont<_type>& q)
+ {
+ const _type x2 = sq(q.x());
+ const _type y2 = sq(q.y());
+ const _type z2 = sq(q.z());
+ const _type w2 = sq(q.w());
+ const _type xy = 2 * q.x() * q.y();
+ const _type xz = 2 * q.x() * q.z();
+ const _type xw = 2 * q.x() * q.w();
+ const _type yz = 2 * q.y() * q.z();
+ const _type yw = 2 * q.y() * q.w();
+ const _type zw = 2 * q.z() * q.w();
+
+ return matrix3x3t::rows(
+ w2 + x2 - y2 - z2, xy - zw, xz + yw,
+ xy + zw, w2 - x2 + y2 - z2, yz - xw,
+ xz - yw, yz + xw, w2 - x2 - y2 + z2
+ );
+ }
};
template <typename _type>
@@ -612,12 +637,12 @@ class matrix4x4t : public _internal::matrixnxnt<4, _type, matrix4x4t<_type>>
static matrix4x4t scaling(_type sx, _type sy, _type sz)
{
- return from3x3(matrix3x3t<_type>::scaling(scale));
+ return scaling(v(sx, sy, sz));
}
static matrix4x4t scaling(const vector3t<_type>& scale)
{
- return scaling(scale.x(), scale.y(), scale.z());
+ return from3x3(matrix3x3t<_type>::scaling(scale));
}
static matrix4x4t scaling_uniform(_type s)
@@ -655,6 +680,11 @@ class matrix4x4t : public _internal::matrixnxnt<4, _type, matrix4x4t<_type>>
return from3x3(matrix3x3t<_type>::rotation_vectors(src, target));
}
+ static matrix4x4t rotation_quaternion(const quaterniont<_type>& q)
+ {
+ return from3x3(matrix3x3t<_type>::rotation_quaternion(q));
+ }
+
////////////////////////////////////////////////////////
// functions
View
@@ -246,9 +246,10 @@ _this_type operator-(const ntuple<_n, _type, _this_type>& a,
return ret;
}
-template <size_t _n, typename _type, typename _this_type>
-_this_type operator*(const ntuple<_n, _type, _this_type>& a,
- const _type& scalar)
+template <size_t _n, typename _type, typename _this_type, typename _scalar>
+typename std::enable_if<std::is_arithmetic<_scalar>::value,
+_this_type>::type operator*(const ntuple<_n, _type, _this_type>& a,
+ const _scalar& scalar)
{
_this_type ret;
@@ -257,8 +258,9 @@ _this_type operator*(const ntuple<_n, _type, _this_type>& a,
return ret;
}
-template <size_t _n, typename _type, typename _this_type>
-_this_type operator*(const _type& scalar,
+template <size_t _n, typename _type, typename _this_type, typename _scalar>
+typename std::enable_if<std::is_arithmetic<_scalar>::value,
+_this_type>::type operator*(const _scalar& scalar,
const ntuple<_n, _type, _this_type>& b)
{
_this_type ret;
@@ -268,9 +270,10 @@ _this_type operator*(const _type& scalar,
return ret;
}
-template <size_t _n, typename _type, typename _this_type>
-_this_type operator/(const ntuple<_n, _type, _this_type>& a,
- const _type& scalar)
+template <size_t _n, typename _type, typename _this_type, typename _scalar>
+typename std::enable_if<std::is_arithmetic<_scalar>::value,
+_this_type>::type operator/(const ntuple<_n, _type, _this_type>& a,
+ const _scalar& scalar)
{
_this_type ret;
@@ -325,7 +328,7 @@ bool close(const ntuple<_n, _type, _this_type>& a, const ntuple<_n, _type, _this
const _type& epsilon = constants<_type>::EPSILON())
{
for(size_t i = 0; i < _n; ++i)
- if(!close(a, b, epsilon))
+ if(!::mathgp::close(a.at(i), b.at(i), epsilon))
return false;
return true;
@@ -375,6 +378,20 @@ _this_type sign(const ntuple<_n, _type, _this_type>& a)
} // namespace _internal
+template <typename _t>
+class is_ntuple
+{
+ struct yes { char c; };
+ struct no { char c[2]; };
+
+ template <size_t _n, typename _type, typename _this_type>
+ static yes check(_internal::ntuple<_n, _type, _this_type>*);
+ static no check(...);
+
+public:
+ static const bool value = sizeof(check(static_cast<_t*>(nullptr))) == sizeof(yes);
+};
+
// to be used if ntuples are keys in maps or sets
struct strict_ordering
{
View
@@ -0,0 +1,27 @@
+// MathGP Library
+// Copyright (c) 2012 Borislav Stanimirov
+//
+// See the LICENSE.txt file, included in this
+// distribution for details about the copyright
+
+// platform.h - some platform dependent checks and defines
+#pragma once
+
+////////////////////////////////////////////////////////
+// compiler specific stuff
+
+#if defined(_MSC_VER)
+# if _MSC_VER < 1600
+# error "A minimum cl version of 16 is required to compile MathGP"
+# endif
+#elif defined(__GNUC__)
+ #if __GNUC__ < 4 || __GNUC_MINOR__ < 5 || __GNUC_PATCHLEVEL__ < 2
+ #error "A minimum gcc version of 4.5.2 is required to compile MathGP"
+ #elif __GNUC_MINOR__ < 6
+ // can be emulated through
+ // http://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/nullptr#Solution_and_Sample_Code
+ // but no need to maintain a global variable.
+ // the define is fine for now
+ #define nullptr NULL
+ #endif
+#endif
View
@@ -1,16 +1,10 @@
// MathGP Library
// Copyright (c) 2012 Borislav Stanimirov
//
-// See the LICENSE.txt file, included in this
+// See the LICENSE.txt file, included in this
// distribution for details about the copyright
-#include <boost/test/unit_test.hpp>
-
-#define MATHGP_DISABLE_SWIZZLE
-#define MATHGP_PREFERRED_TYPE float
-
-#include <mathgp/mathgp.h>
-#include <mathgp/stdext.h>
+#include "precompiled.h"
using namespace boost::unit_test;
using namespace std;
@@ -23,7 +17,7 @@ void ntuple_arithmetic()
void vector_arithmetic()
{
vector3 v1 = vector3::uniform(1);
- vector3 v6 = 6.f * v1;
+ vector3 v6 = 6 * v1;
BOOST_CHECK_EQUAL(v6, vector3::coord(6, 6, 6));
}
@@ -1,16 +1,10 @@
// MathGP Library
// Copyright (c) 2012 Borislav Stanimirov
-//
-// See the LICENSE.txt file, included in this
+//
+// See the LICENSE.txt file, included in this
// distribution for details about the copyright
-#include <boost/test/unit_test.hpp>
-
-#define MATHGP_DISABLE_SWIZZLE
-#define MATHGP_PREFERRED_TYPE float
-
-#include <mathgp/mathgp.h>
-#include <mathgp/stdext.h>
+#include "precompiled.h"
using namespace boost::unit_test;
using namespace std;
View
@@ -1,23 +1,38 @@
// MathGP Library
// Copyright (c) 2012 Borislav Stanimirov
-//
-// See the LICENSE.txt file, included in this
+//
+// See the LICENSE.txt file, included in this
// distribution for details about the copyright
-#include <boost/test/unit_test.hpp>
-
-#define MATHGP_DISABLE_SWIZZLE
-#define MATHGP_PREFERRED_TYPE float
-
-#include <mathgp/mathgp.h>
+#include "precompiled.h"
+#include "mathgp_test.h"
using namespace boost::unit_test;
using namespace std;
using namespace mathgp;
+void rotation()
+{
+ matrix rot;
+
+ quaternion q = quaternion::identity();
+
+ matrix qrot = matrix::rotation_quaternion(q);
+
+ BOOST_CHECK(qrot.is_identity());
+
+ q = quaternion::rotation_axis(vector3::coord(1, 2, 3), 0.15f);
+ qrot = matrix::rotation_quaternion(q);
+ rot = matrix::rotation_axis(vector3::coord(1, 2, 3), 0.15f);
+
+ MAT4_CHECK_CLOSE(qrot, rot);
+}
+
test_suite* geometry()
{
test_suite* suite = BOOST_TEST_SUITE("geometry");
+ suite->add(BOOST_TEST_CASE(rotation));
+
return suite;
-}
+}
View
@@ -1,10 +1,10 @@
// MathGP Library
// Copyright (c) 2012 Borislav Stanimirov
-//
-// See the LICENSE.txt file, included in this
+//
+// See the LICENSE.txt file, included in this
// distribution for details about the copyright
-#include <boost/test/unit_test.hpp>
+#include "precompiled.h"
using namespace boost::unit_test;
View
@@ -0,0 +1,12 @@
+// MathGP Library
+// Copyright (c) 2012 Borislav Stanimirov
+//
+// See the LICENSE.txt file, included in this
+// distribution for details about the copyright
+
+#pragma once
+
+#define MAT4_CHECK_CLOSE_E(m1, m2, e) \
+ BOOST_CHECK_PREDICATE( std::bind(&_internal::close<16, float, matrix>, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3), (m1)(m2)(e))
+
+#define MAT4_CHECK_CLOSE(m1, m2) MAT4_CHECK_CLOSE_E(m1, m2, constants<float>::EPSILON())
View
@@ -0,0 +1,7 @@
+// MathGP Library
+// Copyright (c) 2012 Borislav Stanimirov
+//
+// See the LICENSE.txt file, included in this
+// distribution for details about the copyright
+
+#include "precompiled.h"
View
@@ -0,0 +1,18 @@
+// MathGP Library
+// Copyright (c) 2012 Borislav Stanimirov
+//
+// See the LICENSE.txt file, included in this
+// distribution for details about the copyright
+
+// retro include guards to suppress a gcc precompiled headers warning
+#if !defined(_mathgp_test_precompiled_h_included)
+#define _mathgp_test_precompiled_h_included
+
+#include <boost/test/unit_test.hpp>
+
+#define MATHGP_PREFERRED_TYPE float
+
+#include <mathgp/mathgp.h>
+#include <mathgp/stdext.h>
+
+#endif
View
@@ -1,10 +1,10 @@
// MathGP Library
// Copyright (c) 2012 Borislav Stanimirov
-//
-// See the LICENSE.txt file, included in this
+//
+// See the LICENSE.txt file, included in this
// distribution for details about the copyright
-#include <boost/test/unit_test.hpp>
+#include "precompiled.h"
using namespace boost::unit_test;
View
@@ -1,15 +1,10 @@
// MathGP Library
// Copyright (c) 2012 Borislav Stanimirov
-//
-// See the LICENSE.txt file, included in this
+//
+// See the LICENSE.txt file, included in this
// distribution for details about the copyright
-#include <boost/test/unit_test.hpp>
-
-//#define MATHGP_DISABLE_SWIZZLE
-#define MATHGP_PREFERRED_TYPE float
-
-#include <mathgp/mathgp.h>
+#include "precompiled.h"
using namespace boost::unit_test;
using namespace std;
Oops, something went wrong.

0 comments on commit 9a981cd

Please sign in to comment.