0028259: Method MakeBlocksCnx is duplicated in two different places in BOPAlgo
authoremv <emv@opencascade.com>
Sat, 29 Apr 2017 22:09:36 +0000 (01:09 +0300)
committerbugmaster <bugmaster@opencascade.com>
Thu, 1 Jun 2017 07:20:25 +0000 (10:20 +0300)
The methods BOPAlgo_Tools::MakeBlocksCnx(), BOPAlgo_Tools::MakeBlocks() and static method MakeBlocksCnx in BOPAlgo_Builder_2.cxx have been replaced with the new template method BOPAlgo_Tools::MakeBlocks(). The blocks of connected elements are now stored into the list of list instead of data map.
All methods BOPAlgo_Tools::FillMap() have been replaced with the new template method BOPAlgo_Tools::FillMap().

Making the Pave Block with the smallest index of original edge to be the first in the Common Block (i.e. the representing Pave Block).

The following improvements have been made in Boolean Operations algorithm to avoid regressions:
- When updating the existing common block update its pave blocks in a way that the parameters of the paves should be valid for the original edge (bugs/modalg_5/bug24809);
- When trying to reduce the tolerance of the section edge check the tolerance of all Face/Face interferences that created this edge (boolean/volumemaker/C4,D2);
- Avoid producing the different Pave Blocks for the same section edge (boolean/volumemaker/D6);

Adjustment of the test cases.

22 files changed:
dox/dev_guides/upgrade/upgrade.md
src/BOPAlgo/BOPAlgo_Builder_2.cxx
src/BOPAlgo/BOPAlgo_PaveFiller_1.cxx
src/BOPAlgo/BOPAlgo_PaveFiller_10.cxx
src/BOPAlgo/BOPAlgo_PaveFiller_3.cxx
src/BOPAlgo/BOPAlgo_PaveFiller_6.cxx
src/BOPAlgo/BOPAlgo_PaveFiller_7.cxx
src/BOPAlgo/BOPAlgo_Tools.cxx
src/BOPAlgo/BOPAlgo_Tools.hxx
src/BOPDS/BOPDS_CommonBlock.cxx
src/BOPDS/BOPDS_CommonBlock.hxx
src/BOPDS/BOPDS_DS.cxx
src/BOPDS/BOPDS_DS.hxx
src/BOPDS/BOPDS_IndexedDataMapOfPaveBlockListOfInteger.hxx
src/BOPTools/BOPTools_AlgoTools.cxx
src/BRepOffset/BRepOffset_Inter3d.cxx
src/BRepOffset/BRepOffset_MakeOffset.cxx
src/BRepOffset/BRepOffset_MakeOffset_1.cxx
tests/bugs/modalg_5/bug25721
tests/bugs/modalg_6/bug26954_3
tests/bugs/modalg_6/bug27383_1
tests/offset/shape_type_i_c/XC1

index b998024..f26694e 100644 (file)
@@ -1246,8 +1246,15 @@ In most cases this change should be transparent, however applications implementi
 * Types GeomPlate_Array1OfHCurveOnSurface and GeomPlate_HArray1OfHCurveOnSurface have been replaced with GeomPlate_Array1OfHCurve and GeomPlate_HArray1OfHCurve correspondingly (accept base class Adaptor3d_HCurve instead of Adaptor3d_HCurveOnSurface).
 * Enumeration *Image_PixMap::ImgFormat*, previously declared as nested enumeration within class *Image_PixMap*, has been moved to global namespace as *Image_Format* following OCCT coding rules.
   The enumeration values have suffix Image_Format_ and preserve previous name scheme for easy renaming of old values - e.g. Image_PixMap::ImgGray become Image_Format_Gray.
+<<<<<<< HEAD
   Old definitions are preserved as depreacated aliases to the new ones;
 * The method BOPAlgo_Builder::Origins() returns BOPCol_DataMapOfShapeListOfShape instead of BOPCol_DataMapOfShapeShape.
+=======
+  Old definitions are preserved as depreacated aliases to the new ones.
+* The methods BOPDS_DS::IsToSort(const Handle(BOPDS_CommonBlock)&, Standard_Integer&) and BOPDS_DS::SortPaveBlocks(const Handle(BOPDS_CommonBlock)&) have been removed. The sorting is now performed during the addition of the Pave Blocks into Common Block.
+* The methods BOPAlgo_Tools::MakeBlocks() and BOPAlgo_Tools::MakeBlocksCnx() have been replaced with the single template method BOPAlgo_Tools::MakeBlocks(). The chains of connected elements are now stored into the list of list instead of data map.
+* The methods BOPAlgo_Tools::FillMap() have been replaced with the single template method BOPAlgo_Tools::FillMap().
+>>>>>>> 648fab3... 0028259: Method MakeBlocksCnx is duplicated in two different places in BOPAlgo
 
 @subsection upgrade_720_BOP_DataStructure BOP - Pairs of interfering indices
 
index cd79f01..54ed083 100644 (file)
@@ -19,6 +19,7 @@
 #include <BOPAlgo_Builder.hxx>
 #include <BOPAlgo_BuilderFace.hxx>
 #include <BOPAlgo_PaveFiller.hxx>
+#include <BOPAlgo_Tools.hxx>
 #include <BOPCol_DataMapOfIntegerListOfShape.hxx>
 #include <BOPCol_DataMapOfShapeShape.hxx>
 #include <BOPCol_ListOfInteger.hxx>
 static
   Standard_Boolean HasPaveBlocksOnIn(const BOPDS_FaceInfo& aFI1,
                                      const BOPDS_FaceInfo& aFI2);
-static
-  void FillMap(const TopoDS_Shape& aS1,
-               const TopoDS_Shape& aS2,
-               BOPCol_IndexedDataMapOfShapeListOfShape& aDMSLS,
-               Handle(NCollection_BaseAllocator)& aAllocator);
-static
-  void MakeBlocksCnx(const BOPCol_IndexedDataMapOfShapeListOfShape& aMILI,
-                     BOPCol_DataMapOfIntegerListOfShape& aMBlocks,
-                     Handle(NCollection_BaseAllocator)& aAllocator);
 //
 typedef BOPCol_NCVector<TopoDS_Shape> BOPAlgo_VectorOfShape;
 //
