0031207: Regression in Boolean Operations: fuse gives wrong result
authoremv <emv@opencascade.com>
Mon, 13 Apr 2020 10:35:32 +0000 (13:35 +0300)
committerbugmaster <bugmaster@opencascade.com>
Thu, 16 Apr 2020 07:00:54 +0000 (10:00 +0300)
ForceInterfEE, ForceInterfEF - Use normalized vectors for angle computation. Increase the criteria angle.

src/BOPAlgo/BOPAlgo_PaveFiller_3.cxx
src/BOPAlgo/BOPAlgo_PaveFiller_5.cxx
tests/bugs/modalg_7/bug31207 [new file with mode: 0644]

index 1df7f3c..8988912 100644 (file)
@@ -1002,6 +1002,7 @@ void BOPAlgo_PaveFiller::ForceInterfEE()
       aBAC1.D1((aT11 + aT12) * 0.5, aPm, aVTgt1);
       if (aVTgt1.SquareMagnitude() < gp::Resolution())
         continue;
+      aVTgt1.Normalize();
 
       BOPDS_ListIteratorOfListOfPaveBlock aItLPB2 = aItLPB1;
       for (aItLPB2.Next(); aItLPB2.More(); aItLPB2.Next())
@@ -1034,25 +1035,30 @@ void BOPAlgo_PaveFiller::ForceInterfEE()
         aPB2->Range(aT21, aT22);
 
         // Check the angle between edges in the middle point.
-        // If the angle is more than 10 degrees, do not use the additional
+        // If the angle is more than 25 degrees, do not use the additional
         // tolerance, as it may lead to undesired unification of edges
         Standard_Boolean bUseAddTol = Standard_True;
         {
-          GeomAPI_ProjectPointOnCurve& aProjPC = myContext->ProjPC(aE2);
-          aProjPC.Perform(aPm);
-          if (!aProjPC.NbPoints())
-            continue;
-
           BRepAdaptor_Curve aBAC2(aE2);
-          gp_Pnt aPm2;
-          gp_Vec aVTgt2;
-          aBAC2.D1(aProjPC.LowerDistanceParameter(), aPm2, aVTgt2);
-          if (aVTgt2.SquareMagnitude() < gp::Resolution())
-            continue;
-          // The angle should be close to zero
-          Standard_Real aCos = aVTgt1.Dot(aVTgt2);
-          if (Abs(aCos) < 0.984)
-            bUseAddTol = Standard_False;
+          if (aBAC1.GetType() != GeomAbs_Line ||
+              aBAC2.GetType() != GeomAbs_Line)
+          {
+            GeomAPI_ProjectPointOnCurve& aProjPC = myContext->ProjPC(aE2);
+            aProjPC.Perform(aPm);
+            if (!aProjPC.NbPoints())
+              continue;
+
+            gp_Pnt aPm2;
+            gp_Vec aVTgt2;
+            aBAC2.D1(aProjPC.LowerDistanceParameter(), aPm2, aVTgt2);
+            if (aVTgt2.SquareMagnitude() < gp::Resolution())
+              continue;
+
+            // The angle should be close to zero
+            Standard_Real aCos = aVTgt1.Dot (aVTgt2.Normalized());
+            if (Abs(aCos) < 0.9063)
+              bUseAddTol = Standard_False;
+          }
         }
 
         // Add pair for intersection
index 933f3c7..ae20670 100644 (file)
@@ -847,6 +847,7 @@ void BOPAlgo_PaveFiller::ForceInterfEF(const BOPDS_IndexedMapOfPaveBlock& theMPB
 
     // Projection tool
     GeomAPI_ProjectPointOnSurf& aProjPS = myContext->ProjPS(aF);
+    BRepAdaptor_Surface& aSurfAdaptor = myContext->SurfaceAdaptor (aF);
 
     // Iterate on pave blocks and combine pairs containing
     // the same vertices
@@ -886,7 +887,7 @@ void BOPAlgo_PaveFiller::ForceInterfEF(const BOPDS_IndexedMapOfPaveBlock& theMPB
       // Check directions coincidence at middle point on the edge
       // and projection of that point on the face.
       // If the angle between tangent vector to the curve and normal
-      // of the face is not in the range of 80 - 100 degrees, do not use the additional
+      // of the face is not in the range of 65 - 115 degrees, do not use the additional
       // tolerance, as it may lead to undesired unification of edge with the face.
       Standard_Boolean bUseAddTol = Standard_True;
 
@@ -926,15 +927,19 @@ void BOPAlgo_PaveFiller::ForceInterfEF(const BOPDS_IndexedMapOfPaveBlock& theMPB
       if (!myContext->IsPointInFace(aF, gp_Pnt2d(U, V)))
         continue;
 
-      gp_Pnt aPOnS = aProjPS.NearestPoint();
-      gp_Vec aVFNorm(aPOnS, aPOnE);
-      if (aVFNorm.SquareMagnitude() > gp::Resolution())
+      if (aSurfAdaptor.GetType() != GeomAbs_Plane ||
+          aBAC.GetType() != GeomAbs_Line)
       {
-        // Angle between vectors should be close to 90 degrees.
-        // We allow deviation of 10 degrees.
-        Standard_Real aCos = aVFNorm.Dot(aVETgt);
-        if (Abs(aCos) > 0.174)
-          bUseAddTol = Standard_False;
+        gp_Pnt aPOnS = aProjPS.NearestPoint();
+        gp_Vec aVFNorm(aPOnS, aPOnE);
+        if (aVFNorm.SquareMagnitude() > gp::Resolution())
+        {
+          // Angle between vectors should be close to 90 degrees.
+          // We allow deviation of 25 degrees.
+          Standard_Real aCos = aVFNorm.Normalized().Dot (aVETgt.Normalized());
+          if (Abs(aCos) > 0.4226)
+            bUseAddTol = Standard_False;
+        }
       }
 
       // Compute an addition to Fuzzy value
diff --git a/tests/bugs/modalg_7/bug31207 b/tests/bugs/modalg_7/bug31207
new file mode 100644 (file)
index 0000000..5b6fe00
--- /dev/null
@@ -0,0 +1,41 @@
+puts "========"
+puts "0031207: Regression in Boolean Operations: fuse gives wrong result"
+puts "========"
+puts ""
+
+restore [locate_data_file bug31207_cylinder.brep] s1
+restore [locate_data_file bug31207_pipe.brep] s2
+
+bclearobjects
+bcleartools
+baddobjects s1
+baddtools s2
+bfillds
+
+bbop r0 0
+bbop r1 1
+bbop r2 2
+bbop r3 3
+bbop r4 4
+
+checkshape r0
+checknbshapes r0 -wire 10 -face 10 -shell 1 -solid 1 -t
+checkprops r0 -s 0.00309819 -v 1.751e-07
+
+checkshape r1
+checknbshapes r1 -wire 15 -face 15 -shell 1 -solid 1 -t
+checkprops r1 -s 0.0266469 -v 9.78558e-05
+
+checkshape r2
+checknbshapes r2 -wire 9 -face 9 -shell 1 -solid 1 -t
+checkprops r2 -s 0.0241535 -v 9.41001e-05
+
+checkshape r3
+checknbshapes r3 -wire 12 -face 12 -shell 1 -solid 1 -t
+checkprops r3 -s 0.00559005 -v 3.58054e-06
+
+checkshape r4
+checksection r4 -r 4
+checkprops r4 -l 0.970304
+
+checkview -display r1 -2d -path ${imagedir}/${test_image}.png