]> OCCT Git - occt-copy.git/commitdiff
0027903: Patch AdvApp2Var_ApproxAFunc2Var and GeomPlate_MakeApprox to handle the... CR27903_1
authorrazmyslovich <razmyslovich@volumegraphics.com>
Fri, 20 Jan 2017 11:59:06 +0000 (12:59 +0100)
committerrazmyslovich <razmyslovich@volumegraphics.com>
Fri, 20 Jan 2017 11:59:06 +0000 (12:59 +0100)
src/AdvApp2Var/AdvApp2Var_ApproxAFunc2Var.cxx
src/AdvApp2Var/AdvApp2Var_ApproxAFunc2Var.hxx
src/AdvApp2Var/AdvApp2Var_ApproxAFunc2Var.lxx
src/GeomPlate/GeomPlate_MakeApprox.cxx
src/GeomPlate/GeomPlate_MakeApprox.hxx
src/QABugs/QABugs_20.cxx
tests/bugs/modalg_6/bug27903 [new file with mode: 0644]

index 92423d9447b6319ef5e189591744a3ddfd8f6ad5..370d7b0707b96fce158c3fa8eafdc1be387feeca 100644 (file)
 #include <Geom_BezierSurface.hxx>
 #include <Geom_BSplineSurface.hxx>
 
+AdvApp2Var_ApproxAFunc2Var::AdvApp2Var_ApproxAFunc2Var
+(
+  const Parameters & parameters,
+  const AdvApp2Var_EvaluatorFunc2Var& Func,
+  AdvApprox_Cutting& UChoice,
+  AdvApprox_Cutting& VChoice
+):
+  myParameters    (parameters),
+  myDone          (Standard_False),
+  myHasResult     (Standard_False),
+  myDegreeInU     (0),
+  myDegreeInV     (0),
+  myCriterionError(0.0)
+{
+  Init();
+  Perform(UChoice, VChoice, Func);
+  ConvertBS();
+}
+
+AdvApp2Var_ApproxAFunc2Var::AdvApp2Var_ApproxAFunc2Var
+(
+  const Parameters & parameters,
+  const AdvApp2Var_EvaluatorFunc2Var& Func,
+  const AdvApp2Var_Criterion& Crit,
+  AdvApprox_Cutting& UChoice,
+  AdvApprox_Cutting& VChoice
+):
+  myParameters    (parameters),
+  myDone          (Standard_False),
+  myHasResult     (Standard_False),
+  myDegreeInU     (0),
+  myDegreeInV     (0),
+  myCriterionError(0.0)
+{
+  Init();
+  Perform(UChoice, VChoice, Func, Crit);
+  ConvertBS();
+}
 
 //=======================================================================
 //function : AdvApp2Var_ApproxAFunc2Var
@@ -73,32 +111,41 @@ AdvApp2Var_ApproxAFunc2Var::AdvApp2Var_ApproxAFunc2Var(
                            const AdvApp2Var_EvaluatorFunc2Var& Func,
                            AdvApprox_Cutting& UChoice,
                            AdvApprox_Cutting& VChoice)
