I’m attempting to set the rotation of my RootNode children to a certain value that aligns it correctly to other files (coordinate system in Unity 3D).
I’m setting EulerAngles directly:
node.Transform.EulerAngles = new Vector3( -90, 0, 180 );
When I read the property immediately afterwards I get the following back: (x: 180 y: 0 z: 180)
This is clearly incorrect.
I’ve written more unit tests to try and figure out what is going on, and It’s just adding to confusion.
public const double RadToDegree = 180 / Math.PI; public const double DegreeToRad = Math.PI / 180; [Test] public void SimpleQuaternionTest() { var q1 = Quaternion.FromEulerAngle( 0, 0, 180 * DegreeToRad); var q2 = Quaternion.FromEulerAngle( 180 * DegreeToRad, 0, 180 * DegreeToRad); Assert.AreEqual( q1, q2 ); }
The above fails. A 180 degree roll should equal a 180 degree yaw and 180 pitch.
The following fail whenever I use 180 degrees for an axis.
[ Test ] [ TestCase( 0, 0, 0 ) ] [ TestCase( 20, 45, 0 ) ] [ TestCase( 45, 0, 0 ) ] [ TestCase( 0, 60, 0 ) ] [ TestCase( 0, 90, 0 ) ] [ TestCase( 0, 120, 0 ) ] [ TestCase( 0, 179, 0 ) ] [ TestCase( 0, 180, 0 ) ] [ TestCase( 0, 0, 180 ) ] public void QuaternionEulerTests( double pitch, double yaw, double roll ) { // Added comments taken from apsoe 3d documentation site: // https://reference.aspose.com/net/3d/aspose.threed.utilities.quaternion/fromeulerangle/methods/1 // Parameters // pitch // Type: System.Double // Pitch in radian // yaw // Type: System.Double // Yaw in radian // roll // Type: System.Double // Roll in radian var quaternionFromEuler = Quaternion.FromEulerAngle( pitch * DegreeToRad, yaw * DegreeToRad, roll * DegreeToRad ); // Quaternion.EulerAngles Method // Converts quaternion to rotation represented by euler angles All components are in radian var quaternionToEuler = quaternionFromEuler.EulerAngles(); // My extension method var quaternionEulerDegrees = quaternionToEuler.ToDegrees(); Assert.AreEqual( pitch * ThreeDExtensions.DegreeToRad, quaternionFromEuler.EulerAngles().x, TestTolerance ); Assert.AreEqual( yaw * ThreeDExtensions.DegreeToRad, quaternionFromEuler.EulerAngles().y, TestTolerance ); Assert.AreEqual( roll * ThreeDExtensions.DegreeToRad, quaternionFromEuler.EulerAngles().z, TestTolerance ); }
public static class ThreeDExtensions { public static Vector3 ToDegrees( this Vector3 eulerRadians ) { return new Vector3( 180 / Math.PI * eulerRadians.x, 180 / Math.PI * eulerRadians.y, 180 / Math.PI * eulerRadians.z ); } public static Vector3 ToRadians( this Vector3 eulerDegrees ) { return new Vector3( Math.PI / 180 * eulerDegrees.x, Math.PI / 180 * eulerDegrees.y, Math.PI / 180 * eulerDegrees.z ); } public const double RadToDegree = 180 / Math.PI; public const double DegreeToRad = Math.PI / 180; }