0024166: Unable to create file with "Save" menu of voxeldemo Qt sample
[occt.git] / src / gp / gp_Dir.cxx
CommitLineData
b311480e 1// Copyright (c) 1995-1999 Matra Datavision
2// Copyright (c) 1999-2012 OPEN CASCADE SAS
3//
4// The content of this file is subject to the Open CASCADE Technology Public
5// License Version 6.5 (the "License"). You may not use the content of this file
6// except in compliance with the License. Please obtain a copy of the License
7// at http://www.opencascade.org and read it completely before using this file.
8//
9// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
10// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
11//
12// The Original Code and all software distributed under the License is
13// distributed on an "AS IS" basis, without warranty of any kind, and the
14// Initial Developer hereby disclaims all such warranties, including without
15// limitation, any warranties of merchantability, fitness for a particular
16// purpose or non-infringement. Please see the License for the specific terms
17// and conditions governing the rights and limitations under the License.
18
7fd59977 19// JCV 07/12/90 Modifs suite a l'introduction des classes XYZ et Mat dans gp
20
21#include <gp_Dir.ixx>
22
7637f2b3 23
7fd59977 24Standard_Real gp_Dir::Angle (const gp_Dir& Other) const
25{
26 // Commentaires :
27 // Au dessus de 45 degres l'arccos donne la meilleur precision pour le
28 // calcul de l'angle. Sinon il vaut mieux utiliser l'arcsin.
29 // Les erreurs commises sont loin d'etre negligeables lorsque l'on est
30 // proche de zero ou de 90 degres.
31 // En 3d les valeurs angulaires sont toujours positives et comprises entre
32 // 0 et PI
33 Standard_Real Cosinus = coord.Dot (Other.coord);
34 if (Cosinus > -0.70710678118655 && Cosinus < 0.70710678118655)
35 return acos (Cosinus);
36 else {
37 Standard_Real Sinus = (coord.Crossed (Other.coord)).Modulus ();
c6541a0c 38 if(Cosinus < 0.0) return M_PI - asin (Sinus);
7fd59977 39 else return asin (Sinus);
40 }
41}
42
43Standard_Real gp_Dir::AngleWithRef (const gp_Dir& Other,
44 const gp_Dir& Vref) const
45{
46 Standard_Real Ang;
47 gp_XYZ XYZ = coord.Crossed (Other.coord);
48 Standard_Real Cosinus = coord.Dot(Other.coord);
49 Standard_Real Sinus = XYZ.Modulus ();
50 if (Cosinus > -0.70710678118655 && Cosinus < 0.70710678118655)
51 Ang = acos (Cosinus);
52 else {
c6541a0c 53 if(Cosinus < 0.0) Ang = M_PI - asin (Sinus);
7fd59977 54 else Ang = asin (Sinus);
55 }
56 if (XYZ.Dot (Vref.coord) >= 0.0) return Ang;
57 else return -Ang;
58}
59
60void gp_Dir::Mirror (const gp_Dir& V)
61{
62 const gp_XYZ& XYZ = V.coord;
63 Standard_Real A = XYZ.X();
64 Standard_Real B = XYZ.Y();
65 Standard_Real C = XYZ.Z();
66 Standard_Real X = coord.X();
67 Standard_Real Y = coord.Y();
68 Standard_Real Z = coord.Z();
69 Standard_Real M1 = 2.0 * A * B;
70 Standard_Real M2 = 2.0 * A * C;
71 Standard_Real M3 = 2.0 * B * C;
72 Standard_Real XX = ((2.0 * A * A) - 1.0) * X + M1 * Y + M2 * Z;
73 Standard_Real YY = M1 * X + ((2.0 * B * B) - 1.0) * Y + M3 * Z;
74 Standard_Real ZZ = M2 * X + M3 * Y + ((2.0 * C * C) - 1.0) * Z;
75 coord.SetCoord(XX,YY,ZZ);
76}
77
78void gp_Dir::Mirror (const gp_Ax1& A1)
79{
80 const gp_XYZ& XYZ = A1.Direction().coord;
81 Standard_Real A = XYZ.X();
82 Standard_Real B = XYZ.Y();
83 Standard_Real C = XYZ.Y();
84 Standard_Real X = coord.X();
85 Standard_Real Y = coord.Y();
86 Standard_Real Z = coord.Z();
87 Standard_Real M1 = 2.0 * A * B;
88 Standard_Real M2 = 2.0 * A * C;
89 Standard_Real M3 = 2.0 * B * C;
90 Standard_Real XX = ((2.0 * A * A) - 1.0) * X + M1 * Y + M2 * Z;
91 Standard_Real YY = M1 * X + ((2.0 * B * B) - 1.0) * Y + M3 * Z;
92 Standard_Real ZZ = M2 * X + M3 * Y + ((2.0 * C * C) - 1.0) * Z;
93 coord.SetCoord(XX,YY,ZZ);
94}
95
96void gp_Dir::Mirror (const gp_Ax2& A2)
97{
7637f2b3
J
98 const gp_Dir& Vz = A2.Direction();
99 Mirror(Vz);
100 Reverse();
7fd59977 101}
102
103void gp_Dir::Transform (const gp_Trsf& T)
104{
105 if (T.Form() == gp_Identity || T.Form() == gp_Translation) { }
106 else if (T.Form() == gp_PntMirror) { coord.Reverse(); }
107 else if (T.Form() == gp_Scale) {
108 if (T.ScaleFactor() < 0.0) { coord.Reverse(); }
109 }
110 else {
111 coord.Multiply (T.HVectorialPart());
112 Standard_Real D = coord.Modulus();
113 coord.Divide(D);
114 if (T.ScaleFactor() < 0.0) { coord.Reverse(); }
115 }
116}
117
118gp_Dir gp_Dir::Mirrored (const gp_Dir& V) const
119{
120 gp_Dir Vres = *this;
121 Vres.Mirror (V);
122 return Vres;
123}
124
125gp_Dir gp_Dir::Mirrored (const gp_Ax1& A1) const
126{
127 gp_Dir V = *this;
128 V.Mirror (A1);
129 return V;
130}
131
132gp_Dir gp_Dir::Mirrored (const gp_Ax2& A2) const
133{
134 gp_Dir V = *this;
135 V.Mirror (A2);
136 return V;
137}
138