0024530: TKMesh - remove unused package IntPoly
[occt.git] / src / IntTools / IntTools_TopolTool.cxx
CommitLineData
973c2be1 1// Copyright (c) 1999-2014 OPEN CASCADE SAS
b311480e 2//
973c2be1 3// This file is part of Open CASCADE Technology software library.
b311480e 4//
973c2be1 5// This library is free software; you can redistribute it and / or modify it
6// under the terms of the GNU Lesser General Public version 2.1 as published
7// by the Free Software Foundation, with special exception defined in the file
8// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
9// distribution for complete text of the license and disclaimer of any warranty.
b311480e 10//
973c2be1 11// Alternatively, this file may be used under the terms of Open CASCADE
12// commercial license or contractual agreement.
b311480e 13
7fd59977 14#include <IntTools_TopolTool.ixx>
15
16#include <Standard_NotImplemented.hxx>
17#include <Precision.hxx>
18#include <TColgp_Array2OfPnt.hxx>
19#include <Geom_BSplineSurface.hxx>
20#include <Geom_BezierSurface.hxx>
21#include <gp_Circ.hxx>
22#include <gp_Cone.hxx>
23#include <ElSLib.hxx>
24
25#include <TColStd_HArray1OfReal.hxx>
26
27static void Analyse(const TColgp_Array2OfPnt& array2,
28 Standard_Integer& theNbSamplesU,
29 Standard_Integer& theNbSamplesV);
30
31// =====================================================================================
32// function: Constructor
33// purpose:
34// =====================================================================================
35IntTools_TopolTool::IntTools_TopolTool()
36{
37 myNbSmplU = 0;
38 myNbSmplV = 0;
39 myDU = 1.;
40 myDV = 1.;
41}
42
43// =====================================================================================
44// function: Constructor
45// purpose:
46// =====================================================================================
47IntTools_TopolTool::IntTools_TopolTool(const Handle(Adaptor3d_HSurface)& theSurface)
48{
49 Initialize(theSurface);
50 myNbSmplU = 0;
51 myNbSmplV = 0;
52 myDU = 1.;
53 myDV = 1.;
54}
55
56// =====================================================================================
57// function: Initialize
58// purpose:
59// =====================================================================================
60void IntTools_TopolTool::Initialize()
61{
62 Standard_NotImplemented::Raise("IntTools_TopolTool::Initialize ()");
63}
64
65// =====================================================================================
66// function: Initialize
67// purpose:
68// =====================================================================================
69void IntTools_TopolTool::Initialize(const Handle(Adaptor3d_HSurface)& theSurface)
70{
71 Adaptor3d_TopolTool::Initialize(theSurface);
72 //myS = theSurface;
73 myNbSmplU = 0;
74 myNbSmplV = 0;
75 myDU = 1.;
76 myDV = 1.;
77}
78
79// =====================================================================================
80// function: ComputeSamplePoints
81// purpose:
82// =====================================================================================
83void IntTools_TopolTool::ComputeSamplePoints()
84{
85 Standard_Real uinf, usup, vinf, vsup;
86 uinf = myS->FirstUParameter();
87 usup = myS->LastUParameter();
88 vinf = myS->FirstVParameter();
89 vsup = myS->LastVParameter();
90 const Standard_Integer aMaxNbSample = 50;
91
92 if (usup < uinf) { Standard_Real temp = uinf; uinf = usup; usup = temp; }
93 if (vsup < vinf) { Standard_Real temp = vinf; vinf = vsup; vsup = temp; }
94 Standard_Boolean isbiguinf, isbigusup, isbigvinf, isbigvsup;
95 isbiguinf = Precision::IsNegativeInfinite(uinf);
96 isbigusup = Precision::IsPositiveInfinite(usup);
97 isbigvinf = Precision::IsNegativeInfinite(vinf);
98 isbigvsup = Precision::IsPositiveInfinite(vsup);
99
100 if(isbiguinf && isbigusup) {uinf = -1.e5; usup = 1.e5;}
101 else if(isbiguinf) {uinf = usup - 2.e5;}
102 else if(isbigusup) {usup = uinf + 2.e5;}
103
104 if(isbigvinf && isbigvsup) {vinf = -1.e5; vsup = 1.e5;}
105 else if(isbigvinf) {vinf = vsup - 2.e5;}
106 else if(isbigvsup) {vsup = vinf + 2.e5;}
107 myU0 = uinf;
108 myV0 = vinf;
109
5cbfdb41 110 Standard_Integer nbsu = 0,nbsv = 0;
7fd59977 111 GeomAbs_SurfaceType typS = myS->GetType();
112
113 switch(typS) {
114 case GeomAbs_Plane: {
115 nbsu = 10; nbsv = 10;
116 }
117 break;
118 case GeomAbs_Cylinder: {
119 Standard_Real aRadius = myS->Cylinder().Radius();
c6541a0c 120 Standard_Real aMaxAngle = M_PI * 0.5;
7fd59977 121 Standard_Real aDeflection = 1.e-02;
122
123 if(aRadius > aDeflection) {
124 aMaxAngle = ACos(1. - aDeflection / aRadius) * 2.;
125 }
126 if(aMaxAngle > Precision::Angular()) {
127 nbsu = Standard_Integer((usup-uinf) / aMaxAngle);
128 }
129 nbsv = (Standard_Integer)(vsup-vinf);
130 nbsv /= 10;
131
132 if(nbsu < 2) nbsu = 2;
133 if(nbsv < 2) nbsv = 2;
134
135// if(nbsu < 10) nbsu = 10;
136// if(nbsv < 10) nbsv = 10;
137 if(nbsu > aMaxNbSample) nbsu = aMaxNbSample;
138 if(nbsv > aMaxNbSample) nbsv = aMaxNbSample;
139 }
140 break;
141 case GeomAbs_Cone: {
142 gp_Cone aCone = myS->Cone();
143 gp_Circ aCircle = ElSLib::ConeVIso(aCone.Position(), aCone.RefRadius(), aCone.SemiAngle(), vinf);
144 Standard_Real aRadius = aCircle.Radius();
145 aCircle = ElSLib::ConeVIso(aCone.Position(), aCone.RefRadius(), aCone.SemiAngle(), vsup);
146
147 if(aRadius < aCircle.Radius())
148 aRadius = aCircle.Radius();
c6541a0c 149 Standard_Real aMaxAngle = M_PI * 0.5;
7fd59977 150 Standard_Real aDeflection = 1.e-02;
151
152 if(aRadius > aDeflection) {
153 aMaxAngle = ACos(1. - aDeflection / aRadius) * 2.;
154 }
155
156 if(aMaxAngle > Precision::Angular()) {
157 nbsu = Standard_Integer((usup - uinf) / aMaxAngle);
158 }
159 nbsv = (Standard_Integer)(vsup - vinf);
160 nbsv /= 10;
161
162// if(nbsu < 2) nbsu = 2;
163// if(nbsv < 2) nbsv = 2;
164
165 if(nbsu < 10) nbsu = 10;
166 if(nbsv < 10) nbsv = 10;
167 if(nbsu > aMaxNbSample) nbsu = aMaxNbSample;
168 if(nbsv > aMaxNbSample) nbsv = aMaxNbSample;
169 }
170 break;
171 case GeomAbs_Sphere:
172 case GeomAbs_Torus: {
173 gp_Circ aCircle;
174 Standard_Real aRadius1, aRadius2;
175
176 if(typS == GeomAbs_Torus) {
177 gp_Torus aTorus = myS->Torus();
178 aCircle = ElSLib::TorusUIso(aTorus.Position(), aTorus.MajorRadius(), aTorus.MinorRadius(), uinf);
179 aRadius2 = aCircle.Radius();
180 aCircle = ElSLib::TorusUIso(aTorus.Position(), aTorus.MajorRadius(), aTorus.MinorRadius(), usup);
181 aRadius2 = (aRadius2 < aCircle.Radius()) ? aCircle.Radius() : aRadius2;
182
183 aCircle = ElSLib::TorusVIso(aTorus.Position(), aTorus.MajorRadius(), aTorus.MinorRadius(), vinf);
184 aRadius1 = aCircle.Radius();
185 aCircle = ElSLib::TorusVIso(aTorus.Position(), aTorus.MajorRadius(), aTorus.MinorRadius(), vsup);
186 aRadius1 = (aRadius1 < aCircle.Radius()) ? aCircle.Radius() : aRadius1;
187 }
188 else {
189 gp_Sphere aSphere = myS->Sphere();
190 aRadius1 = aSphere.Radius();
191 aRadius2 = aSphere.Radius();
192 }
c6541a0c 193 Standard_Real aMaxAngle = M_PI * 0.5;
7fd59977 194 Standard_Real aDeflection = 1.e-02;
195
196 if(aRadius1 > aDeflection) {
197 aMaxAngle = ACos(1. - aDeflection / aRadius1) * 2.;
198 }
199
200 if(aMaxAngle > Precision::Angular()) {
201 nbsu = Standard_Integer((usup - uinf) / aMaxAngle);
202 }
c6541a0c 203 aMaxAngle = M_PI * 0.5;
7fd59977 204
205 if(aRadius2 > aDeflection) {
206 aMaxAngle = ACos(1. - aDeflection / aRadius2) * 2.;
207 }
208
209 if(aMaxAngle > Precision::Angular()) {
210 nbsv = Standard_Integer((vsup - vinf) / aMaxAngle);
211 }
212 if(nbsu < 10) nbsu = 10;
213 if(nbsv < 10) nbsv = 10;
214 if(nbsu > aMaxNbSample) nbsu = aMaxNbSample;
215 if(nbsv > aMaxNbSample) nbsv = aMaxNbSample;
216 }
217 break;
218 case GeomAbs_BezierSurface: {
219 nbsv = 3 + myS->NbVPoles();
220 nbsu = 3 + myS->NbUPoles();
221
222 if(nbsu > 10 || nbsv > 10) {
223 TColgp_Array2OfPnt array2(1, myS->NbUPoles(), 1, myS->NbVPoles());
224 myS->Bezier()->Poles(array2);
225 Analyse(array2, nbsu, nbsv);
226 }
227
228 if(nbsu < 10) nbsu = 10;
229 if(nbsv < 10) nbsv = 10;
230 }
231 break;
232 case GeomAbs_BSplineSurface: {
233 nbsv = myS->NbVKnots(); nbsv *= myS->VDegree(); if(nbsv < 4) nbsv=4;
234 nbsu = myS->NbUKnots(); nbsu *= myS->UDegree(); if(nbsu < 4) nbsu=4;
235
236 if(nbsu > 10 || nbsv > 10) {
237 TColgp_Array2OfPnt array2(1, myS->NbUPoles(), 1, myS->NbVPoles());
238 myS->BSpline()->Poles(array2);
239 Analyse(array2, nbsu, nbsv);
240 }
241 if(nbsu < 10) nbsu = 10;
242 if(nbsv < 10) nbsv = 10;
243 }
244 break;
245 case GeomAbs_SurfaceOfExtrusion: {
246 nbsu = 15;
247 nbsv = (Standard_Integer)(vsup - vinf);
248 nbsv /= 10;
249 if(nbsv < 15) nbsv = 15;
250 if(nbsv > aMaxNbSample) nbsv = aMaxNbSample;
251 }
252 break;
253 case GeomAbs_SurfaceOfRevolution: {
254 nbsv = 15; nbsu = 15;
255 }
256 break;
257 default: {
258 nbsu = 10; nbsv = 10;
259 }
260 break;
261 }
262 myNbSmplU = nbsu;
263 myNbSmplV = nbsv;
264
265 myNbSamplesU = myNbSmplU;
266 myNbSamplesV = myNbSmplV;
267
268 myDU = (usup - uinf)/(myNbSmplU + 1);
269 myDV = (vsup - vinf)/(myNbSmplV + 1);
270}
271
272// =====================================================================================
273// function: NbSamplesU
274// purpose:
275// =====================================================================================
276Standard_Integer IntTools_TopolTool::NbSamplesU()
277{
278 if(myNbSmplU <= 0) {
279 ComputeSamplePoints();
280 }
281 return myNbSmplU;
282}
283
284// =====================================================================================
285// function: NbSamplesV
286// purpose:
287// =====================================================================================
288Standard_Integer IntTools_TopolTool::NbSamplesV()
289{
290 if(myNbSmplV <= 0) {
291 ComputeSamplePoints();
292 }
293 return myNbSmplV;
294}
295
296// =====================================================================================
297// function: NbSamples
298// purpose:
299// =====================================================================================
300Standard_Integer IntTools_TopolTool::NbSamples()
301{
302 if(myNbSmplU <= 0) {
303 ComputeSamplePoints();
304 }
305 return(myNbSmplU * myNbSmplV);
306}
307
308// =====================================================================================
309// function: SamplePoint
310// purpose:
311// =====================================================================================
312void IntTools_TopolTool::SamplePoint(const Standard_Integer Index,
313 gp_Pnt2d& P2d,
314 gp_Pnt& P3d)
315{
316 if (myUPars.IsNull())
317 {
318 if(myNbSmplU <= 0) {
319 ComputeSamplePoints();
320 }
321 Standard_Integer iv = 1 + Index / myNbSmplU;
322 Standard_Integer iu = 1 + Index - (iv - 1) * myNbSmplU;
323 Standard_Real u = myU0 + iu * myDU;
324 Standard_Real v = myV0 + iv * myDV;
325 P2d.SetCoord(u, v);
326 P3d = myS->Value(u, v);
327 }
328 else
329 Adaptor3d_TopolTool::SamplePoint(Index, P2d, P3d);
330}
331
332
333//=======================================================================
334// function : Analyse
335// purpose :
336//=======================================================================
337void Analyse(const TColgp_Array2OfPnt& array2,
338 Standard_Integer& theNbSamplesU,
339 Standard_Integer& theNbSamplesV)
340{
341 gp_Vec Vi,Vip1;
342 Standard_Integer sh,nbch,i,j;
343 const Standard_Integer nbup = array2.UpperRow() - array2.LowerRow() + 1;
344 const Standard_Integer nbvp = array2.UpperCol() - array2.LowerCol() + 1;
345
346 sh = 1;
347 nbch = 0;
348 if(nbvp>2) {
349
350 for(i = array2.LowerRow(); i <= array2.UpperRow(); i++) {
351 const gp_Pnt& A=array2.Value(i,1);
352 const gp_Pnt& B=array2.Value(i,2);
353 const gp_Pnt& C=array2.Value(i,3);
354 Vi.SetCoord(C.X()-B.X()-B.X()+A.X(),
355 C.Y()-B.Y()-B.Y()+A.Y(),
356 C.Z()-B.Z()-B.Z()+A.Z());
357 Standard_Integer locnbch=0;
358
359 for(j = array2.LowerCol() + 2; j < array2.UpperCol();j++) { //-- essai
360 const gp_Pnt& Ax=array2.Value(i,j-1);
361 const gp_Pnt& Bx=array2.Value(i,j);
362 const gp_Pnt& Cx=array2.Value(i,j+1);
363 Vip1.SetCoord(Cx.X()-Bx.X()-Bx.X()+Ax.X(),
364 Cx.Y()-Bx.Y()-Bx.Y()+Ax.Y(),
365 Cx.Z()-Bx.Z()-Bx.Z()+Ax.Z());
366 Standard_Real pd = Vi.Dot(Vip1);
367 Vi=Vip1;
368 if(pd>1.0e-7 || pd<-1.0e-7) {
369 if(pd>0) { if(sh==-1) { sh=1; locnbch++; } }
370 else { if(sh==1) { sh=-1; locnbch++; } }
371 }
372 }
373 if(locnbch>nbch) {
374 nbch=locnbch;
375 }
376 }
377 }
378 theNbSamplesV = nbch+5;
379
380
381 nbch=0;
382 if(nbup > 2) {
383 for(j = array2.LowerCol(); j <= array2.UpperCol(); j++) {
384 const gp_Pnt& A=array2.Value(array2.LowerRow(), j);
385 const gp_Pnt& B=array2.Value(array2.LowerRow() + 1, j);
386 const gp_Pnt& C=array2.Value(array2.LowerRow() + 2, j);
387 Vi.SetCoord(C.X()-B.X()-B.X()+A.X(),
388 C.Y()-B.Y()-B.Y()+A.Y(),
389 C.Z()-B.Z()-B.Z()+A.Z());
390 Standard_Integer locnbch=0;
391
392 for(i = array2.LowerRow() + 2; i < array2.UpperRow(); i++) { //-- essai
393 const gp_Pnt& Ax=array2.Value(i-1,j);
394 const gp_Pnt& Bx=array2.Value(i,j);
395 const gp_Pnt& Cx=array2.Value(i+1,j);
396 Vip1.SetCoord(Cx.X()-Bx.X()-Bx.X()+Ax.X(),
397 Cx.Y()-Bx.Y()-Bx.Y()+Ax.Y(),
398 Cx.Z()-Bx.Z()-Bx.Z()+Ax.Z());
399 Standard_Real pd = Vi.Dot(Vip1);
400 Vi=Vip1;
401 if(pd>1.0e-7 || pd<-1.0e-7) {
402 if(pd>0) { if(sh==-1) { sh=1; locnbch++; } }
403 else { if(sh==1) { sh=-1; locnbch++; } }
404 }
405 }
406 if(locnbch>nbch) nbch=locnbch;
407 }
408 }
409 theNbSamplesU = nbch+5;
410}
411
412//Modified IFV
413//=======================================================================
414//function : SamplePnts
415//purpose :
416//=======================================================================
417
418void IntTools_TopolTool::SamplePnts(const Standard_Real theDefl,
419 const Standard_Integer theNUmin,
420 const Standard_Integer theNVmin)
421{
422 Adaptor3d_TopolTool::SamplePnts(theDefl, theNUmin, theNVmin);
423
424 myNbSmplU = Adaptor3d_TopolTool::NbSamplesU();
425 myNbSmplV = Adaptor3d_TopolTool::NbSamplesV();
426
427 myU0 = myUPars->Value(1);
428 myV0 = myVPars->Value(1);
429
430 myDU = (myUPars->Value(myNbSmplU) - myU0)/(myNbSmplU-1);
431 myDV = (myVPars->Value(myNbSmplV) - myU0)/(myNbSmplV-1);
432}