@@ -475,7 +467,7 @@ void BOPAlgo_Builder::BuildSplitFaces()
 void BOPAlgo_Builder::FillSameDomainFaces()
 {
   Standard_Boolean bFlag;
-  Standard_Integer i, j, k, aNbFFs, nF1, nF2, aNbS;
+  Standard_Integer i, j, k, aNbFFs, nF1, nF2;
   Handle(NCollection_BaseAllocator) aAllocator;
   BOPCol_ListIteratorOfListOfShape aItF;
   BOPCol_MapOfShape aMFence;
@@ -605,7 +597,7 @@ void BOPAlgo_Builder::FillSameDomainFaces()
   aAllocator=
     NCollection_BaseAllocator::CommonBaseAllocator();
   BOPCol_IndexedDataMapOfShapeListOfShape aDMSLS(100, aAllocator);
-  BOPCol_DataMapOfIntegerListOfShape aMBlocks(100, aAllocator);
+  NCollection_List<BOPCol_ListOfShape> aMBlocks(aAllocator);
   //
   aNbVPSB=aVPSB.Extent();
   for (i=0; i<aNbVPSB; ++i) {
@@ -614,21 +606,18 @@ void BOPAlgo_Builder::FillSameDomainFaces()
     if (bFlagSD) {
       const TopoDS_Shape& aFj=aPSB.Shape1();
       const TopoDS_Shape& aFk=aPSB.Shape2();
-      FillMap(aFj, aFk, aDMSLS, aAllocator);
+      BOPAlgo_Tools::FillMap<TopoDS_Shape, TopTools_ShapeMapHasher>(aFj, aFk, aDMSLS, aAllocator);
     }
   }
   aVPSB.Clear();
   //
   // 2. Make blocks
-  MakeBlocksCnx(aDMSLS, aMBlocks, aAllocator);
+  BOPAlgo_Tools::MakeBlocks<TopoDS_Shape, TopTools_ShapeMapHasher>(aDMSLS, aMBlocks, aAllocator);
   //
   // 3. Fill same domain faces map -> aMSDF
-  aNbS = aMBlocks.Extent();
-  for (i=0; i<aNbS; ++i) {
-    const BOPCol_ListOfShape& aLSD=aMBlocks.Find(i);
-    if (aLSD.IsEmpty()) {
-      continue;
-    }
+  NCollection_List<BOPCol_ListOfShape>::Iterator aItB(aMBlocks);
+  for (; aItB.More(); aItB.Next()) {
+    const BOPCol_ListOfShape& aLSD = aItB.Value();
     //
     const TopoDS_Shape& aFSD1=aLSD.First();
     aItF.Initialize(aLSD);
@@ -753,116 +742,6 @@ void BOPAlgo_Builder::FillImagesFaces1()
   }
 }
 //=======================================================================
-//function : MakeBlocksCnx
-//purpose  : 
-//=======================================================================
-void MakeBlocksCnx(const BOPCol_IndexedDataMapOfShapeListOfShape& aMILI,
-                   BOPCol_DataMapOfIntegerListOfShape& aMBlocks,
-                   Handle(NCollection_BaseAllocator)& aAllocator)
-{
-  Standard_Integer aNbV, aNbVS, aNbVP, aNbEC, k, i, j;
-  BOPCol_ListIteratorOfListOfShape aItLI;
-  //
-  BOPCol_MapOfShape aMVS(100, aAllocator);
-  BOPCol_IndexedMapOfShape aMEC(100, aAllocator);
-  BOPCol_IndexedMapOfShape aMVP(100, aAllocator);
-  BOPCol_IndexedMapOfShape aMVAdd(100, aAllocator);
-  //
-  aNbV=aMILI.Extent();
-  //
-  for (k=0,i=1; i<=aNbV; ++i) {
-    aNbVS=aMVS.Extent();
-    if (aNbVS==aNbV) {
-      break;
-    }
-    //
-    const TopoDS_Shape& nV=aMILI.FindKey(i);
-    if (aMVS.Contains(nV)){
-      continue;
-    }
-    aMVS.Add(nV);
-    //
-    aMEC.Clear();
-    aMVP.Clear();
-    aMVAdd.Clear();
-    //
-    aMVP.Add(nV);
-    for(;;) {
-      aNbVP=aMVP.Extent();
-      for (j=1; j<=aNbVP; ++j) {
-        const TopoDS_Shape& nVP=aMVP(j);
-        const BOPCol_ListOfShape& aLV=aMILI.FindFromKey(nVP);
-        aItLI.Initialize(aLV);
-        for (; aItLI.More(); aItLI.Next()) {
-          const TopoDS_Shape& nVx=aItLI.Value();
-          if (aMEC.Contains(nVx)) {
-            continue;
-          }
-          //
-          aMVS.Add(nVx);
-          aMEC.Add(nVx);
-          aMVAdd.Add(nVx);
-        }
-      }
-      //
-      aNbVP=aMVAdd.Extent();
-      if (!aNbVP) {
-        break; // from while(1)
-      }
-      //
-      aMVP.Clear();
-      for (j=1; j<=aNbVP; ++j) {
-        aMVP.Add(aMVAdd(j));
-      }
-      aMVAdd.Clear();
-    }//while(1) {
-    //
-    BOPCol_ListOfShape aLIx(aAllocator);
-    //
-    aNbEC = aMEC.Extent();
-    for (j=1; j<=aNbEC; ++j) {
-      const TopoDS_Shape& nVx=aMEC(j);
-      aLIx.Append(nVx);
-    }
-    //
-    aMBlocks.Bind(k, aLIx);
-    ++k;
-  }//for (k=0,i=1; i<=aNbV; ++i)
-  aMVAdd.Clear();
-  aMVP.Clear();
-  aMEC.Clear();
-  aMVS.Clear();
-}
-//=======================================================================
-//function : FillMap
-//purpose  : 
-//=======================================================================
-void FillMap(const TopoDS_Shape& aS1,
-             const TopoDS_Shape& aS2,
-             BOPCol_IndexedDataMapOfShapeListOfShape& aDMSLS,
-             Handle(NCollection_BaseAllocator)& aAllocator)
-{
-  if (aDMSLS.Contains(aS1)) {
-    BOPCol_ListOfShape& aLS=aDMSLS.ChangeFromKey(aS1);
-    aLS.Append(aS2);
-  }
-  else {
-    BOPCol_ListOfShape aLS(aAllocator);
-    aLS.Append(aS2);
-    aDMSLS.Add(aS1, aLS);
-  }
-  //
-  if (aDMSLS.Contains(aS2)) {
-    BOPCol_ListOfShape& aLS=aDMSLS.ChangeFromKey(aS2);
-    aLS.Append(aS1);
-  }
-  else {
-    BOPCol_ListOfShape aLS(aAllocator);
-    aLS.Append(aS1);
-    aDMSLS.Add(aS2, aLS);
-  }
-}
-//=======================================================================
 //function :HasPaveBlocksOnIn
 //purpose  : 
 //=======================================================================
@@ -897,22 +776,3 @@ Standard_Boolean HasPaveBlocksOnIn(const BOPDS_FaceInfo& aFI1,
   }
   return bRet;
 }
-
-/*
-//DEBf
-    {
-      TopoDS_Compound aCx;
-      BRep_Builder aBBx;
-      BOPCol_ListIteratorOfListOfShape aItx;
-      //
-      aBBx.MakeCompound(aCx);
-      aBBx.Add(aCx, aFF);
-      aItx.Initialize(aLE);
-      for (; aItx.More(); aItx.Next()) {
-      const TopoDS_Shape& aEx=aItx.Value();
-      aBBx.Add(aCx, aEx);
-      }
-      int a=0;
-    }
-    //DEBt
-*/
index 7cb90da..68f1214 100644 (file)
@@ -22,6 +22,7 @@
 #include <BOPAlgo_Tools.hxx>
 #include <BOPCol_DataMapOfIntegerInteger.hxx>
 #include <BOPCol_DataMapOfIntegerListOfInteger.hxx>
+#include <BOPCol_IndexedDataMapOfIntegerListOfInteger.hxx>
 #include <BOPCol_ListOfShape.hxx>
 #include <BOPCol_MapOfInteger.hxx>
 #include <BOPDS_Curve.hxx>
@@ -48,7 +49,7 @@
 //=======================================================================
 void BOPAlgo_PaveFiller::PerformVV() 
 {
-  Standard_Integer n1, n2, iFlag, aSize, k, aNbBlocks;
+  Standard_Integer n1, n2, iFlag, aSize;
   Handle(NCollection_BaseAllocator) aAllocator;
   //
   myErrorStatus=0;
@@ -66,7 +67,7 @@ void BOPAlgo_PaveFiller::PerformVV()
   aAllocator=
     NCollection_BaseAllocator::CommonBaseAllocator();
   BOPCol_IndexedDataMapOfIntegerListOfInteger aMILI(100, aAllocator);
-  BOPCol_DataMapOfIntegerListOfInteger aMBlocks(100, aAllocator);
+  NCollection_List<BOPCol_ListOfInteger> aMBlocks(aAllocator);
   //
   // 1. Map V/LV
   for (; myIterator->More(); myIterator->Next()) {
@@ -77,18 +78,17 @@ void BOPAlgo_PaveFiller::PerformVV()
     //
     iFlag=BOPTools_AlgoTools::ComputeVV(aV1, aV2, myFuzzyValue);
     if (!iFlag) {
-      BOPAlgo_Tools::FillMap(n1, n2, aMILI, aAllocator);
+      BOPAlgo_Tools::FillMap<Standard_Integer, TColStd_MapIntegerHasher>(n1, n2, aMILI, aAllocator);
     }
   } 
   //
   // 2. Make blocks
-  BOPAlgo_Tools::MakeBlocksCnx(aMILI, aMBlocks, aAllocator);
+  BOPAlgo_Tools::MakeBlocks<Standard_Integer, TColStd_MapIntegerHasher>(aMILI, aMBlocks, aAllocator);
   //
   // 3. Make vertices
-  aNbBlocks=aMBlocks.Extent();
-  for (k=0; k<aNbBlocks; ++k) {
-    const BOPCol_ListOfInteger& aLI=aMBlocks.Find(k);
-    //
+  NCollection_List<BOPCol_ListOfInteger>::Iterator aItB(aMBlocks);
+  for (; aItB.More(); aItB.Next()) {
+    const BOPCol_ListOfInteger& aLI = aItB.Value();
     MakeSDVertices(aLI);
   }
   //
index 742155a..37b683b 100644 (file)
@@ -220,7 +220,6 @@ void BOPAlgo_PaveFiller::UpdateCommonBlocksWithSDVertices()
       }
       //
       if (aMCB.Add(aCB)) {
-        myDS->SortPaveBlocks(aCB);
         aPB->Indices(nV1, nV2);
         UpdateVertex(nV1, aTolV);
         UpdateVertex(nV2, aTolV);
index 9970247..d46bc08 100644 (file)
@@ -632,7 +632,7 @@ void BOPAlgo_PaveFiller::PerformEE()
           // 2
           myDS->AddInterf(nE1, nE2);
           //
-          BOPAlgo_Tools::FillMap(aPB1, aPB2, aMPBLPB, aAllocator);
+          BOPAlgo_Tools::FillMap<Handle(BOPDS_PaveBlock), TColStd_MapTransientHasher>(aPB1, aPB2, aMPBLPB, aAllocator);
         }//case TopAbs_EDGE
           break;
         default:
index d35a331..a092485 100644 (file)
@@ -844,6 +844,15 @@ Standard_Integer BOPAlgo_PaveFiller::PostTreatFF
   }
   aPDS=aPF.PDS();
   //
