aboutsummaryrefslogtreecommitdiffhomepage
path: root/Eigen/src/Geometry/Transform.h
diff options
context:
space:
mode:
Diffstat (limited to 'Eigen/src/Geometry/Transform.h')
-rw-r--r--Eigen/src/Geometry/Transform.h99
1 files changed, 52 insertions, 47 deletions
diff --git a/Eigen/src/Geometry/Transform.h b/Eigen/src/Geometry/Transform.h
index 214b286bd..702e87663 100644
--- a/Eigen/src/Geometry/Transform.h
+++ b/Eigen/src/Geometry/Transform.h
@@ -26,6 +26,14 @@
#ifndef EIGEN_TRANSFORM_H
#define EIGEN_TRANSFORM_H
+template<typename Transform, typename OtherTransform>
+struct ei_is_any_projective
+{
+ static const bool value =
+ ((int)Transform::Mode == Projective) ||
+ ((int)OtherTransform::Mode == Projective);
+};
+
// Note that we have to pass Dim and HDim because it is not allowed to use a template
// parameter to define a template specialization. To be more precise, in the following
// specializations, it is not allowed to use Dim+1 instead of HDim.
@@ -47,7 +55,10 @@ template< typename Other,
int OtherCols=Other::ColsAtCompileTime>
struct ei_transform_left_product_impl;
-template<typename Lhs,typename Rhs> struct ei_transform_transform_product_impl;
+template<typename Lhs,
+ typename Rhs,
+ bool AnyProjective = ei_is_any_projective<Lhs,Rhs>::value >
+struct ei_transform_transform_product_impl;
template< typename Other,
int Mode,
@@ -243,8 +254,15 @@ public:
template<int OtherMode>
inline Transform(const Transform<Scalar,Dim,OtherMode>& other)
{
+ // prevent conversions as:
+ // Affine | AffineCompact | Isometry = Projective
EIGEN_STATIC_ASSERT(EIGEN_IMPLIES(OtherMode==int(Projective), Mode==int(Projective)),
- YOU_CANT_CONVERT_A_PROJECTIVE_TRANSFORM_INTO_AN_AFFINE_TRANSFORM)
+ YOU_PERFORMED_AN_INVALID_TRANSFORMATION_CONVERSION)
+
+ // prevent conversions as:
+ // Isometry = Affine | AffineCompact
+ EIGEN_STATIC_ASSERT(EIGEN_IMPLIES(OtherMode==int(Affine)||OtherMode==int(AffineCompact), Mode!=int(Isometry)),
+ YOU_PERFORMED_AN_INVALID_TRANSFORMATION_CONVERSION)
enum { ModeIsAffineCompact = Mode == int(AffineCompact),
OtherModeIsAffineCompact = OtherMode == int(AffineCompact)
@@ -252,7 +270,11 @@ public:
if(ModeIsAffineCompact == OtherModeIsAffineCompact)
{
- m_matrix = other.matrix();
+ // We need the block expression because the code is compiled for all
+ // combinations of transformations and will trigger a compile time error
+ // if one tries to assign the matrices directly
+ m_matrix.template block<Dim,Dim+1>(0,0) = other.matrix().template block<Dim,Dim+1>(0,0);
+ makeAffine();
}
else if(OtherModeIsAffineCompact)
{
@@ -499,15 +521,6 @@ public:
};
/** \ingroup Geometry_Module */
-typedef Transform<float,2> Transform2f;
-/** \ingroup Geometry_Module */
-typedef Transform<float,3> Transform3f;
-/** \ingroup Geometry_Module */
-typedef Transform<double,2> Transform2d;
-/** \ingroup Geometry_Module */
-typedef Transform<double,3> Transform3d;
-
-/** \ingroup Geometry_Module */
typedef Transform<float,2,Isometry> Isometry2f;
/** \ingroup Geometry_Module */
typedef Transform<float,3,Isometry> Isometry3f;
@@ -981,6 +994,7 @@ Transform<Scalar,Dim,Mode>::inverse(TransformTraits hint) const
// translation and remaining parts
res.matrix().template topRightCorner<Dim,1>()
= - res.matrix().template topLeftCorner<Dim,Dim>() * translation();
+ res.makeAffine(); // we do need this, because in the beginning res is uninitialized
}
return res;
}
@@ -1058,7 +1072,18 @@ template<typename Lhs, typename D2> struct ei_general_product_return_type<Lhs, M
template<typename D1, typename Rhs> struct ei_general_product_return_type<MatrixBase<D1>, Rhs >
{ typedef D1 Type; };
-
+template<int LhsMode,int RhsMode>
+struct ei_transform_product_result
+{
+ enum
+ {
+ Mode =
+ (LhsMode == (int)Projective || RhsMode == (int)Projective ) ? Projective :
+ (LhsMode == (int)Affine || RhsMode == (int)Affine ) ? Affine :
+ (LhsMode == (int)AffineCompact || RhsMode == (int)AffineCompact ) ? AffineCompact :
+ (LhsMode == (int)Isometry || RhsMode == (int)Isometry ) ? Isometry : Projective
+ };
+};
// Projective * set of homogeneous column vectors
template<typename Other, int Dim, int HDim>
@@ -1281,52 +1306,32 @@ struct ei_transform_left_product_impl<Other,Mode,Dim,HDim, Dim,Dim>
*** Specializations of operator* with another Transform ***
**********************************************************/
-template<typename Scalar, int Dim, int Mode>
-struct ei_transform_transform_product_impl<Transform<Scalar,Dim,Mode>,Transform<Scalar,Dim,Mode> >
-{
- typedef Transform<Scalar,Dim,Mode> TransformType;
- typedef TransformType ResultType;
- static ResultType run(const TransformType& lhs, const TransformType& rhs)
- {
- return ResultType(lhs.matrix() * rhs.matrix());
- }
-};
-
-template<typename Scalar, int Dim>
-struct ei_transform_transform_product_impl<Transform<Scalar,Dim,AffineCompact>,Transform<Scalar,Dim,AffineCompact> >
-{
- typedef Transform<Scalar,Dim,AffineCompact> TransformType;
- typedef TransformType ResultType;
- static ResultType run(const TransformType& lhs, const TransformType& rhs)
- {
- return ei_transform_right_product_impl<typename TransformType::MatrixType,
- AffineCompact,Dim,Dim+1>::run(lhs,rhs.matrix());
- }
-};
-
template<typename Scalar, int Dim, int LhsMode, int RhsMode>
-struct ei_transform_transform_product_impl<Transform<Scalar,Dim,LhsMode>,Transform<Scalar,Dim,RhsMode> >
+struct ei_transform_transform_product_impl<Transform<Scalar,Dim,LhsMode>,Transform<Scalar,Dim,RhsMode>,false >
{
+ enum { ResultMode = ei_transform_product_result<LhsMode,RhsMode>::Mode };
typedef Transform<Scalar,Dim,LhsMode> Lhs;
typedef Transform<Scalar,Dim,RhsMode> Rhs;
- typedef typename ei_transform_right_product_impl<typename Rhs::MatrixType,
- LhsMode,Dim,Dim+1>::ResultType ResultType;
+ typedef Transform<Scalar,Dim,ResultMode> ResultType;
static ResultType run(const Lhs& lhs, const Rhs& rhs)
{
- return ei_transform_right_product_impl<typename Rhs::MatrixType,LhsMode,Dim,Dim+1>::run(lhs,rhs.matrix());
+ ResultType res;
+ res.linear() = lhs.linear() * rhs.linear();
+ res.translation() = lhs.linear() * rhs.translation() + lhs.translation();
+ res.makeAffine();
+ return res;
}
};
-template<typename Scalar, int Dim>
-struct ei_transform_transform_product_impl<Transform<Scalar,Dim,AffineCompact>,
- Transform<Scalar,Dim,Affine> >
+template<typename Scalar, int Dim, int LhsMode, int RhsMode>
+struct ei_transform_transform_product_impl<Transform<Scalar,Dim,LhsMode>,Transform<Scalar,Dim,RhsMode>,true >
{
- typedef Transform<Scalar,Dim,AffineCompact> Lhs;
- typedef Transform<Scalar,Dim,Affine> Rhs;
- typedef Transform<Scalar,Dim,AffineCompact> ResultType;
+ typedef Transform<Scalar,Dim,LhsMode> Lhs;
+ typedef Transform<Scalar,Dim,RhsMode> Rhs;
+ typedef Transform<Scalar,Dim,Projective> ResultType;
static ResultType run(const Lhs& lhs, const Rhs& rhs)
{
- return ResultType(lhs.matrix() * rhs.matrix());
+ return ResultType( lhs.matrix() * rhs.matrix() );
}
};