From a64882191288d92f0bda66023e807b680465a093 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vladim=C3=ADr=20Vondru=C5=A1?= Date: Sun, 9 Nov 2014 21:39:44 +0100 Subject: [PATCH] SceneGraph: deprecating TransformationType enum and related functions. The enum was only two-state, in almost all cases it included unnecessary branching and the non-default usage was too verbose, thus all transformation functions were split into two variants, () and Local(). The () behaves exactly like the previous implementation with TransformationType::Global, the Local() behaves like the previous implementation with TransformationType::Local. The enum and original functions were kept, they are marked as deprecated and will be removed in future release. This is rather large changeset, I triple checked that the new (both deprecated and non-deprecated) implementations work as intended, but can't possibly test every possible use case, so I'm sorry if I messed something up :-) Also there was probably some bug in internal virtual function implementations before, it should be now fixed. --- .../SceneGraph/AbstractTransformation.h | 10 +- src/Magnum/SceneGraph/AbstractTranslation.h | 48 ++- .../AbstractTranslationRotation2D.h | 49 ++- .../AbstractTranslationRotation3D.h | 188 ++++++++++-- .../AbstractTranslationRotationScaling2D.h | 61 +++- .../AbstractTranslationRotationScaling3D.h | 98 +++++- .../SceneGraph/DualComplexTransformation.h | 115 +++++-- .../SceneGraph/DualQuaternionTransformation.h | 151 ++++++++-- .../SceneGraph/MatrixTransformation2D.h | 175 +++++++++-- .../SceneGraph/MatrixTransformation3D.h | 283 +++++++++++++++--- .../SceneGraph/RigidMatrixTransformation2D.h | 145 +++++++-- .../SceneGraph/RigidMatrixTransformation3D.h | 261 ++++++++++++---- src/Magnum/SceneGraph/SceneGraph.h | 2 + .../Test/DualComplexTransformationTest.cpp | 6 +- .../Test/DualQuaternionTransformationTest.cpp | 12 +- .../Test/MatrixTransformation2DTest.cpp | 10 +- .../Test/MatrixTransformation3DTest.cpp | 16 +- .../Test/RigidMatrixTransformation2DTest.cpp | 8 +- .../Test/RigidMatrixTransformation3DTest.cpp | 14 +- .../SceneGraph/TranslationTransformation.h | 39 ++- 20 files changed, 1403 insertions(+), 288 deletions(-) diff --git a/src/Magnum/SceneGraph/AbstractTransformation.h b/src/Magnum/SceneGraph/AbstractTransformation.h index 110eb37ff..d494b5259 100644 --- a/src/Magnum/SceneGraph/AbstractTransformation.h +++ b/src/Magnum/SceneGraph/AbstractTransformation.h @@ -29,6 +29,8 @@ * @brief Class @ref Magnum::SceneGraph::AbstractTransformation, alias @ref Magnum::SceneGraph::AbstractBasicTransformation2D, @ref Magnum::SceneGraph::AbstractBasicTransformation3D, typedef @ref Magnum::SceneGraph::AbstractTransformation2D, @ref Magnum::SceneGraph::AbstractTransformation3D, enum @ref Magnum::SceneGraph::TransformationType */ +#include + #include "Magnum/SceneGraph/SceneGraph.h" #include "Magnum/SceneGraph/visibility.h" @@ -85,18 +87,20 @@ template class AbstractTransformation { virtual void doResetTransformation() = 0; }; +#ifdef MAGNUM_BUILD_DEPRECATED /** @brief Transformation type - -@todo Get rid of this in favor of separate function for each type (less branching) +@deprecated Use `*Transformation*::*()` and `*Transformation::*Local*()` + overloads instead. */ -enum class TransformationType: UnsignedByte { +enum class TransformationType: UnsignedByte CORRADE_DEPRECATED("use *() and *Local() overloads instead") { /** Global transformation, applied after all other transformations. */ Global = 0x00, /** Local transformation, applied before all other transformations. */ Local = 0x01 }; +#endif /** @brief Base transformation for two-dimensional scenes diff --git a/src/Magnum/SceneGraph/AbstractTranslation.h b/src/Magnum/SceneGraph/AbstractTranslation.h index d50b232db..dbf2c3c95 100644 --- a/src/Magnum/SceneGraph/AbstractTranslation.h +++ b/src/Magnum/SceneGraph/AbstractTranslation.h @@ -57,19 +57,48 @@ class AbstractTranslation: public AbstractTransformation { /** * @brief Translate object - * @param vector Translation vector - * @param type Transformation type * @return Reference to self (for method chaining) * - * @see @ref Math::Vector2::xAxis(), @ref Math::Vector2::yAxis(), - * @ref Math::Vector3::xAxis(), @ref Math::Vector3::yAxis(), - * @ref Math::Vector3::zAxis() + * @see @ref translateLocal(), @ref Math::Vector2::xAxis(), + * @ref Math::Vector2::yAxis(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() */ - AbstractTranslation& translate(const VectorTypeFor& vector, TransformationType type = TransformationType::Global) { - doTranslate(vector, type); + AbstractTranslation& translate(const VectorTypeFor& vector) { + doTranslate(vector); return *this; } + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + AbstractTranslation& translateLocal(const VectorTypeFor& vector) { + doTranslateLocal(vector); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslation::translate() "translate()" + * or @ref Magnum::SceneGraph::AbstractTranslation::translateLocal() "translateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use translate() or translateLocal() instead") AbstractTranslation& translate(const VectorTypeFor& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); + } + #endif + + /* Overloads to remove WTF-factor from method chaining order */ + #ifndef DOXYGEN_GENERATING_OUTPUT + AbstractTranslation& resetTransformation() { + AbstractTransformation::resetTransformation(); + return *this; + } + #endif + protected: ~AbstractTranslation() = default; @@ -79,7 +108,10 @@ class AbstractTranslation: public AbstractTransformation { private: #endif /** @brief Polymorphic implementation for @ref translate() */ - virtual void doTranslate(const VectorTypeFor& vector, TransformationType type) = 0; + virtual void doTranslate(const VectorTypeFor& vector) = 0; + + /** @brief Polymorphic implementation for @ref translateLocal() */ + virtual void doTranslateLocal(const VectorTypeFor& vector) = 0; }; /** diff --git a/src/Magnum/SceneGraph/AbstractTranslationRotation2D.h b/src/Magnum/SceneGraph/AbstractTranslationRotation2D.h index bdd8a56bf..2ab7806c7 100644 --- a/src/Magnum/SceneGraph/AbstractTranslationRotation2D.h +++ b/src/Magnum/SceneGraph/AbstractTranslationRotation2D.h @@ -47,20 +47,58 @@ template class AbstractBasicTranslationRotation2D: public AbstractBasic /** * @brief Rotate object * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) + * + * @see @ref rotateLocal() */ - AbstractBasicTranslationRotation2D& rotate(Math::Rad angle, TransformationType type = TransformationType::Global) { - doRotate(angle, type); + AbstractBasicTranslationRotation2D& rotate(Math::Rad angle) { + doRotate(angle); return *this; } + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + AbstractBasicTranslationRotation2D& rotateLocal(Math::Rad angle) { + doRotateLocal(angle); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotation2D::rotate() "rotate()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotation2D::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") AbstractBasicTranslationRotation2D& rotate(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotate(angle, type) : rotateLocal(angle, type); + } + #endif + /* Overloads to remove WTF-factor from method chaining order */ #ifndef DOXYGEN_GENERATING_OUTPUT AbstractBasicTranslationRotation2D& resetTransformation() { AbstractBasicTranslation2D::resetTransformation(); return *this; } + AbstractBasicTranslationRotation2D& translate(const Math::Vector2& vector) { + AbstractBasicTranslation2D::translate(vector); + return *this; + } + AbstractBasicTranslationRotation2D& translateLocal(const Math::Vector2& vector) { + AbstractBasicTranslation2D::translateLocal(vector); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use translate() or translateLocal() instead") AbstractBasicTranslationRotation2D& translate(const Math::Vector2& vector, TransformationType type) { + AbstractBasicTranslation2D::translate(vector, type); + return *this; + } + #endif #endif protected: @@ -72,7 +110,10 @@ template class AbstractBasicTranslationRotation2D: public AbstractBasic private: #endif /** @brief Polymorphic implementation for @ref rotate() */ - virtual void doRotate(Math::Rad angle, TransformationType type) = 0; + virtual void doRotate(Math::Rad angle) = 0; + + /** @brief Polymorphic implementation for @ref rotateLocal() */ + virtual void doRotateLocal(Math::Rad angle) = 0; }; /** diff --git a/src/Magnum/SceneGraph/AbstractTranslationRotation3D.h b/src/Magnum/SceneGraph/AbstractTranslationRotation3D.h index f64ca9f12..9edefba74 100644 --- a/src/Magnum/SceneGraph/AbstractTranslationRotation3D.h +++ b/src/Magnum/SceneGraph/AbstractTranslationRotation3D.h @@ -49,69 +49,180 @@ template class AbstractBasicTranslationRotation3D: public AbstractBasic * @brief Rotate object * @param angle Angle (counterclockwise) * @param normalizedAxis Normalized rotation axis - * @param type Transformation type * @return Reference to self (for method chaining) * - * @see @ref rotateX(), @ref rotateY(), @ref rotateZ(), - * @ref Math::Vector3::xAxis(), @ref Math::Vector3::yAxis(), - * @ref Math::Vector3::zAxis() + * @see @ref rotateLocal(), @ref rotateX(), @ref rotateY(), + * @ref rotateZ(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() */ - AbstractBasicTranslationRotation3D& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type = TransformationType::Global) { - doRotate(angle, normalizedAxis, type); + AbstractBasicTranslationRotation3D& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis) { + doRotate(angle, normalizedAxis); return *this; } + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + AbstractBasicTranslationRotation3D& rotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) { + doRotateLocal(angle, normalizedAxis); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotate() "rotate()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") AbstractBasicTranslationRotation3D& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) { + return type == TransformationType::Global ? rotate(angle, normalizedAxis) : rotateLocal(angle, normalizedAxis); + } + #endif + /** * @brief Rotate object around X axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * In some implementations faster than calling * `rotate(angle, Vector3::xAxis())`, see subclasses for more * information. + * @see @ref rotateXLocal() */ - AbstractBasicTranslationRotation3D& rotateX(Math::Rad angle, TransformationType type = TransformationType::Global) { - doRotateX(angle, type); + AbstractBasicTranslationRotation3D& rotateX(Math::Rad angle) { + doRotateX(angle); return *this; } + /** + * @brief Rotate object around X axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. In some implementations faster than calling + * `rotateLocal(angle, Vector3::xAxis())`, see subclasses for more + * information. + */ + AbstractBasicTranslationRotation3D& rotateXLocal(Math::Rad angle) { + doRotateXLocal(angle); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateX() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateX() "rotateX()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateXLocal() "rotateXLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateX() or rotateXLocal() instead") AbstractBasicTranslationRotation3D& rotateX(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateX(angle) : rotateXLocal(angle); + } + #endif + /** * @brief Rotate object around Y axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * In some implementations faster than calling * `rotate(angle, Vector3::yAxis())`, see subclasses for more * information. + * @see @ref rotateYLocal() + */ + AbstractBasicTranslationRotation3D& rotateY(Math::Rad angle) { + doRotateY(angle); + return *this; + } + + /** + * @brief Rotate object around Y axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. In some implementations faster than calling + * `rotateLocal(angle, Vector3::yAxis())`, see subclasses for more + * information. */ - AbstractBasicTranslationRotation3D& rotateY(Math::Rad angle, TransformationType type = TransformationType::Global) { - doRotateX(angle, type); + AbstractBasicTranslationRotation3D& rotateYLocal(Math::Rad angle) { + doRotateY(angle); return *this; } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief roateY() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateY() "rotateY()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateYLocal() "rotateYLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateY() or rotateYLocal() instead") AbstractBasicTranslationRotation3D& rotateY(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateY(angle) : rotateYLocal(angle); + } + #endif + /** * @brief Rotate object around Z axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * In some implementations faster than calling * `rotate(angle, Vector3::zAxis())`, see subclasses for more * information. + * @see @ref rotateZLocal() */ - AbstractBasicTranslationRotation3D& rotateZ(Math::Rad angle, TransformationType type = TransformationType::Global) { - doRotateZ(angle, type); + AbstractBasicTranslationRotation3D& rotateZ(Math::Rad angle) { + doRotateZ(angle); return *this; } + /** + * @brief Rotate object around Z axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. In some implementations faster than calling + * `rotateLocal(angle, Vector3::zAxis())`, see subclasses for more + * information. + */ + AbstractBasicTranslationRotation3D& rotateZLocal(Math::Rad angle) { + doRotateZLocal(angle); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateZ() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateZ() "rotateZ()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotation3D::rotateZLocal() "rotateZLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateZ() or rotateZLocal() instead") AbstractBasicTranslationRotation3D& rotateZ(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateZ(angle) : rotateZLocal(); + } + #endif + /* Overloads to remove WTF-factor from method chaining order */ #ifndef DOXYGEN_GENERATING_OUTPUT AbstractBasicTranslationRotation3D& resetTransformation() { AbstractBasicTranslation3D::resetTransformation(); return *this; } + AbstractBasicTranslationRotation3D& translate(const Math::Vector3& vector) { + AbstractBasicTranslation3D::translate(vector); + return *this; + } + AbstractBasicTranslationRotation3D& translateLocal(const Math::Vector3& vector) { + AbstractBasicTranslation3D::translateLocal(vector); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use translate() or translateLocal() instead") AbstractBasicTranslationRotation3D& translate(const Math::Vector2& vector, TransformationType type) { + AbstractBasicTranslation3D::translate(vector, type); + return *this; + } + #endif #endif protected: @@ -123,7 +234,10 @@ template class AbstractBasicTranslationRotation3D: public AbstractBasic private: #endif /** @brief Polymorphic implementation for @ref rotate() */ - virtual void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) = 0; + virtual void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis) = 0; + + /** @brief Polymorphic implementation for @ref rotateLocal() */ + virtual void doRotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) = 0; /** * @brief Polymorphic implementation for @ref rotateX() @@ -131,8 +245,18 @@ template class AbstractBasicTranslationRotation3D: public AbstractBasic * Default implementation calls @ref rotate() with * @ref Math::Vector3::xAxis(). */ - virtual void doRotateX(Math::Rad angle, TransformationType type) { - rotate(angle, Math::Vector3::xAxis(), type); + virtual void doRotateX(Math::Rad angle) { + rotate(angle, Math::Vector3::xAxis()); + } + + /** + * @brief Polymorphic implementation for @ref rotateXLocal() + * + * Default implementation calls @ref rotateLocal() with + * @ref Math::Vector3::xAxis(). + */ + virtual void doRotateXLocal(Math::Rad angle) { + rotateLocal(angle, Math::Vector3::xAxis()); } /** @@ -141,8 +265,18 @@ template class AbstractBasicTranslationRotation3D: public AbstractBasic * Default implementation calls @ref rotate() with * @ref Math::Vector3::yAxis(). */ - virtual void doRotateY(Math::Rad angle, TransformationType type) { - rotate(angle, Math::Vector3::yAxis(), type); + virtual void doRotateY(Math::Rad angle) { + rotate(angle, Math::Vector3::yAxis()); + } + + /** + * @brief Polymorphic implementation for @ref rotateYLocal() + * + * Default implementation calls @ref rotateLocal() with + * @ref Math::Vector3::yAxis(). + */ + virtual void doRotateYLocal(Math::Rad angle) { + rotateLocal(angle, Math::Vector3::yAxis()); } /** @@ -151,8 +285,18 @@ template class AbstractBasicTranslationRotation3D: public AbstractBasic * Default implementation calls @ref rotate() with * @ref Math::Vector3::zAxis(). */ - virtual void doRotateZ(Math::Rad angle, TransformationType type) { - rotate(angle, Math::Vector3::zAxis(), type); + virtual void doRotateZ(Math::Rad angle) { + rotate(angle, Math::Vector3::zAxis()); + } + + /** + * @brief Polymorphic implementation for @ref rotateZLocal() + * + * Default implementation calls @ref rotateLocal() with + * @ref Math::Vector3::zAxis(). + */ + virtual void doRotateZLocal(Math::Rad angle) { + rotateLocal(angle, Math::Vector3::zAxis()); } }; diff --git a/src/Magnum/SceneGraph/AbstractTranslationRotationScaling2D.h b/src/Magnum/SceneGraph/AbstractTranslationRotationScaling2D.h index 38d3022db..4315273af 100644 --- a/src/Magnum/SceneGraph/AbstractTranslationRotationScaling2D.h +++ b/src/Magnum/SceneGraph/AbstractTranslationRotationScaling2D.h @@ -46,32 +46,74 @@ template class AbstractBasicTranslationRotationScaling2D: public Abstra /** * @brief Scale object - * @param vector Scaling vector - * @param type Transformation type * @return Reference to self (for method chaining) * - * @see @ref Math::Vector2::xScale(), @ref Math::Vector2::yScale() + * @see @ref scaleLocal(), @ref Math::Vector2::xScale(), + * @ref Math::Vector2::yScale() */ - AbstractBasicTranslationRotationScaling2D& scale(const Math::Vector2& vector, TransformationType type = TransformationType::Global) { - doScale(vector, type); + AbstractBasicTranslationRotationScaling2D& scale(const Math::Vector2& vector) { + doScale(vector); return *this; } + /** + * @brief Scale object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + AbstractBasicTranslationRotationScaling2D& scaleLocal(const Math::Vector2& vector) { + doScaleLocal(vector); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief scale() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotationScaling2D::scale() "scale()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotationScaling2D::scaleLocal() "scaleLocal()" + * instead. + */ + CORRADE_DEPRECATED("use scale() or scaleLocal() instead") AbstractBasicTranslationRotationScaling2D& scale(const Math::Vector2& vector, TransformationType type) { + return type == TransformationType::Global ? scale(vector) : scaleLocal(vector); + } + #endif + /* Overloads to remove WTF-factor from method chaining order */ #ifndef DOXYGEN_GENERATING_OUTPUT AbstractBasicTranslationRotationScaling2D& resetTransformation() { AbstractBasicTranslationRotation2D::resetTransformation(); return *this; } - AbstractBasicTranslationRotationScaling2D& translate(const Math::Vector2& vector, TransformationType type = TransformationType::Global) { + AbstractBasicTranslationRotationScaling2D& translate(const Math::Vector2& vector) { + AbstractBasicTranslationRotation2D::translate(vector); + return *this; + } + AbstractBasicTranslationRotationScaling2D& translateLocal(const Math::Vector2& vector) { + AbstractBasicTranslationRotation2D::translateLocal(vector); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use translate() or translateLocal() instead") AbstractBasicTranslationRotationScaling2D& translate(const Math::Vector2& vector, TransformationType type) { AbstractBasicTranslationRotation2D::translate(vector, type); return *this; } - AbstractBasicTranslationRotationScaling2D& rotate(Math::Rad angle, TransformationType type = TransformationType::Global) { + #endif + AbstractBasicTranslationRotationScaling2D& rotate(Math::Rad angle) { + AbstractBasicTranslationRotation2D::rotate(angle); + return *this; + } + AbstractBasicTranslationRotationScaling2D& rotateLocal(Math::Rad angle) { + AbstractBasicTranslationRotation2D::rotateLocal(angle); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") AbstractBasicTranslationRotationScaling2D& rotate(Math::Rad angle, TransformationType type) { AbstractBasicTranslationRotation2D::rotate(angle, type); return *this; } #endif + #endif protected: ~AbstractBasicTranslationRotationScaling2D() = default; @@ -82,7 +124,10 @@ template class AbstractBasicTranslationRotationScaling2D: public Abstra private: #endif /** @brief Polymorphic implementation for @ref scale() */ - virtual void doScale(const Math::Vector2& vector, TransformationType type) = 0; + virtual void doScale(const Math::Vector2& vector) = 0; + + /** @brief Polymorphic implementation for @ref scaleLocal() */ + virtual void doScaleLocal(const Math::Vector2& vector) = 0; }; /** diff --git a/src/Magnum/SceneGraph/AbstractTranslationRotationScaling3D.h b/src/Magnum/SceneGraph/AbstractTranslationRotationScaling3D.h index f87c1167d..73e2f59b7 100644 --- a/src/Magnum/SceneGraph/AbstractTranslationRotationScaling3D.h +++ b/src/Magnum/SceneGraph/AbstractTranslationRotationScaling3D.h @@ -46,45 +46,116 @@ template class AbstractBasicTranslationRotationScaling3D: public Abstra /** * @brief Scale object - * @param vector Scaling vector - * @param type Transformation type * @return Reference to self (for method chaining) * - * @see @ref Math::Vector3::xScale(), @ref Math::Vector3::yScale(), - * @ref Math::Vector3::zScale() + * @see @ref scaleLocal(), @ref Math::Vector3::xScale(), + * @ref Math::Vector3::yScale(), @ref Math::Vector3::zScale() */ - AbstractBasicTranslationRotationScaling3D& scale(const Math::Vector3& vector, TransformationType type = TransformationType::Global) { - doScale(vector, type); + AbstractBasicTranslationRotationScaling3D& scale(const Math::Vector3& vector) { + doScale(vector); return *this; } + /** + * @brief Scale object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + AbstractBasicTranslationRotationScaling3D& scaleLocal(const Math::Vector3& vector) { + doScaleLocal(vector); + return *this; + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief scale() + * @deprecated Use @ref Magnum::SceneGraph::AbstractTranslationRotationScaling3D::scale() "scale()" + * or @ref Magnum::SceneGraph::AbstractTranslationRotationScaling3D::scaleLocal() "scaleLocal()" + * instead. + */ + CORRADE_DEPRECATED("use scale() or scaleLocal() instead") AbstractBasicTranslationRotationScaling3D& scale(const Math::Vector3& vector, TransformationType type) { + return type == TransformationType::Global ? scale(vector) : scaleLocal(vector); + } + #endif + /* Overloads to remove WTF-factor from method chaining order */ #ifndef DOXYGEN_GENERATING_OUTPUT AbstractBasicTranslationRotationScaling3D& resetTransformation() { AbstractBasicTranslationRotation3D::resetTransformation(); return *this; } - AbstractBasicTranslationRotationScaling3D& translate(const Math::Vector3& vector, TransformationType type = TransformationType::Global) { + AbstractBasicTranslationRotationScaling3D& translate(const Math::Vector3& vector) { + AbstractBasicTranslationRotation3D::translate(vector); + return *this; + } + AbstractBasicTranslationRotationScaling3D& translateLocal(const Math::Vector3& vector) { + AbstractBasicTranslationRotation3D::translateLocal(vector); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use translate() or translateLocal() instead") AbstractBasicTranslationRotationScaling3D& translate(const Math::Vector3& vector, TransformationType type) { AbstractBasicTranslationRotation3D::translate(vector, type); return *this; } - AbstractBasicTranslationRotationScaling3D& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type = TransformationType::Global) { + #endif + AbstractBasicTranslationRotationScaling3D& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis) { + AbstractBasicTranslationRotation3D::rotate(angle, normalizedAxis); + return *this; + } + AbstractBasicTranslationRotationScaling3D& rotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) { + AbstractBasicTranslationRotation3D::rotateLocal(angle, normalizedAxis); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") AbstractBasicTranslationRotationScaling3D& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) { AbstractBasicTranslationRotation3D::rotate(angle, normalizedAxis, type); return *this; } - AbstractBasicTranslationRotationScaling3D& rotateX(Math::Rad angle, TransformationType type = TransformationType::Global) { + #endif + AbstractBasicTranslationRotationScaling3D& rotateX(Math::Rad angle) { + AbstractBasicTranslationRotation3D::rotateX(angle); + return *this; + } + AbstractBasicTranslationRotationScaling3D& rotateXLocal(Math::Rad angle) { + AbstractBasicTranslationRotation3D::rotateXLocal(angle); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotateX() or rotateXLocal() instead") AbstractBasicTranslationRotationScaling3D& rotateX(Math::Rad angle, TransformationType type) { AbstractBasicTranslationRotation3D::rotateX(angle, type); return *this; } - AbstractBasicTranslationRotationScaling3D& rotateY(Math::Rad angle, TransformationType type = TransformationType::Global) { + #endif + AbstractBasicTranslationRotationScaling3D& rotateY(Math::Rad angle) { + AbstractBasicTranslationRotation3D::rotateY(angle); + return *this; + } + AbstractBasicTranslationRotationScaling3D& rotateYLocal(Math::Rad angle) { + AbstractBasicTranslationRotation3D::rotateYLocal(angle); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotateY() or rotateYLocal() instead") AbstractBasicTranslationRotationScaling3D& rotateY(Math::Rad angle, TransformationType type) { AbstractBasicTranslationRotation3D::rotateY(angle, type); return *this; } - AbstractBasicTranslationRotationScaling3D& rotateZ(Math::Rad angle, TransformationType type = TransformationType::Global) { + #endif + AbstractBasicTranslationRotationScaling3D& rotateZ(Math::Rad angle) { + AbstractBasicTranslationRotation3D::rotateZ(angle); + return *this; + } + AbstractBasicTranslationRotationScaling3D& rotateZLocal(Math::Rad angle) { + AbstractBasicTranslationRotation3D::rotateZLocal(angle); + return *this; + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotateZ() or rotateZLocal() instead") AbstractBasicTranslationRotationScaling3D& rotateZ(Math::Rad angle, TransformationType type) { AbstractBasicTranslationRotation3D::rotateZ(angle, type); return *this; } #endif + #endif protected: ~AbstractBasicTranslationRotationScaling3D() = default; @@ -95,7 +166,10 @@ template class AbstractBasicTranslationRotationScaling3D: public Abstra private: #endif /** @brief Polymorphic implementation for @ref scale() */ - virtual void doScale(const Math::Vector3& vector, TransformationType type) = 0; + virtual void doScale(const Math::Vector3& vector) = 0; + + /** @brief Polymorphic implementation for @ref scaleLocal() */ + virtual void doScaleLocal(const Math::Vector3& vector) = 0; }; /** diff --git a/src/Magnum/SceneGraph/DualComplexTransformation.h b/src/Magnum/SceneGraph/DualComplexTransformation.h index 9446a8c27..ac5bac8fc 100644 --- a/src/Magnum/SceneGraph/DualComplexTransformation.h +++ b/src/Magnum/SceneGraph/DualComplexTransformation.h @@ -84,41 +84,112 @@ template class BasicDualComplexTransformation: public AbstractBasicTran /** * @brief Transform object - * @param transformation Transformation - * @param type Transformation type * @return Reference to self (for method chaining) * * Expects that the dual complex number is normalized. - * @see @ref Math::DualComplex::isNormalized() + * @see @ref transformLocal(), @ref Math::DualComplex::isNormalized() */ - Object>& transform(const Math::DualComplex& transformation, TransformationType type = TransformationType::Global) { + Object>& transform(const Math::DualComplex& transformation) { CORRADE_ASSERT(transformation.isNormalized(), "SceneGraph::DualComplexTransformation::transform(): the dual complex number is not normalized", static_cast>&>(*this)); - return transformInternal(transformation, type); + return transformInternal(transformation); + } + + /** + * @brief Transform object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + Object>& transformLocal(const Math::DualComplex& transformation) { + CORRADE_ASSERT(transformation.isNormalized(), + "SceneGraph::DualComplexTransformation::transformLocal(): the dual complex number is not normalized", + static_cast>&>(*this)); + return transformLocalInternal(transformation); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::DualComplexTransformation::transform() "transform()" + * or @ref Magnum::SceneGraph::DualComplexTransformation::transformLocal() "transformLocal()" + * instead. + */ + CORRADE_DEPRECATED("use transform() or transformLocal() instead") Object>& transform(const Math::DualComplex& transformation, TransformationType type) { + return type == TransformationType::Global ? transform(transformation) : transformLocal(transformation); } + #endif /** - * @copydoc AbstractTranslationRotationScaling2D::translate() + * @brief Translate object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::DualComplex::translation(). + * @see @ref translateLocal(), @ref Math::Vector2::xAxis(), + * @ref Math::Vector2::yAxis() */ - Object>& translate(const Math::Vector2& vector, TransformationType type = TransformationType::Global) { - return transformInternal(Math::DualComplex::translation(vector), type); + Object>& translate(const Math::Vector2& vector) { + return transformInternal(Math::DualComplex::translation(vector)); } + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::DualComplex::translation(). + */ + Object>& translateLocal(const Math::Vector2& vector) { + return transformLocalInternal(Math::DualComplex::translation(vector)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::DualComplexTransformation::translate() "translate()" + * or @ref Magnum::SceneGraph::DualComplexTransformation::translateLocal() "translateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use translate() or translateLocal() instead") Object>& translate(const Math::Vector2& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); + } + #endif + /** * @brief Rotate object * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::DualComplex::rotation(). - * @see @ref normalizeRotation() + * @see @ref rotateLocal(), @ref normalizeRotation() */ - Object>& rotate(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transformInternal(Math::DualComplex::rotation(angle), type); + Object>& rotate(Math::Rad angle) { + return transformInternal(Math::DualComplex::rotation(angle)); } + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + Object>& rotateLocal(Math::Rad angle) { + return transformLocalInternal(Math::DualComplex::rotation(angle)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::DualComplexTransformation::rotate() "rotate()" + * or @ref Magnum::SceneGraph::DualComplexTransformation::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") Object>& rotate(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotate(angle) : rotateLocal(angle); + } + #endif + protected: /* Allow construction only from Object */ explicit BasicDualComplexTransformation() = default; @@ -126,14 +197,16 @@ template class BasicDualComplexTransformation: public AbstractBasicTran private: void doResetTransformation() override final { resetTransformation(); } - void doTranslate(const Math::Vector2& vector, TransformationType type) override final { - translate(vector, type); + void doTranslate(const Math::Vector2& vector) override final { + translate(vector); } - - void doRotate(Math::Rad angle, TransformationType type) override final { - rotate(angle, type); + void doTranslateLocal(const Math::Vector2& vector) override final { + translateLocal(vector); } + void doRotate(Math::Rad angle) override final { rotate(angle); } + void doRotateLocal(Math::Rad angle) override final { rotateLocal(angle); } + /* No assertions fired, for internal use */ Object>& setTransformationInternal(const Math::DualComplex& transformation) { /* Setting transformation is forbidden for the scene */ @@ -148,9 +221,11 @@ template class BasicDualComplexTransformation: public AbstractBasicTran } /* No assertions fired, for internal use */ - Object>& transformInternal(const Math::DualComplex& transformation, TransformationType type) { - return setTransformationInternal(type == TransformationType::Global ? - transformation*_transformation : _transformation*transformation); + Object>& transformInternal(const Math::DualComplex& transformation) { + return setTransformationInternal(transformation*_transformation); + } + Object>& transformLocalInternal(const Math::DualComplex& transformation) { + return setTransformationInternal(_transformation*transformation); } Math::DualComplex _transformation; diff --git a/src/Magnum/SceneGraph/DualQuaternionTransformation.h b/src/Magnum/SceneGraph/DualQuaternionTransformation.h index 4307b4d1d..2836f6a55 100644 --- a/src/Magnum/SceneGraph/DualQuaternionTransformation.h +++ b/src/Magnum/SceneGraph/DualQuaternionTransformation.h @@ -83,56 +83,151 @@ template class BasicDualQuaternionTransformation: public AbstractBasicT } /** - * @brief Multiply transformation - * @param transformation Transformation - * @param type Transformation type + * @brief Transform object * @return Reference to self (for method chaining) * * Expects that the dual quaternion is normalized. - * @see @ref Math::DualQuaternion::isNormalized() + * @see @ref transformLocal(), @ref Math::DualQuaternion::isNormalized() */ - Object>& transform(const Math::DualQuaternion& transformation, TransformationType type = TransformationType::Global) { + Object>& transform(const Math::DualQuaternion& transformation) { CORRADE_ASSERT(transformation.isNormalized(), "SceneGraph::DualQuaternionTransformation::transform(): the dual quaternion is not normalized", static_cast>&>(*this)); - return transformInternal(transformation, type); + return transformInternal(transformation); + } + + /** + * @brief Transform object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + Object>& transformLocal(const Math::DualQuaternion& transformation) { + CORRADE_ASSERT(transformation.isNormalized(), + "SceneGraph::DualQuaternionTransformation::transformLocal(): the dual quaternion is not normalized", + static_cast>&>(*this)); + return transformLocalInternal(transformation); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::DualQuaternionTransformation::transform() "transform()" + * or @ref Magnum::SceneGraph::DualQuaternionTransformation::transformLocal() "transformLocal()" + * instead. + */ + Object>& transform(const Math::DualQuaternion& transformation, TransformationType type) { + return type == TransformationType::Global ? transform(transformation) : transformLocal(transformation); } + #endif /** - * @copydoc AbstractTranslationRotationScaling3D::translate() + * @brief Translate object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::DualQuaternion::translation(). + * @see @ref translateLocal(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() + */ + Object>& translate(const Math::Vector3& vector) { + return transformInternal(Math::DualQuaternion::translation(vector)); + } + + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. */ - Object>& translate(const Math::Vector3& vector, TransformationType type = TransformationType::Global) { - return transformInternal(Math::DualQuaternion::translation(vector), type); + Object>& translateLocal(const Math::Vector3& vector) { + return transformLocalInternal(Math::DualQuaternion::translation(vector)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::DualQuaternionTransformation::translate() "translate()" + * or @ref Magnum::SceneGraph::DualQuaternionTransformation::translateLocal() "translateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use translate() or translateLocal() instead") Object>& translate(const Math::Vector3& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); + } + #endif + /** * @brief Rotate object * @param angle Angle (counterclockwise) * @param normalizedAxis Normalized rotation axis - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::DualQuaternion::rotation(). - * @see @ref Math::Vector3::xAxis(), @ref Math::Vector3::yAxis(), - * @ref Math::Vector3::zAxis(), @ref normalizeRotation() + * @see @ref rotateLocal(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis(), + * @ref normalizeRotation() + */ + Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis) { + return transformInternal(Math::DualQuaternion::rotation(angle, normalizedAxis)); + } + + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. */ - Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type = TransformationType::Global) { - return transformInternal(Math::DualQuaternion::rotation(angle, normalizedAxis), type); + Object>& rotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) { + return transformLocalInternal(Math::DualQuaternion::rotation(angle, normalizedAxis)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::DualQuaternionTransformation::rotate() "rotate()" + * or @ref Magnum::SceneGraph::DualQuaternionTransformation::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("usr rotate() or rotateLocal() instead") Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) { + return type == TransformationType::Global ? rotate(angle, normalizedAxis) : rotateLocal(angle, normalizedAxis); + } + #endif + /* Overloads to remove WTF-factor from method chaining order */ #ifndef DOXYGEN_GENERATING_OUTPUT - Object>& rotateX(Math::Rad angle, TransformationType type = TransformationType::Global) { + Object>& rotateX(Math::Rad angle) { + return rotate(angle, Math::Vector3::xAxis()); + } + Object>& rotateXLocal(Math::Rad angle) { + return rotateLocal(angle, Math::Vector3::xAxis()); + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotateX() or rotateXLocal() instead") Object>& rotateX(Math::Rad angle, TransformationType type) { return rotate(angle, Math::Vector3::xAxis(), type); } - Object>& rotateY(Math::Rad angle, TransformationType type = TransformationType::Global) { + #endif + Object>& rotateY(Math::Rad angle) { + return rotate(angle, Math::Vector3::yAxis()); + } + Object>& rotateYLocal(Math::Rad angle) { + return rotateLocal(angle, Math::Vector3::yAxis()); + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotateY() or rotateYLocal() instead") Object>& rotateY(Math::Rad angle, TransformationType type) { return rotate(angle, Math::Vector3::yAxis(), type); } - Object>& rotateZ(Math::Rad angle, TransformationType type = TransformationType::Global) { + #endif + Object>& rotateZ(Math::Rad angle) { + return rotate(angle, Math::Vector3::zAxis()); + } + Object>& rotateZLocal(Math::Rad angle) { + return rotateLocal(angle, Math::Vector3::zAxis()); + } + #ifdef MAGNUM_BUILD_DEPRECATED + CORRADE_DEPRECATED("use rotateZ() or rotateZLocal() instead") Object>& rotateZ(Math::Rad angle, TransformationType type) { return rotate(angle, Math::Vector3::zAxis(), type); } #endif + #endif protected: /* Allow construction only from Object */ @@ -141,12 +236,18 @@ template class BasicDualQuaternionTransformation: public AbstractBasicT private: void doResetTransformation() override final { resetTransformation(); } - void doTranslate(const Math::Vector3& vector, TransformationType type) override final { - translate(vector, type); + void doTranslate(const Math::Vector3& vector) override final { + translate(vector); + } + void doTranslateLocal(const Math::Vector3& vector) override final { + translateLocal(vector); } - void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) override final { - rotate(angle, normalizedAxis, type); + void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis) override final { + rotate(angle, normalizedAxis); + } + void doRotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) override final { + rotateLocal(angle, normalizedAxis); } /* No assertions fired, for internal use */ @@ -163,9 +264,11 @@ template class BasicDualQuaternionTransformation: public AbstractBasicT } /* No assertions fired, for internal use */ - Object>& transformInternal(const Math::DualQuaternion& transformation, TransformationType type) { - return setTransformationInternal(type == TransformationType::Global ? - transformation*_transformation : _transformation*transformation); + Object>& transformInternal(const Math::DualQuaternion& transformation) { + return setTransformationInternal(transformation*_transformation); + } + Object>& transformLocalInternal(const Math::DualQuaternion& transformation) { + return setTransformationInternal(_transformation*transformation); } Math::DualQuaternion _transformation; diff --git a/src/Magnum/SceneGraph/MatrixTransformation2D.h b/src/Magnum/SceneGraph/MatrixTransformation2D.h index 29d26f78d..f855734aa 100644 --- a/src/Magnum/SceneGraph/MatrixTransformation2D.h +++ b/src/Magnum/SceneGraph/MatrixTransformation2D.h @@ -68,14 +68,35 @@ template class BasicMatrixTransformation2D: public AbstractBasicTransla /** * @brief Transform object - * @param transformation Transformation - * @param type Transformation type * @return Reference to self (for method chaining) + * + * @see @ref transformLocal() + */ + Object>& transform(const Math::Matrix3& transformation) { + return setTransformation(transformation*_transformation); + } + + /** + * @brief Transform object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + Object>& transformLocal(const Math::Matrix3& transformation) { + return setTransformation(_transformation*transformation); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation2D::transform() "transform()" + * or @ref Magnum::SceneGraph::MatrixTransformation2D::transformLocal() "transformLocal()" + * instead. */ - Object>& transform(const Math::Matrix3& transformation, TransformationType type = TransformationType::Global) { - return setTransformation(type == TransformationType::Global ? - transformation*_transformation : _transformation*transformation); + CORRADE_DEPRECATED("use transform() or transformLocal() instead") Object>& transform(const Math::Matrix3& transformation, TransformationType type) { + return type == TransformationType::Global ? transform(transformation) : transformLocal(transformation); } + #endif /** @copydoc AbstractTranslationRotationScaling2D::resetTransformation() */ Object>& resetTransformation() { @@ -83,42 +104,147 @@ template class BasicMatrixTransformation2D: public AbstractBasicTransla } /** - * @copydoc AbstractTranslationRotationScaling2D::translate() + * Translate object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix3::translation(). + * @see @ref translateLocal(), @ref Math::Vector2::xAxis(), + * @ref Math::Vector2::yAxis() + */ + Object>& translate(const Math::Vector2& vector) { + return transform(Math::Matrix3::translation(vector)); + } + + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix3::translation(). + */ + Object>& translateLocal(const Math::Vector2& vector) { + return transformLocal(Math::Matrix3::translation(vector)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation2D::translate() "translate()" + * or @ref Magnum::SceneGraph::MatrixTransformation2D::translateLocal() "translateLocal()" + * instead. */ - Object>& translate(const Math::Vector2& vector, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix3::translation(vector), type); + CORRADE_DEPRECATED("use translate() or translateLocal() instead") Object>& translate(const Math::Vector2& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); } + #endif /** - * @copydoc AbstractTranslationRotationScaling2D::rotate() + * @brief Rotate object + * @param angle Angle (counterclockwise) + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix3::rotation(). + * @see @ref rotateLocal() + */ + Object>& rotate(Math::Rad angle) { + return transform(Math::Matrix3::rotation(angle)); + } + + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix3::rotation(). */ - Object>& rotate(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix3::rotation(angle), type); + Object>& rotateLocal(Math::Rad angle) { + return transformLocal(Math::Matrix3::rotation(angle)); } + #ifdef MAGNUM_BUILD_DEPRECATED /** - * @copydoc AbstractTranslationRotationScaling2D::scale() + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation2D::rotate() "rotate()" + * or @ref Magnum::SceneGraph::MatrixTransformation2D::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") Object>& rotate(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotate(angle) : rotateLocal(angle); + } + #endif + + /** + * @brief Scale object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix3::scaling(). + * @see @ref scaleLocal(), @ref Math::Vector2::xScale(), + * @ref Math::Vector2::yScale() + */ + Object>& scale(const Math::Vector2& vector) { + return transform(Math::Matrix3::scaling(vector)); + } + + /** + * @brief Scale object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix3::scaling(). */ - Object>& scale(const Math::Vector2& vector, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix3::scaling(vector), type); + Object>& scaleLocal(const Math::Vector2& vector) { + return transformLocal(Math::Matrix3::scaling(vector)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief scale() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation2D::scale() "scale()" + * or @ref Magnum::SceneGraph::MatrixTransformation2D::scaleLocal() "scaleLocal()" + * instead. + */ + CORRADE_DEPRECATED("use scale() or scaleLocal() instead") Object>& scale(const Math::Vector2& vector, TransformationType type) { + return type == TransformationType::Global ? scale(vector) : scaleLocal(vector); + } + #endif + /** * @brief Reflect object * @param normal Normal of the line through which to reflect * (normalized) - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::Matrix3::reflection(). + * @see @ref reflectLocal(), @ref Math::Vector2::xAxis(), + * @ref Math::Vector2::yAxis() */ - Object>& reflect(const Math::Vector2& normal, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix3::reflection(normal), type); + Object>& reflect(const Math::Vector2& normal) { + return transform(Math::Matrix3::reflection(normal)); } + /** + * @brief Reflect object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix3::reflection(). + */ + Object>& reflectLocal(const Math::Vector2& normal) { + return transformLocal(Math::Matrix3::reflection(normal)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief reflect() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation2D::reflect() "reflect()" + * or @ref Magnum::SceneGraph::MatrixTransformation2D::reflectLocal() "reflectLocal()" + * instead. + */ + CORRADE_DEPRECATED("use reflect() or reflectLocal() instead") Object>& reflect(const Math::Vector2& normal, TransformationType type) { + return type == TransformationType::Global ? reflect(normal) : reflectLocal(normal); + } + #endif + protected: /* Allow construction only from Object */ explicit BasicMatrixTransformation2D() = default; @@ -126,17 +252,14 @@ template class BasicMatrixTransformation2D: public AbstractBasicTransla private: void doResetTransformation() override final { resetTransformation(); } - void doTranslate(const Math::Vector2& vector, TransformationType type) override final { - translate(vector, type); - } + void doTranslate(const Math::Vector2& vector) override final { translate(vector); } + void doTranslateLocal(const Math::Vector2& vector) override final { translateLocal(vector); } - void doRotate(Math::Rad angle, TransformationType type) override final { - rotate(angle, type); - } + void doRotate(Math::Rad angle) override final { rotate(angle); } + void doRotateLocal(Math::Rad angle) override final { rotateLocal(angle); } - void doScale(const Math::Vector2& vector, TransformationType type) override final { - scale(vector, type); - } + void doScale(const Math::Vector2& vector) override final { scale(vector); } + void doScaleLocal(const Math::Vector2& vector) override final { scaleLocal(vector); } Math::Matrix3 _transformation; }; diff --git a/src/Magnum/SceneGraph/MatrixTransformation3D.h b/src/Magnum/SceneGraph/MatrixTransformation3D.h index ccbc13302..f374ecf15 100644 --- a/src/Magnum/SceneGraph/MatrixTransformation3D.h +++ b/src/Magnum/SceneGraph/MatrixTransformation3D.h @@ -71,89 +71,286 @@ template class BasicMatrixTransformation3D: public AbstractBasicTransla } /** - * @brief Multiply transformation - * @param transformation Transformation - * @param type Transformation type + * @brief Transform object * @return Reference to self (for method chaining) + * + * @see @ref transformLocal() + */ + Object>& transform(const Math::Matrix4& transformation) { + return setTransformation(transformation*_transformation); + } + + /** + * @brief Transform object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. */ - Object>& transform(const Math::Matrix4& transformation, TransformationType type = TransformationType::Global) { - return setTransformation(type == TransformationType::Global ? - transformation*_transformation : _transformation*transformation); + Object>& transformLocal(const Math::Matrix4& transformation) { + return setTransformation(_transformation*transformation); } + #ifdef MAGNUM_BUILD_DEPRECATED /** - * @copydoc AbstractTranslationRotationScaling3D::translate() + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::transform() "transform()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::transformLocal() "transformLocal()" + * instead. + */ + CORRADE_DEPRECATED("use transform() or transformLocal() instead") Object>& transform(const Math::Matrix4& transformation, TransformationType type) { + return type == TransformationType::Global ? transform(transformation) : transformLocal(transformation); + } + #endif + + /** + * @brief Translate object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix4::translation(). + * @see @ref translateLocal(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() + */ + Object>& translate(const Math::Vector3& vector) { + return transform(Math::Matrix4::translation(vector)); + } + + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::translation(). */ - Object>& translate(const Math::Vector3& vector, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::translation(vector), type); + Object>& translateLocal(const Math::Vector3& vector) { + return transformLocal(Math::Matrix4::translation(vector)); } + #ifdef MAGNUM_BUILD_DEPRECATED /** - * @copydoc AbstractTranslationRotationScaling3D::rotate() + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::translate() "translate()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::translateLocal() "translateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use translate() or translateLocal() instead") Object>& translate(const Math::Vector3& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); + } + #endif + + /** + * @brief Rotate object + * @param angle Angle (counterclockwise) + * @param normalizedAxis Normalized rotation axis + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix4::rotation(). + * @see @ref rotateLocal(), @ref rotateX(), @ref rotateY(), + * @ref rotateZ(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() + */ + Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis) { + return transform(Math::Matrix4::rotation(angle, normalizedAxis)); + } + + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::rotation(). + */ + Object>& rotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) { + return transformLocal(Math::Matrix4::rotation(angle, normalizedAxis)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::rotate() "rotate()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::rotateLocal() "rotateLocal()" + * instead. */ - Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::rotation(angle, normalizedAxis), type); + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) { + return type == TransformationType::Global ? rotate(angle, normalizedAxis) : rotateLocal(angle, normalizedAxis); } + #endif /** * @brief Rotate object around X axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::Matrix4::rotationX(). + * @see @ref rotateXLocal() */ - Object>& rotateX(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::rotationX(angle), type); + Object>& rotateX(Math::Rad angle) { + return transform(Math::Matrix4::rotationX(angle)); } + /** + * @brief Rotate object around X axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::rotationX(). + */ + Object>& rotateXLocal(Math::Rad angle) { + return transformLocal(Math::Matrix4::rotationX(angle)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateX() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::rotateX() "rotateX()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::rotateXLocal() "rotateXLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateX() or rotateXLocal() instead") Object>& rotateX(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateX(angle) : rotateXLocal(angle); + } + #endif + /** * @brief Rotate object around Y axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::Matrix4::rotationY(). + * @see @ref rotateYLocal() + */ + Object>& rotateY(Math::Rad angle) { + return transform(Math::Matrix4::rotationY(angle)); + } + + /** + * @brief Rotate object around Y axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::rotationY(). */ - Object>& rotateY(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::rotationY(angle), type); + Object>& rotateYLocal(Math::Rad angle) { + return transformLocal(Math::Matrix4::rotationY(angle)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateY() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::rotateY() "rotateY()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::rotateYLocal() "rotateYLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateY() or rotateYLocal() instead") Object>& rotateY(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateY(angle) : rotateYLocal(angle); + } + #endif + /** * @brief Rotate object around Z axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::Matrix4::rotationZ(). + * @see @ref rotateZLocal() + */ + Object>& rotateZ(Math::Rad angle) { + return transform(Math::Matrix4::rotationZ(angle)); + } + + /** + * @brief Rotate object around Z axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::rotationZ(). + */ + Object>& rotateZLocal(Math::Rad angle) { + return transformLocal(Math::Matrix4::rotationZ(angle)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateZ() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::rotateZ() "rotateZ()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::rotateZLocal() "rotateZLocal()" + * instead. */ - Object>& rotateZ(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::rotationZ(angle), type); + CORRADE_DEPRECATED("use rotateZ() or rotateZLocal() instead") Object>& rotateZ(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateZ(angle) : rotateZLocal(angle); } + #endif /** - * @copydoc AbstractTranslationRotationScaling3D::scale() + * @brief Scale object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix4::scaling(). + * @see @ref scaleLocal(), @ref Math::Vector3::xScale(), + * @ref Math::Vector3::yScale(), @ref Math::Vector3::zScale() */ - Object>& scale(const Math::Vector3& vector, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::scaling(vector), type); + Object>& scale(const Math::Vector3& vector) { + return transform(Math::Matrix4::scaling(vector)); } + /** + * @brief Scale object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::scaling(). + */ + Object>& scaleLocal(const Math::Vector3& vector) { + return transformLocal(Math::Matrix4::scaling(vector)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief scale() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::scale() "scale()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::scaleLocal() "scaleLocal()" + * instead. + */ + CORRADE_DEPRECATED("use scale() or scaleLocal() instead") Object>& scale(const Math::Vector3& vector, TransformationType type) { + return type == TransformationType::Global ? scale(vector) : scaleLocal(vector); + } + #endif + /** * @brief Reflect object * @param normal Normal of the plane through which to reflect * (normalized) - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::Matrix4::reflection(). + * @see @ref reflectLocal() + */ + Object>& reflect(const Math::Vector3& normal) { + return transform(Math::Matrix4::reflection(normal)); + } + + /** + * @brief Reflect object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::reflection(). */ - Object>& reflect(const Math::Vector3& normal, TransformationType type = TransformationType::Global) { - return transform(Math::Matrix4::reflection(normal), type); + Object>& reflectLocal(const Math::Vector3& normal) { + return transformLocal(Math::Matrix4::reflection(normal)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief reflect() + * @deprecated Use @ref Magnum::SceneGraph::MatrixTransformation3D::reflect() "reflect()" + * or @ref Magnum::SceneGraph::MatrixTransformation3D::reflectLocal() "reflectLocal()" + * instead. + */ + CORRADE_DEPRECATED("use reflect() or reflectLocal() instead") Object>& reflect(const Math::Vector3& normal, TransformationType type) { + return type == TransformationType::Global ? reflect(normal) : reflectLocal(normal); + } + #endif + protected: /* Allow construction only from Object */ explicit BasicMatrixTransformation3D() = default; @@ -161,29 +358,27 @@ template class BasicMatrixTransformation3D: public AbstractBasicTransla private: void doResetTransformation() override final { resetTransformation(); } - void doTranslate(const Math::Vector3& vector, TransformationType type) override final { - translate(vector, type); - } + void doTranslate(const Math::Vector3& vector) override final { translate(vector); } + void doTranslateLocal(const Math::Vector3& vector) override final { translateLocal(vector); } - void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) override final { - rotate(angle, normalizedAxis, type); + void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis) override final { + rotate(angle, normalizedAxis); } - - void doRotateX(Math::Rad angle, TransformationType type) override final { - rotateX(angle, type); + void doRotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) override final { + rotateLocal(angle, normalizedAxis); } - void doRotateY(Math::Rad angle, TransformationType type) override final { - rotateY(angle, type); - } + void doRotateX(Math::Rad angle) override final { rotateX(angle); } + void doRotateXLocal(Math::Rad angle) override final { rotateXLocal(angle); } - void doRotateZ(Math::Rad angle, TransformationType type) override final { - rotateZ(angle, type); - } + void doRotateY(Math::Rad angle) override final { rotateY(angle); } + void doRotateYLocal(Math::Rad angle) override final { rotateYLocal(angle); } - void doScale(const Math::Vector3& vector, TransformationType type) override final { - scale(vector, type); - } + void doRotateZ(Math::Rad angle) override final { rotateZ(angle); } + void doRotateZLocal(Math::Rad angle) override final { rotateZLocal(angle); } + + void doScale(const Math::Vector3& vector) override final { scale(vector); } + void doScaleLocal(const Math::Vector3& vector) override final { scaleLocal(vector); } Math::Matrix4 _transformation; }; diff --git a/src/Magnum/SceneGraph/RigidMatrixTransformation2D.h b/src/Magnum/SceneGraph/RigidMatrixTransformation2D.h index ad74708a6..16eace59a 100644 --- a/src/Magnum/SceneGraph/RigidMatrixTransformation2D.h +++ b/src/Magnum/SceneGraph/RigidMatrixTransformation2D.h @@ -89,57 +89,150 @@ template class BasicRigidMatrixTransformation2D: public AbstractBasicTr /** * @brief Transform object - * @param transformation Transformation - * @param type Transformation type * @return Reference to self (for method chaining) * * Expects that the matrix represents rigid transformation. - * @see @ref Math::Matrix3::isRigidTransformation() + * @see @ref transformLocal(), @ref Math::Matrix3::isRigidTransformation() */ - Object>& transform(const Math::Matrix3& transformation, TransformationType type = TransformationType::Global) { + Object>& transform(const Math::Matrix3& transformation) { CORRADE_ASSERT(transformation.isRigidTransformation(), "SceneGraph::RigidMatrixTransformation2D::transform(): the matrix doesn't represent rigid transformation", static_cast>&>(*this)); - return transformInternal(transformation, type); + return transformInternal(transformation); + } + + /** + * @brief Transform object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + Object>& transformLocal(const Math::Matrix3& transformation) { + CORRADE_ASSERT(transformation.isRigidTransformation(), + "SceneGraph::RigidMatrixTransformation2D::transformLocal(): the matrix doesn't represent rigid transformation", + static_cast>&>(*this)); + return transformLocalInternal(transformation); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation2D::transform() "transform()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation2D::transformLocal() "transformLocal()" + * instead. + */ + CORRADE_DEPRECATED("use transform() or transformLocal() instead") Object>& transform(const Math::Matrix3& transformation, TransformationType type) { + return type == TransformationType::Global ? transform(transformation) : transformLocal(transformation); } + #endif /** - * @copydoc AbstractTranslationRotationScaling2D::translate() - * Same as calling @ref transform() with + * Translate object + * @return Reference to self (for method chaining) + * + * Same as calling @ref transform() with @ref Math::Matrix3::translation(). + * @see @ref translateLocal(), @ref Math::Vector2::xAxis(), + * @ref Math::Vector2::yAxis() + */ + Object>& translate(const Math::Vector2& vector) { + return transformInternal(Math::Matrix3::translation(vector)); + } + + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix3::translation(). */ - Object>& translate(const Math::Vector2& vector, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix3::translation(vector), type); + Object>& translateLocal(const Math::Vector2& vector) { + return transformLocalInternal(Math::Matrix3::translation(vector)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation2D::translate() "translate()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation2D::translateLocal() "translateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use translate() or translateLocal() instead") Object>& translate(const Math::Vector2& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); } + #endif /** * @brief Rotate object * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * - * Same as calling @ref transform() with + * Same as calling @ref transform() with @ref Math::Matrix3::rotation(). + * @see @ref rotateLocal(), @ref normalizeRotation() + */ + Object>& rotate(Math::Rad angle) { + return transformInternal(Math::Matrix3::rotation(angle)); + } + + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix3::rotation(). * @see @ref normalizeRotation() */ - Object>& rotate(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix3::rotation(angle), type); + Object>& rotateLocal(Math::Rad angle) { + return transformLocalInternal(Math::Matrix3::rotation(angle)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation2D::rotate() "rotate()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation2D::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") Object>& rotate(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotate(angle) : rotateLocal(angle); + } + #endif + /** * @brief Reflect object * @param normal Normal of the line through which to reflect * (normalized) - * @param type Transformation type * @return Reference to self (for method chaining) * - * Same as calling @ref transform() with + * Same as calling @ref transform() with @ref Math::Matrix3::reflection(). + * @see @ref reflectLocal() + */ + Object>& reflect(const Math::Vector2& normal) { + return transformInternal(Math::Matrix3::reflection(normal)); + } + + /** + * @brief Reflect object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix3::reflection(). */ - Object>& reflect(const Math::Vector2& normal, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix3::reflection(normal), type); + Object>& reflectLocal(const Math::Vector2& normal) { + return transformLocalInternal(Math::Matrix3::reflection(normal)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief reflect() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation2D::reflect() "reflect()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation2D::reflectLocal() "reflectLocal()" + * instead. + */ + CORRADE_DEPRECATED("use reflect() or reflectInternal() instead") Object>& reflect(const Math::Vector2& normal, TransformationType type) { + return type == TransformationType::Global ? reflect(normal) : reflectLocal(normal); + } + #endif + protected: /* Allow construction only from Object */ explicit BasicRigidMatrixTransformation2D() = default; @@ -147,13 +240,11 @@ template class BasicRigidMatrixTransformation2D: public AbstractBasicTr private: void doResetTransformation() override final { resetTransformation(); } - void doTranslate(const Math::Vector2& vector, TransformationType type) override final { - translate(vector, type); - } + void doTranslate(const Math::Vector2& vector) override final { translate(vector); } + void doTranslateLocal(const Math::Vector2& vector) override final { translateLocal(vector); } - void doRotate(Math::Rad angle, TransformationType type) override final { - rotate(angle, type); - } + void doRotate(Math::Rad angle) override final { rotate(angle); } + void doRotateLocal(Math::Rad angle) override final { rotateLocal(angle); } /* No assertions fired, for internal use */ Object>& setTransformationInternal(const Math::Matrix3& transformation) { @@ -169,9 +260,11 @@ template class BasicRigidMatrixTransformation2D: public AbstractBasicTr } /* No assertions fired, for internal use */ - Object>& transformInternal(const Math::Matrix3& transformation, TransformationType type) { - return setTransformationInternal(type == TransformationType::Global ? - transformation*_transformation : _transformation*transformation); + Object>& transformInternal(const Math::Matrix3& transformation) { + return setTransformationInternal(transformation*_transformation); + } + Object>& transformLocalInternal(const Math::Matrix3& transformation) { + return setTransformationInternal(_transformation*transformation); } Math::Matrix3 _transformation; diff --git a/src/Magnum/SceneGraph/RigidMatrixTransformation3D.h b/src/Magnum/SceneGraph/RigidMatrixTransformation3D.h index a9b1bda7b..70630188c 100644 --- a/src/Magnum/SceneGraph/RigidMatrixTransformation3D.h +++ b/src/Magnum/SceneGraph/RigidMatrixTransformation3D.h @@ -86,101 +86,259 @@ template class BasicRigidMatrixTransformation3D: public AbstractBasicTr } /** - * @brief Multiply transformation - * @param transformation Transformation - * @param type Transformation type + * @brief Transform object * @return Reference to self (for method chaining) * * Expects that the matrix represents rigid transformation. - * @see @ref Math::Matrix4::isRigidTransformation() + * @see @ref transformLocal(), @ref Math::Matrix4::isRigidTransformation() */ - Object>& transform(const Math::Matrix4& transformation, TransformationType type = TransformationType::Global) { + Object>& transform(const Math::Matrix4& transformation) { CORRADE_ASSERT(transformation.isRigidTransformation(), "SceneGraph::RigidMatrixTransformation3D::transform(): the matrix doesn't represent rigid transformation", static_cast>&>(*this)); - return transformInternal(transformation, type); + return transformInternal(transformation); } /** - * @copydoc AbstractTranslationRotationScaling3D::translate() + * @brief Transform object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. + */ + Object>& transformLocal(const Math::Matrix4& transformation) { + CORRADE_ASSERT(transformation.isRigidTransformation(), + "SceneGraph::RigidMatrixTransformation3D::transform(): the matrix doesn't represent rigid transformation", + static_cast>&>(*this)); + return transformLocalInternal(transformation); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::transform() "transform()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::transformLocal() "transformLocal()" + * instead. + */ + CORRADE_DEPRECATED("use transform() or transformLocal() instead") Object>& transform(const Math::Matrix4& transformation, TransformationType type) { + return type == TransformationType::Global ? transform(transformation) : transformLocal(transformation); + } + #endif + + /** + * @brief Translate object + * @return Reference to self (for method chaining) + * * Same as calling @ref transform() with @ref Math::Matrix4::translation(). + * @see @ref translateLocal(), @ref Math::Vector3::xAxis(), + * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() + */ + Object>& translate(const Math::Vector3& vector) { + return transformInternal(Math::Matrix4::translation(vector)); + } + + /** + * @brief Translate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::translation(). + */ + Object>& translateLocal(const Math::Vector3& vector) { + return transformLocalInternal(Math::Matrix4::translation(vector)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::translate() "translate()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::translateLocal() "translateLocal()" + * instead. */ - Object>& translate(const Math::Vector3& vector, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix4::translation(vector), type); + CORRADE_DEPRECATED("use translate() or translateLocal() instead") Object>& translate(const Math::Vector3& vector, TransformationType type) { + return type == TransformationType::Global ? translate(vector) : translateLocal(vector); } + #endif /** * @brief Rotate object * @param angle Angle (counterclockwise) * @param normalizedAxis Normalized rotation axis - * @param type Transformation type * @return Reference to self (for method chaining) * * Same as calling @ref transform() with @ref Math::Matrix4::rotation(). - * @see @ref rotateX(), @ref rotateY(), @ref rotateZ(), - * @ref normalizeRotation(), @ref Math::Vector3::xAxis(), - * @ref Math::Vector3::yAxis(), @ref Math::Vector3::zAxis() + * @see @ref rotateLocal(), @ref rotateX(), @ref rotateY(), + * @ref rotateZ(), @ref normalizeRotation(), + * @ref Math::Vector3::xAxis(), @ref Math::Vector3::yAxis(), + * @ref Math::Vector3::zAxis() */ - Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix4::rotation(angle, normalizedAxis), type); + Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis) { + return transformInternal(Math::Matrix4::rotation(angle, normalizedAxis)); } + /** + * @brief Rotate object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with + * @ref Math::Matrix4::rotation(). + */ + Object>& rotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) { + return transformLocalInternal(Math::Matrix4::rotation(angle, normalizedAxis)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotate() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotate() "rotate()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateLocal() "rotateLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotate() or rotateLocal() instead") Object>& rotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) { + return type == TransformationType::Global ? rotate(angle, normalizedAxis) : rotateLocal(angle, normalizedAxis); + } + #endif + /** * @brief Rotate object around X axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * - * Same as calling @ref transform() with + * Same as calling @ref transform() with @ref Math::Matrix4::rotationX(). + * @see @ref rotateXLocal(), @ref normalizeRotation() + */ + Object>& rotateX(Math::Rad angle) { + return transformInternal(Math::Matrix4::rotationX(angle)); + } + + /** + * @brief Rotate object around X axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix4::rotationX(). - * @see @ref normalizeRotation() */ - Object>& rotateX(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix4::rotationX(angle), type); + Object>& rotateXLocal(Math::Rad angle) { + return transformLocalInternal(Math::Matrix4::rotationX(angle)); + } + + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateX() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateX() "rotateX()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateXLocal() "rotateXLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateX() or rotateXLocal() instead") Object>& rotateX(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateX(angle) : rotateXLocal(angle); } + #endif /** * @brief Rotate object around Y axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * - * Same as calling @ref transform() with + * Same as calling @ref transform() with @ref Math::Matrix4::rotationY(). + * @see @ref rotateYLocal(), @ref normalizeRotation() + */ + Object>& rotateY(Math::Rad angle) { + return transformInternal(Math::Matrix4::rotationY(angle)); + } + + /** + * @brief Rotate object around Y axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix4::rotationY(). - * @see @ref normalizeRotation() */ - Object>& rotateY(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix4::rotationY(angle), type); + Object>& rotateYLocal(Math::Rad angle) { + return transformLocalInternal(Math::Matrix4::rotationY(angle)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateY() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateY() "rotateY()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateYLocal() "rotateYLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateY() or rotateYLocal() instead") Object>& rotateY(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateY(angle) : rotateYLocal(angle); + } + #endif + /** * @brief Rotate object around Z axis * @param angle Angle (counterclockwise) - * @param type Transformation type * @return Reference to self (for method chaining) * - * Same as calling @ref transform() with + * Same as calling @ref transform() with @ref Math::Matrix4::rotationZ(). + * @see @ref rotateZLocal(), @ref normalizeRotation() + */ + Object>& rotateZ(Math::Rad angle) { + return transformInternal(Math::Matrix4::rotationZ(angle)); + } + + /** + * @brief Rotate object around Z axis as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix4::rotationZ(). - * @see @ref normalizeRotation() */ - Object>& rotateZ(Math::Rad angle, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix4::rotationZ(angle), type); + Object>& rotateZLocal(Math::Rad angle) { + return transformLocalInternal(Math::Matrix4::rotationZ(angle)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief rotateZ() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateZ() "rotateZ()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::rotateZLocal() "rotateZLocal()" + * instead. + */ + CORRADE_DEPRECATED("use rotateZ() or rotateZLocal() instead") Object>& rotateZ(Math::Rad angle, TransformationType type) { + return type == TransformationType::Global ? rotateZ(angle) : rotateZLocal(angle); + } + #endif + /** * @brief Reflect object * @param normal Normal of the plane through which to reflect * (normalized) - * @param type Transformation type * @return Reference to self (for method chaining) * - * Same as calling @ref transform() with + * Same as calling @ref transform() with @ref Math::Matrix4::reflection(). + * @see @ref reflectLocal() + */ + Object>& reflect(const Math::Vector3& normal) { + return transformInternal(Math::Matrix4::reflection(normal)); + } + + /** + * @brief Reflect object as a local transformation + * + * Similar to the above, except that the transformation is applied + * before all others. Same as calling @ref transformLocal() with * @ref Math::Matrix4::reflection(). */ - Object>& reflect(const Math::Vector3& normal, TransformationType type = TransformationType::Global) { - return transformInternal(Math::Matrix4::reflection(normal), type); + Object>& reflectLocal(const Math::Vector3& normal) { + return transformLocalInternal(Math::Matrix4::reflection(normal)); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief reflect() + * @deprecated Use @ref Magnum::SceneGraph::RigidMatrixTransformation3D::reflect() "reflect()" + * or @ref Magnum::SceneGraph::RigidMatrixTransformation3D::reflectLocal() "reflectLocal()" + * instead. + */ + CORRADE_DEPRECATED("use reflect() or reflectLocal() instead") Object>& reflect(const Math::Vector3& normal, TransformationType type) { + return type == TransformationType::Global ? reflect(normal) : reflectLocal(normal); + } + #endif + protected: /* Allow construction only from Object */ explicit BasicRigidMatrixTransformation3D() = default; @@ -188,25 +346,24 @@ template class BasicRigidMatrixTransformation3D: public AbstractBasicTr private: void doResetTransformation() override final { resetTransformation(); } - void doTranslate(const Math::Vector3& vector, TransformationType type) override final { - translate(vector, type); - } + void doTranslate(const Math::Vector3& vector) override final { translate(vector); } + void doTranslateLocal(const Math::Vector3& vector) override final { translateLocal(vector); } - void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis, TransformationType type) override final { - rotate(angle, normalizedAxis, type); + void doRotate(Math::Rad angle, const Math::Vector3& normalizedAxis) override final { + rotate(angle, normalizedAxis); } - - void doRotateX(Math::Rad angle, TransformationType type) override final { - rotateX(angle, type); + void doRotateLocal(Math::Rad angle, const Math::Vector3& normalizedAxis) override final { + rotateLocal(angle, normalizedAxis); } - void doRotateY(Math::Rad angle, TransformationType type) override final { - rotateY(angle, type); - } + void doRotateX(Math::Rad angle) override final { rotateX(angle); } + void doRotateXLocal(Math::Rad angle) override final { rotateXLocal(angle); } - void doRotateZ(Math::Rad angle, TransformationType type) override final { - rotateZ(angle, type); - } + void doRotateY(Math::Rad angle) override final { rotateY(angle); } + void doRotateYLocal(Math::Rad angle) override final { rotateYLocal(angle); } + + void doRotateZ(Math::Rad angle) override final { rotateZ(angle); } + void doRotateZLocal(Math::Rad angle) override final { rotateZLocal(angle); } /* No assertions fired, for internal use */ Object>& setTransformationInternal(const Math::Matrix4& transformation) { @@ -222,9 +379,11 @@ template class BasicRigidMatrixTransformation3D: public AbstractBasicTr } /* No assertions fired, for internal use */ - Object>& transformInternal(const Math::Matrix4& transformation, TransformationType type) { - return setTransformationInternal(type == TransformationType::Global ? - transformation*_transformation : _transformation*transformation); + Object>& transformInternal(const Math::Matrix4& transformation) { + return setTransformationInternal(transformation*_transformation); + } + Object>& transformLocalInternal(const Math::Matrix4& transformation) { + return setTransformationInternal(_transformation*transformation); } Math::Matrix4 _transformation; diff --git a/src/Magnum/SceneGraph/SceneGraph.h b/src/Magnum/SceneGraph/SceneGraph.h index 566ac7bb4..d8a392590 100644 --- a/src/Magnum/SceneGraph/SceneGraph.h +++ b/src/Magnum/SceneGraph/SceneGraph.h @@ -64,7 +64,9 @@ template using AbstractBasicObject3D = AbstractObject<3, T>; typedef AbstractBasicObject2D AbstractObject2D; typedef AbstractBasicObject3D AbstractObject3D; +#ifdef MAGNUM_BUILD_DEPRECATED enum class TransformationType: UnsignedByte; +#endif template class AbstractTransformation; template using AbstractBasicTransformation2D = AbstractTransformation<2, T>; diff --git a/src/Magnum/SceneGraph/Test/DualComplexTransformationTest.cpp b/src/Magnum/SceneGraph/Test/DualComplexTransformationTest.cpp index 64cb5fb8a..79d5d2fc7 100644 --- a/src/Magnum/SceneGraph/Test/DualComplexTransformationTest.cpp +++ b/src/Magnum/SceneGraph/Test/DualComplexTransformationTest.cpp @@ -136,7 +136,7 @@ void DualComplexTransformationTest::transform() { } { Object2D o; o.setTransformation(DualComplex::rotation(Deg(17.0f))); - o.transform(DualComplex::translation({1.0f, -0.3f}), TransformationType::Local); + o.transformLocal(DualComplex::translation({1.0f, -0.3f})); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::translation({1.0f, -0.3f})); } } @@ -150,7 +150,7 @@ void DualComplexTransformationTest::translate() { } { Object2D o; o.setTransformation(DualComplex::rotation(Deg(17.0f))); - o.translate({1.0f, -0.3f}, TransformationType::Local); + o.translateLocal({1.0f, -0.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::translation({1.0f, -0.3f})); } } @@ -164,7 +164,7 @@ void DualComplexTransformationTest::rotate() { } { Object2D o; o.setTransformation(DualComplex::translation({1.0f, -0.3f})); - o.rotate(Deg(17.0f), TransformationType::Local); + o.rotateLocal(Deg(17.0f)); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::translation({1.0f, -0.3f})*Matrix3::rotation(Deg(17.0f))); } } diff --git a/src/Magnum/SceneGraph/Test/DualQuaternionTransformationTest.cpp b/src/Magnum/SceneGraph/Test/DualQuaternionTransformationTest.cpp index e3d0423bb..14b71ba80 100644 --- a/src/Magnum/SceneGraph/Test/DualQuaternionTransformationTest.cpp +++ b/src/Magnum/SceneGraph/Test/DualQuaternionTransformationTest.cpp @@ -142,7 +142,7 @@ void DualQuaternionTransformationTest::transform() { } { Object3D o; o.setTransformation(DualQuaternion::rotation(Deg(17.0f), Vector3::xAxis())); - o.transform(DualQuaternion::translation({1.0f, -0.3f, 2.3f}), TransformationType::Local); + o.transformLocal(DualQuaternion::translation({1.0f, -0.3f, 2.3f})); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::translation({1.0f, -0.3f, 2.3f})); } } @@ -156,7 +156,7 @@ void DualQuaternionTransformationTest::translate() { } { Object3D o; o.setTransformation(DualQuaternion::rotation(Deg(17.0f), Vector3::xAxis())); - o.translate({1.0f, -0.3f, 2.3f}, TransformationType::Local); + o.translateLocal({1.0f, -0.3f, 2.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::translation({1.0f, -0.3f, 2.3f})); } } @@ -178,10 +178,10 @@ void DualQuaternionTransformationTest::rotate() { } { Object3D o; o.transform(DualQuaternion::translation({1.0f, -0.3f, 2.3f})); - o.rotateX(Deg(17.0f), TransformationType::Local) - .rotateY(Deg(25.0f), TransformationType::Local) - .rotateZ(Deg(-23.0f), TransformationType::Local) - .rotate(Deg(96.0f), Vector3(1.0f/Constants::sqrt3()), TransformationType::Local); + o.rotateXLocal(Deg(17.0f)) + .rotateYLocal(Deg(25.0f)) + .rotateZLocal(Deg(-23.0f)) + .rotateLocal(Deg(96.0f), Vector3(1.0f/Constants::sqrt3())); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::translation({1.0f, -0.3f, 2.3f})* Matrix4::rotationX(Deg(17.0f))* diff --git a/src/Magnum/SceneGraph/Test/MatrixTransformation2DTest.cpp b/src/Magnum/SceneGraph/Test/MatrixTransformation2DTest.cpp index 1675decc0..70ccd2d11 100644 --- a/src/Magnum/SceneGraph/Test/MatrixTransformation2DTest.cpp +++ b/src/Magnum/SceneGraph/Test/MatrixTransformation2DTest.cpp @@ -122,7 +122,7 @@ void MatrixTransformation2DTest::transform() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.transform(Matrix3::translation({1.0f, -0.3f}), TransformationType::Local); + o.transformLocal(Matrix3::translation({1.0f, -0.3f})); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::translation({1.0f, -0.3f})); } } @@ -136,7 +136,7 @@ void MatrixTransformation2DTest::translate() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.translate({1.0f, -0.3f}, TransformationType::Local); + o.translateLocal({1.0f, -0.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::translation({1.0f, -0.3f})); } } @@ -150,7 +150,7 @@ void MatrixTransformation2DTest::rotate() { } { Object2D o; o.setTransformation(Matrix3::translation({1.0f, -0.3f})); - o.rotate(Deg(17.0f), TransformationType::Local); + o.rotateLocal(Deg(17.0f)); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::translation({1.0f, -0.3f})*Matrix3::rotation(Deg(17.0f))); } } @@ -164,7 +164,7 @@ void MatrixTransformation2DTest::scale() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.scale({1.0f, -0.3f}, TransformationType::Local); + o.scaleLocal({1.0f, -0.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::scaling({1.0f, -0.3f})); } } @@ -178,7 +178,7 @@ void MatrixTransformation2DTest::reflect() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.reflect(Vector2(-1.0f/Constants::sqrt2()), TransformationType::Local); + o.reflectLocal(Vector2(-1.0f/Constants::sqrt2())); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::reflection(Vector2(-1.0f/Constants::sqrt2()))); } } diff --git a/src/Magnum/SceneGraph/Test/MatrixTransformation3DTest.cpp b/src/Magnum/SceneGraph/Test/MatrixTransformation3DTest.cpp index 3f06f507a..c62700db8 100644 --- a/src/Magnum/SceneGraph/Test/MatrixTransformation3DTest.cpp +++ b/src/Magnum/SceneGraph/Test/MatrixTransformation3DTest.cpp @@ -122,7 +122,7 @@ void MatrixTransformation3DTest::transform() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.transform(Matrix4::translation({1.0f, -0.3f, 2.3f}), TransformationType::Local); + o.transformLocal(Matrix4::translation({1.0f, -0.3f, 2.3f})); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::translation({1.0f, -0.3f, 2.3f})); } } @@ -136,7 +136,7 @@ void MatrixTransformation3DTest::translate() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.translate({1.0f, -0.3f, 2.3f}, TransformationType::Local); + o.translateLocal({1.0f, -0.3f, 2.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::translation({1.0f, -0.3f, 2.3f})); } } @@ -158,10 +158,10 @@ void MatrixTransformation3DTest::rotate() { } { Object3D o; o.setTransformation(Matrix4::translation({1.0f, -0.3f, 2.3f})); - o.rotateX(Deg(17.0f), TransformationType::Local) - .rotateY(Deg(25.0f), TransformationType::Local) - .rotateZ(Deg(-23.0f), TransformationType::Local) - .rotate(Deg(96.0f), Vector3(1.0f/Constants::sqrt3()), TransformationType::Local); + o.rotateXLocal(Deg(17.0f)) + .rotateYLocal(Deg(25.0f)) + .rotateZLocal(Deg(-23.0f)) + .rotateLocal(Deg(96.0f), Vector3(1.0f/Constants::sqrt3())); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::translation({1.0f, -0.3f, 2.3f})* Matrix4::rotationX(Deg(17.0f))* @@ -180,7 +180,7 @@ void MatrixTransformation3DTest::scale() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.scale({1.0f, -0.3f, 2.3f}, TransformationType::Local); + o.scaleLocal({1.0f, -0.3f, 2.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::scaling({1.0f, -0.3f, 2.3f})); } } @@ -194,7 +194,7 @@ void MatrixTransformation3DTest::reflect() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.reflect(Vector3(-1.0f/Constants::sqrt3()), TransformationType::Local); + o.reflectLocal(Vector3(-1.0f/Constants::sqrt3())); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::reflection(Vector3(-1.0f/Constants::sqrt3()))); } } diff --git a/src/Magnum/SceneGraph/Test/RigidMatrixTransformation2DTest.cpp b/src/Magnum/SceneGraph/Test/RigidMatrixTransformation2DTest.cpp index 408998f0e..28436b1f8 100644 --- a/src/Magnum/SceneGraph/Test/RigidMatrixTransformation2DTest.cpp +++ b/src/Magnum/SceneGraph/Test/RigidMatrixTransformation2DTest.cpp @@ -141,7 +141,7 @@ void RigidMatrixTransformation2DTest::transform() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.transform(Matrix3::translation({1.0f, -0.3f}), TransformationType::Local); + o.transformLocal(Matrix3::translation({1.0f, -0.3f})); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::translation({1.0f, -0.3f})); } } @@ -155,7 +155,7 @@ void RigidMatrixTransformation2DTest::translate() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.translate({1.0f, -0.3f}, TransformationType::Local); + o.translateLocal({1.0f, -0.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::translation({1.0f, -0.3f})); } } @@ -169,7 +169,7 @@ void RigidMatrixTransformation2DTest::rotate() { } { Object2D o; o.setTransformation(Matrix3::translation({1.0f, -0.3f})); - o.rotate(Deg(17.0f), TransformationType::Local); + o.rotateLocal(Deg(17.0f)); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::translation({1.0f, -0.3f})*Matrix3::rotation(Deg(17.0f))); } } @@ -183,7 +183,7 @@ void RigidMatrixTransformation2DTest::reflect() { } { Object2D o; o.setTransformation(Matrix3::rotation(Deg(17.0f))); - o.reflect(Vector2(-1.0f/Constants::sqrt2()), TransformationType::Local); + o.reflectLocal(Vector2(-1.0f/Constants::sqrt2())); CORRADE_COMPARE(o.transformationMatrix(), Matrix3::rotation(Deg(17.0f))*Matrix3::reflection(Vector2(-1.0f/Constants::sqrt2()))); } } diff --git a/src/Magnum/SceneGraph/Test/RigidMatrixTransformation3DTest.cpp b/src/Magnum/SceneGraph/Test/RigidMatrixTransformation3DTest.cpp index 72408d8a5..853800c7e 100644 --- a/src/Magnum/SceneGraph/Test/RigidMatrixTransformation3DTest.cpp +++ b/src/Magnum/SceneGraph/Test/RigidMatrixTransformation3DTest.cpp @@ -142,7 +142,7 @@ void RigidMatrixTransformation3DTest::transform() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.transform(Matrix4::translation({1.0f, -0.3f, 2.3f}), TransformationType::Local); + o.transformLocal(Matrix4::translation({1.0f, -0.3f, 2.3f})); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::translation({1.0f, -0.3f, 2.3f})); } } @@ -156,7 +156,7 @@ void RigidMatrixTransformation3DTest::translate() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.translate({1.0f, -0.3f, 2.3f}, TransformationType::Local); + o.translateLocal({1.0f, -0.3f, 2.3f}); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::translation({1.0f, -0.3f, 2.3f})); } } @@ -178,10 +178,10 @@ void RigidMatrixTransformation3DTest::rotate() { } { Object3D o; o.setTransformation(Matrix4::translation({1.0f, -0.3f, 2.3f})); - o.rotateX(Deg(17.0f), TransformationType::Local) - .rotateY(Deg(25.0f), TransformationType::Local) - .rotateZ(Deg(-23.0f), TransformationType::Local) - .rotate(Deg(96.0f), Vector3(1.0f/Constants::sqrt3()), TransformationType::Local); + o.rotateXLocal(Deg(17.0f)) + .rotateYLocal(Deg(25.0f)) + .rotateZLocal(Deg(-23.0f)) + .rotateLocal(Deg(96.0f), Vector3(1.0f/Constants::sqrt3())); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::translation({1.0f, -0.3f, 2.3f})* Matrix4::rotationX(Deg(17.0f))* @@ -200,7 +200,7 @@ void RigidMatrixTransformation3DTest::reflect() { } { Object3D o; o.setTransformation(Matrix4::rotationX(Deg(17.0f))); - o.reflect(Vector3(-1.0f/Constants::sqrt3()), TransformationType::Local); + o.reflectLocal(Vector3(-1.0f/Constants::sqrt3())); CORRADE_COMPARE(o.transformationMatrix(), Matrix4::rotationX(Deg(17.0f))*Matrix4::reflection(Vector3(-1.0f/Constants::sqrt3()))); } } diff --git a/src/Magnum/SceneGraph/TranslationTransformation.h b/src/Magnum/SceneGraph/TranslationTransformation.h index ae80b04e7..df10e078d 100644 --- a/src/Magnum/SceneGraph/TranslationTransformation.h +++ b/src/Magnum/SceneGraph/TranslationTransformation.h @@ -87,31 +87,53 @@ class TranslationTransformation: public AbstractTranslation>& transform(const VectorTypeFor& transformation, TransformationType = TransformationType::Global) { + Object>& transform(const VectorTypeFor& transformation) { return translate(transformation); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief transform() + * @deprecated Use @ref Magnum::SceneGraph::TranslationTransformation::transform() "transform()" + * instead. + */ + CORRADE_DEPRECATED("use transform() instead") Object>& transform(const VectorTypeFor& transformation, TransformationType) { + return transform(transformation); + } + #endif + /** * @brief Translate object - * @param vector Translation vector * @return Reference to self (for method chaining) * + * There is no difference between global and local translation. * @see @ref Math::Vector2::xAxis(), @ref Math::Vector2::yAxis(), * @ref Math::Vector3::xAxis(), @ref Math::Vector3::yAxis(), * @ref Math::Vector3::zAxis() */ - Object>& translate(const VectorTypeFor& vector, TransformationType = TransformationType::Global) { + Object>& translate(const VectorTypeFor& vector) { _transformation += vector; return static_cast>&>(*this); } + #ifdef MAGNUM_BUILD_DEPRECATED + /** + * @copybrief translate() + * @deprecated Use @ref Magnum::SceneGraph::TranslationTransformation::translate() "translate()" + * instead. + */ + CORRADE_DEPRECATED("use translate() instead") Object>& translate(const VectorTypeFor& vector, TransformationType) { + return translate(vector); + } + #endif + protected: /* Allow construction only from Object */ explicit TranslationTransformation() = default; @@ -119,7 +141,10 @@ class TranslationTransformation: public AbstractTranslation& vector, TransformationType) override final { + void doTranslate(const VectorTypeFor& vector) override final { + translate(vector); + } + void doTranslateLocal(const VectorTypeFor& vector) override final { translate(vector); }