From 33a90322cfba5aae6a707ee6b0d6d0da0e55ee50 Mon Sep 17 00:00:00 2001 From: nbv Date: Thu, 28 Jan 2016 13:43:08 +0300 Subject: [PATCH] Patch for CR26980_1 fix --- src/IntPatch/IntPatch_Intersection.cxx | 30 +- src/IntPatch/IntPatch_PrmPrmIntersection.cxx | 490 ++++++++----------- src/IntWalk/IntWalk.cdl | 4 +- src/IntWalk/IntWalk_PWalking.cdl | 22 + src/IntWalk/IntWalk_PWalking.cxx | 259 +++++++--- src/IntWalk/IntWalk_PWalking.lxx | 6 + tests/bugs/modalg_6/bug26980 | 64 +++ 7 files changed, 484 insertions(+), 391 deletions(-) create mode 100644 tests/bugs/modalg_6/bug26980 diff --git a/src/IntPatch/IntPatch_Intersection.cxx b/src/IntPatch/IntPatch_Intersection.cxx index fb0107e333..7cdb4daf11 100644 --- a/src/IntPatch/IntPatch_Intersection.cxx +++ b/src/IntPatch/IntPatch_Intersection.cxx @@ -524,7 +524,7 @@ void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)& S1, default: { IntPatch_PrmPrmIntersection interpp; - interpp.Perform(S1,D1,TolArc,TolTang,myFleche,myUVMaxStep); + interpp.Perform(S1,D1,TolTang,TolArc,myFleche,myUVMaxStep); if (interpp.IsDone()) { done = Standard_True; @@ -1329,7 +1329,7 @@ void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)& theS1, ParamParamPerfom(theS1, theD1, theS2, theD2, TolArc, TolTang, ListOfPnts, RestrictLine, typs1, typs2); } -} + } //======================================================================= //function : Perform @@ -1548,7 +1548,7 @@ void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)& theS1, TolArc, TolTang, ListOfPnts, RestrictLine, typs1, typs2); } } -} + } //======================================================================= //function : ParamParamPerfom @@ -1571,10 +1571,10 @@ void IntPatch_Intersection::ParamParamPerfom(const Handle(Adaptor3d_HSurface)& Standard_Boolean ClearFlag = Standard_True; if(!ListOfPnts.IsEmpty()) { - interpp.Perform(theS1,theD1,theS2,theD2,TolArc,TolTang,myFleche,myUVMaxStep, ListOfPnts, RestrictLine); + interpp.Perform(theS1,theD1,theS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep, ListOfPnts, RestrictLine); ClearFlag = Standard_False; } - interpp.Perform(theS1,theD1,theS2,theD2,TolArc,TolTang,myFleche,myUVMaxStep,ClearFlag); //double call!!!!!!! + interpp.Perform(theS1,theD1,theS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep,ClearFlag); //double call!!!!!!! } else if((theD1->DomainIsInfinite()) ^ (theD2->DomainIsInfinite())) { @@ -1587,7 +1587,7 @@ void IntPatch_Intersection::ParamParamPerfom(const Handle(Adaptor3d_HSurface)& const Standard_Real AP = Max(MU, MV); Handle(Adaptor3d_HSurface) SS; FUN_TrimInfSurf(pMinXYZ, pMaxXYZ, theS1, AP, SS); - interpp.Perform(SS,theD1,theS2,theD2,TolArc,TolTang,myFleche,myUVMaxStep); + interpp.Perform(SS,theD1,theS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep); } else { @@ -1597,7 +1597,7 @@ void IntPatch_Intersection::ParamParamPerfom(const Handle(Adaptor3d_HSurface)& const Standard_Real AP = Max(MU, MV); Handle(Adaptor3d_HSurface) SS; FUN_TrimInfSurf(pMinXYZ, pMaxXYZ, theS2, AP, SS); - interpp.Perform(theS1, theD1, SS, theD2,TolArc,TolTang,myFleche,myUVMaxStep); + interpp.Perform(theS1, theD1, SS, theD2,TolTang, TolArc,myFleche,myUVMaxStep); } }//(theD1->DomainIsInfinite()) ^ (theD2->DomainIsInfinite()) else @@ -1636,7 +1636,7 @@ void IntPatch_Intersection::ParamParamPerfom(const Handle(Adaptor3d_HSurface)& Handle(Adaptor3d_HSurface) nS1 = theS1; Handle(Adaptor3d_HSurface) nS2 = theS2; FUN_TrimBothSurf(theS1,typs1,theS2,typs2,1.e+8,nS1,nS2); - interpp.Perform(nS1,theD1,nS2,theD2,TolArc,TolTang,myFleche,myUVMaxStep); + interpp.Perform(nS1,theD1,nS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep); }// 'NON - COLLINEAR LINES' }// both domains are infinite @@ -1906,10 +1906,10 @@ void IntPatch_Intersection:: } JoinWLines( slin, spnt, theTolTang, - theS1->IsUPeriodic()? theS1->UPeriod() : 0.0, - theS2->IsUPeriodic()? theS2->UPeriod() : 0.0, - theS1->IsVPeriodic()? theS1->VPeriod() : 0.0, - theS2->IsVPeriodic()? theS2->VPeriod() : 0.0, + theS1->IsUPeriodic()? theS1->UPeriod() : 0.0, + theS2->IsUPeriodic()? theS2->UPeriod() : 0.0, + theS1->IsVPeriodic()? theS1->VPeriod() : 0.0, + theS2->IsVPeriodic()? theS2->VPeriod() : 0.0, theS1->FirstUParameter(), theS1->LastUParameter(), theS1->FirstVParameter(), theS1->LastVParameter(), theS2->FirstUParameter(), theS2->LastUParameter(), @@ -1982,7 +1982,7 @@ void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)& S1, else { IntPatch_PrmPrmIntersection interpp; - interpp.Perform(S1,D1,S2,D2,U1,V1,U2,V2,TolArc,TolTang,myFleche,myUVMaxStep); + interpp.Perform(S1,D1,S2,D2,U1,V1,U2,V2,TolTang,TolArc,myFleche,myUVMaxStep); if (interpp.IsDone()) { done = Standard_True; @@ -1993,7 +1993,7 @@ void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)& S1, for (; i<=nblm; i++) slin.Append(interpp.Line(i)); } } -} + } //====================================================================== #include #include @@ -2053,7 +2053,7 @@ void IntPatch_Intersection::Dump(const Standard_Integer , NR1[nbR1]=0; nbR1++; } - for(D2->Init();D2->More() && nbR2Next()) { + for(D2->Init();D2->More() && nbR2Next()) { R2[nbR2]=D2->Value(); NR2[nbR2]=0; nbR2++; diff --git a/src/IntPatch/IntPatch_PrmPrmIntersection.cxx b/src/IntPatch/IntPatch_PrmPrmIntersection.cxx index 8d07c7b2df..a0bc4144a8 100644 --- a/src/IntPatch/IntPatch_PrmPrmIntersection.cxx +++ b/src/IntPatch/IntPatch_PrmPrmIntersection.cxx @@ -68,6 +68,192 @@ static void AddWLine(IntPatch_SequenceOfLine &theLines, const Handle(IntPatch_WLine) &theWLine, const Standard_Real Deflection); +static void SeveralWlinesProcessing(const Handle(Adaptor3d_HSurface)& theSurf1, + const Handle(Adaptor3d_HSurface)& theSurf2, + const IntPatch_SequenceOfLine& theSLin, + const Standard_Real* const thePeriodsArr, + const IntSurf_TypeTrans theTrans1, + const IntSurf_TypeTrans theTrans2, + const Standard_Real theTol, + const Standard_Real theMaxStepS1, + const Standard_Real theMaxStepS2, + Handle(IntPatch_WLine)& theWLline) +{ + if(theSLin.Length() == 0) + return; + + Standard_Real aU1 = 0.0, aV1 = 0.0, aU2 = 0.0, aV2 = 0.0; + + Standard_Integer cnbV = theWLline->NbVertex(); + Standard_Integer ciV; + for( ciV = 1; ciV <= cnbV; ciV++ ) + { + Standard_Real pntDMin = 1.e+100; + Standard_Integer VDMin = 0; + Standard_Integer WLDMin = 0; + gp_Pnt cPV = theWLline->Vertex(ciV).Value(); + theWLline->Vertex(ciV).Parameters(aU1, aV1, aU2, aV2); + const gp_Pnt2d aPCS1(aU1, aV1), aPCS2(aU2, aV2); + Standard_Integer iL; + for( iL = 1; iL <= theSLin.Length(); iL++) + { + const Handle(IntPatch_Line)& aSLine = theSLin.Value(iL); + IntPatch_IType aType = aSLine->ArcType(); + if( aType != IntPatch_Walking) + continue; + const Handle(IntPatch_WLine) aWLine = Handle(IntPatch_WLine)::DownCast(aSLine); + Standard_Integer tnbV = aWLine->NbVertex(); + Standard_Integer tiV; + for( tiV = 1; tiV <= tnbV; tiV++ ) + { + gp_Pnt tPV = aWLine->Vertex(tiV).Value(); + + aWLine->Vertex(tiV).Parameters(aU1, aV1, aU2, aV2); + const gp_Pnt2d aPTS1(aU1, aV1), aPTS2(aU2, aV2); + + Standard_Real tDistance = cPV.Distance(tPV); + Standard_Real uRs1 = theSurf1->Surface().UResolution(tDistance); + Standard_Real vRs1 = theSurf1->Surface().VResolution(tDistance); + Standard_Real uRs2 = theSurf2->Surface().UResolution(tDistance); + Standard_Real vRs2 = theSurf2->Surface().VResolution(tDistance); + Standard_Real RmaxS1 = Max(uRs1,vRs1); + Standard_Real RmaxS2 = Max(uRs2,vRs2); + + if(RmaxS1 < theMaxStepS1 && RmaxS2 < theMaxStepS2) + { + if( pntDMin > tDistance && tDistance > Precision::PConfusion()) + { + const Standard_Real aSqDist1 = aPCS1.SquareDistance(aPTS1), + aSqDist2 = aPCS2.SquareDistance(aPTS2); + if((aSqDist1 < RmaxS1*RmaxS1) && (aSqDist2 < RmaxS2*RmaxS2)) + { + pntDMin = tDistance; + VDMin = tiV; + WLDMin = iL; + } + } + } + } + } + + if( VDMin != 0 ) + { + const Handle(IntPatch_Line)& aSLine = theSLin.Value(WLDMin); + const Handle(IntPatch_WLine) aWLine = Handle(IntPatch_WLine)::DownCast(aSLine); + Standard_Integer tiVpar = (Standard_Integer)aWLine->Vertex(VDMin).ParameterOnLine(); + Standard_Integer ciVpar = (Standard_Integer)theWLline->Vertex(ciV).ParameterOnLine(); + Standard_Real u11 = 0., u12 = 0., v11 = 0., v12 = 0.; + Standard_Real u21 = 0., u22 = 0., v21 = 0., v22 = 0.; + theWLline->Point(ciVpar).Parameters(u11,v11,u12,v12); + aWLine->Point(tiVpar).Parameters(u21,v21,u22,v22); + + Handle(IntSurf_LineOn2S) newL2s = new IntSurf_LineOn2S(); + IntSurf_PntOn2S replacePnt = aWLine->Point(tiVpar); + Standard_Integer cNbP = theWLline->NbPnts(); + + TColStd_SequenceOfInteger VPold; + Standard_Integer iPo; + for( iPo = 1; iPo <= cnbV; iPo++ ) + { + Standard_Real Po = theWLline->Vertex(iPo).ParameterOnLine(); + Standard_Integer IPo = (Standard_Integer) Po; + VPold.Append(IPo); + } + + Standard_Boolean removeNext = Standard_False; + Standard_Boolean removePrev = Standard_False; + if( ciV == 1) + { + Standard_Integer dPar = Abs( VPold.Value(ciV) - VPold.Value(ciV+1)); + if(dPar > 10) + { + removeNext = Standard_True; + for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) + VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); + } + } + else if( ciV == cnbV) + { + Standard_Integer dPar = Abs( VPold.Value(ciV) - VPold.Value(ciV-1)); + if(dPar > 10) + { + removePrev = Standard_True; + VPold.SetValue(ciV, VPold.Value(ciV) - 1 ); + } + } + else + { + Standard_Integer dParMi = Abs( VPold.Value(ciV) - VPold.Value(ciV-1)); + Standard_Integer dParMa = Abs( VPold.Value(ciV) - VPold.Value(ciV+1)); + if(dParMi > 10) + { + removePrev = Standard_True; + VPold.SetValue(ciV, VPold.Value(ciV) - 1 ); + } + + if(dParMa > 10) + { + removeNext = Standard_True; + for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) + { + if(dParMi > 10) + VPold.SetValue(iPo, VPold.Value(iPo) - 2 ); + else + VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); + } + } + else + { + if(dParMi > 10) + for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) + VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); + } + } + + Standard_Integer pI = ciVpar; + + Standard_Integer iP; + for( iP = 1; iP <= cNbP; iP++) + { + if( pI == iP ) + { + IntSurf_PntOn2S newPnt = MakeNewPoint(replacePnt, theWLline->Point(iP), thePeriodsArr); + newL2s->Add(newPnt); + } + else if(removeNext && iP == (pI + 1)) + continue; + else if(removePrev && iP == (pI - 1)) + continue; + else + newL2s->Add(theWLline->Point(iP)); + } + + IntPatch_Point newVtx; + gp_Pnt Pnt3dV = aWLine->Vertex(VDMin).Value(); + newVtx.SetValue(Pnt3dV,theTol,Standard_False); + newVtx.SetParameters(u21,v21,u22,v22); + newVtx.SetParameter(VPold.Value(ciV)); + + Handle(IntPatch_WLine) NWLine = new IntPatch_WLine(newL2s,Standard_False,theTrans1,theTrans2); + + Standard_Integer iV; + for( iV = 1; iV <= cnbV; iV++ ) + { + if( iV == ciV ) + NWLine->AddVertex(newVtx); + else + { + IntPatch_Point theVtx = theWLline->Vertex(iV); + theVtx.SetParameter(VPold.Value(iV)); + NWLine->AddVertex(theVtx); + } + } + + theWLline = NWLine; + }//if( VDMin != 0 ) + }//for( ciV = 1; ciV <= cnbV; ciV++ ) +} + //======================================================================= //function : DublicateOfLinesProcessing //purpose : Decides, if rejecting current line is necessary @@ -1606,144 +1792,9 @@ void IntPatch_PrmPrmIntersection::Perform (const Handle(Adaptor3d_HSurface)& wline->AddVertex(vtx); } - Standard_Integer slinlen = SLin.Length(); - if( slinlen > 0 ) { - Standard_Integer cnbV = wline->NbVertex(); - Standard_Integer ciV; - for( ciV = 1; ciV <= cnbV; ciV++ ) { - Standard_Real pntDMin = 1.e+100; - Standard_Integer VDMin = 0; - Standard_Integer WLDMin = 0; - gp_Pnt cPV = wline->Vertex(ciV).Value(); - Standard_Integer iL; - for( iL = 1; iL <= slinlen; iL++) { - const Handle(IntPatch_Line)& aSLine = SLin.Value(iL); - IntPatch_IType aType = aSLine->ArcType(); - if( aType != IntPatch_Walking) - continue; - const Handle(IntPatch_WLine)& aWLine = (*((Handle(IntPatch_WLine)*)&aSLine)); - Standard_Integer tnbV = aWLine->NbVertex(); - Standard_Integer tiV; - for( tiV = 1; tiV <= tnbV; tiV++ ) { - gp_Pnt tPV = aWLine->Vertex(tiV).Value(); - Standard_Real tDistance = cPV.Distance(tPV); - Standard_Real uRs1 = Surf1->Surface().UResolution(tDistance); - Standard_Real vRs1 = Surf1->Surface().VResolution(tDistance); - Standard_Real uRs2 = Surf2->Surface().UResolution(tDistance); - Standard_Real vRs2 = Surf2->Surface().VResolution(tDistance); - Standard_Real RmaxS1 = Max(uRs1,vRs1); - Standard_Real RmaxS2 = Max(uRs2,vRs2); - if(RmaxS1 < 1.e-4 && RmaxS2 < 1.e-4) { - if( pntDMin > tDistance && tDistance > 1.e-9) { - pntDMin = tDistance; - VDMin = tiV; - WLDMin = iL; - } - } - } - } - - if( VDMin != 0 ) { - const Handle(IntPatch_Line)& aSLine = SLin.Value(WLDMin); - const Handle(IntPatch_WLine)& aWLine = (*((Handle(IntPatch_WLine)*)&aSLine)); - Standard_Integer tiVpar = (Standard_Integer)aWLine->Vertex(VDMin).ParameterOnLine(); - Standard_Integer ciVpar = (Standard_Integer)wline->Vertex(ciV).ParameterOnLine(); - Standard_Real u11 = 0., u12 = 0., v11 = 0., v12 = 0.; - Standard_Real u21 = 0., u22 = 0., v21 = 0., v22 = 0.; - wline->Point(ciVpar).Parameters(u11,v11,u12,v12); - aWLine->Point(tiVpar).Parameters(u21,v21,u22,v22); - - Handle(IntSurf_LineOn2S) newL2s = new IntSurf_LineOn2S(); - IntSurf_PntOn2S replacePnt = aWLine->Point(tiVpar); - Standard_Integer cNbP = wline->NbPnts(); - - TColStd_SequenceOfInteger VPold; - Standard_Integer iPo; - for( iPo = 1; iPo <= cnbV; iPo++ ) { - Standard_Real Po = wline->Vertex(iPo).ParameterOnLine(); - Standard_Integer IPo = (Standard_Integer) Po; - VPold.Append(IPo); - } - - Standard_Boolean removeNext = Standard_False; - Standard_Boolean removePrev = Standard_False; - if( ciV == 1) { - Standard_Integer dPar = Abs( VPold.Value(ciV) - VPold.Value(ciV+1)); - if(dPar > 10) { - removeNext = Standard_True; - for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) - VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); - } - } - else if( ciV == cnbV) { - Standard_Integer dPar = Abs( VPold.Value(ciV) - VPold.Value(ciV-1)); - if(dPar > 10) { - removePrev = Standard_True; - VPold.SetValue(ciV, VPold.Value(ciV) - 1 ); - } - } - else { - Standard_Integer dParMi = Abs( VPold.Value(ciV) - VPold.Value(ciV-1)); - Standard_Integer dParMa = Abs( VPold.Value(ciV) - VPold.Value(ciV+1)); - if(dParMi > 10) { - removePrev = Standard_True; - VPold.SetValue(ciV, VPold.Value(ciV) - 1 ); - } - if(dParMa > 10) { - removeNext = Standard_True; - for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) { - if(dParMi > 10) - VPold.SetValue(iPo, VPold.Value(iPo) - 2 ); - else - VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); - } - } - else { - if(dParMi > 10) - for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) - VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); - } - } - Standard_Integer pI = (Standard_Integer) ciVpar; - - Standard_Integer iP; - for( iP = 1; iP <= cNbP; iP++) { - if( pI == iP ) - { - IntSurf_PntOn2S newPnt = MakeNewPoint(replacePnt, wline->Point(iP), Periods); - newL2s->Add(newPnt); - } - else if(removeNext && iP == (pI + 1)) - continue; - else if(removePrev && iP == (pI - 1)) - continue; - else - newL2s->Add(wline->Point(iP)); - } - - IntPatch_Point newVtx; - gp_Pnt Pnt3dV = aWLine->Vertex(VDMin).Value(); - newVtx.SetValue(Pnt3dV,TolTang,Standard_False); - newVtx.SetParameters(u21,v21,u22,v22); - newVtx.SetParameter(VPold.Value(ciV)); - - Handle(IntPatch_WLine) NWLine = new IntPatch_WLine(newL2s,Standard_False,trans1,trans2); - - Standard_Integer iV; - for( iV = 1; iV <= cnbV; iV++ ) { - if( iV == ciV ) - NWLine->AddVertex(newVtx); - else { - IntPatch_Point theVtx = wline->Vertex(iV); - theVtx.SetParameter(VPold.Value(iV)); - NWLine->AddVertex(theVtx); - } - } - - wline = NWLine; - } - } - }// SLin.Length > 0 + SeveralWlinesProcessing(Surf1, Surf2, SLin, Periods, trans1, trans2, + TolTang, Max(PW.MaxStep(0), PW.MaxStep(1)), + Max(PW.MaxStep(2), PW.MaxStep(3)), wline); AddWLine(SLin, wline, Deflection); empt = Standard_False; @@ -2423,166 +2474,9 @@ void IntPatch_PrmPrmIntersection::Perform (const Handle(Adaptor3d_HSurface)& Sur lignetrouvee = Standard_True; - Standard_Integer slinlen = SLin.Length(); - if( slinlen > 0 ) - { - Standard_Integer cnbV = wline->NbVertex(); - Standard_Integer ciV; - for( ciV = 1; ciV <= cnbV; ciV++ ) - { - Standard_Real pntDMin = 1.e+100; - Standard_Integer VDMin = 0; - Standard_Integer WLDMin = 0; - gp_Pnt cPV = wline->Vertex(ciV).Value(); - Standard_Integer iL; - for( iL = 1; iL <= slinlen; iL++) - { - const Handle(IntPatch_Line)& aSLine = SLin.Value(iL); - IntPatch_IType aType = aSLine->ArcType(); - if( aType != IntPatch_Walking) - continue; - const Handle(IntPatch_WLine)& aWLine = (*((Handle(IntPatch_WLine)*)&aSLine)); - Standard_Integer tnbV = aWLine->NbVertex(); - Standard_Integer tiV; - for( tiV = 1; tiV <= tnbV; tiV++ ) - { - gp_Pnt tPV = aWLine->Vertex(tiV).Value(); - Standard_Real tDistance = cPV.Distance(tPV); - Standard_Real uRs1 = Surf1->Surface().UResolution(tDistance); - Standard_Real vRs1 = Surf1->Surface().VResolution(tDistance); - Standard_Real uRs2 = Surf2->Surface().UResolution(tDistance); - Standard_Real vRs2 = Surf2->Surface().VResolution(tDistance); - Standard_Real RmaxS1 = Max(uRs1,vRs1); - Standard_Real RmaxS2 = Max(uRs2,vRs2); - if(RmaxS1 < 1.e-4 && RmaxS2 < 1.e-4) - { - if( pntDMin > tDistance && tDistance > 1.e-9) - { - pntDMin = tDistance; - VDMin = tiV; - WLDMin = iL; - } - } - } - } - - if( VDMin != 0 ) - { - const Handle(IntPatch_Line)& aSLine = SLin.Value(WLDMin); - const Handle(IntPatch_WLine)& aWLine = (*((Handle(IntPatch_WLine)*)&aSLine)); - Standard_Integer tiVpar = (Standard_Integer)aWLine->Vertex(VDMin).ParameterOnLine(); - Standard_Integer ciVpar = (Standard_Integer)wline->Vertex(ciV).ParameterOnLine(); - Standard_Real u11 = 0., u12 = 0., v11 = 0., v12 = 0.; - Standard_Real u21 = 0., u22 = 0., v21 = 0., v22 = 0.; - wline->Point(ciVpar).Parameters(u11,v11,u12,v12); - aWLine->Point(tiVpar).Parameters(u21,v21,u22,v22); - - Handle(IntSurf_LineOn2S) newL2s = new IntSurf_LineOn2S(); - IntSurf_PntOn2S replacePnt = aWLine->Point(tiVpar); - Standard_Integer cNbP = wline->NbPnts(); - - TColStd_SequenceOfInteger VPold; - Standard_Integer iPo; - for( iPo = 1; iPo <= cnbV; iPo++ ) - { - Standard_Real Po = wline->Vertex(iPo).ParameterOnLine(); - Standard_Integer IPo = (Standard_Integer) Po; - VPold.Append(IPo); - } - - Standard_Boolean removeNext = Standard_False; - Standard_Boolean removePrev = Standard_False; - if( ciV == 1) - { - Standard_Integer dPar = Abs( VPold.Value(ciV) - VPold.Value(ciV+1)); - if(dPar > 10) - { - removeNext = Standard_True; - for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) - VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); - } - } - else if( ciV == cnbV) - { - Standard_Integer dPar = Abs( VPold.Value(ciV) - VPold.Value(ciV-1)); - if(dPar > 10) - { - removePrev = Standard_True; - VPold.SetValue(ciV, VPold.Value(ciV) - 1 ); - } - } - else - { - Standard_Integer dParMi = Abs( VPold.Value(ciV) - VPold.Value(ciV-1)); - Standard_Integer dParMa = Abs( VPold.Value(ciV) - VPold.Value(ciV+1)); - if(dParMi > 10) - { - removePrev = Standard_True; - VPold.SetValue(ciV, VPold.Value(ciV) - 1 ); - } - - if(dParMa > 10) - { - removeNext = Standard_True; - for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) - { - if(dParMi > 10) - VPold.SetValue(iPo, VPold.Value(iPo) - 2 ); - else - VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); - } - } - else - { - if(dParMi > 10) - for( iPo = (ciV+1); iPo <= cnbV; iPo++ ) - VPold.SetValue(iPo, VPold.Value(iPo) - 1 ); - } - } - - Standard_Integer pI = ciVpar; - - Standard_Integer iP; - for( iP = 1; iP <= cNbP; iP++) - { - if( pI == iP ) - { - IntSurf_PntOn2S newPnt = MakeNewPoint(replacePnt, wline->Point(iP), Periods); - newL2s->Add(newPnt); - } - else if(removeNext && iP == (pI + 1)) - continue; - else if(removePrev && iP == (pI - 1)) - continue; - else - newL2s->Add(wline->Point(iP)); - } - - IntPatch_Point newVtx; - gp_Pnt Pnt3dV = aWLine->Vertex(VDMin).Value(); - newVtx.SetValue(Pnt3dV,TolTang,Standard_False); - newVtx.SetParameters(u21,v21,u22,v22); - newVtx.SetParameter(VPold.Value(ciV)); - - Handle(IntPatch_WLine) NWLine = new IntPatch_WLine(newL2s,Standard_False,trans1,trans2); - - Standard_Integer iV; - for( iV = 1; iV <= cnbV; iV++ ) - { - if( iV == ciV ) - NWLine->AddVertex(newVtx); - else - { - IntPatch_Point theVtx = wline->Vertex(iV); - theVtx.SetParameter(VPold.Value(iV)); - NWLine->AddVertex(theVtx); - } - } - - wline = NWLine; - }//if( VDMin != 0 ) - }//for( ciV = 1; ciV <= cnbV; ciV++ ) - }// SLin.Length > 0 + SeveralWlinesProcessing(Surf1, Surf2, SLin, Periods, trans1, trans2, + TolTang, Max(PW.MaxStep(0), PW.MaxStep(1)), + Max(PW.MaxStep(2), PW.MaxStep(3)), wline); AddWLine(SLin, wline, Deflection); empt = Standard_False; diff --git a/src/IntWalk/IntWalk.cdl b/src/IntWalk/IntWalk.cdl index 5aa4e72566..eb9c321701 100644 --- a/src/IntWalk/IntWalk.cdl +++ b/src/IntWalk/IntWalk.cdl @@ -34,10 +34,10 @@ uses is enumeration StatusDeflection is - PasTropGrand, PointConfondu, ArretSurPointPrecedent, + PasTropGrand, StepTooSmall, PointConfondu, ArretSurPointPrecedent, ArretSurPoint, OK; --- StepTooGreat, ConfusedPoint, StopOnPreviousPoint, StopOnPoint, OK +-- StepTooGreat, StepTooSmall, ConfusedPoint, StopOnPreviousPoint, StopOnPoint, OK --class of result objects marching on a biparametric surface diff --git a/src/IntWalk/IntWalk_PWalking.cdl b/src/IntWalk/IntWalk_PWalking.cdl index 99b7bcd644..bb5721f202 100644 --- a/src/IntWalk/IntWalk_PWalking.cdl +++ b/src/IntWalk/IntWalk_PWalking.cdl @@ -210,7 +210,21 @@ is raises NotDone from StdFail is static; + + + MaxStep(me ; Index : Integer from Standard) + + ---Purpose: Returns the point of range Index on the polyline. + -- An exception is raised if IsDone returns False. + -- An exception is raised if Index<=0 or Index>NbPoints. + returns Real from Standard + ---C++: inline + + raises OutOfRange from Standard + + is static; + TangentAtLine(me; Index: out Integer from Standard) @@ -250,6 +264,12 @@ is POn2S : PntOn2S from IntSurf ) ; ---C++: inline + ComputePasInit(me : in out; + Um1, UM1, Vm1, VM1, Um2, UM2, Vm2, VM2, Um1p, UM1p, Vm1p, VM1p, Um2p, UM2p, Vm2p, VM2p, Increment, tolconf: Real from Standard) + + is protected; + + ExtendLineInCommonZone(me: in out; theChoixIso: ConstIsoparametric from IntImp; theDirectionFlag: Boolean from Standard) returns Boolean from Standard @@ -317,9 +337,11 @@ fields fleche : Real from Standard; -- max possible vector pasMax : Real from Standard; -- max possible uv ratio tolconf : Real from Standard; -- tol of confusion of 2 points + myTolTang : Real from Standard; pasuv : Real from Standard[4];-- uv step on squares pasSav : Real from Standard[4];-- first saved step pasInit : Real from Standard[4];-- saving of steps + myStepMin : Real from Standard[4]; Um1 : Real from Standard; UM1 : Real from Standard; diff --git a/src/IntWalk/IntWalk_PWalking.cxx b/src/IntWalk/IntWalk_PWalking.cxx index ae9e675e82..cca5be548c 100644 --- a/src/IntWalk/IntWalk_PWalking.cxx +++ b/src/IntWalk/IntWalk_PWalking.cxx @@ -40,20 +40,28 @@ // estimate of max step : To avoid abrupt changes // during change of isos //================================================================================== -void ComputePasInit(Standard_Real *pasuv, - Standard_Real Um1,Standard_Real UM1, - Standard_Real Vm1,Standard_Real VM1, - Standard_Real Um2,Standard_Real UM2, - Standard_Real Vm2,Standard_Real VM2, - Standard_Real _Um1,Standard_Real _UM1, - Standard_Real _Vm1,Standard_Real _VM1, - Standard_Real _Um2,Standard_Real _UM2, - Standard_Real _Vm2,Standard_Real _VM2, - const Handle(Adaptor3d_HSurface)& Caro1, - const Handle(Adaptor3d_HSurface)& Caro2, - const Standard_Real Increment, - const Standard_Real tolconf) -{ +void IntWalk_PWalking::ComputePasInit(const Standard_Real Um1, + const Standard_Real UM1, + const Standard_Real Vm1, + const Standard_Real VM1, + const Standard_Real Um2, + const Standard_Real UM2, + const Standard_Real Vm2, + const Standard_Real VM2, + const Standard_Real _Um1, + const Standard_Real _UM1, + const Standard_Real _Vm1, + const Standard_Real _VM1, + const Standard_Real _Um2, + const Standard_Real _UM2, + const Standard_Real _Vm2, + const Standard_Real _VM2, + const Standard_Real Increment, + const Standard_Real tolconf) +{ + const Handle(Adaptor3d_HSurface)& Caro1 = myIntersectionOn2S.Function().AuxillarSurface1(); + const Handle(Adaptor3d_HSurface)& Caro2 = myIntersectionOn2S.Function().AuxillarSurface2(); + Standard_Real du1=Abs(UM1-Um1); Standard_Real dv1=Abs(VM1-Vm1); Standard_Real du2=Abs(UM2-Um2); @@ -72,24 +80,25 @@ void ComputePasInit(Standard_Real *pasuv, if(_du2<1e50 && du2<0.01*_du2) du2=0.01*_du2; if(_dv2<1e50 && dv2<0.01*_dv2) dv2=0.01*_dv2; - pasuv[0]=Increment*du1; - pasuv[1]=Increment*dv1; - pasuv[2]=Increment*du2; - pasuv[3]=Increment*dv2; + pasuv[0]=Max(Increment*du1, pasuv[0]); + pasuv[1]=Max(Increment*dv1, pasuv[1]); + pasuv[2]=Max(Increment*du2, pasuv[2]); + pasuv[3]=Max(Increment*dv2, pasuv[3]); Standard_Real ResoU1tol = Adaptor3d_HSurfaceTool::UResolution(Caro1, tolconf); Standard_Real ResoV1tol = Adaptor3d_HSurfaceTool::VResolution(Caro1, tolconf); Standard_Real ResoU2tol = Adaptor3d_HSurfaceTool::UResolution(Caro2, tolconf); Standard_Real ResoV2tol = Adaptor3d_HSurfaceTool::VResolution(Caro2, tolconf); - if (pasuv[0] < 2*ResoU1tol) - pasuv[0] = 2*ResoU1tol; - if (pasuv[1] < 2*ResoV1tol) - pasuv[1] = 2*ResoV1tol; - if (pasuv[2] < 2*ResoU2tol) - pasuv[2] = 2*ResoU2tol; - if (pasuv[3] < 2*ResoV2tol) - pasuv[3] = 2*ResoV2tol; + myStepMin[0] = Max(myStepMin[0], 2.0*ResoU1tol); + myStepMin[1] = Max(myStepMin[1], 2.0*ResoV1tol); + myStepMin[2] = Max(myStepMin[2], 2.0*ResoU2tol); + myStepMin[3] = Max(myStepMin[3], 2.0*ResoV2tol); + + for(Standard_Integer i = 0; i < 4; i++) + { + pasuv[i]=Max(myStepMin[i], pasuv[i]); + } } //======================================================================= @@ -268,6 +277,7 @@ done(Standard_True), close(Standard_False), fleche(Deflection), tolconf(Epsilon), +myTolTang(TolTangency), sensCheminement(1), myIntersectionOn2S(Caro1,Caro2,TolTangency), STATIC_BLOCAGE_SUR_PAS_TROP_GRAND(0), @@ -378,6 +388,11 @@ STATIC_PRECEDENT_INFLEXION(0) } } + myStepMin[0] = 100.0*ResoU1; + myStepMin[1] = 100.0*ResoV1; + myStepMin[2] = 100.0*ResoU2; + myStepMin[3] = 100.0*ResoV2; + //-- ComputePasInit(pasuv,Um1,UM1,Vm1,VM1,Um2,UM2,Vm2,VM2,Caro1,Caro2); for (Standard_Integer i = 0; i<=3;i++) { @@ -408,6 +423,7 @@ done(Standard_True), close(Standard_False), fleche(Deflection), tolconf(Epsilon), +myTolTang(TolTangency), sensCheminement(1), myIntersectionOn2S(Caro1,Caro2,TolTangency), STATIC_BLOCAGE_SUR_PAS_TROP_GRAND(0), @@ -544,6 +560,12 @@ STATIC_PRECEDENT_INFLEXION(0) if(ResoV1>0.0001*pasuv[1]) ResoV1=0.00001*pasuv[1]; if(ResoU2>0.0001*pasuv[2]) ResoU2=0.00001*pasuv[2]; if(ResoV2>0.0001*pasuv[3]) ResoV2=0.00001*pasuv[3]; + + myStepMin[0] = 100.0*ResoU1; + myStepMin[1] = 100.0*ResoV1; + myStepMin[2] = 100.0*ResoU2; + myStepMin[3] = 100.0*ResoV2; + // TColStd_Array1OfReal Par(1,4); Par(1) = U1; @@ -623,6 +645,7 @@ static Standard_Boolean IsTangentExtCheck(const Handle(Adaptor3d_HSurface)& theS const Standard_Real theV10, const Standard_Real theU20, const Standard_Real theV20, + const Standard_Real theToler, const Standard_Real theArrStep[]) { { @@ -646,7 +669,8 @@ static Standard_Boolean IsTangentExtCheck(const Handle(Adaptor3d_HSurface)& theS } } - const Standard_Real aSQToler = 4.0e-14; + //For two faces (2^2 = 4) + const Standard_Real aSQToler = 4.0*theToler*theToler; const Standard_Integer aNbItems = 4; const Standard_Real aParUS1[aNbItems] = { theU10 + theArrStep[0], theU10 - theArrStep[0], @@ -718,22 +742,9 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep, const Standard_Real ULast2 = Adaptor3d_HSurfaceTool::LastUParameter (Caro2); const Standard_Real VLast2 = Adaptor3d_HSurfaceTool::LastVParameter (Caro2); // - ComputePasInit(pasuv,u1min,u1max,v1min,v1max,u2min,u2max,v2min,v2max, - Um1,UM1,Vm1,VM1,Um2,UM2,Vm2,VM2,Caro1,Caro2,pasMax+pasMax,tolconf); - // - if(pasuv[0]<100.0*ResoU1) { - pasuv[0]=100.0*ResoU1; - } - if(pasuv[1]<100.0*ResoV1) { - pasuv[1]=100.0*ResoV1; - } - if(pasuv[2]<100.0*ResoU2) { - pasuv[2]=100.0*ResoU2; - } - if(pasuv[3]<100.0*ResoV2) { - pasuv[3]=100.0*ResoV2; - } - // + ComputePasInit(u1min,u1max,v1min,v1max,u2min,u2max,v2min,v2max, + Um1,UM1,Vm1,VM1,Um2,UM2,Vm2,VM2,pasMax+pasMax,tolconf); + for (Standard_Integer i=0; i<4; ++i) { if(pasuv[i]>10) @@ -807,7 +818,7 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep, previousPoint.Parameters(Param(1),Param(2),Param(3),Param(4)); - if(IsTangentExtCheck(Caro1, Caro2, Param(1), Param(2), Param(3), Param(4), pasuv)) + if(IsTangentExtCheck(Caro1, Caro2, Param(1), Param(2), Param(3), Param(4), myTolTang, pasuv)) return; AddAPoint(line,previousPoint); @@ -1166,27 +1177,9 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep, { pastroppetit=Standard_True; - if(pasuv[0] pasuv[i]) + { + pasuv[i] = aNewStep; + hasStepBeenIncreased = Standard_True; + } + } + + if(hasStepBeenIncreased) + { + Param(1)=SvParam[0]; + Param(2)=SvParam[1]; + Param(3)=SvParam[2]; + Param(4)=SvParam[3]; + + LevelOfIterWithoutAppend = 0; + + break; + } + } case IntWalk_OK: case IntWalk_ArretSurPoint://006 { @@ -1299,6 +1318,7 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep, if(RejectIndex >= RejectIndexMAX) { + Arrive = Standard_True; break; } @@ -1386,6 +1406,7 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep, if(RejectIndex >= RejectIndexMAX) { + Arrive = Standard_True; break; } @@ -1619,6 +1640,7 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep, if(RejectIndex >= RejectIndexMAX) { + Arrive = Standard_True; break; } @@ -2104,7 +2126,7 @@ DistanceMinimizeByGradient( const Handle(Adaptor3d_HSurface)& theASurf1, aS1 = theASurf1->Surface().BSpline(); break; default: - return Standard_True; + return Standard_True; } switch(theASurf2->GetType()) @@ -2116,7 +2138,7 @@ DistanceMinimizeByGradient( const Handle(Adaptor3d_HSurface)& theASurf1, aS2 = theASurf2->Surface().BSpline(); break; default: - return Standard_True; + return Standard_True; } Standard_Boolean aStatus = Standard_False; @@ -2821,7 +2843,7 @@ IntWalk_StatusDeflection IntWalk_PWalking::TestDeflection() } IntWalk_StatusDeflection Status = IntWalk_OK; - Standard_Real FlecheCourante ,Ratio; + Standard_Real FlecheCourante , Ratio = 1.0; const IntSurf_PntOn2S& CurrentPoint = myIntersectionOn2S.Point(); @@ -2834,10 +2856,12 @@ IntWalk_StatusDeflection IntWalk_PWalking::TestDeflection() const gp_Dir& TgCourante = myIntersectionOn2S.Direction(); + const Standard_Real aCosBetweenTangent = TgCourante.Dot(previousd); + //================================================================================== //========= R i s k o f i n f l e x i o n p o i n t ============ //================================================================================== - if (TgCourante.Dot(previousd)<0) { + if (aCosBetweenTangent < 0) { //------------------------------------------------------------ //-- Risk of inflexion point : Divide the step by 2 //-- Initialize STATIC_PRECEDENT_INFLEXION so that @@ -2855,7 +2879,6 @@ IntWalk_StatusDeflection IntWalk_PWalking::TestDeflection() else return IntWalk_PasTropGrand; } - else { if(STATIC_PRECEDENT_INFLEXION > 0) { STATIC_PRECEDENT_INFLEXION -- ; @@ -2867,11 +2890,11 @@ IntWalk_StatusDeflection IntWalk_PWalking::TestDeflection() //========= D e t e c t c o n f u s e d P o in t s =========== //================================================================================== - Standard_Real Dist = previousPoint.Value(). + const Standard_Real aSqDist = previousPoint.Value(). SquareDistance(CurrentPoint.Value()); - if (Dist < tolconf*tolconf ) { + if (aSqDist < tolconf*tolconf ) { pasuv[0] = Max(5.*ResoU1,Min(1.5*pasuv[0],pasInit[0])); pasuv[1] = Max(5.*ResoV1,Min(1.5*pasuv[1],pasInit[1])); pasuv[2] = Max(5.*ResoU2,Min(1.5*pasuv[2],pasInit[2])); @@ -2994,7 +3017,7 @@ IntWalk_StatusDeflection IntWalk_PWalking::TestDeflection() //-- Estimate of the vector -- //--------------------------------------- FlecheCourante = - Sqrt(Abs((previousd.XYZ()-TgCourante.XYZ()).SquareModulus()*Dist))/8.; + Sqrt(Abs((previousd.XYZ()-TgCourante.XYZ()).SquareModulus()*aSqDist))/8.; if ( FlecheCourante<= fleche*0.5) { //-- Current step too small if(FlecheCourante>1e-16) { @@ -3061,10 +3084,94 @@ IntWalk_StatusDeflection IntWalk_PWalking::TestDeflection() Ratio = 0.75 * (fleche / FlecheCourante); } } - pasuv[0] = Max(5.*ResoU1,Min(Min(Ratio*AbsDu1,pasuv[0]),pasInit[0])); - pasuv[1] = Max(5.*ResoV1,Min(Min(Ratio*AbsDv1,pasuv[1]),pasInit[1])); - pasuv[2] = Max(5.*ResoU2,Min(Min(Ratio*AbsDu2,pasuv[2]),pasInit[2])); - pasuv[3] = Max(5.*ResoV2,Min(Min(Ratio*AbsDv2,pasuv[3]),pasInit[3])); + + if(Status != IntWalk_PointConfondu) + { + //Here, aCosBetweenTangent >= 0.0 definitely. + + /* + Brief algorithm description. + We have two (not-coincindent) intersection point (P1 and P2). In every point, + vector of tangent (to the intersection curve) is known (vectors T1 and T2). + Basing on these data, we create osculating circle. + + * - arc of osculating circle + * * + P1 x----------x P2 + / \ + / \ + Vec(T1) Vec(T2) + + Let me draw your attention to the following facts: + 1. Vectors T1 and T2 direct FROM (not TO) points P1 and P2. Therefore, + one of previously computed vector should be reversed. + + In this case, the absolute (!) value of the deflection between the arc of + the osculating circle and the P1P2 segment can be computed as follows: + e = d*(1-sin(B/2))/(2*cos(B/2)), (1) + where d is the length of P1P2 segment, B is the angle between vectors T1 and T2. + At that, + pi/2 <= B <= pi, + cos(B/2) >= 0, + sin(B/2) > 0, + sin(B) > 0, + cos(B) < 0. + + Later, the normal state of algorithm work is (as we apply) + tolconf/2 <= e <= tolconf. + In this case, we keep previous step. + + If e < tolconf/2 then the local curvature of the intersection curve is small. + As result, the step should be increased. + + If e > tolconf then the step is too big. Therefore, we should decrease one. + + Condition (1) is equivalent to + cos(B) = 1 - 2*(1-2/(1+(d/(2*e))^2))^2 = Fd(e), + where Fd(e) is some function with parameter "deflection". + + Let mean that Fd(e) is increasing function, i.e. the greater cos(B) + the greater real deflection e. + */ + + //When Deflection is equal to tolconf + const Standard_Real anInvSqAbsArcDeflMax = 0.25*aSqDist/(tolconf*tolconf); + + //When Deflection is equal to tolconf/2 + const Standard_Real anInvSqAbsArcDeflMin = 4.0*anInvSqAbsArcDeflMax; + const Standard_Real aThresholdCosMin = 1.0 - 2.0/(1.0 + anInvSqAbsArcDeflMin); + const Standard_Real aThresholdCosMax = 1.0 - 2.0/(1.0 + anInvSqAbsArcDeflMax); + + if((Status != IntWalk_PasTropGrand) && (aCosBetweenTangent < 2.0*aThresholdCosMax*aThresholdCosMax - 1.0)) + { // I.e. cos(B) >= Fd(tolconf). + // Consequently, real deflection is greater than tolconf (too big) ==> decrease step + pasuv[0]*=0.5; pasuv[1]*=0.5; pasuv[2]*=0.5; pasuv[3]*=0.5; + return IntWalk_PasTropGrand; + } + + if(aCosBetweenTangent > 2.0*aThresholdCosMin*aThresholdCosMin - 1.0) + { //I.e. cos(B) <= Fd(tolconf/2) + // Consequently, real deflection is less than tolconf/2 (too small) ==> increase step + + pasuv[0] = Max(pasuv[0], AbsDu1); + pasuv[1] = Max(pasuv[1], AbsDv1); + pasuv[2] = Max(pasuv[2], AbsDu2); + pasuv[3] = Max(pasuv[3], AbsDv2); + + pasInit[0] = Max(pasInit[0], AbsDu1); + pasInit[1] = Max(pasInit[1], AbsDv1); + pasInit[2] = Max(pasInit[2], AbsDu2); + pasInit[3] = Max(pasInit[3], AbsDv2); + + return IntWalk_StepTooSmall; + } + } + + pasuv[0] = Max(myStepMin[0],Min(Min(Ratio*AbsDu1,pasuv[0]),pasInit[0])); + pasuv[1] = Max(myStepMin[1],Min(Min(Ratio*AbsDv1,pasuv[1]),pasInit[1])); + pasuv[2] = Max(myStepMin[2],Min(Min(Ratio*AbsDu2,pasuv[2]),pasInit[2])); + pasuv[3] = Max(myStepMin[3],Min(Min(Ratio*AbsDv2,pasuv[3]),pasInit[3])); + if(Status == IntWalk_OK) STATIC_BLOCAGE_SUR_PAS_TROP_GRAND=0; return Status; } diff --git a/src/IntWalk/IntWalk_PWalking.lxx b/src/IntWalk/IntWalk_PWalking.lxx index e1614170c9..430d1bf124 100644 --- a/src/IntWalk/IntWalk_PWalking.lxx +++ b/src/IntWalk/IntWalk_PWalking.lxx @@ -62,6 +62,12 @@ inline const gp_Dir& IntWalk_PWalking::TangentAtLine return tgdir; } +inline Standard_Real IntWalk_PWalking::MaxStep(Standard_Integer theIndex) const +{ + Standard_OutOfRange_Raise_if((theIndex < 0) || (theIndex > 3), ""); + return pasInit[theIndex]; +} + #define REGLAGE 0 inline void IntWalk_PWalking::AddAPoint(Handle(IntSurf_LineOn2S)& theLine, diff --git a/tests/bugs/modalg_6/bug26980 b/tests/bugs/modalg_6/bug26980 new file mode 100644 index 0000000000..2c2e4525aa --- /dev/null +++ b/tests/bugs/modalg_6/bug26980 @@ -0,0 +1,64 @@ +puts "========" +puts "OCC26980" +puts "========" +puts "" +################################# +# Intersection part of Boolean algorithm spends much system time and system memory +################################# + +cpulimit 5000 + +set max_time 120 +set mem_max_wsetpeak 700000000 + + +bclearobjects; +bcleartools; + +restore [locate_data_file bug26980-cmp.brep] cmp + +puts [nbshapes cmp -t] + +eval baddobjects [explode cmp] + +dchrono cr reset +dchrono cr start + +bfillds +bbuild result + +dchrono cr stop + +set mem_wsetpeak [meminfo wsetpeak] + +if { ${mem_wsetpeak} > ${mem_max_wsetpeak}} { + puts "Error : there is memory problem (${mem_wsetpeak} MBytes has been allocated)" +} + +set chrono_info [dchrono cr show] +regexp {CPU user time: ([-0-9.+eE]+) seconds} $chrono_info full CPU_time +if { $CPU_time > ${max_time} } { + puts "CPU user time of Boolean operation is more than ${max_time} seconds - Error" +} else { + puts "CPU user time of Boolean operation is less than ${max_time} seconds - OK" +} + +set nbshapes_expected " + VERTEX : 365 + EDGE : 793 + WIRE : 531 + FACE : 531 + SHELL : 102 + SOLID : 101 + COMPSOLID : 0 + COMPOUND : 1 + SHAPE : 2424 +" + +checknbshapes result -ref ${nbshapes_expected} -t + +smallview +donly result +fit + +set 2dviewer 1 -- 2.39.5