0028191: Inefficient implementation of the BRepOffset_Tool::HasCommonShapes() method
[occt.git] / src / BRepOffset / BRepOffset_Inter3d.cxx
CommitLineData
b311480e 1// Created on: 1996-09-03
2// Created by: Yves FRICAUD
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// Modified by skv - Fri Dec 26 12:20:14 2003 OCC4455
18
7fd59977 19#include <BRep_Builder.hxx>
20#include <BRep_Tool.hxx>
42cf5bc1 21#include <BRepAdaptor_Curve.hxx>
22#include <BRepAlgo_AsDes.hxx>
23#include <BRepAlgo_Image.hxx>
7fd59977 24#include <BRepLib_MakeVertex.hxx>
42cf5bc1 25#include <BRepOffset_Analyse.hxx>
26#include <BRepOffset_DataMapOfShapeOffset.hxx>
27#include <BRepOffset_Inter3d.hxx>
28#include <BRepOffset_Interval.hxx>
29#include <BRepOffset_ListOfInterval.hxx>
30#include <BRepOffset_Offset.hxx>
31#include <BRepOffset_Tool.hxx>
32#include <Extrema_ExtPC.hxx>
9b7f3f83 33#include <GeomAPI_ProjectPointOnCurve.hxx>
42cf5bc1 34#include <Precision.hxx>
7fd59977 35#include <TopExp.hxx>
36#include <TopExp_Explorer.hxx>
37#include <TopoDS.hxx>
38#include <TopoDS_Compound.hxx>
39#include <TopoDS_Edge.hxx>
42cf5bc1 40#include <TopoDS_Face.hxx>
41#include <TopoDS_Shape.hxx>
7fd59977 42#include <TopoDS_Vertex.hxx>
43#include <TopOpeBRepTool_BoxSort.hxx>
42cf5bc1 44#include <TopTools_IndexedMapOfShape.hxx>
7fd59977 45#include <TopTools_ListIteratorOfListOfShape.hxx>
46#include <TopTools_MapIteratorOfMapOfShape.hxx>
975ec82a 47#include <TopTools_MapOfShape.hxx>
ecf4f17c 48//
49#include <BOPTools_AlgoTools.hxx>
7fd59977 50
51//=======================================================================
52//function : BRepOffset_Inter3d
53//purpose :
54//=======================================================================
7fd59977 55BRepOffset_Inter3d::BRepOffset_Inter3d(const Handle(BRepAlgo_AsDes)& AsDes,
9b7f3f83 56 const TopAbs_State Side ,
57 const Standard_Real Tol)
7fd59977 58:myAsDes(AsDes),
59mySide(Side),
60myTol(Tol)
61{
62}
63
64
65//=======================================================================
66//function : ExtentEdge
67//purpose :
68//=======================================================================
69
35e08fe8 70static void ExtentEdge(const TopoDS_Face& /*F*/,
9b7f3f83 71 const TopoDS_Edge& E,
72 TopoDS_Edge& NE)
7fd59977 73{
74 TopoDS_Shape aLocalShape = E.EmptyCopied();
75 NE = TopoDS::Edge(aLocalShape);
76// NE = TopoDS::Edge(E.EmptyCopied());
77
78
0d969553
Y
79 // Enough for analytic edges, in general case reconstruct the
80 // geometry of the edge recalculating the intersection of surfaces.
7fd59977 81
82 NE.Orientation(TopAbs_FORWARD);
83 Standard_Real f,l;
84 BRep_Tool::Range(E,f,l);
85 Standard_Real length = l-f;
86 f -= 100*length;
87 l += 100*length;
88
89 BRep_Builder B;
90 B.Range(NE,f,l);
91 BRepAdaptor_Curve CE(E);
92 TopoDS_Vertex V1 = BRepLib_MakeVertex(CE.Value(f));
93 TopoDS_Vertex V2 = BRepLib_MakeVertex(CE.Value(l));
94 B.Add(NE,V1.Oriented(TopAbs_FORWARD));
95 B.Add(NE,V2.Oriented(TopAbs_REVERSED));
96 NE.Orientation(E.Orientation());
97
98}
99
100//=======================================================================
101//function : SelectEdge
102//purpose :
103//=======================================================================
9b7f3f83 104static void SelectEdge (const TopoDS_Shape& theS,
105 TopTools_ListOfShape& theLE)
7fd59977 106{
9b7f3f83 107 Standard_Real aT1, aT2, aDist, aDistMin;
108 TopExp_Explorer aExp;
109 TopTools_ListIteratorOfListOfShape aIt;
110 GeomAPI_ProjectPointOnCurve aProjPC;
111 gp_Pnt aPE1, aPE2;
112 TopoDS_Edge aRE;
113 //
114 aDistMin = RealLast();
115 //
116 aIt.Initialize(theLE);
117 for (; aIt.More(); aIt.Next()) {
118 const TopoDS_Edge& aE = *(TopoDS_Edge*)&aIt.Value();
119 //
120 const Handle(Geom_Curve)& aC = BRep_Tool::Curve(aE, aT1, aT2);
121 //
122 aProjPC.Init(aC, aT1, aT2);
123 aPE1 = aC->Value(aT1);
124 aPE2 = aC->Value(aT2);
125 //
126 aDist = 0.;
127 aExp.Init(theS, TopAbs_VERTEX);
128 for (; aExp.More(); aExp.Next()) {
129 const TopoDS_Vertex& aV = *(TopoDS_Vertex*)&aExp.Current();
130 const gp_Pnt aP = BRep_Tool::Pnt(aV);
131 //
132 aProjPC.Perform(aP);
133 if (aProjPC.NbPoints()) {
134 aDist += aProjPC.LowerDistance();
7fd59977 135 }
9b7f3f83 136 else {
137 aDist += Min(aP.Distance(aPE1), aP.Distance(aPE2));
7fd59977 138 }
139 }
9b7f3f83 140 //
141 if (aDist < aDistMin) {
142 aDistMin = aDist;
143 aRE = aE;
7fd59977 144 }
7fd59977 145 }
9b7f3f83 146 //
147 theLE.Clear();
148 theLE.Append(aRE);
7fd59977 149}
150
7fd59977 151//=======================================================================
152//function : CompletInt
153//purpose :
154//=======================================================================
155
156void BRepOffset_Inter3d::CompletInt(const TopTools_ListOfShape& SetOfFaces,
9b7f3f83 157 const BRepAlgo_Image& InitOffsetFace)
7fd59977 158{
159 //---------------------------------------------------------------
0d969553
Y
160 // Calculate the intersections of offset faces
161 // Distinction of intersection between faces // tangents.
7fd59977 162 //---------------------------------------------------------------
51740958 163 TopoDS_Face F2;
7fd59977 164 TopTools_ListIteratorOfListOfShape it;
165
166 //---------------------------------------------------------------
0d969553 167 // Construction of bounding boxes
7fd59977 168 //---------------------------------------------------------------
169 TopOpeBRepTool_BoxSort BOS;
170 BRep_Builder B;
171 TopoDS_Compound CompOS;
172 B.MakeCompound(CompOS);
173
174 for (it.Initialize(SetOfFaces); it.More(); it.Next()) {
175 const TopoDS_Shape& OS = it.Value();
176 B.Add(CompOS,OS);
177 }
178 BOS.AddBoxesMakeCOB(CompOS,TopAbs_FACE);
179
180 //---------------------------
0d969553 181 // Intersection of faces //
7fd59977 182 //---------------------------
183 for (it.Initialize(SetOfFaces); it.More(); it.Next()) {
184 const TopoDS_Face& F1 = TopoDS::Face(it.Value());
185 TColStd_ListIteratorOfListOfInteger itLI = BOS.Compare(F1);
186 for (; itLI.More(); itLI.Next()) {
187 F2 = TopoDS::Face(BOS.TouchedShape(itLI));
188 FaceInter(F1,F2,InitOffsetFace);
189 }
190 }
191}
192
193
194//=======================================================================
195//function : CompletInt
196//purpose :
197//=======================================================================
198
199void BRepOffset_Inter3d::FaceInter(const TopoDS_Face& F1,
9b7f3f83 200 const TopoDS_Face& F2,
201 const BRepAlgo_Image& InitOffsetFace)
7fd59977 202{
203 TopTools_ListOfShape LInt1, LInt2;
204 TopoDS_Edge NullEdge;
205
206 if (F1.IsSame(F2)) return;
207 if (IsDone(F1,F2)) return;
208 const TopoDS_Shape& InitF1 = InitOffsetFace.ImageFrom(F1);
209 const TopoDS_Shape& InitF2 = InitOffsetFace.ImageFrom(F2);
210 Standard_Boolean InterPipes = (InitF2.ShapeType() == TopAbs_EDGE &&
9b7f3f83 211 InitF1.ShapeType() == TopAbs_EDGE );
7fd59977 212 Standard_Boolean InterFaces = (InitF1.ShapeType() == TopAbs_FACE &&
9b7f3f83 213 InitF2.ShapeType() == TopAbs_FACE);
7fd59977 214 TopTools_ListOfShape LE,LV;
215 LInt1.Clear(); LInt2.Clear();
fe1d4d6c 216 if (BRepOffset_Tool::FindCommonShapes(F1,F2,LE,LV) ||
7fd59977 217 myAsDes->HasCommonDescendant(F1,F2,LE)) {
218 //-------------------------------------------------
0d969553 219 // F1 and F2 share shapes.
7fd59977 220 //-------------------------------------------------
221 if ( LE.IsEmpty() && !LV.IsEmpty()) {
222 if (InterPipes) {
9b7f3f83 223 //----------------------
224 // tubes share a vertex.
225 //----------------------
226 const TopoDS_Edge& EE1 = TopoDS::Edge(InitF1);
227 const TopoDS_Edge& EE2 = TopoDS::Edge(InitF2);
228 TopoDS_Vertex VE1[2],VE2[2];
229 TopExp::Vertices(EE1,VE1[0],VE1[1]);
230 TopExp::Vertices(EE2,VE2[0],VE2[1]);
231 TopoDS_Vertex V;
232 for (Standard_Integer i = 0 ; i < 2; i++) {
233 for (Standard_Integer j = 0 ; j < 2; j++) {
234 if (VE1[i].IsSame(VE2[j])) {
235 V = VE1[i];
236 }
237 }
238 }
239 if (!InitOffsetFace.HasImage(V)) { //no sphere
240 BRepOffset_Tool::PipeInter(F1,F2,LInt1,LInt2,mySide);
241 }
7fd59977 242 }
243 else {
9b7f3f83 244 //--------------------------------------------------------
245 // Intersection having only common vertices
246 // and supports having common edges.
247 // UNSUFFICIENT, but a larger criterion shakes too
248 // many sections.
249 //--------------------------------------------------------
250 if (InterFaces) {
fe1d4d6c 251 if (BRepOffset_Tool::FindCommonShapes(TopoDS::Face(InitF1),
252 TopoDS::Face(InitF2),LE,LV)) {
9b7f3f83 253 if (!LE.IsEmpty()) {
254 BRepOffset_Tool::Inter3D (F1,F2,LInt1,LInt2,mySide,NullEdge);
255 }
256 }
257 else {
258 BRepOffset_Tool::Inter3D(F1,F2,LInt1,LInt2,mySide,NullEdge);
259 }
260 }
7fd59977 261 }
262 }
263 }
264 else {
265 if (InterPipes) {
266 BRepOffset_Tool::PipeInter(F1,F2,LInt1,LInt2,mySide);
267 }
268 else {
269 BRepOffset_Tool::Inter3D (F1,F2,LInt1,LInt2,mySide,NullEdge);
270 }
271 }
272 Store (F1,F2,LInt1,LInt2);
273}
274
275
276//=======================================================================
277//function : ConnexIntByArc
278//purpose :
279//=======================================================================
280
35e08fe8 281void BRepOffset_Inter3d::ConnexIntByArc(const TopTools_ListOfShape& /*SetOfFaces*/,
282 const TopoDS_Shape& ShapeInit,
283 const BRepOffset_Analyse& Analyse,
284 const BRepAlgo_Image& InitOffsetFace)
7fd59977 285{
286 BRepOffset_Type OT = BRepOffset_Concave;
287 if (mySide == TopAbs_OUT) OT = BRepOffset_Convex;
288 TopExp_Explorer Exp(ShapeInit,TopAbs_EDGE);
289 TopTools_ListOfShape LInt1,LInt2;
290 TopoDS_Face F1,F2;
291 TopoDS_Edge NullEdge;
292
293 //---------------------------------------------------------------------
0d969553
Y
294 // etape 1 : Intersection of faces // corresponding to the initial faces
295 // separated by a concave edge if offset > 0, otherwise convex.
7fd59977 296 //---------------------------------------------------------------------
297 for (; Exp.More(); Exp.Next()) {
298 const TopoDS_Edge& E = TopoDS::Edge(Exp.Current());
299 const BRepOffset_ListOfInterval& L = Analyse.Type(E);
300 if (!L.IsEmpty() && L.First().Type() == OT) {
301 //-----------------------------------------------------------
0d969553 302 // edge is of the proper type , return adjacent faces.
7fd59977 303 //-----------------------------------------------------------
304 const TopTools_ListOfShape& Anc = Analyse.Ancestors(E);
305 if (Anc.Extent() == 2) {
9b7f3f83 306 F1 = TopoDS::Face(InitOffsetFace.Image(Anc.First()).First());
307 F2 = TopoDS::Face(InitOffsetFace.Image(Anc.Last ()).First());
308 if (!IsDone(F1,F2)) {
309 BRepOffset_Tool::Inter3D (F1,F2,LInt1,LInt2,mySide,E,Standard_True);
310 Store (F1,F2,LInt1,LInt2);
311 }
312 }
7fd59977 313 }
314 }
315 //---------------------------------------------------------------------
0d969553
Y
316 // etape 2 : Intersections of tubes sharing a vertex without sphere with:
317 // - tubes on each other edge sharing the vertex
318 // - faces containing an edge connected to vertex that has no tubes.
7fd59977 319 //---------------------------------------------------------------------
320 TopoDS_Vertex V[2];
321 TopTools_ListIteratorOfListOfShape it;
322
323 for (Exp.Init(ShapeInit,TopAbs_EDGE); Exp.More(); Exp.Next()) {
324 const TopoDS_Edge& E1 = TopoDS::Edge(Exp.Current());
325 if (InitOffsetFace.HasImage(E1)) {
326 //---------------------------
0d969553 327 // E1 generated a tube.
7fd59977 328 //---------------------------
329 F1 = TopoDS::Face(InitOffsetFace.Image(E1).First());;
330 TopExp::Vertices(E1,V[0],V[1]);
331 const TopTools_ListOfShape& AncE1 = Analyse.Ancestors(E1);
332
333 for (Standard_Integer i = 0; i < 2; i++) {
9b7f3f83 334 if (!InitOffsetFace.HasImage(V[i])) {
335 //-----------------------------
336 // the vertex has no sphere.
337 //-----------------------------
338 const TopTools_ListOfShape& Anc = Analyse.Ancestors(V[i]);
339 TopTools_ListOfShape TangOnV;
340 Analyse.TangentEdges(E1,V[i],TangOnV);
341 TopTools_MapOfShape MTEV;
342 for (it.Initialize(TangOnV); it.More(); it.Next()) {
343 MTEV.Add(it.Value());
344 }
345 for (it.Initialize(Anc); it.More(); it.Next()) {
346 const TopoDS_Edge& E2 = TopoDS::Edge(it.Value());
7fd59977 347// Modified by skv - Fri Jan 16 16:27:54 2004 OCC4455 Begin
9b7f3f83 348// if (E1.IsSame(E2) || MTEV.Contains(E2)) continue;
349 Standard_Boolean isToSkip = Standard_False;
7fd59977 350
9b7f3f83 351 if (!E1.IsSame(E2)) {
352 const BRepOffset_ListOfInterval& aL = Analyse.Type(E2);
7fd59977 353
9b7f3f83 354 isToSkip = (MTEV.Contains(E2) &&
355 (aL.IsEmpty() ||
356 (!aL.IsEmpty() && aL.First().Type() != OT)));
357 }
7fd59977 358
9b7f3f83 359 if (E1.IsSame(E2) || isToSkip)
360 continue;
7fd59977 361// Modified by skv - Fri Jan 16 16:27:54 2004 OCC4455 End
9b7f3f83 362 if (InitOffsetFace.HasImage(E2)) {
363 //-----------------------------
364 // E2 generated a tube.
365 //-----------------------------
366 F2 = TopoDS::Face(InitOffsetFace.Image(E2).First());
367 if (!IsDone(F1,F2)) {
368 //---------------------------------------------------------------------
369 // Intersection tube/tube if the edges are not tangent (AFINIR).
370 //----------------------------------------------------------------------
371 BRepOffset_Tool::PipeInter (F1,F2,LInt1,LInt2,mySide);
372 Store (F1,F2,LInt1,LInt2);
373 }
374 }
375 else {
376 //-------------------------------------------------------
377 // Intersection of the tube of E1 with faces //
378 // to face containing E2 if they are not tangent
379 // to the tube or if E2 is not a tangent edge.
380 //-------------------------------------------------------
381 const BRepOffset_ListOfInterval& L = Analyse.Type(E2);
382 if (!L.IsEmpty() && L.First().Type() == BRepOffset_Tangent) {
383 continue;
384 }
385 const TopTools_ListOfShape& AncE2 = Analyse.Ancestors(E2);
386 Standard_Boolean TangentFaces = Standard_False;
387 if (AncE2.Extent() == 2) {
388 TopoDS_Face InitF2 = TopoDS::Face(AncE2.First ());
389 TangentFaces = (InitF2.IsSame(AncE1.First()) ||
390 InitF2.IsSame(AncE1.Last()));
391 if (!TangentFaces) {
392 F2 = TopoDS::Face(InitOffsetFace.Image(InitF2).First());
393 if (!IsDone(F1,F2)) {
394 BRepOffset_Tool::Inter3D (F1,F2,LInt1,LInt2,mySide,NullEdge);
395 Store (F1,F2,LInt1,LInt2);
396 }
397 }
398 InitF2 = TopoDS::Face(AncE2.Last ());
399 TangentFaces = (InitF2.IsSame(AncE1.First()) ||
400 InitF2.IsSame(AncE1.Last()));
401 if (!TangentFaces) {
402 F2 = TopoDS::Face(InitOffsetFace.Image(InitF2).First());
403 if (!IsDone(F1,F2)) {
404 BRepOffset_Tool::Inter3D (F1,F2,LInt1,LInt2,mySide,NullEdge);
405 Store (F1,F2,LInt1,LInt2);
406 }
407 }
408 }
409 }
410 }
411 }
7fd59977 412 }
413 }
414 }
415}
416
417
418//=======================================================================
419//function : ConnexIntByInt
420//purpose :
421//=======================================================================
422
423void BRepOffset_Inter3d::ConnexIntByInt
424(const TopoDS_Shape& SI,
425 const BRepOffset_DataMapOfShapeOffset& MapSF,
426 const BRepOffset_Analyse& Analyse,
427 TopTools_DataMapOfShapeShape& MES,
428 TopTools_DataMapOfShapeShape& Build,
9b7f3f83 429 TopTools_ListOfShape& Failed,
430 const Standard_Boolean bIsPlanar)
7fd59977 431{
432 //TopExp_Explorer Exp(SI,TopAbs_EDGE);
9b7f3f83 433 TopTools_IndexedMapOfShape VEmap;
434 TopTools_IndexedDataMapOfShapeListOfShape aMVF;
7fd59977 435 TopoDS_Face F1,F2,OF1,OF2,NF1,NF2;
436 TopAbs_State CurSide = mySide;
437 BRep_Builder B;
9b7f3f83 438 Standard_Boolean bEdge;
439 Standard_Integer i, aNb;
440 TopTools_ListIteratorOfListOfShape it, it1, itF1, itF2;
441 //
442 TopExp::MapShapes(SI, TopAbs_EDGE , VEmap);
443 // map the shape for vertices
444 if (bIsPlanar) {
445 TopExp::MapShapes(SI, TopAbs_VERTEX, VEmap);
b443d536 446 //
447 // make vertex-faces connexity map with unique ancestors
448 // TopExp::MapShapesAndAncestors(SI, TopAbs_VERTEX, TopAbs_FACE, aMVF);
449 TopExp_Explorer aExpF(SI, TopAbs_FACE);
450 for (; aExpF.More(); aExpF.Next()) {
451 const TopoDS_Shape& aF = aExpF.Current();
452 //
453 TopExp_Explorer aExpV(aF, TopAbs_VERTEX);
454 for (; aExpV.More(); aExpV.Next()) {
455 const TopoDS_Shape& aV = aExpV.Current();
456 //
457 TopTools_ListOfShape *pLF = aMVF.ChangeSeek(aV);
458 if (!pLF) {
459 pLF = &aMVF(aMVF.Add(aV, TopTools_ListOfShape()));
460 pLF->Append(aF);
461 continue;
462 }
463 //
464 TopTools_ListIteratorOfListOfShape aItLF(*pLF);
465 for (; aItLF.More(); aItLF.Next()) {
466 if (aItLF.Value().IsSame(aF)) {
467 break;
468 }
469 }
470 if (!aItLF.More()) {
471 pLF->Append(aF);
472 }
473 }
474 }
9b7f3f83 475 }
476 //
c2bf27a6 477 TopTools_DataMapOfShapeListOfShape aDMVLF1, aDMVLF2, aDMIntFF;
478 TopTools_IndexedDataMapOfShapeListOfShape aDMIntE;
ecf4f17c 479 //
480 if (bIsPlanar) {
481 aNb = VEmap.Extent();
482 for (i = 1; i <= aNb; ++i) {
483 const TopoDS_Shape& aS = VEmap(i);
484 if (aS.ShapeType() != TopAbs_VERTEX) {
9b7f3f83 485 continue;
486 }
487 //
9b7f3f83 488 // faces connected by the vertex
489 const TopTools_ListOfShape& aLF = aMVF.FindFromKey(aS);
490 if (aLF.Extent() < 2) {
491 continue;
492 }
b443d536 493 // build lists of faces connected to the same vertex by looking for
494 // the pairs in which the vertex is alone (not connected to shared edges)
ecf4f17c 495 TopTools_ListOfShape aLF1, aLF2;
9b7f3f83 496 //
497 it.Initialize(aLF);
498 for (; it.More(); it.Next()) {
b443d536 499 const TopoDS_Shape& aFV1 = it.Value();
9b7f3f83 500 //
b443d536 501 // get edges of first face connected to current vertex
9b7f3f83 502 TopTools_MapOfShape aME;
503 TopExp_Explorer aExp(aFV1, TopAbs_EDGE);
504 for (; aExp.More(); aExp.Next()) {
c2bf27a6 505 const TopoDS_Shape& aE = aExp.Current();
506 TopoDS_Iterator aItV(aE);
507 for (; aItV.More(); aItV.Next()) {
508 if (aS.IsSame(aItV.Value())) {
509 aME.Add(aE);
510 break;
511 }
512 }
9b7f3f83 513 }
514 //
b443d536 515 // get to the next face in the list
516 it1 = it;
9b7f3f83 517 for (it1.Next(); it1.More(); it1.Next()) {
b443d536 518 const TopoDS_Shape& aFV2 = it1.Value();
9b7f3f83 519 //
9b7f3f83 520 aExp.Init(aFV2, TopAbs_EDGE);
521 for (; aExp.More(); aExp.Next()) {
522 const TopoDS_Shape& aEV2 = aExp.Current();
523 if (aME.Contains(aEV2)) {
9b7f3f83 524 break;
525 }
526 }
527 //
b443d536 528 if (!aExp.More()) {
529 // faces share only vertex - make pair for intersection
9b7f3f83 530 aLF1.Append(aFV1);
531 aLF2.Append(aFV2);
9b7f3f83 532 }
533 }
534 }
535 //
b443d536 536 if (aLF1.Extent()) {
537 aDMVLF1.Bind(aS, aLF1);
538 aDMVLF2.Bind(aS, aLF2);
9b7f3f83 539 }
ecf4f17c 540 }
541 }
542 //
543 aNb = VEmap.Extent();
544 for (i = 1; i <= aNb; ++i) {
545 const TopoDS_Shape& aS = VEmap(i);
546 //
547 TopoDS_Edge E;
548 TopTools_ListOfShape aLF1, aLF2;
549 //
550 bEdge = (aS.ShapeType() == TopAbs_EDGE);
551 if (bEdge) {
552 // faces connected by the edge
553 E = *(TopoDS_Edge*)&aS;
554 //
555 const BRepOffset_ListOfInterval& L = Analyse.Type(E);
556 if (L.IsEmpty()) {
557 continue;
558 }
559 //
560 BRepOffset_Type OT = L.First().Type();
561 if (OT != BRepOffset_Convex && OT != BRepOffset_Concave) {
562 continue;
563 }
564 //
565 if (OT == BRepOffset_Concave) CurSide = TopAbs_IN;
566 else CurSide = TopAbs_OUT;
567 //-----------------------------------------------------------
568 // edge is of the proper type, return adjacent faces.
569 //-----------------------------------------------------------
570 const TopTools_ListOfShape& Anc = Analyse.Ancestors(E);
571 if (Anc.Extent() != 2) {
572 continue;
573 }
574 //
575 F1 = TopoDS::Face(Anc.First());
576 F2 = TopoDS::Face(Anc.Last ());
577 //
578 aLF1.Append(F1);
579 aLF2.Append(F2);
580 }
581 else {
582 if (!aDMVLF1.IsBound(aS)) {
583 continue;
584 }
585 //
586 aLF1 = aDMVLF1.Find(aS);
587 aLF2 = aDMVLF2.Find(aS);
588 //
9b7f3f83 589 CurSide = mySide;
7fd59977 590 }
9b7f3f83 591 //
592 itF1.Initialize(aLF1);
593 itF2.Initialize(aLF2);
594 for (; itF1.More() && itF2.More(); itF1.Next(), itF2.Next()) {
595 F1 = TopoDS::Face(itF1.Value());
596 F2 = TopoDS::Face(itF2.Value());
597 //
598 OF1 = TopoDS::Face(MapSF(F1).Face());
599 OF2 = TopoDS::Face(MapSF(F2).Face());
600 if (!MES.IsBound(OF1)) {
601 Standard_Boolean enlargeU = Standard_True;
602 Standard_Boolean enlargeVfirst = Standard_True, enlargeVlast = Standard_True;
603 BRepOffset_Tool::CheckBounds( F1, Analyse, enlargeU, enlargeVfirst, enlargeVlast );
604 BRepOffset_Tool::EnLargeFace(OF1,NF1,Standard_True,Standard_True,enlargeU,enlargeVfirst,enlargeVlast);
605 MES.Bind(OF1,NF1);
606 }
607 else {
608 NF1 = TopoDS::Face(MES(OF1));
609 }
610 //
611 if (!MES.IsBound(OF2)) {
612 Standard_Boolean enlargeU = Standard_True;
613 Standard_Boolean enlargeVfirst = Standard_True, enlargeVlast = Standard_True;
614 BRepOffset_Tool::CheckBounds( F2, Analyse, enlargeU, enlargeVfirst, enlargeVlast );
615 BRepOffset_Tool::EnLargeFace(OF2,NF2,Standard_True,Standard_True,enlargeU,enlargeVfirst,enlargeVlast);
616 MES.Bind(OF2,NF2);
617 }
618 else {
619 NF2 = TopoDS::Face(MES(OF2));
620 }
621 //
622 if (!IsDone(NF1,NF2)) {
623 TopTools_ListOfShape LInt1,LInt2;
624 BRepOffset_Tool::Inter3D (NF1,NF2,LInt1,LInt2,CurSide,E,bEdge);
625 if (LInt1.Extent() > 1) {
626 // intersection is in seceral edges (free sewing)
627 SelectEdge(aS, LInt1);
628 SelectEdge(aS, LInt2);
629 }
630 SetDone(NF1,NF2);
631 if (!LInt1.IsEmpty()) {
632 Store (NF1,NF2,LInt1,LInt2);
633 //
634 TopoDS_Compound C;
635 B.MakeCompound(C);
636 //
637 if (Build.IsBound(aS)) {
638 const TopoDS_Shape& aSE = Build(aS);
639 TopExp_Explorer aExp(aSE, TopAbs_EDGE);
640 for (; aExp.More(); aExp.Next()) {
641 const TopoDS_Shape& aNE = aExp.Current();
642 B.Add(C, aNE);
643 }
644 }
645 //
646 it.Initialize(LInt1);
647 for (; it.More(); it.Next()) {
648 const TopoDS_Shape& aNE = it.Value();
649 B.Add(C, aNE);
c2bf27a6 650 //
651 // keep connection from new edge to shape from which it was created
652 TopTools_ListOfShape *pLS = &aDMIntE(aDMIntE.Add(aNE, TopTools_ListOfShape()));
653 pLS->Append(aS);
654 // keep connection to faces created the edge as well
655 TopTools_ListOfShape* pLFF = aDMIntFF.Bound(aNE, TopTools_ListOfShape());
656 pLFF->Append(F1);
657 pLFF->Append(F2);
9b7f3f83 658 }
659 //
660 Build.Bind(aS,C);
661 }
662 else {
663 Failed.Append(aS);
664 }
665 } else { // IsDone(NF1,NF2)
666 // Modified by skv - Fri Dec 26 12:20:13 2003 OCC4455 Begin
667 const TopTools_ListOfShape &aLInt1 = myAsDes->Descendant(NF1);
668 const TopTools_ListOfShape &aLInt2 = myAsDes->Descendant(NF2);
669
670 if (!aLInt1.IsEmpty()) {
671 TopoDS_Compound C;
672 B.MakeCompound(C);
673 //
674 if (Build.IsBound(aS)) {
675 const TopoDS_Shape& aSE = Build(aS);
676 TopExp_Explorer aExp(aSE, TopAbs_EDGE);
677 for (; aExp.More(); aExp.Next()) {
678 const TopoDS_Shape& aNE = aExp.Current();
679 B.Add(C, aNE);
680 }
681 }
682 //
683 for (it.Initialize(aLInt1) ; it.More(); it.Next()) {
684 const TopoDS_Shape &anE1 = it.Value();
685 //
686 for (it1.Initialize(aLInt2) ; it1.More(); it1.Next()) {
687 const TopoDS_Shape &anE2 = it1.Value();
ecf4f17c 688 if (anE1.IsSame(anE2)) {
9b7f3f83 689 B.Add(C, anE1);
c2bf27a6 690 //
691 TopTools_ListOfShape *pLS = aDMIntE.ChangeSeek(anE1);
692 if (pLS) {
693 pLS->Append(aS);
ecf4f17c 694 }
695 }
9b7f3f83 696 }
697 }
698 Build.Bind(aS,C);
699 }
700 else {
701 Failed.Append(aS);
702 }
703 }
704 }
705 // Modified by skv - Fri Dec 26 12:20:14 2003 OCC4455 End
7fd59977 706 }
ecf4f17c 707 //
c2bf27a6 708 // create unique intersection for each localized shared part
ecf4f17c 709 aNb = aDMIntE.Extent();
710 for (i = 1; i <= aNb; ++i) {
c2bf27a6 711 const TopTools_ListOfShape& aLS = aDMIntE(i);
712 if (aLS.Extent() < 2) {
ecf4f17c 713 continue;
714 }
715 //
c2bf27a6 716 // intersection edge
717 const TopoDS_Edge& aE = TopoDS::Edge(aDMIntE.FindKey(i));
718 // faces created the edge
719 const TopTools_ListOfShape& aLFF = aDMIntFF.Find(aE);
720 const TopoDS_Shape& aF1 = aLFF.First();
721 const TopoDS_Shape& aF2 = aLFF.Last();
722
723 // Build really localized blocks from the original shapes in <aLS>:
724 // 1. Find edges from original faces connected to two or more shapes in <aLS>;
725 // 2. Make connexity blocks from edges in <aLS> and found connection edges;
726 // 3. Check if the vertices from <aLS> are not connected by these connection edges:
727 // a. If so - add these vertices to Connexity Block containing the corresponding
728 // connexity edge;
729 // b. If not - add this vertex to list of connexity blocks
730 // 4. Create unique intersection edge for each connexity block
731
732 // list of vertices
733 TopTools_ListOfShape aLV;
734 // compound of edges to build connexity blocks
ecf4f17c 735 TopoDS_Compound aCE;
736 B.MakeCompound(aCE);
c2bf27a6 737 TopTools_MapOfShape aMS;
738 TopTools_ListIteratorOfListOfShape aItLS(aLS);
739 for (; aItLS.More(); aItLS.Next()) {
740 const TopoDS_Shape& aS = aItLS.Value();
741 aMS.Add(aS);
742 if (aS.ShapeType() == TopAbs_EDGE) {
743 B.Add(aCE, aS);
744 }
745 else {
746 aLV.Append(aS);
747 }
748 }
ecf4f17c 749 //
c2bf27a6 750 // look for additional edges to connect the shared parts
751 TopTools_MapOfShape aMEConnection;
752 for (Standard_Integer j = 0; j < 2; ++j) {
753 const TopoDS_Shape& aF = !j ? aF1 : aF2;
754 //
755 TopExp_Explorer aExp(aF, TopAbs_EDGE);
756 for (; aExp.More(); aExp.Next()) {
757 const TopoDS_Shape& aEF = aExp.Current();
758 if (aMS.Contains(aEF) || aMEConnection.Contains(aEF)) {
759 continue;
760 }
761 //
762 TopoDS_Vertex aV1, aV2;
763 TopExp::Vertices(TopoDS::Edge(aEF), aV1, aV2);
764 //
765 // find parts to which the edge is connected
766 Standard_Integer iCounter = 0;
767 aItLS.Initialize(aLS);
768 for (; aItLS.More(); aItLS.Next()) {
769 const TopoDS_Shape& aS = aItLS.Value();
770 // iterator is not suitable here, because aS may be a vertex
771 TopExp_Explorer aExpV(aS, TopAbs_VERTEX);
772 for (; aExpV.More(); aExpV.Next()) {
773 const TopoDS_Shape& aV = aExpV.Current();
774 if (aV.IsSame(aV1) || aV.IsSame(aV2)) {
775 ++iCounter;
776 break;
777 }
778 }
779 }
780 //
781 if (iCounter >= 2) {
782 B.Add(aCE, aEF);
783 aMEConnection.Add(aEF);
784 }
785 }
ecf4f17c 786 }
787 //
788 TopTools_ListOfShape aLCBE;
789 BOPTools_AlgoTools::MakeConnexityBlocks(aCE, TopAbs_VERTEX, TopAbs_EDGE, aLCBE);
c2bf27a6 790 //
791 // create connexity blocks for alone vertices
792 TopTools_ListOfShape aLCBV;
793 TopTools_ListIteratorOfListOfShape aItLV(aLV);
794 for (; aItLV.More(); aItLV.Next()) {
795 const TopoDS_Shape& aV = aItLV.Value();
796 // check if this vertex is contained in some connexity block of edges
797 TopTools_ListIteratorOfListOfShape aItLCB(aLCBE);
798 for (; aItLCB.More(); aItLCB.Next()) {
799 TopoDS_Shape& aCB = aItLCB.ChangeValue();
800 TopExp_Explorer aExpV(aCB, TopAbs_VERTEX);
801 for (; aExpV.More(); aExpV.Next()) {
802 if (aV.IsSame(aExpV.Current())) {
803 B.Add(aCB, aV);
804 break;
805 }
806 }
807 if (aExpV.More()) {
808 break;
809 }
810 }
811 //
812 if (!aItLCB.More()) {
813 TopoDS_Compound aCV;
814 B.MakeCompound(aCV);
815 B.Add(aCV, aV);
816 aLCBV.Append(aCV);
817 }
818 }
819 //
820 aLCBE.Append(aLCBV);
821 //
ecf4f17c 822 if (aLCBE.Extent() == 1) {
823 continue;
824 }
825 //
c2bf27a6 826 const TopoDS_Shape& aNF1 = MES(MapSF(aF1).Face());
827 const TopoDS_Shape& aNF2 = MES(MapSF(aF2).Face());
ecf4f17c 828 //
c2bf27a6 829 TopTools_ListIteratorOfListOfShape aItLCB(aLCBE);
830 for (aItLCB.Next(); aItLCB.More(); aItLCB.Next()) {
ecf4f17c 831 // make new edge with different tedge instance
832 TopoDS_Edge aNewEdge;
833 TopoDS_Vertex aV1, aV2;
834 Standard_Real aT1, aT2;
835 //
836 TopExp::Vertices(aE, aV1, aV2);
837 BRep_Tool::Range(aE, aT1, aT2);
838 //
839 BOPTools_AlgoTools::MakeSplitEdge(aE, aV1, aT1, aV2, aT2, aNewEdge);
840 //
c2bf27a6 841 myAsDes->Add(aNF1, aNewEdge);
842 myAsDes->Add(aNF2, aNewEdge);
ecf4f17c 843 //
c2bf27a6 844 const TopoDS_Shape& aCB = aItLCB.Value();
ecf4f17c 845 TopoDS_Iterator aItCB(aCB);
846 for (; aItCB.More(); aItCB.Next()) {
847 const TopoDS_Shape& aS = aItCB.Value();
c2bf27a6 848 if (aMEConnection.Contains(aS)) {
849 continue;
850 }
ecf4f17c 851 TopoDS_Shape& aCI = Build.ChangeFind(aS);
852 //
853 TopoDS_Compound aNewCI;
854 B.MakeCompound(aNewCI);
855 TopExp_Explorer aExp(aCI, TopAbs_EDGE);
856 for (; aExp.More(); aExp.Next()) {
857 const TopoDS_Shape& aSx = aExp.Current();
858 if (!aSx.IsSame(aE)) {
859 B.Add(aNewCI, aSx);
860 }
861 }
862 B.Add(aNewCI, aNewEdge);
863 aCI = aNewCI;
864 }
865 }
866 }
7fd59977 867}
868
869//=======================================================================
870//function : ContextIntByInt
871//purpose :
872//=======================================================================
873
874void BRepOffset_Inter3d::ContextIntByInt
975ec82a
J
875(const TopTools_IndexedMapOfShape& ContextFaces,
876 const Standard_Boolean ExtentContext,
7fd59977 877 const BRepOffset_DataMapOfShapeOffset& MapSF,
878 const BRepOffset_Analyse& Analyse,
879 TopTools_DataMapOfShapeShape& MES,
880 TopTools_DataMapOfShapeShape& Build,
9b7f3f83 881 TopTools_ListOfShape& Failed,
882 const Standard_Boolean bIsPlanar)
7fd59977 883{
7fd59977 884 TopTools_MapOfShape MV;
885 TopExp_Explorer exp;
886 TopoDS_Face OF,NF,WCF;
887 TopoDS_Edge OE;
888 TopoDS_Compound C;
889 BRep_Builder B;
9b7f3f83 890 TopTools_ListIteratorOfListOfShape it, itF;
891 Standard_Integer i, j, aNb, aNbVE;
892 Standard_Boolean bEdge;
893
894 aNb = ContextFaces.Extent();
895 for (i = 1; i <= aNb; i++) {
975ec82a 896 const TopoDS_Face& CF = TopoDS::Face(ContextFaces(i));
7fd59977 897 myTouched.Add(CF);
898 if (ExtentContext) {
899 BRepOffset_Tool::EnLargeFace(CF,NF,0,0);
900 MES.Bind(CF,NF);
901 }
902 }
903 TopAbs_State Side = TopAbs_OUT;
904
9b7f3f83 905 for (i = 1; i <= aNb; i++) {
975ec82a 906 const TopoDS_Face& CF = TopoDS::Face(ContextFaces(i));
7fd59977 907 if (ExtentContext) WCF = TopoDS::Face(MES(CF));
908 else WCF = CF;
909
9b7f3f83 910 TopTools_IndexedMapOfShape VEmap;
911 TopExp::MapShapes(CF.Oriented(TopAbs_FORWARD), TopAbs_EDGE , VEmap);
912 //
913 if (bIsPlanar) {
914 TopExp::MapShapes(CF.Oriented(TopAbs_FORWARD), TopAbs_VERTEX, VEmap);
915 }
916 //
917 aNbVE = VEmap.Extent();
918 for (j = 1; j <= aNbVE; ++j) {
919 const TopoDS_Shape& aS = VEmap(j);
920 //
921 bEdge = (aS.ShapeType() == TopAbs_EDGE);
922 //
923 TopoDS_Edge E;
924 TopTools_ListOfShape Anc;
925 //
926 if (bEdge) {
927 // faces connected by the edge
928 //
929 E = *(TopoDS_Edge*)&aS;
930 if (!Analyse.HasAncestor(E)) {
931 //----------------------------------------------------------------
932 // the edges of faces of context that are not in the initial shape
933 // can appear in the result.
934 //----------------------------------------------------------------
935 if (!ExtentContext) {
936 myAsDes->Add(CF,E);
937 myNewEdges.Add(E);
938 }
939 else {
940 if (!MES.IsBound(E)) {
941 TopoDS_Edge NE;
942 Standard_Real f,l,Tol;
943 BRep_Tool::Range(E,f,l);
944 Tol = BRep_Tool::Tolerance(E);
945 ExtentEdge(CF,E,NE);
946 TopoDS_Vertex V1,V2;
947 TopExp::Vertices(E,V1,V2);
948 NE.Orientation(TopAbs_FORWARD);
949 myAsDes->Add(NE,V1.Oriented(TopAbs_REVERSED));
950 myAsDes->Add(NE,V2.Oriented(TopAbs_FORWARD));
951 TopoDS_Shape aLocalShape = V1.Oriented(TopAbs_INTERNAL);
952 B.UpdateVertex(TopoDS::Vertex(aLocalShape),f,NE,Tol);
953 aLocalShape = V2.Oriented(TopAbs_INTERNAL);
954 B.UpdateVertex(TopoDS::Vertex(aLocalShape),l,NE,Tol);
955// B.UpdateVertex(TopoDS::Vertex(V1.Oriented(TopAbs_INTERNAL)),f,NE,Tol);
956// B.UpdateVertex(TopoDS::Vertex(V2.Oriented(TopAbs_INTERNAL)),l,NE,Tol);
957 NE.Orientation(E.Orientation());
958 myAsDes->Add(CF,NE);
959 myNewEdges.Add(NE);
960 MES.Bind(E,NE);
961 }
962 else {
963 TopoDS_Shape NE = MES(E);
964 TopoDS_Shape aLocalShape = NE.Oriented(E.Orientation());
965 myAsDes->Add(CF,aLocalShape);
966// myAsDes->Add(CF,NE.Oriented(E.Orientation()));
967 }
968 }
969 continue;
970 }
971 Anc = Analyse.Ancestors(E);
7fd59977 972 }
973 else {
9b7f3f83 974 // faces connected by the vertex
975 //
976 if (!Analyse.HasAncestor(aS)) {
977 continue;
978 }
979 //
980 const TopTools_ListOfShape& aLE = Analyse.Ancestors(aS);
981 it.Initialize(aLE);
982 for (; it.More(); it.Next()) {
983 const TopoDS_Edge& aE = *(TopoDS_Edge*)&it.Value();
984 //
985 if (BRep_Tool::Degenerated(aE)) {
986 continue;
987 }
988 //
989 if (VEmap.Contains(aE)) {
990 continue;
991 }
992 //
993 const TopTools_ListOfShape& aLF = Analyse.Ancestors(aE);
994 itF.Initialize(aLF);
995 for (; itF.More(); itF.Next()) {
996 const TopoDS_Shape& aF = itF.Value();
997 Standard_Boolean bAdd = Standard_True;
998 exp.Init(aF, TopAbs_EDGE);
999 for (; exp.More() && bAdd; exp.Next()) {
1000 const TopoDS_Shape& aEF = exp.Current();
1001 bAdd = !VEmap.Contains(aEF);
1002 }
1003 if (bAdd) {
1004 Anc.Append(aF);
1005 }
1006 }
1007 }
7fd59977 1008 }
9b7f3f83 1009 //
1010 itF.Initialize(Anc);
1011 for (; itF.More(); itF.Next()) {
1012 const TopoDS_Face& F = TopoDS::Face(itF.Value());
1013 OF = TopoDS::Face(MapSF(F).Face());
1014 TopoDS_Shape aLocalShape = MapSF(F).Generated(E);
1015 OE = TopoDS::Edge(aLocalShape);
1016// OE = TopoDS::Edge(MapSF(F).Generated(E));
1017 if (!MES.IsBound(OF)) {
1018 BRepOffset_Tool::EnLargeFace(OF,NF,1,1);
1019 MES.Bind(OF,NF);
1020 }
1021 else {
1022 NF = TopoDS::Face(MES(OF));
1023 }
1024 if (!IsDone(NF,CF)) {
1025 TopTools_ListOfShape LInt1,LInt2;
1026 TopTools_ListOfShape LOE;
1027 LOE.Append(OE);
1028 BRepOffset_Tool::Inter3D (WCF,NF,LInt1,LInt2,Side,E,bEdge);
1029 SetDone(NF,CF);
1030 if (!LInt1.IsEmpty()) {
1031 Store (CF,NF,LInt1,LInt2);
1032 if ((LInt1.Extent() == 1) && !Build.IsBound(aS)) {
1033 Build.Bind(aS,LInt1.First());
1034 }
1035 else {
1036 B.MakeCompound(C);
1037 if (Build.IsBound(aS)) {
1038 const TopoDS_Shape& aSE = Build(aS);
1039 exp.Init(aSE, TopAbs_EDGE);
1040 for (; exp.More(); exp.Next()) {
1041 const TopoDS_Shape& aNE = exp.Current();
1042 B.Add(C, aNE);
1043 }
1044 }
1045 //
1046 for (it.Initialize(LInt1) ; it.More(); it.Next()) {
1047 B.Add(C,it.Value());
1048 }
1049 Build.Bind(aS,C);
1050 }
1051 }
1052 else {
1053 Failed.Append(aS);
1054 }
1055 }
7fd59977 1056 }
1057 }
1058 }
1059}
1060
1061//=======================================================================
1062//function : ContextIntByArc
1063//purpose :
1064//=======================================================================
1065
975ec82a 1066void BRepOffset_Inter3d::ContextIntByArc(const TopTools_IndexedMapOfShape& ContextFaces,
9b7f3f83 1067 const Standard_Boolean InSide,
1068 const BRepOffset_Analyse& Analyse,
1069 const BRepAlgo_Image& InitOffsetFace,
1070 BRepAlgo_Image& InitOffsetEdge)
7fd59977 1071
1072{
1073 TopTools_ListOfShape LInt1,LInt2;
7fd59977 1074 TopTools_MapOfShape MV;
1075 TopExp_Explorer exp;
1076 TopoDS_Face OF1,OF2;
1077 TopoDS_Edge OE;
1078 BRep_Builder B;
1079 TopoDS_Edge NullEdge;
975ec82a 1080 Standard_Integer j;
7fd59977 1081
975ec82a
J
1082 for (j = 1; j <= ContextFaces.Extent(); j++) {
1083 const TopoDS_Face& CF = TopoDS::Face(ContextFaces(j));
7fd59977 1084 myTouched.Add(CF);
1085 }
1086
975ec82a
J
1087 for (j = 1; j <= ContextFaces.Extent(); j++) {
1088 const TopoDS_Face& CF = TopoDS::Face(ContextFaces(j));
7fd59977 1089 for (exp.Init(CF.Oriented(TopAbs_FORWARD),TopAbs_EDGE);
9b7f3f83 1090 exp.More(); exp.Next()) {
7fd59977 1091 const TopoDS_Edge& E = TopoDS::Edge(exp.Current());
1092 if (!Analyse.HasAncestor(E)) {
9b7f3f83 1093 if (InSide)
1094 myAsDes->Add(CF,E);
1095 else {
1096 TopoDS_Edge NE;
1097 if (!InitOffsetEdge.HasImage(E)) {
1098 Standard_Real f,l,Tol;
1099 BRep_Tool::Range(E,f,l);
1100 Tol = BRep_Tool::Tolerance(E);
1101 ExtentEdge(CF,E,NE);
1102 TopoDS_Vertex V1,V2;
1103 TopExp::Vertices(E,V1,V2);
1104 NE.Orientation(TopAbs_FORWARD);
1105 myAsDes->Add(NE,V1.Oriented(TopAbs_REVERSED));
1106 myAsDes->Add(NE,V2.Oriented(TopAbs_FORWARD));
1107 TopoDS_Shape aLocalShape = V1.Oriented(TopAbs_INTERNAL);
1108 B.UpdateVertex(TopoDS::Vertex(aLocalShape),f,NE,Tol);
1109 aLocalShape = V2.Oriented(TopAbs_INTERNAL);
1110 B.UpdateVertex(TopoDS::Vertex(aLocalShape),l,NE,Tol);
1111// B.UpdateVertex(TopoDS::Vertex(V1.Oriented(TopAbs_INTERNAL)),f,NE,Tol);
1112// B.UpdateVertex(TopoDS::Vertex(V2.Oriented(TopAbs_INTERNAL)),l,NE,Tol);
1113 NE.Orientation(E.Orientation());
1114 myAsDes->Add(CF,NE);
1115 InitOffsetEdge.Bind(E,NE);
1116 }
1117 else {
1118 NE = TopoDS::Edge(InitOffsetEdge.Image(E).First());
1119 myAsDes->Add(CF,NE.Oriented(E.Orientation()));
1120 }
1121 }
1122 continue;
7fd59977 1123 }
1124 OE.Nullify();
0d969553
Y
1125 //---------------------------------------------------
1126 // OF1 parallel facee generated by the ancestor of E.
1127 //---------------------------------------------------
7fd59977 1128 const TopoDS_Shape SI = Analyse.Ancestors(E).First();
1129 OF1 = TopoDS::Face(InitOffsetFace.Image(SI).First());
3d58dc49 1130 OE = TopoDS::Edge(InitOffsetEdge.Image(E).First());
1131
1132 {
1133 //Check if OE has pcurve in CF
1134
1135 Standard_Real f,l;
1136
1137 Handle (Geom2d_Curve) C1 = BRep_Tool::CurveOnSurface(OE,CF,f,l);
1138 Handle (Geom2d_Curve) C2 = BRep_Tool::CurveOnSurface(OE,OF1,f,l);
1139
1140 if(C1.IsNull() || C2.IsNull())
1141 {
1142 continue;
1143 }
1144 }
1145
7fd59977 1146 //--------------------------------------------------
0d969553 1147 // MAJ of OE on cap CF.
7fd59977 1148 //--------------------------------------------------
9b7f3f83 1149// TopTools_ListOfShape LOE; LOE.Append(OE);
7fd59977 1150// BRepOffset_Tool::TryProject(CF,OF1,LOE,LInt1,LInt2,mySide);
1151// LInt2.Clear();
1152// StoreInter3d(CF,OF1,myTouched,NewEdges,InterDone,myAsDes,
9b7f3f83 1153// LInt1,LInt2);
7fd59977 1154 LInt1.Clear(); LInt1.Append(OE);
1155 LInt2.Clear();
9b7f3f83 1156 TopAbs_Orientation anOri1, anOri2;
1157 BRepOffset_Tool::OrientSection(OE,CF,OF1, anOri1,anOri2);
1158// if (mySide == TopAbs_OUT);
1159 anOri1 = TopAbs::Reverse(anOri1);
1160 LInt1.First().Orientation(anOri1);
7fd59977 1161 Store(CF,OF1,LInt1,LInt2);
1162
1163 //------------------------------------------------------
0d969553 1164 // Processing of offsets on the ancestors of vertices.
7fd59977 1165 //------------------------------------------------------
1166 TopoDS_Vertex V[2];
1167 TopExp::Vertices (E,V[0],V[1]);
1168 for (Standard_Integer i = 0; i < 2; i++) {
9b7f3f83 1169 if (!MV.Add(V[i])) continue;
1170 OF1.Nullify();
1171 const TopTools_ListOfShape& LE = Analyse.Ancestors(V[i]);
1172 TopTools_ListIteratorOfListOfShape itLE(LE);
1173 for ( ; itLE.More(); itLE.Next()) {
1174 const TopoDS_Edge& EV = TopoDS::Edge(itLE.Value());
1175 if (InitOffsetFace.HasImage(EV)) {
1176 //-------------------------------------------------
1177 // OF1 parallel face generated by an ancester edge of V[i].
1178 //-------------------------------------------------
1179 OF1 = TopoDS::Face(InitOffsetFace.Image(EV).First());
1180 OE = TopoDS::Edge(InitOffsetEdge.Image(V[i]).First());
3d58dc49 1181
1182 {
1183 //Check if OE has pcurve in CF and OF1
1184
1185 Standard_Real f,l;
1186
1187 Handle (Geom2d_Curve) C1 = BRep_Tool::CurveOnSurface(OE,CF,f,l);
1188 Handle (Geom2d_Curve) C2 = BRep_Tool::CurveOnSurface(OE,OF1,f,l);
1189
1190 if(C1.IsNull() || C2.IsNull())
1191 {
1192 continue;
1193 }
1194 }
1195
9b7f3f83 1196 //--------------------------------------------------
1197 // MAj of OE on cap CF.
1198 //--------------------------------------------------
1199 // LOE.Clear(); LOE.Append(OE);
1200 // BRepOffset_Tool::TryProject(CF,OF1,LOE,LInt1,LInt2,mySide);
1201 // LInt2.Clear();
1202 // StoreInter3d(CF,OF1,myTouched,NewEdges,InterDone,myAsDes,
1203 // LInt1,LInt2);
1204 LInt1.Clear(); LInt1.Append(OE);
1205 LInt2.Clear();
1206 TopAbs_Orientation O1,O2;
1207 BRepOffset_Tool::OrientSection(OE,CF,OF1,O1,O2);
1208// if (mySide == TopAbs_OUT);
1209 O1 = TopAbs::Reverse(O1);
1210 LInt1.First().Orientation(O1);
1211 Store(CF,OF1,LInt1,LInt2);
1212 }
1213 }
7fd59977 1214 }
1215 }
1216
1217 for (exp.Init(CF.Oriented(TopAbs_FORWARD),TopAbs_VERTEX);
9b7f3f83 1218 exp.More(); exp.Next()) {
7fd59977 1219 const TopoDS_Vertex& V = TopoDS::Vertex(exp.Current());
1220 if (!Analyse.HasAncestor(V)) {
9b7f3f83 1221 continue;
7fd59977 1222 }
1223 const TopTools_ListOfShape& LE = Analyse.Ancestors(V);
1224 TopTools_ListIteratorOfListOfShape itLE(LE);
1225 for (; itLE.More(); itLE.Next()) {
9b7f3f83 1226 const TopoDS_Edge& EV = TopoDS::Edge(itLE.Value());
1227 const TopTools_ListOfShape& LF = Analyse.Ancestors(EV);
1228 TopTools_ListIteratorOfListOfShape itLF(LF);
1229 for ( ; itLF.More(); itLF.Next()) {
1230 const TopoDS_Face& FEV = TopoDS::Face(itLF.Value());
1231 //-------------------------------------------------
1232 // OF1 parallel face generated by uneFace ancestor of V[i].
1233 //-------------------------------------------------
1234 OF1 = TopoDS::Face(InitOffsetFace.Image(FEV).First());
1235 if (!IsDone(OF1,CF)) {
1236 //-------------------------------------------------------
1237 // Find if one of edges of OF1 has no trace in CF.
1238 //-------------------------------------------------------
1239 TopTools_ListOfShape LOE;
1240 TopExp_Explorer exp2(OF1.Oriented(TopAbs_FORWARD),TopAbs_EDGE);
1241 for ( ;exp2.More(); exp2.Next()) {
1242 LOE.Append(exp2.Current());
1243 }
1244 BRepOffset_Tool::TryProject(CF,OF1,LOE,LInt1,LInt2,mySide,myTol);
1245 //-------------------------------------------------------
1246 // If no trace try intersection.
1247 //-------------------------------------------------------
1248 if (LInt1.IsEmpty()) {
1249 BRepOffset_Tool::Inter3D (CF,OF1,LInt1,LInt2,mySide,NullEdge);
1250 }
1251 Store (CF,OF1,LInt1,LInt2);
1252 }
1253 }
7fd59977 1254 }
1255 }
1256 }
1257}
1258
1259//=======================================================================
1260//function : AddCommonEdges
1261//purpose :
1262//=======================================================================
1263
35e08fe8 1264void BRepOffset_Inter3d::AddCommonEdges(const TopTools_ListOfShape&)
7fd59977 1265{
1266}
1267
1268
1269//=======================================================================
1270//function : SetDone
1271//purpose :
1272//=======================================================================
1273
1274void BRepOffset_Inter3d::SetDone(const TopoDS_Face& F1,
9b7f3f83 1275 const TopoDS_Face& F2)
7fd59977 1276{
1277 if (!myDone.IsBound(F1)) {
1278 TopTools_ListOfShape empty;
1279 myDone.Bind(F1,empty);
1280 }
1281 myDone(F1).Append(F2);
1282 if (!myDone.IsBound(F2)) {
1283 TopTools_ListOfShape empty;
1284 myDone.Bind(F2,empty);
1285 }
1286 myDone(F2).Append(F1);
1287}
1288
1289
1290//=======================================================================
1291//function : IsDone
1292//purpose :
1293//=======================================================================
1294
1295Standard_Boolean BRepOffset_Inter3d::IsDone(const TopoDS_Face& F1,
9b7f3f83 1296 const TopoDS_Face& F2)
7fd59977 1297const
1298{
1299 if (myDone.IsBound(F1)) {
1300 TopTools_ListIteratorOfListOfShape it (myDone(F1));
1301 for (; it.More(); it.Next()) {
1302 if (it.Value().IsSame(F2)) return Standard_True;
1303 }
1304 }
1305 return Standard_False;
1306}
1307
1308
1309//=======================================================================
1310//function : TouchedFaces
1311//purpose :
1312//=======================================================================
1313
975ec82a 1314TopTools_IndexedMapOfShape& BRepOffset_Inter3d::TouchedFaces()
7fd59977 1315{
1316 return myTouched;
1317}
1318
1319
1320//=======================================================================
1321//function : AsDes
1322//purpose :
1323//=======================================================================
1324
1325Handle(BRepAlgo_AsDes) BRepOffset_Inter3d::AsDes() const
1326{
1327 return myAsDes;
1328}
1329
1330
1331//=======================================================================
1332//function : NewEdges
1333//purpose :
1334//=======================================================================
1335
975ec82a 1336TopTools_IndexedMapOfShape& BRepOffset_Inter3d::NewEdges()
7fd59977 1337{
1338 return myNewEdges;
1339}
1340
1341
1342
1343//=======================================================================
1344//function : Store
1345//purpose :
1346//=======================================================================
1347
1348void BRepOffset_Inter3d::Store(const TopoDS_Face& F1,
9b7f3f83 1349 const TopoDS_Face& F2,
1350 const TopTools_ListOfShape& LInt1,
1351 const TopTools_ListOfShape& LInt2)
7fd59977 1352{
1353 if (!LInt1.IsEmpty()) {
1354 myTouched.Add(F1);
1355 myTouched.Add(F2);
1356 myAsDes->Add( F1,LInt1);
1357 myAsDes->Add( F2,LInt2);
1358 TopTools_ListIteratorOfListOfShape it(LInt1);
1359 for (; it.More(); it.Next()) {
1360 myNewEdges.Add(it.Value());
1361 }
1362 }
1363 SetDone(F1,F2);
1364}