+  // Map to store the real tolerance of the common block
+  // and avoid repeated computation of it
+  NCollection_DataMap<Handle(BOPDS_CommonBlock),
+                      Standard_Real,
+                      TColStd_MapTransientHasher> aMCBTol;
+  // Map to avoid creation of different pave blocks for
+  // the same intersection edge
+  NCollection_DataMap<Standard_Integer, Handle(BOPDS_PaveBlock)> aMEPB;
+  //
   aItLS.Initialize(aLS);
   for (; aItLS.More(); aItLS.Next()) {
     const TopoDS_Shape& aSx=aItLS.Value();
@@ -982,37 +991,46 @@ Standard_Integer BOPAlgo_PaveFiller::PostTreatFF
             // add edge
             aE=aPDS->Shape(aPBRx->Edge());
             iE = myDS->Index(aE);
-            //
             if (iE < 0) {
               aSI.SetShapeType(aType);
               aSI.SetShape(aE);
               iE=myDS->Append(aSI);
-              // update real edge tolerance according to distances in common block if any
-              if (aPDS->IsCommonBlock(aPBRx)) {
-                const Handle(BOPDS_CommonBlock)& aCB = aPDS->CommonBlock(aPBRx);
+            }
+            //
+            // update real edge tolerance according to distances in common block if any
+            if (aPDS->IsCommonBlock(aPBRx)) {
+              const Handle(BOPDS_CommonBlock)& aCB = aPDS->CommonBlock(aPBRx);
+              Standard_Real *pTol = aMCBTol.ChangeSeek(aCB);
+              if (!pTol) {
                 Standard_Real aTol = BOPAlgo_Tools::ComputeToleranceOfCB(aCB, aPDS, aPF.Context());
-                if (aNC.Tolerance() < aTol) {
-                  aNC.SetTolerance(aTol);
-                }
+                pTol = aMCBTol.Bound(aCB, aTol);
+              }
+              //
+              if (aNC.Tolerance() < *pTol) {
+                aNC.SetTolerance(*pTol);
               }
             }
             // append new PaveBlock to aLPBC
-            Handle(BOPDS_PaveBlock) aPBC=new BOPDS_PaveBlock();
-            BOPDS_Pave aPaveR1, aPaveR2;
-            aPaveR1 = aPBRx->Pave1();
-            aPaveR2 = aPBRx->Pave2();
-            aPaveR1.SetIndex(myDS->Index(aPDS->Shape(aPaveR1.Index())));
-            aPaveR2.SetIndex(myDS->Index(aPDS->Shape(aPaveR2.Index())));
+            Handle(BOPDS_PaveBlock) *pPBC = aMEPB.ChangeSeek(iE);
+            if (!pPBC) {
+              pPBC = aMEPB.Bound(iE, new BOPDS_PaveBlock());
+              BOPDS_Pave aPaveR1, aPaveR2;
+              aPaveR1 = aPBRx->Pave1();
+              aPaveR2 = aPBRx->Pave2();
+              aPaveR1.SetIndex(myDS->Index(aPDS->Shape(aPaveR1.Index())));
+              aPaveR2.SetIndex(myDS->Index(aPDS->Shape(aPaveR2.Index())));
+              //
+              (*pPBC)->SetPave1(aPaveR1);
+              (*pPBC)->SetPave2(aPaveR2);
+              (*pPBC)->SetEdge(iE);
+            }
             //
-            aPBC->SetPave1(aPaveR1);
-            aPBC->SetPave2(aPaveR2);
-            aPBC->SetEdge(iE);
             if (bOld) {
-              aPBC->SetOriginalEdge(aPB1->OriginalEdge());
-              aDMExEdges.ChangeFind(aPB1).Append(aPBC);
+              (*pPBC)->SetOriginalEdge(aPB1->OriginalEdge());
+              aDMExEdges.ChangeFind(aPB1).Append(*pPBC);
             }
             else {
-              aLPBC.Append(aPBC);
+              aLPBC.Append(*pPBC);
             }
           }
         }
@@ -2228,12 +2246,13 @@ void BOPAlgo_PaveFiller::UpdateExistingPaveBlocks
   //
   // 2. Update pave blocks
   if (bCB) {
-    //create new common blocks
+    // Create new common blocks
     BOPDS_ListOfPaveBlock aLPBNew;
     const BOPCol_ListOfInteger& aFaces = aCB1->Faces();
     aIt.Initialize(aLPB);
     for (; aIt.More(); aIt.Next()) {
       const Handle(BOPDS_PaveBlock)& aPBValue = aIt.Value();
+      BOPDS_Pave aPBValuePaves[2] = {aPBValue->Pave1(), aPBValue->Pave2()};
       //
       aCB = new BOPDS_CommonBlock;
       aIt1.Initialize(aLPB1);
@@ -2241,9 +2260,60 @@ void BOPAlgo_PaveFiller::UpdateExistingPaveBlocks
         aPB2 = aIt1.Value();
         nE = aPB2->OriginalEdge();
         //
+        // Create new pave block
         aPB2n = new BOPDS_PaveBlock;
-        aPB2n->SetPave1(aPBValue->Pave1());
-        aPB2n->SetPave2(aPBValue->Pave2());
+        if (aPBValue->OriginalEdge() == nE) {
+          aPB2n->SetPave1(aPBValuePaves[0]);
+          aPB2n->SetPave2(aPBValuePaves[1]);
+        }
+        else {
+          // For the different original edge compute the parameters of paves
+          BOPDS_Pave aPave[2];
+          for (Standard_Integer i = 0; i < 2; ++i) {
+            Standard_Integer nV = aPBValuePaves[i].Index();
+            aPave[i].SetIndex(nV);
+            if (nV == aPB2->Pave1().Index()) {
+              aPave[i].SetParameter(aPB2->Pave1().Parameter());
+            }
+            else if (nV == aPB2->Pave2().Index()) {
+              aPave[i].SetParameter(aPB2->Pave2().Parameter());
+            }
+            else {
+              // Compute the parameter by projecting the point
+              const TopoDS_Vertex& aV = TopoDS::Vertex(myDS->Shape(nV));
+              const TopoDS_Edge& aEOr = TopoDS::Edge(myDS->Shape(nE));
+              Standard_Real aTOut, aDist;
+              Standard_Integer iErr = myContext->ComputeVE(aV, aEOr, aTOut, aDist, myFuzzyValue);
+              if (!iErr) {
+                aPave[i].SetParameter(aTOut);
+              }
+              else {
+                // Unable to project - set the parameter of the closest boundary
+                const TopoDS_Vertex& aV1 = TopoDS::Vertex(myDS->Shape(aPB2->Pave1().Index()));
+                const TopoDS_Vertex& aV2 = TopoDS::Vertex(myDS->Shape(aPB2->Pave2().Index()));
+                //
+                gp_Pnt aP = BRep_Tool::Pnt(aV);
+                gp_Pnt aP1 = BRep_Tool::Pnt(aV1);
+                gp_Pnt aP2 = BRep_Tool::Pnt(aV2);
+                //
+                Standard_Real aDist1 = aP.SquareDistance(aP1);
+                Standard_Real aDist2 = aP.SquareDistance(aP2);
+                //
+                aPave[i].SetParameter(aDist1 < aDist2 ? aPB2->Pave1().Parameter() : aPB2->Pave2().Parameter());
+              }
+            }
+          }
+          //
+          if (aPave[1].Parameter() < aPave[0].Parameter()) {
+            BOPDS_Pave aPaveTmp = aPave[0];
+            aPave[0] = aPave[1];
+            aPave[1] = aPaveTmp;
+          }
+          //
+          aPB2n->SetPave1(aPave[0]);
+          aPB2n->SetPave2(aPave[1]);
+        }
+        //
         aPB2n->SetEdge(aPBValue->Edge());
         aPB2n->SetOriginalEdge(nE);
         aCB->AddPaveBlock(aPB2n);
@@ -2251,7 +2321,6 @@ void BOPAlgo_PaveFiller::UpdateExistingPaveBlocks
         myDS->ChangePaveBlocks(nE).Append(aPB2n);
       }
       aCB->SetFaces(aFaces);
-      myDS->SortPaveBlocks(aCB);
       //
       const Handle(BOPDS_PaveBlock)& aPBNew = aCB->PaveBlocks().First();
       aLPBNew.Append(aPBNew);
@@ -2788,6 +2857,8 @@ void BOPAlgo_PaveFiller::CorrectToleranceOfSE()
   BOPDS_VectorOfInterfFF& aFFs = myDS->InterfFF();
   NCollection_IndexedDataMap<Standard_Integer,BOPDS_ListOfPaveBlock> aMVIPBs;
   BOPCol_MapOfInteger aMVIToReduce;
+  // Fence map to avoid repeated checking of the same edge
+  BOPDS_MapOfPaveBlock aMPB;
   //
   // 1. iterate on all sections F-F
   Standard_Integer aNb = aFFs.Extent(), i;
@@ -2808,6 +2879,11 @@ void BOPAlgo_PaveFiller::CorrectToleranceOfSE()
           continue;
         }
         //