-: my1DTolerances  (OneDTol),
-  my2DTolerances  (TwoDTol),
-  my3DTolerances  (ThreeDTol),
-  my1DTolOnFront  (OneDTolFr),
-  my2DTolOnFront  (TwoDTolFr),
-  my3DTolOnFront  (ThreeDTolFr),
-  myFirstParInU   (FirstInU),
-  myLastParInU    (LastInU),
-  myFirstParInV   (FirstInV),
-  myLastParInV    (LastInV),
-  myFavoriteIso   (FavorIso),
-  myContInU       (ContInU),
-  myContInV       (ContInV),
-  myPrecisionCode (PrecisCode),
-  myMaxDegInU     (MaxDegInU),
-  myMaxDegInV     (MaxDegInV),
-  myMaxPatches    (MaxPatch),
-  myDone          (Standard_False),
+: myDone          (Standard_False),
   myHasResult     (Standard_False),
   myDegreeInU     (0),
   myDegreeInV     (0),
   myCriterionError(0.0)
 {
-  myNumSubSpaces[0] = Num1DSS;
-  myNumSubSpaces[1] = Num2DSS;
-  myNumSubSpaces[2] = Num3DSS;
+  myParameters.NumberSubSpaces[0] = Num1DSS;
+  myParameters.NumberSubSpaces[1] = Num2DSS;
+  myParameters.NumberSubSpaces[2] = Num3DSS;
+
+  myParameters.Tolerances1D = OneDTol;
+  myParameters.Tolerances2D = TwoDTol;
+  myParameters.Tolerances3D = ThreeDTol;
+
+  myParameters.TolerancesOnFrontier1D = OneDTolFr;
+  myParameters.TolerancesOnFrontier2D = TwoDTolFr;
+  myParameters.TolerancesOnFrontier3D = ThreeDTolFr;
+
+  myParameters.FirstParamU = FirstInU;
+  myParameters.FirstParamV = FirstInV;
+  myParameters.LastParamU = LastInU;
+  myParameters.LastParamV = LastInV;
+
+  myParameters.FavouriteIso = FavorIso;
+
+  myParameters.ContinuityU = ContInU;
+  myParameters.ContinuityV = ContInV;
+
+  myParameters.PrecisionCode = PrecisCode;
+  myParameters.DegreeU = MaxDegInU;
+  myParameters.DegreeV = MaxDegInV;
+
+  myParameters.MaxPatchesU = myParameters.MaxPatchesV = IntegerLast();
+
+  myParameters.TotalPatches = MaxPatch;
 
   Init();
   Perform(UChoice, VChoice, Func);
@@ -135,32 +182,41 @@ AdvApp2Var_ApproxAFunc2Var::AdvApp2Var_ApproxAFunc2Var(
                       const AdvApp2Var_Criterion& Crit,
                       AdvApprox_Cutting& UChoice,
                       AdvApprox_Cutting& VChoice)
-: my1DTolerances  (OneDTol),
-  my2DTolerances  (TwoDTol),
-  my3DTolerances  (ThreeDTol),
-  my1DTolOnFront  (OneDTolFr),
-  my2DTolOnFront  (TwoDTolFr),
-  my3DTolOnFront  (ThreeDTolFr),
-  myFirstParInU   (FirstInU),
-  myLastParInU    (LastInU),
-  myFirstParInV   (FirstInV),
-  myLastParInV    (LastInV),
-  myFavoriteIso   (FavorIso),
-  myContInU       (ContInU),
-  myContInV       (ContInV),
-  myPrecisionCode (PrecisCode),
-  myMaxDegInU     (MaxDegInU),
-  myMaxDegInV     (MaxDegInV),
-  myMaxPatches    (MaxPatch),
-  myDone          (Standard_False),
+: myDone          (Standard_False),
   myHasResult     (Standard_False),
   myDegreeInU     (0),
   myDegreeInV     (0),
   myCriterionError(0.0)
 {
-  myNumSubSpaces[0] = Num1DSS;
-  myNumSubSpaces[1] = Num2DSS;
-  myNumSubSpaces[2] = Num3DSS;
+  myParameters.NumberSubSpaces[0] = Num1DSS;
+  myParameters.NumberSubSpaces[1] = Num2DSS;
+  myParameters.NumberSubSpaces[2] = Num3DSS;
+
+  myParameters.Tolerances1D = OneDTol;
+  myParameters.Tolerances2D = TwoDTol;
+  myParameters.Tolerances3D = ThreeDTol;
+
+  myParameters.TolerancesOnFrontier1D = OneDTolFr;
+  myParameters.TolerancesOnFrontier2D = TwoDTolFr;
+  myParameters.TolerancesOnFrontier3D = ThreeDTolFr;
+
+  myParameters.FirstParamU = FirstInU;
+  myParameters.FirstParamV = FirstInV;
+  myParameters.LastParamU = LastInU;
+  myParameters.LastParamV = LastInV;
+
+  myParameters.FavouriteIso = FavorIso;
+
+  myParameters.ContinuityU = ContInU;
+  myParameters.ContinuityV = ContInV;
+
+  myParameters.PrecisionCode = PrecisCode;
+  myParameters.DegreeU = MaxDegInU;
+  myParameters.DegreeV = MaxDegInV;
+
+  myParameters.MaxPatchesU = myParameters.MaxPatchesV = IntegerLast();
+
+  myParameters.TotalPatches = MaxPatch;
 
   Init();
   Perform(UChoice, VChoice, Func, Crit);
@@ -175,7 +231,7 @@ AdvApp2Var_ApproxAFunc2Var::AdvApp2Var_ApproxAFunc2Var(
 void AdvApp2Var_ApproxAFunc2Var::Init()
 {
   Standard_Integer ifav,iu=0,iv=0,ndu,ndv;
-  switch (myFavoriteIso) {
+  switch (myParameters.FavouriteIso) {
   case GeomAbs_IsoU :
     ifav = 1;
     break;
@@ -186,7 +242,7 @@ void AdvApp2Var_ApproxAFunc2Var::Init()
     ifav = 2;
     break;
   }
-  switch (myContInU) {
+  switch (myParameters.ContinuityU) {
   case GeomAbs_C0 :
     iu = 0;
     break;
@@ -199,7 +255,7 @@ void AdvApp2Var_ApproxAFunc2Var::Init()
   default :
     Standard_ConstructionError::Raise("AdvApp2Var_ApproxAFunc2Var : UContinuity Error");
   }
-  switch (myContInV) {
+  switch (myParameters.ContinuityV) {
   case GeomAbs_C0 :
     iv = 0;
     break;
@@ -212,26 +268,27 @@ void AdvApp2Var_ApproxAFunc2Var::Init()
   default :
     Standard_ConstructionError::Raise("AdvApp2Var_ApproxAFunc2Var : VContinuity Error");
   }
-  ndu = Max(myMaxDegInU+1,2*iu+2);
-  ndv = Max(myMaxDegInV+1,2*iv+2);
+  ndu = Max(myParameters.DegreeU+1,2*iu+2);
+  ndv = Max(myParameters.DegreeV+1,2*iv+2);
   if (ndu<2*iu+2)
     Standard_ConstructionError::Raise("AdvApp2Var_ApproxAFunc2Var : UMaxDegree Error");
   if (ndv<2*iv+2)
     Standard_ConstructionError::Raise("AdvApp2Var_ApproxAFunc2Var : VMaxDegree Error");
-  myPrecisionCode = Max(0,Min(myPrecisionCode,3));
+  myParameters.PrecisionCode = Max(0,Min(myParameters.PrecisionCode,3));
   AdvApp2Var_Context Conditions(ifav,iu,iv,ndu,ndv,
-                               myPrecisionCode,
-                               myNumSubSpaces[0],
-                                myNumSubSpaces[1],
-                                myNumSubSpaces[2],
-                                my1DTolerances,
-                                my2DTolerances,
-                                my3DTolerances,
-                                my1DTolOnFront,
-                                my2DTolOnFront,
-                                my3DTolOnFront);
+      myParameters.PrecisionCode,
+      myParameters.NumberSubSpaces[0],
+      myParameters.NumberSubSpaces[1],
+      myParameters.NumberSubSpaces[2],
+      myParameters.Tolerances1D,
+      myParameters.Tolerances2D,
+      myParameters.Tolerances3D,
+      myParameters.TolerancesOnFrontier1D,
+      myParameters.TolerancesOnFrontier2D,
+      myParameters.TolerancesOnFrontier3D
+    );
   myConditions = Conditions;
-  InitGrid(1);
+  InitGrid(1, 1);
 }
 
 
@@ -240,50 +297,50 @@ void AdvApp2Var_ApproxAFunc2Var::Init()
 //purpose  : Initialisation of the approximation with regular cuttings
 //=======================================================================
 
-void AdvApp2Var_ApproxAFunc2Var::InitGrid(const Standard_Integer NbInt)
+void AdvApp2Var_ApproxAFunc2Var::InitGrid(const Standard_Integer sizeU, const Standard_Integer sizeV)
 {
-  Standard_Integer iu=myConditions.UOrder(),iv=myConditions.VOrder(),iint;
+  Standard_Integer iu=myConditions.UOrder(),iv=myConditions.VOrder();
 
-  AdvApp2Var_Patch M0(myFirstParInU,myLastParInU,myFirstParInV,myLastParInV,iu,iv);
+  AdvApp2Var_Patch M0(myParameters.FirstParamU, myParameters.LastParamU, myParameters.FirstParamV, myParameters.LastParamV,iu,iv);
 
   AdvApp2Var_SequenceOfPatch Net;
   Net.Append(M0);
 
   TColStd_SequenceOfReal TheU,TheV;
-  TheU.Append(myFirstParInU);
-  TheV.Append(myFirstParInV);
-  TheU.Append(myLastParInU);
-  TheV.Append(myLastParInV);
+  TheU.Append(myParameters.FirstParamU);
+  TheV.Append(myParameters.FirstParamV);
+  TheU.Append(myParameters.LastParamU);
+  TheV.Append(myParameters.LastParamV);
 
   AdvApp2Var_Network Result(Net,TheU,TheV);
 
+  gp_XY UV1 (myParameters.FirstParamU, myParameters.FirstParamV);
+  AdvApp2Var_Node C1 (UV1, iu, iv);
+  gp_XY UV2 (myParameters.LastParamU, myParameters.FirstParamV);
+  AdvApp2Var_Node C2 (UV2, iu, iv);
+  gp_XY UV3 (myParameters.FirstParamU, myParameters.LastParamV);
+  AdvApp2Var_Node C3 (UV3, iu, iv);
+  gp_XY UV4 (myParameters.LastParamU, myParameters.LastParamV);
+  AdvApp2Var_Node C4 (UV4, iu, iv);
 
-  gp_XY UV1(myFirstParInU,myFirstParInV);
-  AdvApp2Var_Node C1(UV1,iu,iv);
-  gp_XY UV2(myLastParInU,myFirstParInV);
-  AdvApp2Var_Node C2(UV2,iu,iv);
-  gp_XY UV4(myLastParInU,myLastParInV);
-  AdvApp2Var_Node C4(UV4,iu,iv);
-  gp_XY UV3(myFirstParInU,myLastParInV);
-  AdvApp2Var_Node C3(UV3,iu,iv);
   AdvApp2Var_SequenceOfNode Bag;
   Bag.Append(C1);
   Bag.Append(C2);
   Bag.Append(C3);
   Bag.Append(C4);
 
-  AdvApp2Var_Iso V0(GeomAbs_IsoV,myFirstParInV,
-                   myFirstParInU,myLastParInU,myFirstParInV,myLastParInV,
-                   1,iu,iv);
-  AdvApp2Var_Iso V1(GeomAbs_IsoV,myLastParInV,
-                   myFirstParInU,myLastParInU,myFirstParInV,myLastParInV,
-                   2,iu,iv);
-  AdvApp2Var_Iso U0(GeomAbs_IsoU,myFirstParInU,
-                   myFirstParInU,myLastParInU,myFirstParInV,myLastParInV,
-                   3,iu,iv);
-  AdvApp2Var_Iso U1(GeomAbs_IsoU,myLastParInU,
-                   myFirstParInU,myLastParInU,myFirstParInV,myLastParInV,
-                   4,iu,iv);
+  AdvApp2Var_Iso V0(GeomAbs_IsoV,myParameters.FirstParamV,
+        myParameters.FirstParamU,myParameters.LastParamU,myParameters.FirstParamV,myParameters.LastParamV,
+        1,iu,iv);
+  AdvApp2Var_Iso V1(GeomAbs_IsoV,myParameters.LastParamV,
+        myParameters.FirstParamU,myParameters.LastParamU,myParameters.FirstParamV,myParameters.LastParamV,
+        2,iu,iv);
+  AdvApp2Var_Iso U0(GeomAbs_IsoU,myParameters.FirstParamU,
+        myParameters.FirstParamU,myParameters.LastParamU,myParameters.FirstParamV,myParameters.LastParamV,
+        3,iu,iv);
+  AdvApp2Var_Iso U1(GeomAbs_IsoU,myParameters.LastParamU,
+        myParameters.FirstParamU,myParameters.LastParamU,myParameters.FirstParamV,myParameters.LastParamV,
+        4,iu,iv);
 
   AdvApp2Var_Strip BU0,BV0;
   BU0.Append(V0);
@@ -295,16 +352,24 @@ void AdvApp2Var_ApproxAFunc2Var::InitGrid(const Standard_Integer NbInt)
   UStrip.Append(BU0);
   VStrip.Append(BV0);
 
-  AdvApp2Var_Framework Constraints(Bag,UStrip,VStrip);
+  AdvApp2Var_Framework Constraints(Bag, UStrip, VStrip);
 
-// regular cutting if NbInt>1
-  Standard_Real deltu = (myLastParInU-myFirstParInU)/NbInt,
-                deltv = (myLastParInV-myFirstParInV)/NbInt;
-  for (iint=1;iint<=NbInt-1;iint++) {
-    Result.UpdateInU(myFirstParInU+iint*deltu);
-    Constraints.UpdateInU(myFirstParInU+iint*deltu);
-    Result.UpdateInV(myFirstParInV+iint*deltv);
-    Constraints.UpdateInV(myFirstParInV+iint*deltv);
+  {
+    Standard_Real deltaU = (myParameters.LastParamU - myParameters.FirstParamU)/sizeU;
+    for (Standard_Integer i = 1; i < sizeU; ++i)
+    {
+      Result.UpdateInU(myParameters.FirstParamU + i * deltaU);
+      Constraints.UpdateInU(myParameters.FirstParamU + i * deltaU);
+    }
+  }
+
+  {
+    Standard_Real deltaV = (myParameters.LastParamV - myParameters.FirstParamV)/sizeV;
+    for (Standard_Integer i = 1; i < sizeV; ++i)
+    {
+      Result.UpdateInV(myParameters.FirstParamV + i * deltaV);
+      Constraints.UpdateInV(myParameters.FirstParamV + i * deltaV);
+    }
   }
   myResult = Result;
   myConstraints = Constraints;
@@ -375,16 +440,25 @@ void AdvApp2Var_ApproxAFunc2Var::ComputePatches(const AdvApprox_Cutting& UChoice
     Umore = UChoice.Value(myResult(FirstNA).U0(), myResult(FirstNA).U1(),Udec);
     Vmore = VChoice.Value(myResult(FirstNA).V0(), myResult(FirstNA).V1(),Vdec);
 
+    if (NbU >= myParameters.MaxPatchesU)
+    {
+      Umore = Standard_False;
+    }
+    if (NbV >= myParameters.MaxPatchesV)
+    {
+      Vmore = Standard_False;
+    }
+
     NumDec = 0;
-    if ( ((NbPatch+NbV)<=myMaxPatches) && ((NbPatch+NbU)>myMaxPatches)
+    if ( ((NbPatch+NbV)<=myParameters.TotalPatches) && ((NbPatch+NbU)>myParameters.TotalPatches)
          && (Umore) ) NumDec = 1;
-    if ( ((NbPatch+NbV)>myMaxPatches) && ((NbPatch+NbU)<=myMaxPatches) 
+    if ( ((NbPatch+NbV)>myParameters.TotalPatches) && ((NbPatch+NbU)<=myParameters.TotalPatches) 
          && (Vmore) ) NumDec = 2;
-    if ( ((NbPatch+NbV)<=myMaxPatches) && ((NbPatch+NbU)<=myMaxPatches) ) {
+    if ( ((NbPatch+NbV)<=myParameters.TotalPatches) && ((NbPatch+NbU)<=myParameters.TotalPatches) ) {
       if ( Umore ) NumDec = 3;
       if ( (NbV>NbU) && Vmore ) NumDec = 4;
     }
-    if ( (NbU+1)*(NbV+1)<=myMaxPatches ) {
+    if ( (NbU+1)*(NbV+1)<=myParameters.TotalPatches ) {
       if ( !Umore && !Vmore ) NumDec=0;
       if ( Umore && !Vmore ) NumDec=3;
       if ( !Umore && Vmore ) NumDec=4;
@@ -472,17 +546,24 @@ void AdvApp2Var_ApproxAFunc2Var::ComputePatches(const AdvApprox_Cutting& UChoice
     NbInt = NbU;
     Umore = UChoice.Value(myResult(FirstNA).U0(), myResult(FirstNA).U1(),Udec);
     Vmore = VChoice.Value(myResult(FirstNA).V0(), myResult(FirstNA).V1(),Vdec);
-
+    if (NbU >= myParameters.MaxPatchesU)
+    {
+      Umore = Standard_False;
+    }
+    if (NbV >= myParameters.MaxPatchesV)
+    {
+      Vmore = Standard_False;
+    }
     NumDec = 0;
-    if ( ((NbPatch+NbV)<=myMaxPatches) && ((NbPatch+NbU)>myMaxPatches)
+    if ( ((NbPatch+NbV)<=myParameters.TotalPatches) && ((NbPatch+NbU)>myParameters.TotalPatches)
          && (Umore) ) NumDec = 1;
-    if ( ((NbPatch+NbV)>myMaxPatches) && ((NbPatch+NbU)<=myMaxPatches) 
+    if ( ((NbPatch+NbV)>myParameters.TotalPatches) && ((NbPatch+NbU)<=myParameters.TotalPatches) 
          && (Vmore) ) NumDec = 2;
-    if ( ((NbPatch+NbV)<=myMaxPatches) && ((NbPatch+NbU)<=myMaxPatches) ) {
+    if ( ((NbPatch+NbV)<=myParameters.TotalPatches) && ((NbPatch+NbU)<=myParameters.TotalPatches) ) {
       if ( Umore ) NumDec = 3;
       if ( (NbV>NbU) && Vmore ) NumDec = 4;
     }
-    if ( (NbU+1)*(NbV+1)<=myMaxPatches ) {
+    if ( (NbU+1)*(NbV+1)<=myParameters.TotalPatches ) {
       if ( !Umore && !Vmore ) NumDec=0;
       if ( Umore && !Vmore ) NumDec=1;
       if ( !Umore && Vmore ) NumDec=2;
@@ -509,8 +590,19 @@ void AdvApp2Var_ApproxAFunc2Var::ComputePatches(const AdvApprox_Cutting& UChoice
     Standard_Boolean Regular = (Crit.Repartition() ==  AdvApp2Var_Regular);
 //    Standard_Boolean Regular = Standard_True;
     if (Regular && decision>0) {
-      NbInt++;
-      InitGrid(NbInt);
+      switch (decision)
+      {
+      case 1: ++NbU; break;
+      case 2: ++NbV; break;
+      case 3: ++NbU; ++NbV; break;
+      default:
+        {
+          myHasResult =  myDone = Standard_False;
+          Standard_ConstructionError::Raise ("AdvApp2Var_ApproxAFunc2Var : Surface Approximation Error");
+        }
+      }
+
+      InitGrid(NbU, NbV);
     }
     else {
       switch (decision) {
@@ -577,8 +669,8 @@ void AdvApp2Var_ApproxAFunc2Var::ComputeConstraints(const AdvApprox_Cutting& UCh
     N2 = myConstraints.Node(indN2);
 
     Is.MakeApprox(myConditions,
-                 myFirstParInU, myLastParInU,
-                 myFirstParInV, myLastParInV,
+                 myParameters.FirstParamU, myParameters.LastParamU,
+          myParameters.FirstParamV, myParameters.LastParamV,
                  Func, N1 , N2);
 
     if (Is.IsApproximated()) {
@@ -595,13 +687,15 @@ void AdvApp2Var_ApproxAFunc2Var::ComputeConstraints(const AdvApprox_Cutting& UCh
       if (Is.Type()==GeomAbs_IsoV) {
        NbPatch = (NbU+1)*NbV;
        more = UChoice.Value(Is.T0(),Is.T1(),dec);
+    more = more && (NbU < myParameters.MaxPatchesU);
       }
       else {
        NbPatch = (NbV+1)*NbU;
        more = VChoice.Value(Is.T0(),Is.T1(),dec);
+    more = more && (NbU < myParameters.MaxPatchesV);
       }
 
-      if (NbPatch<=myMaxPatches && more) {
+      if (NbPatch<=myParameters.TotalPatches && more) {
 //     It is possible to cut iso
        if (Is.Type()==GeomAbs_IsoV) {
          myResult.UpdateInU(dec);
@@ -659,8 +753,8 @@ void AdvApp2Var_ApproxAFunc2Var::ComputeConstraints(const AdvApprox_Cutting& UCh
       N2 = myConstraints.Node(indN2);
 
       Is.MakeApprox(myConditions,
-                    myFirstParInU, myLastParInU,
-                    myFirstParInV, myLastParInV,
+                    myParameters.FirstParamU, myParameters.LastParamU,
+                    myParameters.FirstParamV, myParameters.LastParamV,
                     Func, N1 , N2);
 
       if (Is.IsApproximated()) {
@@ -677,16 +771,18 @@ void AdvApp2Var_ApproxAFunc2Var::ComputeConstraints(const AdvApprox_Cutting& UCh
        if (Is.Type()==GeomAbs_IsoV) {
          NbPatch = (NbU+1)*NbV;
          more = UChoice.Value(Is.T0(),Is.T1(),dec);
+      more = more && (NbU < myParameters.MaxPatchesU);
        }
        else {
          NbPatch = (NbV+1)*NbU;
          more = VChoice.Value(Is.T0(),Is.T1(),dec);
+      more = more && (NbU < myParameters.MaxPatchesU);
        }
 
 //      To force Overwrite if the criterion is Absolute
        more = more && (CritRel);
 
-       if (NbPatch<=myMaxPatches && more) {
+       if (NbPatch<=myParameters.TotalPatches && more) {
 //     It is possible to cut iso
          if (Is.Type()==GeomAbs_IsoV) {
            myResult.UpdateInU(dec);
@@ -727,23 +823,23 @@ void AdvApp2Var_ApproxAFunc2Var::Compute3DErrors()
   Standard_Integer iesp,ipat;
   Standard_Real error_max,error_moy,error_U0,error_V0,error_U1,error_V1;
   Standard_Real Tol,F1Tol,F2Tol,F3Tol,F4Tol;
-  if ( myNumSubSpaces[2] > 0 ) {
-    my3DMaxError = new (TColStd_HArray1OfReal) (1,myNumSubSpaces[2]);
-    my3DAverageError = new (TColStd_HArray1OfReal) (1,myNumSubSpaces[2]);
-    my3DUFrontError = new (TColStd_HArray1OfReal) (1,myNumSubSpaces[2]);
-    my3DVFrontError = new (TColStd_HArray1OfReal) (1,myNumSubSpaces[2]);
-    for (iesp=1;iesp<=myNumSubSpaces[2];iesp++) {
+  if ( myParameters.NumberSubSpaces[2] > 0 ) {
+    my3DMaxError = new (TColStd_HArray1OfReal) (1,myParameters.NumberSubSpaces[2]);
+    my3DAverageError = new (TColStd_HArray1OfReal) (1,myParameters.NumberSubSpaces[2]);
+    my3DUFrontError = new (TColStd_HArray1OfReal) (1,myParameters.NumberSubSpaces[2]);
+    my3DVFrontError = new (TColStd_HArray1OfReal) (1,myParameters.NumberSubSpaces[2]);
+    for (iesp=1;iesp<=myParameters.NumberSubSpaces[2];iesp++) {
       error_max = 0;
       error_moy = 0.;
       error_U0 = 0.;
       error_V0 = 0.;
       error_U1 = 0.;
       error_V1 = 0.;
-      Tol = my3DTolerances->Value(iesp);
-      F1Tol = my3DTolOnFront->Value(iesp,1);
-      F2Tol = my3DTolOnFront->Value(iesp,2);
-      F3Tol = my3DTolOnFront->Value(iesp,3);
-      F4Tol = my3DTolOnFront->Value(iesp,4);
+      Tol = myParameters.Tolerances3D->Value(iesp);
+      F1Tol = myParameters.TolerancesOnFrontier3D->Value(iesp,1);
+      F2Tol = myParameters.TolerancesOnFrontier3D->Value(iesp,2);
+      F3Tol = myParameters.TolerancesOnFrontier3D->Value(iesp,3);
+      F4Tol = myParameters.TolerancesOnFrontier3D->Value(iesp,4);
       for (ipat=1;ipat<=myResult.NbPatch();ipat++) {
        error_max = Max((myResult(ipat).MaxErrors())->Value(iesp),error_max);
        error_U0 = Max((myResult(ipat).IsoErrors())->Value(iesp,3),error_U0);
@@ -777,8 +873,8 @@ void AdvApp2Var_ApproxAFunc2Var::ComputeCritError()
 
   Standard_Integer iesp,ipat;
   Standard_Real crit_max;
-  if ( myNumSubSpaces[2] > 0 ) {
-    for (iesp=1;iesp<=myNumSubSpaces[2];iesp++) {
+  if ( myParameters.NumberSubSpaces[2] > 0 ) {
+    for (iesp=1;iesp<=myParameters.NumberSubSpaces[2];iesp++) {
       crit_max = 0.;
       for (ipat=1;ipat<=myResult.NbPatch();ipat++) {
        crit_max = Max((myResult(ipat).CritValue()),crit_max);
@@ -803,7 +899,7 @@ void AdvApp2Var_ApproxAFunc2Var::ConvertBS()
   myDegreeInV = ncfv - 1;
 
  // Calculate resulting surfaces 
-  mySurfaces = new ( TColGeom_HArray1OfSurface) (1,  myNumSubSpaces[2]);
+  mySurfaces = new ( TColGeom_HArray1OfSurface) (1,  myParameters.NumberSubSpaces[2]);
 
   Standard_Integer j;
   TColStd_Array1OfReal UKnots (1, myResult.NbPatchInU()+1);
@@ -838,7 +934,7 @@ void AdvApp2Var_ApproxAFunc2Var::ConvertBS()
     new (TColStd_HArray1OfReal) (1, nmax * Size_eq);
 
   Standard_Integer SSP, i;
-  for (SSP=1; SSP <= myNumSubSpaces[2]; SSP++) { 
+  for (SSP=1; SSP <= myParameters.NumberSubSpaces[2]; SSP++) { 
 
     // Creation of the grid of polynoms
     Standard_Integer n=0,icf=1,ieq;
@@ -857,7 +953,7 @@ void AdvApp2Var_ApproxAFunc2Var::ConvertBS()
   
     // Conversion into poles
     Convert_GridPolynomialToPoles CvP (myResult.NbPatchInU(),myResult.NbPatchInV(),
-                                      iu,iv,myMaxDegInU,myMaxDegInV,NbCoeff,
+                                      iu,iv,myParameters.DegreeU,myParameters.DegreeV,NbCoeff,
                                       Poly,Uint1,Vint1,Uint2,Vint2);
     if ( !CvP.IsDone() ) { myDone = Standard_False; }
    
@@ -870,6 +966,21 @@ void AdvApp2Var_ApproxAFunc2Var::ConvertBS()
   }
 }
 
+//=======================================================================
+//function : NumSubSpaces
+//purpose  : 
+//=======================================================================
+
+Standard_Integer
+AdvApp2Var_ApproxAFunc2Var::NumSubSpaces(const Standard_Integer Dimension) const 
+{
+  if (Dimension < 1 || Dimension > 3)
+  {
+    Standard_OutOfRange::Raise ("AdvApp2Var_ApproxAFunc2Var::MaxError : Dimension must be equal to 1,2 or 3 !");
+  }
+  return myParameters.NumberSubSpaces[Dimension-1];
+}
+
 //=======================================================================
 //function : MaxError
 //purpose  : 
@@ -1076,10 +1187,10 @@ void AdvApp2Var_ApproxAFunc2Var::Dump(Standard_OStream& o) const
   else {
     o<<"There is a result";
     if (myDone) {
-      o<<" within the requested tolerance "<<my3DTolerances->Value(iesp)<<endl;
+      o<<" within the requested tolerance "<<myParameters.Tolerances3D->Value(iesp)<<endl;
     }
-    else if (my3DMaxError->Value(iesp)>my3DTolerances->Value(iesp)) {
-      o<<" WITHOUT the requested tolerance "<<my3DTolerances->Value(iesp)<<endl;
+    else if (my3DMaxError->Value(iesp)>myParameters.Tolerances3D->Value(iesp)) {
+      o<<" WITHOUT the requested tolerance "<<myParameters.Tolerances3D->Value(iesp)<<endl;
     }
     else {
       o<<" WITHOUT the requested continuities "<<endl;
index 3930a949c1b4458efa1ff26bc3c3dca3845b1b81..46a380b060228de06e971b2f86f39ee93409c792 100644 (file)
@@ -93,10 +93,110 @@ public:
 
   DEFINE_STANDARD_ALLOC
 
+  struct Parameters
+  {
+    Standard_Integer NumberSubSpaces[3];
+
+    Handle(TColStd_HArray1OfReal) Tolerances1D;
+    Handle(TColStd_HArray1OfReal) Tolerances2D;
+    Handle(TColStd_HArray1OfReal) Tolerances3D;
+    Handle(TColStd_HArray2OfReal) TolerancesOnFrontier1D;
+    Handle(TColStd_HArray2OfReal) TolerancesOnFrontier2D;
+    Handle(TColStd_HArray2OfReal) TolerancesOnFrontier3D;
+
+    Standard_Real FirstParamU;
+    Standard_Real FirstParamV;
+
+    Standard_Real LastParamU;
+    Standard_Real LastParamV;
+
+    GeomAbs_IsoType FavouriteIso;
+
+    GeomAbs_Shape ContinuityU;
+    GeomAbs_Shape ContinuityV;
+
+    Standard_Integer PrecisionCode;
+
+    Standard_Integer DegreeU;
+    Standard_Integer DegreeV;
+
+    Standard_Integer MaxPatchesU;
+    Standard_Integer MaxPatchesV;
+
+    Standard_Integer TotalPatches;
+  };
+
+  Standard_EXPORT AdvApp2Var_ApproxAFunc2Var
+    (
+      const Parameters & parameters,
+      const AdvApp2Var_EvaluatorFunc2Var& Func,
+      AdvApprox_Cutting& UChoice,
+      AdvApprox_Cutting& VChoice
+    );
+
+  Standard_EXPORT AdvApp2Var_ApproxAFunc2Var
+    (
+      const Parameters & parameters,
+      const AdvApp2Var_EvaluatorFunc2Var& Func,
+      const AdvApp2Var_Criterion& Crit,
+      AdvApprox_Cutting& UChoice,
+      AdvApprox_Cutting& VChoice
+    );
   
-  Standard_EXPORT AdvApp2Var_ApproxAFunc2Var(const Standard_Integer Num1DSS, const Standard_Integer Num2DSS, const Standard_Integer Num3DSS, const Handle(TColStd_HArray1OfReal)& OneDTol, const Handle(TColStd_HArray1OfReal)& TwoDTol, const Handle(TColStd_HArray1OfReal)& ThreeDTol, const Handle(TColStd_HArray2OfReal)& OneDTolFr, const Handle(TColStd_HArray2OfReal)& TwoDTolFr, const Handle(TColStd_HArray2OfReal)& ThreeDTolFr, const Standard_Real FirstInU, const Standard_Real LastInU, const Standard_Real FirstInV, const Standard_Real LastInV, const GeomAbs_IsoType FavorIso, const GeomAbs_Shape ContInU, const GeomAbs_Shape ContInV, const Standard_Integer PrecisCode, const Standard_Integer MaxDegInU, const Standard_Integer MaxDegInV, const Standard_Integer MaxPatch, const AdvApp2Var_EvaluatorFunc2Var& Func, AdvApprox_Cutting& UChoice, AdvApprox_Cutting& VChoice);
+  Standard_EXPORT AdvApp2Var_ApproxAFunc2Var
+    (
+      const Standard_Integer Num1DSS,
+      const Standard_Integer Num2DSS,
+      const Standard_Integer Num3DSS,
+      const Handle(TColStd_HArray1OfReal)& OneDTol,
+      const Handle(TColStd_HArray1OfReal)& TwoDTol,
+      const Handle(TColStd_HArray1OfReal)& ThreeDTol,
+      const Handle(TColStd_HArray2OfReal)& OneDTolFr,
+      const Handle(TColStd_HArray2OfReal)& TwoDTolFr,
+      const Handle(TColStd_HArray2OfReal)& ThreeDTolFr,
+      const Standard_Real FirstInU,
+      const Standard_Real LastInU,
+      const Standard_Real FirstInV,
+      const Standard_Real LastInV,
+      const GeomAbs_IsoType FavorIso,
+      const GeomAbs_Shape ContInU,
+      const GeomAbs_Shape ContInV,
+      const Standard_Integer PrecisCode,
+      const Standard_Integer MaxDegInU,
+      const Standard_Integer MaxDegInV,
+      const Standard_Integer MaxPatch,
+      const AdvApp2Var_EvaluatorFunc2Var& Func,
+      AdvApprox_Cutting& UChoice,
+      AdvApprox_Cutting& VChoice
+    );
   
-  Standard_EXPORT AdvApp2Var_ApproxAFunc2Var(const Standard_Integer Num1DSS, const Standard_Integer Num2DSS, const Standard_Integer Num3DSS, const Handle(TColStd_HArray1OfReal)& OneDTol, const Handle(TColStd_HArray1OfReal)& TwoDTol, const Handle(TColStd_HArray1OfReal)& ThreeDTol, const Handle(TColStd_HArray2OfReal)& OneDTolFr, const Handle(TColStd_HArray2OfReal)& TwoDTolFr, const Handle(TColStd_HArray2OfReal)& ThreeDTolFr, const Standard_Real FirstInU, const Standard_Real LastInU, const Standard_Real FirstInV, const Standard_Real LastInV, const GeomAbs_IsoType FavorIso, const GeomAbs_Shape ContInU, const GeomAbs_Shape ContInV, const Standard_Integer PrecisCode, const Standard_Integer MaxDegInU, const Standard_Integer MaxDegInV, const Standard_Integer MaxPatch, const AdvApp2Var_EvaluatorFunc2Var& Func, const AdvApp2Var_Criterion& Crit, AdvApprox_Cutting& UChoice, AdvApprox_Cutting& VChoice);
+  Standard_EXPORT AdvApp2Var_ApproxAFunc2Var
+    (
+      const Standard_Integer Num1DSS,
+      const Standard_Integer Num2DSS,
+      const Standard_Integer Num3DSS,
+      const Handle(TColStd_HArray1OfReal)& OneDTol,
+      const Handle(TColStd_HArray1OfReal)& TwoDTol,
+      const Handle(TColStd_HArray1OfReal)& ThreeDTol,
+      const Handle(TColStd_HArray2OfReal)& OneDTolFr,
+      const Handle(TColStd_HArray2OfReal)& TwoDTolFr,
+      const Handle(TColStd_HArray2OfReal)& ThreeDTolFr,
+      const Standard_Real FirstInU,
+      const Standard_Real LastInU,
+      const Standard_Real FirstInV,
+      const Standard_Real LastInV,
+      const GeomAbs_IsoType FavorIso,
+      const GeomAbs_Shape ContInU,
+      const GeomAbs_Shape ContInV,
+      const Standard_Integer PrecisCode,
+      const Standard_Integer MaxDegInU,
+      const Standard_Integer MaxDegInV,
+      const Standard_Integer MaxPatch,
+      const AdvApp2Var_EvaluatorFunc2Var& Func,
+      const AdvApp2Var_Criterion& Crit,
+      AdvApprox_Cutting& UChoice,
+      AdvApprox_Cutting& VChoice
+    );
   
   //! True if the approximation succeeded within the imposed
   //! tolerances and the wished continuities
@@ -167,7 +267,7 @@ private:
   
   //! Initialisation of the approximation with a grid of regular cuttings ;
   //! used by Init and Perform
-  Standard_EXPORT void InitGrid (const Standard_Integer NbInt);
+  Standard_EXPORT void InitGrid (const Standard_Integer sizeU, const Standard_Integer sizeV);
   
   //! Computation of the approximation result ; used by Create
   Standard_EXPORT void Perform (const AdvApprox_Cutting& UChoice, const AdvApprox_Cutting& VChoice, const AdvApp2Var_EvaluatorFunc2Var& Func);
@@ -197,25 +297,8 @@ private:
   //! Conversion of the approximation result in BSpline; used by Create
   Standard_EXPORT void ConvertBS();
 
+  Parameters myParameters;
 
-  Standard_Integer myNumSubSpaces[3];
-  Handle(TColStd_HArray1OfReal) my1DTolerances;
-  Handle(TColStd_HArray1OfReal) my2DTolerances;
-  Handle(TColStd_HArray1OfReal) my3DTolerances;
-  Handle(TColStd_HArray2OfReal) my1DTolOnFront;
-  Handle(TColStd_HArray2OfReal) my2DTolOnFront;
-  Handle(TColStd_HArray2OfReal) my3DTolOnFront;
-  Standard_Real myFirstParInU;
-  Standard_Real myLastParInU;
-  Standard_Real myFirstParInV;
-  Standard_Real myLastParInV;
-  GeomAbs_IsoType myFavoriteIso;
-  GeomAbs_Shape myContInU;
-  GeomAbs_Shape myContInV;
-  Standard_Integer myPrecisionCode;
-  Standard_Integer myMaxDegInU;
-  Standard_Integer myMaxDegInV;
-  Standard_Integer myMaxPatches;
   AdvApp2Var_Context myConditions;
   AdvApp2Var_Network myResult;
   AdvApp2Var_Framework myConstraints;
index 0f4f55505e54373927d6b5027632789d8a1e44c2..576d308314378f96d666ba7bf2d62b74108f65ee 100644 (file)
@@ -42,8 +42,3 @@ AdvApp2Var_ApproxAFunc2Var::Surface( const Standard_Integer SSPIndex) const
   return myDegreeInV;
 }
 
- inline Standard_Integer AdvApp2Var_ApproxAFunc2Var::NumSubSpaces(const Standard_Integer Dimension) const 
-{
-  return myNumSubSpaces[Dimension-1];
-}
-
index dc53d80cf44ea23bc7b2bb71ff8b05f5c0f0e695..b2fdbc2cd8e60e29f74dfdac6deb768fbaf18f67 100644 (file)
@@ -235,10 +235,39 @@ void GeomPlate_MakeApprox_Eval::Evaluate (Standard_Integer * Dimension,
     }
     break;
   }
- }     
+ }
+}
 
+//=======================================================================
+//function : GeomPlate_MakeApprox
+//purpose  : 
+//=======================================================================
+GeomPlate_MakeApprox::GeomPlate_MakeApprox
+(
+  const Handle(GeomPlate_Surface)& SurfPlate,
+  const AdvApp2Var_Criterion& PlateCrit,
+  const Parameters & parameters,
+  const Standard_Real EnlargeCoeff
+): myPlate (SurfPlate)
+{
+  Perform(parameters, &PlateCrit, EnlargeCoeff);
 }
 
+//=======================================================================
+//function : GeomPlate_MakeApprox
+//purpose  : 
+//=======================================================================
+GeomPlate_MakeApprox::GeomPlate_MakeApprox
+(
+  const Handle(GeomPlate_Surface)& SurfPlate,
+  const Parameters & parameters,
+  const Standard_Integer CritOrder,
+  const Standard_Real dmax,
+  const Standard_Real EnlargeCoeff
+): myPlate (SurfPlate)
+{
+  Perform(parameters, CritOrder, dmax, EnlargeCoeff);
+}
 
 //=======================================================================
 //function : GeomPlate_MakeApprox
@@ -251,55 +280,18 @@ GeomPlate_MakeApprox::GeomPlate_MakeApprox(const Handle(GeomPlate_Surface)& Surf
                                           const Standard_Integer Nbmax,
                                           const Standard_Integer dgmax,
                                           const GeomAbs_Shape Continuity,
-                                          const Standard_Real EnlargeCoeff)
+                                          const Standard_Real EnlargeCoeff
+): myPlate (SurfPlate)
 {
-  myPlate = SurfPlate;
-
-  Standard_Real U0=0., U1=0., V0=0., V1=0.;
-  myPlate->RealBounds(U0, U1, V0, V1);
-  U0 = EnlargeCoeff * U0;
-  U1 = EnlargeCoeff * U1;
-  V0 = EnlargeCoeff * V0;
-  V1 = EnlargeCoeff * V1;
-
-  Standard_Integer nb1 = 0, nb2 = 0, nb3 = 1;
-  Handle(TColStd_HArray1OfReal) nul1 =
-                new TColStd_HArray1OfReal(1,1);
-  nul1->Init(0.);
-  Handle(TColStd_HArray2OfReal) nul2 =
-                new TColStd_HArray2OfReal(1,1,1,4);
-  nul2->Init(0.);
-  Handle(TColStd_HArray1OfReal) eps3D =
-                new TColStd_HArray1OfReal(1,1);
-  eps3D->Init(Tol3d);
-  Handle(TColStd_HArray2OfReal) epsfr =
-                new TColStd_HArray2OfReal(1,1,1,4);
-  epsfr->Init(Tol3d);
-  GeomAbs_IsoType myType = GeomAbs_IsoV;
-  Standard_Integer myPrec = 0;
+  Parameters parameters;
 
-  AdvApprox_DichoCutting myDec;
+  parameters.Tolerance3D = Tol3d;
+  parameters.ContinuityU = parameters.ContinuityV = Continuity;
+  parameters.DegreeU = parameters.DegreeV = dgmax;
+  parameters.MaxPatchesU = parameters.MaxPatchesV = IntegerLast();
+  parameters.TotalPatches = Nbmax;
 
-//POP pour WNT
-  GeomPlate_MakeApprox_Eval ev (myPlate);
-  AdvApp2Var_ApproxAFunc2Var AppPlate(nb1, nb2, nb3,
-                                     nul1,nul1,eps3D,
-                                     nul2,nul2,epsfr,
-                                     U0,U1,V0,V1,
-                                     myType,
-                                     Continuity, Continuity,
-                                     myPrec, 
-                                     dgmax,dgmax,Nbmax,ev,
-//                                   dgmax,dgmax,Nbmax,myPlateSurfEval,
-                                     PlateCrit,myDec,myDec);
-  mySurface = AppPlate.Surface(1);
-  myAppError = AppPlate.MaxError(3,1);
-  myCritError = AppPlate.CritError(3,1);
-#ifdef OCCT_DEBUG
-  cout<<"Approximation results"<<endl;
-  cout<<"  Approximation error : "<<myAppError<<endl;
-  cout<<"  Criterium error : "<<myCritError<<endl;
-#endif
+  Perform(parameters, &PlateCrit, EnlargeCoeff);
 }
 
 
@@ -315,146 +307,209 @@ GeomPlate_MakeApprox::GeomPlate_MakeApprox(const Handle(GeomPlate_Surface)& Surf
                                           const Standard_Real dmax,
                                           const Standard_Integer CritOrder,
                                           const GeomAbs_Shape Continuity,
-                                          const Standard_Real EnlargeCoeff)
+                                          const Standard_Real EnlargeCoeff
+): myPlate (SurfPlate)
 {
-  myPlate = SurfPlate;
-
-  TColgp_SequenceOfXY Seq2d;
-  TColgp_SequenceOfXYZ Seq3d;
-
-  if (CritOrder>=0) {
-
-//    contraintes 2d d'ordre 0
-    myPlate->Constraints(Seq2d);
-
-//    contraintes 3d correspondantes sur plate
-    Standard_Integer i,nbp=Seq2d.Length();
-    for(i=1;i<=nbp;i++){
-      gp_XY P2d=Seq2d.Value(i);
-      gp_Pnt PP;
-      gp_Vec v1h,v2h,v3h;
-      if (CritOrder==0) {
-//    a l'ordre 0
-       myPlate->D0 (P2d.X(), P2d.Y(), PP);
-       gp_XYZ P3d(PP.X(),PP.Y(),PP.Z());
-       Seq3d.Append(P3d);
-      }
-      else {
-//    a l'ordre 1
-       myPlate->D1 (P2d.X(), P2d.Y(), PP, v1h, v2h);
-       v3h=v1h^v2h;
-       gp_XYZ P3d(v3h.X(),v3h.Y(),v3h.Z());
-       Seq3d.Append(P3d);
-      }
-    }
+  Parameters parameters;
+
+  parameters.Tolerance3D = Tol3d;
+  parameters.ContinuityU = parameters.ContinuityV = Continuity;
+  parameters.DegreeU = parameters.DegreeV = dgmax;
+  parameters.MaxPatchesU = parameters.MaxPatchesV = IntegerLast();
+  parameters.TotalPatches = Nbmax;
+
+  Perform(parameters, CritOrder, dmax, EnlargeCoeff);
+}
+
+//=======================================================================
+//function : Perform
+//purpose  : 
+//=======================================================================
+void GeomPlate_MakeApprox::Perform
+(
+  const Parameters & parameters,
+  const Standard_Integer CritOrder,
+  const Standard_Real dmax,
+  const Standard_Real EnlargeCoeff
+)
+{
+  if (myPlate.IsNull() || CritOrder > 1)
+  {
+    return;
   }
 
-  Standard_Real U0=0., U1=0., V0=0., V1=0.;
-  myPlate->RealBounds(U0, U1, V0, V1);
-  U0 = EnlargeCoeff * U0;
-  U1 = EnlargeCoeff * U1;
-  V0 = EnlargeCoeff * V0;
-  V1 = EnlargeCoeff * V1;
+  AdvApp2Var_Criterion * criterion = nullptr;
+
+  if (CritOrder >= 0)
+  {
+    TColgp_SequenceOfXY Seq2d;
+    TColgp_SequenceOfXYZ Seq3d;
+
+    {
+      // contraintes 2d d'ordre 0
+      myPlate->Constraints(Seq2d);
+
+      // contraintes 3d correspondantes sur plate
+      for(Standard_Integer i = 1; i <= Seq2d.Length(); ++i)
+      {
+        gp_XY P2d=Seq2d.Value(i);
+        gp_Pnt PP;
+        gp_Vec v1h,v2h,v3h;
+        if (CritOrder==0)
+        {
+          //    a l'ordre 0
+          myPlate->D0 (P2d.X(), P2d.Y(), PP);
+          gp_XYZ P3d(PP.X(),PP.Y(),PP.Z());
+          Seq3d.Append(P3d);
+        }
+        else
+        {
+          //    a l'ordre 1
+          myPlate->D1 (P2d.X(), P2d.Y(), PP, v1h, v2h);
+          v3h=v1h^v2h;
+          gp_XYZ P3d(v3h.X(),v3h.Y(),v3h.Z());
+          Seq3d.Append(P3d);
+        }
+      }
+    }
 
-  Standard_Real seuil = Tol3d;
-  if (CritOrder==0&&Tol3d<10*dmax) {
-    seuil=10*dmax;
+    Standard_Real seuil = parameters.Tolerance3D;
+    if (parameters.Tolerance3D < 10 * dmax)
+    {
+      seuil = 10 * dmax;
 #ifdef OCCT_DEBUG
-    cout<<"Seuil G0 choisi trop faible par rapport au contour. On prend "<<seuil<<endl;
+      cout<<"Seuil G" << CritOrder << " choisi trop faible par rapport au contour. On prend "<<seuil<<endl;
 #endif
+    }
+
+    if (0 == CritOrder)
+    {
+      criterion = new GeomPlate_PlateG0Criterion (Seq2d, Seq3d, seuil);
+    }
+    else if (1 == CritOrder)
+    {
+      criterion = new GeomPlate_PlateG1Criterion (Seq2d, Seq3d, seuil);
+    }
+
+    if (nullptr == criterion)
+    {
+      return;
+    }
   }
-  if (CritOrder==1&&Tol3d<10*dmax) {
-    seuil=10*dmax;
-#ifdef OCCT_DEBUG
-    cout<<"Seuil G1 choisi trop faible par rapport au contour. On prend "<<seuil<<endl;
-#endif
+
+  Perform(parameters, criterion, EnlargeCoeff);
+
+  if (nullptr != criterion)
+  {
+    delete criterion;
+  }
+}
+  
+//=======================================================================
+//function : Perform
+//purpose  : 
+//=======================================================================
+void GeomPlate_MakeApprox::Perform
+(
+  const Parameters & parameters,
+  const AdvApp2Var_Criterion * criterion,
+  const Standard_Real EnlargeCoeff
+)
+{
+  if (myPlate.IsNull())
+  {
+    return;
   }
-  Standard_Integer nb1 = 0, nb2 = 0, nb3 = 1;
-  Handle(TColStd_HArray1OfReal) nul1 =
-                new TColStd_HArray1OfReal(1,1);
-  nul1->Init(0.);
-  Handle(TColStd_HArray2OfReal) nul2 =
-                new TColStd_HArray2OfReal(1,1,1,4);
-  nul2->Init(0.);
-  Handle(TColStd_HArray1OfReal) eps3D =
-                new TColStd_HArray1OfReal(1,1);
-  eps3D->Init(Tol3d);
-  Handle(TColStd_HArray2OfReal) epsfr =
-                new TColStd_HArray2OfReal(1,1,1,4);
-  epsfr->Init(Tol3d);
-
-  GeomAbs_IsoType myType = GeomAbs_IsoV;
-  Standard_Integer myPrec = 0;
+
+  AdvApp2Var_ApproxAFunc2Var::Parameters approxParameters;
+
+  approxParameters.NumberSubSpaces[0] = 0;
+  approxParameters.NumberSubSpaces[1] = 0;
+  approxParameters.NumberSubSpaces[2] = 1;
+
+  {
+    Standard_Real U0=0., U1=0., V0=0., V1=0.;
+    myPlate->RealBounds(U0, U1, V0, V1);
+
+    approxParameters.FirstParamU  = EnlargeCoeff * U0;
+    approxParameters.LastParamU   = EnlargeCoeff * U1;
+    approxParameters.FirstParamV  = EnlargeCoeff * V0;
+    approxParameters.LastParamV   = EnlargeCoeff * V1;
+  }
+
+  {
+    Handle(TColStd_HArray1OfReal) nul1 = new TColStd_HArray1OfReal(1,1);
+    nul1->Init(0.);
+    Handle(TColStd_HArray2OfReal) nul2 = new TColStd_HArray2OfReal(1,1,1,4);
+    nul2->Init(0.);
+    Handle(TColStd_HArray1OfReal) eps3D = new TColStd_HArray1OfReal(1,1);
+    eps3D->Init(parameters.Tolerance3D);
+    Handle(TColStd_HArray2OfReal) epsfr = new TColStd_HArray2OfReal(1,1,1,4);
+    epsfr->Init(parameters.Tolerance3D);
+
+    approxParameters.Tolerances1D = nul1;
+    approxParameters.Tolerances2D = nul1;
+    approxParameters.Tolerances3D = eps3D;
+
+    approxParameters.TolerancesOnFrontier1D = nul2;
+    approxParameters.TolerancesOnFrontier2D = nul2;
+    approxParameters.TolerancesOnFrontier3D = epsfr;
+  }
+
+  approxParameters.FavouriteIso = GeomAbs_IsoV;
+
+  approxParameters.ContinuityU = parameters.ContinuityU;
+  approxParameters.ContinuityV = parameters.ContinuityV;
+
+  approxParameters.PrecisionCode = 0;
+
+  approxParameters.DegreeU = parameters.DegreeU;
+  approxParameters.DegreeV = parameters.DegreeV;
+
+  approxParameters.MaxPatchesU = parameters.MaxPatchesU;
+  approxParameters.MaxPatchesV = parameters.MaxPatchesV;
+
+  approxParameters.TotalPatches = parameters.TotalPatches;
 
   AdvApprox_DichoCutting myDec;
+  GeomPlate_MakeApprox_Eval ev (myPlate);
+
+  if (nullptr == criterion)
+  {
+    approxParameters.PrecisionCode =  1;
+
+    AdvApp2Var_ApproxAFunc2Var AppPlate
+      (
+        approxParameters,
+        ev,
+        myDec, myDec
+      );
 
-  if (CritOrder==-1) {
-    myPrec = 1;
-// POP pour NT
-    GeomPlate_MakeApprox_Eval ev (myPlate);
-    AdvApp2Var_ApproxAFunc2Var AppPlate(nb1, nb2, nb3,
-                                       nul1,nul1,eps3D,
-                                       nul2,nul2,epsfr,
-                                       U0,U1,V0,V1,
-                                       myType,
-                                       Continuity, Continuity,
-                                       myPrec,
-                                       dgmax,dgmax,Nbmax,ev,
-                                       myDec,myDec);
     mySurface = AppPlate.Surface(1);
     myAppError = AppPlate.MaxError(3,1);
     myCritError = 0.;
-#ifdef OCCT_DEBUG
-    cout<<"Approximation results"<<endl;
-    cout<<"  Approximation error : "<<myAppError<<endl;
-#endif
   }
-  else if (CritOrder==0) {
-    GeomPlate_PlateG0Criterion Crit0(Seq2d,Seq3d,seuil);
-// POP pour NT
-    GeomPlate_MakeApprox_Eval ev (myPlate);
-    AdvApp2Var_ApproxAFunc2Var AppPlate(nb1, nb2, nb3,
-                                       nul1,nul1,eps3D,
-                                       nul2,nul2,epsfr,
-                                       U0,U1,V0,V1,
-                                       myType,
-                                       Continuity, Continuity,
-                                       myPrec,
-                                       dgmax,dgmax,Nbmax,ev,
-//                                     dgmax,dgmax,Nbmax,myPlateSurfEval,
-                                       Crit0,myDec,myDec);
+  else
+  {
+    // POP pour NT
+    AdvApp2Var_ApproxAFunc2Var AppPlate
+      (
+        approxParameters,
+        ev,
+        *criterion,
+        myDec,myDec
+      );
+
     mySurface = AppPlate.Surface(1);
     myAppError = AppPlate.MaxError(3,1);
     myCritError = AppPlate.CritError(3,1);
-#ifdef OCCT_DEBUG
-    cout<<"Approximation results"<<endl;
-    cout<<"  Approximation error : "<<myAppError<<endl;
-    cout<<"  Criterium error : "<<myCritError<<endl;
-#endif
   }
-  else if (CritOrder==1) {
-    GeomPlate_PlateG1Criterion Crit1(Seq2d,Seq3d,seuil);
-// POP pour NT
-    GeomPlate_MakeApprox_Eval ev (myPlate);
-    AdvApp2Var_ApproxAFunc2Var AppPlate(nb1, nb2, nb3,
-                                       nul1,nul1,eps3D,
-                                       nul2,nul2,epsfr,
-                                       U0,U1,V0,V1,
-                                       myType,
-                                       Continuity, Continuity,
-                                       myPrec,
-                                       dgmax,dgmax,Nbmax,ev,
-//                                     dgmax,dgmax,Nbmax,myPlateSurfEval,
-                                       Crit1,myDec,myDec);
-    mySurface = AppPlate.Surface(1);
-    myAppError = AppPlate.MaxError(3,1);
-    myCritError = AppPlate.CritError(3,1);
+
 #ifdef OCCT_DEBUG
-    cout<<"Approximation results"<<endl;
-    cout<<"  Approximation error : "<<myAppError<<endl;
-    cout<<"  Criterium error : "<<myCritError<<endl;
+  cout<<"Approximation results"<<endl;
+  cout<<"  Approximation error : "<<myAppError<<endl;
+  cout<<"  Criterium error : "<<myCritError<<endl;
 #endif
-  }
 }
 
 
index 5656e40af5e6dac0c1654905731df36d384b17c7..09dcc1d21ee556df7e40750ee3d9d19a6a4df52e 100644 (file)
@@ -34,9 +34,26 @@ class AdvApp2Var_Criterion;
 class GeomPlate_MakeApprox 
 {
 public:
-
   DEFINE_STANDARD_ALLOC
 
+  struct Parameters
+  {
+    Standard_Real Tolerance3D;
+
+    GeomAbs_Shape ContinuityU;
+    GeomAbs_Shape ContinuityV;
+
+    Standard_Integer DegreeU;
+    Standard_Integer DegreeV;
+
+    Standard_Integer MaxPatchesU;
+    Standard_Integer MaxPatchesV;
+
+    Standard_Integer TotalPatches;
+  };
+
+  Standard_EXPORT GeomPlate_MakeApprox (const Handle(GeomPlate_Surface)& SurfPlate, const AdvApp2Var_Criterion& PlateCrit, const Parameters & parameters, const Standard_Real EnlargeCoeff = 1.1);
+  Standard_EXPORT GeomPlate_MakeApprox (const Handle(GeomPlate_Surface)& SurfPlate, const Parameters & parameters, const Standard_Integer CritOrder, const Standard_Real dmax, const Standard_Real EnlargeCoeff = 1.1);
   
   //! Converts SurfPlate into a Geom_BSplineSurface with
   //! n Bezier pieces (n<=Nbmax) of degree <= dgmax
@@ -69,14 +86,21 @@ public:
   //! curve and point constraints only.
   Standard_EXPORT Standard_Real CriterionError() const;
 
-
-
-
-protected:
-
-
-
-
+private:
+  void Perform
+    (
+      const Parameters & parameters,
+      const Standard_Integer CritOrder,
+      const Standard_Real dmax,
+      const Standard_Real EnlargeCoeff
+    );
+
+  void Perform
+    (
+      const Parameters & parameters,
+      const AdvApp2Var_Criterion * criterion,
+      const Standard_Real EnlargeCoeff
+    );
 
 private:
 
index 2b88cf893e89164234276a0e1c0115124e438b6c..81f899cf4181e03ed8e7575db4b1f8666f45afef 100644 (file)
@@ -2140,6 +2140,187 @@ static Standard_Integer OCC27875(Draw_Interpretor& theDI,
   return 0;
 }
 
+#include <BRepAdaptor_HCurve.hxx>
+#include <BRepAdaptor_HCurve2d.hxx>
+#include <BRepAdaptor_HSurface.hxx>
+#include <BRepFill_CurveConstraint.hxx>
+#include <GeomPlate_BuildPlateSurface.hxx>
+#include <GeomPlate_MakeApprox.hxx>
+#include <GeomPlate_PlateG0Criterion.hxx>
+#include <GeomPlate_Surface.hxx>
+static Standard_Integer OCC27903(Draw_Interpretor& theDI,
+  Standard_Integer n,
+  const char ** a)
+{
+  /*
+  This test code is a copy-paste of the gplate code, but with the added arguments for the degree, continuity and segments count
+  */
+  if ( n < 13 )
+  {
+    theDI << "Not enough arguments\n";
+    return 1;
+  }
+
+  Standard_Integer NbCurFront = Draw::Atoi(a[9]);
+  Standard_Integer NbPointConstraint = Draw::Atoi(a[10]);
+
+  GeomPlate_BuildPlateSurface Henri(3, 15, 2);
+
+  Standard_Integer Indice=11;
+
+  {
+    TopoDS_Shape aLocalFace (DBRep::Get(a[Indice++],TopAbs_FACE));
+    TopoDS_Face SI = TopoDS::Face(aLocalFace);
+    if(SI.IsNull()) 
+    {
+      theDI << "Wrong arguments\n";
+      return 1;
+    }
+
+    {
+      Handle(BRepAdaptor_HSurface) HSI = new BRepAdaptor_HSurface();
+      HSI->ChangeSurface().Initialize(SI);
+      Henri.LoadInitSurface( BRep_Tool::Surface(HSI->ChangeSurface().Face()));
+    }
+  }
+
+  for (Standard_Integer i=1; i<=NbCurFront ; i++)
+  { 
+    TopoDS_Shape aLocalShape(DBRep::Get(a[Indice++],TopAbs_EDGE));
+    TopoDS_Edge E = TopoDS::Edge(aLocalShape);
+
+    if(E.IsNull())
+    {
+      theDI << "Wrong arguments\n";
+      return 1;
+    }
+
+    Standard_Integer Conti=Draw::Atoi(a[Indice++]);
+    if (Conti==0 || Conti==-1)
+    { 
+      Handle(BRepAdaptor_HCurve) C = new BRepAdaptor_HCurve();
+      C->ChangeCurve().Initialize(E);
+      const Handle(Adaptor3d_HCurve)& aC = C; // to avoid ambiguity
+      Handle(GeomPlate_CurveConstraint) Cont= new BRepFill_CurveConstraint(aC,Conti);
+      Henri.Add(Cont);
+    }
+    else 
+    { 
+      TopoDS_Shape aLocalFace = DBRep::Get(a[Indice++],TopAbs_FACE);
+      TopoDS_Face F = TopoDS::Face(aLocalFace);
+
+      if(F.IsNull()) 
+      {
+        theDI << "Wrong arguments\n";
+        return 1;
+      }
+      Handle(BRepAdaptor_HSurface) S = new BRepAdaptor_HSurface();
+      S->ChangeSurface().Initialize(F);
+      Handle(BRepAdaptor_HCurve2d) C = new BRepAdaptor_HCurve2d();
+      C->ChangeCurve2d().Initialize(E,F);
+      Adaptor3d_CurveOnSurface ConS(C,S);
+
+      Handle (Adaptor3d_HCurveOnSurface) HConS = new Adaptor3d_HCurveOnSurface(ConS);
+      Handle(GeomPlate_CurveConstraint) Cont= new BRepFill_CurveConstraint(HConS,Conti);
+      Henri.Add(Cont);
+    }
+  }
+
+  for (Standard_Integer i=1; i<=NbPointConstraint ; i++) 
+  { 
+    gp_Pnt P1;
+
+    if (DrawTrSurf::GetPoint(a[Indice], P1) ) 
+    {
+      Handle(GeomPlate_PointConstraint) PCont = new GeomPlate_PointConstraint(P1,0);
+      Henri.Add(PCont);
+      Indice++;
+    }
+    else
+    { 
+      Standard_Real u=Draw::Atof(a[Indice++]), 
+      v=Draw::Atof(a[Indice++]);
+
+      Standard_Integer Conti=Draw::Atoi(a[Indice++]);
+      TopoDS_Shape aLocalFace = DBRep::Get(a[Indice++],TopAbs_FACE);
+      TopoDS_Face F = TopoDS::Face(aLocalFace);
+
+      if(F.IsNull()) 
+      {
+        theDI << "Wrong arguments\n";
+        return 1;      
+      }
+
+      Handle(BRepAdaptor_HSurface) HF = new BRepAdaptor_HSurface();
+      HF->ChangeSurface().Initialize(F);
+      Handle(GeomPlate_PointConstraint) PCont= new GeomPlate_PointConstraint(u,v,BRep_Tool::Surface(HF->ChangeSurface().Face()),Conti,0.001,0.001,0.001);
+      Henri.Add(PCont);
+    }
+  }
+
+  Henri.Perform();
+
+  Handle(GeomPlate_Surface) gpPlate = Henri.Surface();
+  TColgp_SequenceOfXY S2d;
+  TColgp_SequenceOfXYZ S3d;
+  S2d.Clear();
+  S3d.Clear();
+  Henri.Disc2dContour(4,S2d);
+  Henri.Disc3dContour(4,0,S3d);
+  Standard_Real seuil = Max(0.0001, 10 * Henri.G0Error());
+  GeomPlate_PlateG0Criterion critere (S2d, S3d, seuil);
+
+  Standard_Integer nbcarreau=9;
+  Standard_Integer degmax=8;
+
+  GeomPlate_MakeApprox::Parameters params;
+  Standard_Integer continuity = Draw::Atoi(a[4]);
+  switch (continuity)
+  {
+  case 0: params.ContinuityU = GeomAbs_C0; break;
+  case 1: params.ContinuityU = GeomAbs_C1; break;
+  case 2: params.ContinuityU = GeomAbs_C2; break;
+  case 3: params.ContinuityU = GeomAbs_C3; break;
+  default: params.ContinuityU = GeomAbs_CN; break;
+  }
+  continuity = Draw::Atoi(a[5]);
+  switch (continuity)
+  {
+  case 0: params.ContinuityV = GeomAbs_C0; break;
+  case 1: params.ContinuityV = GeomAbs_C1; break;
+  case 2: params.ContinuityV = GeomAbs_C2; break;
+  case 3: params.ContinuityV = GeomAbs_C3; break;
+  default: params.ContinuityV = GeomAbs_CN; break;
+  }
+
+  params.DegreeU = Draw::Atoi(a[2]);
+  params.DegreeV = Draw::Atoi(a[3]);
+
+  params.MaxPatchesU = Draw::Atoi(a[6]);
+  params.MaxPatchesV = Draw::Atoi(a[7]);
+
+  params.TotalPatches = Draw::Atoi(a[8]);
+
+  params.Tolerance3D = 0.0001;
+
+  GeomPlate_MakeApprox approx (gpPlate, critere, params);
+  Handle (Geom_BSplineSurface) bspline (approx.Surface());
+
+  if (bspline.IsNull())
+  {
+    theDI << "GeomPlate_MakeApprox is not done.\n";
+  }
+
+  {
+    Standard_Real Umin, Umax, Vmin, Vmax;
+    Henri.Surface()->Bounds( Umin, Umax, Vmin, Vmax);
+    BRepBuilderAPI_MakeFace MF(bspline, Umin, Umax, Vmin, Vmax, Precision::Confusion());
+    DBRep::Set(a[1], MF.Face());
+  }
+  
+  return 0;
+}
+
 #include <OSD_Parallel.hxx>
 
 namespace {
@@ -2202,7 +2383,8 @@ void QABugs::Commands_20(Draw_Interpretor& theCommands) {
   theCommands.Add("OCC26270", "OCC26270 shape result", __FILE__, OCC26270, group);
   theCommands.Add ("OCC27552", "OCC27552", __FILE__, OCC27552, group); 
   theCommands.Add("OCC27875", "OCC27875 curve", __FILE__, OCC27875, group);
+  theCommands.Add("OCC27903", "OCC27903 result degmaxU degmaxV contU contV segmaxU segmaxV totalsegmax nbrcurfront nbrpntconst SurfInit [edge 0] [edge tang (1:G1;2:G2) surf]... [point] [u v tang (1:G1;2:G2) surf] ...", __FILE__, OCC27903, group);
   theCommands.Add("OCC28217", "OCC28217", __FILE__, OCC28217, group);
-
+  
   return;
 }
diff --git a/tests/bugs/modalg_6/bug27903 b/tests/bugs/modalg_6/bug27903
new file mode 100644 (file)
index 0000000..438faa5
--- /dev/null
@@ -0,0 +1,26 @@
+pload QAcommands
+
+puts "============"
+puts "OCC27903"
+puts "============"
+puts ""
+######################################################
+# Enhanced approximation algorithm
+######################################################
+
+plane p 
+trim p p -1 3 -1 3 
+mkface p p 
+
+beziercurve c1 3 0 0 0 1 0 1 2 0 0 
+mkedge e1 c1 
+tcopy e1 e2 
+tcopy e1 e3 
+
+ttranslate e2 0 2 0 
+trotate e3 0 0 0 0 0 1 90 
+tcopy e3 e4 
+ttranslate e4 2 0 0 
+# create the surface 
+OCC27903 r1 5 5 0 2 100 100 5000 4 0 p e1 0 e2 0 e3 0 e4 0 
+checkshape r1