diff --git a/src/Math/Test/VectorTest.cpp b/src/Math/Test/VectorTest.cpp index 7cc938656..1cfb76ffb 100644 --- a/src/Math/Test/VectorTest.cpp +++ b/src/Math/Test/VectorTest.cpp @@ -80,6 +80,7 @@ class VectorTest: public Corrade::TestSuite::Tester { void length(); void lengthInverted(); void normalized(); + void resized(); void sum(); void product(); @@ -126,6 +127,7 @@ VectorTest::VectorTest() { &VectorTest::length, &VectorTest::lengthInverted, &VectorTest::normalized, + &VectorTest::resized, &VectorTest::sum, &VectorTest::product, @@ -317,7 +319,15 @@ void VectorTest::lengthInverted() { } void VectorTest::normalized() { - CORRADE_COMPARE(Vector4(1.0f, 1.0f, 1.0f, 1.0f).normalized(), Vector4(0.5f, 0.5f, 0.5f, 0.5f)); + const auto vec = Vector4(1.0f, 1.0f, 1.0f, 1.0f).normalized(); + CORRADE_COMPARE(vec, Vector4(0.5f, 0.5f, 0.5f, 0.5f)); + CORRADE_COMPARE(vec.length(), 1.0f); +} + +void VectorTest::resized() { + const auto vec = Vector4(2.0f, 2.0f, 0.0f, 1.0f).resized(9.0f); + CORRADE_COMPARE(vec, Vector4(6.0f, 6.0f, 0.0f, 3.0f)); + CORRADE_COMPARE(vec.length(), 9.0f); } void VectorTest::sum() { diff --git a/src/Math/Vector.h b/src/Math/Vector.h index d20861288..6e6a55c40 100644 --- a/src/Math/Vector.h +++ b/src/Math/Vector.h @@ -455,7 +455,7 @@ template class Vector { * values. @f[ * |\boldsymbol a| = \sqrt{\boldsymbol a \cdot \boldsymbol a} * @f] - * @see lengthInverted(), Math::sqrt(), normalized() + * @see lengthInverted(), Math::sqrt(), normalized(), resized() * @todo something like std::hypot() for possibly better precision? */ inline T length() const { @@ -468,7 +468,7 @@ template class Vector { * @f[ * \frac{1}{|\boldsymbol a|} = \frac{1}{\sqrt{\boldsymbol a \cdot \boldsymbol a}} * @f] - * @see length(), Math::sqrtInverted(), normalized() + * @see length(), Math::sqrtInverted(), normalized(), resized() */ inline T lengthInverted() const { return T(1)/length(); @@ -477,12 +477,27 @@ template class Vector { /** * @brief Normalized vector (of unit length) * - * @see isNormalized() + * @see isNormalized(), lengthInverted(), resized() */ inline Vector normalized() const { return *this*lengthInverted(); } + /** + * @brief Resized vector + * + * Convenience equivalent to the following code. Due to operation order + * this function is faster than the obvious way of sizing normalized() + * vector. + * @code + * vec*(vec.lengthInverted()*length) // the brackets are important + * @endcode + * @see normalized() + */ + inline Vector resized(T length) const { + return *this*(lengthInverted()*length); + } + /** * @brief %Vector projected onto line * @@ -701,7 +716,12 @@ extern template Corrade::Utility::Debug MAGNUM_EXPORT operator<<(Corrade::Utilit return Math::Vector::operator/(other); \ } \ \ - inline Type normalized() const { return Math::Vector::normalized(); } \ + inline Type normalized() const { \ + return Math::Vector::normalized(); \ + } \ + inline Type resized(T length) const { \ + return Math::Vector::resized(length); \ + } \ inline Type projected(const Math::Vector& other) const { \ return Math::Vector::projected(other); \ }