0032137: Coding Rules - merge redundant .lxx files into header files within Package gp
[occt.git] / src / gp / gp_XY.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_XY_HeaderFile
16 #define _gp_XY_HeaderFile
17
18 #include <gp.hxx>
19 #include <gp_Mat2d.hxx>
20 #include <Standard_ConstructionError.hxx>
21 #include <Standard_OutOfRange.hxx>
22
23 //! This class describes a cartesian coordinate entity in 2D
24 //! space {X,Y}. This class is non persistent. This entity used
25 //! for algebraic calculation. An XY can be transformed with a
26 //! Trsf2d or a  GTrsf2d from package gp.
27 //! It is used in vectorial computations or for holding this type
28 //! of information in data structures.
29 class gp_XY 
30 {
31 public:
32
33   DEFINE_STANDARD_ALLOC
34
35   //! Creates XY object with zero coordinates (0,0).
36   gp_XY()
37   : x (0.),
38     y (0.)
39   {}
40
41   //! a number pair defined by the XY coordinates
42   gp_XY (const Standard_Real theX, const Standard_Real theY)
43   : x (theX),
44     y (theY)
45   {}
46
47   //! modifies the coordinate of range theIndex
48   //! theIndex = 1 => X is modified
49   //! theIndex = 2 => Y is modified
50   //! Raises OutOfRange if theIndex != {1, 2}.
51   inline void SetCoord (const Standard_Integer theIndex, const Standard_Real theXi)
52   {
53     Standard_OutOfRange_Raise_if (theIndex < 1 || theIndex > 2, NULL);
54     (&x)[theIndex - 1] = theXi;
55   }
56
57   //! For this number pair, assigns
58   //! the values theX and theY to its coordinates
59   inline void SetCoord (const Standard_Real theX, const Standard_Real theY)
60   {
61     x = theX;
62     y = theY;
63   }
64
65   //! Assigns the given value to the X coordinate of this number pair.
66   void SetX (const Standard_Real theX) { x = theX; }
67
68   //! Assigns the given value to the Y  coordinate of this number pair.
69   void SetY (const Standard_Real theY) { y = theY; }
70
71   //! returns the coordinate of range theIndex :
72   //! theIndex = 1 => X is returned
73   //! theIndex = 2 => Y is returned
74   //! Raises OutOfRange if theIndex != {1, 2}.
75   inline Standard_Real Coord (const Standard_Integer theIndex) const
76   {
77     Standard_OutOfRange_Raise_if (theIndex < 1 || theIndex > 2, NULL);
78     return (&x)[theIndex - 1];
79   }
80
81   inline Standard_Real& ChangeCoord (const Standard_Integer theIndex)
82   {
83     Standard_OutOfRange_Raise_if (theIndex < 1 || theIndex > 2, NULL);
84     return (&x)[theIndex - 1];
85   }
86
87   //! For this number pair, returns its coordinates X and Y.
88   inline void Coord (Standard_Real& theX, Standard_Real& theY) const
89   {
90     theX = x;
91     theY = y;
92   }
93
94   //! Returns the X coordinate of this number pair.
95   Standard_Real X() const { return x; }
96
97   //! Returns the Y coordinate of this number pair.
98   Standard_Real Y() const { return y; }
99
100   //! Computes Sqrt (X*X + Y*Y) where X and Y are the two coordinates of this number pair.
101   Standard_Real Modulus() const { return sqrt (x * x + y * y); }
102
103   //! Computes X*X + Y*Y where X and Y are the two coordinates of this number pair.
104   Standard_Real SquareModulus() const { return x * x + y * y; }
105
106   //! Returns true if the coordinates of this number pair are
107   //! equal to the respective coordinates of the number pair
108   //! theOther, within the specified tolerance theTolerance. I.e.:
109   //! abs(<me>.X() - theOther.X()) <= theTolerance and
110   //! abs(<me>.Y() - theOther.Y()) <= theTolerance and
111   //! computations
112   Standard_EXPORT Standard_Boolean IsEqual (const gp_XY& theOther, const Standard_Real theTolerance) const;
113
114   //! Computes the sum of this number pair and number pair theOther
115   //! @code
116   //! <me>.X() = <me>.X() + theOther.X()
117   //! <me>.Y() = <me>.Y() + theOther.Y()
118   inline void Add (const gp_XY& theOther)
119   {
120     x += theOther.x;
121     y += theOther.y;
122   }
123
124   void operator+= (const gp_XY& theOther) { Add (theOther); }
125
126   //! Computes the sum of this number pair and number pair theOther
127   //! @code
128   //! new.X() = <me>.X() + theOther.X()
129   //! new.Y() = <me>.Y() + theOther.Y()
130   //! @endcode
131   Standard_NODISCARD gp_XY Added (const gp_XY& theOther) const
132   {
133     return gp_XY (x + theOther.X(), y + theOther.Y());
134   }
135
136   Standard_NODISCARD gp_XY operator+ (const gp_XY& theOther) const { return Added (theOther); }
137
138   //! @code
139   //! double D = <me>.X() * theOther.Y() - <me>.Y() * theOther.X()
140   //! @endcode
141   Standard_NODISCARD Standard_Real Crossed (const gp_XY& theOther) const { return x * theOther.y - y * theOther.x; }
142
143   Standard_NODISCARD Standard_Real operator^ (const gp_XY& theOther) const { return Crossed (theOther); }
144
145   //! computes the magnitude of the cross product between <me> and
146   //! theRight. Returns || <me> ^ theRight ||
147   inline Standard_Real CrossMagnitude (const gp_XY& theRight) const
148   {
149     Standard_Real aVal = x * theRight.y - y * theRight.x;
150     return aVal < 0 ? -aVal : aVal;
151   }
152
153   //! computes the square magnitude of the cross product between <me> and
154   //! theRight. Returns || <me> ^ theRight ||**2
155   inline Standard_Real CrossSquareMagnitude (const gp_XY& theRight) const
156   {
157     Standard_Real aZresult = x * theRight.y - y * theRight.x;
158     return aZresult * aZresult;
159   }
160
161   //! divides <me> by a real.
162   void Divide (const Standard_Real theScalar)
163   {
164     x /= theScalar;
165     y /= theScalar;
166   }
167
168   void operator /= (const Standard_Real theScalar) { Divide (theScalar); }
169
170   //! Divides <me> by a real.
171   Standard_NODISCARD gp_XY Divided (const Standard_Real theScalar) const
172   {
173     return gp_XY (x / theScalar, y / theScalar);
174   }
175
176   Standard_NODISCARD gp_XY operator/ (const Standard_Real theScalar) const { return Divided (theScalar); }
177
178   //! Computes the scalar product between <me> and theOther
179   Standard_Real Dot (const gp_XY& theOther) const { return x * theOther.x + y * theOther.y; }
180
181   Standard_Real operator* (const gp_XY& theOther) const { return Dot (theOther); }
182
183   //! @code
184   //! <me>.X() = <me>.X() * theScalar;
185   //! <me>.Y() = <me>.Y() * theScalar;
186   void Multiply (const Standard_Real theScalar)
187   {
188     x *= theScalar;
189     y *= theScalar;
190   }
191
192   void operator*= (const Standard_Real theScalar) { Multiply (theScalar); }
193
194   //! @code
195   //! <me>.X() = <me>.X() * theOther.X();
196   //! <me>.Y() = <me>.Y() * theOther.Y();
197   void Multiply (const gp_XY& theOther)
198   {
199     x *= theOther.x;
200     y *= theOther.y;
201   }
202
203   void operator*= (const gp_XY& theOther) { Multiply (theOther); }
204
205   //! <me> = theMatrix * <me>
206   void Multiply (const gp_Mat2d& theMatrix);
207
208   void operator*= (const gp_Mat2d& theMatrix) { Multiply (theMatrix); }
209
210   //! @code
211   //! New.X() = <me>.X() * theScalar;
212   //! New.Y() = <me>.Y() * theScalar;
213   Standard_NODISCARD gp_XY Multiplied (const Standard_Real theScalar) const { return gp_XY (x * theScalar, y * theScalar); }
214
215   Standard_NODISCARD gp_XY operator*  (const Standard_Real theScalar) const { return Multiplied (theScalar); }
216   //! @code
217   //! new.X() = <me>.X() * theOther.X();
218   //! new.Y() = <me>.Y() * theOther.Y();
219   Standard_NODISCARD gp_XY Multiplied (const gp_XY& theOther) const { return gp_XY (x * theOther.X(), y * theOther.Y()); }
220
221   //! New = theMatrix * <me>
222   //! @endcode
223   Standard_NODISCARD gp_XY Multiplied (const gp_Mat2d& theMatrix) const
224   {
225     const Standard_Address aM = (Standard_Address) &(theMatrix.Value (1, 1));
226     return gp_XY (Mat2d00 * x + Mat2d01 * y, Mat2d10 * x + Mat2d11 * y);
227   }
228
229   Standard_NODISCARD gp_XY operator*  (const gp_Mat2d& theMatrix) const { return Multiplied (theMatrix); }
230   //! @code
231   //! <me>.X() = <me>.X()/ <me>.Modulus()
232   //! <me>.Y() = <me>.Y()/ <me>.Modulus()
233   //! @endcode
234   //! Raises ConstructionError if <me>.Modulus() <= Resolution from gp
235   void Normalize();
236
237   //! @code
238   //! New.X() = <me>.X()/ <me>.Modulus()
239   //! New.Y() = <me>.Y()/ <me>.Modulus()
240   //! @endcode
241   //! Raises ConstructionError if <me>.Modulus() <= Resolution from gp
242   Standard_NODISCARD gp_XY Normalized() const
243   {
244     Standard_Real aD = Modulus();
245     Standard_ConstructionError_Raise_if (aD <= gp::Resolution(), "gp_XY::Normalized() - vector has zero norm");
246     return gp_XY (x / aD, y / aD);
247   }
248
249   //! @code
250   //! <me>.X() = -<me>.X()
251   //! <me>.Y() = -<me>.Y()
252   inline void Reverse()
253   {
254     x = -x;
255     y = -y;
256   }
257
258   //! @code
259   //! New.X() = -<me>.X()
260   //! New.Y() = -<me>.Y()
261   Standard_NODISCARD gp_XY Reversed() const
262   {
263     gp_XY aCoord2D = *this;
264     aCoord2D.Reverse();
265     return aCoord2D;
266   }
267
268   Standard_NODISCARD gp_XY operator-() const { return Reversed(); }
269
270   //! Computes  the following linear combination and
271   //! assigns the result to this number pair:
272   //! @code
273   //! theA1 * theXY1 + theA2 * theXY2
274   inline void SetLinearForm (const Standard_Real theA1, const gp_XY& theXY1,
275                              const Standard_Real theA2, const gp_XY& theXY2)
276   {
277     x = theA1 * theXY1.x + theA2 * theXY2.x;
278     y = theA1 * theXY1.y + theA2 * theXY2.y;
279   }
280
281   //! --  Computes  the following linear combination and
282   //! assigns the result to this number pair:
283   //! @code
284   //! theA1 * theXY1 + theA2 * theXY2 + theXY3
285   inline void SetLinearForm (const Standard_Real theA1, const gp_XY& theXY1,
286                              const Standard_Real theA2, const gp_XY& theXY2,
287                              const gp_XY& theXY3)
288   {
289     x = theA1 * theXY1.x + theA2 * theXY2.x + theXY3.x;
290     y = theA1 * theXY1.y + theA2 * theXY2.y + theXY3.y;
291   }
292
293   //! Computes  the following linear combination and
294   //! assigns the result to this number pair:
295   //! @code
296   //! theA1 * theXY1 + theXY2
297   inline void SetLinearForm (const Standard_Real theA1, const gp_XY& theXY1,
298                              const gp_XY& theXY2)
299   {
300     x = theA1 * theXY1.x + theXY2.x;
301     y = theA1 * theXY1.y + theXY2.y;
302   }
303
304   //! Computes  the following linear combination and
305   //! assigns the result to this number pair:
306   //! @code
307   //! theXY1 + theXY2
308   inline void SetLinearForm (const gp_XY& theXY1,
309                              const gp_XY& theXY2)
310   {
311     x = theXY1.x + theXY2.x;
312     y = theXY1.y + theXY2.y;
313   }
314
315   //! @code
316   //! <me>.X() = <me>.X() - theOther.X()
317   //! <me>.Y() = <me>.Y() - theOther.Y()
318   inline void Subtract (const gp_XY& theOther)
319   {
320     x -= theOther.x;
321     y -= theOther.y;
322   }
323
324   void operator-= (const gp_XY& theOther) { Subtract (theOther); }
325
326   //! @code
327   //! new.X() = <me>.X() - theOther.X()
328   //! new.Y() = <me>.Y() - theOther.Y()
329   //! @endcode
330   Standard_NODISCARD gp_XY Subtracted (const gp_XY& theOther) const
331   {
332     gp_XY aCoord2D = *this;
333     aCoord2D.Subtract (theOther);
334     return aCoord2D;
335   }
336
337   Standard_NODISCARD gp_XY operator-  (const gp_XY& theOther) const { return Subtracted (theOther); }
338
339 private:
340
341   Standard_Real x;
342   Standard_Real y;
343
344 };
345
346 //=======================================================================
347 //function :  Multiply
348 // purpose :
349 //=======================================================================
350 inline void gp_XY::Multiply (const gp_Mat2d& theMatrix)
351 {
352   const Standard_Address aM = (Standard_Address) &(theMatrix.Value (1, 1));
353   Standard_Real aXresult = Mat2d00 * x + Mat2d01 * y;
354   y = Mat2d10 * x + Mat2d11 * y;
355   x = aXresult;
356 }
357
358 //=======================================================================
359 //function :  Normalize
360 // purpose :
361 //=======================================================================
362 inline void gp_XY::Normalize()
363 {
364   Standard_Real aD = Modulus();
365   Standard_ConstructionError_Raise_if (aD <= gp::Resolution(), "gp_XY::Normalize() - vector has zero norm");
366   x = x / aD;
367   y = y / aD;
368 }
369
370 //=======================================================================
371 //function :  operator*
372 // purpose :
373 //=======================================================================
374 inline gp_XY operator* (const gp_Mat2d& theMatrix,
375                         const gp_XY&    theCoord1)
376 {
377   return theCoord1.Multiplied (theMatrix);
378 }
379
380 //=======================================================================
381 //function :  operator*
382 // purpose :
383 //=======================================================================
384 inline gp_XY operator* (const Standard_Real theScalar,
385                         const gp_XY&        theCoord1)
386 {
387   return theCoord1.Multiplied (theScalar);
388 }
389
390 #endif // _gp_XY_HeaderFile