Home | History | Annotate | Download | only in Geometry
      1 // This file is part of Eigen, a lightweight C++ template library
      2 // for linear algebra. Eigen itself is part of the KDE project.
      3 //
      4 // Copyright (C) 2008 Gael Guennebaud <g.gael (at) free.fr>
      5 //
      6 // This Source Code Form is subject to the terms of the Mozilla
      7 // Public License v. 2.0. If a copy of the MPL was not distributed
      8 // with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
      9 
     10 // no include guard, we'll include this twice from All.h from Eigen2Support, and it's internal anyway
     11 
     12 namespace Eigen {
     13 
     14 /** \geometry_module \ingroup Geometry_Module
     15   *
     16   * \class Translation
     17   *
     18   * \brief Represents a translation transformation
     19   *
     20   * \param _Scalar the scalar type, i.e., the type of the coefficients.
     21   * \param _Dim the  dimension of the space, can be a compile time value or Dynamic
     22   *
     23   * \note This class is not aimed to be used to store a translation transformation,
     24   * but rather to make easier the constructions and updates of Transform objects.
     25   *
     26   * \sa class Scaling, class Transform
     27   */
     28 template<typename _Scalar, int _Dim>
     29 class Translation
     30 {
     31 public:
     32   EIGEN_MAKE_ALIGNED_OPERATOR_NEW_IF_VECTORIZABLE_FIXED_SIZE(_Scalar,_Dim)
     33   /** dimension of the space */
     34   enum { Dim = _Dim };
     35   /** the scalar type of the coefficients */
     36   typedef _Scalar Scalar;
     37   /** corresponding vector type */
     38   typedef Matrix<Scalar,Dim,1> VectorType;
     39   /** corresponding linear transformation matrix type */
     40   typedef Matrix<Scalar,Dim,Dim> LinearMatrixType;
     41   /** corresponding scaling transformation type */
     42   typedef Scaling<Scalar,Dim> ScalingType;
     43   /** corresponding affine transformation type */
     44   typedef Transform<Scalar,Dim> TransformType;
     45 
     46 protected:
     47 
     48   VectorType m_coeffs;
     49 
     50 public:
     51 
     52   /** Default constructor without initialization. */
     53   Translation() {}
     54   /**  */
     55   inline Translation(const Scalar& sx, const Scalar& sy)
     56   {
     57     ei_assert(Dim==2);
     58     m_coeffs.x() = sx;
     59     m_coeffs.y() = sy;
     60   }
     61   /**  */
     62   inline Translation(const Scalar& sx, const Scalar& sy, const Scalar& sz)
     63   {
     64     ei_assert(Dim==3);
     65     m_coeffs.x() = sx;
     66     m_coeffs.y() = sy;
     67     m_coeffs.z() = sz;
     68   }
     69   /** Constructs and initialize the scaling transformation from a vector of scaling coefficients */
     70   explicit inline Translation(const VectorType& vector) : m_coeffs(vector) {}
     71 
     72   const VectorType& vector() const { return m_coeffs; }
     73   VectorType& vector() { return m_coeffs; }
     74 
     75   /** Concatenates two translation */
     76   inline Translation operator* (const Translation& other) const
     77   { return Translation(m_coeffs + other.m_coeffs); }
     78 
     79   /** Concatenates a translation and a scaling */
     80   inline TransformType operator* (const ScalingType& other) const;
     81 
     82   /** Concatenates a translation and a linear transformation */
     83   inline TransformType operator* (const LinearMatrixType& linear) const;
     84 
     85   template<typename Derived>
     86   inline TransformType operator*(const RotationBase<Derived,Dim>& r) const
     87   { return *this * r.toRotationMatrix(); }
     88 
     89   /** Concatenates a linear transformation and a translation */
     90   // its a nightmare to define a templated friend function outside its declaration
     91   friend inline TransformType operator* (const LinearMatrixType& linear, const Translation& t)
     92   {
     93     TransformType res;
     94     res.matrix().setZero();
     95     res.linear() = linear;
     96     res.translation() = linear * t.m_coeffs;
     97     res.matrix().row(Dim).setZero();
     98     res(Dim,Dim) = Scalar(1);
     99     return res;
    100   }
    101 
    102   /** Concatenates a translation and an affine transformation */
    103   inline TransformType operator* (const TransformType& t) const;
    104 
    105   /** Applies translation to vector */
    106   inline VectorType operator* (const VectorType& other) const
    107   { return m_coeffs + other; }
    108 
    109   /** \returns the inverse translation (opposite) */
    110   Translation inverse() const { return Translation(-m_coeffs); }
    111 
    112   Translation& operator=(const Translation& other)
    113   {
    114     m_coeffs = other.m_coeffs;
    115     return *this;
    116   }
    117 
    118   /** \returns \c *this with scalar type casted to \a NewScalarType
    119     *
    120     * Note that if \a NewScalarType is equal to the current scalar type of \c *this
    121     * then this function smartly returns a const reference to \c *this.
    122     */
    123   template<typename NewScalarType>
    124   inline typename internal::cast_return_type<Translation,Translation<NewScalarType,Dim> >::type cast() const
    125   { return typename internal::cast_return_type<Translation,Translation<NewScalarType,Dim> >::type(*this); }
    126 
    127   /** Copy constructor with scalar type conversion */
    128   template<typename OtherScalarType>
    129   inline explicit Translation(const Translation<OtherScalarType,Dim>& other)
    130   { m_coeffs = other.vector().template cast<Scalar>(); }
    131 
    132   /** \returns \c true if \c *this is approximately equal to \a other, within the precision
    133     * determined by \a prec.
    134     *
    135     * \sa MatrixBase::isApprox() */
    136   bool isApprox(const Translation& other, typename NumTraits<Scalar>::Real prec = precision<Scalar>()) const
    137   { return m_coeffs.isApprox(other.m_coeffs, prec); }
    138 
    139 };
    140 
    141 /** \addtogroup Geometry_Module */
    142 //@{
    143 typedef Translation<float, 2> Translation2f;
    144 typedef Translation<double,2> Translation2d;
    145 typedef Translation<float, 3> Translation3f;
    146 typedef Translation<double,3> Translation3d;
    147 //@}
    148 
    149 
    150 template<typename Scalar, int Dim>
    151 inline typename Translation<Scalar,Dim>::TransformType
    152 Translation<Scalar,Dim>::operator* (const ScalingType& other) const
    153 {
    154   TransformType res;
    155   res.matrix().setZero();
    156   res.linear().diagonal() = other.coeffs();
    157   res.translation() = m_coeffs;
    158   res(Dim,Dim) = Scalar(1);
    159   return res;
    160 }
    161 
    162 template<typename Scalar, int Dim>
    163 inline typename Translation<Scalar,Dim>::TransformType
    164 Translation<Scalar,Dim>::operator* (const LinearMatrixType& linear) const
    165 {
    166   TransformType res;
    167   res.matrix().setZero();
    168   res.linear() = linear;
    169   res.translation() = m_coeffs;
    170   res.matrix().row(Dim).setZero();
    171   res(Dim,Dim) = Scalar(1);
    172   return res;
    173 }
    174 
    175 template<typename Scalar, int Dim>
    176 inline typename Translation<Scalar,Dim>::TransformType
    177 Translation<Scalar,Dim>::operator* (const TransformType& t) const
    178 {
    179   TransformType res = t;
    180   res.pretranslate(m_coeffs);
    181   return res;
    182 }
    183 
    184 } // end namespace Eigen
    185