Forráskód Böngészése

Fixed quaternion set from euler.

Daniel Buckmaster 11 éve
szülő
commit
8b1ff267f0
2 módosított fájl, 74 hozzáadás és 11 törlés
  1. 11 11
      Engine/source/math/mQuat.cpp
  2. 63 0
      Engine/source/math/test/mQuatTest.cpp

+ 11 - 11
Engine/source/math/mQuat.cpp

@@ -35,27 +35,27 @@ QuatF& QuatF::set( const EulerF & e )
    F32 cx, sx;
    F32 cy, sy;
    F32 cz, sz;
-   mSinCos( -e.x * 0.5f, sx, cx );
-   mSinCos( -e.y * 0.5f, sy, cy );
-   mSinCos( -e.z * 0.5f, sz, cz );
+   mSinCos( e.x * 0.5f, sx, cx );
+   mSinCos( e.y * 0.5f, sy, cy );
+   mSinCos( e.z * 0.5f, sz, cz );
 
-   // Qyaw(z)   = [ (0, 0, sin z/2), cos z/2 ]
+   // Qyaw(z) = [ (0, 0, sin z/2), cos z/2 ]
    // Qpitch(x) = [ (sin x/2, 0, 0), cos x/2 ]
-   // Qroll(y)  = [ (0, sin y/2, 0), cos y/2 ]
-   // this = Qresult = Qyaw*Qpitch*Qroll  ZXY
+   // Qroll(y) = [ (0, sin y/2, 0), cos y/2 ]
+   // this = Qresult = Qyaw*Qpitch*Qroll ZXY
    //
    // The code that folows is a simplification of:
-   //    roll*=pitch;
-   //    roll*=yaw;
-   //    *this = roll;
+   // roll*=pitch;
+   // roll*=yaw;
+   // *this = roll;
    F32 cycz, sysz, sycz, cysz;
    cycz = cy*cz;
    sysz = sy*sz;
    sycz = sy*cz;
    cysz = cy*sz;
-   w = cycz*cx + sysz*sx;
+   w = cycz*cx - sysz*sx;
    x = cycz*sx + sysz*cx;
-   y = sycz*cx - cysz*sx;
+   y = sycz*cx + cysz*sx;
    z = cysz*cx - sycz*sx;
 
    return *this;

+ 63 - 0
Engine/source/math/test/mQuatTest.cpp

@@ -0,0 +1,63 @@
+//-----------------------------------------------------------------------------
+// Copyright (c) 2014 GarageGames, LLC
+//
+// Permission is hereby granted, free of charge, to any person obtaining a copy
+// of this software and associated documentation files (the "Software"), to
+// deal in the Software without restriction, including without limitation the
+// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+// sell copies of the Software, and to permit persons to whom the Software is
+// furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in
+// all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+// IN THE SOFTWARE.
+//-----------------------------------------------------------------------------
+
+#ifdef TORQUE_TESTS_ENABLED
+#include "testing/unitTesting.h"
+#include "math/mQuat.h"
+#include "math/mAngAxis.h"
+#include "math/mMatrix.h"
+
+/// For testing things that should be close to 0, but accounting for floating-
+/// point inaccuracy.
+static const F32 epsilon = 1e-3f;
+
+/// Test quaternions for equality by expecting the angle between them to be
+/// close to 0.
+#define EXPECT_QUAT_EQ(q1, q2) EXPECT_LT(q1.angleBetween(q2), epsilon)
+
+TEST(QuatF, AngleBetween)
+{
+   QuatF p(QuatF::Identity), q(QuatF::Identity);
+   EXPECT_LT(p.angleBetween(q), epsilon)
+      << "Angle between identity quaternions should be ~0.";
+
+   p.set(EulerF(0.1, 0.15, -0.2));
+   q = p;
+   EXPECT_LT(p.angleBetween(q), epsilon)
+      << "Angle between identical quaternions should be ~0.";
+}
+
+/// Test conversion from EulerF.
+TEST(QuatF, Construction)
+{
+   EulerF eId(0, 0, 0);
+   EXPECT_QUAT_EQ(QuatF(eId), QuatF::Identity)
+      << "Quaternions constructed from identity EulerF and QuatF::Identity not equal.";
+
+   EulerF eRot(0.0f, -0.0f, 1.5707963267948966f);
+   MatrixF mat(eRot);
+   AngAxisF aaRot(mat);
+   EXPECT_QUAT_EQ(QuatF(eRot), QuatF(aaRot))
+      << "Quaternions constructed from EulerF and AngAxisF not equal.";
+}
+
+#endif