From a793b75e21053455300fd711b1c4487480adc918 Mon Sep 17 00:00:00 2001 From: azv Date: Wed, 6 Apr 2022 22:49:01 +0300 Subject: [PATCH] 0032809: Sweep algorithm with Round Corner mode failed Fix indentation within GeomFill_Sweep.cxx 0032809: Sweep algorithm with Round Corner mode failed Add fix what repair shipping at corner after circle edge at path Add fix test for bug 24909_3 --- src/BRepFill/BRepFill_Sweep.cxx | 6 +- src/GeomFill/GeomFill_Sweep.cxx | 1011 +++++++++++++++---------------- tests/pipe/bugs/bug24909_3 | 8 +- tests/pipe/bugs/bug32809 | 16 + tests/pipe/bugs/end | 1 + 5 files changed, 530 insertions(+), 512 deletions(-) create mode 100644 tests/pipe/bugs/bug32809 create mode 100644 tests/pipe/bugs/end diff --git a/src/BRepFill/BRepFill_Sweep.cxx b/src/BRepFill/BRepFill_Sweep.cxx index d26a35f807..a74fdfc452 100644 --- a/src/BRepFill/BRepFill_Sweep.cxx +++ b/src/BRepFill/BRepFill_Sweep.cxx @@ -861,7 +861,8 @@ static Standard_Boolean Filling(const TopoDS_Shape& EF, Prof2 = BRep_Tool::Curve(E2, f2, l2); // Indeed, both Prof1 and Prof2 are the same curves but in different positions - + // Prof1's param domain may equals to Prof2's param domain *(-1), which means EF.Orientation() == EL.Orientation() + Standard_Boolean bSameCurveDomain = EF.Orientation() != EL.Orientation(); gp_Pnt P1, P2, P; // Choose the angle of opening @@ -887,7 +888,8 @@ static Standard_Boolean Filling(const TopoDS_Shape& EF, } } - const gp_Pnt aP2 = Prof2->Value(aPrm[aMaxIdx]).Transformed(aTf); + const Standard_Real aPrm2[] = { f2, 0.5*(f2 + l2), l2 }; + const gp_Pnt aP2 = Prof2->Value(aPrm2[bSameCurveDomain ? aMaxIdx : 2 - aMaxIdx]).Transformed(aTf); const gp_Vec2d aV1(aP1[aMaxIdx].Z(), aP1[aMaxIdx].X()); const gp_Vec2d aV2(aP2.Z(), aP2.X()); if (aV1.SquareMagnitude() <= gp::Resolution() || diff --git a/src/GeomFill/GeomFill_Sweep.cxx b/src/GeomFill/GeomFill_Sweep.cxx index 95804f3d26..4336c619b6 100644 --- a/src/GeomFill/GeomFill_Sweep.cxx +++ b/src/GeomFill/GeomFill_Sweep.cxx @@ -76,34 +76,34 @@ //======================================================================= class GeomFill_Sweep_Eval : public AdvApprox_EvaluatorFunction { - public: - GeomFill_Sweep_Eval (GeomFill_LocFunction& theTool) +public: + GeomFill_Sweep_Eval(GeomFill_LocFunction& theTool) : theAncore(theTool) {} - - virtual void Evaluate (Standard_Integer *Dimension, - Standard_Real StartEnd[2], - Standard_Real *Parameter, - Standard_Integer *DerivativeRequest, - Standard_Real *Result, // [Dimension] - Standard_Integer *ErrorCode); - - private: + + virtual void Evaluate(Standard_Integer *Dimension, + Standard_Real StartEnd[2], + Standard_Real *Parameter, + Standard_Integer *DerivativeRequest, + Standard_Real *Result, // [Dimension] + Standard_Integer *ErrorCode); + +private: GeomFill_LocFunction& theAncore; }; -void GeomFill_Sweep_Eval::Evaluate (Standard_Integer *,/*Dimension*/ - Standard_Real StartEnd[2], - Standard_Real *Parameter, - Standard_Integer *DerivativeRequest, - Standard_Real *Result,// [Dimension] - Standard_Integer *ErrorCode) +void GeomFill_Sweep_Eval::Evaluate(Standard_Integer *,/*Dimension*/ + Standard_Real StartEnd[2], + Standard_Real *Parameter, + Standard_Integer *DerivativeRequest, + Standard_Real *Result,// [Dimension] + Standard_Integer *ErrorCode) { - theAncore.DN (*Parameter, - StartEnd[0], - StartEnd[1], - *DerivativeRequest, - Result[0], - ErrorCode[0]); + theAncore.DN(*Parameter, + StartEnd[0], + StartEnd[1], + *DerivativeRequest, + Result[0], + ErrorCode[0]); } //=============================================================== @@ -111,12 +111,12 @@ void GeomFill_Sweep_Eval::Evaluate (Standard_Integer *,/*Dimension*/ // Purpose : //=============================================================== GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, - const Standard_Boolean WithKpart) + const Standard_Boolean WithKpart) { done = Standard_False; - myLoc = Location; - myKPart = WithKpart; + myLoc = Location; + myKPart = WithKpart; SetTolerance(1.e-4); myForceApproxC1 = Standard_False; @@ -129,13 +129,13 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : SetDomain // Purpose : //=============================================================== - void GeomFill_Sweep::SetDomain(const Standard_Real LocFirst, - const Standard_Real LocLast, - const Standard_Real SectionFirst, - const Standard_Real SectionLast) +void GeomFill_Sweep::SetDomain(const Standard_Real LocFirst, + const Standard_Real LocLast, + const Standard_Real SectionFirst, + const Standard_Real SectionLast) { First = LocFirst; - Last = LocLast; + Last = LocLast; SFirst = SectionFirst; SLast = SectionLast; } @@ -144,14 +144,14 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : SetTolerance // Purpose : //=============================================================== - void GeomFill_Sweep::SetTolerance(const Standard_Real Tolerance3d, - const Standard_Real BoundTolerance, - const Standard_Real Tolerance2d, - const Standard_Real ToleranceAngular) +void GeomFill_Sweep::SetTolerance(const Standard_Real Tolerance3d, + const Standard_Real BoundTolerance, + const Standard_Real Tolerance2d, + const Standard_Real ToleranceAngular) { Tol3d = Tolerance3d; BoundTol = BoundTolerance; - Tol2d =Tolerance2d; + Tol2d = Tolerance2d; TolAngular = ToleranceAngular; } @@ -161,7 +161,7 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // a C1-continuous surface if a swept surface proved // to be C0. //======================================================================= - void GeomFill_Sweep::SetForceApproxC1(const Standard_Boolean ForceApproxC1) +void GeomFill_Sweep::SetForceApproxC1(const Standard_Boolean ForceApproxC1) { myForceApproxC1 = ForceApproxC1; } @@ -171,7 +171,7 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : ExchangeUV // Purpose : //=============================================================== - Standard_Boolean GeomFill_Sweep::ExchangeUV() const +Standard_Boolean GeomFill_Sweep::ExchangeUV() const { return myExchUV; } @@ -180,7 +180,7 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : UReversed // Purpose : //=============================================================== - Standard_Boolean GeomFill_Sweep::UReversed() const +Standard_Boolean GeomFill_Sweep::UReversed() const { return isUReversed; } @@ -189,7 +189,7 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : VReversed // Purpose : //=============================================================== - Standard_Boolean GeomFill_Sweep::VReversed() const +Standard_Boolean GeomFill_Sweep::VReversed() const { return isVReversed; } @@ -198,51 +198,51 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : Build // Purpose : //=============================================================== - void GeomFill_Sweep::Build(const Handle(GeomFill_SectionLaw)& Section, - const GeomFill_ApproxStyle Methode, - const GeomAbs_Shape Continuity, - const Standard_Integer Degmax, - const Standard_Integer Segmax) +void GeomFill_Sweep::Build(const Handle(GeomFill_SectionLaw)& Section, + const GeomFill_ApproxStyle Methode, + const GeomAbs_Shape Continuity, + const Standard_Integer Degmax, + const Standard_Integer Segmax) { // Inits done = Standard_False; myExchUV = Standard_False; isUReversed = isVReversed = Standard_False; - mySec = Section; + mySec = Section; - if ((SFirst == SLast) && (SLast == 30.081996)) { + if ((SFirst == SLast) && (SLast == 30.081996)) { mySec->GetDomain(SFirst, SLast); } - - Standard_Boolean isKPart = Standard_False, - isProduct = Standard_False; - - // Traitement des KPart - if (myKPart) isKPart = BuildKPart(); - if (!isKPart) - { - myExchUV = Standard_False; - isUReversed = isVReversed = Standard_False; - } - - // Traitement des produits Formelles - if ((!isKPart) && (Methode == GeomFill_Location)) { - Handle(Geom_BSplineSurface) BS; - BS = mySec->BSplineSurface(); - if (! BS.IsNull()) { + Standard_Boolean isKPart = Standard_False, + isProduct = Standard_False; + + // Traitement des KPart + if (myKPart) isKPart = BuildKPart(); + + if (!isKPart) + { + myExchUV = Standard_False; + isUReversed = isVReversed = Standard_False; + } + + // Traitement des produits Formelles + if ((!isKPart) && (Methode == GeomFill_Location)) { + Handle(Geom_BSplineSurface) BS; + BS = mySec->BSplineSurface(); + if (!BS.IsNull()) { // Approx de la loi // isProduct = BuildProduct(Continuity, Degmax, Segmax); - } - } + } + } - if (isKPart || isProduct) { - // Approx du 2d - done = Build2d(Continuity, Degmax, Segmax); - } + if (isKPart || isProduct) { + // Approx du 2d + done = Build2d(Continuity, Degmax, Segmax); + } else { - // Approx globale - done = BuildAll(Continuity, Degmax, Segmax); + // Approx globale + done = BuildAll(Continuity, Degmax, Segmax); } } @@ -250,12 +250,9 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function ::Build2d // Purpose :A venir... //=============================================================== -// Standard_Boolean GeomFill_Sweep::Build2d(const GeomAbs_Shape Continuity, - Standard_Boolean GeomFill_Sweep::Build2d(const GeomAbs_Shape , -// const Standard_Integer Degmax, - const Standard_Integer , -// const Standard_Integer Segmax) - const Standard_Integer ) +Standard_Boolean GeomFill_Sweep::Build2d(const GeomAbs_Shape, + const Standard_Integer, + const Standard_Integer) { Standard_Boolean Ok = Standard_False; if (myLoc->Nb2dCurves() == 0) { @@ -268,20 +265,20 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : BuildAll // Purpose : //=============================================================== - Standard_Boolean GeomFill_Sweep::BuildAll(const GeomAbs_Shape Continuity, - const Standard_Integer Degmax, - const Standard_Integer Segmax) +Standard_Boolean GeomFill_Sweep::BuildAll(const GeomAbs_Shape Continuity, + const Standard_Integer Degmax, + const Standard_Integer Segmax) { Standard_Boolean Ok = Standard_False; - Handle(GeomFill_SweepFunction) Func + Handle(GeomFill_SweepFunction) Func = new (GeomFill_SweepFunction) (mySec, myLoc, First, SFirst, - (SLast-SFirst)/(Last-First) ); - Approx_SweepApproximation Approx( Func ); + (SLast - SFirst) / (Last - First)); + Approx_SweepApproximation Approx(Func); - Approx.Perform(First, Last, - Tol3d, BoundTol, Tol2d, TolAngular, - Continuity, Degmax, Segmax); + Approx.Perform(First, Last, + Tol3d, BoundTol, Tol2d, TolAngular, + Continuity, Degmax, Segmax); if (Approx.IsDone()) { Ok = Standard_True; @@ -289,29 +286,29 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, #ifdef OCCT_DEBUG Approx.Dump(std::cout); #endif - - // La surface - Standard_Integer UDegree,VDegree,NbUPoles, - NbVPoles,NbUKnots,NbVKnots; - Approx.SurfShape(UDegree,VDegree,NbUPoles, - NbVPoles,NbUKnots,NbVKnots); - TColgp_Array2OfPnt Poles(1,NbUPoles, 1,NbVPoles); - TColStd_Array2OfReal Weights(1,NbUPoles, 1,NbVPoles); - TColStd_Array1OfReal UKnots(1, NbUKnots),VKnots(1, NbVKnots); + // La surface + Standard_Integer UDegree, VDegree, NbUPoles, + NbVPoles, NbUKnots, NbVKnots; + Approx.SurfShape(UDegree, VDegree, NbUPoles, + NbVPoles, NbUKnots, NbVKnots); + + TColgp_Array2OfPnt Poles(1, NbUPoles, 1, NbVPoles); + TColStd_Array2OfReal Weights(1, NbUPoles, 1, NbVPoles); + TColStd_Array1OfReal UKnots(1, NbUKnots), VKnots(1, NbVKnots); TColStd_Array1OfInteger UMults(1, NbUKnots), VMults(1, NbVKnots); Approx.Surface(Poles, Weights, - UKnots,VKnots, - UMults,VMults); + UKnots, VKnots, + UMults, VMults); mySurface = new (Geom_BSplineSurface) (Poles, Weights, - UKnots,VKnots, - UMults,VMults, - Approx.UDegree(), Approx.VDegree(), - mySec->IsUPeriodic()); - SError = Approx. MaxErrorOnSurf(); + UKnots, VKnots, + UMults, VMults, + Approx.UDegree(), Approx.VDegree(), + mySec->IsUPeriodic()); + SError = Approx.MaxErrorOnSurf(); if (myForceApproxC1 && !mySurface->IsCNv(1)) { @@ -319,48 +316,48 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, GeomAbs_Shape theUCont = GeomAbs_C1, theVCont = GeomAbs_C1; Standard_Integer degU = 14, degV = 14; Standard_Integer nmax = 16; - Standard_Integer thePrec = 1; - - GeomConvert_ApproxSurface ConvertApprox(mySurface,theTol,theUCont,theVCont, - degU,degV,nmax,thePrec); + Standard_Integer thePrec = 1; + + GeomConvert_ApproxSurface ConvertApprox(mySurface, theTol, theUCont, theVCont, + degU, degV, nmax, thePrec); if (ConvertApprox.HasResult()) { mySurface = ConvertApprox.Surface(); myCurve2d = new (TColGeom2d_HArray1OfCurve) (1, 2); - CError = new (TColStd_HArray2OfReal) (1,2, 1,2); + CError = new (TColStd_HArray2OfReal) (1, 2, 1, 2); + + Handle(Geom_BSplineSurface) BSplSurf(Handle(Geom_BSplineSurface)::DownCast(mySurface)); - Handle(Geom_BSplineSurface) BSplSurf (Handle(Geom_BSplineSurface)::DownCast(mySurface)); - gp_Dir2d D(0., 1.); gp_Pnt2d P(BSplSurf->UKnot(1), 0); Handle(Geom2d_Line) LC1 = new (Geom2d_Line) (P, D); Handle(Geom2d_TrimmedCurve) TC1 = new (Geom2d_TrimmedCurve) (LC1, 0, BSplSurf->VKnot(BSplSurf->NbVKnots())); - + myCurve2d->SetValue(1, TC1); CError->SetValue(1, 1, 0.); CError->SetValue(2, 1, 0.); - + P.SetCoord(BSplSurf->UKnot(BSplSurf->NbUKnots()), 0); Handle(Geom2d_Line) LC2 = new (Geom2d_Line) (P, D); - Handle(Geom2d_TrimmedCurve) TC2 = + Handle(Geom2d_TrimmedCurve) TC2 = new (Geom2d_TrimmedCurve) (LC2, 0, BSplSurf->VKnot(BSplSurf->NbVKnots())); - + myCurve2d->SetValue(myCurve2d->Length(), TC2); CError->SetValue(1, myCurve2d->Length(), 0.); CError->SetValue(2, myCurve2d->Length(), 0.); - + SError = theTol; } } //if (!mySurface->IsCNv(1)) - + // Les Courbes 2d if (myCurve2d.IsNull()) { - myCurve2d = new (TColGeom2d_HArray1OfCurve) (1, 2+myLoc->TraceNumber()); - CError = new (TColStd_HArray2OfReal) (1,2, 1, 2+myLoc->TraceNumber()); - Standard_Integer kk,ii, ifin = 1, ideb; - + myCurve2d = new (TColGeom2d_HArray1OfCurve) (1, 2 + myLoc->TraceNumber()); + CError = new (TColStd_HArray2OfReal) (1, 2, 1, 2 + myLoc->TraceNumber()); + Standard_Integer kk, ii, ifin = 1, ideb; + if (myLoc->HasFirstRestriction()) { ideb = 1; } @@ -369,44 +366,44 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, } ifin += myLoc->TraceNumber(); if (myLoc->HasLastRestriction()) ifin++; - - for (ii=ideb, kk=1; ii<=ifin; ii++, kk++) { - Handle(Geom2d_BSplineCurve) C + + for (ii = ideb, kk = 1; ii <= ifin; ii++, kk++) { + Handle(Geom2d_BSplineCurve) C = new (Geom2d_BSplineCurve) (Approx.Curve2dPoles(kk), Approx.Curves2dKnots(), Approx.Curves2dMults(), Approx.Curves2dDegree()); myCurve2d->SetValue(ii, C); - CError->SetValue(1, ii, Approx.Max2dError(kk)); - CError->SetValue(2, ii, Approx.Max2dError(kk)); + CError->SetValue(1, ii, Approx.Max2dError(kk)); + CError->SetValue(2, ii, Approx.Max2dError(kk)); } - + // Si les courbes de restriction, ne sont pas calcules, on prend // les iso Bords. - if (! myLoc->HasFirstRestriction()) { + if (!myLoc->HasFirstRestriction()) { gp_Dir2d D(0., 1.); gp_Pnt2d P(UKnots(UKnots.Lower()), 0); Handle(Geom2d_Line) LC = new (Geom2d_Line) (P, D); Handle(Geom2d_TrimmedCurve) TC = new (Geom2d_TrimmedCurve) (LC, First, Last); - + myCurve2d->SetValue(1, TC); CError->SetValue(1, 1, 0.); CError->SetValue(2, 1, 0.); } - - if (! myLoc->HasLastRestriction()) { + + if (!myLoc->HasLastRestriction()) { gp_Dir2d D(0., 1.); gp_Pnt2d P(UKnots(UKnots.Upper()), 0); Handle(Geom2d_Line) LC = new (Geom2d_Line) (P, D); - Handle(Geom2d_TrimmedCurve) TC = + Handle(Geom2d_TrimmedCurve) TC = new (Geom2d_TrimmedCurve) (LC, First, Last); myCurve2d->SetValue(myCurve2d->Length(), TC); CError->SetValue(1, myCurve2d->Length(), 0.); CError->SetValue(2, myCurve2d->Length(), 0.); } } //if (myCurve2d.IsNull()) - } + } return Ok; } @@ -414,47 +411,44 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Function : BuildProduct // Purpose : A venir... //=============================================================== - Standard_Boolean GeomFill_Sweep::BuildProduct(const GeomAbs_Shape Continuity, - const Standard_Integer Degmax, - const Standard_Integer Segmax) +Standard_Boolean GeomFill_Sweep::BuildProduct(const GeomAbs_Shape Continuity, + const Standard_Integer Degmax, + const Standard_Integer Segmax) { Standard_Boolean Ok = Standard_False; - Handle(Geom_BSplineSurface) BSurf; - BSurf = Handle(Geom_BSplineSurface)::DownCast( - mySec->BSplineSurface()->Copy()); + Handle(Geom_BSplineSurface) BSurf = Handle(Geom_BSplineSurface)::DownCast(mySec->BSplineSurface()->Copy()); if (BSurf.IsNull()) return Ok; // Ce mode de construction est impossible - Standard_Integer NbIntervalC2, NbIntervalC3; + Standard_Integer NbIntervalC2, NbIntervalC3; GeomFill_LocFunction Func(myLoc); NbIntervalC2 = myLoc->NbIntervals(GeomAbs_C2); NbIntervalC3 = myLoc->NbIntervals(GeomAbs_C3); - TColStd_Array1OfReal Param_de_decoupeC2 (1, NbIntervalC2+1); + TColStd_Array1OfReal Param_de_decoupeC2(1, NbIntervalC2 + 1); myLoc->Intervals(Param_de_decoupeC2, GeomAbs_C2); - TColStd_Array1OfReal Param_de_decoupeC3 (1, NbIntervalC3+1); + TColStd_Array1OfReal Param_de_decoupeC3(1, NbIntervalC3 + 1); myLoc->Intervals(Param_de_decoupeC3, GeomAbs_C3); - AdvApprox_PrefAndRec Preferentiel(Param_de_decoupeC2, - Param_de_decoupeC3); - - Handle(TColStd_HArray1OfReal) ThreeDTol = new (TColStd_HArray1OfReal) (1,4); + AdvApprox_PrefAndRec Preferentiel(Param_de_decoupeC2, Param_de_decoupeC3); + + Handle(TColStd_HArray1OfReal) ThreeDTol = new (TColStd_HArray1OfReal) (1, 4); ThreeDTol->Init(Tol3d); // A Affiner... - GeomFill_Sweep_Eval eval (Func); + GeomFill_Sweep_Eval eval(Func); AdvApprox_ApproxAFunction Approx(0, 0, 4, - ThreeDTol, - ThreeDTol, - ThreeDTol, - First, - Last, - Continuity, - Degmax, - Segmax, - eval, - Preferentiel); + ThreeDTol, + ThreeDTol, + ThreeDTol, + First, + Last, + Continuity, + Degmax, + Segmax, + eval, + Preferentiel); #ifdef OCCT_DEBUG Approx.Dump(std::cout); #endif @@ -468,13 +462,13 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // Produit Tensoriel for (ii=1; ii<=nbpoles; ii++) { TM(ii).SetCols(ResPoles->Value(ii,2).XYZ(), - ResPoles->Value(ii,3).XYZ(), - ResPoles->Value(ii,4).XYZ()); + ResPoles->Value(ii,3).XYZ(), + ResPoles->Value(ii,4).XYZ()); TR(ii) = ResPoles->Value(ii,1); } GeomLib::TensorialProduct(BSurf, TM, TR, - Approx.Knots()->Array1(), - Approx.Multiplicities()->Array1()); + Approx.Knots()->Array1(), + Approx.Multiplicities()->Array1()); // Somme TColgp_Array1OfPnt TPoles(1, nbpoles); @@ -483,16 +477,16 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, } Handle(Geom_BsplineCurve) BS = new (Geom_BsplineCurve) (Poles, - Approx.Knots()->Array1(), - Approx.Multiplicities()->Array1(), - Approx.Degree()); + Approx.Knots()->Array1(), + Approx.Multiplicities()->Array1(), + Approx.Degree()); for (ii=1; ii<=BSurf->NbVKnots(); ii++) BS->InsertKnot( BSurf->VKnot(ii), - BSurf->VMultiplicity(ii), - Precision::Confusion()); + BSurf->VMultiplicity(ii), + Precision::Confusion()); TColgp_Array2OfPnt SurfPoles (1, BSurf->NbUPoles()); for (ii=1; - + */ mySurface = BSurf; } @@ -505,9 +499,9 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location, // * the type of section should be a line // * theLoc should represent a translation. -static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) &theLoc, - const Handle(GeomFill_SectionLaw) &theSec, - const Standard_Real theTol) +static Standard_Boolean IsSweepParallelSpine(const Handle(GeomFill_LocationLaw) &theLoc, + const Handle(GeomFill_SectionLaw) &theSec, + const Standard_Real theTol) { // Get the first and last transformations of the location Standard_Real aFirst; @@ -522,25 +516,25 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) theLoc->GetDomain(aFirst, aLast); -// Get the first transformation + // Get the first transformation theLoc->D0(aFirst, M, VBegin); GTfBegin.SetVectorialPart(M); GTfBegin.SetTranslationPart(VBegin.XYZ()); - TfBegin.SetValues(GTfBegin(1,1), GTfBegin(1,2), GTfBegin(1,3), GTfBegin(1,4), - GTfBegin(2,1), GTfBegin(2,2), GTfBegin(2,3), GTfBegin(2,4), - GTfBegin(3,1), GTfBegin(3,2), GTfBegin(3,3), GTfBegin(3,4)); + TfBegin.SetValues(GTfBegin(1, 1), GTfBegin(1, 2), GTfBegin(1, 3), GTfBegin(1, 4), + GTfBegin(2, 1), GTfBegin(2, 2), GTfBegin(2, 3), GTfBegin(2, 4), + GTfBegin(3, 1), GTfBegin(3, 2), GTfBegin(3, 3), GTfBegin(3, 4)); -// Get the last transformation + // Get the last transformation theLoc->D0(aLast, M, VEnd); GTfEnd.SetVectorialPart(M); GTfEnd.SetTranslationPart(VEnd.XYZ()); - TfEnd.SetValues(GTfEnd(1,1), GTfEnd(1,2), GTfEnd(1,3), GTfEnd(1,4), - GTfEnd(2,1), GTfEnd(2,2), GTfEnd(2,3), GTfEnd(2,4), - GTfEnd(3,1), GTfEnd(3,2), GTfEnd(3,3), GTfEnd(3,4)); + TfEnd.SetValues(GTfEnd(1, 1), GTfEnd(1, 2), GTfEnd(1, 3), GTfEnd(1, 4), + GTfEnd(2, 1), GTfEnd(2, 2), GTfEnd(2, 3), GTfEnd(2, 4), + GTfEnd(3, 1), GTfEnd(3, 2), GTfEnd(3, 3), GTfEnd(3, 4)); Handle(Geom_Surface) aSurf = theSec->BSplineSurface(); Standard_Real Umin; @@ -566,8 +560,8 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) aPntLastSec.Transform(TfEnd); - gp_Pnt aPntFirstSec = ElCLib::Value( UFirst, L ); - gp_Vec aVecSec( aPntFirstSec, aPntLastSec ); + gp_Pnt aPntFirstSec = ElCLib::Value(UFirst, L); + gp_Vec aVecSec(aPntFirstSec, aPntLastSec); gp_Vec aVecSpine = VEnd - VBegin; Standard_Boolean isParallel = aVecSec.IsParallel(aVecSpine, theTol); @@ -580,7 +574,7 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) // Function : BuildKPart // Purpose : //=============================================================== - Standard_Boolean GeomFill_Sweep::BuildKPart() +Standard_Boolean GeomFill_Sweep::BuildKPart() { Standard_Boolean Ok = Standard_False; Standard_Boolean isUPeriodic = Standard_False; @@ -592,9 +586,9 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) GeomAbs_CurveType SectionType; gp_Vec V; gp_Mat M; - Standard_Real levier, error = 0 ; - Standard_Real UFirst=0, VFirst=First, ULast=0, VLast=Last; - Standard_Real Tol = Min (Tol3d, BoundTol); + Standard_Real levier, error = 0; + Standard_Real UFirst = 0, VFirst = First, ULast = 0, VLast = Last; + Standard_Real Tol = Min(Tol3d, BoundTol); // (1) Trajectoire Rectilignes ------------------------- if (myLoc->IsTranslation(error)) { @@ -610,9 +604,9 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) Tf.SetTranslationPart(V.XYZ()); try { // Pas joli mais il n'y as pas d'autre moyens de tester SetValues OCC_CATCH_SIGNALS - Tf2.SetValues(Tf(1,1), Tf(1,2), Tf(1,3), Tf(1,4), - Tf(2,1), Tf(2,2), Tf(2,3), Tf(2,4), - Tf(3,1), Tf(3,2), Tf(3,3), Tf(3,4)); + Tf2.SetValues(Tf(1, 1), Tf(1, 2), Tf(1, 3), Tf(1, 4), + Tf(2, 1), Tf(2, 2), Tf(2, 3), Tf(2, 4), + Tf(3, 1), Tf(3, 2), Tf(3, 3), Tf(3, 4)); } catch (Standard_ConstructionError const&) { IsTrsf = Standard_False; @@ -628,147 +622,147 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) GeomAdaptor_Curve AC(Section); SectionType = AC.GetType(); UFirst = AC.FirstParameter(); - ULast = AC.LastParameter(); - // (1.1.a) Cas Plan - if ( (SectionType == GeomAbs_Line) && IsTrsf) { -// Modified by skv - Thu Feb 5 11:39:06 2004 OCC5073 Begin - if (!IsSweepParallelSpine(myLoc, mySec, Tol)) - return Standard_False; -// Modified by skv - Thu Feb 5 11:39:08 2004 OCC5073 End - gp_Lin L = AC.Line(); + ULast = AC.LastParameter(); + // (1.1.a) Cas Plan + if ((SectionType == GeomAbs_Line) && IsTrsf) { + // Modified by skv - Thu Feb 5 11:39:06 2004 OCC5073 Begin + if (!IsSweepParallelSpine(myLoc, mySec, Tol)) + return Standard_False; + // Modified by skv - Thu Feb 5 11:39:08 2004 OCC5073 End + gp_Lin L = AC.Line(); L.Transform(Tf2); - DS.SetXYZ(L.Position().Direction().XYZ()); - DS.Normalize(); + DS.SetXYZ(L.Position().Direction().XYZ()); + DS.Normalize(); levier = Abs(DS.Dot(DP)); - SError = error + levier * Abs(Last-First); - if (SError <= Tol) { - Ok = Standard_True; - gp_Ax2 AxisOfPlane (L.Location(), DS^DP, DS); - S = new (Geom_Plane) (AxisOfPlane); - } - else SError = 0.; + SError = error + levier * Abs(Last - First); + if (SError <= Tol) { + Ok = Standard_True; + gp_Ax2 AxisOfPlane(L.Location(), DS^DP, DS); + S = new (Geom_Plane) (AxisOfPlane); + } + else SError = 0.; } - - // (1.1.b) Cas Cylindrique - if ( (SectionType == GeomAbs_Circle) && IsTrsf) { + + // (1.1.b) Cas Cylindrique + if ((SectionType == GeomAbs_Circle) && IsTrsf) { const Standard_Real TolProd = 1.e-6; - - gp_Circ C = AC.Circle(); - C.Transform(Tf2); - - DS.SetXYZ (C.Position().Direction().XYZ()); - DS.Normalize(); + + gp_Circ C = AC.Circle(); + C.Transform(Tf2); + + DS.SetXYZ(C.Position().Direction().XYZ()); + DS.Normalize(); levier = Abs(DS.CrossMagnitude(DP)) * C.Radius(); SError = levier * Abs(Last - First); - if (SError <= TolProd) { - Ok = Standard_True; - gp_Ax3 axe (C.Location(), DP, C.Position().XDirection()); - S = new (Geom_CylindricalSurface) - (axe, C.Radius()); - if (C.Position().Direction(). - IsOpposite(axe.Direction(), 0.1) ) { - Standard_Real f, l; - // L'orientation parametrique est inversee - l = 2*M_PI - UFirst; - f = 2*M_PI - ULast; - UFirst = f; - ULast = l; - isUReversed = Standard_True; - } - } - else SError = 0.; + if (SError <= TolProd) { + Ok = Standard_True; + gp_Ax3 axe(C.Location(), DP, C.Position().XDirection()); + S = new (Geom_CylindricalSurface) + (axe, C.Radius()); + if (C.Position().Direction(). + IsOpposite(axe.Direction(), 0.1)) { + Standard_Real f, l; + // L'orientation parametrique est inversee + l = 2 * M_PI - UFirst; + f = 2 * M_PI - ULast; + UFirst = f; + ULast = l; + isUReversed = Standard_True; + } + } + else SError = 0.; } - // (1.1.c) C'est bien une extrusion + // (1.1.c) C'est bien une extrusion if (!Ok) { - if (IsTrsf) { - Section->Transform(Tf2); - S = new (Geom_SurfaceOfLinearExtrusion) - (Section, DP); - SError = 0.; - Ok = Standard_True; - } - else { // extrusion sur BSpline - - } + if (IsTrsf) { + Section->Transform(Tf2); + S = new (Geom_SurfaceOfLinearExtrusion) + (Section, DP); + SError = 0.; + Ok = Standard_True; + } + else { // extrusion sur BSpline + + } } } - - // (1.2) Cas conique - else if (mySec->IsConicalLaw(error)) { - gp_Pnt P1, P2, Centre0, Centre1, Centre2; - gp_Vec dsection; - Handle(Geom_Curve) Section; - GeomAdaptor_Curve AC; - gp_Circ C; - Standard_Real R1, R2; + // (1.2) Cas conique + else if (mySec->IsConicalLaw(error)) { + + gp_Pnt P1, P2, Centre0, Centre1, Centre2; + gp_Vec dsection; + Handle(Geom_Curve) Section; + GeomAdaptor_Curve AC; + gp_Circ C; + Standard_Real R1, R2; - Section = mySec->CirclSection(SLast); - Section->Transform(Tf2); - Section->Translate(Last*DP); - AC.Load(Section); - C = AC.Circle(); - Centre2 = C.Location(); - AC.D1(0, P2, dsection); - R2 = C.Radius(); - - Section = mySec->CirclSection(SFirst); - Section->Transform(Tf2); - Section->Translate(First*DP); - AC.Load(Section); - C = AC.Circle(); - Centre1 = C.Location(); - P1 = AC.Value(0); - R1 = C.Radius(); + Section = mySec->CirclSection(SLast); + Section->Transform(Tf2); + Section->Translate(Last*DP); + AC.Load(Section); + C = AC.Circle(); + Centre2 = C.Location(); + AC.D1(0, P2, dsection); + R2 = C.Radius(); - Section = mySec->CirclSection(SFirst - First*(SLast-SFirst)/(Last-First)); - Section->Transform(Tf2); - AC.Load(Section); - C = AC.Circle(); - Centre0 = C.Location(); - - Standard_Real Angle; - gp_Vec N(Centre1, P1); - if (N.Magnitude() < 1.e-9) { - gp_Vec Bis(Centre2, P2); - N = Bis; - } - gp_Vec L(P1, P2), Dir(Centre1,Centre2); + Section = mySec->CirclSection(SFirst); + Section->Transform(Tf2); + Section->Translate(First*DP); + AC.Load(Section); + C = AC.Circle(); + Centre1 = C.Location(); + P1 = AC.Value(0); + R1 = C.Radius(); - Angle = L.Angle(Dir); - if ((Angle > 0.01) && (Angle < M_PI/2-0.01)) { - if (R2CirclSection(SFirst - First*(SLast - SFirst) / (Last - First)); + Section->Transform(Tf2); + AC.Load(Section); + C = AC.Circle(); + Centre0 = C.Location(); - // Bornes en U - UFirst = AC.FirstParameter(); - ULast = AC.LastParameter(); - gp_Vec diso; - gp_Pnt pbis; - S->VIso(VLast)->D1(0, pbis, diso); - if (diso.Magnitude()>1.e-9 && dsection.Magnitude()>1.e-9) - isUReversed = diso.IsOpposite(dsection, 0.1); - if (isUReversed ) { - Standard_Real f, l; - // L'orientation parametrique est inversee - l = 2*M_PI - UFirst; - f = 2*M_PI - ULast; - UFirst = f; - ULast = l; - } + Standard_Real Angle; + gp_Vec N(Centre1, P1); + if (N.Magnitude() < 1.e-9) { + gp_Vec Bis(Centre2, P2); + N = Bis; + } + gp_Vec L(P1, P2), Dir(Centre1, Centre2); - // C'est un cone - Ok = Standard_True; - } - } + Angle = L.Angle(Dir); + if ((Angle > 0.01) && (Angle < M_PI / 2 - 0.01)) { + if (R2 < R1) Angle = -Angle; + SError = error; + gp_Ax3 Axis(Centre0, Dir, N); + S = new (Geom_ConicalSurface) + (Axis, Angle, C.Radius()); + // Calcul du glissement parametrique + VFirst = First / Cos(Angle); + VLast = Last / Cos(Angle); + + // Bornes en U + UFirst = AC.FirstParameter(); + ULast = AC.LastParameter(); + gp_Vec diso; + gp_Pnt pbis; + S->VIso(VLast)->D1(0, pbis, diso); + if (diso.Magnitude() > 1.e-9 && dsection.Magnitude() > 1.e-9) + isUReversed = diso.IsOpposite(dsection, 0.1); + if (isUReversed) { + Standard_Real f, l; + // L'orientation parametrique est inversee + l = 2 * M_PI - UFirst; + f = 2 * M_PI - ULast; + UFirst = f; + ULast = l; + } + + // C'est un cone + Ok = Standard_True; + } + } } // (2) Trajectoire Circulaire @@ -776,7 +770,7 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) if (mySec->IsConstant(error)) { // La trajectoire gp_Pnt Centre; - isVPeriodic = (Abs(Last-First -2*M_PI) < 1.e-15); + isVPeriodic = (Abs(Last - First - 2 * M_PI) < 1.e-15); Standard_Real RotRadius; gp_Vec DP, DS, DN; myLoc->D0(0.1, M, DS); @@ -784,7 +778,7 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) myLoc->Rotation(Centre); DP = DS - V; - DS.SetXYZ(V.XYZ() - Centre.XYZ()); + DS.SetXYZ(V.XYZ() - Centre.XYZ()); RotRadius = DS.Magnitude(); if (RotRadius > 1.e-15) DS.Normalize(); else return Standard_False; // Pas de KPart, rotation degeneree @@ -799,12 +793,12 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) Tf.SetTranslationPart(V.XYZ()); // try { // Pas joli mais il n'y as pas d'autre moyens de tester SetValues // OCC_CATCH_SIGNALS - Tf2.SetValues(Tf(1,1), Tf(1,2), Tf(1,3), Tf(1,4), - Tf(2,1), Tf(2,2), Tf(2,3), Tf(2,4), - Tf(3,1), Tf(3,2), Tf(3,3), Tf(3,4)); + Tf2.SetValues(Tf(1, 1), Tf(1, 2), Tf(1, 3), Tf(1, 4), + Tf(2, 1), Tf(2, 2), Tf(2, 3), Tf(2, 4), + Tf(3, 1), Tf(3, 2), Tf(3, 3), Tf(3, 4)); // } // catch (Standard_ConstructionError) { -// IsTrsf = Standard_False; +// IsTrsf = Standard_False; // } // La section Handle(Geom_Curve) Section; @@ -812,46 +806,46 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) GeomAdaptor_Curve AC(Section); SectionType = AC.GetType(); UFirst = AC.FirstParameter(); - ULast = AC.LastParameter(); + ULast = AC.LastParameter(); // (2.1) Tore/Sphere ? if ((SectionType == GeomAbs_Circle) && IsTrsf) { - gp_Circ C = AC.Circle(); + gp_Circ C = AC.Circle(); Standard_Real Radius; - Standard_Boolean IsGoodSide = Standard_True; - C.Transform(Tf2); - gp_Vec DC; + Standard_Boolean IsGoodSide = Standard_True; + C.Transform(Tf2); + gp_Vec DC; // On calcul le centre eventuel DC.SetXYZ(C.Location().XYZ() - Centre.XYZ()); - Centre.ChangeCoord() += (DC.Dot(DN))*DN.XYZ(); - DC.SetXYZ(C.Location().XYZ() - Centre.XYZ()); + Centre.ChangeCoord() += (DC.Dot(DN))*DN.XYZ(); + DC.SetXYZ(C.Location().XYZ() - Centre.XYZ()); Radius = DC.Magnitude(); //grand Rayon du tore - if ((Radius > Tol) && (DC.Dot(DS) < 0)) IsGoodSide = Standard_False; - if (Radius < Tol/100) DC = DS; // Pour definir le tore + if ((Radius > Tol) && (DC.Dot(DS) < 0)) IsGoodSide = Standard_False; + if (Radius < Tol / 100) DC = DS; // Pour definir le tore - // On verifie d'abord que le plan de la section est // a - // l'axe de rotation - gp_Vec NC; - NC.SetXYZ (C.Position().Direction().XYZ()); - NC.Normalize(); - error = Abs(NC.Dot(DN)); - // Puis on evalue l'erreur commise sur la section, + // On verifie d'abord que le plan de la section est // a + // l'axe de rotation + gp_Vec NC; + NC.SetXYZ(C.Position().Direction().XYZ()); + NC.Normalize(); + error = Abs(NC.Dot(DN)); + // Puis on evalue l'erreur commise sur la section, // en pivotant son plan ( pour contenir l'axe de rotation) error += Abs(NC.Dot(DS)); error *= C.Radius(); - if (error <= Tol) { - SError = error; - error += Radius; + if (error <= Tol) { + SError = error; + error += Radius; if (Radius <= Tol) { - // (2.1.a) Sphere - Standard_Real f = UFirst , l = ULast, aRadius = 0.0; - SError = error; - Centre.BaryCenter(1.0, C.Location(), 1.0); - gp_Ax3 AxisOfSphere(Centre, DN, DS); + // (2.1.a) Sphere + Standard_Real f = UFirst, l = ULast, aRadius = 0.0; + SError = error; + Centre.BaryCenter(1.0, C.Location(), 1.0); + gp_Ax3 AxisOfSphere(Centre, DN, DS); aRadius = C.Radius(); - gp_Sphere theSphere( AxisOfSphere, aRadius ); - S = new Geom_SphericalSurface(theSphere); - // Pour les spheres on ne peut pas controler le parametre + gp_Sphere theSphere(AxisOfSphere, aRadius); + S = new Geom_SphericalSurface(theSphere); + // Pour les spheres on ne peut pas controler le parametre // V (donc U car myExchUV = Standard_True) // Il faut donc modifier UFirst, ULast... Standard_Real fpar = AC.FirstParameter(); @@ -859,7 +853,7 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) Handle(Geom_Curve) theSection = new Geom_TrimmedCurve(Section, fpar, lpar); theSection->Transform(Tf2); gp_Pnt FirstPoint = theSection->Value(theSection->FirstParameter()); - gp_Pnt LastPoint = theSection->Value(theSection->LastParameter()); + gp_Pnt LastPoint = theSection->Value(theSection->LastParameter()); Standard_Real UfirstOnSec, VfirstOnSec, UlastOnSec, VlastOnSec; ElSLib::Parameters(theSphere, FirstPoint, UfirstOnSec, VfirstOnSec); ElSLib::Parameters(theSphere, LastPoint, UlastOnSec, VlastOnSec); @@ -870,165 +864,168 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) } else { - // L'orientation parametrique est inversee + // L'orientation parametrique est inversee f = VlastOnSec; l = VfirstOnSec; - isUReversed = Standard_True; - } + isUReversed = Standard_True; + } if (Abs(l - f) <= Precision::PConfusion() || - Abs(UlastOnSec - UfirstOnSec) > M_PI_2) + Abs(UlastOnSec - UfirstOnSec) > M_PI_2) { // l == f - "degenerated" surface // UlastOnSec - UfirstOnSec > M_PI_2 - "twisted" surface, // it is impossible to represent with help of trimmed sphere - isUReversed = Standard_False; + isUReversed = Standard_False; return Ok; } - if ( (f >= -M_PI/2) && (l <= M_PI/2)) { - Ok = Standard_True; - myExchUV = Standard_True; - UFirst = f; - ULast = l; - } - else { // On restaure ce qu'il faut - isUReversed = Standard_False; - } - } - else if (IsGoodSide) { - // (2.1.b) Tore - gp_Ax3 AxisOfTore(Centre, DN, DC); - S = new (Geom_ToroidalSurface) (AxisOfTore, - Radius , C.Radius()); - - // Pour les tores on ne peut pas controler le parametre + if ((f >= -M_PI / 2) && (l <= M_PI / 2)) { + Ok = Standard_True; + myExchUV = Standard_True; + UFirst = f; + ULast = l; + } + else { // On restaure ce qu'il faut + isUReversed = Standard_False; + } + } + else if (IsGoodSide) { + // (2.1.b) Tore + gp_Ax3 AxisOfTore(Centre, DN, DC); + S = new (Geom_ToroidalSurface) (AxisOfTore, + Radius, C.Radius()); + + // Pour les tores on ne peut pas controler le parametre // V (donc U car myExchUV = Standard_True) // Il faut donc modifier UFirst, ULast... - Handle(Geom_Circle) Iso; - Iso = Handle(Geom_Circle)::DownCast(S->UIso(0.)); - gp_Ax2 axeiso; - axeiso = Iso->Circ().Position(); - - if (C.Position().Direction(). - IsOpposite(axeiso.Direction(), 0.1) ) { - Standard_Real f, l; - // L'orientation parametrique est inversee - l = 2*M_PI - UFirst; - f = 2*M_PI - ULast; - UFirst = f; - ULast = l; - isUReversed = Standard_True; - } - // On calcul le "glissement" parametrique. - Standard_Real rot; - rot = C.Position().XDirection().AngleWithRef - (axeiso.XDirection(), axeiso.Direction()); - UFirst -= rot; - ULast -= rot; + Handle(Geom_Circle) Iso; + Iso = Handle(Geom_Circle)::DownCast(S->UIso(0.)); + gp_Ax2 axeiso; + axeiso = Iso->Circ().Position(); - myExchUV = Standard_True; + if (C.Position().Direction(). + IsOpposite(axeiso.Direction(), 0.1)) { + Standard_Real f, l; + // L'orientation parametrique est inversee + l = 2 * M_PI - UFirst; + f = 2 * M_PI - ULast; + UFirst = f; + ULast = l; + isUReversed = Standard_True; + } + // On calcul le "glissement" parametrique. + Standard_Real rot; + rot = C.Position().XDirection().AngleWithRef + (axeiso.XDirection(), axeiso.Direction()); + UFirst -= rot; + ULast -= rot; + + myExchUV = Standard_True; // Attention l'arete de couture dans le cas periodique // n'est peut etre pas a la bonne place... - if (isUPeriodic && Abs(UFirst)>Precision::PConfusion()) - isUPeriodic = Standard_False; //Pour trimmer la surface... - Ok = Standard_True; - } - } - else { - SError = 0.; - } + if (isUPeriodic && Abs(UFirst) > Precision::PConfusion()) + isUPeriodic = Standard_False; //Pour trimmer la surface... + Ok = Standard_True; + } + } + else { + SError = 0.; + } } // (2.2) Cone / Cylindre - if ((SectionType == GeomAbs_Line) && IsTrsf) { - gp_Lin L = AC.Line(); - L.Transform(Tf2); - gp_Vec DL; - DL.SetXYZ(L.Direction().XYZ()); - levier = Max(Abs(AC.FirstParameter()), AC.LastParameter()); - // si la line est ortogonale au cercle de rotation - SError = error + levier * Abs(DL.Dot(DP)); - if (SError <= Tol) { + if ((SectionType == GeomAbs_Line) && IsTrsf) { + gp_Lin L = AC.Line(); + L.Transform(Tf2); + gp_Vec DL; + DL.SetXYZ(L.Direction().XYZ()); + levier = Max(Abs(AC.FirstParameter()), AC.LastParameter()); + // si la line est ortogonale au cercle de rotation + SError = error + levier * Abs(DL.Dot(DP)); + if (SError <= Tol) { Standard_Boolean reverse; - gp_Lin Dir(Centre, DN); - Standard_Real aux; - aux = DL.Dot(DN); - reverse = (aux < 0); // On choisit ici le sens de parametrisation - + gp_Lin Dir(Centre, DN); + Standard_Real aux; + aux = DL.Dot(DN); + reverse = (aux < 0); // On choisit ici le sens de parametrisation + // Calcul du centre du vecteur supportant la "XDirection" - gp_Pnt CentreOfSurf; - gp_Vec O1O2(Centre, L.Location()), trans; - trans = DN; - trans *= DN.Dot(O1O2); - CentreOfSurf = Centre.Translated(trans); + gp_Pnt CentreOfSurf; + gp_Vec O1O2(Centre, L.Location()), trans; + trans = DN; + trans *= DN.Dot(O1O2); + CentreOfSurf = Centre.Translated(trans); DS.SetXYZ(L.Location().XYZ() - CentreOfSurf.XYZ()); - error = SError; - error += (DL.XYZ()).CrossMagnitude(DN.XYZ())*levier; - if (error <= Tol) { - // (2.2.a) Cylindre + error = SError; + error += (DL.XYZ()).CrossMagnitude(DN.XYZ())*levier; + if (error <= Tol) { + // (2.2.a) Cylindre // si la line est orthogonale au plan de rotation - SError = error; - // - gp_Ax3 Axis(CentreOfSurf, Dir.Direction()); - if (DS.SquareMagnitude() > gp::Resolution()) - { - Axis.SetXDirection(DS); - } - S = new (Geom_CylindricalSurface) - (Axis, L.Distance(CentreOfSurf)); - Ok = Standard_True; + SError = error; + // + gp_Ax3 Axis(CentreOfSurf, Dir.Direction()); + if (DS.SquareMagnitude() > gp::Resolution()) + { + Axis.SetXDirection(DS); + } + S = new (Geom_CylindricalSurface) + (Axis, L.Distance(CentreOfSurf)); + Ok = Standard_True; myExchUV = Standard_True; - } - else { - // On evalue l'angle du cone - Standard_Real Angle = Abs(Dir.Angle(L)); - if (Angle > M_PI/2) Angle = M_PI -Angle; + } + else { + // On evalue l'angle du cone + Standard_Real Angle = Abs(Dir.Angle(L)); + if (Angle > M_PI / 2) Angle = M_PI - Angle; if (reverse) Angle = -Angle; - aux = DS.Dot(DL); - if (aux < 0) { - Angle = - Angle; - } - if (Abs(Abs(Angle) - M_PI/2) > 0.01) { - // (2.2.b) Cone - // si les 2 droites ne sont pas orthogonales - Standard_Real Radius = CentreOfSurf.Distance(L.Location()); - gp_Ax3 Axis(CentreOfSurf, Dir.Direction(), DS); - S = new (Geom_ConicalSurface) - (Axis, Angle, Radius); - myExchUV = Standard_True; - Ok = Standard_True; - } - else { - // On n'as pas conclue, on remet l'erreur a 0. - SError = 0.; - } - } - if (Ok && reverse) { - // On reverse le parametre - Standard_Real uf, ul; - Handle(Geom_Line) CL = new (Geom_Line)(L); - uf = CL->ReversedParameter(ULast); - ul = CL->ReversedParameter(UFirst); - UFirst = uf; - ULast = ul; - isUReversed = Standard_True; - } - } - else SError = 0.; + aux = DS.Dot(DL); + if (aux < 0) { + Angle = -Angle; + } + if (Abs(Abs(Angle) - M_PI / 2) > 0.01) { + // (2.2.b) Cone + // si les 2 droites ne sont pas orthogonales + Standard_Real Radius = CentreOfSurf.Distance(L.Location()); + gp_Ax3 Axis(CentreOfSurf, Dir.Direction(), DS); + S = new (Geom_ConicalSurface) + (Axis, Angle, Radius); + myExchUV = Standard_True; + Ok = Standard_True; + } + else { + // On n'as pas conclue, on remet l'erreur a 0. + SError = 0.; + } + } + if (Ok && reverse) { + // On reverse le parametre + Standard_Real uf, ul; + Handle(Geom_Line) CL = new (Geom_Line)(L); + uf = CL->ReversedParameter(ULast); + ul = CL->ReversedParameter(UFirst); + + // Following the example of the code for the sphere: + // "we cannot control U because myExchUV = Standard_True, + // so it is necessary to change UFirst and ULast" + UFirst = ul; + ULast = uf; + } + } + else SError = 0.; } - + // (2.3) Revolution if (!Ok) { - if (IsTrsf) { - Section->Transform(Tf2); - gp_Ax1 Axis (Centre, DN); - S = new (Geom_SurfaceOfRevolution) - (Section, Axis); - myExchUV = Standard_True; - SError = 0.; - Ok = Standard_True; - } + if (IsTrsf) { + Section->Transform(Tf2); + gp_Ax1 Axis(Centre, DN); + S = new (Geom_SurfaceOfRevolution) + (Section, Axis); + myExchUV = Standard_True; + SError = 0.; + Ok = Standard_True; + } } } } @@ -1045,37 +1042,37 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) if (!isUPeriodic && !isVPeriodic) mySurface = new (Geom_RectangularTrimmedSurface) - (S, UFirst, ULast, VFirst, VLast); + (S, UFirst, ULast, VFirst, VLast); else if (isUPeriodic) { if (isVPeriodic) mySurface = S; else mySurface = new (Geom_RectangularTrimmedSurface) - (S, VFirst, VLast, Standard_False); + (S, VFirst, VLast, Standard_False); } else mySurface = new (Geom_RectangularTrimmedSurface) - (S,UFirst, ULast, Standard_True); + (S, UFirst, ULast, Standard_True); #ifdef OCCT_DEBUG - if (isUPeriodic && !mySurface->IsUPeriodic()) - std::cout<<"Pb de periodicite en U" << std::endl; - if (isUPeriodic && !mySurface->IsUClosed()) - std::cout<<"Pb de fermeture en U" << std::endl; - if (isVPeriodic && !mySurface->IsVPeriodic()) - std::cout << "Pb de periodicite en V" << std::endl; - if (isVPeriodic && !mySurface->IsVClosed()) - std::cout<<"Pb de fermeture en V" << std::endl; + if (isUPeriodic && !mySurface->IsUPeriodic()) + std::cout << "Pb de periodicite en U" << std::endl; + if (isUPeriodic && !mySurface->IsUClosed()) + std::cout << "Pb de fermeture en U" << std::endl; + if (isVPeriodic && !mySurface->IsVPeriodic()) + std::cout << "Pb de periodicite en V" << std::endl; + if (isVPeriodic && !mySurface->IsVClosed()) + std::cout << "Pb de fermeture en V" << std::endl; #endif } return Ok; -} + } //=============================================================== // Function : IsDone // Purpose : //=============================================================== - Standard_Boolean GeomFill_Sweep::IsDone() const +Standard_Boolean GeomFill_Sweep::IsDone() const { return done; } @@ -1084,7 +1081,7 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) // Function :ErrorOnSurface // Purpose : //=============================================================== - Standard_Real GeomFill_Sweep::ErrorOnSurface() const +Standard_Real GeomFill_Sweep::ErrorOnSurface() const { return SError; } @@ -1093,39 +1090,39 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) // Function ::ErrorOnRestriction // Purpose : //=============================================================== - void GeomFill_Sweep::ErrorOnRestriction(const Standard_Boolean IsFirst, - Standard_Real& UError, - Standard_Real& VError) const +void GeomFill_Sweep::ErrorOnRestriction(const Standard_Boolean IsFirst, + Standard_Real& UError, + Standard_Real& VError) const { Standard_Integer ind; - if (IsFirst) ind=1; + if (IsFirst) ind = 1; else ind = myCurve2d->Length(); - UError = CError->Value(1, ind); - VError = CError->Value(2, ind); + UError = CError->Value(1, ind); + VError = CError->Value(2, ind); } //=============================================================== // Function :ErrorOnTrace // Purpose : //=============================================================== - void GeomFill_Sweep::ErrorOnTrace(const Standard_Integer IndexOfTrace, - Standard_Real& UError, - Standard_Real& VError) const +void GeomFill_Sweep::ErrorOnTrace(const Standard_Integer IndexOfTrace, + Standard_Real& UError, + Standard_Real& VError) const { - Standard_Integer ind = IndexOfTrace+1; + Standard_Integer ind = IndexOfTrace + 1; if (IndexOfTrace > myLoc->TraceNumber()) throw Standard_OutOfRange(" GeomFill_Sweep::ErrorOnTrace"); - UError = CError->Value(1, ind); - VError = CError->Value(2, ind); + UError = CError->Value(1, ind); + VError = CError->Value(2, ind); } //=============================================================== // Function :Surface // Purpose : //=============================================================== - Handle(Geom_Surface) GeomFill_Sweep::Surface() const +Handle(Geom_Surface) GeomFill_Sweep::Surface() const { return mySurface; } @@ -1134,19 +1131,18 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) // Function ::Restriction // Purpose : //=============================================================== - Handle(Geom2d_Curve) GeomFill_Sweep::Restriction(const Standard_Boolean IsFirst) const +Handle(Geom2d_Curve) GeomFill_Sweep::Restriction(const Standard_Boolean IsFirst) const { if (IsFirst) return myCurve2d->Value(1); return myCurve2d->Value(myCurve2d->Length()); - } //=============================================================== // Function : // Purpose : //=============================================================== - Standard_Integer GeomFill_Sweep::NumberOfTrace() const +Standard_Integer GeomFill_Sweep::NumberOfTrace() const { return myLoc->TraceNumber(); } @@ -1155,11 +1151,10 @@ static Standard_Boolean IsSweepParallelSpine (const Handle(GeomFill_LocationLaw) // Function : // Purpose : //=============================================================== - Handle(Geom2d_Curve) - GeomFill_Sweep::Trace(const Standard_Integer IndexOfTrace) const +Handle(Geom2d_Curve) GeomFill_Sweep::Trace(const Standard_Integer IndexOfTrace) const { - Standard_Integer ind = IndexOfTrace+1; + Standard_Integer ind = IndexOfTrace + 1; if (IndexOfTrace > myLoc->TraceNumber()) throw Standard_OutOfRange(" GeomFill_Sweep::Trace"); - return myCurve2d->Value(ind); + return myCurve2d->Value(ind); } diff --git a/tests/pipe/bugs/bug24909_3 b/tests/pipe/bugs/bug24909_3 index 3a118e626a..e40ef32e21 100755 --- a/tests/pipe/bugs/bug24909_3 +++ b/tests/pipe/bugs/bug24909_3 @@ -1,4 +1,4 @@ -puts "TODO OCC24909 ALL: TEST INCOMPLETE" +puts "TODO OCC24909 ALL: Error: sweep failed" puts "========" puts "OCC24909" @@ -28,4 +28,8 @@ trotate Circle001 0 0 0 0.577350269189625731 0.577350269189625731 0.577350269189 ttranslate Circle001 0 -71 203.5 addsweep Circle001 -buildsweep Sweep001 -C -S +set result [buildsweep Sweep001 -C -S] + +if {[regexp "Not Done" $result]} { + puts "Error: sweep failed" +} \ No newline at end of file diff --git a/tests/pipe/bugs/bug32809 b/tests/pipe/bugs/bug32809 new file mode 100644 index 0000000000..3e8cb1687b --- /dev/null +++ b/tests/pipe/bugs/bug32809 @@ -0,0 +1,16 @@ +puts "========" +puts "bug32809: Sweep algorithm with Round Corner doesnot work" +puts "========" +puts "" + +restore [locate_data_file bug32809_path.brep] p +restore [locate_data_file bug32809_profile.brep] pr + +mksweep p +setsweep -CF +addsweep pr + +buildsweep result -R -S + +checkshape result +checknbshapes result -vertex 140 -edge 285 -wire 140 -face 140 -shell 1 diff --git a/tests/pipe/bugs/end b/tests/pipe/bugs/end new file mode 100644 index 0000000000..014cb9024b --- /dev/null +++ b/tests/pipe/bugs/end @@ -0,0 +1 @@ +puts "TEST COMPLETED" \ No newline at end of file