From 7f6f81afc754db5f3ea6e9ff1a0b903a09fb9db8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vladim=C3=ADr=20Vondru=C5=A1?= Date: Wed, 23 May 2012 00:18:33 +0200 Subject: [PATCH] Math::Constants are now inline functions instead of static variables. Static variables were compiled into the library and then linked on every use, which was not good for performance. --- src/Math/Geometry/Test/DistanceTest.cpp | 12 ++++++------ src/Math/Math.h | 26 ++++++++++++++----------- src/Math/Test/MathTest.cpp | 6 +++--- src/Physics/Capsule.cpp | 2 +- src/Physics/Sphere.cpp | 2 +- src/Physics/Test/CapsuleTest.cpp | 4 ++-- src/Physics/Test/PlaneTest.cpp | 6 +++--- src/Physics/Test/SphereTest.cpp | 4 ++-- src/Primitives/Capsule.cpp | 6 +++--- src/Primitives/UVSphere.cpp | 4 ++-- 10 files changed, 38 insertions(+), 34 deletions(-) diff --git a/src/Math/Geometry/Test/DistanceTest.cpp b/src/Math/Geometry/Test/DistanceTest.cpp index 5fff7db48..b0738d7df 100644 --- a/src/Math/Geometry/Test/DistanceTest.cpp +++ b/src/Math/Geometry/Test/DistanceTest.cpp @@ -38,9 +38,9 @@ void DistanceTest::linePoint() { /* The distance should be the same for all equidistant points */ QCOMPARE((Distance::linePoint(a, b, Vector3(1.0f, 0.0f, 1.0f))), - Constants::Sqrt2/Constants::Sqrt3); + Constants::sqrt2()/Constants::sqrt3()); QCOMPARE((Distance::linePoint(a, b, Vector3(1.0f, 0.0f, 1.0f)+Vector3(100.0f))), - Constants::Sqrt2/Constants::Sqrt3); + Constants::sqrt2()/Constants::sqrt3()); } void DistanceTest::lineSegmentPoint() { @@ -51,20 +51,20 @@ void DistanceTest::lineSegmentPoint() { QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(0.25f))), 0.0f); /* Point on the line, outside the segment, closer to A */ - QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(-1.0f))), +Constants::Sqrt3); + QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(-1.0f))), +Constants::sqrt3()); /* Point on the line, outside the segment, closer to B */ - QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(1.0f+1.0f/Constants::Sqrt3))), 1.0f); + QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(1.0f+1.0f/Constants::sqrt3()))), 1.0f); /* Point next to the line segment */ QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(1.0f, 0.0f, 1.0f))), - Constants::Sqrt2/Constants::Sqrt3); + Constants::sqrt2()/Constants::sqrt3()); /* Point outside the line segment, closer to A */ QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(1.0f, 0.0f, 1.0f)-Vector3(1.0f))), 1.0f); /* Point outside the line segment, closer to B */ - QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(1.0f, 0.0f, 1.0f)+Vector3(1.0f))), +Constants::Sqrt2); + QCOMPARE((Distance::lineSegmentPoint(a, b, Vector3(1.0f, 0.0f, 1.0f)+Vector3(1.0f))), +Constants::sqrt2()); } }}}} diff --git a/src/Math/Math.h b/src/Math/Math.h index 7bb42119b..d1b7e830a 100644 --- a/src/Math/Math.h +++ b/src/Math/Math.h @@ -32,25 +32,29 @@ namespace Magnum { namespace Math { matrices) */ -/** @brief Numeric constants */ +/** +@brief Numeric constants + +@internal See MathTypeTraits class for implementation notes. +*/ template struct Constants { #ifdef DOXYGEN_GENERATING_OUTPUT - static constexpr T Pi; /**< @brief Pi */ - static constexpr T Sqrt2; /**< @brief Square root of 2 */ - static constexpr T Sqrt3; /**< @brief Square root of 3 */ + static inline constexpr T pi(); /**< @brief Pi */ + static inline constexpr T sqrt2(); /**< @brief Square root of 2 */ + static inline constexpr T sqrt3(); /**< @brief Square root of 3 */ #endif }; #ifndef DOXYGEN_GENERATING_OUTPUT template<> struct Constants { - static constexpr double Pi = 3.14159265359; - static constexpr double Sqrt2 = 1.41421356237; - static constexpr double Sqrt3 = 1.73205080757; + static inline constexpr double pi() { return 3.14159265359; } + static inline constexpr double sqrt2() { return 1.41421356237; } + static inline constexpr double sqrt3() { return 1.73205080757; } }; template<> struct Constants { - static constexpr float Pi = 3.14159265359f; - static constexpr float Sqrt2 = 1.41421356237f; - static constexpr float Sqrt3 = 1.73205080757f; + static inline constexpr float pi() { return 3.14159265359f; } + static inline constexpr float sqrt2() { return 1.41421356237f; } + static inline constexpr float sqrt3() { return 1.73205080757f; } }; namespace Implementation { @@ -87,7 +91,7 @@ size_t MAGNUM_EXPORT log(size_t base, size_t number); * Function to make angle entering less error-prone. Converts the value to * radians at compile time. For example `deg(180.0f)` is converted to `3.14f`. */ -template inline constexpr T deg(T value) { return value*Constants::Pi/180; } +template inline constexpr T deg(T value) { return value*Constants::pi()/180; } /** * @brief Angle in radians diff --git a/src/Math/Test/MathTest.cpp b/src/Math/Test/MathTest.cpp index eb823548c..4626b0673 100644 --- a/src/Math/Test/MathTest.cpp +++ b/src/Math/Test/MathTest.cpp @@ -24,9 +24,9 @@ QTEST_APPLESS_MAIN(Magnum::Math::Test::MathTest) namespace Magnum { namespace Math { namespace Test { void MathTest::degrad() { - QCOMPARE(deg(90.0), Constants::Pi/2); - QCOMPARE(deg(90.0f), Constants::Pi/2); - QCOMPARE(rad(Constants::Pi/2), Constants::Pi/2); + QCOMPARE(deg(90.0), Constants::pi()/2); + QCOMPARE(deg(90.0f), Constants::pi()/2); + QCOMPARE(rad(Constants::pi()/2), Constants::pi()/2); } void MathTest::pow() { diff --git a/src/Physics/Capsule.cpp b/src/Physics/Capsule.cpp index f6262222b..7c40dc206 100644 --- a/src/Physics/Capsule.cpp +++ b/src/Physics/Capsule.cpp @@ -24,7 +24,7 @@ namespace Magnum { namespace Physics { void Capsule::applyTransformation(const Matrix4& transformation) { _transformedA = (transformation*Vector4(_a)).xyz(); _transformedB = (transformation*Vector4(_b)).xyz(); - float scaling = (transformation.rotationScaling()*Vector3(1/Math::Constants::Sqrt3)).length(); + float scaling = (transformation.rotationScaling()*Vector3(1/Math::Constants::sqrt3())).length(); _transformedRadius = scaling*_radius; } diff --git a/src/Physics/Sphere.cpp b/src/Physics/Sphere.cpp index 106ff3c22..ac9ed700d 100644 --- a/src/Physics/Sphere.cpp +++ b/src/Physics/Sphere.cpp @@ -23,7 +23,7 @@ namespace Magnum { namespace Physics { void Sphere::applyTransformation(const Matrix4& transformation) { _transformedPosition = (transformation*Vector4(_position)).xyz(); - float scaling = (transformation.rotationScaling()*Vector3(1/Math::Constants::Sqrt3)).length(); + float scaling = (transformation.rotationScaling()*Vector3(1/Math::Constants::sqrt3())).length(); _transformedRadius = scaling*_radius; } diff --git a/src/Physics/Test/CapsuleTest.cpp b/src/Physics/Test/CapsuleTest.cpp index b1a39ac59..7b903e1fa 100644 --- a/src/Physics/Test/CapsuleTest.cpp +++ b/src/Physics/Test/CapsuleTest.cpp @@ -32,8 +32,8 @@ void CapsuleTest::applyTransformation() { QCOMPARE(capsule.radius(), 7.0f); /* Apply average scaling to radius */ - capsule.applyTransformation(Matrix4::scaling({Math::Constants::Sqrt3, -Math::Constants::Sqrt2, 2.0f})); - QCOMPARE(capsule.transformedRadius(), Math::Constants::Sqrt3*7.0f); + capsule.applyTransformation(Matrix4::scaling({Math::Constants::sqrt3(), -Math::Constants::sqrt2(), 2.0f})); + QCOMPARE(capsule.transformedRadius(), Math::Constants::sqrt3()*7.0f); } void CapsuleTest::collisionPoint() { diff --git a/src/Physics/Test/PlaneTest.cpp b/src/Physics/Test/PlaneTest.cpp index 4f3712427..f5ebf3952 100644 --- a/src/Physics/Test/PlaneTest.cpp +++ b/src/Physics/Test/PlaneTest.cpp @@ -24,16 +24,16 @@ QTEST_APPLESS_MAIN(Magnum::Physics::Test::PlaneTest) namespace Magnum { namespace Physics { namespace Test { void PlaneTest::applyTransformation() { - Physics::Plane plane({1.0f, 2.0f, 3.0f}, {Math::Constants::Sqrt2, -Math::Constants::Sqrt2, 0}); + Physics::Plane plane({1.0f, 2.0f, 3.0f}, {Math::Constants::sqrt2(), -Math::Constants::sqrt2(), 0}); plane.applyTransformation(Matrix4::rotation(deg(90.0f), Vector3::xAxis())); QVERIFY(plane.transformedPosition() == Vector3(1.0f, -3.0f, 2.0f)); - QVERIFY(plane.transformedNormal() == Vector3(Math::Constants::Sqrt2, 0, -Math::Constants::Sqrt2)); + QVERIFY(plane.transformedNormal() == Vector3(Math::Constants::sqrt2(), 0, -Math::Constants::sqrt2())); /* The normal should stay normalized */ plane.applyTransformation(Matrix4::scaling({1.5f, 2.0f, 3.0f})); QVERIFY(plane.transformedPosition() == Vector3(1.5f, 4.0f, 9.0f)); - QVERIFY(plane.transformedNormal() == Vector3(Math::Constants::Sqrt2, -Math::Constants::Sqrt2, 0)); + QVERIFY(plane.transformedNormal() == Vector3(Math::Constants::sqrt2(), -Math::Constants::sqrt2(), 0)); } void PlaneTest::collisionLine() { diff --git a/src/Physics/Test/SphereTest.cpp b/src/Physics/Test/SphereTest.cpp index 77bb70d6c..f0c9944b0 100644 --- a/src/Physics/Test/SphereTest.cpp +++ b/src/Physics/Test/SphereTest.cpp @@ -37,8 +37,8 @@ void SphereTest::applyTransformation() { QCOMPARE(sphere.transformedRadius(), 14.0f); /* Apply average scaling to radius */ - sphere.applyTransformation(Matrix4::scaling({Math::Constants::Sqrt3, -Math::Constants::Sqrt2, 2.0f})); - QCOMPARE(sphere.transformedRadius(), Math::Constants::Sqrt3*7.0f); + sphere.applyTransformation(Matrix4::scaling({Math::Constants::sqrt3(), -Math::Constants::sqrt2(), 2.0f})); + QCOMPARE(sphere.transformedRadius(), Math::Constants::sqrt3()*7.0f); } void SphereTest::collisionPoint() { diff --git a/src/Primitives/Capsule.cpp b/src/Primitives/Capsule.cpp index 98534e598..66d1bb00c 100644 --- a/src/Primitives/Capsule.cpp +++ b/src/Primitives/Capsule.cpp @@ -24,13 +24,13 @@ Capsule::Capsule(unsigned int rings, unsigned int segments, GLfloat length, Text GLfloat height = 2.0f+length; GLfloat textureCoordsVIncrement = 1.0f/(rings*height); - GLfloat ringAngleIncrement = Math::Constants::Pi/(2*rings); + GLfloat ringAngleIncrement = Math::Constants::pi()/(2*rings); /* Bottom cap vertex */ capVertex(-height/2, -1.0f, 0.0f); /* Rings of bottom hemisphere */ - vertexRings(rings, -length/2, -Math::Constants::Pi/2+ringAngleIncrement, ringAngleIncrement, textureCoordsVIncrement, textureCoordsVIncrement); + vertexRings(rings, -length/2, -Math::Constants::pi()/2+ringAngleIncrement, ringAngleIncrement, textureCoordsVIncrement, textureCoordsVIncrement); /* Rings of top hemisphere */ vertexRings(rings, length/2, 0.0f, ringAngleIncrement, (1.0f + length)/height, textureCoordsVIncrement); @@ -53,7 +53,7 @@ void Capsule::capVertex(GLfloat y, GLfloat normalY, GLfloat textureCoordsV) { } void Capsule::vertexRings(unsigned int count, GLfloat centerY, GLfloat startRingAngle, GLfloat ringAngleIncrement, GLfloat startTextureCoordsV, GLfloat textureCoordsVIncrement) { - GLfloat segmentAngleIncrement = 2*Math::Constants::Pi/segments; + GLfloat segmentAngleIncrement = 2*Math::Constants::pi()/segments; GLfloat x, y, z; for(unsigned int i = 0; i != count; ++i) { GLfloat ringAngle = startRingAngle + i*ringAngleIncrement; diff --git a/src/Primitives/UVSphere.cpp b/src/Primitives/UVSphere.cpp index 825c758e8..9fe9e5227 100644 --- a/src/Primitives/UVSphere.cpp +++ b/src/Primitives/UVSphere.cpp @@ -24,13 +24,13 @@ UVSphere::UVSphere(unsigned int rings, unsigned int segments, TextureCoords text CORRADE_ASSERT(rings >= 2 && segments >= 3, "UVSphere must have at least two rings and three segments", ) GLfloat textureCoordsVIncrement = 1.0f/rings; - GLfloat ringAngleIncrement = Math::Constants::Pi/rings; + GLfloat ringAngleIncrement = Math::Constants::pi()/rings; /* Bottom cap vertex */ capVertex(-1.0f, -1.0f, 0.0f); /* Vertex rings */ - vertexRings(rings-1, 0.0f, -Math::Constants::Pi/2+ringAngleIncrement, ringAngleIncrement, textureCoordsVIncrement, textureCoordsVIncrement); + vertexRings(rings-1, 0.0f, -Math::Constants::pi()/2+ringAngleIncrement, ringAngleIncrement, textureCoordsVIncrement, textureCoordsVIncrement); /* Top cap vertex */ capVertex(1.0f, 1.0f, 1.0f);