b311480e |
1 | // Created on: 1996-04-23 |
2 | // Created by: Jacques GOUSSARD |
3 | // Copyright (c) 1996-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 | |
17 | #include <BRepFeat.ixx> |
18 | |
19 | //#include <BRepAlgo_Cut.hxx> |
20 | |
21 | #include <BRepBuilderAPI.hxx> |
22 | #include <BRepAdaptor_Curve.hxx> |
23 | #include <TopExp_Explorer.hxx> |
24 | #include <TopTools_MapOfShape.hxx> |
25 | #include <BRep_Tool.hxx> |
26 | #include <BRep_Builder.hxx> |
27 | #include <Geom_Curve.hxx> |
28 | #include <Geom_TrimmedCurve.hxx> |
29 | #include <Geom2d_TrimmedCurve.hxx> |
30 | #include <Extrema_ExtPC.hxx> |
31 | #include <GeomAdaptor_Curve.hxx> |
32 | #include <BRepLProp.hxx> |
33 | #include <TopoDS.hxx> |
34 | #include <TopoDS_Vertex.hxx> |
35 | #include <TopoDS_Face.hxx> |
36 | #include <TopoDS_Edge.hxx> |
37 | #include <TopoDS_Shell.hxx> |
38 | #include <TopoDS_Solid.hxx> |
39 | #include <Precision.hxx> |
40 | #include <GCPnts_QuasiUniformDeflection.hxx> |
41 | #include <BRepTopAdaptor_FClass2d.hxx> |
42 | #include <Geom2dAdaptor_Curve.hxx> |
43 | #include <GeomProjLib.hxx> |
44 | #include <gp_Vec2d.hxx> |
45 | #include <BRepTools.hxx> |
46 | #include <Geom_Surface.hxx> |
47 | #include <Bnd_Box.hxx> |
48 | #include <BRepBndLib.hxx> |
49 | #include <BRepLib_MakeFace.hxx> |
50 | #include <Geom_RectangularTrimmedSurface.hxx> |
51 | #include <Geom_Plane.hxx> |
52 | #include <Geom_CylindricalSurface.hxx> |
53 | #include <Geom_ConicalSurface.hxx> |
54 | #include <LocOpe_CSIntersector.hxx> |
55 | #include <LocOpe_PntFace.hxx> |
56 | #include <LocOpe_BuildShape.hxx> |
57 | |
58 | #include <TColGeom_SequenceOfCurve.hxx> |
59 | |
60 | |
61 | #include <LocOpe.hxx> |
62 | |
63 | #define NECHANTBARYC 11 |
64 | |
65 | //======================================================================= |
66 | //function : SampleEdges |
67 | //purpose : |
68 | //======================================================================= |
69 | |
70 | void BRepFeat::SampleEdges(const TopoDS_Shape& theShape, |
71 | TColgp_SequenceOfPnt& theSeq) |
72 | { |
73 | LocOpe::SampleEdges(theShape,theSeq); |
74 | } |
75 | |
76 | |
77 | |
78 | //======================================================================= |
79 | //function : Barycenter |
80 | //purpose : Calcul du barycentre des edges d'un shape |
81 | //======================================================================= |
82 | |
83 | void BRepFeat::Barycenter(const TopoDS_Shape& S, |
84 | gp_Pnt& B) |
85 | { |
86 | TopTools_MapOfShape theMap; |
87 | TopExp_Explorer exp(S,TopAbs_EDGE); |
88 | TopLoc_Location Loc; |
89 | Handle(Geom_Curve) C; |
90 | Standard_Real f,l,prm; |
91 | gp_XYZ Bar(0.,0.,0.); |
92 | Standard_Integer i, nbp= 0; |
93 | |
94 | for (; exp.More(); exp.Next()) { |
95 | const TopoDS_Edge& edg = TopoDS::Edge(exp.Current()); |
96 | if (!theMap.Add(edg)) { |
97 | continue; |
98 | } |
99 | if (!BRep_Tool::Degenerated(edg)) { |
100 | C = BRep_Tool::Curve(edg,Loc,f,l); |
101 | C = Handle(Geom_Curve)::DownCast(C->Transformed(Loc.Transformation())); |
102 | for (i=1;i<NECHANTBARYC; i++) { |
103 | prm = ((NECHANTBARYC-i)*f + i*l)/NECHANTBARYC; |
104 | Bar += C->Value(prm).XYZ(); |
105 | nbp++; |
106 | } |
107 | } |
108 | } |
109 | // Adds every vertex |
110 | for (exp.Init(S,TopAbs_VERTEX); exp.More(); exp.Next()) { |
111 | if (theMap.Add(exp.Current())) { |
112 | Bar += (BRep_Tool::Pnt(TopoDS::Vertex(exp.Current()))).XYZ(); |
113 | nbp++; |
114 | } |
115 | } |
116 | |
117 | Bar.Divide((Standard_Real)nbp); |
118 | B.SetXYZ(Bar); |
119 | } |
120 | |
121 | |
122 | //======================================================================= |
123 | //function : ParametricBarycenter |
124 | //purpose : Calcul du barycentre "parametrique" shape sur une courbe |
125 | //======================================================================= |
126 | |
127 | Standard_Real BRepFeat::ParametricBarycenter(const TopoDS_Shape& S, |
128 | const Handle(Geom_Curve)& CC) |
129 | { |
130 | TopTools_MapOfShape theMap; |
131 | TopExp_Explorer exp(S,TopAbs_EDGE); |
132 | TopLoc_Location Loc; |
133 | Handle(Geom_Curve) C; |
134 | Standard_Real f,l,prm; |
135 | Standard_Integer i, nbp= 0; |
136 | GeomAdaptor_Curve TheCurve(CC); |
137 | Extrema_ExtPC extpc; |
138 | extpc.Initialize(TheCurve,CC->FirstParameter(),CC->LastParameter()); |
139 | Standard_Real parbar = 0; |
140 | |
141 | for (; exp.More(); exp.Next()) { |
142 | const TopoDS_Edge& edg = TopoDS::Edge(exp.Current()); |
143 | if (!theMap.Add(edg)) { |
144 | continue; |
145 | } |
146 | if (!BRep_Tool::Degenerated(edg)) { |
147 | C = BRep_Tool::Curve(edg,Loc,f,l); |
148 | C = Handle(Geom_Curve)::DownCast(C->Transformed(Loc.Transformation())); |
149 | for (i=1;i<NECHANTBARYC; i++) { |
150 | prm = ((NECHANTBARYC-i)*f + i*l)/NECHANTBARYC; |
151 | gp_Pnt pone = C->Value(prm); |
152 | // On projette sur CC |
153 | extpc.Perform(pone); |
154 | if (extpc.IsDone() && extpc.NbExt() >= 1) { |
155 | Standard_Real Dist2Min = extpc.SquareDistance(1); |
156 | Standard_Integer kmin = 1; |
157 | for (Standard_Integer k=2; k<=extpc.NbExt(); k++) { |
158 | Standard_Real Dist2 = extpc.SquareDistance(k); |
159 | if (Dist2 < Dist2Min) { |
160 | Dist2Min = Dist2; |
161 | kmin = k; |
162 | } |
163 | } |
164 | nbp++; |
165 | Standard_Real prmp = extpc.Point(kmin).Parameter(); |
166 | parbar += prmp; |
167 | } |
168 | } |
169 | } |
170 | } |
171 | // Adds every vertex |
172 | for (exp.Init(S,TopAbs_VERTEX); exp.More(); exp.Next()) { |
173 | if (theMap.Add(exp.Current())) { |
174 | gp_Pnt pone = BRep_Tool::Pnt(TopoDS::Vertex(exp.Current())); |
175 | // On projette sur CC |
176 | extpc.Perform(pone); |
177 | if (extpc.IsDone() && extpc.NbExt() >= 1) { |
302f96fb |
178 | Standard_Real Dist2Min = extpc.SquareDistance(1); |
302f96fb |
179 | for (Standard_Integer k=2; k<=extpc.NbExt(); k++) { |
180 | Standard_Real Dist2 = extpc.SquareDistance(k); |
181 | if (Dist2 < Dist2Min) { |
182 | Dist2Min = Dist2; |
302f96fb |
183 | } |
184 | } |
185 | nbp++; |
7fd59977 |
186 | } |
187 | } |
188 | } |
189 | |
190 | parbar /=((Standard_Real)nbp); |
191 | return parbar; |
192 | } |
193 | |
194 | |
195 | //======================================================================= |
196 | //function : ParametricBarycenter |
197 | //purpose : Calcul du barycentre "parametrique" shape sur une courbe |
198 | //======================================================================= |
199 | |
200 | void BRepFeat::ParametricMinMax(const TopoDS_Shape& S, |
201 | const Handle(Geom_Curve)& CC, |
202 | Standard_Real& prmin, |
203 | Standard_Real& prmax, |
204 | Standard_Real& prbmin, |
205 | Standard_Real& prbmax, |
206 | Standard_Boolean& flag, |
207 | const Standard_Boolean Ori) |
208 | { |
209 | LocOpe_CSIntersector ASI(S); |
210 | TColGeom_SequenceOfCurve scur; |
211 | scur.Append(CC); |
212 | ASI.Perform(scur); |
213 | if(ASI.IsDone() && ASI.NbPoints(1) >=1) { |
214 | if (!Ori) { |
215 | prmin = Min(ASI.Point(1,1).Parameter(), |
216 | ASI.Point(1, ASI.NbPoints(1)).Parameter()); |
217 | prmax = Max(ASI.Point(1,1).Parameter(), |
218 | ASI.Point(1, ASI.NbPoints(1)).Parameter()); |
219 | } |
220 | else { |
221 | TopAbs_Orientation Ori = ASI.Point(1,1).Orientation(); |
222 | if (Ori == TopAbs_FORWARD) { |
223 | prmin = ASI.Point(1,1).Parameter(); |
224 | prmax = ASI.Point(1, ASI.NbPoints(1)).Parameter(); |
225 | } |
226 | else { |
227 | prmax = ASI.Point(1,1).Parameter(); |
228 | prmin = ASI.Point(1, ASI.NbPoints(1)).Parameter(); |
229 | } |
230 | } |
231 | flag = Standard_True; |
232 | } |
233 | else { |
234 | prmax = RealFirst(); |
235 | prmin = RealLast(); |
236 | flag = Standard_False; |
237 | } |
238 | |
239 | TopTools_MapOfShape theMap; |
240 | TopExp_Explorer exp(S,TopAbs_EDGE); |
241 | TopLoc_Location Loc; |
242 | Handle(Geom_Curve) C; |
243 | Standard_Real f,l,prm; |
244 | // Standard_Integer i, nbp= 0; |
245 | Standard_Integer i; |
246 | GeomAdaptor_Curve TheCurve(CC); |
247 | Extrema_ExtPC extpc; |
248 | extpc.Initialize(TheCurve,CC->FirstParameter(),CC->LastParameter()); |
249 | prbmin = RealLast(); |
250 | prbmax = RealFirst(); |
251 | for (; exp.More(); exp.Next()) { |
252 | const TopoDS_Edge& edg = TopoDS::Edge(exp.Current()); |
253 | if (!theMap.Add(edg)) { |
254 | continue; |
255 | } |
256 | if (!BRep_Tool::Degenerated(edg)) { |
257 | C = BRep_Tool::Curve(edg,Loc,f,l); |
258 | C = Handle(Geom_Curve)::DownCast(C->Transformed(Loc.Transformation())); |
259 | for (i=1;i<NECHANTBARYC; i++) { |
260 | prm = ((NECHANTBARYC-i)*f + i*l)/NECHANTBARYC; |
261 | gp_Pnt pone = C->Value(prm); |
262 | // On projette sur CC |
263 | extpc.Perform(pone); |
264 | if (extpc.IsDone() && extpc.NbExt() >= 1) { |
265 | Standard_Real Dist2Min = extpc.SquareDistance(1); |
266 | Standard_Integer kmin = 1; |
267 | for (Standard_Integer k=2; k<=extpc.NbExt(); k++) { |
268 | Standard_Real Dist2 = extpc.SquareDistance(k); |
269 | if (Dist2 < Dist2Min) { |
270 | Dist2Min = Dist2; |
271 | kmin = k; |
272 | } |
273 | } |
274 | Standard_Real prmp = extpc.Point(kmin).Parameter(); |
275 | if (prmp <= prbmin) { |
276 | prbmin = prmp; |
277 | } |
278 | if (prmp >= prbmax) { |
279 | prbmax = prmp; |
280 | } |
281 | } |
282 | } |
283 | } |
284 | } |
285 | // Adds every vertex |
286 | for (exp.Init(S,TopAbs_VERTEX); exp.More(); exp.Next()) { |
287 | if (theMap.Add(exp.Current())) { |
288 | gp_Pnt pone = BRep_Tool::Pnt(TopoDS::Vertex(exp.Current())); |
289 | // On projette sur CC |
290 | extpc.Perform(pone); |
291 | if (extpc.IsDone() && extpc.NbExt() >= 1) { |
292 | Standard_Real Dist2Min = extpc.SquareDistance(1); |
293 | Standard_Integer kmin = 1; |
294 | for (Standard_Integer k=2; k<=extpc.NbExt(); k++) { |
295 | Standard_Real Dist2 = extpc.SquareDistance(k); |
296 | if (Dist2 < Dist2Min) { |
297 | Dist2Min = Dist2; |
298 | kmin = k; |
299 | } |
300 | } |
301 | Standard_Real prmp = extpc.Point(kmin).Parameter(); |
302 | if (prmp <= prbmin) { |
303 | prbmin = prmp; |
304 | } |
305 | if (prmp >= prbmax) { |
306 | prbmax = prmp; |
307 | } |
308 | } |
309 | } |
310 | } |
311 | } |
312 | |
313 | |
314 | |
315 | |
316 | //======================================================================= |
317 | //function : IsIn |
318 | //purpose : |
319 | //======================================================================= |
320 | |
321 | static Standard_Boolean IsIn (BRepTopAdaptor_FClass2d& FC, |
322 | Geom2dAdaptor_Curve AC) |
323 | { |
324 | Standard_Real Def = 100*Precision::Confusion(); |
325 | GCPnts_QuasiUniformDeflection QU(AC,Def); |
326 | |
327 | for (Standard_Integer i = 1; i <= QU.NbPoints(); i++) { |
328 | gp_Pnt2d P = AC.Value(QU.Parameter(i)); |
329 | if (FC.Perform(P, Standard_False) == TopAbs_OUT) { |
330 | return Standard_False; |
7fd59977 |
331 | } |
332 | } |
333 | return Standard_True; |
334 | } |
335 | |
336 | |
337 | //======================================================================= |
338 | //function : PutInBoundsU |
339 | //purpose : Recadre la courbe 2d dans les bounds de la face |
340 | //======================================================================= |
341 | //--------------- |
342 | // Recadre en U. |
343 | //--------------- |
344 | |
345 | static void PutInBoundsU (Standard_Real umin, |
346 | Standard_Real umax, |
347 | Standard_Real eps, |
348 | Standard_Real period, |
349 | Standard_Real f, |
350 | Standard_Real l, |
351 | Handle(Geom2d_Curve)& C2d) |
352 | { |
353 | gp_Pnt2d Pf = C2d->Value(f); |
354 | gp_Pnt2d Pl = C2d->Value(l); |
355 | gp_Pnt2d Pm = C2d->Value(0.34*f + 0.66*l); |
356 | Standard_Real minC = Min(Pf.X(),Pl.X()); minC = Min(minC,Pm.X()); |
357 | Standard_Real maxC = Max(Pf.X(),Pl.X()); maxC = Max(maxC,Pm.X()); |
358 | Standard_Real du = 0.; |
359 | if (minC< umin - eps) { |
360 | du = (int((umin - minC)/period) + 1)*period; |
361 | } |
362 | if (minC > umax + eps) { |
363 | du = -(int((minC - umax)/period) + 1)*period; |
364 | } |
365 | if (du != 0) { |
366 | gp_Vec2d T1(du,0.); |
367 | C2d->Translate(T1); |
368 | minC += du; maxC += du; |
369 | } |
370 | // Ajuste au mieux la courbe dans le domaine. |
371 | if (maxC > umax +100*eps) { |
372 | Standard_Real d1 = maxC - umax; |
373 | Standard_Real d2 = umin - minC + period; |
374 | if (d2 < d1) du =-period; |
375 | if ( du != 0.) { |
376 | gp_Vec2d T2(du,0.); |
377 | C2d->Translate(T2); |
378 | } |
379 | } |
380 | } |
381 | |
382 | |
383 | //======================================================================= |
384 | //function : PutInBoundsU |
385 | //purpose : Recadre la courbe 2d dans les bounds de la face |
386 | //======================================================================= |
387 | //--------------- |
388 | // Recadre en V. |
389 | //--------------- |
390 | |
391 | static void PutInBoundsV (Standard_Real vmin, |
392 | Standard_Real vmax, |
393 | Standard_Real eps, |
394 | Standard_Real period, |
395 | Standard_Real f, |
396 | Standard_Real l, |
397 | Handle(Geom2d_Curve)& C2d) |
398 | { |
399 | gp_Pnt2d Pf = C2d->Value(f); |
400 | gp_Pnt2d Pl = C2d->Value(l); |
401 | gp_Pnt2d Pm = C2d->Value(0.34*f + 0.66*l); |
402 | Standard_Real minC = Min(Pf.Y(),Pl.Y()); minC = Min(minC,Pm.Y()); |
403 | Standard_Real maxC = Max(Pf.Y(),Pl.Y()); maxC = Max(maxC,Pm.Y()); |
404 | Standard_Real dv = 0.; |
405 | if (minC< vmin - eps) { |
406 | dv = (int((vmin - minC)/period) + 1)*period; |
407 | } |
408 | if (minC > vmax + eps) { |
409 | dv = -(int((minC - vmax)/period) + 1)*period; |
410 | } |
411 | if (dv != 0) { |
412 | gp_Vec2d T1(0.,dv); |
413 | C2d->Translate(T1); |
414 | minC += dv; maxC += dv; |
415 | } |
416 | // Ajuste au mieux la courbe dans le domaine. |
417 | if (maxC > vmax +100*eps) { |
418 | Standard_Real d1 = maxC - vmax; |
419 | Standard_Real d2 = vmin - minC + period; |
420 | if (d2 < d1) dv =-period; |
421 | if ( dv != 0.) { |
422 | gp_Vec2d T2(0.,dv); |
423 | C2d->Translate(T2); |
424 | } |
425 | } |
426 | } |
427 | |
428 | |
429 | //======================================================================= |
430 | //function : IsInside |
431 | //purpose : |
432 | //======================================================================= |
433 | |
434 | |
435 | Standard_Boolean BRepFeat::IsInside(const TopoDS_Face& F1, |
436 | const TopoDS_Face& F2) |
437 | { |
438 | TopExp_Explorer exp; |
439 | exp.Init(F1, TopAbs_EDGE); |
440 | |
441 | Standard_Real umin,umax,vmin,vmax, uperiod=0, vperiod=0; |
442 | Standard_Integer flagu = 0, flagv = 0; |
443 | TopLoc_Location L; // Recup S avec la location pour eviter la copie. |
444 | Handle (Geom_Surface) S = BRep_Tool::Surface(F2); |
445 | // Standard_Real periodu, periodv; |
446 | BRepTools::UVBounds(F2,umin,umax,vmin,vmax); |
447 | |
448 | if (S->IsUPeriodic()) { |
449 | flagu = 1; |
450 | uperiod = S->UPeriod(); |
451 | } |
452 | |
453 | if (S->IsVPeriodic()) { |
454 | flagv = 1; |
455 | vperiod = S->VPeriod(); |
456 | } |
457 | TopoDS_Shape aLocalShape = F2.Oriented(TopAbs_FORWARD); |
458 | BRepTopAdaptor_FClass2d FC (TopoDS::Face(aLocalShape),Precision::Confusion()); |
459 | // BRepTopAdaptor_FClass2d FC (TopoDS::Face(F2.Oriented(TopAbs_FORWARD)), |
460 | // Precision::Confusion()); |
461 | for(; exp.More(); exp.Next()) { |
462 | Standard_Real f1,l1; |
463 | Handle(Geom_Curve) C0 = BRep_Tool::Curve(TopoDS::Edge(exp.Current()),f1,l1); |
464 | Handle(Geom2d_Curve) C = GeomProjLib::Curve2d(C0,f1,l1,S); |
465 | TopoDS_Edge E = TopoDS::Edge(exp.Current()); |
466 | if(flagu == 1 || flagv == 1) { |
467 | Standard_Real eps = BRep_Tool::Tolerance(E); |
468 | BRep_Tool::Range(E,f1,l1); |
469 | if(flagu == 1) PutInBoundsU(umin, umax, eps, uperiod, f1, l1, C); |
470 | if(flagv == 1) PutInBoundsV(vmin, vmax, eps, vperiod, f1, l1, C); |
471 | } |
472 | Geom2dAdaptor_Curve AC(C,f1,l1); |
473 | if (!IsIn(FC,AC)) { |
474 | return Standard_False; |
7fd59977 |
475 | } |
476 | } |
477 | return Standard_True; |
478 | } |
479 | |
480 | |
481 | |
482 | //======================================================================= |
483 | //function : FaceUntil |
484 | //purpose : |
485 | //======================================================================= |
486 | |
487 | |
488 | void BRepFeat::FaceUntil(const TopoDS_Shape& Sbase, |
489 | TopoDS_Face& FUntil) |
490 | { |
491 | Bnd_Box B; |
492 | BRepBndLib::Add(Sbase,B); |
493 | Standard_Real c[6], bnd; |
494 | B.Get(c[0],c[2],c[4],c[1],c[3],c[5]); |
495 | bnd = c[0]; |
496 | for(Standard_Integer i = 1 ; i < 6; i++) { |
497 | if(c[i] > bnd) bnd = c[i]; |
498 | } |
499 | bnd = 10*bnd; |
500 | |
501 | |
502 | Handle(Geom_Surface) s = BRep_Tool::Surface(FUntil); |
503 | Handle(Standard_Type) styp = s->DynamicType(); |
504 | if (styp == STANDARD_TYPE(Geom_RectangularTrimmedSurface)) { |
505 | s = Handle(Geom_RectangularTrimmedSurface)::DownCast(s)->BasisSurface(); |
506 | styp = s->DynamicType(); |
507 | } |
508 | Handle(Geom_RectangularTrimmedSurface) str; |
509 | if (styp == STANDARD_TYPE(Geom_Plane)) { |
510 | str = new Geom_RectangularTrimmedSurface |
511 | (s, bnd, -bnd, bnd, -bnd, Standard_True, Standard_True); |
512 | } |
513 | else if (styp == STANDARD_TYPE(Geom_CylindricalSurface)) { |
514 | str = new Geom_RectangularTrimmedSurface |
c6541a0c |
515 | (s, 0., 2.*M_PI, bnd, -bnd, Standard_True, Standard_True); |
7fd59977 |
516 | } |
517 | else if (styp == STANDARD_TYPE(Geom_ConicalSurface)) { |
518 | str = new Geom_RectangularTrimmedSurface |
c6541a0c |
519 | (s, 0., 2.*M_PI, bnd, -bnd, Standard_True, Standard_True); |
7fd59977 |
520 | } |
521 | else { |
522 | FUntil.Nullify(); |
523 | return; |
524 | } |
525 | |
1c72dff6 |
526 | FUntil = BRepLib_MakeFace(str, Precision::Confusion()); |
7fd59977 |
527 | } |
528 | |
529 | |
530 | |
531 | //======================================================================= |
532 | //function : Tool |
533 | //purpose : |
534 | //======================================================================= |
535 | |
536 | TopoDS_Solid BRepFeat::Tool(const TopoDS_Shape& SRef, |
537 | const TopoDS_Face& Fac, |
538 | const TopAbs_Orientation Orf) |
539 | { |
540 | TopTools_ListOfShape lfaces; |
541 | // for (TopExp_Explorer exp(SRef,TopAbs_FACE); exp.More(); exp.Next()) { |
542 | TopExp_Explorer exp(SRef,TopAbs_FACE) ; |
543 | for ( ; exp.More(); exp.Next()) { |
544 | if (exp.Current().ShapeType() == TopAbs_FACE) { |
545 | lfaces.Append(exp.Current()); |
546 | } |
547 | } |
548 | |
549 | LocOpe_BuildShape bs(lfaces); |
550 | const TopoDS_Shape& Res = bs.Shape(); |
551 | TopoDS_Shell Sh; |
552 | if (Res.ShapeType() == TopAbs_SHELL) { |
553 | // faire un solide |
554 | Sh = TopoDS::Shell(Res); |
555 | } |
556 | else if (Res.ShapeType() == TopAbs_SOLID) { |
557 | exp.Init(Res,TopAbs_SHELL); |
558 | Sh = TopoDS::Shell(exp.Current()); |
559 | exp.Next(); |
560 | if (exp.More()) { |
561 | Sh.Nullify(); |
562 | } |
563 | } |
564 | |
565 | if (Sh.IsNull()) { |
566 | TopoDS_Solid So; |
567 | return So; |
568 | } |
569 | |
570 | |
571 | Sh.Orientation(TopAbs_FORWARD); |
1d47d8d0 |
572 | |
7fd59977 |
573 | TopAbs_Orientation orient = TopAbs_FORWARD; |
1d47d8d0 |
574 | |
7fd59977 |
575 | for (exp.Init(Sh,TopAbs_FACE); exp.More(); exp.Next()) { |
576 | if (exp.Current().IsSame(Fac)) { |
577 | orient = exp.Current().Orientation(); |
578 | break; |
579 | } |
580 | } |
581 | |
582 | Standard_Boolean reverse = Standard_False; |
583 | if ((orient == Fac.Orientation() && Orf == TopAbs_REVERSED) || |
584 | (orient != Fac.Orientation() && Orf == TopAbs_FORWARD)) { |
585 | reverse = Standard_True; |
586 | } |
587 | |
588 | if (reverse) { |
589 | Sh.Reverse(); |
590 | } |
591 | |
592 | BRep_Builder B; |
593 | TopoDS_Solid Soc; |
594 | B.MakeSolid(Soc); |
595 | B.Add(Soc,Sh); |
596 | return Soc; |
597 | } |
598 | |
599 | |
600 | //======================================================================= |
601 | //function : Print |
602 | //purpose : Print the error Description of a StatusError on a stream. |
603 | //======================================================================= |
604 | |
605 | Standard_OStream& BRepFeat::Print(const BRepFeat_StatusError se, |
606 | Standard_OStream& s) |
607 | { |
608 | switch(se) { |
609 | case BRepFeat_OK : |
610 | s << "No error"; |
611 | break; |
612 | case BRepFeat_BadDirect : |
613 | s << "Directions must be opposite"; |
614 | break; |
615 | case BRepFeat_BadIntersect : |
616 | s << "Intersection failure"; |
617 | break; |
618 | case BRepFeat_EmptyBaryCurve : |
619 | s << "Empty BaryCurve"; |
620 | break; |
621 | case BRepFeat_EmptyCutResult : |
622 | s << "Failure in Cut : Empty resulting shape"; |
623 | break;; |
624 | case BRepFeat_FalseSide : |
625 | s << "Verify plane and wire orientation"; |
626 | break; |
627 | case BRepFeat_IncDirection : |
628 | s << "Incoherent Direction for shapes From and Until"; |
629 | break; |
630 | case BRepFeat_IncSlidFace : |
631 | s << "Sliding face not in Base shape"; |
632 | break; |
633 | case BRepFeat_IncParameter : |
634 | s << "Incoherent Parameter : shape Until before shape From"; |
635 | break; |
636 | case BRepFeat_IncTypes : |
637 | s << "Invalid option for faces From and Until : 1 Support and 1 not"; |
638 | break; |
639 | case BRepFeat_IntervalOverlap : |
640 | s << "Shapes From and Until overlap"; |
641 | break; |
642 | case BRepFeat_InvFirstShape : |
643 | s << "Invalid First shape : more than 1 face"; |
644 | break; |
645 | case BRepFeat_InvOption : |
646 | s << "Invalid option"; |
647 | break; |
648 | case BRepFeat_InvShape : |
649 | s << "Invalid shape"; |
650 | break; |
651 | case BRepFeat_LocOpeNotDone : |
652 | s << "Local Operation not done"; |
653 | break; |
654 | case BRepFeat_LocOpeInvNotDone : |
655 | s << "Local Operation : intersection line conflict"; |
656 | break; |
657 | case BRepFeat_NoExtFace : |
658 | s << "No Extreme faces"; |
659 | break; |
660 | case BRepFeat_NoFaceProf : |
661 | s << "No Face Profile"; |
662 | break; |
663 | case BRepFeat_NoGluer : |
664 | s << "Gluer Failure"; |
665 | break; |
666 | case BRepFeat_NoIntersectF : |
667 | s << "No intersection between Feature and shape From"; |
668 | break; |
669 | case BRepFeat_NoIntersectU : |
670 | s << "No intersection between Feature and shape Until"; |
671 | break; |
672 | case BRepFeat_NoParts : |
673 | s << "No parts of tool kept"; |
674 | break; |
675 | case BRepFeat_NoProjPt : |
676 | s << "No projection points"; |
677 | break; |
678 | case BRepFeat_NotInitialized : |
679 | s << "Fields not initialized"; |
680 | break; |
681 | case BRepFeat_NotYetImplemented : |
682 | s << "Not yet implemented"; |
683 | break; |
684 | case BRepFeat_NullRealTool : |
685 | s << "Real Tool : Null DPrism"; |
686 | break; |
687 | case BRepFeat_NullToolF : |
688 | s << "Null Tool : Invalid type for shape Form"; |
689 | break; |
690 | case BRepFeat_NullToolU : |
691 | s << "Null Tool : Invalid type for shape Until"; |
692 | break; |
693 | } |
694 | return s; |
695 | } |
696 | |