143877ae9bd93bbb2ab7df29de0c62f9052bb5d1
[occt.git] / src / gp / gp_Trsf2d.hxx
1 // Copyright (c) 1991-1999 Matra Datavision
2 // Copyright (c) 1999-2014 OPEN CASCADE SAS
3 //
4 // This file is part of Open CASCADE Technology software library.
5 //
6 // This library is free software; you can redistribute it and/or modify it under
7 // the terms of the GNU Lesser General Public License version 2.1 as published
8 // by the Free Software Foundation, with special exception defined in the file
9 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
10 // distribution for complete text of the license and disclaimer of any warranty.
11 //
12 // Alternatively, this file may be used under the terms of Open CASCADE
13 // commercial license or contractual agreement.
14
15 #ifndef _gp_Trsf2d_HeaderFile
16 #define _gp_Trsf2d_HeaderFile
17
18 #include <gp_TrsfForm.hxx>
19 #include <gp_Mat2d.hxx>
20 #include <gp_XY.hxx>
21 #include <Standard_ConstructionError.hxx>
22 #include <Standard_OutOfRange.hxx>
23
24 class gp_GTrsf2d;
25 class gp_Trsf;
26 class gp_Pnt2d;
27 class gp_Ax2d;
28 class gp_Vec2d;
29 class gp_XY;
30 class gp_Mat2d;
31
32 //! Defines a non-persistent transformation in 2D space.
33 //! The following transformations are implemented :
34 //! - Translation, Rotation, Scale
35 //! - Symmetry with respect to a point and a line.
36 //! Complex transformations can be obtained by combining the
37 //! previous elementary transformations using the method Multiply.
38 //! The transformations can be represented as follow :
39 //! @code
40 //!    V1   V2   T       XY        XY
41 //! | a11  a12  a13 |   | x |     | x'|
42 //! | a21  a22  a23 |   | y |     | y'|
43 //! |  0    0    1  |   | 1 |     | 1 |
44 //! @endcode
45 //! where {V1, V2} defines the vectorial part of the transformation
46 //! and T defines the translation part of the transformation.
47 //! This transformation never change the nature of the objects.
48 class gp_Trsf2d 
49 {
50 public:
51
52   DEFINE_STANDARD_ALLOC
53
54   //! Returns identity transformation.
55   gp_Trsf2d();
56
57   //! Creates a 2d transformation in the XY plane from a
58   //! 3d transformation .
59   gp_Trsf2d (const gp_Trsf& theT);
60
61   //! Changes the transformation into a symmetrical transformation.
62   //! theP is the center of the symmetry.
63   void SetMirror (const gp_Pnt2d& theP);
64
65   //! Changes the transformation into a symmetrical transformation.
66   //! theA is the center of the axial symmetry.
67   Standard_EXPORT void SetMirror (const gp_Ax2d& theA);
68
69   //! Changes the transformation into a rotation.
70   //! theP is the rotation's center and theAng is the angular value of the
71   //! rotation in radian.
72   void SetRotation (const gp_Pnt2d& theP, const Standard_Real theAng);
73
74   //! Changes the transformation into a scale.
75   //! theP is the center of the scale and theS is the scaling value.
76   void SetScale (const gp_Pnt2d& theP, const Standard_Real theS);
77
78   //! Changes a transformation allowing passage from the coordinate
79   //! system "theFromSystem1" to the coordinate system "theToSystem2".
80   Standard_EXPORT void SetTransformation (const gp_Ax2d& theFromSystem1, const gp_Ax2d& theToSystem2);
81
82   //! Changes the transformation allowing passage from the basic
83   //! coordinate system
84   //! {P(0.,0.,0.), VX (1.,0.,0.), VY (0.,1.,0.)}
85   //! to the local coordinate system defined with the Ax2d theToSystem.
86   Standard_EXPORT void SetTransformation (const gp_Ax2d& theToSystem);
87
88   //! Changes the transformation into a translation.
89   //! theV is the vector of the translation.
90   void SetTranslation (const gp_Vec2d& theV);
91
92   //! Makes the transformation into a translation from
93   //! the point theP1 to the point theP2.
94   void SetTranslation (const gp_Pnt2d& theP1, const gp_Pnt2d& theP2);
95
96   //! Replaces the translation vector with theV.
97   Standard_EXPORT void SetTranslationPart (const gp_Vec2d& theV);
98
99   //! Modifies the scale factor.
100   Standard_EXPORT void SetScaleFactor (const Standard_Real theS);
101
102   //! Returns true if the determinant of the vectorial part of
103   //! this transformation is negative..
104   Standard_Boolean IsNegative() const { return (matrix.Determinant() < 0.0); }
105
106   //! Returns the nature of the transformation. It can be  an
107   //! identity transformation, a rotation, a translation, a mirror
108   //! (relative to a point or an axis), a scaling transformation,
109   //! or a compound transformation.
110   gp_TrsfForm Form() const { return shape; }
111
112   //! Returns the scale factor.
113   Standard_Real ScaleFactor() const { return scale; }
114
115   //! Returns the translation part of the transformation's matrix
116   const gp_XY& TranslationPart() const { return loc; }
117
118   //! Returns the vectorial part of the transformation. It is a
119   //! 2*2 matrix which includes the scale factor.
120   Standard_EXPORT gp_Mat2d VectorialPart() const;
121
122   //! Returns the homogeneous vectorial part of the transformation.
123   //! It is a 2*2 matrix which doesn't include the scale factor.
124   //! The coefficients of this matrix must be multiplied by the
125   //! scale factor to obtain the coefficients of the transformation.
126   const gp_Mat2d& HVectorialPart() const { return matrix; }
127
128   //! Returns the angle corresponding to the rotational component
129   //! of the transformation matrix (operation opposite to SetRotation()).
130   Standard_EXPORT Standard_Real RotationPart() const;
131
132   //! Returns the coefficients of the transformation's matrix.
133   //! It is a 2 rows * 3 columns matrix.
134   //! Raises OutOfRange if theRow < 1 or theRow > 2 or theCol < 1 or theCol > 3
135   Standard_Real Value (const Standard_Integer theRow, const Standard_Integer theCol) const;
136
137   Standard_EXPORT void Invert();
138
139   //! Computes the reverse transformation.
140   //! Raises an exception if the matrix of the transformation
141   //! is not inversible, it means that the scale factor is lower
142   //! or equal to Resolution from package gp.
143   Standard_NODISCARD gp_Trsf2d Inverted() const
144   {
145     gp_Trsf2d aT = *this;
146     aT.Invert();
147     return aT;
148   }
149
150   Standard_NODISCARD gp_Trsf2d Multiplied (const gp_Trsf2d& theT) const
151   {
152     gp_Trsf2d aTresult (*this);
153     aTresult.Multiply (theT);
154     return aTresult;
155   }
156
157   Standard_NODISCARD gp_Trsf2d operator * (const gp_Trsf2d& theT) const { return Multiplied (theT); }
158
159   //! Computes the transformation composed from <me> and theT.
160   //! <me> = <me> * theT
161   Standard_EXPORT void Multiply (const gp_Trsf2d& theT);
162
163   void operator *= (const gp_Trsf2d& theT) { Multiply (theT); }
164
165   //! Computes the transformation composed from <me> and theT.
166   //! <me> = theT * <me>
167   Standard_EXPORT void PreMultiply (const gp_Trsf2d& theT);
168
169   Standard_EXPORT void Power (const Standard_Integer theN);
170
171   //! Computes the following composition of transformations
172   //! <me> * <me> * .......* <me>,  theN time.
173   //! if theN = 0 <me> = Identity
174   //! if theN < 0 <me> = <me>.Inverse() *...........* <me>.Inverse().
175   //!
176   //! Raises if theN < 0 and if the matrix of the transformation not
177   //! inversible.
178   gp_Trsf2d Powered (const Standard_Integer theN)
179   {
180     gp_Trsf2d aT = *this;
181     aT.Power (theN);
182     return aT;
183   }
184
185   void Transforms (Standard_Real& theX, Standard_Real& theY) const;
186
187   //! Transforms  a doublet XY with a Trsf2d
188   void Transforms (gp_XY& theCoord) const;
189
190   //! Sets the coefficients  of the transformation. The
191   //! transformation  of the  point  x,y is  the point
192   //! x',y' with :
193   //! @code
194   //! x' = a11 x + a12 y + a13
195   //! y' = a21 x + a22 y + a23
196   //! @endcode
197   //! The method Value(i,j) will return aij.
198   //! Raises ConstructionError if the determinant of the aij is null.
199   //! If the matrix as not a uniform scale it will be orthogonalized before future using.
200   Standard_EXPORT void SetValues (const Standard_Real a11, const Standard_Real a12, const Standard_Real a13, const Standard_Real a21, const Standard_Real a22, const Standard_Real a23);
201
202 friend class gp_GTrsf2d;
203
204 protected:
205
206   //! Makes orthogonalization of "matrix"
207   Standard_EXPORT void Orthogonalize();
208
209 private:
210
211   Standard_Real scale;
212   gp_TrsfForm shape;
213   gp_Mat2d matrix;
214   gp_XY loc;
215
216 };
217
218 #include <gp_Trsf.hxx>
219 #include <gp_Pnt2d.hxx>
220
221 //=======================================================================
222 //function : gp_Trsf2d
223 // purpose :
224 //=======================================================================
225 inline gp_Trsf2d::gp_Trsf2d()
226 {
227   shape = gp_Identity;
228   scale = 1.0;
229   matrix.SetIdentity();
230   loc.SetCoord (0.0, 0.0);
231 }
232
233 //=======================================================================
234 //function : gp_Trsf2d
235 // purpose :
236 //=======================================================================
237 inline gp_Trsf2d::gp_Trsf2d (const gp_Trsf& theT)
238 : scale (theT.ScaleFactor()),
239   shape (theT.Form()),
240   loc (theT.TranslationPart().X(), theT.TranslationPart().Y())
241 {
242   const gp_Mat& M = theT.HVectorialPart();
243   matrix(1,1) = M(1,1);
244   matrix(1,2) = M(1,2);
245   matrix(2,1) = M(2,1);
246   matrix(2,2) = M(2,2);
247 }
248
249 //=======================================================================
250 //function : SetRotation
251 // purpose :
252 //=======================================================================
253 inline void gp_Trsf2d::SetRotation (const gp_Pnt2d& theP,
254                                     const Standard_Real theAng)
255 {
256   shape = gp_Rotation;
257   scale = 1.0;
258   loc = theP.XY ();
259   loc.Reverse ();
260   matrix.SetRotation (theAng);
261   loc.Multiply (matrix);
262   loc.Add (theP.XY());
263 }
264
265 //=======================================================================
266 //function : SetMirror
267 // purpose :
268 //=======================================================================
269 inline void gp_Trsf2d::SetMirror (const gp_Pnt2d& theP)
270 {
271   shape = gp_PntMirror;
272   scale = -1.0;
273   matrix.SetIdentity();
274   loc = theP.XY();
275   loc.Multiply (2.0);
276 }
277
278 //=======================================================================
279 //function : SetScale
280 // purpose :
281 //=======================================================================
282 inline void gp_Trsf2d::SetScale (const gp_Pnt2d& theP, const Standard_Real theS)
283 {
284   shape = gp_Scale;
285   scale = theS;
286   matrix.SetIdentity();
287   loc = theP.XY();
288   loc.Multiply (1.0 - theS);
289 }
290
291 //=======================================================================
292 //function : SetTranslation
293 // purpose :
294 //=======================================================================
295 inline void gp_Trsf2d::SetTranslation (const gp_Vec2d& theV)
296 {
297   shape = gp_Translation;
298   scale = 1.0;
299   matrix.SetIdentity();
300   loc = theV.XY();
301 }
302
303 //=======================================================================
304 //function : SetTranslation
305 // purpose :
306 //=======================================================================
307 inline void gp_Trsf2d::SetTranslation (const gp_Pnt2d& theP1, const gp_Pnt2d& theP2)
308 {
309   shape = gp_Translation;
310   scale = 1.0;
311   matrix.SetIdentity();
312   loc = (theP2.XY()).Subtracted (theP1.XY());
313 }
314
315 //=======================================================================
316 //function : Value
317 // purpose :
318 //=======================================================================
319 inline Standard_Real gp_Trsf2d::Value (const Standard_Integer theRow, const Standard_Integer theCol) const
320 {
321   Standard_OutOfRange_Raise_if (theRow < 1 || theRow > 2 || theCol < 1 || theCol > 3, " ");
322   if (theCol < 3)
323   {
324     return scale * matrix.Value (theRow, theCol);
325   }
326   else
327   {
328     return loc.Coord (theRow);
329   }
330 }
331
332 //=======================================================================
333 //function : Transforms
334 // purpose :
335 //=======================================================================
336 inline void gp_Trsf2d::Transforms (Standard_Real& theX, Standard_Real& theY) const
337 {
338   gp_XY aDoublet(theX, theY);
339   aDoublet.Multiply (matrix);
340   if (scale != 1.0)
341   {
342     aDoublet.Multiply (scale);
343   }
344   aDoublet.Add (loc);
345   aDoublet.Coord (theX, theY);
346 }
347
348 //=======================================================================
349 //function : Transforms
350 // purpose :
351 //=======================================================================
352 inline void gp_Trsf2d::Transforms (gp_XY& theCoord) const
353 {
354   theCoord.Multiply (matrix);
355   if (scale != 1.0)
356   {
357     theCoord.Multiply (scale);
358   }
359   theCoord.Add (loc);
360 }
361
362 #endif // _gp_Trsf2d_HeaderFile