0023024: Update headers of OCCT files
[occt.git] / src / UnitsMethods / UnitsMethods.cxx
CommitLineData
b311480e 1// Copyright (c) 1999-2012 OPEN CASCADE SAS
2//
3// The content of this file is subject to the Open CASCADE Technology Public
4// License Version 6.5 (the "License"). You may not use the content of this file
5// except in compliance with the License. Please obtain a copy of the License
6// at http://www.opencascade.org and read it completely before using this file.
7//
8// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
9// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
10//
11// The Original Code and all software distributed under the License is
12// distributed on an "AS IS" basis, without warranty of any kind, and the
13// Initial Developer hereby disclaims all such warranties, including without
14// limitation, any warranties of merchantability, fitness for a particular
15// purpose or non-infringement. Please see the License for the specific terms
16// and conditions governing the rights and limitations under the License.
17
7fd59977 18#include <UnitsMethods.ixx>
19
20#include <Geom_Plane.hxx>
21#include <Geom_Surface.hxx>
22#include <Geom_ConicalSurface.hxx>
23#include <Geom_CylindricalSurface.hxx>
24#include <Geom_SphericalSurface.hxx>
25#include <Geom_ToroidalSurface.hxx>
26#include <Geom_SurfaceOfRevolution.hxx>
27#include <Geom2dConvert.hxx>
28#include <Geom2d_BSplineCurve.hxx>
29#include <Geom2d_Circle.hxx>
30#include <Geom2d_Curve.hxx>
31#include <Geom2d_Ellipse.hxx>
32#include <Geom2d_Hyperbola.hxx>
33#include <Geom2d_Line.hxx>
34#include <Geom2d_Parabola.hxx>
35#include <gp.hxx>
36#include <gp_GTrsf2d.hxx>
37#include <gp_Trsf2d.hxx>
38#include <gp_Pnt2d.hxx>
39#include <gp_Dir2d.hxx>
40
41static Standard_Real theLengthFactor = 1.;
42static Standard_Real thePlaneAngleFactor = 1.;
43static Standard_Real theSolidAngleFactor = 1.;
44static Standard_Boolean set3d = Standard_True;
45
46static Standard_Real FactRD = 1.;
47static Standard_Real FactDR = 1.;
48
49static Standard_Real theCasCadeLengthUnit = 1.; // abv 28 Feb 00
50
51// ============================================================================
52// Method :
53// Purpose:
54// ============================================================================
55
56void UnitsMethods::InitializeFactors(const Standard_Real LengthFactor, const Standard_Real PlaneAngleFactor, const Standard_Real SolidAngleFactor)
57{
58 theLengthFactor = LengthFactor;
59 thePlaneAngleFactor = PlaneAngleFactor;
60 theSolidAngleFactor = SolidAngleFactor;
61 FactRD = 1./PlaneAngleFactor;
62 FactDR = PlaneAngleFactor;
63}
64
65// ============================================================================
66// Method :
67// Purpose:
68// ============================================================================
69
70Standard_Real UnitsMethods ::LengthFactor()
71{
72 return theLengthFactor;
73}
74
75// ============================================================================
76// Method :
77// Purpose:
78// ============================================================================
79
80Standard_Real UnitsMethods::PlaneAngleFactor()
81{
82 return thePlaneAngleFactor;
83}
84
85// ============================================================================
86// Method :
87// Purpose:
88// ============================================================================
89
90Standard_Real UnitsMethods::SolidAngleFactor()
91{
92 return theSolidAngleFactor;
93}
94
95// ============================================================================
96// Method :
97// Purpose:
98// ============================================================================
99
100void UnitsMethods::Set3dConversion(const Standard_Boolean B)
101{
102 set3d = B;
103}
104
105// ============================================================================
106// Method :
107// Purpose:
108// ============================================================================
109
110Standard_Boolean UnitsMethods::Convert3d()
111{
112 return set3d;
113}
114
115
116// ============================================================================
117// Method :
118// Purpose:
119// ============================================================================
120
121Handle(Geom2d_Curve) UnitsMethods::RadianToDegree
122 (const Handle(Geom2d_Curve) & theCurve2d,
123 const Handle(Geom_Surface) & theSurf)
124{
125 Handle(Geom2d_Curve) aCurve2d = Handle(Geom2d_Curve)::DownCast(theCurve2d->Copy());
126 Standard_Real uFact = 1.;
127 Standard_Real vFact = 1.;
128 Standard_Real LengthFact = 1. / UnitsMethods::LengthFactor();
129 Standard_Real AngleFact = FactRD; // 180./PI; pilotable
130
131 gp_Pnt2d Pt1;
132 gp_XY pXY;
133 gp_GTrsf2d tMatu , tMatv;
134
135 // theSurf is a CylindricalSurface or a ConicalSurface or
136 // a ToroidalSurface or a SphericalSurface or
137 // a SurfaceOfRevolution
138 if (theSurf->IsKind(STANDARD_TYPE(Geom_SphericalSurface)) ||
139 theSurf->IsKind(STANDARD_TYPE(Geom_ToroidalSurface))) {
140 uFact = vFact = AngleFact;
141 }
142 else if (theSurf->IsKind(STANDARD_TYPE(Geom_CylindricalSurface))) {
143 uFact = AngleFact;
144 vFact = LengthFact;
145 }
146 else if ( theSurf->IsKind(STANDARD_TYPE(Geom_SurfaceOfRevolution))) {
147 uFact = AngleFact;
148 }
149 else if (theSurf->IsKind(STANDARD_TYPE(Geom_ConicalSurface))) {
150 Handle(Geom_ConicalSurface) conicS =
151 Handle(Geom_ConicalSurface)::DownCast(theSurf);
152 Standard_Real semAng = conicS->SemiAngle();
153 uFact = AngleFact;
154 vFact = LengthFact * Cos(semAng);
155 }
156 else if (theSurf->IsKind(STANDARD_TYPE(Geom_Plane))) {
157 uFact = vFact = LengthFact;
158 if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Circle))) {
159 Handle(Geom2d_Circle) newCircle =
160 Handle(Geom2d_Circle)::DownCast(aCurve2d);
161 gp_Pnt2d Loc = newCircle->Location();
162 Loc.SetX(Loc.X()*LengthFact);
163 Loc.SetY(Loc.Y()*LengthFact);
164 newCircle->SetRadius(newCircle->Radius()*LengthFact);
165 return newCircle;
166 }
167 else if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Ellipse))) {
168 Handle(Geom2d_Ellipse) newEllipse =
169 Handle(Geom2d_Ellipse)::DownCast(aCurve2d);
170 gp_Pnt2d Loc = newEllipse->Location();
171 Loc.SetX(Loc.X()*LengthFact);
172 Loc.SetY(Loc.Y()*LengthFact);
173 newEllipse->SetMajorRadius(newEllipse->MajorRadius()*LengthFact);
174 newEllipse->SetMinorRadius(newEllipse->MinorRadius()*LengthFact);
175 return newEllipse;
176 }
177 }
178 else {
179// debug
180// cout <<"UnitsMethods: SurfType = "<< aSurface->DynamicType();
181 return aCurve2d;
182 }
183
184 if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Line))) {
185 Handle(Geom2d_Line) aLine2d = Handle(Geom2d_Line)::DownCast(aCurve2d);
186
187 gp_Pnt2d myLoc = aLine2d->Location();
188 gp_Dir2d myDir = aLine2d->Direction();
189
190 gp_Pnt2d myNewLoc;
191 myNewLoc.SetCoord(myLoc.X()*uFact, myLoc.Y()*vFact);
192
193 gp_Dir2d myNewDir;
194 myNewDir.SetCoord(myDir.X()*uFact, myDir.Y()*vFact);
195
196 Handle(Geom2d_Line) myNewLine2d = Handle(Geom2d_Line)::DownCast(aLine2d->Copy());
197 myNewLine2d->SetLocation(myNewLoc);
198 myNewLine2d->SetDirection(myNewDir);
199
200 return myNewLine2d;
201 }
202 else if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Conic))) {
203 if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Circle))) {
204 Handle(Geom2d_Circle) aCirc2d =
205 Handle(Geom2d_Circle)::DownCast(aCurve2d);
206 Handle(Geom2d_BSplineCurve) aBSpline2d =
207 Geom2dConvert::CurveToBSplineCurve(aCirc2d);
208 aCurve2d = aBSpline2d;
209 }
210 else if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Ellipse))) {
211 Handle(Geom2d_Ellipse) aHel2d =
212 Handle(Geom2d_Ellipse)::DownCast(aCurve2d);
213 Handle(Geom2d_BSplineCurve) aBSpline2d =
214 Geom2dConvert::CurveToBSplineCurve(aHel2d);
215 aCurve2d = aBSpline2d;
216 }
217 else if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Parabola))) {
218#ifdef DEBUG
219 cout << "PCURVE of Parabola type in U or V Periodic Surface" << endl;
220 cout << "Parameters Not transformed to Degree" << endl;
221#endif
222 }
223 else if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_Hyperbola))) {
224#ifdef DEBUG
225 cout << "PCURVE of Hyperbola type in U or V Periodic Surface" << endl;
226 cout << "Parameters Not transformed to Degree" << endl;
227#endif
228 }
229
230 }
231
232 // Compute affinity
233 tMatu.SetAffinity(gp::OY2d(), uFact);
234 tMatv.SetAffinity(gp::OX2d(), vFact);
235
236 if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_BoundedCurve))) {
237 if (aCurve2d->IsKind(STANDARD_TYPE(Geom2d_BSplineCurve))) {
238 Handle(Geom2d_BSplineCurve) aBSpline2d =
239 Handle(Geom2d_BSplineCurve)::DownCast(aCurve2d);
240 Handle(Geom2d_BSplineCurve) myNewBSpline2d =
241 Handle(Geom2d_BSplineCurve)::DownCast(aBSpline2d->Copy());
242 Standard_Integer nbPol = aBSpline2d->NbPoles();
243 for (Standard_Integer i = 1; i<=nbPol ; i++) {
244 pXY = aBSpline2d->Pole(i).XY();
245 tMatu.Transforms(pXY);
246 tMatv.Transforms(pXY);
247 Pt1.SetXY(pXY);
248 myNewBSpline2d->SetPole(i, Pt1);
249 }
250 return myNewBSpline2d;
251 }
252 else {
253#ifdef DEBUG
254 cout << "PCURVE of Other Types of Bounded Curve in U or V Periodic Surface" << endl;
255 cout << "Parameters Not transformed to Degree" << endl;
256#endif
257 }
258 }
259 return aCurve2d;
260}
261
262//=============================================================================
263// DegreeToRadian: 1. Change definition of the pcurves according to Length
264// Factor
265// 2. STEP cylinder, torus, cone and sphere are parametrized
266// from 0 to 360 degree
267// Then pcurves parameter have to be transformed
268// from DEGREE to RADIAN
269//=============================================================================
270
271Handle(Geom2d_Curve) UnitsMethods::DegreeToRadian
272 (const Handle(Geom2d_Curve) & thePcurve,
273 const Handle(Geom_Surface) & aSurface)
274{
275 Handle(Geom2d_Curve) aPcurve = Handle(Geom2d_Curve)::DownCast(thePcurve->Copy());
276 Standard_Real uFact = 1.;
277 Standard_Real vFact = 1.;
278 Standard_Real LengthFact = UnitsMethods::LengthFactor();
279 Standard_Real AngleFact = FactDR; // PI/180.; pilotable
280
281 gp_Pnt2d Pt1;
282 gp_XY pXY;
283 gp_GTrsf2d tMatu , tMatv;
284
285 // What to change ??
286
287 if (aSurface->IsKind(STANDARD_TYPE(Geom_SphericalSurface)) ||
288 aSurface->IsKind(STANDARD_TYPE(Geom_ToroidalSurface))) {
289 uFact = vFact = AngleFact;
290 }
291 else if (aSurface->IsKind(STANDARD_TYPE(Geom_CylindricalSurface))) {
292 uFact = AngleFact;
293 vFact = LengthFact;
294 }
295 else if ( aSurface->IsKind(STANDARD_TYPE(Geom_SurfaceOfRevolution))) {
296 uFact = AngleFact;
297 }
298 else if (aSurface->IsKind(STANDARD_TYPE(Geom_ConicalSurface))) {
299 Handle(Geom_ConicalSurface) conicS =
300 Handle(Geom_ConicalSurface)::DownCast(aSurface);
301 Standard_Real semAng = conicS->SemiAngle();
302 uFact = AngleFact;
303 vFact = LengthFact / Cos(semAng);
304 }
305 else if (aSurface->IsKind(STANDARD_TYPE(Geom_Plane))) {
306 uFact = vFact = LengthFact;
307 if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Circle))) {
308 Handle(Geom2d_Circle) newCircle =
309 Handle(Geom2d_Circle)::DownCast(aPcurve);
310 gp_Pnt2d Loc = newCircle->Location();
311 Loc.SetX(Loc.X()*LengthFact);
312 Loc.SetY(Loc.Y()*LengthFact);
313 newCircle->SetRadius(newCircle->Radius()*LengthFact);
314 return newCircle;
315 }
316 else if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Ellipse))) {
317 Handle(Geom2d_Ellipse) newEllipse =
318 Handle(Geom2d_Ellipse)::DownCast(aPcurve);
319 gp_Pnt2d Loc = newEllipse->Location();
320 Loc.SetX(Loc.X()*LengthFact);
321 Loc.SetY(Loc.Y()*LengthFact);
322 newEllipse->SetMajorRadius(newEllipse->MajorRadius()*LengthFact);
323 newEllipse->SetMinorRadius(newEllipse->MinorRadius()*LengthFact);
324 return newEllipse;
325 }
326 }
327 else {
328// debug
329// cout <<"UnitsMethods: SurfType = "<< aSurface->DynamicType();
330 return aPcurve;
331 }
332
333 if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Conic))) {
334 if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Circle)) ||
335 aPcurve->IsKind(STANDARD_TYPE(Geom2d_Ellipse))) {
336 Handle(Geom2d_BSplineCurve) aBSpline2d =
337 Geom2dConvert::CurveToBSplineCurve(aPcurve);
338 aPcurve = aBSpline2d;
339 }
340 else if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Parabola))) {
341#ifdef DEBUG
342 cout << "PCURVE of Parabola type" << endl;
343 cout << "Parameters Not Yet transformed according to LenghtUnit" << endl;
344#endif
345 return aPcurve;
346 }
347 else if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Hyperbola))) {
348#ifdef DEBUG
349 cout << "PCURVE of Hyperbola type" << endl;
350 cout << "Parameters Not Yet transformed according to LenghtUnit" << endl;
351#endif
352 return aPcurve;
353 }
354 }
355
356 // Compute affinity
357
358 tMatu.SetAffinity(gp::OY2d(), uFact);
359 tMatv.SetAffinity(gp::OX2d(), vFact);
360
361 if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_Line))) {
362 Handle(Geom2d_Line) aLine2d = Handle(Geom2d_Line)::DownCast(aPcurve);
363
364 gp_Pnt2d myLoc = aLine2d->Location();
365 gp_Dir2d myDir = aLine2d->Direction();
366
367 gp_Pnt2d myNewLoc;
368 myNewLoc.SetCoord(myLoc.X()*uFact, myLoc.Y()*vFact);
369
370 gp_Dir2d myNewDir;
371 myNewDir.SetCoord(myDir.X()*uFact, myDir.Y()*vFact);
372
373 aLine2d->SetLocation(myNewLoc);
374 aLine2d->SetDirection(myNewDir);
375
376 aPcurve = aLine2d;
377 }
378 else if (aPcurve->IsKind(STANDARD_TYPE(Geom2d_BSplineCurve))) {
379 Handle(Geom2d_BSplineCurve) aBSpline2d =
380 Handle(Geom2d_BSplineCurve)::DownCast(aPcurve);
381
382// transform the Poles of the BSplineCurve according to AngleFact and LengthFact
383
384 Standard_Integer nbPol = aBSpline2d->NbPoles();
385 for (Standard_Integer i = 1; i<=nbPol ; i++) {
386 pXY = aBSpline2d->Pole(i).XY();
387 tMatu.Transforms(pXY);
388 tMatv.Transforms(pXY);
389 Pt1.SetXY(pXY);
390 aBSpline2d->SetPole(i, Pt1);
391 }
392 aPcurve = aBSpline2d;
393 }
394 else {
395#ifdef DEBUG
396 cout << "DegreeToRadian : Type " << aPcurve->DynamicType();
397 cout << " not yet implemented" << endl;
398#endif
399 }
400 return aPcurve;
401}
402
403// ============================================================================
404// Method :
405// Purpose:
406// ============================================================================
407
408Handle(Geom2d_Curve) UnitsMethods::MirrorPCurve
409(const Handle(Geom2d_Curve) & C2d)
410{
411 Handle(Geom2d_Curve) theMirrored =
412 Handle(Geom2d_Curve)::DownCast(C2d->Copy());
413
414 gp_Trsf2d T;
415 gp_Pnt2d Loc(0.,0.);
416 gp_Dir2d Dir(1.,0.);
417 gp_Ax2d ax2(Loc, Dir);
418 T.SetMirror(ax2);
419 theMirrored->Transform(T);
420 return theMirrored;
421}
422
423//=======================================================================
424//function : GetCasCadeLengthUnit
425//purpose :
426//=======================================================================
427
428Standard_Real UnitsMethods::GetCasCadeLengthUnit ()
429{
430 return theCasCadeLengthUnit;
431}
432
433//=======================================================================
434//function : SetCasCadeLengthUnit
435//purpose :
436//=======================================================================
437
438void UnitsMethods::SetCasCadeLengthUnit (const Standard_Integer unit)
439{
440 theCasCadeLengthUnit = UnitsMethods::GetLengthFactorValue ( unit );
441}
442
443//=======================================================================
444//function : GetLengthFactorValue
445//purpose :
446//=======================================================================
447
448Standard_Real UnitsMethods::GetLengthFactorValue (const Standard_Integer par)
449{
450 switch ( par ) {
451 case 1 : return 25.4;
452 case 2 : return 1.;
453
454 case 4 : return 304.8;
455 case 5 : return 1609270.;
456 case 6 : return 1000.;
457 case 7 : return 1000000.;
458 case 8 : return 0.0254;
459 case 9 : return 0.001;
460 case 10 : return 10.;
461 case 11 : return 0.0000254;
462 default : return 1.;
463 }
464}
465