Commit | Line | Data |
---|---|---|
b311480e | 1 | // Created on: 1993-01-21 |
2 | // Created by: Remi LEQUETTE | |
3 | // Copyright (c) 1993-1999 Matra Datavision | |
973c2be1 | 4 | // Copyright (c) 1999-2014 OPEN CASCADE SAS |
b311480e | 5 | // |
973c2be1 | 6 | // This file is part of Open CASCADE Technology software library. |
b311480e | 7 | // |
d5f74e42 | 8 | // This library is free software; you can redistribute it and/or modify it under |
9 | // the terms of the GNU Lesser General Public License version 2.1 as published | |
973c2be1 | 10 | // by the Free Software Foundation, with special exception defined in the file |
11 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT | |
12 | // distribution for complete text of the license and disclaimer of any warranty. | |
b311480e | 13 | // |
973c2be1 | 14 | // Alternatively, this file may be used under the terms of Open CASCADE |
15 | // commercial license or contractual agreement. | |
7fd59977 | 16 | |
7fd59977 | 17 | |
42cf5bc1 | 18 | #include <Bnd_Box2d.hxx> |
7fd59977 | 19 | #include <BndLib_Add2dCurve.hxx> |
42cf5bc1 | 20 | #include <BRep_Builder.hxx> |
7fd59977 | 21 | #include <BRep_CurveRepresentation.hxx> |
e50ebf1f | 22 | #include <BRep_GCurve.hxx> |
23 | #include <BRep_ListOfCurveRepresentation.hxx> | |
7fd59977 | 24 | #include <BRep_TEdge.hxx> |
42cf5bc1 | 25 | #include <BRep_Tool.hxx> |
26 | #include <BRepTools.hxx> | |
27 | #include <BRepTools_MapOfVertexPnt2d.hxx> | |
28 | #include <BRepTools_ShapeSet.hxx> | |
11af6cdd | 29 | #include <BRepAdaptor_Surface.hxx> |
7fd59977 | 30 | #include <ElCLib.hxx> |
42cf5bc1 | 31 | #include <Geom2d_Curve.hxx> |
32 | #include <Geom2dAdaptor_Curve.hxx> | |
33 | #include <Geom_BSplineSurface.hxx> | |
34 | #include <Geom_Curve.hxx> | |
35 | #include <Geom_RectangularTrimmedSurface.hxx> | |
36 | #include <Geom_Surface.hxx> | |
37 | #include <gp_Lin2d.hxx> | |
7fd59977 | 38 | #include <gp_Vec2d.hxx> |
42cf5bc1 | 39 | #include <Message_ProgressIndicator.hxx> |
40 | #include <OSD_OpenFile.hxx> | |
41 | #include <Poly_PolygonOnTriangulation.hxx> | |
42 | #include <Poly_Triangulation.hxx> | |
43 | #include <Precision.hxx> | |
7fd59977 | 44 | #include <Standard_ErrorHandler.hxx> |
45 | #include <Standard_Failure.hxx> | |
42cf5bc1 | 46 | #include <Standard_Stream.hxx> |
47 | #include <TColGeom2d_SequenceOfCurve.hxx> | |
48 | #include <TColgp_SequenceOfPnt2d.hxx> | |
49 | #include <TColStd_Array1OfReal.hxx> | |
50 | #include <TColStd_HArray1OfInteger.hxx> | |
51 | #include <TColStd_MapOfTransient.hxx> | |
52 | #include <TColStd_SequenceOfReal.hxx> | |
53 | #include <TopExp.hxx> | |
54 | #include <TopExp_Explorer.hxx> | |
55 | #include <TopoDS.hxx> | |
56 | #include <TopoDS_Compound.hxx> | |
57 | #include <TopoDS_CompSolid.hxx> | |
58 | #include <TopoDS_Edge.hxx> | |
59 | #include <TopoDS_Face.hxx> | |
42cf5bc1 | 60 | #include <TopoDS_Shape.hxx> |
61 | #include <TopoDS_Shell.hxx> | |
62 | #include <TopoDS_Solid.hxx> | |
63 | #include <TopoDS_Vertex.hxx> | |
64 | #include <TopoDS_Wire.hxx> | |
65 | #include <TopTools_SequenceOfShape.hxx> | |
2651bfde | 66 | #include <GeomLib_CheckCurveOnSurface.hxx> |
7fd59977 | 67 | #include <errno.h> |
11af6cdd | 68 | |
69 | ||
70 | //======================================================================= | |
7fd59977 | 71 | //function : UVBounds |
72 | //purpose : | |
73 | //======================================================================= | |
7fd59977 | 74 | void BRepTools::UVBounds(const TopoDS_Face& F, |
75 | Standard_Real& UMin, Standard_Real& UMax, | |
76 | Standard_Real& VMin, Standard_Real& VMax) | |
77 | { | |
78 | Bnd_Box2d B; | |
79 | AddUVBounds(F,B); | |
413b1c1a | 80 | if (!B.IsVoid()) |
81 | { | |
82 | B.Get(UMin,VMin,UMax,VMax); | |
83 | } | |
84 | else | |
85 | { | |
86 | UMin = UMax = VMin = VMax = 0.0; | |
87 | } | |
7fd59977 | 88 | } |
89 | ||
90 | //======================================================================= | |
91 | //function : UVBounds | |
92 | //purpose : | |
93 | //======================================================================= | |
94 | ||
95 | void BRepTools::UVBounds(const TopoDS_Face& F, | |
96 | const TopoDS_Wire& W, | |
97 | Standard_Real& UMin, Standard_Real& UMax, | |
98 | Standard_Real& VMin, Standard_Real& VMax) | |
99 | { | |
100 | Bnd_Box2d B; | |
101 | AddUVBounds(F,W,B); | |
413b1c1a | 102 | if (!B.IsVoid()) |
103 | { | |
104 | B.Get(UMin,VMin,UMax,VMax); | |
105 | } | |
106 | else | |
107 | { | |
108 | UMin = UMax = VMin = VMax = 0.0; | |
109 | } | |
7fd59977 | 110 | } |
111 | ||
112 | ||
113 | //======================================================================= | |
114 | //function : UVBounds | |
115 | //purpose : | |
116 | //======================================================================= | |
117 | ||
118 | void BRepTools::UVBounds(const TopoDS_Face& F, | |
119 | const TopoDS_Edge& E, | |
120 | Standard_Real& UMin, Standard_Real& UMax, | |
121 | Standard_Real& VMin, Standard_Real& VMax) | |
122 | { | |
123 | Bnd_Box2d B; | |
124 | AddUVBounds(F,E,B); | |
413b1c1a | 125 | if (!B.IsVoid()) |
126 | { | |
127 | B.Get(UMin,VMin,UMax,VMax); | |
128 | } | |
129 | else | |
130 | { | |
131 | UMin = UMax = VMin = VMax = 0.0; | |
132 | } | |
7fd59977 | 133 | } |
134 | ||
135 | //======================================================================= | |
136 | //function : AddUVBounds | |
137 | //purpose : | |
138 | //======================================================================= | |
139 | ||
140 | void BRepTools::AddUVBounds(const TopoDS_Face& FF, Bnd_Box2d& B) | |
141 | { | |
142 | TopoDS_Face F = FF; | |
143 | F.Orientation(TopAbs_FORWARD); | |
144 | TopExp_Explorer ex(F,TopAbs_EDGE); | |
145 | ||
146 | // fill box for the given face | |
147 | Bnd_Box2d aBox; | |
148 | for (;ex.More();ex.Next()) { | |
149 | BRepTools::AddUVBounds(F,TopoDS::Edge(ex.Current()),aBox); | |
150 | } | |
151 | ||
152 | // if the box is empty (face without edges or without pcurves), | |
153 | // get natural bounds | |
154 | if (aBox.IsVoid()) { | |
155 | Standard_Real UMin,UMax,VMin,VMax; | |
156 | TopLoc_Location L; | |
413b1c1a | 157 | const Handle(Geom_Surface)& aSurf = BRep_Tool::Surface(F, L); |
158 | if (aSurf.IsNull()) | |
159 | { | |
160 | return; | |
161 | } | |
162 | ||
163 | aSurf->Bounds(UMin,UMax,VMin,VMax); | |
7fd59977 | 164 | aBox.Update(UMin,VMin,UMax,VMax); |
165 | } | |
166 | ||
167 | // add face box to result | |
168 | B.Add ( aBox ); | |
169 | } | |
170 | ||
171 | ||
172 | //======================================================================= | |
173 | //function : AddUVBounds | |
174 | //purpose : | |
175 | //======================================================================= | |
7fd59977 | 176 | void BRepTools::AddUVBounds(const TopoDS_Face& F, |
177 | const TopoDS_Wire& W, | |
178 | Bnd_Box2d& B) | |
179 | { | |
180 | TopExp_Explorer ex; | |
181 | for (ex.Init(W,TopAbs_EDGE);ex.More();ex.Next()) { | |
182 | BRepTools::AddUVBounds(F,TopoDS::Edge(ex.Current()),B); | |
183 | } | |
184 | } | |
185 | ||
186 | ||
187 | //======================================================================= | |
188 | //function : AddUVBounds | |
189 | //purpose : | |
190 | //======================================================================= | |
59495dbe | 191 | void BRepTools::AddUVBounds(const TopoDS_Face& aF, |
6219c44c | 192 | const TopoDS_Edge& aE, |
193 | Bnd_Box2d& aB) | |
7fd59977 | 194 | { |
413b1c1a | 195 | Standard_Real aT1, aT2, aXmin = 0.0, aYmin = 0.0, aXmax = 0.0, aYmax = 0.0; |
59495dbe | 196 | Standard_Real aUmin, aUmax, aVmin, aVmax; |
197 | Bnd_Box2d aBoxC, aBoxS; | |
198 | TopLoc_Location aLoc; | |
199 | // | |
200 | const Handle(Geom2d_Curve) aC2D = BRep_Tool::CurveOnSurface(aE, aF, aT1, aT2); | |
201 | if (aC2D.IsNull()) { | |
202 | return; | |
203 | } | |
204 | // | |
205 | BndLib_Add2dCurve::Add(aC2D, aT1, aT2, 0., aBoxC); | |
413b1c1a | 206 | if (!aBoxC.IsVoid()) |
207 | { | |
208 | aBoxC.Get(aXmin, aYmin, aXmax, aYmax); | |
209 | } | |
59495dbe | 210 | // |
211 | Handle(Geom_Surface) aS = BRep_Tool::Surface(aF, aLoc); | |
212 | aS->Bounds(aUmin, aUmax, aVmin, aVmax); | |
213 | ||
214 | if(aS->DynamicType() == STANDARD_TYPE(Geom_RectangularTrimmedSurface)) | |
215 | { | |
216 | const Handle(Geom_RectangularTrimmedSurface) aSt = | |
217 | Handle(Geom_RectangularTrimmedSurface)::DownCast(aS); | |
218 | aS = aSt->BasisSurface(); | |
7fd59977 | 219 | } |
7fd59977 | 220 | |
59495dbe | 221 | // |
222 | if(!aS->IsUPeriodic()) | |
223 | { | |
6219c44c | 224 | Standard_Boolean isUPeriodic = Standard_False; |
225 | ||
226 | // Additional verification for U-periodicity for B-spline surfaces | |
227 | // 1. Verify that the surface is U-closed (if such flag is false). Verification uses 2 points | |
228 | // 2. Verify periodicity of surface inside UV-bounds of the edge. Verification uses 3 or 6 points. | |
229 | if (aS->DynamicType() == STANDARD_TYPE(Geom_BSplineSurface) && | |
230 | (aXmin < aUmin || aXmax > aUmax)) | |
9c06009a | 231 | { |
6219c44c | 232 | Standard_Real aTol2 = 100 * Precision::Confusion() * Precision::Confusion(); |
233 | isUPeriodic = Standard_True; | |
234 | gp_Pnt P1, P2; | |
235 | // 1. Verify that the surface is U-closed | |
236 | if (!aS->IsUClosed()) | |
237 | { | |
238 | Standard_Real aVStep = aVmax - aVmin; | |
239 | for (Standard_Real aV = aVmin; aV <= aVmax; aV += aVStep) | |
240 | { | |
241 | P1 = aS->Value(aUmin, aV); | |
242 | P2 = aS->Value(aUmax, aV); | |
243 | if (P1.SquareDistance(P2) > aTol2) | |
244 | { | |
245 | isUPeriodic = Standard_False; | |
246 | break; | |
247 | } | |
248 | } | |
249 | } | |
250 | // 2. Verify periodicity of surface inside UV-bounds of the edge | |
251 | if (isUPeriodic) // the flag still not changed | |
252 | { | |
253 | Standard_Real aV = (aVmin + aVmax) * 0.5; | |
254 | Standard_Real aU[6]; // values of U lying out of surface boundaries | |
255 | Standard_Real aUpp[6]; // corresponding U-values plus/minus period | |
256 | Standard_Integer aNbPnt = 0; | |
257 | if (aXmin < aUmin) | |
258 | { | |
259 | aU[0] = aXmin; | |
260 | aU[1] = (aXmin + aUmin) * 0.5; | |
261 | aU[2] = aUmin; | |
262 | aUpp[0] = aU[0] + aUmax - aUmin; | |
263 | aUpp[1] = aU[1] + aUmax - aUmin; | |
264 | aUpp[2] = aU[2] + aUmax - aUmin; | |
265 | aNbPnt += 3; | |
266 | } | |
267 | if (aXmax > aUmax) | |
268 | { | |
269 | aU[aNbPnt] = aUmax; | |
270 | aU[aNbPnt + 1] = (aXmax + aUmax) * 0.5; | |
271 | aU[aNbPnt + 2] = aXmax; | |
272 | aUpp[aNbPnt] = aU[aNbPnt] - aUmax + aUmin; | |
273 | aUpp[aNbPnt + 1] = aU[aNbPnt + 1] - aUmax + aUmin; | |
274 | aUpp[aNbPnt + 2] = aU[aNbPnt + 2] - aUmax + aUmin; | |
275 | aNbPnt += 3; | |
276 | } | |
277 | for (Standard_Integer anInd = 0; anInd < aNbPnt; anInd++) | |
278 | { | |
279 | P1 = aS->Value(aU[anInd], aV); | |
280 | P2 = aS->Value(aUpp[anInd], aV); | |
281 | if (P1.SquareDistance(P2) > aTol2) | |
282 | { | |
283 | isUPeriodic = Standard_False; | |
284 | break; | |
285 | } | |
286 | } | |
287 | } | |
9c06009a | 288 | } |
6219c44c | 289 | |
290 | if (!isUPeriodic) | |
59495dbe | 291 | { |
6219c44c | 292 | if((aXmin<aUmin) && (aUmin < aXmax)) |
293 | { | |
294 | aXmin=aUmin; | |
295 | } | |
296 | if((aXmin < aUmax) && (aUmax < aXmax)) | |
297 | { | |
298 | aXmax=aUmax; | |
299 | } | |
7fd59977 | 300 | } |
59495dbe | 301 | } |
7fd59977 | 302 | |
59495dbe | 303 | if(!aS->IsVPeriodic()) |
304 | { | |
6219c44c | 305 | Standard_Boolean isVPeriodic = Standard_False; |
306 | ||
307 | // Additional verification for V-periodicity for B-spline surfaces | |
308 | // 1. Verify that the surface is V-closed (if such flag is false). Verification uses 2 points | |
309 | // 2. Verify periodicity of surface inside UV-bounds of the edge. Verification uses 3 or 6 points. | |
310 | if (aS->DynamicType() == STANDARD_TYPE(Geom_BSplineSurface) && | |
311 | (aYmin < aVmin || aYmax > aVmax)) | |
59495dbe | 312 | { |
6219c44c | 313 | Standard_Real aTol2 = 100 * Precision::Confusion() * Precision::Confusion(); |
314 | isVPeriodic = Standard_True; | |
315 | gp_Pnt P1, P2; | |
316 | // 1. Verify that the surface is V-closed | |
317 | if (!aS->IsVClosed()) | |
318 | { | |
319 | Standard_Real aUStep = aUmax - aUmin; | |
320 | for (Standard_Real aU = aUmin; aU <= aUmax; aU += aUStep) | |
321 | { | |
322 | P1 = aS->Value(aU, aVmin); | |
323 | P2 = aS->Value(aU, aVmax); | |
324 | if (P1.SquareDistance(P2) > aTol2) | |
325 | { | |
326 | isVPeriodic = Standard_False; | |
327 | break; | |
328 | } | |
329 | } | |
330 | } | |
331 | // 2. Verify periodicity of surface inside UV-bounds of the edge | |
332 | if (isVPeriodic) // the flag still not changed | |
333 | { | |
334 | Standard_Real aU = (aUmin + aUmax) * 0.5; | |
335 | Standard_Real aV[6]; // values of V lying out of surface boundaries | |
336 | Standard_Real aVpp[6]; // corresponding V-values plus/minus period | |
337 | Standard_Integer aNbPnt = 0; | |
338 | if (aYmin < aVmin) | |
339 | { | |
340 | aV[0] = aYmin; | |
341 | aV[1] = (aYmin + aVmin) * 0.5; | |
342 | aV[2] = aVmin; | |
343 | aVpp[0] = aV[0] + aVmax - aVmin; | |
344 | aVpp[1] = aV[1] + aVmax - aVmin; | |
345 | aVpp[2] = aV[2] + aVmax - aVmin; | |
346 | aNbPnt += 3; | |
347 | } | |
348 | if (aYmax > aVmax) | |
349 | { | |
350 | aV[aNbPnt] = aVmax; | |
351 | aV[aNbPnt + 1] = (aYmax + aVmax) * 0.5; | |
352 | aV[aNbPnt + 2] = aYmax; | |
353 | aVpp[aNbPnt] = aV[aNbPnt] - aVmax + aVmin; | |
354 | aVpp[aNbPnt + 1] = aV[aNbPnt + 1] - aVmax + aVmin; | |
355 | aVpp[aNbPnt + 2] = aV[aNbPnt + 2] - aVmax + aVmin; | |
356 | aNbPnt += 3; | |
357 | } | |
358 | for (Standard_Integer anInd = 0; anInd < aNbPnt; anInd++) | |
359 | { | |
360 | P1 = aS->Value(aU, aV[anInd]); | |
361 | P2 = aS->Value(aU, aVpp[anInd]); | |
362 | if (P1.SquareDistance(P2) > aTol2) | |
363 | { | |
364 | isVPeriodic = Standard_False; | |
365 | break; | |
366 | } | |
367 | } | |
368 | } | |
7fd59977 | 369 | } |
6219c44c | 370 | |
371 | if (!isVPeriodic) | |
59495dbe | 372 | { |
6219c44c | 373 | if((aYmin<aVmin) && (aVmin < aYmax)) |
374 | { | |
375 | aYmin=aVmin; | |
376 | } | |
377 | if((aYmin < aVmax) && (aVmax < aYmax)) | |
378 | { | |
379 | aYmax=aVmax; | |
380 | } | |
59495dbe | 381 | } |
7fd59977 | 382 | } |
59495dbe | 383 | |
384 | aBoxS.Update(aXmin, aYmin, aXmax, aYmax); | |
385 | ||
386 | aB.Add(aBoxS); | |
7fd59977 | 387 | } |
388 | ||
389 | //======================================================================= | |
390 | //function : Update | |
391 | //purpose : | |
392 | //======================================================================= | |
393 | ||
394 | void BRepTools::Update(const TopoDS_Vertex&) | |
395 | { | |
396 | } | |
397 | ||
398 | //======================================================================= | |
399 | //function : Update | |
400 | //purpose : | |
401 | //======================================================================= | |
402 | ||
403 | void BRepTools::Update(const TopoDS_Edge&) | |
404 | { | |
405 | } | |
406 | ||
407 | //======================================================================= | |
408 | //function : Update | |
409 | //purpose : | |
410 | //======================================================================= | |
411 | ||
412 | void BRepTools::Update(const TopoDS_Wire&) | |
413 | { | |
414 | } | |
415 | ||
416 | //======================================================================= | |
417 | //function : Update | |
418 | //purpose : | |
419 | //======================================================================= | |
420 | ||
421 | void BRepTools::Update(const TopoDS_Face& F) | |
422 | { | |
423 | if (!F.Checked()) { | |
424 | UpdateFaceUVPoints(F); | |
425 | F.TShape()->Checked(Standard_True); | |
426 | } | |
427 | } | |
428 | ||
429 | //======================================================================= | |
430 | //function : Update | |
431 | //purpose : | |
432 | //======================================================================= | |
433 | ||
434 | void BRepTools::Update(const TopoDS_Shell& S) | |
435 | { | |
436 | TopExp_Explorer ex(S,TopAbs_FACE); | |
437 | while (ex.More()) { | |
438 | Update(TopoDS::Face(ex.Current())); | |
439 | ex.Next(); | |
440 | } | |
441 | } | |
442 | ||
443 | //======================================================================= | |
444 | //function : Update | |
445 | //purpose : | |
446 | //======================================================================= | |
447 | ||
448 | void BRepTools::Update(const TopoDS_Solid& S) | |
449 | { | |
450 | TopExp_Explorer ex(S,TopAbs_FACE); | |
451 | while (ex.More()) { | |
452 | Update(TopoDS::Face(ex.Current())); | |
453 | ex.Next(); | |
454 | } | |
455 | } | |
456 | ||
457 | //======================================================================= | |
458 | //function : Update | |
459 | //purpose : | |
460 | //======================================================================= | |
461 | ||
462 | void BRepTools::Update(const TopoDS_CompSolid& CS) | |
463 | { | |
464 | TopExp_Explorer ex(CS,TopAbs_FACE); | |
465 | while (ex.More()) { | |
466 | Update(TopoDS::Face(ex.Current())); | |
467 | ex.Next(); | |
468 | } | |
469 | } | |
470 | ||
471 | //======================================================================= | |
472 | //function : Update | |
473 | //purpose : | |
474 | //======================================================================= | |
475 | ||
476 | void BRepTools::Update(const TopoDS_Compound& C) | |
477 | { | |
478 | TopExp_Explorer ex(C,TopAbs_FACE); | |
479 | while (ex.More()) { | |
480 | Update(TopoDS::Face(ex.Current())); | |
481 | ex.Next(); | |
482 | } | |
483 | } | |
484 | ||
485 | //======================================================================= | |
486 | //function : Update | |
487 | //purpose : | |
488 | //======================================================================= | |
489 | ||
490 | void BRepTools::Update(const TopoDS_Shape& S) | |
491 | { | |
492 | switch (S.ShapeType()) { | |
493 | ||
494 | case TopAbs_VERTEX : | |
495 | Update(TopoDS::Vertex(S)); | |
496 | break; | |
497 | ||
498 | case TopAbs_EDGE : | |
499 | Update(TopoDS::Edge(S)); | |
500 | break; | |
501 | ||
502 | case TopAbs_WIRE : | |
503 | Update(TopoDS::Wire(S)); | |
504 | break; | |
505 | ||
506 | case TopAbs_FACE : | |
507 | Update(TopoDS::Face(S)); | |
508 | break; | |
509 | ||
510 | case TopAbs_SHELL : | |
511 | Update(TopoDS::Shell(S)); | |
512 | break; | |
513 | ||
514 | case TopAbs_SOLID : | |
515 | Update(TopoDS::Solid(S)); | |
516 | break; | |
517 | ||
518 | case TopAbs_COMPSOLID : | |
519 | Update(TopoDS::CompSolid(S)); | |
520 | break; | |
521 | ||
522 | case TopAbs_COMPOUND : | |
523 | Update(TopoDS::Compound(S)); | |
524 | break; | |
525 | ||
526 | default: | |
527 | break; | |
528 | ||
529 | } | |
530 | } | |
531 | ||
7fd59977 | 532 | //======================================================================= |
533 | //function : UpdateFaceUVPoints | |
e50ebf1f | 534 | //purpose : Reset the UV points of edges on the Face |
7fd59977 | 535 | //======================================================================= |
e50ebf1f | 536 | void BRepTools::UpdateFaceUVPoints(const TopoDS_Face& theF) |
7fd59977 | 537 | { |
e50ebf1f | 538 | // For each edge of the face <F> reset the UV points to the bounding |
539 | // points of the parametric curve of the edge on the face. | |
7fd59977 | 540 | |
e50ebf1f | 541 | // Get surface of the face |
542 | TopLoc_Location aLoc; | |
543 | const Handle(Geom_Surface)& aSurf = BRep_Tool::Surface(theF, aLoc); | |
544 | // Iterate on edges and reset UV points | |
545 | TopExp_Explorer anExpE(theF, TopAbs_EDGE); | |
546 | for (; anExpE.More(); anExpE.Next()) | |
7fd59977 | 547 | { |
e50ebf1f | 548 | const TopoDS_Edge& aE = TopoDS::Edge(anExpE.Current()); |
549 | ||
550 | const Handle(BRep_TEdge)& TE = *((Handle(BRep_TEdge)*)&aE.TShape()); | |
551 | if (TE->Locked()) | |
552 | return; | |
553 | ||
554 | const TopLoc_Location aELoc = aLoc.Predivided(aE.Location()); | |
555 | // Edge representations | |
556 | BRep_ListOfCurveRepresentation& aLCR = TE->ChangeCurves(); | |
557 | BRep_ListIteratorOfListOfCurveRepresentation itLCR(aLCR); | |
558 | for (; itLCR.More(); itLCR.Next()) | |
559 | { | |
560 | Handle(BRep_GCurve) GC = Handle(BRep_GCurve)::DownCast(itLCR.Value()); | |
561 | if (!GC.IsNull() && GC->IsCurveOnSurface(aSurf, aELoc)) | |
562 | { | |
563 | // Update UV points | |
564 | GC->Update(); | |
565 | break; | |
7fd59977 | 566 | } |
567 | } | |
7fd59977 | 568 | } |
569 | } | |
570 | ||
7fd59977 | 571 | //======================================================================= |
572 | //function : Compare | |
573 | //purpose : | |
574 | //======================================================================= | |
575 | ||
576 | Standard_Boolean BRepTools::Compare(const TopoDS_Vertex& V1, | |
577 | const TopoDS_Vertex& V2) | |
578 | { | |
579 | if (V1.IsSame(V2)) return Standard_True; | |
580 | gp_Pnt p1 = BRep_Tool::Pnt(V1); | |
581 | gp_Pnt p2 = BRep_Tool::Pnt(V2); | |
582 | Standard_Real l = p1.Distance(p2); | |
583 | if (l <= BRep_Tool::Tolerance(V1)) return Standard_True; | |
584 | if (l <= BRep_Tool::Tolerance(V2)) return Standard_True; | |
585 | return Standard_False; | |
586 | } | |
587 | ||
588 | //======================================================================= | |
589 | //function : Compare | |
590 | //purpose : | |
591 | //======================================================================= | |
592 | ||
593 | Standard_Boolean BRepTools::Compare(const TopoDS_Edge& E1, | |
594 | const TopoDS_Edge& E2) | |
595 | { | |
596 | if (E1.IsSame(E2)) return Standard_True; | |
597 | return Standard_False; | |
598 | } | |
599 | ||
600 | //======================================================================= | |
601 | //function : OuterWire | |
602 | //purpose : | |
603 | //======================================================================= | |
604 | ||
605 | TopoDS_Wire BRepTools::OuterWire(const TopoDS_Face& F) | |
606 | { | |
607 | TopoDS_Wire Wres; | |
608 | TopExp_Explorer expw (F,TopAbs_WIRE); | |
609 | ||
610 | if (expw.More()) { | |
611 | Wres = TopoDS::Wire(expw.Current()); | |
612 | expw.Next(); | |
613 | if (expw.More()) { | |
614 | Standard_Real UMin, UMax, VMin, VMax; | |
615 | Standard_Real umin, umax, vmin, vmax; | |
616 | BRepTools::UVBounds(F,Wres,UMin,UMax,VMin,VMax); | |
617 | while (expw.More()) { | |
618 | const TopoDS_Wire& W = TopoDS::Wire(expw.Current()); | |
619 | BRepTools::UVBounds(F,W,umin, umax, vmin, vmax); | |
620 | if ((umin <= UMin) && | |
621 | (umax >= UMax) && | |
622 | (vmin <= VMin) && | |
623 | (vmax >= VMax)) { | |
624 | Wres = W; | |
625 | UMin = umin; | |
626 | UMax = umax; | |
627 | VMin = vmin; | |
628 | VMax = vmax; | |
629 | } | |
630 | expw.Next(); | |
631 | } | |
632 | } | |
633 | } | |
634 | return Wres; | |
635 | } | |
636 | ||
7fd59977 | 637 | //======================================================================= |
638 | //function : Map3DEdges | |
639 | //purpose : | |
640 | //======================================================================= | |
641 | ||
642 | void BRepTools::Map3DEdges(const TopoDS_Shape& S, | |
643 | TopTools_IndexedMapOfShape& M) | |
644 | { | |
645 | TopExp_Explorer Ex; | |
646 | for (Ex.Init(S,TopAbs_EDGE); Ex.More(); Ex.Next()) { | |
647 | if (!BRep_Tool::Degenerated(TopoDS::Edge(Ex.Current()))) | |
648 | M.Add(Ex.Current()); | |
649 | } | |
650 | } | |
651 | ||
652 | //======================================================================= | |
653 | //function : Dump | |
654 | //purpose : | |
655 | //======================================================================= | |
656 | ||
657 | void BRepTools::Dump(const TopoDS_Shape& Sh, Standard_OStream& S) | |
658 | { | |
659 | BRepTools_ShapeSet SS; | |
660 | SS.Add(Sh); | |
661 | SS.Dump(Sh,S); | |
662 | SS.Dump(S); | |
663 | } | |
664 | ||
7fd59977 | 665 | //======================================================================= |
666 | //function : Write | |
667 | //purpose : | |
668 | //======================================================================= | |
669 | ||
670 | void BRepTools::Write(const TopoDS_Shape& Sh, Standard_OStream& S, | |
671 | const Handle(Message_ProgressIndicator)& PR) | |
672 | { | |
673 | BRepTools_ShapeSet SS; | |
674 | SS.SetProgress(PR); | |
675 | SS.Add(Sh); | |
676 | SS.Write(S); | |
677 | SS.Write(Sh,S); | |
678 | } | |
679 | ||
680 | ||
681 | //======================================================================= | |
682 | //function : Read | |
683 | //purpose : | |
684 | //======================================================================= | |
685 | ||
686 | void BRepTools::Read(TopoDS_Shape& Sh, | |
04232180 | 687 | std::istream& S, |
7fd59977 | 688 | const BRep_Builder& B, |
689 | const Handle(Message_ProgressIndicator)& PR) | |
690 | { | |
691 | BRepTools_ShapeSet SS(B); | |
692 | SS.SetProgress(PR); | |
693 | SS.Read(S); | |
694 | SS.Read(Sh,S); | |
695 | } | |
696 | ||
697 | //======================================================================= | |
698 | //function : Write | |
699 | //purpose : | |
700 | //======================================================================= | |
701 | ||
702 | Standard_Boolean BRepTools::Write(const TopoDS_Shape& Sh, | |
703 | const Standard_CString File, | |
704 | const Handle(Message_ProgressIndicator)& PR) | |
705 | { | |
04232180 | 706 | std::ofstream os; |
707 | OSD_OpenStream(os, File, std::ios::out); | |
fc8918ad | 708 | if (!os.is_open() || !os.good()) |
709 | return Standard_False; | |
7fd59977 | 710 | |
711 | Standard_Boolean isGood = (os.good() && !os.eof()); | |
712 | if(!isGood) | |
713 | return isGood; | |
714 | ||
715 | BRepTools_ShapeSet SS; | |
716 | SS.SetProgress(PR); | |
717 | SS.Add(Sh); | |
718 | ||
719 | os << "DBRep_DrawableShape\n"; // for easy Draw read | |
720 | SS.Write(os); | |
721 | isGood = os.good(); | |
722 | if(isGood ) | |
723 | SS.Write(Sh,os); | |
724 | os.flush(); | |
725 | isGood = os.good(); | |
726 | ||
727 | errno = 0; | |
728 | os.close(); | |
7fd59977 | 729 | isGood = os.good() && isGood && !errno; |
730 | ||
731 | return isGood; | |
732 | } | |
733 | ||
734 | //======================================================================= | |
735 | //function : Read | |
736 | //purpose : | |
737 | //======================================================================= | |
738 | ||
739 | Standard_Boolean BRepTools::Read(TopoDS_Shape& Sh, | |
740 | const Standard_CString File, | |
741 | const BRep_Builder& B, | |
742 | const Handle(Message_ProgressIndicator)& PR) | |
743 | { | |
04232180 | 744 | std::filebuf fic; |
745 | std::istream in(&fic); | |
746 | OSD_OpenStream (fic, File, std::ios::in); | |
94708556 | 747 | if(!fic.is_open()) return Standard_False; |
748 | ||
7fd59977 | 749 | BRepTools_ShapeSet SS(B); |
750 | SS.SetProgress(PR); | |
751 | SS.Read(in); | |
752 | if(!SS.NbShapes()) return Standard_False; | |
753 | SS.Read(Sh,in); | |
754 | return Standard_True; | |
755 | } | |
756 | ||
757 | ||
758 | //======================================================================= | |
759 | //function : Clean | |
760 | //purpose : | |
761 | //======================================================================= | |
762 | ||
128654b6 | 763 | void BRepTools::Clean (const TopoDS_Shape& theShape) |
7fd59977 | 764 | { |
128654b6 | 765 | if (theShape.IsNull()) |
766 | return; | |
767 | ||
d0a994c7 | 768 | BRep_Builder aBuilder; |
769 | Handle(Poly_Triangulation) aNullTriangulation; | |
770 | Handle(Poly_PolygonOnTriangulation) aNullPoly; | |
7fd59977 | 771 | |
128654b6 | 772 | TopTools_MapOfShape aShapeMap; |
773 | const TopLoc_Location anEmptyLoc; | |
d0a994c7 | 774 | |
775 | TopExp_Explorer aFaceIt(theShape, TopAbs_FACE); | |
776 | for (; aFaceIt.More(); aFaceIt.Next()) | |
777 | { | |
128654b6 | 778 | TopoDS_Shape aFaceNoLoc = aFaceIt.Value(); |
779 | aFaceNoLoc.Location (anEmptyLoc); | |
780 | if (!aShapeMap.Add (aFaceNoLoc)) | |
781 | { | |
782 | // the face has already been processed | |
783 | continue; | |
784 | } | |
785 | ||
786 | const TopoDS_Face& aFace = TopoDS::Face (aFaceIt.Current()); | |
787 | if (!BRep_Tool::IsGeometric (aFace)) | |
788 | { | |
789 | // Do not remove triangulation as there is no surface to recompute it. | |
790 | continue; | |
791 | } | |
792 | ||
d0a994c7 | 793 | |
794 | TopLoc_Location aLoc; | |
795 | const Handle(Poly_Triangulation)& aTriangulation = | |
796 | BRep_Tool::Triangulation(aFace, aLoc); | |
797 | ||
798 | if (aTriangulation.IsNull()) | |
799 | continue; | |
800 | ||
801 | // Nullify edges | |
128654b6 | 802 | // Theoretically, the edges on the face (with surface) may have no geometry |
803 | // (no curve 3d or 2d or both). Such faces should be considered as invalid and | |
804 | // are not supported by current implementation. So, both triangulation of the face | |
805 | // and polygon on triangulation of the edges are removed unconditionally. | |
d0a994c7 | 806 | TopExp_Explorer aEdgeIt(aFace, TopAbs_EDGE); |
807 | for (; aEdgeIt.More(); aEdgeIt.Next()) | |
808 | { | |
809 | const TopoDS_Edge& aEdge = TopoDS::Edge(aEdgeIt.Current()); | |
810 | aBuilder.UpdateEdge(aEdge, aNullPoly, aTriangulation, aLoc); | |
7fd59977 | 811 | } |
d0a994c7 | 812 | |
813 | aBuilder.UpdateFace(aFace, aNullTriangulation); | |
7fd59977 | 814 | } |
a4ab454c | 815 | |
816 | // Iterate over all edges seeking for 3d polygons | |
817 | Handle (Poly_Polygon3D) aNullPoly3d; | |
818 | TopExp_Explorer aEdgeIt (theShape, TopAbs_EDGE); | |
819 | for (; aEdgeIt.More (); aEdgeIt.Next ()) | |
820 | { | |
128654b6 | 821 | TopoDS_Edge anEdgeNoLoc = TopoDS::Edge (aEdgeIt.Value()); |
822 | anEdgeNoLoc.Location (anEmptyLoc); | |
823 | ||
824 | if (!aShapeMap.Add (anEdgeNoLoc)) | |
825 | { | |
826 | // the edge has already been processed | |
827 | continue; | |
828 | } | |
829 | ||
830 | if (!BRep_Tool::IsGeometric (TopoDS::Edge (anEdgeNoLoc))) | |
831 | { | |
832 | // Do not remove polygon 3d as there is no curve to recompute it. | |
833 | continue; | |
834 | } | |
a4ab454c | 835 | |
836 | TopLoc_Location aLoc; | |
128654b6 | 837 | Handle (Poly_Polygon3D) aPoly3d = BRep_Tool::Polygon3D (anEdgeNoLoc, aLoc); |
838 | if (aPoly3d.IsNull()) | |
a4ab454c | 839 | continue; |
840 | ||
128654b6 | 841 | aBuilder.UpdateEdge (anEdgeNoLoc, aNullPoly3d); |
a4ab454c | 842 | } |
7fd59977 | 843 | } |
4b114473 | 844 | //======================================================================= |
845 | //function : CleanGeometry | |
846 | //purpose : | |
847 | //======================================================================= | |
848 | ||
849 | void BRepTools::CleanGeometry(const TopoDS_Shape& theShape) | |
850 | { | |
851 | if (theShape.IsNull()) | |
852 | return; | |
853 | ||
854 | BRep_Builder aBuilder; | |
855 | ||
856 | for (TopExp_Explorer aFaceIt(theShape, TopAbs_FACE); aFaceIt.More(); aFaceIt.Next()) | |
857 | { | |
858 | TopLoc_Location aLocation; | |
859 | const TopoDS_Face& aFace = TopoDS::Face(aFaceIt.Current()); | |
860 | const Handle(Geom_Surface)& aSurface = BRep_Tool::Surface(aFace, aLocation); | |
861 | ||
862 | for (TopExp_Explorer aEdgeIt(aFace, TopAbs_EDGE); aEdgeIt.More(); aEdgeIt.Next()) | |
863 | { | |
864 | const TopoDS_Edge& anEdge = TopoDS::Edge(aEdgeIt.Current()); | |
865 | aBuilder.UpdateEdge(anEdge, Handle(Geom2d_Curve)(), aSurface, | |
866 | aLocation, BRep_Tool::Tolerance(anEdge)); | |
867 | } | |
868 | ||
869 | aBuilder.UpdateFace(aFace, Handle(Geom_Surface)(), aFace.Location(), BRep_Tool::Tolerance(aFace)); | |
870 | } | |
871 | ||
872 | for (TopExp_Explorer aEdgeIt2(theShape, TopAbs_EDGE); aEdgeIt2.More(); aEdgeIt2.Next()) | |
873 | { | |
874 | const TopoDS_Edge& anEdge = TopoDS::Edge(aEdgeIt2.Current()); | |
875 | ||
876 | aBuilder.UpdateEdge(anEdge, Handle(Geom_Curve)(), | |
877 | TopLoc_Location(), BRep_Tool::Tolerance(anEdge)); | |
878 | } | |
879 | } | |
880 | ||
7fd59977 | 881 | |
01697018 J |
882 | //======================================================================= |
883 | //function : RemoveUnusedPCurves | |
884 | //purpose : | |
885 | //======================================================================= | |
886 | ||
887 | void BRepTools::RemoveUnusedPCurves(const TopoDS_Shape& S) | |
888 | { | |
889 | TColStd_MapOfTransient UsedSurfaces; | |
890 | ||
891 | TopExp_Explorer Explo(S, TopAbs_FACE); | |
892 | for (; Explo.More(); Explo.Next()) | |
893 | { | |
894 | TopoDS_Face aFace = TopoDS::Face(Explo.Current()); | |
895 | TopLoc_Location aLoc; | |
896 | Handle(Geom_Surface) aSurf = BRep_Tool::Surface(aFace, aLoc); | |
897 | UsedSurfaces.Add(aSurf); | |
898 | } | |
899 | ||
900 | TopTools_IndexedMapOfShape Emap; | |
901 | TopExp::MapShapes(S, TopAbs_EDGE, Emap); | |
7fd59977 | 902 | |
01697018 J |
903 | Standard_Integer i; |
904 | for (i = 1; i <= Emap.Extent(); i++) | |
905 | { | |
906 | const Handle(BRep_TEdge)& TE = *((Handle(BRep_TEdge)*) &Emap(i).TShape()); | |
907 | BRep_ListOfCurveRepresentation& lcr = TE -> ChangeCurves(); | |
908 | BRep_ListIteratorOfListOfCurveRepresentation itrep(lcr ); | |
909 | while (itrep.More()) | |
910 | { | |
911 | Standard_Boolean ToRemove = Standard_False; | |
912 | ||
913 | Handle(BRep_CurveRepresentation) CurveRep = itrep.Value(); | |
914 | if (CurveRep->IsCurveOnSurface()) | |
915 | { | |
916 | Handle(Geom_Surface) aSurface = CurveRep->Surface(); | |
917 | if (!UsedSurfaces.Contains(aSurface)) | |
918 | ToRemove = Standard_True; | |
919 | } | |
920 | else if (CurveRep->IsRegularity()) | |
921 | { | |
922 | Handle(Geom_Surface) Surf1 = CurveRep->Surface(); | |
923 | Handle(Geom_Surface) Surf2 = CurveRep->Surface2(); | |
924 | ToRemove = (!UsedSurfaces.Contains(Surf1) || !UsedSurfaces.Contains(Surf2)); | |
925 | } | |
926 | ||
927 | if (ToRemove) | |
928 | lcr.Remove(itrep); | |
929 | else | |
930 | itrep.Next(); | |
931 | } | |
932 | } | |
933 | } | |
7fd59977 | 934 | |
935 | //======================================================================= | |
936 | //function : Triangulation | |
937 | //purpose : | |
938 | //======================================================================= | |
939 | ||
29263c94 | 940 | Standard_Boolean BRepTools::Triangulation(const TopoDS_Shape& theShape, |
941 | const Standard_Real theLinDefl, | |
942 | const Standard_Boolean theToCheckFreeEdges) | |
7fd59977 | 943 | { |
29263c94 | 944 | TopExp_Explorer anEdgeIter; |
945 | TopLoc_Location aDummyLoc; | |
946 | for (TopExp_Explorer aFaceIter (theShape, TopAbs_FACE); aFaceIter.More(); aFaceIter.Next()) | |
947 | { | |
948 | const TopoDS_Face& aFace = TopoDS::Face (aFaceIter.Current()); | |
949 | const Handle(Poly_Triangulation)& aTri = BRep_Tool::Triangulation (aFace, aDummyLoc); | |
950 | if (aTri.IsNull() | |
951 | || aTri->Deflection() > theLinDefl) | |
952 | { | |
7fd59977 | 953 | return Standard_False; |
7fd59977 | 954 | } |
29263c94 | 955 | |
956 | for (anEdgeIter.Init (aFace, TopAbs_EDGE); anEdgeIter.More(); anEdgeIter.Next()) | |
957 | { | |
958 | const TopoDS_Edge& anEdge = TopoDS::Edge (anEdgeIter.Current()); | |
959 | const Handle(Poly_PolygonOnTriangulation)& aPoly = BRep_Tool::PolygonOnTriangulation (anEdge, aTri, aDummyLoc); | |
960 | if (aPoly.IsNull()) | |
961 | { | |
962 | return Standard_False; | |
963 | } | |
964 | } | |
965 | } | |
966 | if (!theToCheckFreeEdges) | |
967 | { | |
968 | return Standard_True; | |
7fd59977 | 969 | } |
29263c94 | 970 | |
971 | Handle(Poly_Triangulation) anEdgeTri; | |
972 | for (anEdgeIter.Init (theShape, TopAbs_EDGE, TopAbs_FACE); anEdgeIter.More(); anEdgeIter.Next()) | |
973 | { | |
974 | const TopoDS_Edge& anEdge = TopoDS::Edge (anEdgeIter.Current()); | |
975 | const Handle(Poly_Polygon3D)& aPolygon = BRep_Tool::Polygon3D (anEdge, aDummyLoc); | |
976 | if (!aPolygon.IsNull()) | |
977 | { | |
978 | if (aPolygon->Deflection() > theLinDefl) | |
979 | { | |
980 | return Standard_False; | |
981 | } | |
982 | } | |
983 | else | |
984 | { | |
985 | const Handle(Poly_PolygonOnTriangulation)& aPoly = BRep_Tool::PolygonOnTriangulation (anEdge, anEdgeTri, aDummyLoc); | |
986 | if (aPoly.IsNull() | |
987 | || anEdgeTri.IsNull() | |
988 | || anEdgeTri->Deflection() > theLinDefl) | |
989 | { | |
990 | return Standard_False; | |
991 | } | |
992 | } | |
993 | } | |
994 | ||
7fd59977 | 995 | return Standard_True; |
996 | } | |
997 | ||
998 | ||
999 | //======================================================================= | |
1000 | //function : IsReallyClosed | |
1001 | //purpose : | |
1002 | //======================================================================= | |
1003 | ||
1004 | Standard_Boolean BRepTools::IsReallyClosed(const TopoDS_Edge& E, | |
1005 | const TopoDS_Face& F) | |
1006 | { | |
1007 | if (!BRep_Tool::IsClosed(E,F)) { | |
1008 | return Standard_False; | |
1009 | } | |
1010 | Standard_Integer nbocc = 0; | |
1011 | TopExp_Explorer exp; | |
1012 | for (exp.Init(F,TopAbs_EDGE);exp.More();exp.Next()) { | |
1013 | if (exp.Current().IsSame(E)) { | |
1014 | nbocc++; | |
1015 | } | |
1016 | } | |
1017 | return nbocc == 2; | |
1018 | } | |
1019 | ||
2651bfde | 1020 | //======================================================================= |
11af6cdd | 1021 | //function : DetectClosedness |
1022 | //purpose : | |
1023 | //======================================================================= | |
1024 | ||
1025 | void BRepTools::DetectClosedness(const TopoDS_Face& theFace, | |
1026 | Standard_Boolean& theUclosed, | |
1027 | Standard_Boolean& theVclosed) | |
1028 | { | |
1029 | theUclosed = theVclosed = Standard_False; | |
1030 | ||
11af6cdd | 1031 | TopExp_Explorer Explo(theFace, TopAbs_EDGE); |
1032 | for (; Explo.More(); Explo.Next()) | |
1033 | { | |
1034 | const TopoDS_Edge& anEdge = TopoDS::Edge(Explo.Current()); | |
85c103d2 | 1035 | if (BRep_Tool::IsClosed(anEdge, theFace) && |
1036 | BRepTools::IsReallyClosed(anEdge, theFace)) | |
11af6cdd | 1037 | { |
1038 | Standard_Real fpar, lpar; | |
85c103d2 | 1039 | Handle(Geom2d_Curve) PCurve1 = BRep_Tool::CurveOnSurface(anEdge, theFace, fpar, lpar); |
1040 | Handle(Geom2d_Curve) PCurve2 = BRep_Tool::CurveOnSurface(TopoDS::Edge(anEdge.Reversed()), | |
1041 | theFace, fpar, lpar); | |
1042 | gp_Pnt2d Point1 = PCurve1->Value(fpar); | |
1043 | gp_Pnt2d Point2 = PCurve2->Value(fpar); | |
1044 | Standard_Boolean IsUiso = (Abs(Point1.X() - Point2.X()) > Abs(Point1.Y() - Point2.Y())); | |
1045 | if (IsUiso) | |
11af6cdd | 1046 | theUclosed = Standard_True; |
85c103d2 | 1047 | else |
11af6cdd | 1048 | theVclosed = Standard_True; |
11af6cdd | 1049 | } |
1050 | } | |
1051 | } | |
1052 | ||
1053 | //======================================================================= | |
2651bfde | 1054 | //function : EvalAndUpdateTol |
1055 | //purpose : | |
1056 | //======================================================================= | |
1057 | ||
1058 | Standard_Real BRepTools::EvalAndUpdateTol(const TopoDS_Edge& theE, | |
1059 | const Handle(Geom_Curve)& C3d, | |
1060 | const Handle(Geom2d_Curve) C2d, | |
1061 | const Handle(Geom_Surface)& S, | |
1062 | const Standard_Real f, | |
1063 | const Standard_Real l) | |
1064 | { | |
1065 | Standard_Real newtol = 0.; | |
1066 | Standard_Real first = f, last = l; | |
1067 | //Set first, last to avoid ErrosStatus = 2 because of | |
1068 | //too strong checking of limits in class CheckCurveOnSurface | |
1069 | // | |
1070 | if(!C3d->IsPeriodic()) | |
1071 | { | |
1072 | first = Max(first, C3d->FirstParameter()); | |
1073 | last = Min(last, C3d->LastParameter()); | |
1074 | } | |
1075 | if(!C2d->IsPeriodic()) | |
1076 | { | |
1077 | first = Max(first, C2d->FirstParameter()); | |
1078 | last = Min(last, C2d->LastParameter()); | |
1079 | } | |
1080 | ||
1081 | GeomLib_CheckCurveOnSurface CT(C3d, S, first, last); | |
1082 | CT.Perform(C2d); | |
1083 | if(CT.IsDone()) | |
1084 | { | |
1085 | newtol = CT.MaxDistance(); | |
1086 | } | |
1087 | else | |
1088 | { | |
1089 | if(CT.ErrorStatus() == 3 || (CT.ErrorStatus() == 2 && | |
1090 | (C3d->IsPeriodic() || C2d->IsPeriodic()))) | |
1091 | { | |
1092 | //Try to estimate by sample points | |
1093 | Standard_Integer nbint = 22; | |
1094 | Standard_Real dt = (last - first) / nbint; | |
1095 | dt = Max(dt, Precision::Confusion()); | |
1096 | Standard_Real d, dmax = 0.; | |
1097 | gp_Pnt2d aP2d; | |
1098 | gp_Pnt aPC, aPS; | |
1099 | Standard_Integer cnt = 0; | |
1100 | Standard_Real t = first; | |
1101 | for(; t <= last; t += dt) | |
1102 | { | |
1103 | cnt++; | |
1104 | C2d->D0(t, aP2d); | |
1105 | C3d->D0(t, aPC); | |
1106 | S->D0(aP2d.X(), aP2d.Y(), aPS); | |
1107 | d = aPS.SquareDistance(aPC); | |
1108 | if(d > dmax) | |
1109 | { | |
1110 | dmax = d; | |
1111 | } | |
1112 | } | |
1113 | if(cnt < nbint + 1) | |
1114 | { | |
1115 | t = last; | |
1116 | C2d->D0(t, aP2d); | |
1117 | C3d->D0(t, aPC); | |
1118 | S->D0(aP2d.X(), aP2d.Y(), aPS); | |
1119 | d = aPS.SquareDistance(aPC); | |
1120 | if(d > dmax) | |
1121 | { | |
1122 | dmax = d; | |
1123 | } | |
1124 | } | |
1125 | ||
1126 | newtol = 1.2 * Sqrt(dmax); | |
1127 | } | |
1128 | } | |
1129 | Standard_Real Tol = BRep_Tool::Tolerance(theE); | |
1130 | if(newtol > Tol) | |
1131 | { | |
1132 | Tol = newtol; | |
1133 | BRep_Builder B; | |
1134 | B.UpdateEdge(theE, Tol); | |
1135 | } | |
1136 | ||
1137 | return Tol; | |
1138 | ||
1139 | } | |
7fd59977 | 1140 | |
eff3eff9 | 1141 | //======================================================================= |
1142 | //function : OriEdgeInFace | |
1143 | //purpose : | |
1144 | //======================================================================= | |
7fd59977 | 1145 | |
eff3eff9 | 1146 | TopAbs_Orientation BRepTools::OriEdgeInFace (const TopoDS_Edge& E, |
1147 | const TopoDS_Face& F ) | |
1148 | ||
1149 | { | |
1150 | TopExp_Explorer Exp(F.Oriented(TopAbs_FORWARD),TopAbs_EDGE); | |
1151 | ||
1152 | for (; Exp.More() ;Exp.Next()) { | |
1153 | if (Exp.Current().IsSame(E)) { | |
1154 | return Exp.Current().Orientation(); | |
1155 | } | |
1156 | } | |
1157 | throw Standard_ConstructionError("BRepTools::OriEdgeInFace"); | |
1158 | } |