1 // File: NMTTools_PaveFiller_5.cxx
2 // Created: Mon Dec 15 11:28:33 2003
3 // Author: Peter KURNEV
7 #include <NMTTools_PaveFiller.ixx>
9 #include <TColStd_IndexedMapOfInteger.hxx>
11 #include <BRep_Tool.hxx>
12 #include <BRep_Builder.hxx>
14 #include <Bnd_Box.hxx>
16 #include <TopAbs_ShapeEnum.hxx>
19 #include <TopoDS_Face.hxx>
20 #include <TopoDS_Edge.hxx>
21 #include <TopoDS_Vertex.hxx>
22 #include <TopoDS_Compound.hxx>
24 #include <TopTools_IndexedMapOfShape.hxx>
26 #include <IntTools_ShrunkRange.hxx>
27 #include <IntTools_Range.hxx>
28 #include <IntTools_EdgeFace.hxx>
29 #include <IntTools_PContext.hxx>
30 #include <IntTools_SequenceOfCommonPrts.hxx>
31 #include <IntTools_CommonPrt.hxx>
32 #include <IntTools_Tools.hxx>
34 #include <BooleanOperations_AncestorsSeqAndSuccessorsSeq.hxx>
35 #include <BooleanOperations_IndexedDataMapOfShapeInteger.hxx>
36 #include <BooleanOperations_OnceExplorer.hxx>
38 #include <BOPTools_Tools.hxx>
39 #include <BOPTools_Pave.hxx>
40 #include <BOPTools_PaveSet.hxx>
41 #include <BOPTools_ListOfPave.hxx>
42 #include <BOPTools_ListIteratorOfListOfPave.hxx>
43 #include <BOPTools_PaveBlock.hxx>
44 #include <BOPTools_ListOfPaveBlock.hxx>
45 #include <BOPTools_ListIteratorOfListOfPaveBlock.hxx>
46 #include <BOPTools_ESInterference.hxx>
47 #include <BOPTools_InterferencePool.hxx>
48 #include <BOPTools_CArray1OfVVInterference.hxx>
49 #include <BOPTools_CArray1OfESInterference.hxx>
50 #include <BOPTools_VVInterference.hxx>
51 #include <BOPTools_ESInterference.hxx>
52 #include <BOPTools_IDMapOfPaveBlockIMapOfInteger.hxx>
53 #include <BOPTools_IMapOfPaveBlock.hxx>
55 #include <NMTDS_ShapesDataStructure.hxx>
57 #include <NMTTools_ListOfCommonBlock.hxx>
58 #include <NMTTools_CommonBlockAPI.hxx>
59 #include <NMTTools_IndexedDataMapOfIndexedMapOfInteger.hxx>
60 #include <NMTTools_CommonBlockAPI.hxx>
61 #include <NMTTools_ListOfCommonBlock.hxx>
64 void VertexParameter(const IntTools_CommonPrt& aCPart,
67 Standard_Boolean IsOnPave(const Standard_Real& aTR,
68 const IntTools_Range& aCPRange,
69 const Standard_Real& aTolerance);
71 //=======================================================================
72 // function: PerformEF
74 //=======================================================================
75 void NMTTools_PaveFiller::PerformEF()
77 myIsDone=Standard_False;
79 Standard_Integer n1, n2, anIndexIn=0, nE, nF, aNbEFs, aBlockLength;
80 Standard_Boolean bJustAdd;
81 Standard_Real aTolE, aTolF, aDeflection=0.01;
82 Standard_Integer aDiscretize=35;
83 BooleanOperations_IndexedDataMapOfShapeInteger aMapVI;
84 BOPTools_IDMapOfPaveBlockIMapOfInteger aMapCB;
85 BOPTools_IMapOfPaveBlock aIMPBx;
88 BOPTools_CArray1OfESInterference& aEFs=myIntrPool->ESInterferences();
90 myDSIt.Initialize(TopAbs_EDGE, TopAbs_FACE);
92 // BlockLength correction
93 aNbEFs=ExpectedPoolLength();
94 aBlockLength=aEFs.BlockLength();
95 if (aNbEFs > aBlockLength) {
96 aEFs.SetBlockLength(aNbEFs);
99 for (; myDSIt.More(); myDSIt.Next()) {
100 myDSIt.Current(n1, n2, bJustAdd);
103 if (myIntrPool->IsComputed(n1, n2)) {
111 // all Common Blocks for face nF
113 NMTTools_ListOfCommonBlock aLCBF;
114 CommonBlocksFace(nF, aLCBF);
115 NMTTools_CommonBlockAPI aCBAPIF(aLCBF);
118 myIntrPool->AddInterference (nE, nF, BooleanOperations_EdgeSurface, anIndexIn);
122 const TopoDS_Edge& aE=TopoDS::Edge(myDS->GetShape(nE));
123 if (BRep_Tool::Degenerated(aE)){
126 aTolE=BRep_Tool::Tolerance(aE);
128 const TopoDS_Face& aF=TopoDS::Face(myDS->GetShape(nF));
129 aTolF=BRep_Tool::Tolerance(aF);
130 const Bnd_Box& aBBF=myDS->GetBoundingBox(nF);
132 // Process each PaveBlock on edge nE
133 BOPTools_ListOfPaveBlock& aLPB=mySplitShapesPool(myDS->RefEdge(nE));
135 BOPTools_ListIteratorOfListOfPaveBlock anIt(aLPB);
136 for (; anIt.More(); anIt.Next()) {
137 BOPTools_PaveBlock& aPB=anIt.Value();
139 if (aCBAPIF.IsCommonBlock(aPB)) {
143 const IntTools_ShrunkRange& aShrunkRange=aPB.ShrunkRange();
144 const IntTools_Range& aSR =aShrunkRange.ShrunkRange();
145 const Bnd_Box& aBBE=aShrunkRange.BndBox();
147 if (aBBF.IsOut (aBBE)) {
152 IntTools_EdgeFace aEF;
157 aEF.SetDiscretize (aDiscretize);
158 aEF.SetDeflection (aDeflection);
160 aEF.SetContext((IntTools_PContext)&myContext);
162 IntTools_Range anewSR = aSR;
164 // Correction of the Shrunk Range
165 BOPTools_Tools::CorrectRange(aE, aF, aSR, anewSR);
166 aEF.SetRange (anewSR);
171 const IntTools_SequenceOfCommonPrts& aCPrts=aEF.CommonParts();
172 Standard_Integer i, aNbCPrts;
173 aNbCPrts=aCPrts.Length();
174 for (i=1; i<=aNbCPrts; i++) {
178 const IntTools_CommonPrt& aCPart=aCPrts(i);
179 TopAbs_ShapeEnum aType=aCPart.Type();
182 case TopAbs_VERTEX: {
183 Standard_Boolean bIsOnPave1, bIsOnPave2;
184 Standard_Integer nVF;
185 Standard_Real aT, aTolToDecide;
186 TopoDS_Vertex aNewVertex;
188 const IntTools_Range& aR=aCPart.Range1();
191 VertexParameter(aCPart, aT);
192 BOPTools_Tools::MakeNewVertex(aE, aT, aF, aNewVertex);
194 //decide to add pave or not
197 bIsOnPave1=IsOnPave(anewSR.First(), aR, aTolToDecide);
198 bIsOnPave2=IsOnPave(anewSR.Last() , aR, aTolToDecide);
200 if (!bIsOnPave1 && !bIsOnPave2) {
201 nVF=CheckFacePaves(aNewVertex, nF);
204 // Add Interference to the Pool
205 BOPTools_ESInterference anInterf (nE, nF, aCPart);
206 anIndexIn=aEFs.Append(anInterf);
207 anInterf.SetNewShape(0);
209 aMapVI.Add(aNewVertex, anIndexIn);
213 }// if (!bIsOnPave1 && !bIsOnPave2)
214 myIntrPool->AddInterference (nE, nF, BooleanOperations_EdgeSurface, anIndexIn);
215 }// case TopAbs_VERTEX:
219 Standard_Boolean aCoinsideFlag;
221 aCoinsideFlag=BOPTools_Tools::IsBlockInOnFace(aPB, aF, myContext);
222 if (!aCoinsideFlag) {
223 myIntrPool->AddInterference (nE, nF, BooleanOperations_EdgeSurface, anIndexIn);
228 if (aMapCB.Contains(aPB)) {
229 TColStd_IndexedMapOfInteger& aMapF=aMapCB.ChangeFromKey(aPB);
233 TColStd_IndexedMapOfInteger aMapF;
235 aMapCB.Add(aPB, aMapF);
237 //modified by NIZNHY-PKV Fri Jan 23 14:13:08 2004 f
239 //modified by NIZNHY-PKV Fri Jan 23 14:13:10 2004 t
240 }// case TopAbs_EDGE:
246 } // for (i=1; i<=aNbCPrts; i++)
247 } //if (aEF.IsDone())
248 } // for (; anIt.More(); anIt.Next())
249 }// for (; myDSIt.More(); myDSIt.Next())
251 // Treat New vertices
252 EFNewVertices(aMapVI);
254 // Add draft Common Blocks of EF type
255 EFCommonBlocks(aMapCB);
257 // Collect all CB we suspected to split by new vertices
258 NMTTools_ListOfCommonBlock aLCBx;
260 Standard_Integer i, aNbPBx, nEx;
261 BOPTools_IMapOfPaveBlock aMx;
263 aNbPBx=aIMPBx.Extent();
264 for (i=1; i<=aNbPBx; ++i) {
265 const BOPTools_PaveBlock& aPBx=aIMPBx(i);
266 nEx=aPBx.OriginalEdge();
267 NMTTools_ListOfCommonBlock& aLCB=myCommonBlockPool(myDS->RefEdge(nEx));
269 NMTTools_CommonBlockAPI aCBAPIx(aLCB);
270 if (aCBAPIx.IsCommonBlock(aPBx)) {
271 NMTTools_CommonBlock& aCBx=aCBAPIx.CommonBlock(aPBx);
272 const BOPTools_PaveBlock& aPB1=aCBx.PaveBlock1();
273 if (!aMx.Contains(aPB1)){
282 // Split the common blocks above
283 if (aLCBx.Extent()) {
284 ReplaceCommonBlocks(aLCBx);
287 myIsDone=Standard_True;
289 //=======================================================================
290 // function:EFCommonBlocks
292 //=======================================================================
293 void NMTTools_PaveFiller::EFCommonBlocks(const BOPTools_IDMapOfPaveBlockIMapOfInteger& aMapCB)
295 Standard_Integer i, aNbPB, nE, j, aNbF, nF;
297 aNbPB=aMapCB.Extent();
299 for (i=1; i<=aNbPB; ++i) {
300 const BOPTools_PaveBlock& aPB=aMapCB.FindKey(i);
301 const TColStd_IndexedMapOfInteger& aMapF=aMapCB.FindFromIndex(i);
304 nE=aPB.OriginalEdge();
306 NMTTools_ListOfCommonBlock& aLCB=myCommonBlockPool(myDS->RefEdge(nE));
308 NMTTools_CommonBlockAPI aCBAPI(aLCB);
309 if (aCBAPI.IsCommonBlock(aPB)) {
310 NMTTools_CommonBlock& aCB=aCBAPI.CommonBlock(aPB);
311 for (j=1; j<=aNbF; ++j) {
317 NMTTools_CommonBlock aCB;
319 aCB.AddPaveBlock(aPB);
320 for (j=1; j<=aNbF; ++j) {
328 //=======================================================================
329 // function:EFNewVertices
331 //=======================================================================
332 void NMTTools_PaveFiller::EFNewVertices (const BooleanOperations_IndexedDataMapOfShapeInteger& aMapVI)
334 Standard_Integer i, j, aNb, aNewShape, aFlag, iX, aNbVV, aNbSimple;
335 Standard_Integer aWhat, aWith, nE, nF, nV, aNbIEF, aNbEdges;
337 TopoDS_Compound aCompound;
338 TopoDS_Vertex aNewVertex;
341 NMTTools_IndexedDataMapOfIndexedMapOfInteger aMNVE, aMNVIEF;
342 BooleanOperations_AncestorsSeqAndSuccessorsSeq anASSeq;
343 TopTools_IndexedMapOfShape aMNVComplex, aMNVSimple;
345 BOPTools_CArray1OfESInterference& aEFs=myIntrPool->ESInterferences();
349 if (!aNb) { // no new vertices, no new problems
355 aNewVertex=TopoDS::Vertex(aMapVI.FindKey(1));
356 EFNewVertices(aNewVertex, aMapVI);
360 // 1. Make compound from new vertices
361 aBB.MakeCompound(aCompound);
362 for (i=1; i<=aNb; ++i) {
363 const TopoDS_Shape& aV=aMapVI.FindKey(i);
364 aBB.Add(aCompound, aV);
367 // 2. VV intersection between these vertices
368 // using the auxiliary Filler
369 NMTDS_ShapesDataStructure tDS;
371 tDS.SetCompositeShape(aCompound);
374 BOPTools_InterferencePool tInterfPool(tDS);
375 NMTTools_PaveFiller tPaveFiller(tInterfPool);
379 tPaveFiller.PerformVV();
380 tPaveFiller.PerformNewVertices();
382 const BOPTools_CArray1OfVVInterference& aVVInterfs=tInterfPool.VVInterfs();
384 // 3. Separate Comlex and Simple new vertices
385 aNbVV=aVVInterfs.Extent();
386 for (i=1; i<=aNbVV; ++i) {
387 const BOPTools_VVInterference& aVV=aVVInterfs(i);
388 aVV.Indices(aWhat, aWith);
389 const TopoDS_Shape& aV1=tDS.Shape(aWhat);
390 const TopoDS_Shape& aV2=tDS.Shape(aWith);
391 aMNVComplex.Add(aV1);
392 aMNVComplex.Add(aV2);
395 for (i=1; i<=aNb; ++i) {
396 const TopoDS_Shape& aV=aMapVI.FindKey(i);
397 if (!aMNVComplex.Contains(aV)) {
402 // 4. Treat Simple new Vertices
403 aNbSimple=aMNVSimple.Extent();
404 for (i=1; i<=aNbSimple; ++i) {
405 const TopoDS_Vertex& aV=TopoDS::Vertex(aMNVSimple(i));
406 EFNewVertices(aV, aMapVI);
409 // 3. Fill Maps : NewVertex-edges (aMNVE)
410 // NewVertex-interferences (aMNVIEE)
411 aNb=aVVInterfs.Extent();
412 for (i=1; i<=aNb; ++i) {
413 const BOPTools_VVInterference& aVV=aVVInterfs(i);
414 aNewShape=aVV.NewShape();
419 if (!aMNVE.Contains(aNewShape)) {
420 TColStd_IndexedMapOfInteger aMx;
421 aMNVE.Add(aNewShape, aMx);
423 if (!aMNVIEF.Contains(aNewShape)) {
424 TColStd_IndexedMapOfInteger aMx;
425 aMNVIEF.Add(aNewShape, aMx);
428 TColStd_IndexedMapOfInteger& aME=aMNVE.ChangeFromKey(aNewShape);
429 TColStd_IndexedMapOfInteger& aMIEF=aMNVIEF.ChangeFromKey(aNewShape);
431 aVV.Indices(aWhat, aWith);
433 const TopoDS_Shape& aV1=tDS.Shape(aWhat);
434 iX=aMapVI.FindFromKey(aV1);
435 const BOPTools_ESInterference& aEF1=aEFs(iX);
436 aEF1.Indices(nE, nF);
441 const TopoDS_Shape& aV2=tDS.Shape(aWith);
442 iX=aMapVI.FindFromKey(aV2);
443 const BOPTools_ESInterference& aEF2=aEFs(iX);
444 aEF2.Indices(nE, nF);
449 // 4. Process new vertices
451 for (i=1; i<=aNb; ++i) { // xx
455 aNewVertex=TopoDS::Vertex(tDS.Shape(nV));
457 // Insert New Vertex in DS;
458 myDS->InsertShapeAndAncestorsSuccessors(aNewVertex, anASSeq);
459 aNewShape=myDS->NumberOfInsertedShapes();
460 myDS->SetState (aNewShape, BooleanOperations_ON);
462 // Update index of NewShape in EF interferences
463 const TColStd_IndexedMapOfInteger& aMIEF=aMNVIEF.FindFromKey(nV);
464 aNbIEF=aMIEF.Extent();
465 for (j=1; j<=aNbIEF; ++j) {
467 BOPTools_ESInterference& aEF=aEFs(iX);
468 aEF.SetNewShape(aNewShape);
471 // Update Paves on all edges
472 const TColStd_IndexedMapOfInteger& aME=aMNVE(i);
473 aNbEdges=aME.Extent();
474 for (j=1; j<=aNbEdges; ++j) {
476 const TopoDS_Edge& aE=TopoDS::Edge(myDS->Shape(nE));
478 aFlag=myContext.ComputeVE (aNewVertex, aE, aT);
481 aPave.SetInterference(-1);
482 aPave.SetType (BooleanOperations_EdgeSurface);
483 aPave.SetIndex(aNewShape);
486 BOPTools_PaveSet& aPaveSet=myPavePoolNew(myDS->RefEdge(nE));
487 aPaveSet.Append(aPave);
492 //=======================================================================
493 // function:EFNewVertices
495 //=======================================================================
496 void NMTTools_PaveFiller::EFNewVertices (const TopoDS_Vertex& aNewVertex,
497 const BooleanOperations_IndexedDataMapOfShapeInteger& aMapVI)
499 Standard_Integer i, aNewShape, nE, nF;
502 BooleanOperations_AncestorsSeqAndSuccessorsSeq anASSeq;
504 BOPTools_CArray1OfESInterference& aEFs=myIntrPool->ESInterferences();
506 // Insert New Vertex in DS;
507 myDS->InsertShapeAndAncestorsSuccessors(aNewVertex, anASSeq);
508 aNewShape=myDS->NumberOfInsertedShapes();
509 myDS->SetState (aNewShape, BooleanOperations_ON);
510 // Insert New Vertex in EFInterference
511 i=aMapVI.FindFromKey(aNewVertex);
512 BOPTools_ESInterference& aEFInterf= aEFs(i);
513 aEFInterf.SetNewShape(aNewShape);
514 // Extract interference info
515 aEFInterf.Indices(nE, nF);
517 const IntTools_CommonPrt& aCPart=aEFInterf.CommonPrt();
518 VertexParameter(aCPart, aT);
521 aPave.SetInterference(i);
522 aPave.SetType (BooleanOperations_EdgeSurface);
523 aPave.SetIndex(aNewShape);
525 // Append the Pave to the myPavePoolNew
526 BOPTools_PaveSet& aPaveSet=myPavePoolNew(myDS->RefEdge(nE));
527 aPaveSet.Append(aPave);
530 //=======================================================================
531 // function: CheckFacePaves
533 //=======================================================================
534 Standard_Integer NMTTools_PaveFiller::CheckFacePaves (const TopoDS_Vertex& aNewVertex,
535 const Standard_Integer nF)
537 Standard_Integer nEF, nVF, iFlag, i, aNbV;
538 BOPTools_ListIteratorOfListOfPave anIt;
539 TColStd_IndexedMapOfInteger aMVF;
541 BooleanOperations_OnceExplorer aExp(*myDS);
543 aExp.Init(nF, TopAbs_EDGE);
544 for (; aExp.More(); aExp.Next()) {
546 BOPTools_PaveSet& aPaveSet=myPavePool(myDS->RefEdge(nEF));
547 const BOPTools_ListOfPave& aLP=aPaveSet.Set();
548 anIt.Initialize(aLP);
549 for (; anIt.More(); anIt.Next()) {
550 const BOPTools_Pave& aPave=anIt.Value();
557 for (i=1; i<=aNbV; ++i) {
559 const TopoDS_Vertex& aVF=TopoDS::Vertex(myDS->Shape(nVF));
560 iFlag=IntTools_Tools::ComputeVV(aNewVertex, aVF);
569 //=======================================================================
570 // function: VertexParameter
572 //=======================================================================
573 void VertexParameter(const IntTools_CommonPrt& aCPart,
576 const IntTools_Range& aR=aCPart.Range1();
577 aT=0.5*(aR.First()+aR.Last());
579 if((aCPart.VertexParameter1() >= aR.First()) &&
580 (aCPart.VertexParameter1() <= aR.Last())) {
581 aT = aCPart.VertexParameter1();
584 //=======================================================================
585 // function: IsOnPave
587 //=======================================================================
588 Standard_Boolean IsOnPave(const Standard_Real& aTR,
589 const IntTools_Range& aCPRange,
590 const Standard_Real& aTolerance)
592 Standard_Boolean bIsOnPave;
593 Standard_Real aT1, aT2, dT1, dT2;
595 aT1=aCPRange.First();
597 bIsOnPave=(aTR>=aT1 && aTR<=aT1);
603 bIsOnPave=(dT1<=aTolerance || dT2<=aTolerance);