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