+        if (!aMPB.Add(aPB)) {
+          aItLPB.Next();
+          continue;
+        }
+        //
         Standard_Boolean bIsReduced = Standard_False;
         if (aPB->OriginalEdge() < 0) {
           // It is possible that due to small angle between faces the
index da5542d..a712323 100644 (file)
@@ -393,13 +393,20 @@ void BOPAlgo_PaveFiller::MakeSplitEdges()
       bCB=myDS->IsCommonBlock(aPB);
       //
       if (!(bV1 || bV2)) { // no new vertices here
-        if (!myNonDestructive || (myNonDestructive && !bCB)) {
-          nE = aPB->OriginalEdge();
-          aPB->SetEdge(nE);
-          if (!myNonDestructive && bCB) {
-            const Handle(BOPDS_CommonBlock)& aCB = myDS->CommonBlock(aPB);
-            Standard_Real aTol = BOPAlgo_Tools::ComputeToleranceOfCB(aCB, myDS, myContext);
-            myDS->UpdateEdgeTolerance(nE, aTol);
+        if (!myNonDestructive || !bCB) {
+          if (bCB) {
+            if (!aPB->HasEdge()) {
+              const Handle(BOPDS_CommonBlock)& aCB = myDS->CommonBlock(aPB);
+              nE = aCB->PaveBlock1()->OriginalEdge();
+              aCB->SetEdge(nE);
+              // Compute tolerance of the common block and update the edge
+              Standard_Real aTol = BOPAlgo_Tools::ComputeToleranceOfCB(aCB, myDS, myContext);
+              myDS->UpdateEdgeTolerance(nE, aTol);
+            }
+          }
+          else {
+            nE = aPB->OriginalEdge();
+            aPB->SetEdge(nE);
           }
           continue;
         }
@@ -418,7 +425,6 @@ void BOPAlgo_PaveFiller::MakeSplitEdges()
       const Handle(BOPDS_CommonBlock)& aCB=myDS->CommonBlock(aPB);
       bCB=!aCB.IsNull();
       if (bCB) {
-        myDS->SortPaveBlocks(aCB);
         aPB=aCB->PaveBlock1();
       }
       //
index 952b655..6b9ec2f 100644 (file)
@@ -95,143 +95,6 @@ static
                                    gp_Vec& theTangent);
 
 //=======================================================================
-//function : MakeBlocksCnx
-//purpose  : 
-//=======================================================================
-void BOPAlgo_Tools::MakeBlocksCnx(const BOPCol_IndexedDataMapOfIntegerListOfInteger& aMILI,
-                                  BOPCol_DataMapOfIntegerListOfInteger& aMBlocks,
-                                  const Handle(NCollection_BaseAllocator)& aAllocator)
-{
-  Standard_Integer aNbV, nV, aNbVS, nVP, nVx, aNbVP, aNbEC, k, i, j;
-  BOPCol_ListIteratorOfListOfInteger aItLI;
-  //
-  BOPCol_MapOfInteger aMVS(100, aAllocator);
-  BOPCol_IndexedMapOfInteger aMEC(100, aAllocator);
-  BOPCol_IndexedMapOfInteger aMVP(100, aAllocator);
-  BOPCol_IndexedMapOfInteger aMVAdd(100, aAllocator);
-  //
-  aNbV=aMILI.Extent();
-  //
-  for (k=0,i=1; i<=aNbV; ++i) {
-    aNbVS=aMVS.Extent();
-    if (aNbVS==aNbV) {
-      break;
-    }
-    //
-    nV = aMILI.FindKey(i);
-    if (aMVS.Contains(nV)){
-      continue;
-    }
-    aMVS.Add(nV);
-    //
-    aMEC.Clear();
-    aMVP.Clear();
-    aMVAdd.Clear();
-    //
-    aMVP.Add(nV);
-    for(;;) {
-      aNbVP=aMVP.Extent();
-      for (j=1; j<=aNbVP; ++j) {
-        nVP=aMVP(j);
-        const BOPCol_ListOfInteger& aLV=aMILI.FindFromKey(nVP);
-        aItLI.Initialize(aLV);
-        for (; aItLI.More(); aItLI.Next()) {
-          nVx=aItLI.Value();
-          if (aMEC.Contains(nVx)) {
-            continue;
-          }
-          //
-          aMVS.Add(nVx);
-          aMEC.Add(nVx);
-          aMVAdd.Add(nVx);
-        }
-      }
-      //
-      aNbVP=aMVAdd.Extent();
-      if (!aNbVP) {
-        break; // from while(1)
-      }
-      //
-      aMVP.Clear();
-      for (j=1; j<=aNbVP; ++j) {
-        aMVP.Add(aMVAdd(j));
-      }
-      aMVAdd.Clear();
-    }//while(1) {
-    //
-    BOPCol_ListOfInteger aLIx(aAllocator);
-    //
-    aNbEC = aMEC.Extent();
-    for (j=1; j<=aNbEC; ++j) {
-      nVx=aMEC(j);
-      aLIx.Append(nVx);
-    }
-    //
-    aMBlocks.Bind(k, aLIx);
-    ++k;
-  }//for (k=0,i=1; i<=aNbV; ++i)
-  aMVAdd.Clear();
-  aMVP.Clear();
-  aMEC.Clear();
-  aMVS.Clear();
-}
-//=======================================================================
-//function : FillMap
-//purpose  : 
-//=======================================================================
-void BOPAlgo_Tools::FillMap(const Standard_Integer n1,
-                            const Standard_Integer n2,
-                            BOPCol_IndexedDataMapOfIntegerListOfInteger& aMILI,
-                            const Handle(NCollection_BaseAllocator)& aAllocator)
-{
-  if (aMILI.Contains(n1)) {
-    BOPCol_ListOfInteger& aLI=aMILI.ChangeFromKey(n1);
-    aLI.Append(n2);
-  }
-  else {
-    BOPCol_ListOfInteger aLI(aAllocator);
-    aLI.Append(n2);
-    aMILI.Add(n1, aLI);
-  }
-  if (aMILI.Contains(n2)) {
-    BOPCol_ListOfInteger& aLI=aMILI.ChangeFromKey(n2);
-    aLI.Append(n1);
-  }
-  else {
-    BOPCol_ListOfInteger aLI(aAllocator);
-    aLI.Append(n1);
-    aMILI.Add(n2, aLI);
-  }
-}
-//=======================================================================
-//function : FillMap
-//purpose  : 
-//=======================================================================
-void BOPAlgo_Tools::FillMap(const Handle(BOPDS_PaveBlock)& aPB1,
-                            const Handle(BOPDS_PaveBlock)& aPB2,
-                            BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock& aMPBLPB,
-                            const Handle(NCollection_BaseAllocator)& aAllocator)
-{
-  if (aMPBLPB.Contains(aPB1)) {
-    BOPDS_ListOfPaveBlock& aLPB=aMPBLPB.ChangeFromKey(aPB1);
-    aLPB.Append(aPB2);
-  }
-  else {
-    BOPDS_ListOfPaveBlock aLPB(aAllocator);
-    aLPB.Append(aPB2);
-    aMPBLPB.Add(aPB1, aLPB);
-  }
-  if (aMPBLPB.Contains(aPB2)) {
-    BOPDS_ListOfPaveBlock& aLPB=aMPBLPB.ChangeFromKey(aPB2);
-    aLPB.Append(aPB1);
-  }
-  else {
-    BOPDS_ListOfPaveBlock aLPB(aAllocator);
-    aLPB.Append(aPB1);
-    aMPBLPB.Add(aPB2, aLPB);
-  }
-}
-//=======================================================================
 //function : FillMap
 //purpose  : 
 //=======================================================================
@@ -240,96 +103,11 @@ void BOPAlgo_Tools::FillMap(const Handle(BOPDS_PaveBlock)& aPB,
                             BOPDS_IndexedDataMapOfPaveBlockListOfInteger& aMPBLI,
                             const Handle(NCollection_BaseAllocator)& aAllocator)
 {
-  if (aMPBLI.Contains(aPB)) {
-    BOPCol_ListOfInteger& aLI=aMPBLI.ChangeFromKey(aPB);
-    aLI.Append(nF);
+  BOPCol_ListOfInteger *pLI = aMPBLI.ChangeSeek(aPB);
+  if (!pLI) {
+    pLI = &aMPBLI(aMPBLI.Add(aPB, BOPCol_ListOfInteger(aAllocator)));
   }
-  else {
-    BOPCol_ListOfInteger aLI(aAllocator);
-    aLI.Append(nF);
-    aMPBLI.Add(aPB, aLI);
-  }
-}
-//=======================================================================
-//function : MakeBlocks
-//purpose  : 
-//=======================================================================
-void BOPAlgo_Tools::MakeBlocks(const BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock& aMILI,
-                               BOPDS_DataMapOfIntegerListOfPaveBlock& aMBlocks,
-                               const Handle(NCollection_BaseAllocator)& aAllocator)
-{
-  Standard_Integer aNbV,  aNbVS, aNbVP, aNbEC, k, i, j;
-  BOPDS_ListIteratorOfListOfPaveBlock aItLI;
-  //
-  BOPDS_MapOfPaveBlock aMVS(100, aAllocator);
-  BOPDS_IndexedMapOfPaveBlock aMEC(100, aAllocator);
-  BOPDS_IndexedMapOfPaveBlock aMVP(100, aAllocator);
-  BOPDS_IndexedMapOfPaveBlock aMVAdd(100, aAllocator);
-  //
-  aNbV=aMILI.Extent();
-  //
-  for (k=0, i=1; i<=aNbV; ++i) {
-    aNbVS=aMVS.Extent();
-    if (aNbVS==aNbV) {
-      break;
-    }
-    //
-    const Handle(BOPDS_PaveBlock)& nV=aMILI.FindKey(i);
-    if (aMVS.Contains(nV)){
-      continue;
-    }
-    aMVS.Add(nV);
-    //
-    aMEC.Clear();
-    aMVP.Clear();
-    aMVAdd.Clear();
-    //
-    aMVP.Add(nV);
-    for(;;) {
-      aNbVP=aMVP.Extent();
-      for (j=1; j<=aNbVP; ++j) {
-        const Handle(BOPDS_PaveBlock)& nVP=aMVP(j);
-        const BOPDS_ListOfPaveBlock& aLV=aMILI.FindFromKey(nVP);
-        aItLI.Initialize(aLV);
-        for (; aItLI.More(); aItLI.Next()) {
-          const Handle(BOPDS_PaveBlock)& nVx=aItLI.Value();
-          if (aMEC.Contains(nVx)) {
-            continue;
-          }
-          //
-          aMVS.Add(nVx);
-          aMEC.Add(nVx);
-          aMVAdd.Add(nVx);
-        }
-      }
-      //
-      aNbVP=aMVAdd.Extent();
-      if (!aNbVP) {
-        break; // from while(1)
-      }
-      //
-      aMVP.Clear();
-      for (j=1; j<=aNbVP; ++j) {
-        aMVP.Add(aMVAdd(j));
-      }
-      aMVAdd.Clear();
-    }//while(1) {
-    //
-    BOPDS_ListOfPaveBlock aLIx(aAllocator);
-    //
-    aNbEC = aMEC.Extent();
-    for (j=1; j<=aNbEC; ++j) {
-      const Handle(BOPDS_PaveBlock)& nVx=aMEC(j);
-      aLIx.Append(nVx);
-    }
-    //
-    aMBlocks.Bind(k, aLIx);
-    ++k;
-  }//for (k=0, i=1; i<=aNbV; ++i)
-  aMVAdd.Clear();
-  aMVP.Clear();
-  aMEC.Clear();
-  aMVS.Clear();
+  pLI->Append(nF);
 }
 //=======================================================================
 //function : PerformCommonBlocks
@@ -346,30 +124,22 @@ void BOPAlgo_Tools::PerformCommonBlocks(BOPDS_IndexedDataMapOfPaveBlockListOfPav
     return;
   }
   //
-  Standard_Integer aNbPB, aNbBlocks, k;
-  BOPDS_ListIteratorOfListOfPaveBlock aItLPB;
   Handle(BOPDS_CommonBlock) aCB;
-  BOPDS_DataMapOfIntegerListOfPaveBlock aMBlocks(100, aAllocator);
+  NCollection_List<BOPDS_ListOfPaveBlock> aMBlocks(aAllocator);
   //
-  BOPAlgo_Tools::MakeBlocks(aMPBLPB, aMBlocks, aAllocator);
+  BOPAlgo_Tools::MakeBlocks<Handle(BOPDS_PaveBlock), TColStd_MapTransientHasher>(aMPBLPB, aMBlocks, aAllocator);
   //
-  aNbBlocks = aMBlocks.Extent();
-  for (k=0; k<aNbBlocks; ++k) {
-    const BOPDS_ListOfPaveBlock& aLPB=aMBlocks.Find(k);
-    aNbPB=aLPB.Extent();
+  NCollection_List<BOPDS_ListOfPaveBlock>::Iterator aItB(aMBlocks);
+  for (; aItB.More(); aItB.Next()) {
+    const BOPDS_ListOfPaveBlock& aLPB = aItB.Value();
+    Standard_Integer aNbPB = aLPB.Extent();
     if (aNbPB>1) {
       aCB=new BOPDS_CommonBlock;
+      aCB->SetPaveBlocks(aLPB);
       //
-      aItLPB.Initialize(aLPB);
-      for (; aItLPB.More(); aItLPB.Next()) {
-        const Handle(BOPDS_PaveBlock)& aPBx=aItLPB.Value();
-        aCB->AddPaveBlock(aPBx);
-      }
-      //
-      aItLPB.Initialize(aLPB);
+      BOPDS_ListIteratorOfListOfPaveBlock aItLPB(aLPB);
       for (; aItLPB.More(); aItLPB.Next()) {
-        const Handle(BOPDS_PaveBlock)& aPBx=aItLPB.Value();
-        pDS->SetCommonBlock(aPBx, aCB);
+        pDS->SetCommonBlock(aItLPB.Value(), aCB);
       }
     }//if (aNbPB>1) {
   }
index a964ef6..b8d4949 100644 (file)
 #include <Standard_DefineAlloc.hxx>
 #include <Standard_Handle.hxx>
 
-#include <BOPCol_IndexedDataMapOfIntegerListOfInteger.hxx>
-#include <BOPCol_DataMapOfIntegerListOfInteger.hxx>
 #include <BOPCol_BaseAllocator.hxx>
+#include <BOPDS_IndexedDataMapOfPaveBlockListOfInteger.hxx>
 #include <BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock.hxx>
-#include <BOPDS_DataMapOfIntegerListOfPaveBlock.hxx>
 #include <BOPDS_PDS.hxx>
 #include <Standard_Integer.hxx>
-#include <BOPDS_IndexedDataMapOfPaveBlockListOfInteger.hxx>
 
 class BOPDS_PaveBlock;
 class BOPDS_CommonBlock;
 class IntTools_Context;
 class TopoDS_Shape;
 
-class BOPAlgo_Tools 
+class BOPAlgo_Tools
 {
 public:
 
-  DEFINE_STANDARD_ALLOC
+  //! Makes the chains of the connected elements from the given connexity map
+  template <class theType, class theTypeHasher>
+  static void MakeBlocks(const NCollection_IndexedDataMap<theType, NCollection_List<theType>, theTypeHasher>& theMILI,
+                         NCollection_List<NCollection_List<theType>>& theMBlocks,
+                         const BOPCol_BaseAllocator& theAllocator)
+  {
+    NCollection_Map<theType, theTypeHasher> aMFence;
+    Standard_Integer i, aNb = theMILI.Extent();
+    for (i = 1; i <= aNb; ++i) {
+      const theType& n = theMILI.FindKey(i);
+      if (!aMFence.Add(n))
+        continue;
+      //
+      // Start the chain
+      NCollection_List<theType>& aChain = theMBlocks.Append(NCollection_List<theType>(theAllocator));
+      aChain.Append(n);
+      // Look for connected elements
+      typename NCollection_List<theType>::Iterator aItLChain(aChain);
+      for (; aItLChain.More(); aItLChain.Next()) {
+        const theType& n1 = aItLChain.Value();
+        const NCollection_List<theType>& aLI = theMILI.FindFromKey(n1);
+        // Add connected elements into the chain
+        typename NCollection_List<theType>::Iterator aItLI(aLI);
+        for (; aItLI.More(); aItLI.Next()) {
+          const theType& n2 = aItLI.Value();
+          if (aMFence.Add(n2)) {
+            aChain.Append(n2);
+          }
+        }
+      }
+    }
+  }
 
+  //! Fills the map with the connected entities
+  template <class theType, class theTypeHasher>
+  static void FillMap(const theType& n1,
+                      const theType& n2,
+                      NCollection_IndexedDataMap<theType, NCollection_List<theType>, theTypeHasher>& theMILI,
+                      const BOPCol_BaseAllocator& theAllocator)
+  {
+    NCollection_List<theType> *pList1 = theMILI.ChangeSeek(n1);
+    if (!pList1) {
+      pList1 = &theMILI(theMILI.Add(n1, NCollection_List<theType>(theAllocator)));
+    }
+    pList1->Append(n2);
+    //
+    NCollection_List<theType> *pList2 = theMILI.ChangeSeek(n2);
+    if (!pList2) {
+      pList2 = &theMILI(theMILI.Add(n2, NCollection_List<theType>(theAllocator)));
+    }
+    pList2->Append(n1);
+  }
+
+  Standard_EXPORT static void FillMap(const Handle(BOPDS_PaveBlock)& thePB1,
+                                      const Standard_Integer theF,
+                                      BOPDS_IndexedDataMapOfPaveBlockListOfInteger& theMILI,
+                                      const BOPCol_BaseAllocator& theAllocator);
   
-  Standard_EXPORT static void MakeBlocksCnx (const BOPCol_IndexedDataMapOfIntegerListOfInteger& theMILI, BOPCol_DataMapOfIntegerListOfInteger& theMBlocks, const BOPCol_BaseAllocator& theAllocator);
-  
-  Standard_EXPORT static void MakeBlocks (const BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock& theMILI, BOPDS_DataMapOfIntegerListOfPaveBlock& theMBlocks, const BOPCol_BaseAllocator& theAllocator);
-  
-  Standard_EXPORT static void PerformCommonBlocks (BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock& theMBlocks, const BOPCol_BaseAllocator& theAllocator, BOPDS_PDS& pDS);
-  
-  Standard_EXPORT static void FillMap (const Standard_Integer tneN1, const Standard_Integer tneN2, BOPCol_IndexedDataMapOfIntegerListOfInteger& theMILI, const BOPCol_BaseAllocator& theAllocator);
-  
-  Standard_EXPORT static void FillMap (const Handle(BOPDS_PaveBlock)& tnePB1, const Handle(BOPDS_PaveBlock)& tnePB2, BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock& theMILI, const BOPCol_BaseAllocator& theAllocator);
-  
-  Standard_EXPORT static void FillMap (const Handle(BOPDS_PaveBlock)& tnePB1, const Standard_Integer tneF, BOPDS_IndexedDataMapOfPaveBlockListOfInteger& theMILI, const BOPCol_BaseAllocator& theAllocator);
-  
-  Standard_EXPORT static void PerformCommonBlocks (const BOPDS_IndexedDataMapOfPaveBlockListOfInteger& theMBlocks, const BOPCol_BaseAllocator& theAllocator, BOPDS_PDS& pDS);
+  Standard_EXPORT static void PerformCommonBlocks(BOPDS_IndexedDataMapOfPaveBlockListOfPaveBlock& theMBlocks,
+                                                  const BOPCol_BaseAllocator& theAllocator,
+                                                  BOPDS_PDS& theDS);
+
+  Standard_EXPORT static void PerformCommonBlocks(const BOPDS_IndexedDataMapOfPaveBlockListOfInteger& theMBlocks,
+                                                  const BOPCol_BaseAllocator& theAllocator,
+                                                  BOPDS_PDS& pDS);
 
   Standard_EXPORT static Standard_Real ComputeToleranceOfCB
                                         (const Handle(BOPDS_CommonBlock)& theCB,
index db84c3d..ebdc5f4 100644 (file)
@@ -42,15 +42,30 @@ IMPLEMENT_STANDARD_RTTIEXT(BOPDS_CommonBlock,MMgt_TShared)
 //=======================================================================
   void BOPDS_CommonBlock::AddPaveBlock(const Handle(BOPDS_PaveBlock)& aPB)
 {
-  myPaveBlocks.Append(aPB);
+  if (myPaveBlocks.IsEmpty()) {
+    myPaveBlocks.Append(aPB);
+    return;
+  }
+  //
+  // Put the pave block with the minimal index of the original edge in the first place
+  if (aPB->OriginalEdge() < myPaveBlocks.First()->OriginalEdge()) {
+    myPaveBlocks.Prepend(aPB);
+  }
+  else {
+    myPaveBlocks.Append(aPB);
+  }
 }
 //=======================================================================
-// function:  AddPaveBlocks
+// function:  SetPaveBlocks
 // purpose: 
 //=======================================================================
-  void BOPDS_CommonBlock::AddPaveBlocks(const BOPDS_ListOfPaveBlock& aLPB)
+  void BOPDS_CommonBlock::SetPaveBlocks(const BOPDS_ListOfPaveBlock& aLPB)
 {
-  myPaveBlocks=aLPB;
+  myPaveBlocks.Clear();
+  BOPDS_ListIteratorOfListOfPaveBlock aIt(aLPB);
+  for (; aIt.More(); aIt.Next()) {
+    AddPaveBlock(aIt.Value());
+  }
 }
 //=======================================================================
 // function:  PaveBlocks
index 520d5e0..9c14fb7 100644 (file)
@@ -31,11 +31,13 @@ class BOPDS_CommonBlock;
 DEFINE_STANDARD_HANDLE(BOPDS_CommonBlock, MMgt_TShared)
 
 
-//! The class BOPDS_CommonBlock is to store
-//! the information about pave blocks that have
-//! geometry coincidence (in  terms of a tolerance)  with
-//! a) other pave block(s)
-//! b) face(s)
+//! The class BOPDS_CommonBlock is to store the information
+//! about pave blocks that have geometrical coincidence
+//! (in terms of a tolerance) with:<br>
+//! a) other pave block(s);<br>
+//! b) face(s).<br>
+//! First pave block in the common block (real pave block)
+//! is always a pave block with the minimal index of the original edge.
 class BOPDS_CommonBlock : public MMgt_TShared
 {
 
@@ -62,7 +64,7 @@ public:
   //! Adds the list of pave blocks <aLPB>
   //! to the list of pave blocks
   //! of the common block
-  Standard_EXPORT void AddPaveBlocks (const BOPDS_ListOfPaveBlock& aLPB);
+  Standard_EXPORT void SetPaveBlocks (const BOPDS_ListOfPaveBlock& aLPB);
   
 
   //! Modifier
index 7cb15ce..372b499 100644 (file)
@@ -1065,7 +1065,6 @@ void BOPDS_DS::UpdateCommonBlock(const Handle(BOPDS_CommonBlock)& theCB,
     //
     while (aLPBx.Extent()) {
       Standard_Boolean bCoinside;
-      Standard_Real aTol, aTolMax(0.);
       BOPDS_ListOfPaveBlock aLPBxN;
       //
       aItPB.Initialize(aLPBx);
@@ -1075,27 +1074,12 @@ void BOPDS_DS::UpdateCommonBlock(const Handle(BOPDS_CommonBlock)& theCB,
           const Handle(BOPDS_PaveBlock)& aPBCx = aLPBxN.First();
           bCoinside = CheckCoincidence(aPBx, aPBCx, theFuzz);
           if (bCoinside) {
-            nE = aPBx->OriginalEdge();
-            const TopoDS_Edge& aE = *(TopoDS_Edge*)&Shape(nE);
-            aTol = BRep_Tool::Tolerance(aE);
-            //
-            //pave block with the max tolerance of the original edge
-            //must be the first in the common block
-            if (aTolMax < aTol) {
-              aTolMax = aTol;
-              aLPBxN.Prepend(aPBx);
-            } else {
-              aLPBxN.Append(aPBx);
-            }
+            aLPBxN.Append(aPBx);
             aLPBx.Remove(aItPB);
             continue;
           }//if (bCoinside) {
         }//if (aLPBxN.Extent()) {
         else {
-          nE = aPBx->OriginalEdge();
-          const TopoDS_Edge& aE = *(TopoDS_Edge*)&Shape(nE);
-          aTolMax = BRep_Tool::Tolerance(aE);
-          //
           aLPBxN.Append(aPBx);
           aLPBx.Remove(aItPB);
           continue;
@@ -1104,7 +1088,7 @@ void BOPDS_DS::UpdateCommonBlock(const Handle(BOPDS_CommonBlock)& theCB,
       }//for(; aItPB.More(); ) {
       //
       aCBx=new BOPDS_CommonBlock;
-      aCBx->AddPaveBlocks(aLPBxN);
+      aCBx->SetPaveBlocks(aLPBxN);
       aCBx->SetFaces(aLF);
       //
       aItPB.Initialize(aLPBxN);
@@ -1695,8 +1679,8 @@ Standard_Boolean BOPDS_DS::CheckCoincidence
   if (aNbPoints) {
     aD=aPPC.LowerDistance();
     //
-    aTol=BRep_Tool::Tolerance(aE1);
-    aTol = aTol + BRep_Tool::Tolerance(aE2) + Max(theFuzz, Precision::Confusion());
+    aTol = BRep_Tool::MaxTolerance(aE1, TopAbs_VERTEX);
+    aTol = aTol + BRep_Tool::MaxTolerance(aE2, TopAbs_VERTEX) + Max(theFuzz, Precision::Confusion());
     if (aD<aTol) {
       aT2x=aPPC.LowerDistanceParameter();
       if (aT2x>aT21 && aT2x<aT22) {
@@ -1707,82 +1691,6 @@ Standard_Boolean BOPDS_DS::CheckCoincidence
   return bRet;
 }
 //=======================================================================
-// function: SortPaveBlocks
-// purpose:
-//=======================================================================
-void BOPDS_DS::SortPaveBlocks(const Handle(BOPDS_CommonBlock)& aCB)
-{
-  Standard_Integer theI;
-  Standard_Boolean bToSort;
-  bToSort = IsToSort(aCB, theI);
-  if (!bToSort) {
-    return;
-  }
-
-  Standard_Integer i(0);
-  const BOPDS_ListOfPaveBlock& aLPB = aCB->PaveBlocks();
-  BOPDS_ListOfPaveBlock aLPBN = aLPB;
-  
-  Handle(BOPDS_PaveBlock) aPB;
-  BOPDS_ListIteratorOfListOfPaveBlock aIt;
-  //
-  aIt.Initialize(aLPBN);
-  for (aIt.Next(); aIt.More(); ) {
-    i++;
-    if(i == theI) {
-      aPB = aIt.Value();
-      aLPBN.Remove(aIt);
-      aLPBN.Prepend(aPB);
-      break;
-    }
-    aIt.Next();
-  }
-  //
-  aCB->AddPaveBlocks(aLPBN);
-}
-//=======================================================================
-// function: IsToSort
-// purpose:
-//=======================================================================
-Standard_Boolean BOPDS_DS::IsToSort
-  (const Handle(BOPDS_CommonBlock)& aCB,
-   Standard_Integer& theI)
-{
-  Standard_Boolean bRet;
-  bRet = Standard_False;
-  const BOPDS_ListOfPaveBlock& aLPB = aCB->PaveBlocks();
-  if (aLPB.Extent()==1) {
-    return bRet;
-  }
-
-  Standard_Integer nE;
-  Standard_Real aTolMax, aTol;
-  Handle(BOPDS_PaveBlock) aPB;
-  TopoDS_Edge aE;
-  BOPDS_ListIteratorOfListOfPaveBlock aIt;
-  //
-  aPB = aLPB.First();
-  nE = aPB->OriginalEdge();
-  aE = (*(TopoDS_Edge *)(&Shape(nE)));
-  aTolMax = BRep_Tool::Tolerance(aE);
-  //
-  theI = 0;
-  aIt.Initialize(aLPB);
-  for (aIt.Next(); aIt.More(); aIt.Next()) {
-    theI++;
-    aPB = aIt.Value();
-    nE = aPB->OriginalEdge();
-    aE = (*(TopoDS_Edge *)(&Shape(nE)));
-    aTol = BRep_Tool::Tolerance(aE);
-    if (aTolMax < aTol) {
-      aTolMax = aTol;
-      bRet = Standard_True;
-    }
-  }
-
-  return bRet;
-}
-//=======================================================================
 // function: IsSubShape
 // purpose:
 //=======================================================================
index 8119fac..bfdabf7 100644 (file)
@@ -436,10 +436,6 @@ Standard_EXPORT virtual ~BOPDS_DS();
   
   Standard_EXPORT void Dump() const;
   
-  Standard_EXPORT void SortPaveBlocks (const Handle(BOPDS_CommonBlock)& theCB);
-  
-  Standard_EXPORT Standard_Boolean IsToSort (const Handle(BOPDS_CommonBlock)& theCB, Standard_Integer& theI);
-  
   Standard_EXPORT Standard_Boolean IsSubShape (const Standard_Integer theI1, const Standard_Integer theI2);
   
   //! Fills theLP with sorted paves
index 01235d9..ac4f3f3 100644 (file)
@@ -18,6 +18,7 @@
 #include <NCollection_IndexedDataMap.hxx>
 #include <TColStd_MapTransientHasher.hxx>
 #include <BOPCol_ListOfInteger.hxx>
+#include <BOPDS_PaveBlock.hxx>
 
 typedef NCollection_IndexedDataMap<Handle(BOPDS_PaveBlock), BOPCol_ListOfInteger, TColStd_MapTransientHasher> BOPDS_IndexedDataMapOfPaveBlockListOfInteger; 
 
index 1ad0090..795686c 100644 (file)
@@ -118,88 +118,53 @@ static
 // function: MakeConnexityBlocks
 // purpose: 
 //=======================================================================
-void BOPTools_AlgoTools::MakeConnexityBlocks 
+void BOPTools_AlgoTools::MakeConnexityBlocks
   (const TopoDS_Shape& theS,
    const TopAbs_ShapeEnum theType1,
    const TopAbs_ShapeEnum theType2,
    BOPCol_ListOfShape& theLCB)
 {
-  Standard_Integer  aNbF, aNbAdd, aNbAdd1, i;
+  // Map shapes to find connected elements
+  BOPCol_IndexedDataMapOfShapeListOfShape aDMSLS;
+  BOPTools::MapShapesAndAncestors(theS, theType1, theType2, aDMSLS);
+  // Fence map
+  BOPCol_MapOfShape aMFence;
+  Standard_Integer i;
   BRep_Builder aBB;
-  TopoDS_Compound aC;
-  TopoDS_Iterator aIt;
-  TopExp_Explorer aExp;
-  BOPCol_MapOfShape aMP;
-  BOPCol_IndexedMapOfShape aMCB, aMAdd, aMAdd1;
-  BOPCol_IndexedDataMapOfShapeListOfShape aMEF;
-  BOPCol_ListIteratorOfListOfShape aItLF;
   //
-  // 1. aMEF
-  BOPTools::MapShapesAndAncestors(theS, theType1, theType2, aMEF);
-  //
-  // 2. aMCB
-  aIt.Initialize(theS);
-  for (; aIt.More(); aIt.Next()) {
-    const TopoDS_Shape& aF1=aIt.Value();
-    if (aMP.Contains(aF1)) {
+  TopExp_Explorer aExp(theS, theType2);
+  for (; aExp.More(); aExp.Next()) {
+    const TopoDS_Shape& aS = aExp.Current();
+    if (!aMFence.Add(aS)) {
       continue;
     }
-    //
-    aMCB.Clear();
-    aMAdd.Clear();
-    aMAdd.Add(aF1);
-    //
-    for(;;) {
-      aMAdd1.Clear();
-      //
-      aNbAdd = aMAdd.Extent();
-      for (i=1; i<=aNbAdd; ++i) {
-        const TopoDS_Shape& aF=aMAdd(i);
-        //
-        aExp.Init(aF, theType1);
-        for (; aExp.More(); aExp.Next()) {
-          const TopoDS_Shape& aE=aExp.Current();
-          //
-          const BOPCol_ListOfShape& aLF=aMEF.FindFromKey(aE);
-          aItLF.Initialize(aLF);
-          for (; aItLF.More(); aItLF.Next()) {
-            const TopoDS_Shape& aFx=aItLF.Value();
-            if (aFx.IsSame(aF)) {
-              continue;
-            }
-            if (aMCB.Contains(aFx)) {
-              continue;
-            }
-            aMAdd1.Add(aFx);
+    // The block
+    BOPCol_IndexedMapOfShape aMBlock;
+    TopoDS_Compound aBlock;
+    aBB.MakeCompound(aBlock);
+    // Start the block
+    aMBlock.Add(aS);
+    aBB.Add(aBlock, aS);
+    // Look for connected parts
+    for (i = 1; i <= aMBlock.Extent(); ++i) {
+      const TopoDS_Shape& aS1 = aMBlock(i);
+      TopExp_Explorer aExpSS(aS1, theType1);
+      for (; aExpSS.More(); aExpSS.Next()) {
+        const TopoDS_Shape& aSubS = aExpSS.Current();
+        const BOPCol_ListOfShape& aLS = aDMSLS.FindFromKey(aSubS);
+        BOPCol_ListIteratorOfListOfShape aItLS(aLS);
+        for (; aItLS.More(); aItLS.Next()) {
+          const TopoDS_Shape& aS2 = aItLS.Value();
+          if (aMFence.Add(aS2)) {
+            aMBlock.Add(aS2);
+            aBB.Add(aBlock, aS2);
           }
-        }//for (; aExp.More(); aExp.Next()){
-        aMCB.Add(aF);
-      }// for (i=1; i<=aNbAdd; ++i) {
-      //
-      aNbAdd1=aMAdd1.Extent();
-      if (!aNbAdd1) {
-        break;// ->make new CB from aMCB
-      }
-      //
-      aMAdd.Clear();
-      for (i=1; i<=aNbAdd1; ++i) {
-        const TopoDS_Shape& aFAdd = aMAdd1(i);
-        aMAdd.Add(aFAdd);
-      }
-    }//while(1) {
-    //
-    aNbF=aMCB.Extent();
-    if (aNbF) {
-      aBB.MakeCompound(aC);
-      //
-      for (i=1; i<=aNbF; ++i) {
-        const TopoDS_Shape& aF=aMCB(i);
-        aBB.Add(aC, aF);  
-        aMP.Add(aF);
+        }
       }
-      theLCB.Append(aC);
     }
-  }// for (; aIt.More(); aIt.Next()) 
+    // Add the block into result
+    theLCB.Append(aBlock);
+  }
 }
 //=======================================================================
 // function: OrientEdgesOnWire
index 9296c52..8309b18 100644 (file)
@@ -223,8 +223,11 @@ void BRepOffset_Inter3d::FaceInter(const TopoDS_Face& F1,
 
   if (F1.IsSame(F2)) return;
   if (IsDone(F1,F2)) return;
+
   const TopoDS_Shape& InitF1 = InitOffsetFace.ImageFrom(F1);
   const TopoDS_Shape& InitF2 = InitOffsetFace.ImageFrom(F2);
+  if (InitF1.IsSame(InitF2)) return;
+
   Standard_Boolean InterPipes = (InitF2.ShapeType() == TopAbs_EDGE &&
                                  InitF1.ShapeType() == TopAbs_EDGE );
   Standard_Boolean InterFaces = (InitF1.ShapeType() == TopAbs_FACE && 
index 834ab96..9564da0 100644 (file)
@@ -731,7 +731,10 @@ static void MakeList (TopTools_ListOfShape&             OffsetFaces,
     const TopoDS_Shape& Root = itLOF.Value();
     if (!myFaces.Contains(Root)) {
       if (myInitOffsetFace.HasImage(Root)) {
-        OffsetFaces.Append(myInitOffsetFace.Image(Root).First());
+        TopTools_ListIteratorOfListOfShape aItLS(myInitOffsetFace.Image(Root));
+        for (; aItLS.More(); aItLS.Next()) {
+          OffsetFaces.Append(aItLS.Value());
+        }
       }
     }
   }
index 77f3473..87702f2 100644 (file)
@@ -5205,8 +5205,14 @@ void UpdateValidEdges(const TopTools_IndexedDataMapOfShapeListOfShape& theFImage
   //
   // intersect valid splits with bounds and update both
   BOPAlgo_Builder aGF;
-  aGF.AddArgument(aSplits);
+  // The order is important here, because we need to keep the
+  // unmodified edges from the Bounds in the resulting maps.
+  // In case of total coincidence of the edges with the same vertices
+  // the edges in the common block will not be split and no new
+  // edges will be created and the first pave block
+  // will be used as a real pave block.
   aGF.AddArgument(aBounds);
+  aGF.AddArgument(aSplits);
   aGF.Perform();
   //
   // update splits
@@ -5222,7 +5228,7 @@ void UpdateValidEdges(const TopTools_IndexedDataMapOfShapeListOfShape& theFImage
   UpdateOrigins(aLABounds, theEdgesOrigins, aGF);
   UpdateIntersectedEdges(aLABounds, theETrimEInf, aGF);
   //
-  // update the edges to avoid with the splits
+  // update the EdgesToAvoid with the splits
   TopTools_IndexedMapOfShape aNewEdges;
   const TopTools_ListOfShape* pSplitsIm = aGF.Images().Seek(aSplits);
   if (pSplitsIm) {
@@ -5240,7 +5246,7 @@ void UpdateValidEdges(const TopTools_IndexedDataMapOfShapeListOfShape& theFImage
     for (; aItLEIm.More(); aItLEIm.Next()) {
       const TopoDS_Shape& aEIm = aItLEIm.Value();
       if (!aNewEdges.Contains(aEIm)) {
-        theEdgesToAvoid.Add(aItLEIm.Value());
+        theEdgesToAvoid.Add(aEIm);
       }
     }
   }
index f2286f1..ab47d61 100644 (file)
@@ -21,5 +21,5 @@ bbop result 0
 
 checkprops result -s 181.203 
 checkshape result
-checknbshapes result -vertex 2 -edge 3 -wire 3 -face 1 -shell 0 -solid 0 -compsolid 0 -compound 1 -shape 10
+checknbshapes result -face 1
 checkview -display result -2d -path ${imagedir}/${test_image}.png
index d99a3f2..8ebde56 100644 (file)
@@ -17,6 +17,6 @@ baddtools b2
 bfillds
 bbop result 0
 
-checkprops result -s 42.1078
+checkprops result -s 40.7799
 
 checkview -display result -2d -path ${imagedir}/${test_image}.png
index 0e0fed7..2b03c78 100644 (file)
@@ -13,10 +13,10 @@ box b2 5 5 0 10 10 10
 bfuse r b1 b2
 explode r f
 explode r_7 e
-getedgeregularity r_7_3 r_3 r_7 ;# returns C0: regularity is not set at all
+getedgeregularity r_7_4 r_3 r_7 ;# returns C0: regularity is not set at all
 encoderegularity r
 
-if { ! [regexp "CN" [getedgeregularity r_7_3 r_3 r_7]] } {
+if { ! [regexp "CN" [getedgeregularity r_7_4 r_3 r_7]] } {
   puts "Error: Invalid regularity of the edge, expected CN"
 }
 
index 60a62df..5f11858 100644 (file)
@@ -1,5 +1,6 @@
-puts "TODO OCC27414 ALL: Error : The volume of result shape is"
-puts "TODO OCC27414 ALL: Error : The area of result shape is"
+puts "TODO OCC27414 ALL: Error: The command cannot be built"
+puts "TODO OCC27414 ALL: gives an empty result"
+puts "TODO OCC27414 ALL: TEST INCOMPLETE"
 
 restore [locate_data_file bug26917_input.dom7742_trim1.brep] s