0024474: GCPnts_AbscissaPoint calculates invalid point
authorabk <abk@opencascade.com>
Tue, 17 Dec 2013 13:01:51 +0000 (17:01 +0400)
committerbugmaster <bugmaster@opencascade.com>
Thu, 16 Jan 2014 17:05:26 +0000 (21:05 +0400)
DRAW command discrCurve was created to test GCPnts_UniformAbscissa by count of discretization point.
Two bugs in GCPnts_AbscissaPoint were fixed.
DRAW tests for the bug were created.

src/GCPnts/GCPnts_AbscissaPoint.gxx
src/GeometryTest/GeometryTest_CurveCommands.cxx
tests/bugs/moddata_3/bug24474 [new file with mode: 0644]
tests/bugs/moddata_3/bug24474_2 [new file with mode: 0644]

index 0a657c0..01c9aad 100644 (file)
@@ -167,12 +167,6 @@ static void AdvCompute(CPnts_AbscissaPoint& theComputer,
                    Standard_Real& Ui,
                    const Standard_Real EPSILON) 
 {
-  // test for easy solution
-  if (Abs(Abscis) <= EPSILON) {
-    theComputer.SetParameter(U0);
-    return;
-  }
-  
   Standard_Real Ratio;
   GCPnts_AbscissaType Type = computeType(C,Ratio);
 
@@ -230,7 +224,7 @@ static void AdvCompute(CPnts_AbscissaPoint& theComputer,
       while ((Index >= 1) && (Index <= NbIntervals)) {
 
        L = CPnts_AbscissaPoint::Length(C, U0, TI(Index+Direction), EPSILON);
-       if (Abs(L - Abscis) <= /*Precision::Confusion()*/EPSILON) {
+       if (Abs(L - Abscis) <= Precision::PConfusion()) {
          theComputer.SetParameter(TI(Index+Direction));
          return;
        }
index f12ddb7..2e98440 100644 (file)
@@ -1126,6 +1126,107 @@ static Standard_Integer EllipsUniformAbscissa (Draw_Interpretor& di, Standard_In
 }
 
 //=======================================================================
+//function : discrCurve
+//purpose  :
+//=======================================================================
+static Standard_Integer discrCurve(Draw_Interpretor& di, Standard_Integer theArgNb, const char** theArgVec)
+{
+  if (theArgNb < 3)
+  {
+    di << "Invalid number of parameters.\n";
+    return 1;
+  }
+
+  Handle(Geom_Curve) aCurve = DrawTrSurf::GetCurve(theArgVec[2]);
+  if (aCurve.IsNull())
+  {
+    di << "Curve is NULL.\n";
+    return 1;
+  }
+
+  Standard_Integer aSrcNbPnts = 0;
+  Standard_Boolean isUniform = Standard_False;
+  for (Standard_Integer anArgIter = 3; anArgIter < theArgNb; ++anArgIter)
+  {
+    TCollection_AsciiString anArg     (theArgVec[anArgIter]);
+    TCollection_AsciiString anArgCase (anArg);
+    anArgCase.LowerCase();
+    if (anArgCase == "nbpnts")
+    {
+      if (++anArgIter >= theArgNb)
+      {
+        di << "Value for argument '" << anArg << "' is absent.\n";
+        return 1;
+      }
+
+      aSrcNbPnts = Draw::Atoi (theArgVec[anArgIter]);
+    }
+    else if (anArgCase == "uniform")
+    {
+      if (++anArgIter >= theArgNb)
+      {
+        di << "Value for argument '" << anArg << "' is absent.\n";
+        return 1;
+      }
+
+      isUniform = (Draw::Atoi (theArgVec[anArgIter]) == 1);
+    }
+    else
+    {
+      di << "Invalid argument '" << anArg << "'.\n";
+      return 1;
+    }
+  }
+
+  if (aSrcNbPnts < 2)
+  {
+    di << "Invalid count of points.\n";
+    return 1;
+  }
+
+  if (!isUniform)
+  {
+    di << "Invalid type of discretization.\n";
+    return 1;
+  }
+
+  GeomAdaptor_Curve aCurveAdaptor(aCurve);
+  GCPnts_UniformAbscissa aSplitter(aCurveAdaptor, aSrcNbPnts, Precision::Confusion());
+  if (!aSplitter.IsDone())
+  {
+    di << "Error: Invalid result.\n";
+    return 0;
+  }
+
+  const Standard_Integer aDstNbPnts = aSplitter.NbPoints();
+
+  if (aDstNbPnts < 2)
+  {
+    di << "Error: Invalid result.\n";
+    return 0;
+  }
+
+  TColgp_Array1OfPnt aPoles(1, aDstNbPnts);
+  TColStd_Array1OfReal aKnots(1, aDstNbPnts);
+  TColStd_Array1OfInteger aMultiplicities(1, aDstNbPnts);
+
+  for (Standard_Integer aPntIter = 1; aPntIter <= aDstNbPnts; ++aPntIter)
+  {
+    aPoles.ChangeValue(aPntIter) = aCurveAdaptor.Value(aSplitter.Parameter(aPntIter));
+    aKnots.ChangeValue(aPntIter) = (aPntIter - 1) / (aDstNbPnts - 1.0);
+    aMultiplicities.ChangeValue(aPntIter) = 1;
+  }
+  aMultiplicities.ChangeValue(1) = 2;
+  aMultiplicities.ChangeValue(aDstNbPnts) = 2;
+
+  Handle(Geom_BSplineCurve) aPolyline =
+    new Geom_BSplineCurve(aPoles, aKnots, aMultiplicities, 1);
+  DrawTrSurf::Set(theArgVec[1], aPolyline);
+
+  return 0;
+}
+
+//=======================================================================
 //function : mypoints
 //purpose  : 
 //=======================================================================
@@ -1622,6 +1723,13 @@ void  GeometryTest::CurveCommands(Draw_Interpretor& theCommands)
                  "uniformAbscissaEl maxR minR nbPnt",
                  __FILE__,  EllipsUniformAbscissa,g);
 
+  theCommands.Add("discrCurve",
+    "discrCurve polyline curve params\n"
+    "Approximates a curve by a polyline (first degree B-spline).\n"
+    "nbPnts number - creates polylines with the number points\n"
+    "uniform 0 | 1 - creates polyline with equal length segments",
+    __FILE__,  discrCurve, g);
+
   theCommands.Add("mypoints",
                  "mypoints result curv deflection",
                  __FILE__,
diff --git a/tests/bugs/moddata_3/bug24474 b/tests/bugs/moddata_3/bug24474
new file mode 100644 (file)
index 0000000..1c3e110
--- /dev/null
@@ -0,0 +1,11 @@
+puts "=================================================="
+puts "Check count of segments in approximating polyline."
+puts "=================================================="
+puts ""
+
+restore [locate_data_file bug24474.brep] c
+discrCurve p c nbPnts 3 uniform 1
+regexp {Poles\, +([0-9]+)} [dump p] full n
+if {$n != 3} {
+  puts "Error: invalid discretization."
+}
diff --git a/tests/bugs/moddata_3/bug24474_2 b/tests/bugs/moddata_3/bug24474_2
new file mode 100644 (file)
index 0000000..662c1f9
--- /dev/null
@@ -0,0 +1,11 @@
+puts "=================================================="
+puts "Check count of segments in approximating polyline."
+puts "=================================================="
+puts ""
+
+restore [locate_data_file bug24474_2.brep] c
+discrCurve p c nbPnts 3 uniform 1
+regexp {Poles\, +([0-9]+)} [dump p] full n
+if {$n != 3} {
+  puts "Error: invalid discretization."
+}