7fd59977 |
1 | // File: LocOpe_Generator.cxx |
2 | // Created: Tue Jan 9 13:57:18 1996 |
3 | // Author: Jacques GOUSSARD |
4 | // <jag@bravox> |
5 | // Modifed: Portage NT 7-5-97 DPF (return NewParameter) |
6 | |
7 | #include <LocOpe_Generator.ixx> |
8 | |
9 | #include <TopTools_MapOfShape.hxx> |
10 | #include <TopTools_DataMapOfShapeShape.hxx> |
11 | #include <TopTools_DataMapOfShapeListOfShape.hxx> |
12 | #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx> |
13 | #include <TopTools_ListIteratorOfListOfShape.hxx> |
14 | #include <TopTools_MapIteratorOfMapOfShape.hxx> |
15 | #include <TopTools_DataMapIteratorOfDataMapOfShapeListOfShape.hxx> |
16 | #include <TopoDS_Iterator.hxx> |
17 | #include <TopoDS_Solid.hxx> |
18 | #include <TopoDS_Wire.hxx> |
19 | #include <TopoDS_Edge.hxx> |
20 | #include <TopoDS_Vertex.hxx> |
21 | |
22 | |
23 | #include <TopExp_Explorer.hxx> |
24 | |
25 | #include <gp_Pln.hxx> |
26 | #include <gp_Cylinder.hxx> |
27 | |
28 | #include <BRep_Builder.hxx> |
29 | #include <BRep_Tool.hxx> |
30 | #include <BRepAlgo_Loop.hxx> |
31 | |
32 | #include <Geom_Surface.hxx> |
33 | #include <Geom_RectangularTrimmedSurface.hxx> |
34 | #include <Geom_Plane.hxx> |
35 | #include <Geom_CylindricalSurface.hxx> |
36 | #include <Geom_Curve.hxx> |
37 | #include <Geom_TrimmedCurve.hxx> |
38 | #include <Geom_Line.hxx> |
39 | #include <Geom_Circle.hxx> |
40 | #include <Geom2d_Curve.hxx> |
41 | |
42 | #include <LocOpe_BuildShape.hxx> |
43 | |
44 | #include <TopoDS.hxx> |
45 | #include <TopExp.hxx> |
46 | #include <BRepTools.hxx> |
47 | #include <GeomProjLib.hxx> |
48 | #include <ElCLib.hxx> |
49 | #include <Precision.hxx> |
50 | |
51 | static Standard_Boolean ToFuse(const TopoDS_Face& , |
52 | const TopoDS_Face&); |
53 | |
54 | |
55 | static Standard_Boolean ToFuse(const TopoDS_Edge& , |
56 | const TopoDS_Edge&); |
57 | |
58 | |
59 | static Standard_Boolean ToFuse(const TopoDS_Edge&, |
60 | const TopoDS_Face&, |
61 | const TopoDS_Vertex&, |
62 | const TopTools_MapOfShape&); |
63 | |
64 | static Standard_Real NewParameter(const TopoDS_Edge&, |
65 | const TopoDS_Vertex&, |
66 | const TopoDS_Edge&, |
67 | const TopoDS_Vertex&); |
68 | |
69 | #ifdef DEB |
70 | static Standard_Boolean Contains(const TopTools_ListOfShape&, |
71 | const TopoDS_Shape&); |
72 | #endif |
73 | |
74 | |
75 | |
76 | |
77 | //======================================================================= |
78 | //function : Perform |
79 | //purpose : |
80 | //======================================================================= |
81 | |
82 | void LocOpe_Generator::Perform(const Handle(LocOpe_GeneratedShape)& G) |
83 | { |
84 | if (myShape.IsNull()) { |
85 | Standard_NullObject::Raise(); |
86 | } |
87 | myDone = Standard_False; |
88 | myRes.Nullify(); |
89 | // myDescFaces.Clear(); |
90 | myModShapes.Clear(); |
91 | // myFFromE.Clear(); |
92 | |
93 | const TopTools_ListOfShape& ledges = G->GeneratingEdges(); |
94 | |
95 | // On genere une liste des faces a gauche du wire. Equivalent du LeftOf. |
96 | // Attention : il faudra bien propager pour ne pas oublier des faces |
97 | // a l`interieur |
98 | |
99 | TopExp_Explorer exp, exp2, exp3; |
100 | TopTools_MapOfShape theLeft; // Faces a gauche |
101 | |
102 | TopTools_MapOfShape GEdg,GVtx; // Edges et vertex generateurs |
103 | |
104 | TopTools_ListIteratorOfListOfShape itl,itl2; |
105 | |
106 | |
107 | for (itl.Initialize(ledges); itl.More(); itl.Next()) { |
108 | const TopoDS_Edge& edg = TopoDS::Edge(itl.Value()); |
109 | |
110 | GEdg.Add(edg); |
111 | for (exp2.Init(edg,TopAbs_VERTEX); exp2.More(); exp2.Next()) { |
112 | const TopoDS_Vertex& vtx = TopoDS::Vertex(exp2.Current()); |
113 | if (!GVtx.Contains(vtx)) { |
114 | GVtx.Add(vtx); |
115 | } |
116 | } |
117 | for (exp2.Init(myShape, TopAbs_FACE); exp2.More(); exp2.Next()) { |
118 | const TopoDS_Face& fac = TopoDS::Face(exp2.Current()); |
119 | for (exp3.Init(fac,TopAbs_EDGE); exp3.More(); exp3.Next()) { |
120 | if (exp3.Current().IsSame(edg) && |
121 | exp3.Current().Orientation() == edg.Orientation()) { |
122 | theLeft.Add(fac); |
123 | TopTools_ListOfShape emptylist; |
124 | if(!myModShapes.IsBound(fac)) { |
125 | myModShapes.Bind(fac,emptylist); |
126 | } |
127 | break; |
128 | } |
129 | } |
130 | if (exp3.More()) { |
131 | break; |
132 | } |
133 | } |
134 | } |
135 | |
136 | TopTools_IndexedDataMapOfShapeListOfShape theEFMap; |
137 | TopExp::MapShapesAndAncestors(myShape,TopAbs_EDGE,TopAbs_FACE,theEFMap); |
138 | |
139 | TopTools_DataMapOfShapeListOfShape theEEMap; |
140 | TopTools_DataMapOfShapeListOfShape theFFMap; |
141 | TopTools_MapOfShape toRemove; |
142 | TopTools_MapIteratorOfMapOfShape itm; |
143 | TopTools_DataMapIteratorOfDataMapOfShapeListOfShape itf; |
144 | |
145 | // recherche des fusions de faces |
146 | for (itm.Initialize(GEdg); itm.More(); itm.Next()) { |
147 | const TopoDS_Edge& edg = TopoDS::Edge(itm.Key()); |
148 | if (!theEFMap.Contains(edg)) { |
149 | continue; |
150 | } |
151 | for (itl2.Initialize(theEFMap.FindFromKey(edg));itl2.More();itl2.Next()){ |
152 | if (!theLeft.Contains(itl2.Value())) { |
153 | break; |
154 | } |
155 | } |
156 | if (!itl2.More()) { // edge "interne" au shell, ou bord libre |
157 | } |
158 | else { |
159 | const TopoDS_Face& fac = TopoDS::Face(itl2.Value()); |
160 | TopoDS_Face facbis = G->Generated(edg); |
161 | if (ToFuse(fac,facbis)) { |
162 | // On recherche si une face a deja fusionne avec facbis |
163 | Standard_Boolean facbisfound = Standard_False; |
164 | for (itf.Initialize(theFFMap); itf.More(); itf.Next()) { |
165 | if (itf.Key().IsSame(fac)) { |
166 | continue; |
167 | } |
168 | for (itl.Initialize(itf.Value()); itl.More(); itl.Next()) { |
169 | if (itl.Value().IsSame(facbis)) { |
170 | facbisfound = Standard_True; |
171 | break; |
172 | } |
173 | } |
174 | if (facbisfound) { |
175 | theFFMap(itf.Key()).Append(fac); |
176 | toRemove.Add(fac); |
177 | toRemove.Add(edg); |
178 | break; |
179 | } |
180 | } |
181 | |
182 | if (!facbisfound) { |
183 | if (!theFFMap.IsBound(fac)) { |
184 | TopTools_ListOfShape thelist; |
185 | theFFMap.Bind(fac, thelist); |
186 | } |
187 | for (itl.Initialize(theFFMap(fac)); itl.More(); itl.Next()) { |
188 | if (itl.Value().IsSame(facbis)) { |
189 | break; |
190 | } |
191 | } |
192 | if (!itl.More()) { |
193 | theFFMap(fac).Append(facbis); |
194 | } |
195 | toRemove.Add(edg); |
196 | toRemove.Add(facbis); |
197 | } |
198 | } |
199 | else { // face generee par edg : on la marque. |
200 | // myFFromE.Bind(edg,facbis); |
201 | } |
202 | } |
203 | } |
204 | |
205 | |
206 | // Il faut ici ajouter dans toRemove les edges de connexites entre faces |
207 | // a fusionner avec une meme face de base |
208 | |
209 | // TopTools_DataMapIteratorOfDataMapOfShapeListOfShape itf(theFFMap); |
210 | itf.Initialize(theFFMap); |
211 | for (; itf.More(); itf.Next()) { |
212 | for (itl.Initialize(itf.Value()); itl.More(); itl.Next()) { |
213 | for (exp.Init(itl.Value(),TopAbs_EDGE); exp.More(); exp.Next()) { |
214 | const TopoDS_Edge& ed = TopoDS::Edge(exp.Current()); |
215 | if (toRemove.Contains(ed)) { |
216 | continue; |
217 | } |
218 | for (itl2.Initialize(itf.Value()); itl2.More(); itl2.Next()) { |
219 | if (!itl2.Value().IsSame(itl.Value())) { |
220 | for (exp2.Init(itl2.Value(),TopAbs_EDGE);exp2.More();exp2.Next()) { |
221 | if (ed.IsSame(exp2.Current())) { |
222 | toRemove.Add(ed); |
223 | break; |
224 | } |
225 | } |
226 | if (exp2.More()) { |
227 | break; |
228 | } |
229 | } |
230 | } |
231 | } |
232 | } |
233 | } |
234 | |
235 | TopTools_ListOfShape RebuildFace; |
236 | TopTools_MapOfShape mapTreated; |
237 | TopTools_DataMapOfShapeShape DontFuse; |
238 | TopAbs_Orientation orient,orface,orsav; |
239 | |
240 | for (itf.Reset(); itf.More(); itf.Next()) { |
241 | const TopoDS_Face& fac = TopoDS::Face(itf.Key()); |
242 | for (exp.Init(fac,TopAbs_EDGE); exp.More(); exp.Next()) { |
243 | const TopoDS_Edge& edg = TopoDS::Edge(exp.Current()); |
244 | if (mapTreated.Contains(edg)) { |
245 | continue; // on saute l`edge |
246 | } |
247 | |
248 | mapTreated.Add(edg); |
249 | for (exp2.Init(edg,TopAbs_VERTEX); exp2.More(); exp2.Next()) { |
250 | const TopoDS_Vertex& vtx = TopoDS::Vertex(exp2.Current()); |
251 | if (GVtx.Contains(vtx)) { |
252 | TopoDS_Edge edgbis = G->Generated(vtx); |
253 | |
254 | if ((edgbis.IsNull() || BRep_Tool::Degenerated(edgbis)) || |
255 | // toRemove.Contains(edgbis) || |
256 | !ToFuse(edg,edgbis)) { |
257 | continue; |
258 | } |
259 | // a voir |
260 | if (BRepTools::IsReallyClosed(edg,fac)) { |
261 | if (!theEEMap.IsBound(edg)) { |
262 | TopTools_ListOfShape thelist1; |
263 | theEEMap.Bind(edg, thelist1); |
264 | theEEMap(edg).Append(edgbis); |
265 | toRemove.Add(edgbis); // toujours vrai pour edge double |
266 | Standard_Boolean FuseEdge = Standard_True; |
267 | TopoDS_Vertex Vf,Vl; |
268 | TopExp::Vertices(edg,Vf,Vl); |
269 | Standard_Boolean ConnectLast = (Vl.IsSame(vtx)); |
270 | for (exp3.Init(fac.Oriented(TopAbs_FORWARD),TopAbs_EDGE); |
271 | exp3.More(); exp3.Next()) { |
272 | const TopoDS_Edge& eee = TopoDS::Edge(exp3.Current()); |
273 | orient = eee.Orientation(); |
274 | if (!eee.IsSame(edg)) { |
275 | TopExp::Vertices(eee,Vf,Vl); |
276 | if ((Vf.IsSame(vtx) || Vl.IsSame(vtx)) && |
277 | !toRemove.Contains(eee)) { |
278 | FuseEdge = Standard_False; |
279 | // On recherche celui qu`il ne faut pas fusionner |
280 | |
281 | if ((Vf.IsSame(vtx) && orient == TopAbs_FORWARD) || |
282 | (Vl.IsSame(vtx) && orient == TopAbs_REVERSED)) { |
283 | if (ConnectLast) { |
284 | DontFuse.Bind(edg,fac.Oriented(TopAbs_FORWARD)); |
285 | } |
286 | else { |
287 | DontFuse.Bind(edg,fac.Oriented(TopAbs_REVERSED)); |
288 | } |
289 | } |
290 | else { |
291 | if (ConnectLast) { |
292 | DontFuse.Bind(edg,fac.Oriented(TopAbs_REVERSED)); |
293 | } |
294 | else { |
295 | DontFuse.Bind(edg,fac.Oriented(TopAbs_FORWARD)); |
296 | } |
297 | } |
298 | break; |
299 | } |
300 | } |
301 | } |
302 | if (FuseEdge) { |
303 | toRemove.Add(vtx); |
304 | } |
305 | } |
306 | } |
307 | |
308 | |
309 | else { |
310 | /* A VOIR |
311 | if (!BRep_Tool::IsClosed(edg,fac)) { |
312 | */ |
313 | if (!theEEMap.IsBound(edg)) { |
314 | TopTools_ListOfShape thelist2; |
315 | theEEMap.Bind(edg, thelist2); |
316 | } |
317 | theEEMap(edg).Append(edgbis); |
318 | const TopTools_ListOfShape& L = theEEMap(edg); |
319 | TopTools_ListIteratorOfListOfShape Lit(L); |
320 | Standard_Boolean OK = Standard_True; |
321 | for (; Lit.More(); Lit.Next()) { |
322 | if (Lit.Value().IsSame(edgbis)) { |
323 | OK = Standard_False; |
324 | break; |
325 | } |
326 | } |
327 | if (OK) theEEMap(edg).Append(edgbis); |
328 | |
329 | itl.Initialize(theEFMap.FindFromKey(edg)); |
330 | Standard_Boolean FuseEdge = ToFuse(edg,fac,vtx,toRemove); |
331 | if (!FuseEdge) { |
332 | DontFuse.Bind(edg,fac); |
333 | } |
334 | else { |
335 | for (; itl.More(); itl.Next()) { |
336 | if (!itl.Value().IsSame(fac)) { |
337 | if (theFFMap.IsBound(itl.Value())) { |
338 | FuseEdge = ToFuse(edg,TopoDS::Face(itl.Value()), |
339 | vtx,toRemove); |
340 | // edge a fusionner |
341 | if (FuseEdge) { |
342 | toRemove.Add(vtx); |
343 | } |
344 | else { |
345 | if (toRemove.Contains(vtx)) { |
346 | toRemove.Remove(vtx); |
347 | } |
348 | DontFuse.Bind(edg,itl.Value()); |
349 | } |
350 | } |
351 | else { // on marque comme face a reconstruire |
352 | RebuildFace.Append(itl.Value()); |
353 | if (toRemove.Contains(vtx)) { |
354 | toRemove.Remove(vtx); |
355 | } |
356 | DontFuse.Bind(edg,itl.Value()); |
357 | } |
358 | |
359 | break; |
360 | } |
361 | } |
362 | } |
363 | } |
364 | } |
365 | } |
366 | } |
367 | } |
368 | |
369 | |
370 | |
371 | for (itl.Initialize(RebuildFace); itl.More(); itl.Next()) { |
372 | TopTools_ListOfShape thelist3; |
373 | theFFMap.Bind(itl.Value(), thelist3); |
374 | } |
375 | |
376 | BRep_Builder B; |
377 | TopoDS_Face newface; |
378 | TopoDS_Wire outw,newwire; |
379 | TopoDS_Edge newedg; |
380 | TopoDS_Vertex newvtx; |
381 | TopLoc_Location loc; |
382 | Standard_Real tol,prm,f,l, Uminc,Umaxc;; |
383 | gp_Pnt2d pf,pl; |
384 | |
385 | Handle(Geom_Surface) S; |
386 | Handle(Geom_Plane) P; |
387 | Handle(Geom_Curve) C; |
388 | |
389 | // Fusion des edges |
390 | TopTools_DataMapIteratorOfDataMapOfShapeListOfShape ite(theEEMap); |
391 | for (; ite.More(); ite.Next()) { |
392 | Standard_Boolean KeepNewEdge = Standard_False; |
393 | const TopoDS_Edge& edg = TopoDS::Edge(ite.Key()); |
394 | BRep_Tool::Range(edg,f,l); |
395 | TopoDS_Shape aLocalEdge = edg.EmptyCopied(); |
396 | newedg = TopoDS::Edge(aLocalEdge); |
397 | // newedg = TopoDS::Edge(edg.EmptyCopied()); |
398 | newedg.Orientation(TopAbs_FORWARD); |
399 | for (exp.Init(edg.Oriented(TopAbs_FORWARD),TopAbs_VERTEX); |
400 | exp.More(); exp.Next()) { |
401 | const TopoDS_Vertex& vtx = TopoDS::Vertex(exp.Current()); |
402 | prm = BRep_Tool::Parameter(vtx,edg); |
403 | |
404 | newvtx.Nullify(); |
405 | for (itl.Initialize(theEEMap(edg)); itl.More(); itl.Next()) { |
406 | const TopoDS_Edge& edgbis = TopoDS::Edge(itl.Value()); |
407 | for (exp2.Init(edgbis,TopAbs_VERTEX); exp2.More(); exp2.Next()) { |
408 | if (exp2.Current().IsSame(vtx)) { |
409 | break; |
410 | } |
411 | } |
412 | if (exp2.More()) { |
413 | for (exp2.ReInit(); exp2.More(); exp2.Next()) { |
414 | if (!exp2.Current().IsSame(vtx)) { |
415 | newvtx = TopoDS::Vertex(exp2.Current()); |
416 | prm = NewParameter(edg,vtx,newedg,newvtx); |
417 | break; |
418 | } |
419 | } |
420 | break; |
421 | } |
422 | } |
423 | |
424 | if (toRemove.Contains(vtx) || |
425 | (prm <l && prm > f)) { |
426 | B.Add(newedg,newvtx.Oriented(vtx.Orientation())); |
427 | tol = BRep_Tool::Tolerance(newvtx); |
428 | B.UpdateVertex(newvtx,prm,newedg,tol); |
429 | toRemove.Add(itl.Value()); // i-e edgbis |
430 | KeepNewEdge = Standard_True; |
431 | } |
432 | else { |
433 | B.Add(newedg,vtx.Oriented(vtx.Orientation())); |
434 | tol = BRep_Tool::Tolerance(vtx); |
435 | B.UpdateVertex(vtx,prm,newedg,tol); |
436 | } |
437 | } |
438 | if (KeepNewEdge) { |
439 | TopTools_ListOfShape emptylist; |
440 | if(!myModShapes.IsBound(edg)) { |
441 | myModShapes.Bind(edg,emptylist); |
442 | } |
443 | myModShapes(edg).Append(newedg); |
444 | toRemove.Add(edg); |
445 | } |
446 | } |
447 | |
448 | TopTools_MapOfShape EdgAdded; |
449 | |
450 | // Fusion des faces, ou reconstruction |
451 | for (itf.Reset();itf.More(); itf.Next()) { |
452 | const TopoDS_Face& fac = TopoDS::Face(itf.Key()); |
453 | Standard_Boolean ModFace = Standard_False; |
454 | Standard_Boolean HasWire = Standard_False; |
455 | TopTools_ListOfShape listofedg; |
456 | |
457 | EdgAdded.Clear(); |
458 | |
459 | for(exp.Init(myShape,TopAbs_FACE); exp.More(); exp.Next()) { |
460 | if (exp.Current().IsSame(fac)) { |
461 | break; |
462 | } |
463 | } |
464 | orface = exp.Current().Orientation(); |
465 | TopoDS_Shape aLocalFace = fac.EmptyCopied(); |
466 | newface = TopoDS::Face(aLocalFace); |
467 | // newface = TopoDS::Face(fac.EmptyCopied()); |
468 | newface.Orientation(TopAbs_FORWARD); |
469 | S = BRep_Tool::Surface(fac); |
470 | if (S->DynamicType()== STANDARD_TYPE(Geom_RectangularTrimmedSurface)) { |
471 | S = (*((Handle(Geom_RectangularTrimmedSurface)*)&S))->BasisSurface(); |
472 | } |
473 | P = Handle(Geom_Plane)::DownCast(S); |
474 | TopoDS_Wire wir; |
475 | for (exp.Init(fac.Oriented(TopAbs_FORWARD),TopAbs_WIRE); |
476 | exp.More(); exp.Next()) { |
477 | wir = TopoDS::Wire(exp.Current()); |
478 | for (exp2.Init(wir,TopAbs_EDGE); exp2.More(); exp2.Next()) { |
479 | const TopoDS_Edge& edg = TopoDS::Edge(exp2.Current()); |
480 | if (toRemove.Contains(edg) || myModShapes.IsBound(edg) ) { |
481 | break; |
482 | } |
483 | } |
484 | if (!exp2.More()) { // wire non modifie |
485 | // B.Add(newface,wir.Oriented(wir.Orientation())); |
486 | for (exp2.Init(wir,TopAbs_EDGE); exp2.More(); exp2.Next()) { |
487 | listofedg.Append(exp2.Current()); |
488 | } |
489 | HasWire = Standard_True; |
490 | } |
491 | else { |
492 | if (!ModFace) { |
493 | |
494 | // Petit truc crad pour les p-curves sur les cylindres... |
495 | if (P.IsNull()) { |
496 | Standard_Real Vminc,Vmaxc; |
497 | BRepTools::UVBounds(fac,Uminc,Umaxc,Vminc,Vmaxc); |
498 | } |
499 | |
500 | |
501 | // premier passage : on met les wires non touches des faces |
502 | // en vis a vis |
503 | |
504 | for (itl.Initialize(itf.Value()); itl.More(); itl.Next()) { |
505 | TopoDS_Face facbis = TopoDS::Face(itl.Value()); |
506 | for (itl2.Initialize(G->OrientedFaces());itl2.More();itl2.Next()) { |
507 | if (itl2.Value().IsSame(facbis)) { |
508 | break; |
509 | } |
510 | } |
511 | if (itl2.More()) { |
512 | orient = itl2.Value().Orientation(); |
513 | facbis.Orientation(orient); |
514 | } |
515 | else { // on fusionne avec une autre face du shape... |
516 | for (exp2.Init(myShape, TopAbs_FACE); exp2.More(); exp2.Next()) { |
517 | if (exp2.Current().IsSame(facbis)) { |
518 | facbis.Orientation(exp2.Current().Orientation()); |
519 | break; |
520 | } |
521 | } |
522 | } |
523 | |
524 | for (exp3.Init(facbis,TopAbs_WIRE); exp3.More(); exp3.Next()) { |
525 | for (exp2.Init(exp3.Current(),TopAbs_EDGE); |
526 | exp2.More(); exp2.Next()) { |
527 | if (toRemove.Contains(exp2.Current())) { |
528 | break; |
529 | } |
530 | } |
531 | if (!exp2.More()) { |
532 | TopoDS_Wire theNew; |
533 | B.MakeWire(theNew); // FORWARD |
534 | for (exp2.ReInit(); exp2.More(); exp2.Next()) { |
535 | const TopoDS_Edge& edg = TopoDS::Edge(exp2.Current()); |
536 | |
537 | orient = TopAbs::Compose(orface,edg.Orientation()); |
538 | // B.Add(theNew,edg.Oriented(or)); |
539 | listofedg.Append(edg.Oriented(orient)); |
540 | EdgAdded.Add(edg); |
541 | if (P.IsNull()) { |
542 | // on met les courbes 2d si on n`est pas sur un plan |
543 | // on ne devrait pas avoir de pb d`edge de couture. |
544 | tol = BRep_Tool::Tolerance(edg); |
545 | C = BRep_Tool::Curve(edg,loc,f,l); |
546 | if (!loc.IsIdentity()) { |
547 | Handle(Geom_Geometry) GG = C->Transformed(loc.Transformation()); |
548 | C = *((Handle(Geom_Curve)*)&GG); |
549 | } |
550 | if (C->DynamicType() == STANDARD_TYPE(Geom_TrimmedCurve)) { |
551 | C = (*((Handle(Geom_TrimmedCurve)*)&C))->BasisCurve(); |
552 | } |
553 | |
554 | Handle(Geom2d_Curve) C2d = GeomProjLib::Curve2d(C,f,l,S,tol); |
555 | |
556 | // Tentative de recalage dans la facette |
557 | pf = C2d->Value(f); |
558 | pl = C2d->Value(l); |
559 | Standard_Real tttol = Precision::Angular(); |
560 | while (Min(pf.X(),pl.X()) >= Umaxc-tttol) { |
561 | C2d->Translate(gp_Vec2d(-2.*PI,0)); |
562 | pf = C2d->Value(f); |
563 | pl = C2d->Value(l); |
564 | } |
565 | |
566 | while (Max(pf.X(),pl.X()) <= Uminc+tttol) { |
567 | C2d->Translate(gp_Vec2d(2.*PI,0)); |
568 | pf = C2d->Value(f); |
569 | pl = C2d->Value(l); |
570 | } |
571 | |
572 | if (!BRepTools::IsReallyClosed(edg,facbis)) { |
573 | B.UpdateEdge(edg,C2d,newface,tol); |
574 | } |
575 | // else { |
576 | // cout << "Edge double bizarre... " << endl; |
577 | // } |
578 | } |
579 | } |
580 | // B.Add(newface,theNew); |
581 | HasWire = Standard_True; |
582 | } |
583 | } |
584 | } |
585 | ModFace = Standard_True; |
586 | } |
587 | |
588 | orsav = wir.Orientation(); |
589 | // reconstruction du wire |
590 | //B.MakeWire(newwire); |
591 | |
592 | Handle(Geom2d_Curve) C2d,C2d1; |
593 | Standard_Boolean EmptyWire = Standard_True; |
594 | |
595 | // for (exp2.Init(wir.Oriented(TopAbs_FORWARD),TopAbs_EDGE); |
596 | for (exp2.Init(wir,TopAbs_EDGE); exp2.More(); exp2.Next()) { |
597 | const TopoDS_Edge& edg = TopoDS::Edge(exp2.Current()); |
598 | orient = edg.Orientation(); |
599 | if (!toRemove.Contains(edg) && !theEEMap.IsBound(edg)) { |
600 | // B.Add(newwire,edg.Oriented(or)); |
601 | // listofedg.Append(edg.Oriented(or)); |
602 | listofedg.Append(edg); |
603 | EmptyWire = Standard_False; |
604 | } |
605 | else if (myModShapes.IsBound(edg) || theEEMap.IsBound(edg)) { |
606 | if (myModShapes.IsBound(edg)) { |
607 | newedg = TopoDS::Edge(myModShapes(edg).First()); |
608 | } |
609 | else { |
610 | newedg = edg; |
611 | } |
612 | // B.Add(newwire,newedg.Oriented(or)); |
613 | listofedg.Append(newedg.Oriented(orient)); |
614 | EmptyWire = Standard_False; |
615 | C = BRep_Tool::Curve(newedg,loc,f,l); |
616 | if (!loc.IsIdentity()) { |
617 | Handle(Geom_Geometry) GG = C->Transformed(loc.Transformation()); |
618 | C = *((Handle(Geom_Curve)*)&GG); |
619 | } |
620 | if (C->DynamicType() == STANDARD_TYPE(Geom_TrimmedCurve)) { |
621 | C = (*((Handle(Geom_TrimmedCurve)*)&C))->BasisCurve(); |
622 | } |
623 | if (P.IsNull()) { // on met les courbes 2d si on n`est pas |
624 | // sur un plan |
625 | // TopAbs_Orientation oredonfafw = TopAbs::Compose(or,orsav); |
626 | TopAbs_Orientation oredonfafw = orient; |
627 | tol = BRep_Tool::Tolerance(newedg); |
628 | TopoDS_Shape aLocalEdge = edg.Oriented(oredonfafw); |
629 | TopoDS_Shape aLocalFace = fac.Oriented(TopAbs_FORWARD); |
630 | C2d = BRep_Tool::CurveOnSurface |
631 | (TopoDS::Edge(aLocalEdge),TopoDS::Face(aLocalFace),f,l); |
632 | // C2d = BRep_Tool::CurveOnSurface |
633 | // (TopoDS::Edge(edg.Oriented(oredonfafw)), |
634 | // TopoDS::Face(fac.Oriented(TopAbs_FORWARD)), |
635 | // f,l); |
636 | |
637 | if (!BRepTools::IsReallyClosed(edg,fac)) { |
638 | B.UpdateEdge(newedg,C2d,newface,tol); |
639 | } |
640 | else if (C2d1.IsNull()){ |
641 | C2d1 = C2d; |
642 | } |
643 | else { |
644 | // if (TopAbs::Compose(orsav,or) == TopAbs_FORWARD) { |
645 | if (orient == TopAbs_FORWARD) { |
646 | B.UpdateEdge(newedg,C2d,C2d1,newface,tol); |
647 | } |
648 | else { |
649 | B.UpdateEdge(newedg,C2d1,C2d,newface,tol); |
650 | } |
651 | } |
652 | } |
653 | Standard_Boolean AddPart = Standard_False; |
654 | if (DontFuse.IsBound(edg)) { |
655 | if (!BRepTools::IsReallyClosed(edg,fac)) { |
656 | if (DontFuse(edg).IsSame(fac)) { |
657 | if (myModShapes.IsBound(edg)) { |
658 | AddPart = Standard_True; |
659 | } |
660 | } |
661 | else if (!toRemove.Contains(edg)) { |
662 | AddPart = Standard_True; |
663 | } |
664 | |
665 | } |
666 | else { |
667 | if (myModShapes.IsBound(edg)) { // edg raccourci |
668 | // if (TopAbs::Compose(orsav,or)==DontFuse(edg).Orientation()){ |
669 | if (orient == DontFuse(edg).Orientation()){ |
670 | AddPart = Standard_True; |
671 | } |
672 | } |
673 | else { |
674 | // if (TopAbs::Compose(orsav,or) == |
675 | if (orient == |
676 | TopAbs::Reverse(DontFuse(edg).Orientation())) { |
677 | AddPart = Standard_True; |
678 | } |
679 | } |
680 | } |
681 | } |
682 | if (AddPart) { |
683 | itl2.Initialize(theEEMap(edg)); |
684 | gp_Vec dir1,dir2; |
685 | for (; itl2.More(); itl2.Next()) { |
686 | if (EdgAdded.Contains(itl2.Value())) { |
687 | continue; |
688 | } |
689 | const TopoDS_Edge& edgbis = TopoDS::Edge(itl2.Value()); |
690 | TopoDS_Iterator it1(newedg),it2; |
691 | for (; it1.More(); it1.Next()) { |
692 | for (it2.Initialize(edgbis); it2.More(); it2.Next()) { |
693 | if (it1.Value().IsSame(it2.Value())) { |
694 | break; |
695 | } |
696 | } |
697 | if (it2.More()) { |
698 | break; |
699 | } |
700 | } |
701 | |
702 | if (it1.More()) { |
703 | gp_Pnt ptbid; |
704 | Standard_Real prmvt = |
705 | BRep_Tool::Parameter(TopoDS::Vertex(it1.Value()),newedg); |
706 | C->D1(prmvt,ptbid,dir1); |
707 | |
708 | |
709 | C = BRep_Tool::Curve(edgbis,loc,f,l); |
710 | if (!loc.IsIdentity()) { |
711 | Handle(Geom_Geometry) GG = C->Transformed(loc.Transformation()); |
712 | C = *((Handle(Geom_Curve)*)&GG); |
713 | } |
714 | if (C->DynamicType() == STANDARD_TYPE(Geom_TrimmedCurve)) { |
715 | C = (*((Handle(Geom_TrimmedCurve)*)&C))->BasisCurve(); |
716 | } |
717 | prmvt = |
718 | BRep_Tool::Parameter(TopoDS::Vertex(it1.Value()),edgbis); |
719 | C->D1(prmvt,ptbid,dir2); |
720 | } |
721 | else { |
722 | dir1 = dir2 = gp_Vec(1,0,0); |
723 | } |
724 | EdgAdded.Add(edgbis); |
725 | if (dir1.Dot(dir2) <0.) { |
726 | // B.Add(newwire,edgbis.Oriented(TopAbs::Reverse(or))); |
727 | listofedg.Append(edgbis.Oriented(TopAbs::Reverse(orient))); |
728 | } |
729 | else { |
730 | // B.Add(newwire,edgbis.Oriented(or)); |
731 | listofedg.Append(edgbis.Oriented(orient)); |
732 | } |
733 | |
734 | |
735 | if (P.IsNull()) { |
736 | // on met les courbes 2d si on n`est pas sur un plan |
737 | // C est la courbe de edgbis, f et l s`y rapportent |
738 | Handle(Geom2d_Curve) PTC = GeomProjLib::Curve2d(C,f,l,S,tol); |
739 | if (S->IsUPeriodic()) { |
740 | Standard_Real Uref; |
741 | if (DontFuse.IsBound(edg)) { |
742 | TopAbs_Orientation oredge = DontFuse(edg).Orientation(); |
743 | if (myModShapes.IsBound(edg)) { // edge raccourci... |
744 | TopoDS_Shape aLocalShape = edg.Oriented(oredge); |
745 | TopoDS_Shape aLocalFace = fac.Oriented(TopAbs_FORWARD); |
746 | BRep_Tool:: |
747 | UVPoints(TopoDS::Edge(aLocalShape),TopoDS::Face(aLocalFace),pf,pl); |
748 | // BRep_Tool:: |
749 | // UVPoints(TopoDS::Edge(edg.Oriented(oredge)), |
750 | // TopoDS::Face(fac.Oriented(TopAbs_FORWARD)), |
751 | // pf,pl); |
752 | } |
753 | else { |
754 | TopoDS_Shape aLocalShape = edg.Oriented(TopAbs::Reverse(oredge)); |
755 | TopoDS_Shape aLocalFace = fac.Oriented(TopAbs_FORWARD); |
756 | BRep_Tool:: |
757 | UVPoints(TopoDS::Edge(aLocalShape),TopoDS::Face(aLocalFace),pf,pl); |
758 | // BRep_Tool:: |
759 | // UVPoints(TopoDS::Edge(edg.Oriented(TopAbs::Reverse(oredge))), |
760 | // TopoDS::Face(fac.Oriented(TopAbs_FORWARD)), |
761 | // pf,pl); |
762 | } |
763 | Uref = pf.X(); |
764 | } |
765 | else { |
766 | BRep_Tool::UVPoints(edg,fac,pf,pl); |
767 | Uref = pf.X(); |
768 | } |
769 | |
770 | Standard_Real NewU = (PTC->Value(f)).X(); |
771 | |
772 | // if(abs(NewU - Uref) > Epsilon(S->UPeriod())) { |
773 | if(fabs(NewU - Uref) > Epsilon(S->UPeriod())) { |
774 | PTC -> Translate(gp_Vec2d((Uref - NewU), 0.)); |
775 | } |
776 | } |
777 | |
778 | B.UpdateEdge(edgbis,PTC,newface,tol); |
779 | } |
780 | } |
781 | } |
782 | } |
783 | } |
784 | |
785 | // Recuperation des edges sur les faces a fusionner. |
786 | |
787 | // ICICICICI |
788 | |
789 | // orface = TopAbs::Compose(orsav,orface); |
790 | |
791 | Standard_Boolean includeinw = Standard_False; |
792 | for (itl.Initialize(itf.Value()); itl.More(); itl.Next()) { |
793 | TopoDS_Face facbis = TopoDS::Face(itl.Value()); |
794 | Standard_Boolean genface = Standard_True; |
795 | for (itl2.Initialize(G->OrientedFaces()); itl2.More(); itl2.Next()) { |
796 | if (itl2.Value().IsSame(facbis)) { |
797 | break; |
798 | } |
799 | } |
800 | if (itl2.More()) { |
801 | orient = itl2.Value().Orientation(); |
802 | facbis.Orientation(orient); |
803 | } |
804 | else { // on fusionne avec une autre face du shape... |
805 | genface = Standard_False; |
806 | for (exp2.Init(myShape, TopAbs_FACE); exp2.More(); exp2.Next()) { |
807 | if (exp2.Current().IsSame(facbis)) { |
808 | facbis.Orientation(exp2.Current().Orientation()); |
809 | break; |
810 | } |
811 | } |
812 | } |
813 | |
814 | for (exp3.Init(facbis,TopAbs_WIRE); exp3.More(); exp3.Next()) { |
815 | for (exp2.Init(exp3.Current(),TopAbs_EDGE); |
816 | exp2.More(); exp2.Next()) { |
817 | if (toRemove.Contains(exp2.Current())) { |
818 | break; |
819 | } |
820 | } |
821 | if (genface) { |
822 | includeinw = Standard_True; |
823 | } |
824 | else { |
825 | Standard_Boolean includeinw = Standard_False; |
826 | if (exp2.More()) { |
827 | for (exp2.ReInit(); exp2.More(); exp2.Next()) { |
828 | if (!toRemove.Contains(exp2.Current())) { |
829 | continue; |
830 | } |
831 | TopoDS_Vertex VF,VL; |
832 | TopExp::Vertices(TopoDS::Edge(exp2.Current()),VF,VL); |
833 | TopExp_Explorer exp4; |
834 | for (exp4.Init(wir,TopAbs_VERTEX); |
835 | // for (TopExp_Explorer exp4(wir,TopAbs_VERTEX); |
836 | exp4.More(); exp4.Next()) { |
837 | if (exp4.Current().IsSame(VF) || |
838 | exp4.Current().IsSame(VL)) { |
839 | includeinw = Standard_True; |
840 | break; |
841 | } |
842 | } |
843 | if (includeinw) { |
844 | break; |
845 | } |
846 | } |
847 | } |
848 | } |
849 | |
850 | if (!includeinw) { |
851 | continue; |
852 | } |
853 | |
854 | for (exp2.ReInit(); exp2.More(); exp2.Next()) { |
855 | const TopoDS_Edge& edg = TopoDS::Edge(exp2.Current()); |
856 | if (!toRemove.Contains(edg) && !EdgAdded.Contains(edg)) { |
857 | |
858 | orient = TopAbs::Compose(orface,edg.Orientation()); |
859 | // B.Add(newwire,edg.Oriented(or)); |
860 | listofedg.Append(edg.Oriented(orient)); |
861 | EmptyWire = Standard_False; |
862 | EdgAdded.Add(edg); |
863 | if (P.IsNull()) { |
864 | // on met les courbes 2d si on n`est pas sur un plan |
865 | // on ne devrait pas avoir de pb d`edge de couture. |
866 | tol = BRep_Tool::Tolerance(edg); |
867 | C = BRep_Tool::Curve(edg,loc,f,l); |
868 | if (!loc.IsIdentity()) { |
869 | Handle(Geom_Geometry) GG = C->Transformed(loc.Transformation()); |
870 | C = *((Handle(Geom_Curve)*)&GG); |
871 | } |
872 | if (C->DynamicType() == STANDARD_TYPE(Geom_TrimmedCurve)) { |
873 | C = (*((Handle(Geom_TrimmedCurve)*)&C))->BasisCurve(); |
874 | } |
875 | |
876 | C2d = GeomProjLib::Curve2d(C,f,l,S,tol); |
877 | |
878 | // Tentative de recalage dans la facette |
879 | pf = C2d->Value(f); |
880 | pl = C2d->Value(l); |
881 | Standard_Real tttol = Precision::Angular(); |
882 | while (Min(pf.X(),pl.X()) >= Umaxc - tttol) { |
883 | C2d->Translate(gp_Vec2d(-2.*PI,0)); |
884 | pf = C2d->Value(f); |
885 | pl = C2d->Value(l); |
886 | } |
887 | |
888 | while (Max(pf.X(),pl.X()) <= Uminc + tttol) { |
889 | C2d->Translate(gp_Vec2d(2.*PI,0)); |
890 | pf = C2d->Value(f); |
891 | pl = C2d->Value(l); |
892 | } |
893 | |
894 | if (!BRepTools::IsReallyClosed(edg,facbis)) { |
895 | B.UpdateEdge(edg,C2d,newface,tol); |
896 | } |
897 | // else { |
898 | // cout << "Edge double bizarre... " << endl; |
899 | // } |
900 | } |
901 | } |
902 | } |
903 | } |
904 | } |
905 | } |
906 | } |
907 | if (!listofedg.IsEmpty()) { |
908 | BRepAlgo_Loop L; |
909 | L.Init(newface); |
910 | L.AddConstEdges(listofedg); |
911 | L.Perform(); |
912 | L.WiresToFaces(); |
913 | #ifdef DEB |
914 | const TopTools_ListOfShape& listofwires = |
915 | #endif |
916 | L.NewWires(); |
917 | const TopTools_ListOfShape& listoffaces = L.NewFaces(); |
918 | toRemove.Add(fac); |
919 | // if (!HasWire) { |
920 | // newface.Nullify(); |
921 | // } |
922 | myModShapes.Bind(fac,listoffaces); |
923 | for (itl.Initialize(itf.Value()); itl.More(); itl.Next()) { |
924 | myModShapes.Bind(itl.Value(),listoffaces); |
925 | } |
926 | } |
927 | } |
928 | |
929 | /* JAG 16.09.96 : on utilise LocOpe_BuildShape |
930 | TopoDS_Shell theShell; |
931 | B.MakeShell(theShell); |
932 | for (exp.Init(myShape,TopAbs_FACE); exp.More(); exp.Next()) { |
933 | const TopoDS_Face& fac = TopoDS::Face(exp.Current()); |
934 | if (!theLeft.Contains(fac)) { |
935 | if (!toRemove.Contains(exp.Current())) { |
936 | B.Add(theShell,fac); |
937 | myModShapes.Bind(fac,fac); |
938 | } |
939 | else if (!myModShapes(fac).IsNull()) { |
940 | B.Add(theShell, myModShapes(fac).Oriented(fac.Orientation())); |
941 | } |
942 | } |
943 | } |
944 | |
945 | |
946 | TopAbs_Orientation orsolid = myShape.Orientation(); |
947 | for (itl.Initialize(G->OrientedFaces()); itl.More(); itl.Next()) { |
948 | const TopoDS_Face& fac = TopoDS::Face(itl.Value()); |
949 | if (toRemove.Contains(fac)) { |
950 | continue; |
951 | } |
952 | |
953 | if (orsolid == TopAbs_FORWARD) { |
954 | B.Add(theShell,fac); |
955 | } |
956 | else { |
957 | B.Add(theShell,fac.Reversed()); |
958 | } |
959 | myModShapes.Bind(fac,fac); |
960 | |
961 | } |
962 | |
963 | B.MakeSolid(TopoDS::Solid(myRes)); |
964 | B.Add(myRes,theShell); |
965 | myRes.Orientation(orsolid); |
966 | |
967 | */ |
968 | |
969 | // 06.11.96 |
970 | // Debug temporaire. Il faudra prevoir un syntaxe de BuildShape |
971 | // qui impose une ori de certaines faces. |
972 | |
973 | TopoDS_Face FaceRefOri; |
974 | |
975 | TopTools_ListOfShape lfres; |
976 | for (exp.Init(myShape,TopAbs_FACE); exp.More(); exp.Next()) { |
977 | const TopoDS_Face& fac = TopoDS::Face(exp.Current()); |
978 | if (!theLeft.Contains(fac)) { |
979 | if (!toRemove.Contains(exp.Current())) { |
980 | lfres.Append(fac); |
981 | if(!myModShapes.IsBound(fac)) { |
982 | TopTools_ListOfShape emptylist; |
983 | myModShapes.Bind(fac, emptylist); |
984 | } |
985 | myModShapes(fac).Append(fac); |
986 | if (FaceRefOri.IsNull()) { |
987 | FaceRefOri = fac; |
988 | } |
989 | } |
990 | else if (myModShapes.IsBound(fac)) { |
991 | lfres.Append(myModShapes(fac).First().Oriented(fac.Orientation())); |
992 | } |
993 | } |
994 | } |
995 | |
996 | |
997 | TopAbs_Orientation orsolid = myShape.Orientation(); |
998 | for (itl.Initialize(G->OrientedFaces()); itl.More(); itl.Next()) { |
999 | const TopoDS_Face& fac = TopoDS::Face(itl.Value()); |
1000 | if (toRemove.Contains(fac)) { |
1001 | continue; |
1002 | } |
1003 | |
1004 | if (orsolid == TopAbs_FORWARD) { |
1005 | lfres.Append(fac); |
1006 | } |
1007 | else { |
1008 | lfres.Append(fac.Reversed()); |
1009 | } |
1010 | if(!myModShapes.IsBound(fac)) { |
1011 | TopTools_ListOfShape emptylist; |
1012 | myModShapes.Bind(fac, emptylist); |
1013 | } |
1014 | myModShapes(fac).Append(fac); |
1015 | } |
1016 | |
1017 | LocOpe_BuildShape BS(lfres); |
1018 | myRes = BS.Shape(); |
1019 | // Suite debug du 06.11.96 |
1020 | if (myRes.ShapeType() == TopAbs_SOLID) { |
1021 | for (exp.Init(myRes,TopAbs_FACE); exp.More(); exp.Next()) { |
1022 | if (exp.Current().IsSame(FaceRefOri)) { |
1023 | break; |
1024 | } |
1025 | } |
1026 | if (exp.More() && |
1027 | exp.Current().Orientation() != FaceRefOri.Orientation()) { |
1028 | // ---C++: return const& ---C++: return const& ---C++: return const&Si un seul Shell , on change son orientation |
1029 | TopoDS_Solid NewSol; |
1030 | B.MakeSolid(NewSol); |
1031 | exp.Init(myRes,TopAbs_SHELL); |
1032 | B.Add(NewSol,exp.Current().Reversed()); |
1033 | myRes.Nullify(); |
1034 | myRes = NewSol; |
1035 | } |
1036 | } |
1037 | |
1038 | |
1039 | // recodage des regularites qui existaient sur le shape colle |
1040 | |
1041 | |
1042 | |
1043 | myDone = Standard_True; |
1044 | } |
1045 | |
1046 | //======================================================================= |
1047 | //function : DescendantFace |
1048 | //purpose : |
1049 | //======================================================================= |
1050 | |
1051 | const TopTools_ListOfShape& LocOpe_Generator::DescendantFace(const TopoDS_Face& F) |
1052 | { |
1053 | // TopTools_ListOfShape list; |
1054 | |
1055 | if (!myDone) {StdFail_NotDone::Raise();} |
1056 | return myModShapes(F); |
1057 | } |
1058 | |
1059 | //======================================================================= |
1060 | //function : ToFuse |
1061 | //purpose : |
1062 | //======================================================================= |
1063 | |
1064 | Standard_Boolean ToFuse(const TopoDS_Face& F1, |
1065 | const TopoDS_Face& F2) |
1066 | { |
1067 | if (F1.IsNull() || F2.IsNull()) { |
1068 | return Standard_False; |
1069 | } |
1070 | |
1071 | Handle(Geom_Surface) S1,S2; |
1072 | TopLoc_Location loc1, loc2; |
1073 | Handle(Standard_Type) typS1,typS2; |
1074 | const Standard_Real tollin = Precision::Confusion(); |
1075 | const Standard_Real tolang = Precision::Angular(); |
1076 | |
1077 | S1 = BRep_Tool::Surface(F1,loc1); |
1078 | S2 = BRep_Tool::Surface(F2,loc2); |
1079 | |
1080 | typS1 = S1->DynamicType(); |
1081 | typS2 = S2->DynamicType(); |
1082 | |
1083 | if (typS1 == STANDARD_TYPE(Geom_RectangularTrimmedSurface)) { |
1084 | S1 = (*((Handle(Geom_RectangularTrimmedSurface)*)&S1))->BasisSurface(); |
1085 | typS1 = S1->DynamicType(); |
1086 | } |
1087 | |
1088 | if (typS2 == STANDARD_TYPE(Geom_RectangularTrimmedSurface)) { |
1089 | S2 = (*((Handle(Geom_RectangularTrimmedSurface)*)&S2))->BasisSurface(); |
1090 | typS2 = S2->DynamicType(); |
1091 | } |
1092 | |
1093 | if (typS1 != typS2) { |
1094 | return Standard_False; |
1095 | } |
1096 | |
1097 | |
1098 | Standard_Boolean ValRet = Standard_False; |
1099 | if (typS1 == STANDARD_TYPE(Geom_Plane)) { |
1100 | |
1101 | gp_Pln pl1( (*((Handle(Geom_Plane)*)&S1))->Pln()); |
1102 | gp_Pln pl2( (*((Handle(Geom_Plane)*)&S2))->Pln()); |
1103 | |
1104 | pl1.Transform(loc1.Transformation()); |
1105 | pl2.Transform(loc2.Transformation()); |
1106 | |
1107 | if (pl1.Position().IsCoplanar(pl2.Position(),tollin,tolang)) { |
1108 | ValRet = Standard_True; |
1109 | } |
1110 | } |
1111 | |
1112 | return ValRet; |
1113 | } |
1114 | |
1115 | |
1116 | //======================================================================= |
1117 | //function : ToFuse |
1118 | //purpose : |
1119 | //======================================================================= |
1120 | |
1121 | Standard_Boolean ToFuse(const TopoDS_Edge& E1, |
1122 | const TopoDS_Edge& E2) |
1123 | { |
1124 | |
1125 | if (E1.IsNull() || E2.IsNull()) { |
1126 | return Standard_False; |
1127 | } |
1128 | |
1129 | Handle(Geom_Curve) C1,C2; |
1130 | TopLoc_Location loc1, loc2; |
1131 | Handle(Standard_Type) typC1,typC2; |
1132 | const Standard_Real tollin = Precision::Confusion(); |
1133 | const Standard_Real tolang = Precision::Angular(); |
1134 | Standard_Real f,l; |
1135 | |
1136 | C1 = BRep_Tool::Curve(E1,loc1,f,l); |
1137 | if (!loc1.IsIdentity()) { |
1138 | Handle(Geom_Geometry) CC1 = C1->Transformed(loc1.Transformation()); |
1139 | C1 = *((Handle(Geom_Curve)*)&CC1); |
1140 | } |
1141 | |
1142 | C2 = BRep_Tool::Curve(E2,loc2,f,l); |
1143 | if (!loc2.IsIdentity()) { |
1144 | Handle(Geom_Geometry) CC2 = C2->Transformed(loc2.Transformation()); |
1145 | C2 = *((Handle(Geom_Curve)*)&CC2); |
1146 | } |
1147 | |
1148 | typC1 = C1->DynamicType(); |
1149 | typC2 = C2->DynamicType(); |
1150 | |
1151 | if (typC1 == STANDARD_TYPE(Geom_TrimmedCurve)) { |
1152 | C1 = (*((Handle(Geom_TrimmedCurve)*)&C1))->BasisCurve(); |
1153 | typC1 = C1->DynamicType(); |
1154 | } |
1155 | if (typC2 == STANDARD_TYPE(Geom_TrimmedCurve)) { |
1156 | C2 = (*((Handle(Geom_TrimmedCurve)*)&C2))->BasisCurve(); |
1157 | typC2 = C2->DynamicType(); |
1158 | } |
1159 | |
1160 | if (typC1 != typC2) { |
1161 | return Standard_False; |
1162 | } |
1163 | |
1164 | Standard_Boolean ValRet = Standard_False; |
1165 | if (typC1 == STANDARD_TYPE(Geom_Line)) { |
1166 | gp_Lin li1( (*((Handle(Geom_Line)*)&C1))->Lin()); |
1167 | gp_Lin li2( (*((Handle(Geom_Line)*)&C2))->Lin()); |
1168 | |
1169 | if (li1.Position().IsCoaxial(li2.Position(),tolang,tollin)) { |
1170 | ValRet = Standard_True; |
1171 | } |
1172 | } |
1173 | |
1174 | return ValRet; |
1175 | } |
1176 | |
1177 | |
1178 | //======================================================================= |
1179 | //function : ToFuse |
1180 | //purpose : |
1181 | //======================================================================= |
1182 | |
1183 | Standard_Boolean ToFuse(const TopoDS_Edge& E, |
1184 | const TopoDS_Face& F, |
1185 | const TopoDS_Vertex& V, |
1186 | const TopTools_MapOfShape& toRemove) |
1187 | { |
1188 | TopoDS_Vertex Vf,Vl; |
1189 | TopExp_Explorer exp; |
1190 | for (exp.Init(F,TopAbs_EDGE); exp.More(); exp.Next()) { |
1191 | // for (TopExp_Explorer exp(F,TopAbs_EDGE); exp.More(); exp.Next()) { |
1192 | const TopoDS_Edge& eee = TopoDS::Edge(exp.Current()); |
1193 | if (!eee.IsSame(E)) { |
1194 | TopExp::Vertices(eee,Vf,Vl); |
1195 | if ((Vf.IsSame(V) || Vl.IsSame(V)) && |
1196 | !toRemove.Contains(eee)) { |
1197 | return Standard_False; |
1198 | } |
1199 | } |
1200 | } |
1201 | return Standard_True; |
1202 | } |
1203 | |
1204 | |
1205 | //======================================================================= |
1206 | //function : NewParameter |
1207 | //purpose : |
1208 | //======================================================================= |
1209 | |
1210 | Standard_Real NewParameter(const TopoDS_Edge& Edg, |
1211 | const TopoDS_Vertex& Vtx, |
1212 | const TopoDS_Edge& NewEdg, |
1213 | const TopoDS_Vertex& NewVtx) |
1214 | { |
1215 | |
1216 | Handle(Geom_Curve) C; |
1217 | TopLoc_Location loc; |
1218 | Handle(Standard_Type) typC; |
1219 | Standard_Real f,l; |
1220 | |
1221 | gp_Pnt P = BRep_Tool::Pnt(NewVtx); |
1222 | |
1223 | C = BRep_Tool::Curve(Edg,loc,f,l); |
1224 | if (!loc.IsIdentity()) { |
1225 | Handle(Geom_Geometry) GG = C->Transformed(loc.Transformation()); |
1226 | C = *((Handle(Geom_Curve)*)&GG); |
1227 | } |
1228 | typC = C->DynamicType(); |
1229 | if (typC == STANDARD_TYPE(Geom_TrimmedCurve)) { |
1230 | C = (*((Handle(Geom_TrimmedCurve)*)&C))->BasisCurve(); |
1231 | typC = C->DynamicType(); |
1232 | } |
1233 | |
1234 | if (typC == STANDARD_TYPE(Geom_Line)) { |
1235 | return ElCLib::Parameter( (*((Handle(Geom_Line)*)&C))->Lin(),P); |
1236 | } |
1237 | else if (typC == STANDARD_TYPE(Geom_Circle)) { |
1238 | Standard_Real prm = ElCLib::Parameter |
1239 | ( (*((Handle(Geom_Circle)*)&C))->Circ(),P); |
1240 | // Vtx vient d`une exploration de Edg orientee FORWARD |
1241 | |
1242 | TopAbs_Orientation orient = TopAbs::Reverse(Vtx.Orientation()); |
1243 | if (orient == TopAbs_FORWARD || orient == TopAbs_REVERSED) { |
1244 | // for (TopExp_Explorer exp(NewEdg.Oriented(TopAbs_FORWARD),TopAbs_VERTEX); |
1245 | TopExp_Explorer exp(NewEdg.Oriented(TopAbs_FORWARD),TopAbs_VERTEX) ; |
1246 | for ( ; exp.More(); exp.Next()) { |
1247 | if (exp.Current().Orientation() == orient) { |
1248 | break; |
1249 | } |
1250 | } |
1251 | if (exp.More()) { |
1252 | Standard_Real prmmax = BRep_Tool::Parameter |
1253 | (TopoDS::Vertex(exp.Current()),NewEdg); |
1254 | if (Abs(prmmax - prm) <= Epsilon(2.*PI)) { |
1255 | if (orient == TopAbs_REVERSED) { |
1256 | prm -= 2.*PI; |
1257 | } |
1258 | else { |
1259 | prm += 2.*PI; |
1260 | } |
1261 | } |
1262 | } |
1263 | } |
1264 | return prm; |
1265 | } |
1266 | return 0; |
1267 | } |
1268 | |
1269 | |
1270 | //======================================================================= |
1271 | //function : Contains |
1272 | //purpose : |
1273 | //======================================================================= |
1274 | |
1275 | // Unused : |
1276 | #ifdef DEB |
1277 | Standard_Boolean Contains(const TopTools_ListOfShape& L, |
1278 | const TopoDS_Shape& S) |
1279 | { |
1280 | TopTools_ListIteratorOfListOfShape itl; |
1281 | for (itl.Initialize(L); itl.More(); itl.Next()) { |
1282 | // for (TopTools_ListIteratorOfListOfShape itl(L); itl.More(); itl.Next()) { |
1283 | if (itl.Value().IsSame(S)) { |
1284 | return Standard_True; |
1285 | } |
1286 | } |
1287 | return Standard_False; |
1288 | } |
1289 | #endif |
1290 | |