diff --git a/OpenMetaverse.Tests/TypeTests.cs b/OpenMetaverse.Tests/TypeTests.cs index fdfb63e1..a5c5be8f 100644 --- a/OpenMetaverse.Tests/TypeTests.cs +++ b/OpenMetaverse.Tests/TypeTests.cs @@ -99,6 +99,66 @@ namespace OpenMetaverse.Tests Assert.IsTrue(b.ApproxEquals(a, 0.0001f), "ApproxEquals failed (7)"); } + [Test] + public void VectorCasting() + { + Dictionary testNumbers; + testNumbers = new Dictionary(); + testNumbers["1.0"] = 1.0; + testNumbers["1.1"] = 1.1; + testNumbers["1.01"] = 1.01; + testNumbers["1.001"] = 1.001; + testNumbers["1.0001"] = 1.0001; + testNumbers["1.00001"] = 1.00001; + testNumbers["1.000001"] = 1.000001; + testNumbers["1.0000001"] = 1.0000001; + testNumbers["1.00000001"] = 1.00000001; + + foreach (KeyValuePair kvp in testNumbers) + { + double testNumber = kvp.Value; + double testNumber2 = (double)((float)testNumber); + bool noPrecisionLoss = testNumber == testNumber2; + + Vector3 a = new Vector3( + (float)testNumber, + (float)testNumber, (float)testNumber); + Vector3d b = new Vector3d(testNumber, testNumber, testNumber); + + Vector3 c = (Vector3)b; + Vector3d d = a; + + if (noPrecisionLoss) + { + Console.Error.WriteLine("Unsuitable test value used-" + + " test number should have precision loss when" + + " cast to float ({0}).", kvp.Key); + } + else + { + Assert.IsFalse(a == b, string.Format( + "Vector casting failed, precision loss should" + + " have occurred. " + + "{0}: {1}, {2}", kvp.Key, a.X, b.X)); + Assert.IsFalse(b == d, string.Format( + "Vector casting failed, explicit cast of double" + + " to float should result in precision loss" + + " whichwas should not magically disappear when" + + " Vector3 is implicitly cast to Vector3d." + + " {0}: {1}, {2}", kvp.Key, b.X, d.X)); + } + Assert.IsTrue(a == c, string.Format( + "Vector casting failed, Vector3 compared to" + + " explicit cast of Vector3d to Vector3 should" + + " result in identical precision loss." + + " {0}: {1}, {2}", kvp.Key, a.X, c.X)); + Assert.IsTrue(a == d, string.Format( + "Vector casting failed, implicit cast of Vector3" + + " to Vector3d should not result in precision loss." + + " {0}: {1}, {2}", kvp.Key, a.X, d.X)); + } + } + [Test] public void Quaternions() { diff --git a/OpenMetaverseTypes/Vector3.cs b/OpenMetaverseTypes/Vector3.cs index e702e693..da02c24e 100644 --- a/OpenMetaverseTypes/Vector3.cs +++ b/OpenMetaverseTypes/Vector3.cs @@ -566,6 +566,17 @@ namespace OpenMetaverse return Cross(value1, value2); } + /// + /// Explicit casting for Vector3d > Vector3 + /// + /// + /// + public static explicit operator Vector3(Vector3d value) + { + Vector3d foo = (Vector3d)Vector3.Zero; + return new Vector3(value); + } + #endregion Operators /// A vector with a value of 0,0,0 diff --git a/OpenMetaverseTypes/Vector3d.cs b/OpenMetaverseTypes/Vector3d.cs index 084ac3d7..12e4c938 100644 --- a/OpenMetaverseTypes/Vector3d.cs +++ b/OpenMetaverseTypes/Vector3d.cs @@ -497,6 +497,16 @@ namespace OpenMetaverse return Cross(value1, value2); } + /// + /// Implicit casting for Vector3 > Vector3d + /// + /// + /// + public static implicit operator Vector3d(Vector3 value) + { + return new Vector3d(value); + } + #endregion Operators /// A vector with a value of 0,0,0