// Copyright (C) 2005 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN, // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS // // This library is free software; you can redistribute it and/or // modify it under the terms of the GNU Lesser General Public // License as published by the Free Software Foundation; either // version 2.1 of the License. // // This library is distributed in the hope that it will be useful // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU // Lesser General Public License for more details. // // You should have received a copy of the GNU Lesser General Public // License along with this library; if not, write to the Free Software // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA // // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com // // File: GEOMAlgo_BuilderTools.cxx // Created: // Author: Peter KURNEV // #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include static Standard_Integer ComputeProps(const TopoDS_Face& aF, Standard_Real& aA, Standard_Real& aV); static void BuildTriangulation(const TopoDS_Face& aF); //======================================================================= //function : IsHole //purpose : //======================================================================= Standard_Boolean GEOMAlgo_BuilderTools::IsHole(const TopoDS_Shape& aW, const TopoDS_Shape& aFace) { Standard_Boolean bIsHole; Standard_Integer i, aNbS; Standard_Real aT1, aT2, aS; Standard_Real aU1, aU2, aU, dU; Standard_Real aX1, aY1, aX0, aY0; TopAbs_Orientation aOr; gp_Pnt2d aP2D0, aP2D1; Handle(Geom2d_Curve) aC2D; TopoDS_Face aF, aFF; TopoDS_Iterator aItW; // bIsHole=Standard_False; // aF=TopoDS::Face(aFace); aFF=aF; aFF.Orientation(TopAbs_FORWARD); // aS=0.; aItW.Initialize(aW); for (; aItW.More(); aItW.Next()) { const TopoDS_Edge& aE=TopoDS::Edge(aItW.Value()); aOr=aE.Orientation(); if (!(aOr==TopAbs_FORWARD || aOr==TopAbs_REVERSED)) { continue; } // aC2D=BRep_Tool::CurveOnSurface(aE, aFF, aT1, aT2); if (aC2D.IsNull()) { break; //xx } // BRepAdaptor_Curve2d aBAC2D(aE, aFF); aNbS=Geom2dInt_Geom2dCurveTool::NbSamples(aBAC2D); if (aNbS>2) { aNbS*=4; } // dU=(aT2-aT1)/(Standard_Real)(aNbS-1); aU =aT1; aU1=aT1; aU2=aT2; if (aOr==TopAbs_REVERSED) { aU =aT2; aU1=aT2; aU2=aT1; dU=-dU; } // aC2D->D0(aU, aP2D0); for(i=2; i<=aNbS; i++) { aU=aU1+(i-1)*dU; aC2D->D0(aU, aP2D1); aP2D0.Coord(aX0, aY0); aP2D1.Coord(aX1, aY1); // aS=aS+(aY0+aY1)*(aX1-aX0); // aP2D0=aP2D1; } }//for (; aItW.More(); aItW.Next()) { bIsHole=(aS>0.); return bIsHole; } //======================================================================= //function : IsHole //purpose : //======================================================================= Standard_Boolean GEOMAlgo_BuilderTools::IsHole(const TopoDS_Shape& aShell) { Standard_Boolean bIsHole; Standard_Integer iRet; Standard_Real aAi, aA, aV, aVi; TopExp_Explorer aExp; // aA=0.; aV=0.; aExp.Init(aShell, TopAbs_FACE); for (; aExp.More(); aExp.Next()) { const TopoDS_Face& aF=TopoDS::Face(aExp.Current()); iRet=ComputeProps(aF, aAi, aVi); if (!iRet) { aA+=aAi; aV+=aVi; } } // bIsHole=aV<0.; return bIsHole; } //======================================================================= //function : ComputeProps //purpose : //======================================================================= Standard_Integer ComputeProps(const TopoDS_Face& aF, Standard_Real& aA, Standard_Real& aV) { Standard_Integer j, i, i1, i2, aNbNodes, aNbTrigs, n[3]; Standard_Real aAi, aVi; gp_Pnt aP[3], aGC, aGC1; TopLoc_Location aLoc; TopAbs_Orientation aOr; Handle(Poly_Triangulation) aTri; // aA=0.; aV=0.; // aTri=BRep_Tool::Triangulation(aF, aLoc); if(aTri.IsNull()) { BuildTriangulation(aF); aTri=BRep_Tool::Triangulation(aF, aLoc); if(aTri.IsNull()) { return 1;// a face is without triangulation } } // aNbNodes=aTri->NbNodes(); aNbTrigs=aTri->NbTriangles(); if (!aNbTrigs){ return 2;//no triangles } // aOr=aF.Orientation(); // const TColgp_Array1OfPnt& aNodes=aTri->Nodes(); const Poly_Array1OfTriangle& aTriangles=aTri->Triangles(); // i1=aTriangles.Lower(); i2=aTriangles.Upper(); // for (i=i1; i<=i2; ++i){ const Poly_Triangle& aTriangle=aTriangles.Value(i); aTriangle.Get(n[0], n[1], n[2]); aGC.SetCoord(0.,0.,0.); for (j=0; j<3; ++j) { aP[j]=aNodes.Value(n[j]); aGC.ChangeCoord()+=aP[j].XYZ(); } aGC.ChangeCoord()*=0.333333333333; // // Normal gp_Vec aV01(aP[0], aP[1]); gp_Vec aV12(aP[1], aP[2]); gp_Vec aVN=aV01^aV12; aAi=aVN.Magnitude(); aA=aA+aAi; // if (aAi>0.0000001) { Standard_Real aSx, aZx; gp_Dir aDN(aVN); if (aOr==TopAbs_REVERSED) { aDN.Reverse(); } // aSx=aAi*aDN.Z(); aZx=aGC.Z(); aVi=aZx*aSx; aV=aV+aVi; } } return 0; } //======================================================================= //function : BuildTriangulation //purpose : //======================================================================= void BuildTriangulation(const TopoDS_Face& aF) { Standard_Boolean bWithShare; Standard_Real aDiscret, aXmin, aYmin, aZmin, aXmax, aYmax, aZmax; Standard_Real dX, dY, dZ, dMax, aCoeff, aAngle; Bnd_Box aBox; // bWithShare=Standard_False; aAngle=0.5; // BRepBndLib::Add(aF, aBox); // // aDiscret aBox.Get(aXmin, aYmin, aZmin, aXmax, aYmax, aZmax); dX=aXmax-aXmin; dY=aYmax-aYmin; dZ=aZmax-aZmin; dMax=dX; if (dY>dMax) { dMax=dY; } if (dZ>dMax) { dMax=dZ; } // aCoeff=0.1; aDiscret=aCoeff*dMax; // BRepMesh_FastDiscret aMesher(aDiscret, aAngle, aBox, bWithShare, Standard_True, Standard_False, Standard_True); aMesher.Add(aF); }