Back to home page

EIC code displayed by LXR

 
 

    


Warning, /include/opencascade/IntPatch_ImpImpIntersection_2.gxx is written in an unsupported language. File is not indexed.

0001 // Created on: 1992-05-07
0002 // Created by: Jacques GOUSSARD
0003 // Copyright (c) 1992-1999 Matra Datavision
0004 // Copyright (c) 1999-2014 OPEN CASCADE SAS
0005 //
0006 // This file is part of Open CASCADE Technology software library.
0007 //
0008 // This library is free software; you can redistribute it and/or modify it under
0009 // the terms of the GNU Lesser General Public License version 2.1 as published
0010 // by the Free Software Foundation, with special exception defined in the file
0011 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
0012 // distribution for complete text of the license and disclaimer of any warranty.
0013 //
0014 // Alternatively, this file may be used under the terms of Open CASCADE
0015 // commercial license or contractual agreement.
0016 
0017 #include <IntPatch_WLine.hxx>
0018 
0019 static 
0020   Standard_Integer SetQuad(const Handle(Adaptor3d_Surface)& theS,
0021                            GeomAbs_SurfaceType& theTS,
0022                            IntSurf_Quadric& theQuad);
0023 
0024 //=======================================================================
0025 //function : IntPatch_ImpImpIntersection
0026 //purpose  : 
0027 //=======================================================================
0028 IntPatch_ImpImpIntersection::IntPatch_ImpImpIntersection ():
0029 myDone(IntStatus_Fail),
0030 empt(Standard_True),
0031 tgte(Standard_False),
0032 oppo(Standard_False)
0033 {
0034 }
0035 //=======================================================================
0036 //function : IntPatch_ImpImpIntersection
0037 //purpose  : 
0038 //=======================================================================
0039 IntPatch_ImpImpIntersection::IntPatch_ImpImpIntersection
0040        (const Handle(Adaptor3d_Surface)&  S1,
0041         const Handle(Adaptor3d_TopolTool)& D1,
0042         const Handle(Adaptor3d_Surface)&  S2,
0043         const Handle(Adaptor3d_TopolTool)& D2,
0044         const Standard_Real TolArc,
0045         const Standard_Real TolTang,
0046         const Standard_Boolean theIsReqToKeepRLine)
0047 {
0048   Perform(S1,D1,S2,D2,TolArc,TolTang, theIsReqToKeepRLine);
0049 }
0050 //=======================================================================
0051 //function : Perform
0052 //purpose  : 
0053 //=======================================================================
0054 void IntPatch_ImpImpIntersection::Perform(const Handle(Adaptor3d_Surface)&  S1,
0055                                           const Handle(Adaptor3d_TopolTool)& D1,
0056                                           const Handle(Adaptor3d_Surface)&  S2,
0057                                           const Handle(Adaptor3d_TopolTool)& D2,
0058                                           const Standard_Real TolArc,
0059                                           const Standard_Real TolTang,
0060                                           const Standard_Boolean theIsReqToKeepRLine)
0061 {
0062   myDone = IntStatus_Fail;
0063   spnt.Clear();
0064   slin.Clear();
0065 
0066   Standard_Boolean isPostProcessingRequired = Standard_True;
0067 
0068   empt = Standard_True;
0069   tgte = Standard_False;
0070   oppo = Standard_False;
0071 
0072   Standard_Boolean all1 = Standard_False;
0073   Standard_Boolean all2 = Standard_False;
0074   Standard_Boolean SameSurf = Standard_False;
0075   Standard_Boolean multpoint = Standard_False;
0076 
0077   Standard_Boolean nosolonS1 = Standard_False;
0078   // indique s il y a des points sur restriction du carreau 1
0079   Standard_Boolean nosolonS2 = Standard_False;
0080   // indique s il y a des points sur restriction du carreau 2
0081   Standard_Integer i, nbpt, nbseg;
0082   IntPatch_SequenceOfSegmentOfTheSOnBounds edg1,edg2;
0083   IntPatch_SequenceOfPathPointOfTheSOnBounds pnt1,pnt2;
0084   //
0085   // On commence par intersecter les supports des surfaces
0086   IntSurf_Quadric quad1, quad2;
0087   IntPatch_ArcFunction AFunc;
0088   const Standard_Real Tolang = 1.e-8;
0089   GeomAbs_SurfaceType typs1, typs2;
0090   Standard_Boolean bEmpty = Standard_False;
0091   //
0092   const Standard_Integer iT1 = SetQuad(S1, typs1, quad1);
0093   const Standard_Integer iT2 = SetQuad(S2, typs2, quad2);
0094   //
0095   if (!iT1 || !iT2) {
0096     throw Standard_ConstructionError();
0097     return;
0098   }
0099   //
0100   const Standard_Boolean bReverse = iT1 > iT2;
0101   const Standard_Integer iTT = iT1*10 + iT2;
0102   //
0103   switch (iTT) {
0104     case 11: { // Plane/Plane
0105       if (!IntPP(quad1, quad2, Tolang, TolTang, SameSurf, slin)) {
0106         return;
0107       }
0108       break;
0109     }
0110     //
0111     case 12:
0112     case 21: { // Plane/Cylinder
0113       Standard_Real VMin, VMax, H;
0114       //
0115       const Handle(Adaptor3d_Surface)& aSCyl = bReverse ? S1 : S2;
0116       VMin = aSCyl->FirstVParameter();
0117       VMax = aSCyl->LastVParameter();
0118       H = (Precision::IsNegativeInfinite(VMin) || 
0119            Precision::IsPositiveInfinite(VMax)) ? 0 : (VMax - VMin);
0120       //
0121       if (!IntPCy(quad1, quad2, Tolang, TolTang, bReverse, empt, slin, H)) {
0122         return;
0123       }
0124       bEmpty = empt;
0125       break;
0126     }
0127     //
0128     case 13:
0129     case 31: { // Plane/Cone
0130       if (!IntPCo(quad1, quad2, Tolang, TolTang, bReverse, empt, multpoint, slin, spnt)) {
0131         return;
0132       }
0133       bEmpty = empt;
0134       break;
0135     }
0136     //
0137     case 14:
0138     case 41: { // Plane/Sphere
0139       if (!IntPSp(quad1, quad2, Tolang, TolTang, bReverse, empt, slin, spnt)) {
0140         return;
0141       }
0142       bEmpty = empt;
0143       break;
0144     }
0145     //
0146     case 15:
0147     case 51: { // Plane/Torus
0148       if (!IntPTo(quad1, quad2, TolTang, bReverse, empt, slin)) {
0149         return;
0150       }
0151       bEmpty = empt;
0152       break;
0153     }
0154     //
0155     case 22:
0156       { // Cylinder/Cylinder
0157         Bnd_Box2d aBox1, aBox2;
0158 
0159         const Standard_Real aU1f = S1->FirstUParameter();
0160         Standard_Real aU1l = S1->LastUParameter();
0161         const Standard_Real aU2f = S2->FirstUParameter();
0162         Standard_Real aU2l = S2->LastUParameter();
0163 
0164         const Standard_Real anUperiod = 2.0*M_PI;
0165 
0166         if(aU1l - aU1f > anUperiod)
0167           aU1l = aU1f + anUperiod;
0168 
0169         if(aU2l - aU2f > anUperiod)
0170           aU2l = aU2f + anUperiod;
0171 
0172         aBox1.Add(gp_Pnt2d(aU1f, S1->FirstVParameter()));
0173         aBox1.Add(gp_Pnt2d(aU1l, S1->LastVParameter()));
0174         aBox2.Add(gp_Pnt2d(aU2f, S2->FirstVParameter()));
0175         aBox2.Add(gp_Pnt2d(aU2l, S2->LastVParameter()));
0176 
0177         // Resolution is too big if the cylinder radius is
0178         // too small. Therefore, we shall bind its value above. 
0179         // Here, we use simple constant.
0180         const Standard_Real a2DTol = Min(1.0e-4, Min( S1->UResolution(TolTang),
0181                                             S2->UResolution(TolTang)));
0182 
0183         myDone = IntCyCy(quad1, quad2, TolTang, a2DTol, aBox1, aBox2,
0184                                     empt, SameSurf, multpoint, slin, spnt);
0185 
0186         if (myDone == IntPatch_ImpImpIntersection::IntStatus_Fail)
0187         {
0188           return;
0189         }
0190 
0191         bEmpty = empt;
0192         if(!slin.IsEmpty())
0193         {
0194           const Handle(IntPatch_WLine)& aWLine = 
0195                                     Handle(IntPatch_WLine)::DownCast(slin.Value(1));
0196 
0197           if(!aWLine.IsNull())
0198           {//No geometric solution
0199             isPostProcessingRequired = Standard_False;
0200           }
0201         }
0202 
0203         break;
0204       }
0205     //
0206     case 23:
0207     case 32: { // Cylinder/Cone
0208       if (!IntCyCo(quad1, quad2, TolTang, bReverse, empt, multpoint, slin, spnt)) {
0209         return;
0210       }
0211       bEmpty = empt;
0212       break;
0213     }
0214     //
0215     case 24:
0216     case 42: { // Cylinder/Sphere
0217       if (!IntCySp(quad1, quad2, TolTang, bReverse, empt, multpoint, slin, spnt)) {
0218         return;
0219       }
0220       bEmpty = empt;
0221       break;
0222     }
0223     //
0224     case 25:
0225     case 52: { // Cylinder/Torus
0226       if (!IntCyTo(quad1, quad2, TolTang, bReverse, empt, slin)) {
0227         return;
0228       }
0229       bEmpty = empt;
0230       break;
0231     }
0232     //
0233     case 33: { // Cone/Cone
0234       if (!IntCoCo(quad1, quad2, TolTang, empt, SameSurf, multpoint, slin, spnt)) {
0235         return;
0236       }
0237       bEmpty = empt;
0238       break;
0239     }
0240     //
0241     case 34:
0242     case 43: { // Cone/Sphere
0243       if (!IntCoSp(quad1, quad2, TolTang, bReverse, empt, multpoint, slin, spnt)) {
0244         return;
0245       }
0246       bEmpty = empt;
0247       break;
0248     }
0249     //
0250     case 35:
0251     case 53: { // Cone/Torus
0252       if (!IntCoTo(quad1, quad2, TolTang, bReverse, empt, slin)) {
0253         return;
0254       }
0255       break;
0256     }
0257     //
0258     case 44: { // Sphere/Sphere
0259       if (!IntSpSp(quad1, quad2, TolTang, empt, SameSurf, slin, spnt)) {
0260         return;
0261       }
0262       bEmpty = empt;
0263       break;
0264     }
0265     //
0266     case 45:
0267     case 54: { // Sphere/Torus
0268       if (!IntSpTo(quad1, quad2, TolTang, bReverse, empt, slin)) {
0269         return;
0270       }
0271       bEmpty = empt;
0272       break;
0273     }
0274     //
0275     case 55: { // Torus/Torus
0276       if (!IntToTo(quad1, quad2, TolTang, SameSurf, empt, slin)) {
0277         return;
0278       }
0279       bEmpty = empt;
0280       break;
0281     }
0282     //
0283     default: {
0284       throw Standard_ConstructionError();
0285       break;
0286     }
0287   }
0288   //
0289   if (bEmpty) {
0290     if (myDone == IntStatus_Fail)
0291       myDone = IntStatus_OK;
0292 
0293     return;
0294   }
0295   //
0296 
0297   if(isPostProcessingRequired)
0298   {
0299     if (!SameSurf) {
0300       AFunc.SetQuadric(quad2);
0301       AFunc.Set(S1);
0302     
0303       solrst.Perform(AFunc, D1, TolArc, TolTang);
0304       if (!solrst.IsDone()) {
0305         return;
0306       }
0307 
0308       if (solrst.AllArcSolution() && typs1 == typs2) {
0309         all1 = Standard_True;
0310       }
0311       nbpt = solrst.NbPoints();
0312       nbseg= solrst.NbSegments();
0313       for (i = 1; i <= nbpt; i++)
0314       {
0315         const IntPatch_ThePathPointOfTheSOnBounds& aPt = solrst.Point(i);
0316         pnt1.Append(aPt);
0317       }
0318       for (i = 1; i <= nbseg; i++)
0319       {
0320         const IntPatch_TheSegmentOfTheSOnBounds& aSegm = solrst.Segment(i);
0321         edg1.Append(aSegm);
0322       }
0323       nosolonS1 = (nbpt == 0) && (nbseg == 0);
0324 
0325       if (nosolonS1 && all1) {  // cas de face sans restrictions
0326         all1 = Standard_False;
0327       }
0328     }//if (!SameSurf) {
0329     else {
0330       nosolonS1 = Standard_True;
0331     }
0332 
0333     if (!SameSurf) {
0334       AFunc.SetQuadric(quad1);
0335       AFunc.Set(S2);
0336 
0337       solrst.Perform(AFunc, D2, TolArc, TolTang);
0338       if (!solrst.IsDone()) {
0339         return;
0340       }
0341     
0342       if (solrst.AllArcSolution() && typs1 == typs2) {
0343         all2 = Standard_True;
0344       }
0345 
0346       nbpt = solrst.NbPoints();
0347       nbseg= solrst.NbSegments();
0348       for (i=1; i<= nbpt; i++) {
0349         const IntPatch_ThePathPointOfTheSOnBounds& aPt = solrst.Point(i);
0350         pnt2.Append(aPt);
0351       }
0352     
0353       for (i=1; i<= nbseg; i++) {
0354         const IntPatch_TheSegmentOfTheSOnBounds& aSegm = solrst.Segment(i);
0355         edg2.Append(aSegm);
0356       }
0357       
0358       nosolonS2 = (nbpt == 0) && (nbseg == 0);
0359 
0360       if (nosolonS2 && all2) {  // cas de face sans restrictions
0361         all2 = Standard_False;
0362       }
0363     }// if (!SameSurf) {
0364     else {
0365       nosolonS2 = Standard_True;
0366     }
0367     //
0368     if (SameSurf || (all1 && all2)) {
0369       // faces "paralleles" parfaites
0370       empt = Standard_False;
0371       tgte = Standard_True;
0372       slin.Clear();
0373       spnt.Clear();
0374 
0375       gp_Pnt Ptreference;
0376 
0377       switch (typs1) {
0378       case GeomAbs_Plane:      {
0379         Ptreference = (S1->Plane()).Location();
0380       }
0381         break;
0382       case GeomAbs_Cylinder: {
0383         Ptreference = ElSLib::Value(0.,0.,S1->Cylinder());
0384       }
0385         break;
0386       case GeomAbs_Sphere:      {
0387         Ptreference = ElSLib::Value(M_PI/4.,M_PI/4.,S1->Sphere());
0388       }
0389         break;
0390       case GeomAbs_Cone:      {
0391         Ptreference = ElSLib::Value(0.,10.,S1->Cone());
0392       }
0393         break;
0394       case GeomAbs_Torus:      {
0395         Ptreference = ElSLib::Value(0.,0.,S1->Torus());
0396       }
0397         break;
0398       default: 
0399         break;
0400       }
0401       //
0402       oppo = quad1.Normale(Ptreference).Dot(quad2.Normale(Ptreference)) < 0.0;
0403       myDone = IntStatus_OK;
0404       return;
0405     }// if (SameSurf || (all1 && all2)) {
0406 
0407     if (!nosolonS1 || !nosolonS2) {
0408       empt = Standard_False;
0409       // C est la qu il faut commencer a bosser...
0410       PutPointsOnLine(S1,S2,pnt1, slin, Standard_True, D1, quad1,quad2,
0411                       multpoint,TolArc);
0412     
0413       PutPointsOnLine(S1,S2,pnt2, slin, Standard_False,D2, quad2,quad1,
0414                       multpoint,TolArc);
0415 
0416       if (edg1.Length() != 0) {
0417         ProcessSegments(edg1,slin,quad1,quad2,Standard_True,TolArc);
0418       }
0419 
0420       if (edg2.Length() != 0) {
0421         ProcessSegments(edg2,slin,quad1,quad2,Standard_False,TolArc);
0422       }
0423 
0424       if (edg1.Length() !=0 || edg2.Length() !=0) {
0425         //      ProcessRLine(slin,S1,S2,TolArc);
0426         ProcessRLine(slin,quad1,quad2,TolArc, theIsReqToKeepRLine);
0427       }
0428     }//if (!nosolonS1 || !nosolonS2) {
0429     else {
0430       empt = ((slin.Length()==0) && (spnt.Length()==0));
0431     }
0432   }
0433   
0434   Standard_Integer  nblin = slin.Length(),
0435                     aNbPnt = spnt.Length();
0436   //
0437   //modified by NIZNHY-PKV Tue Sep 06 10:03:35 2011f
0438   if (aNbPnt) {
0439     IntPatch_SequenceOfPoint aSIP;
0440     //
0441     for(i=1; i<=aNbPnt; ++i) {
0442       Standard_Real aU1, aV1, aU2, aV2;
0443       gp_Pnt2d aP2D;
0444       TopAbs_State aState1, aState2;
0445       //
0446       const IntPatch_Point& aIP=spnt(i);
0447       aIP.Parameters(aU1, aV1, aU2, aV2);
0448       //
0449       aP2D.SetCoord(aU1, aV1);
0450       aState1=D1->Classify(aP2D, TolArc);
0451       //
0452       aP2D.SetCoord(aU2, aV2);
0453       aState2=D2->Classify(aP2D, TolArc);
0454       //
0455       if(aState1!=TopAbs_OUT && aState2!=TopAbs_OUT) {
0456         aSIP.Append(aIP);
0457       }
0458     }
0459     //
0460     spnt.Clear();
0461     //
0462     aNbPnt=aSIP.Length();
0463     for(i=1; i<=aNbPnt; ++i) {
0464       const IntPatch_Point& aIP=aSIP(i);
0465       spnt.Append(aIP);
0466     }
0467     //
0468   }//  if (aNbPnt) {
0469   //modified by NIZNHY-PKV Tue Sep 06 10:18:20 2011t
0470   //
0471   for(i=1; i<=nblin; i++) {
0472     IntPatch_IType thetype = slin.Value(i)->ArcType();
0473     if(  (thetype ==  IntPatch_Ellipse)
0474        ||(thetype ==  IntPatch_Circle)
0475        ||(thetype ==  IntPatch_Lin)
0476        ||(thetype ==  IntPatch_Parabola)
0477        ||(thetype ==  IntPatch_Hyperbola)) { 
0478       Handle(IntPatch_GLine)& glin = *((Handle(IntPatch_GLine)*)&slin.Value(i));
0479     glin->ComputeVertexParameters(TolArc); 
0480     }
0481     else if(thetype == IntPatch_Analytic) { 
0482       Handle(IntPatch_ALine)& aligold = *((Handle(IntPatch_ALine)*)&slin.Value(i));
0483       aligold->ComputeVertexParameters(TolArc);
0484     }
0485     else if(thetype == IntPatch_Restriction) {
0486       Handle(IntPatch_RLine)& rlig = *((Handle(IntPatch_RLine)*)&slin.Value(i));
0487       rlig->ComputeVertexParameters(TolArc); 
0488     }
0489   }
0490   //
0491   //----------------------------------------------------------------
0492   //-- On place 2 vertex sur les courbes de GLine qui n en 
0493   //-- contiennent pas. 
0494   for(i=1; i<=nblin; i++) {
0495     gp_Pnt P;
0496     IntPatch_Point point;
0497     Standard_Real u1,v1,u2,v2; 
0498     if(slin.Value(i)->ArcType() == IntPatch_Circle) { 
0499       const Handle(IntPatch_GLine)& glin = *((Handle(IntPatch_GLine)*)&slin.Value(i));
0500       if(glin->NbVertex() == 0) { 
0501         gp_Circ Circ = glin->Circle();
0502         P=ElCLib::Value(0.0,Circ);
0503         quad1.Parameters(P,u1,v1);
0504         quad2.Parameters(P,u2,v2);
0505         point.SetValue(P,TolArc,Standard_False);
0506         point.SetParameters(u1,v1,u2,v2);
0507         point.SetParameter(0.0);
0508         glin->AddVertex(point);
0509 
0510         P=ElCLib::Value(0.0,Circ);
0511         quad1.Parameters(P,u1,v1);
0512         quad2.Parameters(P,u2,v2);
0513         point.SetValue(P,TolArc,Standard_False);
0514         point.SetParameters(u1,v1,u2,v2);
0515         point.SetParameter(M_PI+M_PI);
0516         glin->AddVertex(point);
0517       }
0518     }
0519     
0520     else if(slin.Value(i)->ArcType() == IntPatch_Ellipse) { 
0521       const Handle(IntPatch_GLine)& glin = *((Handle(IntPatch_GLine)*)&slin.Value(i));
0522       if(glin->NbVertex() == 0) { 
0523         gp_Elips Elips = glin->Ellipse();
0524         P=ElCLib::Value(0.0,Elips);
0525         quad1.Parameters(P,u1,v1);
0526         quad2.Parameters(P,u2,v2);
0527         point.SetValue(P,TolArc,Standard_False);
0528         point.SetParameters(u1,v1,u2,v2);
0529         point.SetParameter(0.0);
0530         glin->AddVertex(point);
0531 
0532         P=ElCLib::Value(0.0,Elips);
0533         quad1.Parameters(P,u1,v1);
0534         quad2.Parameters(P,u2,v2);
0535         point.SetValue(P,TolArc,Standard_False);
0536         point.SetParameters(u1,v1,u2,v2);
0537         point.SetParameter(M_PI+M_PI);
0538         glin->AddVertex(point);
0539       }
0540     }
0541   }
0542   myDone = IntStatus_OK;
0543 }
0544 
0545 //=======================================================================
0546 //function : SetQuad
0547 //purpose  : 
0548 //=======================================================================
0549 Standard_Integer SetQuad(const Handle(Adaptor3d_Surface)& theS,
0550                          GeomAbs_SurfaceType& theTS,
0551                          IntSurf_Quadric& theQuad)
0552 {
0553   theTS = theS->GetType();
0554   Standard_Integer iRet = 0;
0555   switch (theTS) {
0556   case GeomAbs_Plane:
0557     theQuad.SetValue(theS->Plane());
0558     iRet = 1;
0559     break;
0560   case GeomAbs_Cylinder:
0561     theQuad.SetValue(theS->Cylinder());
0562     iRet = 2;
0563     break;
0564   case GeomAbs_Cone:
0565     theQuad.SetValue(theS->Cone());
0566     iRet = 3;
0567     break;
0568   case GeomAbs_Sphere:
0569     theQuad.SetValue(theS->Sphere());
0570     iRet = 4;
0571     break;
0572   case GeomAbs_Torus:
0573     theQuad.SetValue(theS->Torus());
0574     iRet = 5;
0575     break;
0576   default:
0577     break;
0578   }
0579   //
0580   return iRet;
0581 }
0582