mirror of
https://git.dev.opencascade.org/repos/occt.git
synced 2025-08-09 13:22:24 +03:00
0025890: Intersection algorithm produces curves overlaped
1. Function IntImp_Int2S::ChangePoint() has been added (see cdl for detail information). 2. Attempt to forbidden break WLine if it goes along surface boundary. Code optimization. 2nd optimization Test case for issue CR25890
This commit is contained in:
@@ -710,6 +710,11 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep,
|
||||
Standard_Integer LevelOfPointConfondu = 0;
|
||||
Standard_Integer LevelOfIterWithoutAppend = -1;
|
||||
//
|
||||
|
||||
const Standard_Real aTol[4] = { Epsilon(u1max - u1min),
|
||||
Epsilon(v1max - v1min),
|
||||
Epsilon(u2max - u2min),
|
||||
Epsilon(v2max - v2min)};
|
||||
Arrive = Standard_False;
|
||||
while(!Arrive) //010
|
||||
{
|
||||
@@ -792,8 +797,23 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep,
|
||||
|
||||
if (myIntersectionOn2S.IsDone() && !myIntersectionOn2S.IsEmpty())
|
||||
{
|
||||
//If we go along any surface boundary then it is possible
|
||||
//to find "outboundaried" point.
|
||||
//Nevertheless, if this deflection is quite small, we will be
|
||||
//able to adjust this point to the boundary.
|
||||
|
||||
Standard_Real aNewPnt[4], anAbsParamDist[4];
|
||||
myIntersectionOn2S.Point().Parameters(aNewPnt[0], aNewPnt[1], aNewPnt[2], aNewPnt[3]);
|
||||
const Standard_Real aParMin[4] = {u1min, v1min, u2min, v2min};
|
||||
const Standard_Real aParMax[4] = {u1max, v1max, u2max, v2max};
|
||||
|
||||
for(Standard_Integer i = 0; i < 4; i++)
|
||||
{
|
||||
if(Abs(aNewPnt[i] - aParMin[i]) < aTol[i])
|
||||
aNewPnt[i] = aParMin[i];
|
||||
else if(Abs(aNewPnt[i] - aParMax[i]) < aTol[i])
|
||||
aNewPnt[i] = aParMax[i];
|
||||
}
|
||||
|
||||
if (aNewPnt[0] < u1min || aNewPnt[0] > u1max ||
|
||||
aNewPnt[1] < v1min || aNewPnt[1] > v1max ||
|
||||
@@ -803,6 +823,11 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep,
|
||||
break; // Out of borders, handle this later.
|
||||
}
|
||||
|
||||
myIntersectionOn2S.ChangePoint().SetValue(aNewPnt[0],
|
||||
aNewPnt[1],
|
||||
aNewPnt[2],
|
||||
aNewPnt[3]);
|
||||
|
||||
anAbsParamDist[0] = Abs(Param(1) - dP1 - aNewPnt[0]);
|
||||
anAbsParamDist[1] = Abs(Param(2) - dP2 - aNewPnt[1]);
|
||||
anAbsParamDist[2] = Abs(Param(3) - dP3 - aNewPnt[2]);
|
||||
@@ -1327,8 +1352,11 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep,
|
||||
gp_Vec2d V2onS1(gp_Pnt2d(pU1, pV1), gp_Pnt2d(u1, v1));
|
||||
gp_Vec2d V1onS2(gp_Pnt2d(ppU2, ppV2), gp_Pnt2d(pU2, pV2));
|
||||
gp_Vec2d V2onS2(gp_Pnt2d(pU2, pV2), gp_Pnt2d(u2, v2));
|
||||
if (V1onS1 * V2onS1 < 0. ||
|
||||
V1onS2 * V2onS2 < 0.)
|
||||
|
||||
const Standard_Real aDot1 = V1onS1 * V2onS1;
|
||||
const Standard_Real aDot2 = V1onS2 * V2onS2;
|
||||
|
||||
if ((aDot1 < 0.0) || (aDot2 < 0.0))
|
||||
{
|
||||
Arrive = Standard_True;
|
||||
break;
|
||||
@@ -1423,7 +1451,58 @@ void IntWalk_PWalking::Perform(const TColStd_Array1OfReal& ParDep,
|
||||
Arrive = Standard_True;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
//Check singularity.
|
||||
//I.e. check if we are walking along direction, which does not
|
||||
//result in comming to any point (i.e. derivative
|
||||
//3D-intersection curve along this direction is equal to 0).
|
||||
//A sphere with direction {dU=1, dV=0} from point
|
||||
//(U=0, V=M_PI/2) can be considered as example for
|
||||
//this case (we cannot find another 3D-point if we go thus).
|
||||
|
||||
//Direction chosen along 1st and 2nd surface correspondingly
|
||||
const gp_Vec2d aDirS1(prevPntOnS1, curPntOnS1),
|
||||
aDirS2(prevPntOnS2, curPntOnS2);
|
||||
|
||||
gp_Pnt aPtemp;
|
||||
gp_Vec aDuS1, aDvS1, aDuS2, aDvS2;
|
||||
|
||||
myIntersectionOn2S.Function().AuxillarSurface1()->
|
||||
D1(curPntOnS1.X(), curPntOnS1.Y(), aPtemp, aDuS1, aDvS1);
|
||||
myIntersectionOn2S.Function().AuxillarSurface2()->
|
||||
D1(curPntOnS2.X(), curPntOnS2.Y(), aPtemp, aDuS2, aDvS2);
|
||||
|
||||
//Derivative WLine along (it is vector-function indeed)
|
||||
//directions chosen
|
||||
//(https://en.wikipedia.org/wiki/Directional_derivative#Variation_using_only_direction_of_vector).
|
||||
//F1 - on the 1st surface, F2 - on the 2nd surface.
|
||||
//x, y, z - coordinates of derivative vector.
|
||||
const Standard_Real aF1x = aDuS1.X()*aDirS1.X() +
|
||||
aDvS1.X()*aDirS1.Y();
|
||||
const Standard_Real aF1y = aDuS1.Y()*aDirS1.X() +
|
||||
aDvS1.Y()*aDirS1.Y();
|
||||
const Standard_Real aF1z = aDuS1.Z()*aDirS1.X() +
|
||||
aDvS1.Z()*aDirS1.Y();
|
||||
const Standard_Real aF2x = aDuS2.X()*aDirS2.X() +
|
||||
aDvS2.X()*aDirS2.Y();
|
||||
const Standard_Real aF2y = aDuS2.Y()*aDirS2.X() +
|
||||
aDvS2.Y()*aDirS2.Y();
|
||||
const Standard_Real aF2z = aDuS2.Z()*aDirS2.X() +
|
||||
aDvS2.Z()*aDirS2.Y();
|
||||
|
||||
const Standard_Real aF1 = aF1x*aF1x + aF1y*aF1y + aF1z*aF1z;
|
||||
const Standard_Real aF2 = aF2x*aF2x + aF2y*aF2y + aF2z*aF2z;
|
||||
|
||||
if((aF1 < gp::Resolution()) && (aF2 < gp::Resolution()))
|
||||
{
|
||||
//All derivative are equal to 0. Therefore, there is
|
||||
//no point in going along direction chosen.
|
||||
Arrive = Standard_True;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}//if (previoustg) cond.
|
||||
|
||||
////////////////////////////////////////
|
||||
AddAPoint(line,previousPoint);
|
||||
|
Reference in New Issue
Block a user