+++ /dev/null
-// Copyright (c) 1999-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_HeaderFile
-#define _BRepMesh_HeaderFile
-
-#include <gp_Pnt.hxx>
-#include <gp_XYZ.hxx>
-#include <gp_XY.hxx>
-#include <Bnd_B2d.hxx>
-#include <Bnd_Box2d.hxx>
-#include <Standard.hxx>
-#include <NCollection_List.hxx>
-#include <NCollection_Map.hxx>
-#include <NCollection_Vector.hxx>
-#include <NCollection_Handle.hxx>
-#include <NCollection_DataMap.hxx>
-#include <NCollection_IndexedMap.hxx>
-#include <NCollection_IndexedDataMap.hxx>
-#include <NCollection_Array1.hxx>
-#include <NCollection_Sequence.hxx>
-#include <NCollection_CellFilter.hxx>
-#include <NCollection_IncAllocator.hxx>
-#include <NCollection_EBTree.hxx>
-#include <NCollection_UBTreeFiller.hxx>
-#include <BRepMesh_Edge.hxx>
-#include <BRepMesh_Triangle.hxx>
-#include <BRepMesh_PairOfPolygon.hxx>
-#include <BRepMesh_PairOfIndex.hxx>
-#include <BRepMesh_Circle.hxx>
-#include <TopTools_ShapeMapHasher.hxx>
-#include <TopoDS_Face.hxx>
-#include <TopoDS_Shape.hxx>
-
-#include <vector>
-
-class BRepMesh_Vertex;
-class TopoDS_Edge;
-class TopoDS_Vertex;
-class BRepMesh_FaceAttribute;
-class BRepMesh_VertexInspector;
-class BRepMesh_CircleInspector;
-class BRepMesh_Classifier;
-class Poly_Triangulation;
-class BRepMesh_VertexTool;
-
-namespace BRepMesh
-{
- //! Default size for memory block allocated by IncAllocator.
- /**
- * The idea here is that blocks of the given size are returned to the system
- * rather than retained in the malloc heap, at least on WIN32 and WIN64 platforms.
- */
-#ifdef _WIN64
- const size_t MEMORY_BLOCK_SIZE_HUGE = 1024 * 1024;
-#else
- const size_t MEMORY_BLOCK_SIZE_HUGE = 512 * 1024;
-#endif
-
- //! Structure keeping parameters of segment.
- struct Segment
- {
- gp_XY StartPnt;
- gp_XY EndPnt;
- };
-
- //! Sequences
- typedef NCollection_Sequence<Bnd_B2d> SequenceOfBndB2d;
- typedef NCollection_Sequence<Standard_Integer> SequenceOfInteger;
- typedef NCollection_Sequence<Standard_Real> SequenceOfReal;
-
- //! Vectors
- typedef NCollection_Vector<BRepMesh_Vertex> VectorOfVertex;
- typedef NCollection_Vector<Standard_Integer> VectorOfInteger;
- typedef NCollection_Vector<BRepMesh_Circle> VectorOfCircle;
-
- //! Trees
- typedef NCollection_EBTree<Standard_Integer, Bnd_Box2d> BndBox2dTree;
- typedef NCollection_UBTreeFiller<Standard_Integer, Bnd_Box2d> BndBox2dTreeFiller;
-
- //! Arrays
- typedef NCollection_Array1<BRepMesh_Vertex> Array1OfVertexOfDelaun;
- typedef NCollection_Array1<Standard_Integer> Array1OfInteger;
- typedef NCollection_Array1<Standard_Real> Array1OfReal;
- typedef NCollection_Array1<Segment> Array1OfSegments;
-
- //! Lists
- typedef NCollection_List<gp_XY> ListOfXY;
- typedef NCollection_List<BRepMesh_Vertex> ListOfVertex;
- typedef NCollection_List<Standard_Integer> ListOfInteger;
-
- //! Maps
- typedef NCollection_Map<Standard_Real> MapOfReal;
- typedef NCollection_Map<Standard_Integer> MapOfInteger;
- typedef NCollection_DataMap<Handle(Poly_Triangulation), Standard_Boolean> DMapOfTriangulationBool;
- typedef NCollection_Map<TopoDS_Shape, TopTools_ShapeMapHasher> MapOfShape;
-
- typedef NCollection_DataMap<Standard_Integer, Standard_Integer> MapOfIntegerInteger;
- typedef NCollection_DataMap<TopoDS_Vertex, Standard_Integer, TopTools_ShapeMapHasher> DMapOfVertexInteger;
- typedef NCollection_DataMap<TopoDS_Face, Handle(BRepMesh_FaceAttribute), TopTools_ShapeMapHasher> DMapOfFaceAttribute;
- typedef NCollection_DataMap<TopoDS_Shape, BRepMesh_PairOfPolygon, TopTools_ShapeMapHasher> DMapOfShapePairOfPolygon;
- typedef NCollection_DataMap<Standard_Integer, gp_Pnt> DMapOfIntegerPnt;
- typedef NCollection_DataMap<Standard_Integer, ListOfXY> DMapOfIntegerListOfXY;
- typedef NCollection_DataMap<Standard_Integer, ListOfInteger> DMapOfIntegerListOfInteger;
- typedef NCollection_DataMap<TopoDS_Edge, DMapOfTriangulationBool, TopTools_ShapeMapHasher> DMapOfEdgeListOfTriangulationBool;
-
- typedef NCollection_IndexedMap<Standard_Integer> IMapOfInteger;
- typedef NCollection_IndexedMap<Standard_Real> IMapOfReal;
- typedef NCollection_IndexedMap<BRepMesh_Triangle> IMapOfElement;
- typedef NCollection_IndexedDataMap<BRepMesh_Edge, BRepMesh_PairOfIndex> IDMapOfLink;
-
- //! CellFilters
- typedef NCollection_CellFilter<BRepMesh_CircleInspector> CircleCellFilter;
- typedef NCollection_CellFilter<BRepMesh_VertexInspector> VertexCellFilter;
-
- //! Handles
- typedef NCollection_Handle<VectorOfVertex> HVectorOfVertex;
- typedef NCollection_Handle<MapOfInteger> HMapOfInteger;
- typedef NCollection_Handle<IMapOfInteger> HIMapOfInteger;
- typedef NCollection_Handle<DMapOfShapePairOfPolygon> HDMapOfShapePairOfPolygon;
- typedef NCollection_Handle<DMapOfIntegerPnt> HDMapOfIntegerPnt;
- typedef NCollection_Handle<BRepMesh_Classifier> HClassifier;
- typedef NCollection_Handle<BndBox2dTree> HBndBox2dTree;
- typedef NCollection_Handle<Array1OfSegments> HArray1OfSegments;
- typedef NCollection_Handle<DMapOfVertexInteger> HDMapOfVertexInteger;
- typedef NCollection_Handle<DMapOfIntegerListOfXY> HDMapOfIntegerListOfXY;
- typedef NCollection_Handle<BRepMesh_VertexTool> HVertexTool;
- typedef NCollection_Handle<SequenceOfBndB2d> HSequenceOfBndB2d;
- typedef NCollection_Handle<SequenceOfInteger> HSequenceOfInteger;
-
- //! Other data structures
- typedef std::pair<HArray1OfSegments, HBndBox2dTree> SegmentsTree;
- typedef NCollection_Array1<SegmentsTree> Array1OfSegmentsTree;
-
-} // namespace BRepMesh
-
-#endif
+++ /dev/null
-// Created on: 2014-08-13
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_EdgeParameterProvider.hxx>
-#include <gp_Pnt.hxx>
-#include <TopoDS_Edge.hxx>
-#include <TopoDS_Face.hxx>
-#include <TColStd_HArray1OfReal.hxx>
-#include <BRep_Tool.hxx>
-#include <BRepAdaptor_Curve.hxx>
-#include <Precision.hxx>
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_EdgeParameterProvider::BRepMesh_EdgeParameterProvider(
- const TopoDS_Edge& theEdge,
- const TopoDS_Face& theFace,
- const Handle(TColStd_HArray1OfReal)& theParameters)
- : myParameters(theParameters),
- myIsSameParam(BRep_Tool::SameParameter(theEdge)),
- myScale(1.),
- myCurveAdaptor(theEdge, theFace)
-{
- if (myIsSameParam)
- return;
-
- // Extract actual parametric values
- Standard_Real aLastParam;
- BRep_Tool::Range(theEdge, theFace, myFirstParam, aLastParam);
-
- myFoundParam = myCurParam = myFirstParam;
-
- // Extract parameters stored in polygon
- myOldFirstParam =
- myParameters->Value(myParameters->Lower());
-
- const Standard_Real aOldLastParam =
- myParameters->Value(myParameters->Upper());
-
- // Calculate scale factor between actual and stored parameters
- if ((myOldFirstParam != myFirstParam || aOldLastParam != aLastParam) &&
- myOldFirstParam != aOldLastParam)
- {
- myScale = (aLastParam - myFirstParam) /
- (aOldLastParam - myOldFirstParam);
- }
-
- myProjector.Initialize(myCurveAdaptor, myCurveAdaptor.FirstParameter(),
- myCurveAdaptor.LastParameter(), Precision::PConfusion());
-}
-
-//=======================================================================
-//function : Parameter
-//purpose :
-//=======================================================================
-Standard_Real BRepMesh_EdgeParameterProvider::Parameter(
- const Standard_Integer theIndex,
- const gp_Pnt& thePoint3d)
-{
- if (myIsSameParam)
- return myParameters->Value(theIndex);
-
- // Use scaled
- Standard_Real aPrevParam = myCurParam;
- myCurParam = myFirstParam + myScale *
- (myParameters->Value(theIndex) - myOldFirstParam);
-
- myFoundParam += (myCurParam - aPrevParam);
-
- myProjector.Perform(thePoint3d, myFoundParam);
- if (myProjector.IsDone())
- myFoundParam = myProjector.Point().Parameter();
-
- return myFoundParam;
-}
+++ /dev/null
-// Created on: 2014-08-13
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_EdgeTessellator.hxx>
-#include <Geom_Surface.hxx>
-#include <Geom_Plane.hxx>
-#include <Geom2d_Curve.hxx>
-#include <Geom2dAdaptor_Curve.hxx>
-#include <TopoDS_Edge.hxx>
-#include <TopoDS_Face.hxx>
-#include <BRepAdaptor_HSurface.hxx>
-#include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
-#include <TopLoc_Location.hxx>
-#include <BRep_Tool.hxx>
-#include <TColStd_Array1OfReal.hxx>
-#include <TopExp_Explorer.hxx>
-#include <TopoDS_Vertex.hxx>
-#include <TopoDS.hxx>
-#include <TopTools_ListIteratorOfListOfShape.hxx>
-#include <TopTools_ListOfShape.hxx>
-#include <TColStd_Array1OfReal.hxx>
-
-
-IMPLEMENT_STANDARD_RTTIEXT(BRepMesh_EdgeTessellator,BRepMesh_IEdgeTool)
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_EdgeTessellator::BRepMesh_EdgeTessellator(
- const TopoDS_Edge& theEdge,
- const Handle(BRepMesh_FaceAttribute)& theFaceAttribute,
- const TopTools_IndexedDataMapOfShapeListOfShape& theMapOfSharedFaces,
- const Standard_Real theLinDeflection,
- const Standard_Real theAngDeflection,
- const Standard_Real theMinSize)
- : mySurface(theFaceAttribute->Surface())
-{
- Standard_Real aPreciseAngDef = 0.5 * theAngDeflection;
- Standard_Real aPreciseLinDef = 0.5 * theLinDeflection;
- if (theEdge.Orientation() == TopAbs_INTERNAL)
- aPreciseLinDef *= 0.5;
-
- mySquareEdgeDef = aPreciseLinDef * aPreciseLinDef;
- mySquareMinSize = Max(mySquareEdgeDef, theMinSize * theMinSize);
- myEdgeSqTol = BRep_Tool::Tolerance (theEdge);
- myEdgeSqTol *= myEdgeSqTol;
-
- Standard_Boolean isSameParam = BRep_Tool::SameParameter(theEdge);
- if (isSameParam)
- myCOnS.Initialize(theEdge);
- else
- myCOnS.Initialize(theEdge, theFaceAttribute->Face());
-
- const GeomAbs_CurveType aCurveType = myCOnS.GetType();
- Standard_Integer aMinPntNb = (aCurveType == GeomAbs_Circle) ? 4 : 2; //OCC287
-
- // Get 2d curve and init geom tool
- Standard_Real aFirstParam, aLastParam;
- Handle(Geom2d_Curve) aCurve2d =
- BRep_Tool::CurveOnSurface(theEdge, theFaceAttribute->Face(), aFirstParam, aLastParam);
- myCurve2d.Load(aCurve2d, aFirstParam, aLastParam);
- myTool = new BRepMesh_GeomTool(myCOnS, aFirstParam, aLastParam,
- aPreciseLinDef, aPreciseAngDef, aMinPntNb, theMinSize);
-
- if (aCurveType == GeomAbs_BSplineCurve)
- {
- // bug24220
- const Standard_Integer aNbInt = myCOnS.NbIntervals(GeomAbs_C1);
- if ( aNbInt > 1 )
- {
- TColStd_Array1OfReal anIntervals( 1, aNbInt + 1 );
- myCOnS.Intervals(anIntervals, GeomAbs_C1);
- for (Standard_Integer aIntIt = 1; aIntIt <= aNbInt; ++aIntIt)
- {
- const Standard_Real& aStartInt = anIntervals.Value( aIntIt );
- const Standard_Real& anEndInt = anIntervals.Value( aIntIt + 1 );
-
- BRepMesh_GeomTool aDetalizator(myCOnS, aStartInt, anEndInt,
- aPreciseLinDef, aPreciseAngDef, aMinPntNb, theMinSize);
-
- Standard_Integer aNbAddNodes = aDetalizator.NbPoints();
- for ( Standard_Integer aNodeIt = 1; aNodeIt <= aNbAddNodes; ++aNodeIt )
- {
- Standard_Real aParam;
- gp_Pnt aPoint3d;
- gp_Pnt2d aPoint2d;
- aDetalizator.Value( aNodeIt, aParam, aPoint3d);
- myCurve2d.D0(aParam, aPoint2d);
-
- myTool->AddPoint( aPoint3d, aParam, Standard_False );
- }
- }
- }
- }
-
- // PTv, chl/922/G9, Take into account internal vertices
- // it is necessary for internal edges, which do not split other edges, by their vertex
- TopExp_Explorer aVertexIt(theEdge, TopAbs_VERTEX);
- for (; aVertexIt.More(); aVertexIt.Next())
- {
- const TopoDS_Vertex& aVertex = TopoDS::Vertex(aVertexIt.Current());
- if (aVertex.Orientation() != TopAbs_INTERNAL)
- continue;
-
- myTool->AddPoint(BRep_Tool::Pnt(aVertex),
- BRep_Tool::Parameter(aVertex, theEdge), Standard_True);
- }
-
- Standard_Integer aNodesNb = myTool->NbPoints();
- //Check deflection in 2d space for improvement of edge tesselation.
- if( isSameParam && aNodesNb > 1)
- {
- const TopTools_ListOfShape& aSharedFaces = theMapOfSharedFaces.FindFromKey(theEdge);
- TopTools_ListIteratorOfListOfShape aFaceIt(aSharedFaces);
- for (; aFaceIt.More(); aFaceIt.Next())
- {
- const TopoDS_Face& aFace = TopoDS::Face(aFaceIt.Value());
- BRepAdaptor_Surface aSurf(aFace, Standard_False);
-
- if (aSurf.GetType() == GeomAbs_Plane)
- continue;
-
- Standard_Real aF, aL;
- aCurve2d = BRep_Tool::CurveOnSurface(theEdge, aFace, aF, aL);
- if ( Abs(aF - aFirstParam) > Precision::PConfusion() ||
- Abs(aL - aLastParam ) > Precision::PConfusion() )
- {
- continue;
- }
- Geom2dAdaptor_Curve aGACurve(aCurve2d, aF, aL);
-
- aNodesNb = myTool->NbPoints();
- TColStd_Array1OfReal aParamArray(1, aNodesNb);
- for (Standard_Integer i = 1; i <= aNodesNb; ++i)
- {
- gp_Pnt aTmpPnt;
- Standard_Real aParam;
- myTool->Value(i, aParam, aTmpPnt);
- aParamArray.SetValue(i, aParam);
- }
-
- for (Standard_Integer i = 1; i < aNodesNb; ++i)
- splitSegment(aSurf, aGACurve, aParamArray(i), aParamArray(i + 1), 1);
- }
- }
-
- const Standard_Real aTol = Precision::Confusion();
- const Standard_Real aDu = mySurface->UResolution (aTol);
- const Standard_Real aDv = mySurface->VResolution (aTol);
-
- myFaceRangeU[0] = mySurface->FirstUParameter() - aDu;
- myFaceRangeU[1] = mySurface->LastUParameter() + aDu;
-
- myFaceRangeV[0] = mySurface->FirstVParameter() - aDv;
- myFaceRangeV[1] = mySurface->LastVParameter() + aDv;
-}
-
-//=======================================================================
-//function : Value
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_EdgeTessellator::Value(
- const Standard_Integer theIndex,
- Standard_Real& theParameter,
- gp_Pnt& thePoint,
- gp_Pnt2d& theUV)
-{
- myTool->Value(theIndex, theParameter, thePoint);
- myCurve2d.D0(theParameter, theUV);
-
- // If point coordinates are out of surface range,
- // it is necessary to re-project point.
- if (mySurface->GetType() != GeomAbs_BSplineSurface &&
- mySurface->GetType() != GeomAbs_BezierSurface &&
- mySurface->GetType() != GeomAbs_OtherSurface)
- {
- return Standard_True;
- }
-
- // Let skip periodic case.
- if (mySurface->IsUPeriodic() || mySurface->IsVPeriodic())
- return Standard_True;
-
- // Point lies within the surface range - nothing to do.
- if (theUV.X() > myFaceRangeU[0] && theUV.X() < myFaceRangeU[1] &&
- theUV.Y() > myFaceRangeV[0] && theUV.Y() < myFaceRangeV[1])
- {
- return Standard_True;
- }
-
- gp_Pnt aPntOnSurf;
- mySurface->D0 (theUV.X (), theUV.Y (), aPntOnSurf);
-
- return (thePoint.SquareDistance (aPntOnSurf) < myEdgeSqTol);
-}
-
-//=======================================================================
-//function : splitSegment
-//purpose :
-//=======================================================================
-void BRepMesh_EdgeTessellator::splitSegment(
- const Adaptor3d_Surface& theSurf,
- const Geom2dAdaptor_Curve& theCurve2d,
- const Standard_Real theFirst,
- const Standard_Real theLast,
- const Standard_Integer theNbIter)
-{
- // limit iteration depth
- if(theNbIter > 10)
- return;
-
- gp_Pnt2d uvf, uvl, uvm;
- gp_Pnt P3dF, P3dL, midP3d, midP3dFromSurf;
- Standard_Real midpar;
-
- if(Abs(theLast - theFirst) < 2 * Precision::PConfusion())
- return;
-
- theCurve2d.D0(theFirst, uvf);
- theCurve2d.D0(theLast, uvl);
-
- P3dF = theSurf.Value(uvf.X(), uvf.Y());
- P3dL = theSurf.Value(uvl.X(), uvl.Y());
-
- if(P3dF.SquareDistance(P3dL) < mySquareMinSize)
- return;
-
- uvm = gp_Pnt2d((uvf.XY() + uvl.XY())*0.5);
- midP3dFromSurf = theSurf.Value(uvm.X(), uvm.Y());
-
- gp_XYZ Vec1 = midP3dFromSurf.XYZ() - P3dF.XYZ();
- if(Vec1.SquareModulus() < mySquareMinSize)
- return;
-
- gp_XYZ aVec = P3dL.XYZ() - P3dF.XYZ();
- aVec.Normalize();
-
- Standard_Real aModulus = Vec1.Dot(aVec);
- gp_XYZ aProj = aVec * aModulus;
- gp_XYZ aDist = Vec1 - aProj;
-
- if(aDist.SquareModulus() < mySquareEdgeDef)
- return;
-
- midpar = (theFirst + theLast) * 0.5;
- myCOnS.D0(midpar, midP3d);
- myTool->AddPoint(midP3d, midpar, Standard_False);
-
- splitSegment(theSurf, theCurve2d, theFirst, midpar, theNbIter + 1);
- splitSegment(theSurf, theCurve2d, midpar, theLast, theNbIter + 1);
-}
+++ /dev/null
-// Created on: 2014-08-13
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_EdgeTessellator_HeaderFile
-#define _BRepMesh_EdgeTessellator_HeaderFile
-
-#include <Standard.hxx>
-#include <Standard_DefineAlloc.hxx>
-#include <BRepMesh.hxx>
-#include <BRepMesh_IEdgeTool.hxx>
-#include <BRepMesh_GeomTool.hxx>
-#include <BRepMesh_FaceAttribute.hxx>
-#include <BRepAdaptor_Curve.hxx>
-#include <Geom2dAdaptor_Curve.hxx>
-#include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
-
-class Adaptor3d_Surface;
-class TopoDS_Edge;
-class BRepAdaptor_HSurface;
-
-//! Auxiliary class implements functionality producing tessellated
-//! representation of an edge based on edge geometry.
-class BRepMesh_EdgeTessellator : public BRepMesh_IEdgeTool
-{
-public:
-
- //! Constructor.
- //! Automatically performs tessellation of the edge according to the
- //! given parameters.
- BRepMesh_EdgeTessellator(
- const TopoDS_Edge& theEdge,
- const Handle(BRepMesh_FaceAttribute)& theFaceAttribute,
- const TopTools_IndexedDataMapOfShapeListOfShape& theMapOfSharedFaces,
- const Standard_Real theLinDeflection,
- const Standard_Real theAngDeflection,
- const Standard_Real theMinSize);
-
- //! Returns number of dicretization points.
- virtual Standard_Integer NbPoints() const Standard_OVERRIDE
- {
- return myTool->NbPoints();
- }
-
- //! Returns parameters of solution with the given index.
- //! @param theIndex index of tessellation point.
- //! @param theParameter parameters on PCurve corresponded to the solution.
- //! @param thePoint tessellation point.
- //! @param theUV coordinates of tessellation point in parametric space of face.
- //! @return True in case of valid result, false elewhere.
- virtual Standard_Boolean Value(
- const Standard_Integer theIndex,
- Standard_Real& theParameter,
- gp_Pnt& thePoint,
- gp_Pnt2d& theUV) Standard_OVERRIDE;
-
- DEFINE_STANDARD_RTTIEXT(BRepMesh_EdgeTessellator,BRepMesh_IEdgeTool)
-
-private:
-
- //!
- void splitSegment(const Adaptor3d_Surface& theSurf,
- const Geom2dAdaptor_Curve& theCurve2d,
- const Standard_Real theFirst,
- const Standard_Real theLast,
- const Standard_Integer theNbIter);
-
-private:
- NCollection_Handle<BRepMesh_GeomTool> myTool;
- Handle(BRepAdaptor_HSurface) mySurface;
- BRepAdaptor_Curve myCOnS;
- Geom2dAdaptor_Curve myCurve2d;
- Standard_Real mySquareEdgeDef;
- Standard_Real mySquareMinSize;
- Standard_Real myEdgeSqTol;
- Standard_Real myFaceRangeU[2];
- Standard_Real myFaceRangeV[2];
-};
-
-DEFINE_STANDARD_HANDLE(BRepMesh_EdgeTessellator, BRepMesh_IEdgeTool)
-
-#endif
+++ /dev/null
-// Created by: Ekaterina SMIRNOVA
-// Copyright (c) 2008-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_FaceAttribute.hxx>
-#include <TopoDS_Vertex.hxx>
-#include <BRepAdaptor_HSurface.hxx>
-#include <BRepMesh_ShapeTool.hxx>
-#include <BRepMesh_Classifier.hxx>
-#include <BRepTools.hxx>
-#include <TopExp_Explorer.hxx>
-#include <TopoDS_Wire.hxx>
-#include <TopoDS_Edge.hxx>
-#include <TopoDS.hxx>
-#include <TopoDS_Iterator.hxx>
-#include <BRep_Tool.hxx>
-
-IMPLEMENT_STANDARD_RTTIEXT(BRepMesh_FaceAttribute,Standard_Transient)
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_FaceAttribute::BRepMesh_FaceAttribute()
- : myDefFace (0.),
- myUMin (0.),
- myUMax (0.),
- myVMin (0.),
- myVMax (0.),
- myDeltaX (1.),
- myDeltaY (1.),
- myMinStep (-1.),
- myStatus (BRepMesh_NoError),
- myAdaptiveMin (Standard_False)
-{
- init();
-}
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_FaceAttribute::BRepMesh_FaceAttribute(
- const BRepMesh::HDMapOfVertexInteger& theBoundaryVertices,
- const BRepMesh::HDMapOfIntegerPnt& theBoundaryPoints)
- : myDefFace (0.),
- myUMin (0.),
- myUMax (0.),
- myVMin (0.),
- myVMax (0.),
- myDeltaX (1.),
- myDeltaY (1.),
- myMinStep (-1.),
- myStatus (BRepMesh_NoError),
- myAdaptiveMin (Standard_False),
- myBoundaryVertices(theBoundaryVertices),
- myBoundaryPoints (theBoundaryPoints)
-{
-}
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_FaceAttribute::BRepMesh_FaceAttribute(
- const TopoDS_Face& theFace,
- const BRepMesh::HDMapOfVertexInteger& theBoundaryVertices,
- const BRepMesh::HDMapOfIntegerPnt& theBoundaryPoints,
- const Standard_Boolean theAdaptiveMin)
- : myDefFace (0.),
- myUMin (0.),
- myUMax (0.),
- myVMin (0.),
- myVMax (0.),
- myDeltaX (1.),
- myDeltaY (1.),
- myMinStep (-1.),
- myStatus (BRepMesh_NoError),
- myAdaptiveMin (theAdaptiveMin),
- myBoundaryVertices(theBoundaryVertices),
- myBoundaryPoints (theBoundaryPoints),
- myFace (theFace)
-{
- init();
-}
-
-//=======================================================================
-//function : Destructor
-//purpose :
-//=======================================================================
-BRepMesh_FaceAttribute::~BRepMesh_FaceAttribute()
-{
-}
-
-//=======================================================================
-//function : SetFace
-//purpose :
-//=======================================================================
-void BRepMesh_FaceAttribute::SetFace (
- const TopoDS_Face& theFace,
- const Standard_Boolean theAdaptiveMin)
-{
- myFace = theFace;
- myAdaptiveMin = theAdaptiveMin;
-
- init ();
-}
-
-//=======================================================================
-//function : init
-//purpose :
-//=======================================================================
-void BRepMesh_FaceAttribute::init()
-{
- myVertexEdgeMap = new BRepMesh::IMapOfInteger;
- myInternalEdges = new BRepMesh::DMapOfShapePairOfPolygon;
- myLocation2D = new BRepMesh::DMapOfIntegerListOfXY;
- myClassifier = new BRepMesh_Classifier;
-
- if (myFace.IsNull())
- return;
-
- BRepTools::Update(myFace);
- myFace.Orientation(TopAbs_FORWARD);
- BRepTools::UVBounds(myFace, myUMin, myUMax, myVMin, myVMax);
-
- if (myAdaptiveMin)
- {
- // compute minimal UV distance
- // between vertices
-
- myMinStep = RealLast();
- for (TopoDS_Iterator aFaceIt(myFace); aFaceIt.More(); aFaceIt.Next())
- {
- for (TopoDS_Iterator aWireIt(aFaceIt.Value()); aWireIt.More(); aWireIt.Next())
- {
- const TopoDS_Edge& anEdge = TopoDS::Edge(aWireIt.Value());
- if (anEdge.IsNull() || BRep_Tool::IsClosed(anEdge))
- continue;
-
- // Get end points on 2d curve
- gp_Pnt2d aFirst2d, aLast2d;
- BRep_Tool::UVPoints(anEdge, myFace, aFirst2d, aLast2d);
- Standard_Real aDist =aFirst2d.Distance(aLast2d);
- if (aDist < myMinStep)
- myMinStep = aDist;
- }
- }
- }
-
- BRepAdaptor_Surface aSurfAdaptor(myFace, Standard_False);
- mySurface = new BRepAdaptor_HSurface(aSurfAdaptor);
-}
-
-//=======================================================================
-//function : Clear
-//purpose :
-//=======================================================================
-void BRepMesh_FaceAttribute::Clear()
-{
- myStructure.Nullify();
- myLocation2D->Clear();
- myInternalEdges->Clear();
- myVertexEdgeMap->Clear();
-}
-
-//=======================================================================
-//function : computeParametricTolerance
-//purpose :
-//=======================================================================
-Standard_Real BRepMesh_FaceAttribute::computeParametricTolerance(
- const Standard_Real theFirstParam,
- const Standard_Real theLastParam) const
-{
- const Standard_Real aDeflectionUV = 1.e-05;
- Standard_Real aPreci = (theLastParam - theFirstParam) * aDeflectionUV;
- if(myAdaptiveMin && myMinStep < aPreci)
- aPreci = myMinStep;
-
- return Max(Precision::PConfusion(), aPreci);
-}
-
-//=======================================================================
-//function : getVertexIndex
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_FaceAttribute::getVertexIndex(
- const TopoDS_Vertex& theVertex,
- Standard_Integer& theVertexIndex) const
-{
- if (!myBoundaryVertices.IsNull() && myBoundaryVertices->IsBound(theVertex))
- theVertexIndex = myBoundaryVertices->Find(theVertex);
- else if (!mySurfaceVertices.IsNull() && mySurfaceVertices->IsBound(theVertex))
- theVertexIndex = mySurfaceVertices->Find(theVertex);
- else
- return Standard_False;
-
- return Standard_True;
-}
-
-//=======================================================================
-//function : AddNode
-//purpose :
-//=======================================================================
-void BRepMesh_FaceAttribute::AddNode(
- const Standard_Integer theIndex,
- const gp_XY& theUV,
- const BRepMesh_DegreeOfFreedom theMovability,
- Standard_Integer& theNodeIndex,
- Standard_Integer& theNodeOnEdgeIndex)
-{
- BRepMesh_Vertex aNode(theUV, theIndex, theMovability);
- theNodeIndex = myStructure->AddNode(aNode);
- theNodeOnEdgeIndex = myVertexEdgeMap->FindIndex(theNodeIndex);
- if (theNodeOnEdgeIndex == 0)
- theNodeOnEdgeIndex = myVertexEdgeMap->Add(theNodeIndex);
-}
-
-//=======================================================================
-//function : Scale
-//purpose :
-//=======================================================================
-gp_XY BRepMesh_FaceAttribute::Scale(const gp_XY& thePoint2d,
- const Standard_Boolean isToFaceBasis)
-{
- return isToFaceBasis ?
- gp_XY((thePoint2d.X() - myUMin) / myDeltaX, (thePoint2d.Y() - myVMin) / myDeltaY) :
- gp_XY(thePoint2d.X() * myDeltaX + myUMin, thePoint2d.Y() * myDeltaY + myVMin);
-}
-
-//=======================================================================
-//function : ToleranceU
-//purpose :
-//=======================================================================
-Standard_Real BRepMesh_FaceAttribute::ToleranceU() const
-{
- return computeParametricTolerance(myUMin, myUMax);
-}
-
-//=======================================================================
-//function : ToleranceV
-//purpose :
-//=======================================================================
-Standard_Real BRepMesh_FaceAttribute::ToleranceV() const
-{
- return computeParametricTolerance(myVMin, myVMax);
-}
+++ /dev/null
-// Copyright (c) 2013 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_FaceAttribute_HeaderFile
-#define _BRepMesh_FaceAttribute_HeaderFile
-
-#include <Standard.hxx>
-#include <Standard_Transient.hxx>
-#include <Standard_Type.hxx>
-
-#include <BRepMesh_Status.hxx>
-#include <BRepMesh.hxx>
-#include <BRepMesh_DataStructureOfDelaun.hxx>
-
-class BRepAdaptor_HSurface;
-
-//! Auxiliary class for FastDiscret and FastDiscretFace classes.
-class BRepMesh_FaceAttribute : public Standard_Transient
-{
-public:
-
- //! Constructor. Initializes empty attribute.
- //! @param theBoundaryVertices shared map of shape vertices.
- //! @param theBoundaryPoints shared discretization points of shape boundaries.
- Standard_EXPORT BRepMesh_FaceAttribute(
- const BRepMesh::HDMapOfVertexInteger& theBoundaryVertices,
- const BRepMesh::HDMapOfIntegerPnt& theBoundaryPoints);
-
- //! Constructor.
- //! @param theFace face the attribute is created for.
- //! Used for default initialization. Attribute keeps reference
- //! to the source face with forward orientation.
- //! @param theBoundaryVertices shared map of shape vertices.
- //! @param theBoundaryPoints shared discretization points of shape boundaries.
- //! @param theAdaptiveMin switches on adaptive computation of minimal parametric
- //! tolerance (if true).
- Standard_EXPORT BRepMesh_FaceAttribute(
- const TopoDS_Face& theFace,
- const BRepMesh::HDMapOfVertexInteger& theBoundaryVertices,
- const BRepMesh::HDMapOfIntegerPnt& theBoundaryPoints,
- const Standard_Boolean theAdaptiveMin);
-
- //! Destructor.
- Standard_EXPORT virtual ~BRepMesh_FaceAttribute();
-
-public: //! @name main geometrical properties.
-
- //! Returns face's surface.
- inline const Handle(BRepAdaptor_HSurface)& Surface() const
- {
- return mySurface;
- }
-
- //! Returns True in case if this attribute has already been intialized.
- inline Standard_Boolean IsInitialized () const
- {
- return !myFace.IsNull ();
- }
-
- //! Initializes this attribute by the given face.
- Standard_EXPORT void SetFace (
- const TopoDS_Face& theFace,
- const Standard_Boolean theAdaptiveMin);
-
- //! Returns forward oriented face to be used for calculations.
- inline const TopoDS_Face& Face() const
- {
- return myFace;
- }
-
- //! Sets boundary vertices map.
- inline void SetBoundaryVertices(const BRepMesh::HDMapOfVertexInteger& theVertices)
- {
- myBoundaryVertices = theVertices;
- }
-
- //! Sets boundary points map.
- inline void SetBoundaryPoints(const BRepMesh::HDMapOfIntegerPnt& theBoundaryPoints)
- {
- myBoundaryPoints = theBoundaryPoints;
- }
-
- //! Returns U tolerance of face calculated regarding its parameters.
- Standard_EXPORT Standard_Real ToleranceU() const;
-
- //! Returns V tolerance of face calculated regarding its parameters.
- Standard_EXPORT Standard_Real ToleranceV() const;
-
- //! Gives face deflection parameter.
- inline Standard_Real GetDefFace() const
- {
- return myDefFace;
- }
-
- //! Sets face deflection.
- inline void SetDefFace(const Standard_Real theDefFace)
- {
- myDefFace = theDefFace;
- }
-
- //! Gives minimal value in U domain.
- inline Standard_Real GetUMin() const
- {
- return myUMin;
- }
-
- //! Sets minimal value in U domain.
- inline void SetUMin(const Standard_Real theUMin)
- {
- myUMin = theUMin;
- }
-
- //! Gives minimal value in V domain.
- inline Standard_Real GetVMin() const
- {
- return myVMin;
- }
-
- //! Sets minimal value in V domain.
- inline void SetVMin(const Standard_Real theVMin)
- {
- myVMin = theVMin;
- }
-
- //! Gives maximal value in U domain.
- inline Standard_Real GetUMax() const
- {
- return myUMax;
- }
-
- //! Sets maximal value in U domain.
- inline void SetUMax(const Standard_Real theUMax)
- {
- myUMax = theUMax;
- }
-
- //! Gives maximal value in V domain.
- inline Standard_Real GetVMax() const
- {
- return myVMax;
- }
-
- //! Sets maximal value in V domain.
- inline void SetVMax(const Standard_Real theVMax)
- {
- myVMax = theVMax;
- }
-
- //! Gives value of step in U domain.
- inline Standard_Real GetDeltaX() const
- {
- return myDeltaX;
- }
-
- //! Sets value of step in U domain.
- inline void SetDeltaX(const Standard_Real theDeltaX)
- {
- myDeltaX = theDeltaX;
- }
-
- //! Gives value of step in V domain.
- inline Standard_Real GetDeltaY() const
- {
- return myDeltaY;
- }
-
- //! Sets value of step in V domain.
- inline void SetDeltaY(const Standard_Real theDeltaY)
- {
- myDeltaY = theDeltaY;
- }
-
- //! Sets set of status flags for this face.
- inline Standard_Integer GetStatus() const
- {
- return myStatus;
- }
-
- //! Sets status flag for this face.
- inline void SetStatus(const BRepMesh_Status theStatus)
- {
- myStatus |= theStatus;
- }
-
- //! Returns TRUE in case if computed data is valid.
- inline Standard_Boolean IsValid() const
- {
- return (myStatus == BRepMesh_NoError || myStatus == BRepMesh_ReMesh);
- }
-
-public: //! @name auxiliary structures
-
- //! Clear face attribute.
- Standard_EXPORT void Clear();
-
- //! Gives reference to map of internal edges of face.
- inline BRepMesh::HDMapOfShapePairOfPolygon& ChangeInternalEdges()
- {
- return myInternalEdges;
- }
-
- //! Gives reference to map of 2D points of discretization.
- inline BRepMesh::HDMapOfIntegerListOfXY& ChangeLocation2D()
- {
- return myLocation2D;
- }
-
- //! Gives reference to map of 3D points of discretization.
- inline BRepMesh::HDMapOfIntegerPnt& ChangeSurfacePoints()
- {
- return mySurfacePoints;
- }
-
- //! Gives reference to map of vertices of discretization.
- inline BRepMesh::HDMapOfVertexInteger& ChangeSurfaceVertices()
- {
- return mySurfaceVertices;
- }
-
- //! Gives reference on map of (vertex, edge) pairs of face.
- inline BRepMesh::HIMapOfInteger& ChangeVertexEdgeMap()
- {
- return myVertexEdgeMap;
- }
-
- //! Gives Delaunay data structure.
- inline Handle(BRepMesh_DataStructureOfDelaun)& ChangeStructure()
- {
- return myStructure;
- }
-
- //! Returns classifier.
- inline BRepMesh::HClassifier& ChangeClassifier()
- {
- return myClassifier;
- }
-
- //! Returns mesh nodes calculated for boundaries.
- inline BRepMesh::HVectorOfVertex& ChangeMeshNodes()
- {
- return myMeshNodes;
- }
-
-public: //! @name Point/Vertex/Node manipulators
-
- //! Gives the number of different locations in 3D space.
- inline Standard_Integer LastPointId() const
- {
- return (myBoundaryPoints.IsNull() ? 0 : myBoundaryPoints->Extent()) +
- (mySurfacePoints.IsNull() ? 0 : mySurfacePoints->Extent());
- }
-
- //! Gives the 3D location of the vertex.
- inline const gp_Pnt& GetPoint(const BRepMesh_Vertex& theVertex) const
- {
- return GetPoint(theVertex.Location3d());
- }
-
- //! Gives the 3D location of the vertex.
- inline const gp_Pnt& GetPoint(const Standard_Integer theIndex) const
- {
- if (!mySurfacePoints.IsNull() && theIndex > myBoundaryPoints->Extent())
- return mySurfacePoints->Find(theIndex);
-
- return myBoundaryPoints->Find(theIndex);
- }
-
- //! Returns index of the given vertex if it exists in cache,
- //! elsewhere adds it to cache and returns cached index.
- //! @param theVertexExplorer template parameter intended to transfer
- //! parameters of vertex to method. Explorer class can implement different
- //! approaches of extraction of target parameters.
- //! @param isFillEdgeVertices if TRUE adds vertex to shared map of
- //! edges vertices, elsewhere adds it map of face vertices.
- template<class HVertexExplorer>
- Standard_Integer GetVertexIndex(
- const HVertexExplorer& theVertexExplorer,
- const Standard_Boolean isFillEdgeVertices = Standard_False)
- {
- const TopoDS_Vertex& aVertex = theVertexExplorer->Vertex();
- Standard_Integer aNewVertexIndex = 0;
- if (getVertexIndex(aVertex, aNewVertexIndex))
- return aNewVertexIndex;
-
- if (!theVertexExplorer->IsSameUV() ||
- !getVertexIndex(theVertexExplorer->SameVertex(), aNewVertexIndex))
- {
- aNewVertexIndex = LastPointId() + 1;
-
- BRepMesh::DMapOfIntegerPnt& aPointsMap = isFillEdgeVertices ?
- *myBoundaryPoints : *mySurfacePoints;
-
- aPointsMap.Bind(aNewVertexIndex, theVertexExplorer->Point());
- }
-
- BRepMesh::DMapOfVertexInteger& aVertexMap = isFillEdgeVertices ?
- *myBoundaryVertices : *mySurfaceVertices;
-
- aVertexMap.Bind(aVertex, aNewVertexIndex);
-
- return aNewVertexIndex;
- }
-
- //! Adds node with the given parameters to mesh.
- //! @param theIndex index of 3D point corresponded to the node.
- //! @param theUV node position.
- //! @param theMovability movability of a node.
- //! @param theNodeIndex index of vertex in mesh structure.
- //! @param theNodeOnEdgeIndex ordered index of node on the boundary.
- Standard_EXPORT void AddNode(const Standard_Integer theIndex,
- const gp_XY& theUV,
- const BRepMesh_DegreeOfFreedom theMovability,
- Standard_Integer& theNodeIndex,
- Standard_Integer& theNodeOnEdgeIndex);
-
-public: //! @name Auxiliary methods
-
- //! Scales the given point from real parametric space
- //! to face basis and otherwise.
- //! @param thePoint2d point to be scaled.
- //! @param isToFaceBasis if TRUE converts point to face basis,
- //! otherwise performs reverse conversion.
- //! @return scaled point.
- Standard_EXPORT gp_XY Scale(const gp_XY& thePoint2d,
- const Standard_Boolean isToFaceBasis);
-
- DEFINE_STANDARD_RTTIEXT(BRepMesh_FaceAttribute,Standard_Transient)
-
-private:
-
- //! Default constructor.
- BRepMesh_FaceAttribute();
-
- //! Assignment operator.
- void operator =(const BRepMesh_FaceAttribute& /*theOther*/)
- {
- }
-
- //! Initializes internal data structures.
- void init();
-
- //! Computes parametric tolerance of a face regarding the given limits.
- Standard_Real computeParametricTolerance(
- const Standard_Real theFirstParam,
- const Standard_Real theLastParam) const;
-
- //! Clears internal data structures local to face.
- void clearLocal(
- const Standard_Boolean isClearSurfaceDataOnly = Standard_False);
-
- //! Returns index of the given vertex if it exists in cache.
- //! @param theVertex vertex which index should be retrieved.
- //! @param theVertexIndex index of the given vertex.
- //! @return TRUE if cached value is found, FALSE elsewhere.
- Standard_EXPORT Standard_Boolean getVertexIndex(
- const TopoDS_Vertex& theVertex,
- Standard_Integer& theVertexIndex) const;
-
-private:
-
- Standard_Real myDefFace; //!< Restore face deflection
- Standard_Real myUMin; //!< Describes minimal value in U domain
- Standard_Real myUMax; //!< Describes maximal value in U domain
- Standard_Real myVMin; //!< Describes minimal value in V domain
- Standard_Real myVMax; //!< Describes maximal value in V domain
- Standard_Real myDeltaX;
- Standard_Real myDeltaY;
- Standard_Real myMinStep;
- Standard_Integer myStatus;
- Standard_Boolean myAdaptiveMin;
-
- BRepMesh::HDMapOfVertexInteger myBoundaryVertices;
- BRepMesh::HDMapOfIntegerPnt myBoundaryPoints;
-
- TopoDS_Face myFace;
- Handle(BRepAdaptor_HSurface) mySurface;
- BRepMesh::HClassifier myClassifier;
-
- BRepMesh::HDMapOfShapePairOfPolygon myInternalEdges;
-
- BRepMesh::HDMapOfIntegerListOfXY myLocation2D;
- BRepMesh::HIMapOfInteger myVertexEdgeMap;
-
- // This field is intended to keep calculated mesh nodes to prevent
- // extremely high memory consumption in case if the whole structure is kept.
- BRepMesh::HVectorOfVertex myMeshNodes;
-
- BRepMesh::HDMapOfVertexInteger mySurfaceVertices;
- BRepMesh::HDMapOfIntegerPnt mySurfacePoints;
- Handle(BRepMesh_DataStructureOfDelaun) myStructure;
-};
-
-DEFINE_STANDARD_HANDLE(BRepMesh_FaceAttribute, Standard_Transient)
-
-#endif
+++ /dev/null
-// Created on: 1996-02-27
-// Created by: Ekaterina SMIRNOVA
-// Copyright (c) 1996-1999 Matra Datavision
-// Copyright (c) 1999-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_FastDiscret.hxx>
-
-#include <BRepMesh_WireChecker.hxx>
-#include <BRepMesh_FastDiscretFace.hxx>
-#include <BRepMesh_FaceAttribute.hxx>
-#include <BRepMesh_DataStructureOfDelaun.hxx>
-#include <BRepMesh_GeomTool.hxx>
-#include <BRepMesh_PairOfPolygon.hxx>
-#include <BRepMesh_Classifier.hxx>
-#include <BRepMesh_EdgeParameterProvider.hxx>
-#include <BRepMesh_IEdgeTool.hxx>
-#include <BRepMesh_EdgeTessellator.hxx>
-#include <BRepMesh_EdgeTessellationExtractor.hxx>
-
-#include <BRepAdaptor_Curve.hxx>
-#include <BRepAdaptor_Surface.hxx>
-#include <BRepAdaptor_HSurface.hxx>
-
-#include <Bnd_Box.hxx>
-#include <BRepTools.hxx>
-#include <BRepBndLib.hxx>
-#include <BndLib_Add3dCurve.hxx>
-#include <Poly_Triangulation.hxx>
-#include <Poly_PolygonOnTriangulation.hxx>
-
-#include <Precision.hxx>
-#include <Geom2d_Curve.hxx>
-#include <Geom2dAdaptor_HCurve.hxx>
-#include <Geom_Surface.hxx>
-#include <Geom_Plane.hxx>
-#include <GeomAbs_SurfaceType.hxx>
-#include <Extrema_LocateExtPC.hxx>
-
-#include <TColStd_Array1OfInteger.hxx>
-#include <TColStd_Array1OfCharacter.hxx>
-#include <TColStd_HArray1OfReal.hxx>
-#include <TColgp_Array1OfPnt2d.hxx>
-#include <TColGeom2d_SequenceOfCurve.hxx>
-
-#include <TopTools_SequenceOfShape.hxx>
-#include <TopTools_ListIteratorOfListOfShape.hxx>
-
-#include <TopAbs.hxx>
-#include <TopoDS.hxx>
-#include <TopoDS_Vertex.hxx>
-#include <TopExp.hxx>
-#include <TopExp_Explorer.hxx>
-
-#include <OSD_Parallel.hxx>
-
-#include <Standard_ErrorHandler.hxx>
-#include <Standard_Failure.hxx>
-#include <NCollection_IncAllocator.hxx>
-
-#include <BRep_ListIteratorOfListOfPointRepresentation.hxx>
-#include <BRep_PointRepresentation.hxx>
-
-#include <vector>
-
-IMPLEMENT_STANDARD_RTTIEXT(BRepMesh_FastDiscret,Standard_Transient)
-
-#define UVDEFLECTION 1.e-05
-
-//=======================================================================
-//function : BRepMesh_FastDiscret
-//purpose :
-//=======================================================================
-BRepMesh_FastDiscret::BRepMesh_FastDiscret( const Bnd_Box& theBox,
- const BRepMesh_FastDiscret::Parameters& theParams)
- :
- myMapdefle(1000, new NCollection_IncAllocator()),
- myBoundaryVertices(new BRepMesh::DMapOfVertexInteger),
- myBoundaryPoints(new BRepMesh::DMapOfIntegerPnt),
- myParameters(theParams),
- myDtotale(0.)
-{
- if ( myParameters.Relative )
- BRepMesh_ShapeTool::BoxMaxDimension(theBox, myDtotale);
-}
-
-//=======================================================================
-//function : InitSharedFaces
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::InitSharedFaces(const TopoDS_Shape& theShape)
-{
- TopExp::MapShapesAndAncestors(theShape, TopAbs_EDGE, TopAbs_FACE, mySharedFaces);
-}
-
-//=======================================================================
-//function : Perform(shape)
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::Perform(const TopoDS_Shape& theShape)
-{
- InitSharedFaces(theShape);
-
- std::vector<TopoDS_Face> aFaces;
- TopExp_Explorer anExplorer(theShape, TopAbs_FACE);
- for (; anExplorer.More(); anExplorer.Next())
- {
- const TopoDS_Face& aFace = TopoDS::Face(anExplorer.Current());
- Add(aFace);
- aFaces.push_back(aFace);
- }
-
- OSD_Parallel::ForEach(aFaces.begin(), aFaces.end(), *this, !myParameters.InParallel);
-}
-
-
-//=======================================================================
-//function : Process
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::Process(const TopoDS_Face& theFace) const
-{
- Handle(BRepMesh_FaceAttribute) anAttribute;
- if (GetFaceAttribute(theFace, anAttribute))
- {
- try
- {
- OCC_CATCH_SIGNALS
-
- BRepMesh_FastDiscretFace aTool(myParameters.Angle, myParameters.MinSize,
- myParameters.InternalVerticesMode, myParameters.ControlSurfaceDeflection);
- aTool.Perform(anAttribute);
- }
- catch (Standard_Failure)
- {
- anAttribute->SetStatus(BRepMesh_Failure);
- }
- }
-}
-
-//=======================================================================
-//function : resetDataStructure
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::resetDataStructure()
-{
- Handle(NCollection_IncAllocator) aAllocator;
- if (myAttribute->ChangeStructure().IsNull())
- aAllocator = new NCollection_IncAllocator(BRepMesh::MEMORY_BLOCK_SIZE_HUGE);
- else
- aAllocator = myAttribute->ChangeStructure()->Allocator();
-
- myAttribute->Clear();
- aAllocator->Reset(Standard_False);
- Handle(BRepMesh_DataStructureOfDelaun) aStructure =
- new BRepMesh_DataStructureOfDelaun(aAllocator);
-
- const Standard_Real aTolU = myAttribute->ToleranceU();
- const Standard_Real aTolV = myAttribute->ToleranceV();
- const Standard_Real uCellSize = 14.0 * aTolU;
- const Standard_Real vCellSize = 14.0 * aTolV;
-
- aStructure->Data()->SetCellSize ( uCellSize, vCellSize);
- aStructure->Data()->SetTolerance( aTolU , aTolV );
-
- myAttribute->ChangeStructure() = aStructure;
-}
-
-//=======================================================================
-//function : Add(face)
-//purpose :
-//=======================================================================
-Standard_Integer BRepMesh_FastDiscret::Add(const TopoDS_Face& theFace)
-{
- myAttribute.Nullify();
- GetFaceAttribute(theFace, myAttribute, Standard_True);
-
- try
- {
- OCC_CATCH_SIGNALS
-
- // Initialize face attributes
- if (!myAttribute->IsInitialized ())
- myAttribute->SetFace (theFace, myParameters.AdaptiveMin);
-
- BRepMesh::HIMapOfInteger& aVertexEdgeMap = myAttribute->ChangeVertexEdgeMap();
- BRepMesh::HDMapOfShapePairOfPolygon& aInternalEdges = myAttribute->ChangeInternalEdges();
-
- resetDataStructure();
-
- Standard_Real defedge = myParameters.Deflection;
- Standard_Integer nbEdge = 0;
- Standard_Real savangle = myParameters.Angle;
- Standard_Real cdef;
- Standard_Real maxdef = 2.* BRepMesh_ShapeTool::MaxFaceTolerance(theFace);
-
- Standard_Real defface = 0.;
- if (!myParameters.Relative)
- {
- defedge = Max(UVDEFLECTION, defedge);
- defface = Max(myParameters.Deflection, maxdef);
- }
-
- const TopoDS_Face& aFace = myAttribute->Face();
- for (TopoDS_Iterator aWireIt(aFace); aWireIt.More(); aWireIt.Next())
- {
- for (TopoDS_Iterator aEdgeIt(aWireIt.Value()); aEdgeIt.More(); aEdgeIt.Next(), ++nbEdge)
- {
- const TopoDS_Edge& aEdge = TopoDS::Edge(aEdgeIt.Value());
- if (aEdge.IsNull())
- continue;
- if (myParameters.Relative)
- {
- if (!myMapdefle.IsBound(aEdge))
- {
- if (myEdges.IsBound(aEdge))
- {
- const BRepMesh_PairOfPolygon& aPair = myEdges.Find(aEdge);
- const Handle(Poly_PolygonOnTriangulation)& aPolygon = aPair.First();
- defedge = aPolygon->Deflection();
- }
- else
- {
- defedge = BRepMesh_ShapeTool::RelativeEdgeDeflection(
- aEdge, myParameters.Deflection, myDtotale, cdef);
-
- myParameters.Angle = savangle * cdef;
- }
- }
- else
- {
- defedge = myMapdefle(aEdge);
- }
-
- defface += defedge;
- defface = Max(maxdef, defface);
-
- if (!myMapdefle.IsBound(aEdge))
- {
- defedge = Max(UVDEFLECTION, defedge);
- myMapdefle.Bind(aEdge, defedge);
- }
- }
- else
- {
- if (!myMapdefle.IsBound(aEdge))
- {
- myMapdefle.Bind(aEdge, defedge);
- }
- }
-
- Standard_Real aFirstParam, aLastParam;
- Handle(Geom2d_Curve) aCurve2d =
- BRep_Tool::CurveOnSurface(aEdge, aFace, aFirstParam, aLastParam);
-
- if (aCurve2d.IsNull())
- continue;
- Handle(Geom2dAdaptor_HCurve) aPCurve =
- new Geom2dAdaptor_HCurve(aCurve2d, aFirstParam, aLastParam);
-
- add(aEdge, aPCurve, defedge);
- myParameters.Angle = savangle;
- }
- }
-
- if ( nbEdge == 0 || aVertexEdgeMap->Extent() < 3 )
- {
- myAttribute->ChangeStructure().Nullify();
- myAttribute->SetStatus(BRepMesh_Failure);
- return myAttribute->GetStatus();
- }
-
- if ( myParameters.Relative )
- {
- defface = defface / nbEdge;
- }
- else
- {
- defface = myParameters.Deflection;
- }
-
- defface = Max(maxdef, defface);
-
- TopLoc_Location aLoc;
- Handle(Poly_Triangulation) aTriangulation = BRep_Tool::Triangulation(aFace, aLoc);
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
-
- if ( aTriangulation.IsNull() )
- {
- Standard_Real xCur, yCur;
- Standard_Real maxX, minX, maxY, minY;
-
- minX = minY = 1.e100;
- maxX = maxY =-1.e100;
-
- Standard_Integer ipn = 0;
- Standard_Integer i1 = 1;
- for ( i1 = 1; i1 <= aVertexEdgeMap->Extent(); ++i1 )
- {
- const BRepMesh_Vertex& aVertex =
- myAttribute->ChangeStructure()->GetNode(aVertexEdgeMap->FindKey(i1));
-
- ++ipn;
-
- xCur = aVertex.Coord().X();
- yCur = aVertex.Coord().Y();
-
- minX = Min(xCur, minX);
- maxX = Max(xCur, maxX);
- minY = Min(yCur, minY);
- maxY = Max(yCur, maxY);
- }
-
- Standard_Real myumin = minX;
- Standard_Real myumax = maxX;
- Standard_Real myvmin = minY;
- Standard_Real myvmax = maxY;
-
- const Standard_Real umin = gFace->FirstUParameter();
- const Standard_Real umax = gFace->LastUParameter();
- const Standard_Real vmin = gFace->FirstVParameter();
- const Standard_Real vmax = gFace->LastVParameter();
-
- if (myumin < umin || myumax > umax)
- {
- if (gFace->IsUPeriodic())
- {
- if ((myumax - myumin) > (umax - umin))
- myumax = myumin + (umax - umin);
- }
- else
- {
- if (umin > myumin)
- myumin = umin;
-
- if (umax < myumax)
- myumax = umax;
- }
- }
-
- if (myvmin < vmin || myvmax > vmax)
- {
- if (gFace->IsVPeriodic())
- {
- if ((myvmax - myvmin) > (vmax - vmin))
- myvmax = myvmin + (vmax - vmin);
- }
- else
- {
- if ( vmin > myvmin )
- myvmin = vmin;
-
- if (vmax < myvmax)
- myvmax = vmax;
- }
- }
-
- GeomAbs_SurfaceType aSurfType = gFace->GetType();
- // Fast verification of the validity of calculated limits.
- // If wrong, sure a problem of pcurve.
- if (aSurfType == GeomAbs_BezierSurface &&
- (myumin < -0.5 || myumax > 1.5 || myvmin < -0.5 || myvmax > 1.5) )
- {
- myAttribute->ChangeStructure().Nullify();
- myAttribute->SetStatus(BRepMesh_Failure);
- return myAttribute->GetStatus();
- }
-
- //define parameters for correct parametrics
- Standard_Real deltaX = 1.0;
- Standard_Real deltaY = 1.0;
-
- {
- Standard_Real aTolU, aTolV;
- myAttribute->ChangeStructure()->Data()->GetTolerance(aTolU, aTolV);
- const Standard_Real aTol = Sqrt(aTolU * aTolU + aTolV * aTolV);
-
- BRepMesh::HClassifier& aClassifier = myAttribute->ChangeClassifier();
- BRepMesh_WireChecker aDFaceChecker(aFace, aTol, aInternalEdges,
- aVertexEdgeMap, myAttribute->ChangeStructure(),
- myumin, myumax, myvmin, myvmax, myParameters.InParallel );
-
- aDFaceChecker.ReCompute(aClassifier);
- BRepMesh_Status aCheckStatus = aDFaceChecker.Status();
-
- if (aCheckStatus == BRepMesh_SelfIntersectingWire)
- {
- Standard_Integer nbmaill = 0;
- Standard_Real eps = Precision::Confusion();
- while (nbmaill < 5 && aCheckStatus != BRepMesh_ReMesh)
- {
- ++nbmaill;
-
- resetDataStructure();
-
- for (TopoDS_Iterator aWireIt(aFace); aWireIt.More(); aWireIt.Next())
- {
- for (TopoDS_Iterator aEdgeIt(aWireIt.Value()); aEdgeIt.More(); aEdgeIt.Next(), ++nbEdge)
- {
- const TopoDS_Edge& anEdge = TopoDS::Edge(aEdgeIt.Value());
- if (anEdge.IsNull())
- continue;
- if (myEdges.IsBound(anEdge))
- myEdges.UnBind(anEdge);
-
- defedge = Max(myMapdefle(anEdge) / 3.0, eps);
- myMapdefle.Bind(anEdge, defedge);
-
- Standard_Real aFirstParam, aLastParam;
- Handle(Geom2d_Curve) aCurve2d =
- BRep_Tool::CurveOnSurface(anEdge, aFace, aFirstParam, aLastParam);
- if (aCurve2d.IsNull())
- continue;
-
- Handle(Geom2dAdaptor_HCurve) aPCurve =
- new Geom2dAdaptor_HCurve(aCurve2d, aFirstParam, aLastParam);
- add(anEdge, aPCurve, defedge);
- }
- }
-
- aDFaceChecker.ReCompute(aClassifier);
- if (aDFaceChecker.Status() == BRepMesh_NoError)
- aCheckStatus = BRepMesh_ReMesh;
- }
- }
-
- myAttribute->SetStatus(aCheckStatus);
- if (!myAttribute->IsValid())
- {
- myAttribute->ChangeStructure().Nullify();
- return myAttribute->GetStatus();
- }
- }
-
- // try to find the real length:
- // akm (bug OCC16) : We must calculate these measures in non-singular
- // parts of face. Let's try to compute average value of three
- // (umin, (umin+umax)/2, umax), and respectively for v.
- // vvvvv
- Standard_Real longu = 0.0, longv = 0.0; //, last , first;
- gp_Pnt P11, P12, P21, P22, P31, P32;
-
- Standard_Real du = 0.05 * ( myumax - myumin );
- Standard_Real dv = 0.05 * ( myvmax - myvmin );
- Standard_Real dfuave = 0.5 * ( myumin + myumax );
- Standard_Real dfvave = 0.5 * ( myvmin + myvmax );
- Standard_Real dfucur, dfvcur;
-
- // U loop
- gFace->D0(myumin, myvmin, P11);
- gFace->D0(myumin, dfvave, P21);
- gFace->D0(myumin, myvmax, P31);
- for (i1=1, dfucur=myumin+du; i1 <= 20; i1++, dfucur+=du)
- {
- gFace->D0(dfucur, myvmin, P12);
- gFace->D0(dfucur, dfvave, P22);
- gFace->D0(dfucur, myvmax, P32);
- longu += ( P11.Distance(P12) + P21.Distance(P22) + P31.Distance(P32) );
- P11 = P12;
- P21 = P22;
- P31 = P32;
- }
-
- // V loop
- gFace->D0(myumin, myvmin, P11);
- gFace->D0(dfuave, myvmin, P21);
- gFace->D0(myumax, myvmin, P31);
- for (i1=1, dfvcur=myvmin+dv; i1 <= 20; i1++, dfvcur+=dv)
- {
- gFace->D0(myumin, dfvcur, P12);
- gFace->D0(dfuave, dfvcur, P22);
- gFace->D0(myumax, dfvcur, P32);
- longv += ( P11.Distance(P12) + P21.Distance(P22) + P31.Distance(P32) );
- P11 = P12;
- P21 = P22;
- P31 = P32;
- }
-
- longu /= 3.;
- longv /= 3.;
- // akm (bug OCC16) ^^^^^
-
- if (longu <= 1.e-16 || longv <= 1.e-16)
- {
- //yes, it is seen!!
- myAttribute->ChangeStructure().Nullify();
- myAttribute->SetStatus(BRepMesh_Failure);
- return myAttribute->GetStatus();
- }
-
-
- if (aSurfType == GeomAbs_Torus)
- {
- gp_Torus Tor = gFace->Torus();
- Standard_Real r = Tor.MinorRadius(), R = Tor.MajorRadius();
- Standard_Real Du, Dv;//, pasu, pasv;
-
- Dv = Max(1.0e0 - (defface/r),0.0e0) ;
- Standard_Real oldDv = 2.0 * ACos (Dv);
- oldDv = Min(oldDv, myParameters.Angle);
- Dv = 0.9*oldDv; //TWOTHIRD * oldDv;
- Dv = oldDv;
-
- Standard_Integer nbV = Max((Standard_Integer)((myvmax-myvmin)/Dv), 2);
- Dv = (myvmax-myvmin)/(nbV+1);
-
- Standard_Real ru = R + r;
- if ( ru > 1.e-16 )
- {
- Du = Max(1.0e0 - (defface/ru),0.0e0);
- Du = (2.0 * ACos (Du));
- Du = Min(Du, myParameters.Angle);
- Standard_Real aa = sqrt(Du*Du + oldDv*oldDv);
-
- if (aa < gp::Resolution())
- {
- myAttribute->ChangeStructure().Nullify();
- return myAttribute->GetStatus();
- }
-
- Du = Du * Min(oldDv, Du) / aa;
- }
- else
- {
- Du = Dv;
- }
-
- Standard_Integer nbU = Max((Standard_Integer)((myumax-myumin)/Du), 2);
- nbU = Max(nbU, (Standard_Integer)(nbV*(myumax-myumin)*R/((myvmax-myvmin)*r)/5.));
-
- Du = (myumax-myumin)/(nbU+1);
- //-- DeltaX and DeltaY are chosen so that to avoid "jumping"
- //-- of points on the grid
- deltaX = Du;
- deltaY = Dv;
- }
- else if (aSurfType == GeomAbs_Cylinder)
- {
- gp_Cylinder Cyl = gFace->Cylinder();
- Standard_Real R = Cyl.Radius();
-
- // Calculate parameters for iteration in U direction
- Standard_Real Du = 1.0 - (defface/R);
- if (Du < 0.0)
- Du = 0.0;
-
- Du = 2.0 * ACos (Du);
- if (Du > myParameters.Angle)
- Du = myParameters.Angle;
-
- deltaX = Du / longv;
- deltaY = 1.;
- }
- else
- {
- deltaX = (myumax-myumin)/longu;
- deltaY = (myvmax-myvmin)/longv;
- }
-
- // Restore face attribute
- myAttribute->SetDefFace(defface);
- myAttribute->SetUMax(myumax);
- myAttribute->SetVMax(myvmax);
- myAttribute->SetUMin(myumin);
- myAttribute->SetVMin(myvmin);
- myAttribute->SetDeltaX(deltaX);
- myAttribute->SetDeltaY(deltaY);
- }
-
- myAttribute->ChangeMeshNodes() =
- myAttribute->ChangeStructure()->Data()->Vertices();
- }
- catch(Standard_Failure)
- {
- myAttribute->SetStatus(BRepMesh_Failure);
- }
-
- myAttribute->ChangeStructure().Nullify();
- return myAttribute->GetStatus();
-}
-
-//=======================================================================
-//function : getEdgeAttributes
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_FastDiscret::getEdgeAttributes(
- const TopoDS_Edge& theEdge,
- const Handle(Geom2dAdaptor_HCurve)& thePCurve,
- const Standard_Real theDefEdge,
- BRepMesh_FastDiscret::EdgeAttributes& theAttributes) const
-{
- EdgeAttributes& aEAttr = theAttributes;
-
- // Get vertices
- TopExp::Vertices(theEdge, aEAttr.FirstVertex, aEAttr.LastVertex);
- if (aEAttr.FirstVertex.IsNull() || aEAttr.LastVertex.IsNull())
- return Standard_False;
-
- // Get range on 2d curve
- const TopoDS_Face& aFace = myAttribute->Face();
- BRep_Tool::Range(theEdge, aFace, aEAttr.FirstParam, aEAttr.LastParam);
-
- // Get end points on 2d curve
- BRep_Tool::UVPoints(theEdge, aFace, aEAttr.FirstUV, aEAttr.LastUV);
-
- aEAttr.IsSameUV =
- aEAttr.FirstUV.IsEqual(aEAttr.LastUV, Precision::PConfusion());
- if (aEAttr.IsSameUV)
- {
- // 1. is it really sameUV without being degenerated
- gp_Pnt2d uvF, uvL;
- thePCurve->D0(thePCurve->FirstParameter(), uvF);
- thePCurve->D0(thePCurve->LastParameter(), uvL);
-
- if (!aEAttr.FirstUV.IsEqual(uvF, Precision::PConfusion()))
- aEAttr.FirstUV = uvF;
-
- if (!aEAttr.LastUV.IsEqual(uvL, Precision::PConfusion()))
- aEAttr.LastUV = uvL;
-
- aEAttr.IsSameUV =
- aEAttr.FirstUV.IsEqual(aEAttr.LastUV, Precision::PConfusion());
- }
-
- //Control tolerance of vertices
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
- gp_Pnt pFirst = gFace->Value(aEAttr.FirstUV.X(), aEAttr.FirstUV.Y());
- gp_Pnt pLast = gFace->Value(aEAttr.LastUV.X(), aEAttr.LastUV.Y());
-
- Standard_Real aSqDist = pFirst.SquareDistance(BRep_Tool::Pnt(aEAttr.FirstVertex));
- aSqDist = Max(aSqDist, pLast.SquareDistance(BRep_Tool::Pnt(aEAttr.LastVertex)));
-
- aEAttr.Deflection = Max(theDefEdge, BRep_Tool::Tolerance(theEdge));
- aEAttr.Deflection = Max(aEAttr.Deflection, sqrt(aSqDist));
-
- return Standard_True;
-}
-
-//=======================================================================
-//function : registerEdgeVertices
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::registerEdgeVertices(
- BRepMesh_FastDiscret::EdgeAttributes& theAttributes,
- Standard_Integer& ipf,
- Standard_Integer& ivf,
- Standard_Integer& isvf,
- Standard_Integer& ipl,
- Standard_Integer& ivl,
- Standard_Integer& isvl)
-{
- EdgeAttributes& aEAttr = theAttributes;
- if (aEAttr.FirstVExtractor.IsNull())
- {
- // Use edge geometry to produce tesselation.
- aEAttr.FirstVExtractor =
- new TopoDSVExplorer(aEAttr.FirstVertex, aEAttr.IsSameUV, aEAttr.LastVertex);
- }
-
- if (aEAttr.LastVExtractor.IsNull())
- {
- // Use edge geometry to produce tesselation.
- aEAttr.LastVExtractor =
- new TopoDSVExplorer(aEAttr.LastVertex, aEAttr.IsSameUV, aEAttr.FirstVertex);
- }
-
- // Process first vertex
- ipf = myAttribute->GetVertexIndex(aEAttr.FirstVExtractor, Standard_True);
- Standard_Real aMinDist = 2. * BRep_Tool::Tolerance(aEAttr.FirstVertex);
- gp_XY aTmpUV1 = BRepMesh_ShapeTool::FindUV(ipf, aEAttr.FirstUV, aMinDist, myAttribute);
-
- myAttribute->AddNode(ipf, aTmpUV1, BRepMesh_Frontier, ivf, isvf);
-
- // Process last vertex
- ipl = aEAttr.LastVertex.IsSame(aEAttr.FirstVertex) ? ipf :
- myAttribute->GetVertexIndex(aEAttr.LastVExtractor, Standard_True);
- aMinDist = 2. * BRep_Tool::Tolerance(aEAttr.LastVertex);
- gp_XY aTmpUV2 = BRepMesh_ShapeTool::FindUV(ipl, aEAttr.LastUV, aMinDist, myAttribute);
-
- myAttribute->AddNode(ipl, aTmpUV2, BRepMesh_Frontier, ivl, isvl);
-
- // Update edge deflection
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
- gp_Pnt aPntE1 = gFace->Value(aEAttr.FirstUV.X(), aEAttr.FirstUV.Y());
- gp_Pnt aPntFound1 = gFace->Value(aTmpUV1.X(), aTmpUV1.Y());
- Standard_Real aSqDist = aPntE1.SquareDistance(aPntFound1);
- gp_Pnt aPntE2 = gFace->Value(aEAttr.LastUV.X(), aEAttr.LastUV.Y());
- gp_Pnt aPntFound2 = gFace->Value(aTmpUV2.X(), aTmpUV2.Y());
- aSqDist = Max(aSqDist, aPntE2.SquareDistance(aPntFound2));
- aEAttr.Deflection = Max(aEAttr.Deflection, sqrt(aSqDist));
-}
-
-//=======================================================================
-//function : add
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::add(
- const TopoDS_Edge& theEdge,
- const Handle(Geom2dAdaptor_HCurve)& thePCurve,
- const Standard_Real theDefEdge)
-{
- const TopAbs_Orientation orEdge = theEdge.Orientation();
- if (orEdge == TopAbs_EXTERNAL)
- return;
-
- EdgeAttributes aEAttr;
- if (!getEdgeAttributes(theEdge, thePCurve, theDefEdge, aEAttr))
- return;
-
- if (!myEdges.IsBound(theEdge))
- {
- update(theEdge, thePCurve, theDefEdge, aEAttr);
- return;
- }
-
- Standard_Integer ipf, ivf, isvf, ipl, ivl, isvl;
- registerEdgeVertices(aEAttr, ipf, ivf, isvf, ipl, ivl, isvl);
-
- // If this Edge has been already checked and it is not degenerated,
- // the points of the polygon calculated at the first check are retrieved :
-
- // retrieve the polygone:
- const BRepMesh_PairOfPolygon& aPair = myEdges.Find(theEdge);
- const Handle(Poly_PolygonOnTriangulation)& aPolygon = aPair.First();
- const TColStd_Array1OfInteger& aNodes = aPolygon->Nodes();
- Handle(TColStd_HArray1OfReal) aParams = aPolygon->Parameters();
-
- // creation anew:
- const Standard_Integer aNodesNb = aNodes.Length();
- TColStd_Array1OfInteger aNewNodes (1, aNodesNb);
- TColStd_Array1OfReal aNewParams(1, aNodesNb);
-
- aNewNodes (1) = isvf;
- aNewParams(1) = aEAttr.FirstParam;
-
- aNewNodes (aNodesNb) = isvl;
- aNewParams(aNodesNb) = aEAttr.LastParam;
-
- const TopoDS_Face& aFace = myAttribute->Face();
- if (!BRepMesh_ShapeTool::IsDegenerated(theEdge, aFace))
- {
- BRepMesh_EdgeParameterProvider aProvider(theEdge, aFace, aParams);
- for (Standard_Integer i = 2; i < aNodesNb; ++i)
- {
- const Standard_Integer aPointId = aNodes(i);
- const gp_Pnt& aPnt = myBoundaryPoints->Find(aPointId);
-
- const Standard_Real aParam = aProvider.Parameter(i, aPnt);
- gp_Pnt2d aUV = thePCurve->Value(aParam);
-
- Standard_Integer iv2, isv;
- myAttribute->AddNode(aPointId, aUV.Coord(), BRepMesh_OnCurve, iv2, isv);
-
- aNewNodes (i) = isv;
- aNewParams(i) = aParam;
- }
- }
-
- Handle(Poly_PolygonOnTriangulation) P1 =
- new Poly_PolygonOnTriangulation(aNewNodes, aNewParams);
-
- storePolygon(theEdge, P1, aEAttr.Deflection);
-}
-
-//=======================================================================
-//function : update(edge)
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::update(
- const TopoDS_Edge& theEdge,
- const Handle(Geom2dAdaptor_HCurve)& theC2d,
- const Standard_Real theDefEdge,
- BRepMesh_FastDiscret::EdgeAttributes& theAttributes)
-{
- EdgeAttributes& aEAttr = theAttributes;
-
- const TopoDS_Face& aFace = myAttribute->Face();
- Handle(BRepMesh_IEdgeTool) aEdgeTool;
- // Try to find existing tessellation.
- for (Standard_Integer i = 1; aEdgeTool.IsNull(); ++i)
- {
- TopLoc_Location aLoc;
- Handle(Poly_Triangulation) aTriangulation;
- Handle(Poly_PolygonOnTriangulation) aPolygon;
- BRep_Tool::PolygonOnTriangulation(theEdge, aPolygon, aTriangulation, aLoc, i);
-
- if (aPolygon.IsNull())
- break;
-
- if (aTriangulation.IsNull() || !aPolygon->HasParameters())
- continue;
-
- if (aPolygon->Deflection() > 1.1 * theDefEdge)
- continue;
-
- const TColgp_Array1OfPnt& aNodes = aTriangulation->Nodes();
- const TColStd_Array1OfInteger& aIndices = aPolygon->Nodes();
- Handle(TColStd_HArray1OfReal) aParams = aPolygon->Parameters();
-
- aEAttr.FirstVExtractor = new PolyVExplorer(aEAttr.FirstVertex,
- aEAttr.IsSameUV, aEAttr.LastVertex, aIndices(1), aNodes, aLoc);
-
- aEAttr.LastVExtractor = new PolyVExplorer(aEAttr.LastVertex,
- aEAttr.IsSameUV, aEAttr.FirstVertex, aIndices(aIndices.Length()), aNodes, aLoc);
-
- aEdgeTool = new BRepMesh_EdgeTessellationExtractor(theEdge, theC2d,
- aFace, aTriangulation, aPolygon, aLoc);
- }
-
- if (aEdgeTool.IsNull())
- {
- aEdgeTool = new BRepMesh_EdgeTessellator(theEdge, myAttribute,
- mySharedFaces, theDefEdge, myParameters.Angle, myParameters.MinSize);
- }
-
- Standard_Integer ipf, ivf, isvf, ipl, ivl, isvl;
- registerEdgeVertices(aEAttr, ipf, ivf, isvf, ipl, ivl, isvl);
-
- Handle(Poly_PolygonOnTriangulation) P1, P2;
- if (BRepMesh_ShapeTool::IsDegenerated(theEdge, aFace))
- {
- // two nodes
- Standard_Integer aNewNodesArr[] = {isvf, isvl};
- Standard_Integer aNewNodInStructArr[] = {ipf, ipl};
- Standard_Real aNewParamsArr[] = {aEAttr.FirstParam, aEAttr.LastParam};
- TColStd_Array1OfInteger aNewNodes (aNewNodesArr[0], 1, 2);
- TColStd_Array1OfInteger aNewNodInStruct(aNewNodInStructArr[0], 1, 2);
- TColStd_Array1OfReal aNewParams (aNewParamsArr[0], 1, 2);
-
- P1 = new Poly_PolygonOnTriangulation(aNewNodes, aNewParams);
- P2 = new Poly_PolygonOnTriangulation(aNewNodInStruct, aNewParams);
- }
- else
- {
- const Standard_Integer aNodesNb = aEdgeTool->NbPoints();
- // Allocate the memory for arrays aNewNodesVec, aNewNodesInStructVec, aNewParamsVec
- // only once using the buffer aBuf.
- TColStd_Array1OfCharacter aBuf(1, aNodesNb * (2*sizeof(Standard_Integer) + sizeof(Standard_Real)));
- TColStd_Array1OfInteger aNewNodesVec(*reinterpret_cast<const Standard_Integer*>
- (&aBuf(1)), 1, aNodesNb);
- TColStd_Array1OfInteger aNewNodesInStructVec(*reinterpret_cast<const Standard_Integer*>
- (&aBuf(1 + aNodesNb*sizeof(Standard_Integer))), 1, aNodesNb);
- TColStd_Array1OfReal aNewParamsVec(*reinterpret_cast<const Standard_Real*>
- (&aBuf(1 + aNodesNb*2*sizeof(Standard_Integer))), 1, aNodesNb);
-
- Standard_Integer aNodesCount = 1;
- aNewNodesInStructVec(aNodesCount) = ipf;
- aNewNodesVec (aNodesCount) = isvf;
- aNewParamsVec (aNodesCount) = aEAttr.FirstParam;
-
- ++aNodesCount;
- Standard_Integer aPrevNodeId = ivf;
- Standard_Integer aLastPointId = myAttribute->LastPointId();
- for (Standard_Integer i = 2; i < aNodesNb; ++i)
- {
- gp_Pnt aPnt;
- gp_Pnt2d aUV;
- Standard_Real aParam;
- if (!aEdgeTool->Value(i, aParam, aPnt, aUV))
- continue;
-
- // Imitate index of 3d point in order to not to add points to map without necessity.
- Standard_Integer iv2, isv;
- myAttribute->AddNode(aLastPointId + 1, aUV.Coord(), BRepMesh_Frontier, iv2, isv);
- if (aPrevNodeId == iv2)
- continue;
-
- // Ok, now we can add point to the map.
- myBoundaryPoints->Bind (++aLastPointId, aPnt);
-
- aNewNodesInStructVec(aNodesCount) = aLastPointId;
- aNewNodesVec (aNodesCount) = isv;
- aNewParamsVec (aNodesCount) = aParam;
-
- ++aNodesCount;
- aPrevNodeId = iv2;
- }
-
- aNewNodesInStructVec(aNodesCount) = ipl;
- aNewNodesVec (aNodesCount) = isvl;
- aNewParamsVec (aNodesCount) = aEAttr.LastParam;
-
- TColStd_Array1OfInteger aNewNodes (aNewNodesVec.First (), 1, aNodesCount);
- TColStd_Array1OfInteger aNewNodInStruct(aNewNodesInStructVec.First(), 1, aNodesCount);
- TColStd_Array1OfReal aNewParams (aNewParamsVec.First(), 1, aNodesCount);
-
- P1 = new Poly_PolygonOnTriangulation(aNewNodes, aNewParams);
- P2 = new Poly_PolygonOnTriangulation(aNewNodInStruct, aNewParams);
- }
-
- storePolygon(theEdge, P1, aEAttr.Deflection);
- storePolygonSharedData(theEdge, P2, aEAttr.Deflection);
-}
-
-//=======================================================================
-//function : storeInternalPolygon
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::storePolygon(
- const TopoDS_Edge& theEdge,
- Handle(Poly_PolygonOnTriangulation)& thePolygon,
- const Standard_Real theDeflection)
-{
- thePolygon->Deflection(theDeflection);
- BRepMesh::HDMapOfShapePairOfPolygon& aInternalEdges = myAttribute->ChangeInternalEdges();
- if (aInternalEdges->IsBound(theEdge))
- {
- BRepMesh_PairOfPolygon& aPair = aInternalEdges->ChangeFind(theEdge);
- if (theEdge.Orientation() == TopAbs_REVERSED)
- aPair.Append(thePolygon);
- else
- aPair.Prepend(thePolygon);
-
- return;
- }
-
- BRepMesh_PairOfPolygon aPair;
- aPair.Append(thePolygon);
- aInternalEdges->Bind(theEdge, aPair);
-}
-
-//=======================================================================
-//function : storePolygonSharedData
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::storePolygonSharedData(
- const TopoDS_Edge& theEdge,
- Handle(Poly_PolygonOnTriangulation)& thePolygon,
- const Standard_Real theDeflection)
-{
- thePolygon->Deflection(theDeflection);
- BRepMesh_PairOfPolygon aPair;
- aPair.Append(thePolygon);
- myEdges.Bind(theEdge, aPair);
-}
-
-//=======================================================================
-//function : GetFaceAttribute
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_FastDiscret::GetFaceAttribute(
- const TopoDS_Face& theFace,
- Handle(BRepMesh_FaceAttribute)& theAttribute,
- const Standard_Boolean isForceCreate) const
-{
- if (myAttributes.IsBound(theFace))
- {
- theAttribute = myAttributes(theFace);
- return Standard_True;
- }
- else if (isForceCreate)
- {
- theAttribute = new BRepMesh_FaceAttribute(myBoundaryVertices, myBoundaryPoints);
- myAttributes.Bind(theFace, theAttribute);
- }
-
- return Standard_False;
-}
-
-//=======================================================================
-//function : RemoveFaceAttribute
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscret::RemoveFaceAttribute(const TopoDS_Face& theFace)
-{
- if (myAttributes.IsBound(theFace))
- myAttributes.UnBind(theFace);
-}
+++ /dev/null
-// Copyright (c) 2013 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_FastDiscret_HeaderFile
-#define _BRepMesh_FastDiscret_HeaderFile
-
-#include <Standard.hxx>
-#include <Standard_Type.hxx>
-#include <BRepMesh_FastDiscret.hxx>
-#include <BRepMesh_DataStructureOfDelaun.hxx>
-#include <TColStd_IndexedMapOfInteger.hxx>
-#include <BRepMesh_Status.hxx>
-#include <TopTools_DataMapOfShapeReal.hxx>
-#include <TopTools_ListOfShape.hxx>
-#include <TopTools_MutexForShapeProvider.hxx>
-#include <Standard_Transient.hxx>
-#include <BRepMesh_Delaun.hxx>
-#include <TopAbs_ShapeEnum.hxx>
-#include <BRepMesh_Triangle.hxx>
-#include <BRepMesh_FaceAttribute.hxx>
-#include <BRepMesh.hxx>
-#include <TColgp_Array1OfPnt.hxx>
-#include <BRep_Tool.hxx>
-#include <BRepMesh_ShapeTool.hxx>
-#include <TopoDS_Vertex.hxx>
-#include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
-
-class BRepMesh_DataStructureOfDelaun;
-class Bnd_Box;
-class TopoDS_Shape;
-class TopoDS_Face;
-class TopoDS_Edge;
-class Geom2dAdaptor_HCurve;
-class BRepAdaptor_HSurface;
-class BRepMesh_Edge;
-class BRepMesh_Vertex;
-class gp_Pnt;
-class BRepMesh_FaceAttribute;
-
-//! Algorithm to mesh a shape with respect of the <br>
-//! frontier the deflection and by option the shared <br>
-//! components. <br>
-class BRepMesh_FastDiscret : public Standard_Transient
-{
-public:
-
-
- //! Structure storing meshing parameters
- struct Parameters {
-
- //! Default constructor
- Parameters()
- :
- Angle(0.1),
- Deflection(0.001),
- MinSize(Precision::Confusion()),
- InParallel(Standard_False),
- Relative(Standard_False),
- AdaptiveMin(Standard_False),
- InternalVerticesMode(Standard_True),
- ControlSurfaceDeflection(Standard_True)
- {
- }
-
- //! Angular deflection
- Standard_Real Angle;
-
- //! Deflection
- Standard_Real Deflection;
-
- //! Minimal allowed size of mesh element
- Standard_Real MinSize;
-
- //! Switches on/off multy thread computation
- Standard_Boolean InParallel;
-
- //! Switches on/off relative computation of edge tolerance<br>
- //! If trur, deflection used for the polygonalisation of each edge will be
- //! <defle> * Size of Edge. The deflection used for the faces will be the
- //! maximum deflection of their edges.
- Standard_Boolean Relative;
-
- //! Adaptive parametric tolerance flag. <br>
- //! If this flag is set to true the minimal parametric tolerance
- //! is computed taking minimal parametric distance between vertices
- //! into account
- Standard_Boolean AdaptiveMin;
-
- //! Mode to take or ont to take internal face vertices into account
- //! in triangulation process
- Standard_Boolean InternalVerticesMode;
-
- //! Prameter to check the deviation of triangulation and interior of
- //! the face
- Standard_Boolean ControlSurfaceDeflection;
- };
-
-public:
-
-
- //! Constructor.
- //! Sets the meshing parameters and updates
- //! relative defletion according to bounding box
- //! @param B - bounding box encompasing shape
- //! @param theParams - meshing algo parameters
- Standard_EXPORT BRepMesh_FastDiscret (const Bnd_Box& B,
- const Parameters& theParams);
-
- //! Build triangulation on the whole shape.
- Standard_EXPORT void Perform(const TopoDS_Shape& shape);
-
- //! Record a face for further processing.
- //! @return status flags collected during discretization
- //! of boundaries of the given face.
- Standard_EXPORT Standard_Integer Add(const TopoDS_Face& face);
-
- //! Triangulate a face previously recorded for
- //! processing by call to Add(). Can be executed in
- //! parallel threads.
- Standard_EXPORT void Process(const TopoDS_Face& face) const;
-
- void operator () (const TopoDS_Face& face) const
- {
- Process(face);
- }
-
- //! Returns parameters of meshing
- inline const Parameters& MeshParameters() const
- {
- return myParameters;
- }
-
- //! Returns modificable mesh parameters
- inline Parameters& ChangeMeshParameters()
- {
- return myParameters;
- }
-
-
- Standard_EXPORT void InitSharedFaces(const TopoDS_Shape& theShape);
-
- inline const TopTools_IndexedDataMapOfShapeListOfShape& SharedFaces() const
- {
- return mySharedFaces;
- }
-
- //! Returns attribute descriptor for the given face.
- //! @param theFace face the attribute should be returned for.
- //! @param[out] theAttribute attribute found for the specified face.
- //! @param isForceCreate if True creates new attribute in case if there
- //! is no data for the given face.
- Standard_EXPORT Standard_Boolean GetFaceAttribute (
- const TopoDS_Face& theFace,
- Handle(BRepMesh_FaceAttribute)& theAttribute,
- const Standard_Boolean isForceCreate = Standard_False) const;
-
- //! Remove face attribute as useless to free locate memory.
- Standard_EXPORT void RemoveFaceAttribute( const TopoDS_Face& theFace );
-
- //! Returns number of boundary 3d points.
- inline Standard_Integer NbBoundaryPoints() const
- {
- return myBoundaryPoints->Extent();
- }
-
- DEFINE_STANDARD_RTTIEXT(BRepMesh_FastDiscret,Standard_Transient)
-
-private:
-
- //! Auxiliary class used to extract geometrical parameters of TopoDS_Vertex.
- class TopoDSVExplorer
- {
- public:
- TopoDSVExplorer(
- const TopoDS_Vertex& theVertex,
- const Standard_Boolean isSameUV,
- const TopoDS_Vertex& theSameVertex)
- : myVertex(theVertex),
- myIsSameUV(isSameUV),
- mySameVertex(theSameVertex)
- {
- }
- virtual ~TopoDSVExplorer() {
- }
- const TopoDS_Vertex& Vertex() const
- {
- return myVertex;
- }
-
- Standard_Boolean IsSameUV() const
- {
- return myIsSameUV;
- }
-
- const TopoDS_Vertex& SameVertex() const
- {
- return mySameVertex;
- }
-
- virtual gp_Pnt Point() const
- {
- return BRep_Tool::Pnt(myVertex);
- }
-
- private:
-
- void operator =(const TopoDSVExplorer& /*theOther*/)
- {
- }
-
- private:
- const TopoDS_Vertex& myVertex;
- Standard_Boolean myIsSameUV;
- const TopoDS_Vertex& mySameVertex;
- };
-
-
- //! Auxiliary class used to extract polygonal parameters of TopoDS_Vertex.
- class PolyVExplorer : public TopoDSVExplorer
- {
- public:
- PolyVExplorer(
- const TopoDS_Vertex& theVertex,
- const Standard_Boolean isSameUV,
- const TopoDS_Vertex& theSameVertex,
- const Standard_Integer theVertexIndex,
- const TColgp_Array1OfPnt& thePolygon,
- const TopLoc_Location& theLoc)
- : TopoDSVExplorer(theVertex, isSameUV, theSameVertex),
- myVertexIndex(theVertexIndex),
- myPolygon(thePolygon),
- myLoc(theLoc)
- {
- }
-
- virtual gp_Pnt Point() const
- {
- return BRepMesh_ShapeTool::UseLocation(myPolygon(myVertexIndex), myLoc);
- }
-
- private:
-
- void operator =(const PolyVExplorer& /*theOther*/)
- {
- }
-
- private:
- Standard_Integer myVertexIndex;
- const TColgp_Array1OfPnt& myPolygon;
- const TopLoc_Location myLoc;
- };
-
- //! Structure keeps common parameters of edge
- //! used for tessellation.
- struct EdgeAttributes
- {
- TopoDS_Vertex FirstVertex;
- TopoDS_Vertex LastVertex;
-
- Standard_Real FirstParam;
- Standard_Real LastParam;
-
- gp_Pnt2d FirstUV;
- gp_Pnt2d LastUV;
-
- Standard_Real Deflection;
- Standard_Boolean IsSameUV;
-
- NCollection_Handle<TopoDSVExplorer> FirstVExtractor;
- NCollection_Handle<TopoDSVExplorer> LastVExtractor;
- };
-
- //! Fills structure of by attributes of the given edge.
- //! @return TRUE on success, FALSE elsewhere.
- Standard_Boolean getEdgeAttributes(
- const TopoDS_Edge& theEdge,
- const Handle(Geom2dAdaptor_HCurve)& thePCurve,
- const Standard_Real theDefEdge,
- EdgeAttributes& theAttributes) const;
-
- //! Registers end vertices of the edge in mesh data
- //! structure of currently processed face.
- void registerEdgeVertices(
- EdgeAttributes& theAttributes,
- Standard_Integer& ipf,
- Standard_Integer& ivf,
- Standard_Integer& isvf,
- Standard_Integer& ipl,
- Standard_Integer& ivl,
- Standard_Integer& isvl);
-
- //! Adds tessellated representation of the given edge to
- //! mesh data structure of currently processed face.
- void add(const TopoDS_Edge& theEdge,
- const Handle(Geom2dAdaptor_HCurve)& theCurve2D,
- const Standard_Real theEdgeDeflection);
-
- //! Updates tessellated representation of the given edge.
- //! If edge already has a polygon which deflection satisfies
- //! the given value, retrieves tessellation from polygon.
- //! Computes tessellation using edge's geometry elsewhere.
- void update(
- const TopoDS_Edge& theEdge,
- const Handle(Geom2dAdaptor_HCurve)& theCurve2D,
- const Standard_Real theEdgeDeflection,
- EdgeAttributes& theAttributes);
-
- //! Stores polygonal model of the given edge.
- //! @param theEdge edge which polygonal model is stored.
- //! @param thePolygon polygonal model of the edge.
- //! @param theDeflection deflection with which polygonalization is performed.
- //! This value is stored inside the polygon.
- void storePolygon(
- const TopoDS_Edge& theEdge,
- Handle(Poly_PolygonOnTriangulation)& thePolygon,
- const Standard_Real theDeflection);
-
- //! Caches polygonal model of the given edge to be used in further.
- //! @param theEdge edge which polygonal data is stored.
- //! @param thePolygon shared polygonal data of the edge.
- //! @param theDeflection deflection with which polygonalization is performed.
- //! This value is stored inside the polygon.
- void storePolygonSharedData(
- const TopoDS_Edge& theEdge,
- Handle(Poly_PolygonOnTriangulation)& thePolygon,
- const Standard_Real theDeflection);
-
- //! Resets temporary data structure used to collect unique nodes.
- void resetDataStructure();
-
-private:
-
- TopoDS_Face myFace;
-
- BRepMesh::DMapOfShapePairOfPolygon myEdges;
- mutable BRepMesh::DMapOfFaceAttribute myAttributes;
- TopTools_DataMapOfShapeReal myMapdefle;
-
- // Data shared for whole shape
- BRepMesh::HDMapOfVertexInteger myBoundaryVertices;
- BRepMesh::HDMapOfIntegerPnt myBoundaryPoints;
-
- // Fast access to attributes of current face
- Handle(BRepMesh_FaceAttribute) myAttribute;
- TopTools_IndexedDataMapOfShapeListOfShape mySharedFaces;
-
- Parameters myParameters;
-
- Standard_Real myDtotale;
-};
-
-DEFINE_STANDARD_HANDLE(BRepMesh_FastDiscret, Standard_Transient)
-
-#endif
+++ /dev/null
-// Created by: Ekaterina SMIRNOVA
-// Copyright (c) 2008-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_FastDiscretFace.hxx>
-
-#include <BRepMesh_PairOfPolygon.hxx>
-#include <BRepMesh_ShapeTool.hxx>
-#include <Poly_PolygonOnTriangulation.hxx>
-#include <Poly_Triangulation.hxx>
-
-#include <BRepAdaptor_Surface.hxx>
-#include <BRepAdaptor_HSurface.hxx>
-#include <BRepAdaptor_Curve.hxx>
-#include <Adaptor3d_IsoCurve.hxx>
-
-#include <BRep_ListIteratorOfListOfPointRepresentation.hxx>
-#include <BRep_PointRepresentation.hxx>
-#include <BRep_TVertex.hxx>
-#include <BRep_Tool.hxx>
-
-#include <GeomLib.hxx>
-#include <Geom_Surface.hxx>
-#include <Geom_BSplineSurface.hxx>
-#include <Geom_BezierSurface.hxx>
-#include <GCPnts_TangentialDeflection.hxx>
-#include <GCPnts_AbscissaPoint.hxx>
-
-#include <Standard_ErrorHandler.hxx>
-#include <Standard_Failure.hxx>
-#include <TColStd_Array1OfReal.hxx>
-#include <TColStd_ListOfInteger.hxx>
-#include <TColStd_SequenceOfReal.hxx>
-#include <TColStd_Array1OfInteger.hxx>
-#include <TColStd_HArray1OfReal.hxx>
-#include <TColgp_Array1OfPnt2d.hxx>
-#include <TopTools_DataMapOfShapeReal.hxx>
-
-#include <TopExp_Explorer.hxx>
-#include <TopoDS.hxx>
-#include <TopoDS_Vertex.hxx>
-#include <TopExp.hxx>
-
-#include <NCollection_Map.hxx>
-#include <Bnd_Box2d.hxx>
-
-#include <algorithm>
-
-//#define DEBUG_MESH "mesh.tcl"
-#ifdef DEBUG_MESH
-#include <fstream>
-#endif
-
-
-IMPLEMENT_STANDARD_RTTIEXT(BRepMesh_FastDiscretFace,Standard_Transient)
-
-static Standard_Real FUN_CalcAverageDUV(TColStd_Array1OfReal& P, const Standard_Integer PLen)
-{
- Standard_Integer i, j, n = 0;
- Standard_Real p, result = 0.;
-
- for(i = 1; i <= PLen; i++)
- {
- // Sort
- for(j = i + 1; j <= PLen; j++)
- {
- if(P(i) > P(j))
- {
- p = P(i);
- P(i) = P(j);
- P(j) = p;
- }
- }
- // Accumulate
- if (i != 1)
- {
- p = Abs(P(i) - P(i-1));
- if(p > 1.e-7)
- {
- result += p;
- n++;
- }
- }
- }
- return (n? (result / (Standard_Real) n) : -1.);
-}
-
-namespace
-{
- Standard_Real deflectionOfSegment (
- const gp_Pnt& theFirstPoint,
- const gp_Pnt& theLastPoint,
- const gp_Pnt& theMidPoint)
- {
- // 23.03.2010 skl for OCC21645 - change precision for comparison
- if (theFirstPoint.SquareDistance (theLastPoint) > Precision::SquareConfusion ())
- {
- gp_Lin aLin (theFirstPoint, gp_Dir (gp_Vec (theFirstPoint, theLastPoint)));
- return aLin.Distance (theMidPoint);
- }
-
- return theFirstPoint.Distance (theMidPoint);
- }
-
- Standard_Boolean IsCompexSurface (const GeomAbs_SurfaceType theType)
- {
- return (
- theType != GeomAbs_Sphere &&
- theType != GeomAbs_Cylinder &&
- theType != GeomAbs_Cone &&
- theType != GeomAbs_Torus);
- }
-
- //! Auxiliary class used to extract geometrical parameters of fixed TopoDS_Vertex.
- class FixedVExplorer
- {
- public:
-
- DEFINE_STANDARD_ALLOC
-
- FixedVExplorer(const TopoDS_Vertex& theVertex)
- : myVertex(theVertex)
- {
- }
-
- const TopoDS_Vertex& Vertex() const
- {
- return myVertex;
- }
-
- Standard_Boolean IsSameUV() const
- {
- return Standard_False;
- }
-
- TopoDS_Vertex SameVertex() const
- {
- return TopoDS_Vertex();
- }
-
- gp_Pnt Point() const
- {
- return BRep_Tool::Pnt(myVertex);
- }
-
- private:
-
- void operator =(const FixedVExplorer& /*theOther*/)
- {
- }
-
- private:
- const TopoDS_Vertex& myVertex;
- };
-}
-
-
-//=======================================================================
-//function : BRepMesh_FastDiscretFace
-//purpose :
-//=======================================================================
-BRepMesh_FastDiscretFace::BRepMesh_FastDiscretFace(
- const Standard_Real theAngle,
- const Standard_Real theMinSize,
- const Standard_Boolean isInternalVerticesMode,
- const Standard_Boolean isControlSurfaceDeflection)
-: myAngle(theAngle),
- myInternalVerticesMode(isInternalVerticesMode),
- myMinSize(theMinSize),
- myIsControlSurfaceDeflection(isControlSurfaceDeflection)
-{
-}
-
-//=======================================================================
-//function : Perform
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::Perform(const Handle(BRepMesh_FaceAttribute)& theAttribute)
-{
- add(theAttribute);
- commitSurfaceTriangulation();
-}
-
-//=======================================================================
-//function : initDataStructure
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::initDataStructure()
-{
- const Standard_Real aTolU = myAttribute->ToleranceU();
- const Standard_Real aTolV = myAttribute->ToleranceV();
- const Standard_Real uCellSize = 14.0 * aTolU;
- const Standard_Real vCellSize = 14.0 * aTolV;
-
- const Standard_Real deltaX = myAttribute->GetDeltaX();
- const Standard_Real deltaY = myAttribute->GetDeltaY();
-
- Handle(NCollection_IncAllocator) aAllocator =
- new NCollection_IncAllocator(BRepMesh::MEMORY_BLOCK_SIZE_HUGE);
- myStructure = new BRepMesh_DataStructureOfDelaun(aAllocator);
- myStructure->Data()->SetCellSize ( uCellSize / deltaX, vCellSize / deltaY);
- myStructure->Data()->SetTolerance( aTolU / deltaX, aTolV / deltaY);
-
- myAttribute->ChangeStructure() = myStructure;
- myAttribute->ChangeSurfacePoints() = new BRepMesh::DMapOfIntegerPnt(1, aAllocator);
- myAttribute->ChangeSurfaceVertices()= new BRepMesh::DMapOfVertexInteger(1, aAllocator);
-
- // Check the necessity to fill the map of parameters
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
- GeomAbs_SurfaceType thetype = gFace->GetType();
- const Standard_Boolean isBSpline = (thetype == GeomAbs_BezierSurface ||
- thetype == GeomAbs_BSplineSurface);
- const Standard_Boolean useUVParam = (thetype == GeomAbs_Torus || IsCompexSurface (thetype));
-
- Handle(NCollection_BaseAllocator) aBaseAlloc = aAllocator;
- myUParam.Clear (aBaseAlloc);
- myVParam.Clear (aBaseAlloc);
-
- // essai de determination de la longueur vraie:
- // akm (bug OCC16) : We must calculate these measures in non-singular
- // parts of face. Let`s try to compute average value of three
- // (umin, (umin+umax)/2, umax), and respectively for v.
- // vvvvv
- //Standard_Real longu = 0.0, longv = 0.0; //, last , first;
- //gp_Pnt P11, P12, P21, P22, P31, P32;
- BRepMesh::HVectorOfVertex& aBoundaryNodes = myAttribute->ChangeMeshNodes();
- BRepMesh::VectorOfVertex::Iterator aNodesIt(*aBoundaryNodes);
- for (; aNodesIt.More(); aNodesIt.Next())
- {
- BRepMesh_Vertex& aNode = aNodesIt.ChangeValue();
- gp_XY aPnt2d = aNode.Coord();
-
- if (useUVParam)
- {
- myUParam.Add(aPnt2d.X());
- myVParam.Add(aPnt2d.Y());
- }
-
- aNode.ChangeCoord() = myAttribute->Scale(aPnt2d, Standard_True);
- myStructure->AddNode(aNode, Standard_True);
- }
- aBoundaryNodes.Nullify();
-
- if (isBSpline)
- {
- const Standard_Real aRange[2][2] = {
- {myAttribute->GetUMin(), myAttribute->GetUMax()},
- {myAttribute->GetVMin(), myAttribute->GetVMax()}
- };
-
- const GeomAbs_Shape aContinuity = GeomAbs_CN;
- for (Standard_Integer i = 0; i < 2; ++i)
- {
- const Standard_Boolean isU = (i == 0);
- const Standard_Integer aIntervalsNb = isU ?
- gFace->NbUIntervals(aContinuity) :
- gFace->NbVIntervals(aContinuity);
-
- BRepMesh::IMapOfReal& aParams = isU ? myUParam : myVParam;
- if (aIntervalsNb < aParams.Size())
- continue;
-
- TColStd_Array1OfReal aIntervals(1, aIntervalsNb + 1);
- if (isU)
- gFace->UIntervals(aIntervals, aContinuity);
- else
- gFace->VIntervals(aIntervals, aContinuity);
-
- for (Standard_Integer j = 1; j <= aIntervals.Upper(); ++j)
- {
- const Standard_Real aParam = aIntervals(j);
- if (aParam > aRange[i][0] && aParam < aRange[i][1])
- aParams.Add(aParam);
- }
- }
- }
-
- ////////////////////////////////////////////////////////////
- //add internal vertices after self-intersection check
- if ( myInternalVerticesMode )
- {
- TopExp_Explorer anExplorer(myAttribute->Face(), TopAbs_VERTEX, TopAbs_EDGE);
- for ( ; anExplorer.More(); anExplorer.Next() )
- add(TopoDS::Vertex(anExplorer.Current()));
- }
-
- const BRepMesh::HDMapOfShapePairOfPolygon& aEdges = myAttribute->ChangeInternalEdges();
- TopExp_Explorer aWireIt(myAttribute->Face(), TopAbs_WIRE);
- for (; aWireIt.More(); aWireIt.Next())
- {
- TopExp_Explorer aEdgeIt(aWireIt.Current(), TopAbs_EDGE);
- for (; aEdgeIt.More(); aEdgeIt.Next())
- {
- const TopoDS_Edge& aEdge = TopoDS::Edge(aEdgeIt.Current());
- BRepMesh_PairOfPolygon aPair;
- if (!aEdges->Find(aEdge, aPair))
- continue;
-
- TopAbs_Orientation aOri = aEdge.Orientation();
- const Handle(Poly_PolygonOnTriangulation)& aPolygon =
- aOri == TopAbs_REVERSED ? aPair.Last() : aPair.First();
-
- const TColStd_Array1OfInteger& aIndices = aPolygon->Nodes();
- const Standard_Integer aNodesNb = aPolygon->NbNodes();
-
- Standard_Integer aPrevId = aIndices(1);
- for (Standard_Integer i = 2; i <= aNodesNb; ++i)
- {
- const Standard_Integer aCurId = aIndices(i);
- addLinkToMesh(aPrevId, aCurId, aOri);
- aPrevId = aCurId;
- }
- }
- }
-}
-
-//=======================================================================
-//function : addLinkToMesh
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::addLinkToMesh(
- const Standard_Integer theFirstNodeId,
- const Standard_Integer theLastNodeId,
- const TopAbs_Orientation theOrientation)
-{
- if (theOrientation == TopAbs_FORWARD)
- myStructure->AddLink(BRepMesh_Edge(theFirstNodeId, theLastNodeId, BRepMesh_Frontier));
- else if (theOrientation == TopAbs_REVERSED)
- myStructure->AddLink(BRepMesh_Edge(theLastNodeId, theFirstNodeId, BRepMesh_Frontier));
- else if (theOrientation == TopAbs_INTERNAL)
- myStructure->AddLink(BRepMesh_Edge(theFirstNodeId, theLastNodeId, BRepMesh_Fixed));
-}
-
-//=======================================================================
-//function : Add
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::add(const Handle(BRepMesh_FaceAttribute)& theAttribute)
-{
- if (!theAttribute->IsValid() || theAttribute->ChangeMeshNodes()->IsEmpty())
- return;
-
- myAttribute = theAttribute;
- initDataStructure();
-
- BRepMesh::HIMapOfInteger& aVertexEdgeMap = myAttribute->ChangeVertexEdgeMap();
- Standard_Integer nbVertices = aVertexEdgeMap->Extent();
- BRepMesh::Array1OfInteger tabvert_corr(1, nbVertices);
- for ( Standard_Integer i = 1; i <= nbVertices; ++i )
- tabvert_corr(i) = i;
-
- BRepMesh_Delaun trigu(myStructure, tabvert_corr);
-
- //removed all free edges from triangulation
- const Standard_Integer nbLinks = myStructure->NbLinks();
- for( Standard_Integer i = 1; i <= nbLinks; i++ )
- {
- if( myStructure->ElementsConnectedTo(i).Extent() < 1 )
- {
- BRepMesh_Edge& anEdge = (BRepMesh_Edge&)trigu.GetEdge(i);
- if ( anEdge.Movability() == BRepMesh_Deleted )
- continue;
-
- anEdge.SetMovability(BRepMesh_Free);
- myStructure->RemoveLink(i);
- }
- }
-
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
- GeomAbs_SurfaceType thetype = gFace->GetType();
-
- Standard_Boolean rajout =
- (thetype == GeomAbs_Sphere || thetype == GeomAbs_Torus);
-
- // Check the necessity to fill the map of parameters
- const Standard_Boolean useUVParam = (thetype == GeomAbs_Torus ||
- thetype == GeomAbs_BezierSurface ||
- thetype == GeomAbs_BSplineSurface);
-
- const Standard_Real umax = myAttribute->GetUMax();
- const Standard_Real umin = myAttribute->GetUMin();
- const Standard_Real vmax = myAttribute->GetVMax();
- const Standard_Real vmin = myAttribute->GetVMin();
-
- Standard_Boolean isaline =
- ((umax - umin) < Precision::PConfusion() ||
- (vmax - vmin) < Precision::PConfusion());
-
- Standard_Real aDef = -1;
- if ( !isaline && myStructure->ElementsOfDomain().Extent() > 0 )
- {
- if (!rajout)
- {
- // compute maximal deflection
- aDef = control(trigu, Standard_True);
- rajout = (aDef > myAttribute->GetDefFace() || aDef < 0.);
- }
- if (thetype != GeomAbs_Plane)
- {
- if (!rajout && useUVParam)
- {
- rajout = (myVParam.Extent() > 2 &&
- (gFace->IsUClosed() || gFace->IsVClosed()));
- }
-
- if (rajout)
- {
- insertInternalVertices(trigu);
-
- //control internal points
- if (myIsControlSurfaceDeflection)
- aDef = control(trigu, Standard_False);
- }
- }
- }
-
- //modify myStructure back
- BRepMesh::HVectorOfVertex& aMeshNodes = myStructure->Data()->ChangeVertices();
- for ( Standard_Integer i = 1; i <= myStructure->NbNodes(); ++i )
- {
- BRepMesh_Vertex& aNode = aMeshNodes->ChangeValue(i - 1);
- aNode.ChangeCoord() = myAttribute->Scale(aNode.Coord(), Standard_False);
-
- const BRepMesh::ListOfInteger& alist = myStructure->LinksConnectedTo(i);
- // Register internal nodes used in triangulation
- if (!alist.IsEmpty() && aVertexEdgeMap->FindIndex(i) == 0)
- aVertexEdgeMap->Add(i);
- }
-
- if (!(aDef < 0.))
- myAttribute->SetDefFace(aDef);
-}
-
-//=======================================================================
-//function : addVerticesToMesh
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_FastDiscretFace::addVerticesToMesh(
- const BRepMesh::ListOfVertex& theVertices,
- BRepMesh_Delaun& theMeshBuilder)
-{
- if (theVertices.IsEmpty())
- return Standard_False;
-
- BRepMesh::Array1OfVertexOfDelaun aArrayOfNewVertices(1, theVertices.Extent());
- BRepMesh::ListOfVertex::Iterator aVertexIt(theVertices);
- for (Standard_Integer aVertexId = 0; aVertexIt.More(); aVertexIt.Next())
- aArrayOfNewVertices(++aVertexId) = aVertexIt.Value();
-
- theMeshBuilder.AddVertices(aArrayOfNewVertices);
- return Standard_True;
-}
-
-//=======================================================================
-//function : filterParameters
-//purpose :
-//=======================================================================
-static void filterParameters(const BRepMesh::IMapOfReal& theParams,
- const Standard_Real theMinDist,
- const Standard_Real theFilterDist,
- BRepMesh::SequenceOfReal& theResult)
-{
- // Sort sequence of parameters
- const Standard_Integer anInitLen = theParams.Extent();
-
- TColStd_Array1OfReal aParamArray(1, anInitLen);
- Standard_Integer j;
- for (j = 1; j <= anInitLen; j++)
- aParamArray(j) = theParams(j);
-
- std::sort (aParamArray.begin(), aParamArray.end());
-
- // mandatory pre-filtering using the first (minimal) filter value
- Standard_Integer aParamLength = 1;
- for (j = 2; j <= anInitLen; j++)
- {
- if ((aParamArray(j)-aParamArray(aParamLength)) > theMinDist)
- {
- if (++aParamLength < j)
- aParamArray(aParamLength) = aParamArray(j);
- }
- }
-
- //perform filtering on series
- Standard_Real aLastAdded, aLastCandidate;
- Standard_Boolean isCandidateDefined = Standard_False;
- aLastAdded = aParamArray(1);
- aLastCandidate = aLastAdded;
- theResult.Append(aLastAdded);
-
- for(j=2; j < aParamLength; j++)
- {
- Standard_Real aVal = aParamArray(j);
- if(aVal-aLastAdded > theFilterDist)
- {
- //adds the parameter
- if(isCandidateDefined) {
- aLastAdded = aLastCandidate;
- isCandidateDefined = Standard_False;
- j--;
- }
- else
- {
- aLastAdded = aVal;
- }
- theResult.Append(aLastAdded);
- continue;
- }
-
- aLastCandidate = aVal;
- isCandidateDefined = Standard_True;
- }
- theResult.Append(aParamArray(aParamLength));
-}
-
-//=======================================================================
-//function : insertInternalVertices
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertInternalVertices(BRepMesh_Delaun& theMeshBuilder)
-{
- Handle(NCollection_IncAllocator) anAlloc = new NCollection_IncAllocator;
- BRepMesh::ListOfVertex aNewVertices(anAlloc);
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
- switch (gFace->GetType())
- {
- case GeomAbs_Sphere:
- insertInternalVerticesSphere(aNewVertices);
- break;
-
- case GeomAbs_Cylinder:
- insertInternalVerticesCylinder(aNewVertices);
- break;
-
- case GeomAbs_Cone:
- insertInternalVerticesCone(aNewVertices);
- break;
-
- case GeomAbs_Torus:
- insertInternalVerticesTorus(aNewVertices);
- break;
-
- default:
- insertInternalVerticesOther(aNewVertices);
- break;
- }
-
- addVerticesToMesh(aNewVertices, theMeshBuilder);
-}
-
-//=======================================================================
-//function : insertInternalVerticesSphere
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertInternalVerticesSphere(
- BRepMesh::ListOfVertex& theNewVertices)
-{
- Standard_Real aRange[] = {
- myAttribute->GetVMin(), myAttribute->GetVMax(),
- myAttribute->GetUMin(), myAttribute->GetUMax()
- };
-
- gp_Sphere aSphere = myAttribute->Surface()->Sphere();
-
- // Calculate parameters for iteration in V direction
- Standard_Real aStep = 0.7 * GCPnts_TangentialDeflection::ArcAngularStep(
- aSphere.Radius(), myAttribute->GetDefFace(), myAngle, myMinSize);
-
- Standard_Real aDd[2] = {aStep, aStep};
- Standard_Real aPasMax[2] = {0., 0.};
- for (Standard_Integer i = 0; i < 2; ++i)
- {
- const Standard_Real aMax = aRange[2 * i + 1];
- const Standard_Real aDiff = aMax - aRange[2 * i + 0];
- aDd[i] = aDiff / ((Standard_Integer)(aDiff / aDd[i]) + 1);
- aPasMax[i] = aMax - Precision::PConfusion();
- }
-
- const Standard_Real aHalfDu = aDd[1] * 0.5;
- Standard_Boolean Shift = Standard_False;
- Standard_Real aPasV = aRange[0] + aDd[0];
- for (; aPasV < aPasMax[0]; aPasV += aDd[0])
- {
- Shift = !Shift;
- const Standard_Real d = (Shift) ? aHalfDu : 0.;
- Standard_Real aPasU = aRange[2] + d;
- for (; aPasU < aPasMax[1]; aPasU += aDd[1])
- {
- tryToInsertAnalyticVertex(gp_Pnt2d(aPasU, aPasV), aSphere, theNewVertices);
- }
- }
-}
-
-//=======================================================================
-//function : insertInternalVerticesCylinder
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertInternalVerticesCylinder(
- BRepMesh::ListOfVertex& theNewVertices)
-{
- const Standard_Real umax = myAttribute->GetUMax();
- const Standard_Real umin = myAttribute->GetUMin();
- const Standard_Real vmax = myAttribute->GetVMax();
- const Standard_Real vmin = myAttribute->GetVMin();
-
- gp_Cylinder aCylinder = myAttribute->Surface()->Cylinder();
- const Standard_Real aRadius = aCylinder.Radius();
-
- Standard_Integer nbU = 0;
- Standard_Integer nbV = 0;
- const Standard_Real su = umax - umin;
- const Standard_Real sv = vmax - vmin;
- const Standard_Real aArcLen = su * aRadius;
- if (aArcLen > myAttribute->GetDefFace ())
- {
- // Calculate parameters for iteration in U direction
- const Standard_Real Du = GCPnts_TangentialDeflection::ArcAngularStep (
- aRadius, myAttribute->GetDefFace (), myAngle, myMinSize);
- nbU = (Standard_Integer)(su / Du);
-
- // Calculate parameters for iteration in V direction
- const Standard_Real aDv = nbU*sv / aArcLen;
- // Protection against overflow during casting to int in case
- // of long cylinder with small radius.
- nbV = aDv > static_cast<Standard_Real> (IntegerLast ()) ?
- 0 : (Standard_Integer)(aDv);
- nbV = Min (nbV, 100 * nbU);
- }
-
- const Standard_Real Du = su / (nbU + 1);
- const Standard_Real Dv = sv / (nbV + 1);
-
- Standard_Real pasu, pasv, pasvmax = vmax - Dv*0.5, pasumax = umax - Du*0.5;
- for (pasv = vmin + Dv; pasv < pasvmax; pasv += Dv)
- {
- for (pasu = umin + Du; pasu < pasumax; pasu += Du)
- {
- tryToInsertAnalyticVertex(gp_Pnt2d(pasu, pasv), aCylinder, theNewVertices);
- }
- }
-}
-
-//=======================================================================
-//function : insertInternalVerticesCone
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertInternalVerticesCone(
- BRepMesh::ListOfVertex& theNewVertices)
-{
- const Standard_Real umax = myAttribute->GetUMax();
- const Standard_Real umin = myAttribute->GetUMin();
- const Standard_Real vmax = myAttribute->GetVMax();
- const Standard_Real vmin = myAttribute->GetVMin();
-
- gp_Cone aCone = myAttribute->Surface()->Cone();
- Standard_Real RefR = aCone.RefRadius();
- Standard_Real SAng = aCone.SemiAngle();
- Standard_Real aRadius = Max(Abs(RefR + vmin*Sin(SAng)), Abs(RefR + vmax*Sin(SAng)));
-
- Standard_Real Du = GCPnts_TangentialDeflection::ArcAngularStep(
- aRadius, myAttribute->GetDefFace(), myAngle, myMinSize);
-
- Standard_Real Dv, pasu, pasv;
- Standard_Integer nbU = (Standard_Integer)((umax - umin) / Du);
- Standard_Integer nbV = (Standard_Integer)(nbU*(vmax - vmin) / ((umax - umin)*aRadius));
- Du = (umax - umin) / (nbU + 1);
- Dv = (vmax - vmin) / (nbV + 1);
-
- Standard_Real pasvmax = vmax - Dv*0.5, pasumax = umax - Du*0.5;
- for (pasv = vmin + Dv; pasv < pasvmax; pasv += Dv)
- {
- for (pasu = umin + Du; pasu < pasumax; pasu += Du)
- {
- tryToInsertAnalyticVertex(gp_Pnt2d(pasu, pasv), aCone, theNewVertices);
- }
- }
-}
-
-//=======================================================================
-//function : insertInternalVerticesTorus
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertInternalVerticesTorus(
- BRepMesh::ListOfVertex& theNewVertices)
-{
- const Standard_Real umax = myAttribute->GetUMax();
- const Standard_Real umin = myAttribute->GetUMin();
- const Standard_Real vmax = myAttribute->GetVMax();
- const Standard_Real vmin = myAttribute->GetVMin();
- const Standard_Real deltaX = myAttribute->GetDeltaX();
- const Standard_Real deltaY = myAttribute->GetDeltaY();
- const Standard_Real aDefFace = myAttribute->GetDefFace();
-
- gp_Torus T = myAttribute->Surface()->Torus();
-
- Standard_Boolean insert;
- Standard_Integer i, j, ParamULength, ParamVLength;
- Standard_Real pp, pasu, pasv;
- Standard_Real r = T.MinorRadius(), R = T.MajorRadius();
-
- BRepMesh::SequenceOfReal ParamU, ParamV;
-
- Standard_Real oldDv = GCPnts_TangentialDeflection::ArcAngularStep(
- r, aDefFace, myAngle, myMinSize);
-
- Standard_Real Dv = 0.9*oldDv; //TWOTHIRD * oldDv;
- Dv = oldDv;
-
- Standard_Real Du;
- Standard_Integer nbV = Max((Standard_Integer)((vmax - vmin) / Dv), 2);
- Dv = (vmax - vmin) / (nbV + 1);
- Standard_Real ru = R + r;
- if (ru > 1.e-16)
- {
- Du = GCPnts_TangentialDeflection::ArcAngularStep(
- ru, aDefFace, myAngle, myMinSize);
-
- Standard_Real aa = sqrt(Du*Du + oldDv*oldDv);
- if (aa < gp::Resolution())
- return;
- Du *= Min(oldDv, Du) / aa;
- }
- else Du = Dv;
-
- Standard_Integer nbU = Max((Standard_Integer)((umax - umin) / Du), 2);
- nbU = Max(nbU, (int)(nbV*(umax - umin)*R / ((vmax - vmin)*r) / 5.));
- Du = (umax - umin) / (nbU + 1);
-
- if (R < r)
- {
- // As the points of edges are returned.
- // in this case, the points are not representative.
-
- //-- Choose DeltaX and DeltaY so that to avoid skipping points on the grid
- for (i = 0; i <= nbU; i++) ParamU.Append(umin + i* Du);
- }//R<r
- else //U if R > r
- {
- //--ofv: U
- // Number of mapped U parameters
- const Standard_Integer LenU = myUParam.Extent();
- // Fill array of U parameters
- TColStd_Array1OfReal Up(1, LenU);
- for (j = 1; j <= LenU; j++) Up(j) = myUParam(j);
-
- // Calculate DU, leave array of parameters
- Standard_Real aDU = FUN_CalcAverageDUV(Up, LenU);
- aDU = Max(aDU, Abs(umax - umin) / (Standard_Real)nbU / 2.);
- Standard_Real dUstd = Abs(umax - umin) / (Standard_Real)LenU;
- if (aDU > dUstd) dUstd = aDU;
- // Add U parameters
- for (j = 1; j <= LenU; j++)
- {
- pp = Up(j);
- insert = Standard_True;
- ParamULength = ParamU.Length();
- for (i = 1; i <= ParamULength && insert; i++)
- {
- insert = (Abs(ParamU.Value(i) - pp) > (0.5*dUstd));
- }
- if (insert) ParamU.Append(pp);
- }
- }
-
- //--ofv: V
- // Number of mapped V parameters
- const Standard_Integer LenV = myVParam.Extent();
- // Fill array of V parameters
- TColStd_Array1OfReal Vp(1, LenV);
- for (j = 1; j <= LenV; j++) Vp(j) = myVParam(j);
- // Calculate DV, sort array of parameters
- Standard_Real aDV = FUN_CalcAverageDUV(Vp, LenV);
- aDV = Max(aDV, Abs(vmax - vmin) / (Standard_Real)nbV / 2.);
-
- Standard_Real dVstd = Abs(vmax - vmin) / (Standard_Real)LenV;
- if (aDV > dVstd) dVstd = aDV;
- // Add V parameters
- for (j = 1; j <= LenV; j++)
- {
- pp = Vp(j);
-
- insert = Standard_True;
- ParamVLength = ParamV.Length();
- for (i = 1; i <= ParamVLength && insert; i++)
- {
- insert = (Abs(ParamV.Value(i) - pp) > (dVstd*2. / 3.));
- }
- if (insert) ParamV.Append(pp);
- }
-
- Standard_Integer Lu = ParamU.Length(), Lv = ParamV.Length();
- Standard_Real uminnew = umin + deltaY*0.1;
- Standard_Real vminnew = vmin + deltaX*0.1;
- Standard_Real umaxnew = umax - deltaY*0.1;
- Standard_Real vmaxnew = vmax - deltaX*0.1;
-
- for (i = 1; i <= Lu; i++)
- {
- pasu = ParamU.Value(i);
- if (pasu >= uminnew && pasu < umaxnew)
- {
- for (j = 1; j <= Lv; j++)
- {
- pasv = ParamV.Value(j);
- if (pasv >= vminnew && pasv < vmaxnew)
- {
- tryToInsertAnalyticVertex(gp_Pnt2d(pasu, pasv), T, theNewVertices);
- }
- }
- }
- }
-}
-
-//=======================================================================
-//function : insertInternalVerticesOther
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertInternalVerticesOther(
- BRepMesh::ListOfVertex& theNewVertices)
-{
- const Standard_Real aRange[2][2] = {
- { myAttribute->GetUMax(), myAttribute->GetUMin() },
- { myAttribute->GetVMax(), myAttribute->GetVMin() }
- };
-
- const Standard_Real aDelta[2] = {
- myAttribute->GetDeltaX(),
- myAttribute->GetDeltaY()
- };
-
- const Standard_Real aDefFace = myAttribute->GetDefFace();
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
-
- Handle(NCollection_IncAllocator) anAlloc = new NCollection_IncAllocator;
- BRepMesh::SequenceOfReal aParams[2] = { BRepMesh::SequenceOfReal(anAlloc),
- BRepMesh::SequenceOfReal(anAlloc) };
- for (Standard_Integer i = 0; i < 2; ++i)
- {
- Standard_Boolean isU = (i == 0);
- Standard_Real aRes = isU ?
- gFace->UResolution(aDefFace) :
- gFace->VResolution(aDefFace);
-
- // Sort and filter sequence of parameters
- Standard_Real aMinDiff = Precision::PConfusion();
- if (aDelta[i] < 1.)
- aMinDiff /= aDelta[i];
-
- aMinDiff = Max(myMinSize, aMinDiff);
-
- Standard_Real aRangeDiff = aRange[i][0] - aRange[i][1];
- Standard_Real aDiffMaxLim = 0.1 * aRangeDiff;
- Standard_Real aDiffMinLim = Max(0.005 * aRangeDiff, 2. * aRes);
- Standard_Real aDiff = Max(myMinSize, Min(aDiffMaxLim, aDiffMinLim));
- filterParameters(isU ? myUParam : myVParam, aMinDiff, aDiff, aParams[i]);
- }
-
- // check intermediate isolines
- Handle (Geom_Surface) aSurface = gFace->ChangeSurface ().Surface ().Surface ();
-
- BRepMesh::MapOfReal aParamsToRemove[2] = { BRepMesh::MapOfReal(1, anAlloc),
- BRepMesh::MapOfReal(1, anAlloc) };
- BRepMesh::MapOfReal aParamsForbiddenToRemove[2] = { BRepMesh::MapOfReal(1, anAlloc),
- BRepMesh::MapOfReal(1, anAlloc) };
-
- // insert additional points where it is needed to conform criteria.
- // precision for normals calculation
- const Standard_Real aNormPrec = Precision::Confusion();
- for (Standard_Integer k = 0; k < 2; ++k)
- {
- const Standard_Integer aOtherIndex = (k + 1) % 2;
- BRepMesh::SequenceOfReal& aParams1 = aParams[k];
- BRepMesh::SequenceOfReal& aParams2 = aParams[aOtherIndex];
- const Standard_Boolean isU = (k == 0);
- for (Standard_Integer i = 2; i < aParams1.Length(); ++i)
- {
- const Standard_Real aParam1 = aParams1(i);
- GeomAdaptor_Curve aIso(isU ?
- aSurface->UIso(aParam1) : aSurface->VIso(aParam1));
-
- Standard_Real aPrevParam2 = aParams2(1);
- gp_Pnt aPrevPnt2;
- gp_Vec aPrevVec2;
- aIso.D1(aPrevParam2, aPrevPnt2, aPrevVec2);
- for (Standard_Integer j = 2; j <= aParams2.Length();)
- {
- Standard_Real aParam2 = aParams2(j);
- gp_Pnt aPnt2;
- gp_Vec aVec2;
- aIso.D1(aParam2, aPnt2, aVec2);
-
- Standard_Real aMidParam = 0.5 * (aPrevParam2 + aParam2);
- gp_Pnt aMidPnt = aIso.Value(aMidParam);
-
- Standard_Real aDist = deflectionOfSegment(aPrevPnt2, aPnt2, aMidPnt);
- if (aDist > aDefFace && aDist > myMinSize)
- {
- // insertion
- aParams2.InsertBefore(j, aMidParam);
- continue;
- }
- //put regular grig for normals
- gp_Pnt2d aStPnt1, aStPnt2;
- if (isU)
- {
- aStPnt1 = gp_Pnt2d(aParam1, aPrevParam2);
- aStPnt2 = gp_Pnt2d(aParam1, aMidParam);
- }
- else
- {
- aStPnt1 = gp_Pnt2d(aPrevParam2, aParam1);
- aStPnt2 = gp_Pnt2d(aMidParam, aParam1);
- }
-
- gp_Dir N1(0, 0, 1), N2(0, 0, 1);
- Standard_Integer aSt1 = GeomLib::NormEstim(aSurface, aStPnt1, aNormPrec, N1);
- Standard_Integer aSt2 = GeomLib::NormEstim(aSurface, aStPnt2, aNormPrec, N2);
-
- const Standard_Real aAngle = N2.Angle(N1);
- if (aSt1 < 1 && aSt2 < 1 && aAngle > myAngle)
- {
- const Standard_Real aLen = GCPnts_AbscissaPoint::Length(
- aIso, aPrevParam2, aMidParam, aDefFace);
-
- if (aLen > myMinSize)
- {
- // insertion
- aParams2.InsertBefore(j, aMidParam);
- continue;
- }
- }
- aPrevParam2 = aParam2;
- aPrevPnt2 = aPnt2;
- aPrevVec2 = aVec2;
-
- ++j;
- }
- }
- }
-#ifdef DEBUG_InsertInternal
- // output numbers of parameters along U and V
- cout << "aParams: " << aParams[0].Length() << " " << aParams[1].Length() << endl;
-#endif
- // try to reduce number of points evaluating of isolines sampling
- for (Standard_Integer k = 0; k < 2; ++k)
- {
- const Standard_Integer aOtherIndex = (k + 1) % 2;
- BRepMesh::SequenceOfReal& aParams1 = aParams[k];
- BRepMesh::SequenceOfReal& aParams2 = aParams[aOtherIndex];
- const Standard_Boolean isU = (k == 0);
- BRepMesh::MapOfReal& aToRemove2 = aParamsToRemove[aOtherIndex];
- BRepMesh::MapOfReal& aForbiddenToRemove1 = aParamsForbiddenToRemove[k];
- BRepMesh::MapOfReal& aForbiddenToRemove2 = aParamsForbiddenToRemove[aOtherIndex];
- for (Standard_Integer i = 2; i < aParams1.Length(); ++i)
- {
- const Standard_Real aParam1 = aParams1(i);
- GeomAdaptor_Curve aIso(isU ?
- aSurface->UIso (aParam1) : aSurface->VIso (aParam1));
-#ifdef DEBUG_InsertInternal
- // write polyline containing initial parameters to the file
- {
- ofstream ff(DEBUG_InsertInternal, std::ios_base::app);
- ff << "polyline " << (k == 0 ? "u" : "v") << i << " ";
- for (Standard_Integer j = 1; j <= aParams2.Length(); j++)
- {
- gp_Pnt aP;
- aIso.D0(aParams2(j), aP);
- ff << aP.X() << " " << aP.Y() << " " << aP.Z() << " ";
- }
- ff << endl;
- }
-#endif
-
- Standard_Real aPrevParam2 = aParams2(1);
- gp_Pnt aPrevPnt2;
- gp_Vec aPrevVec2;
- aIso.D1 (aPrevParam2, aPrevPnt2, aPrevVec2);
- for (Standard_Integer j = 2; j <= aParams2.Length();)
- {
- Standard_Real aParam2 = aParams2(j);
- gp_Pnt aPnt2;
- gp_Vec aVec2;
- aIso.D1 (aParam2, aPnt2, aVec2);
-
- // Here we should leave at least 3 parameters as far as
- // we must have at least one parameter related to surface
- // internals in order to prevent movement of triangle body
- // outside the surface in case of highly curved ones, e.g.
- // BSpline springs.
- if (aParams2.Length() > 3 && j < aParams2.Length())
- {
- // Remove too dense points
- const Standard_Real aNextParam = aParams2(j + 1);
- gp_Pnt aNextPnt;
- gp_Vec aNextVec;
- aIso.D1(aNextParam, aNextPnt, aNextVec);
-
- // Lets check current parameter.
- // If it fits deflection, we can remove it.
- Standard_Real aDist = deflectionOfSegment(aPrevPnt2, aNextPnt, aPnt2);
- if (aDist < aDefFace)
- {
- // Lets check parameters for angular deflection.
- if (aPrevVec2.SquareMagnitude() > gp::Resolution() &&
- aNextVec.SquareMagnitude() > gp::Resolution() &&
- aPrevVec2.Angle(aNextVec) < myAngle)
- {
- // For current Iso line we can remove this parameter.
-#ifdef DEBUG_InsertInternal
- // write point of removed parameter
- {
- ofstream ff(DEBUG_InsertInternal, std::ios_base::app);
- ff << "point " << (k == 0 ? "u" : "v") << i << "r_" << j << " "
- << aPnt2.X() << " " << aPnt2.Y() << " " << aPnt2.Z() << endl;
- }
-#endif
- aToRemove2.Add(aParam2);
- aPrevParam2 = aNextParam;
- aPrevPnt2 = aNextPnt;
- aPrevVec2 = aNextVec;
- j += 2;
- continue;
- }
- else {
- // We have found a place on the surface refusing
- // removement of this parameter.
-#ifdef DEBUG_InsertInternal
- // write point of forbidden to remove parameter
- {
- ofstream ff(DEBUG_InsertInternal, std::ios_base::app);
- ff << "vertex " << (k == 0 ? "u" : "v") << i << "f_" << j << " "
- << aPnt2.X() << " " << aPnt2.Y() << " " << aPnt2.Z() << endl;
- }
-#endif
- aForbiddenToRemove1.Add(aParam1);
- aForbiddenToRemove2.Add(aParam2);
- }
- }
- }
- aPrevParam2 = aParam2;
- aPrevPnt2 = aPnt2;
- aPrevVec2 = aVec2;
- ++j;
- }
- }
- }
- // remove filtered out parameters
- for (Standard_Integer k = 0; k < 2; ++k)
- {
- BRepMesh::SequenceOfReal& aParamsk = aParams[k];
- for (Standard_Integer i = 1; i <= aParamsk.Length();)
- {
- const Standard_Real aParam = aParamsk.Value(i);
- if (aParamsToRemove[k].Contains(aParam) &&
- !aParamsForbiddenToRemove[k].Contains(aParam))
- {
- aParamsk.Remove(i);
- }
- else
- i++;
- }
- }
-#ifdef DEBUG_InsertInternal
- // write polylines containing remaining parameters
- {
- ofstream ff(DEBUG_InsertInternal, std::ios_base::app);
- for (Standard_Integer k = 0; k < 2; ++k)
- {
- for (Standard_Integer i = 1; i <= aParams[k].Length(); i++)
- {
- ff << "polyline " << (k == 0 ? "uo" : "vo") << i << " ";
- for (Standard_Integer j = 1; j <= aParams[1 - k].Length(); j++)
- {
- gp_Pnt aP;
- if (k == 0)
- gFace->D0(aParams[k](i), aParams[1 - k](j), aP);
- else
- gFace->D0(aParams[1 - k](j), aParams[k](i), aP);
- ff << aP.X() << " " << aP.Y() << " " << aP.Z() << " ";
- }
- ff << endl;
- }
- }
- }
-#endif
-
- // insert nodes of the regular grid
- const BRepMesh::HClassifier& aClassifier = myAttribute->ChangeClassifier();
- for (Standard_Integer i = 1; i <= aParams[0].Length(); ++i)
- {
- const Standard_Real aParam1 = aParams[0].Value (i);
- for (Standard_Integer j = 1; j <= aParams[1].Length(); ++j)
- {
- const Standard_Real aParam2 = aParams[1].Value (j);
- gp_Pnt2d aPnt2d(aParam1, aParam2);
-
- // Classify intersection point
- if (aClassifier->Perform(aPnt2d) == TopAbs_IN)
- {
- gp_Pnt aPnt;
- gFace->D0(aPnt2d.X(), aPnt2d.Y(), aPnt);
- insertVertex(aPnt, aPnt2d.Coord(), theNewVertices);
- }
- }
- }
-}
-
-//=======================================================================
-//function : checkDeflectionAndInsert
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_FastDiscretFace::checkDeflectionAndInsert(
- const gp_Pnt& thePnt3d,
- const gp_XY& theUV,
- const Standard_Boolean isDeflectionCheckOnly,
- const Standard_Real theTriangleDeflection,
- const Standard_Real theFaceDeflection,
- const BRepMesh_CircleTool& theCircleTool,
- BRepMesh::ListOfVertex& theVertices,
- Standard_Real& theMaxTriangleDeflection,
- const Handle(NCollection_IncAllocator)& theTempAlloc)
-{
- if (theTriangleDeflection > theMaxTriangleDeflection)
- theMaxTriangleDeflection = theTriangleDeflection;
-
- if (theTriangleDeflection < theFaceDeflection)
- return Standard_True;
-
- if (myMinSize > Precision::Confusion())
- {
- // Iterator in the list of indexes of circles containing the node
- BRepMesh::ListOfInteger& aCirclesList =
- const_cast<BRepMesh_CircleTool&>(theCircleTool).Select(
- myAttribute->Scale(theUV, Standard_True));
-
- BRepMesh::MapOfInteger aUsedNodes(10, theTempAlloc);
- BRepMesh::ListOfInteger::Iterator aCircleIt(aCirclesList);
- for (; aCircleIt.More(); aCircleIt.Next())
- {
- const BRepMesh_Triangle& aTriangle =
- myStructure->GetElement(aCircleIt.Value());
-
- Standard_Integer aNodes[3];
- myStructure->ElementNodes(aTriangle, aNodes);
-
- for (Standard_Integer i = 0; i < 3; ++i)
- {
- const Standard_Integer aNodeId = aNodes[i];
- if (aUsedNodes.Contains(aNodeId))
- continue;
-
- aUsedNodes.Add(aNodeId);
- const BRepMesh_Vertex& aNode = myStructure->GetNode(aNodeId);
- const gp_Pnt& aPoint = myAttribute->GetPoint(aNode);
-
- if (thePnt3d.SquareDistance(aPoint) < myMinSize * myMinSize)
- return Standard_True;
- }
- }
- }
-
- if (isDeflectionCheckOnly)
- return Standard_False;
-
- insertVertex(thePnt3d, theUV, theVertices);
- return Standard_True;
-}
-
-//=======================================================================
-//function : control
-//purpose :
-//=======================================================================
-Standard_Real BRepMesh_FastDiscretFace::control(
- BRepMesh_Delaun& theTrigu,
- const Standard_Boolean theIsFirst)
-{
- Standard_Integer aTrianglesNb = myStructure->ElementsOfDomain().Extent();
- if (aTrianglesNb < 1)
- return -1.0;
-
- //IMPORTANT: Constants used in calculations
- const Standard_Real MinimalArea2d = 1.e-9;
- const Standard_Real MinimalSqLength3d = 1.e-12;
- const Standard_Real aSqDefFace = myAttribute->GetDefFace() * myAttribute->GetDefFace();
-
- const Handle(BRepAdaptor_HSurface)& gFace = myAttribute->Surface();
-
- Handle(Geom_Surface) aBSpline;
- const GeomAbs_SurfaceType aSurfType = gFace->GetType ();
- if (IsCompexSurface (aSurfType) && aSurfType != GeomAbs_SurfaceOfExtrusion)
- aBSpline = gFace->ChangeSurface ().Surface().Surface();
-
- Handle(NCollection_IncAllocator) anAlloc =
- new NCollection_IncAllocator(BRepMesh::MEMORY_BLOCK_SIZE_HUGE);
- NCollection_DataMap<Standard_Integer, gp_Dir> aNorMap(1, anAlloc);
- BRepMesh::MapOfIntegerInteger aStatMap(1, anAlloc);
- NCollection_Map<BRepMesh_Edge> aCouples(3 * aTrianglesNb, anAlloc);
- const BRepMesh_CircleTool& aCircles = theTrigu.Circles();
-
- // Perform refinement passes
- // Define the number of iterations
- Standard_Integer aIterationsNb = 11;
- const Standard_Integer aPassesNb = (theIsFirst ? 1 : aIterationsNb);
- // Initialize stop condition
- Standard_Real aMaxSqDef = -1.;
- Standard_Integer aPass = 1, aInsertedNb = 1;
- Standard_Boolean isAllDegenerated = Standard_False;
- Handle(NCollection_IncAllocator) aTempAlloc =
- new NCollection_IncAllocator(BRepMesh::MEMORY_BLOCK_SIZE_HUGE);
- for (; aPass <= aPassesNb && aInsertedNb && !isAllDegenerated; ++aPass)
- {
- aTempAlloc->Reset(Standard_False);
- BRepMesh::ListOfVertex aNewVertices(aTempAlloc);
-
- // Reset stop condition
- aInsertedNb = 0;
- aMaxSqDef = -1.;
- isAllDegenerated = Standard_True;
-
- aTrianglesNb = myStructure->ElementsOfDomain().Extent();
- if (aTrianglesNb < 1)
- break;
-
- // Iterate on current triangles
- const BRepMesh::MapOfInteger& aTriangles = myStructure->ElementsOfDomain();
- BRepMesh::MapOfInteger::Iterator aTriangleIt(aTriangles);
- for (; aTriangleIt.More(); aTriangleIt.Next())
- {
- const Standard_Integer aTriangleId = aTriangleIt.Key();
- const BRepMesh_Triangle& aCurrentTriangle = myStructure->GetElement(aTriangleId);
-
- if (aCurrentTriangle.Movability() == BRepMesh_Deleted)
- continue;
-
- Standard_Integer v[3];
- myStructure->ElementNodes(aCurrentTriangle, v);
-
- Standard_Integer e[3];
- Standard_Boolean o[3];
- aCurrentTriangle.Edges(e, o);
-
- gp_XY xy[3];
- gp_XYZ p[3];
- Standard_Boolean m[3];
- for (Standard_Integer i = 0; i < 3; ++i)
- {
- m[i] = (myStructure->GetLink(e[i]).Movability() == BRepMesh_Frontier);
-
- const BRepMesh_Vertex& aVertex = myStructure->GetNode(v[i]);
- xy[i] = myAttribute->Scale(aVertex.Coord(), Standard_False);
- p [i] = myAttribute->GetPoint(aVertex).Coord();
- }
-
- gp_XYZ aLinkVec[3];
- Standard_Boolean isDegeneratedTri = Standard_False;
- for (Standard_Integer i = 0; i < 3 && !isDegeneratedTri; ++i)
- {
- aLinkVec[i] = p[(i + 1) % 3] - p[i];
- isDegeneratedTri = (aLinkVec[i].SquareModulus() < MinimalSqLength3d);
- }
-
- if (isDegeneratedTri)
- continue;
-
- isAllDegenerated = Standard_False;
-
- // Check triangle area in 2d
- if (Abs((xy[1]-xy[0])^(xy[2]-xy[1])) < MinimalArea2d)
- continue;
-
- // Check triangle normal
- gp_Pnt pDef;
- Standard_Real aSqDef = -1.;
- Standard_Boolean isSkipped = Standard_False;
- gp_XYZ normal(aLinkVec[0] ^ aLinkVec[1]);
- if (normal.SquareModulus () < gp::Resolution())
- continue;
-
- normal.Normalize();
-
- // Check deflection at triangle centroid
- gp_XY aCenter2d = (xy[0] + xy[1] + xy[2]) / 3.0;
- gFace->D0(aCenter2d.X(), aCenter2d.Y(), pDef);
- aSqDef = Abs(normal * (pDef.XYZ() - p[0]));
- aSqDef *= aSqDef;
-
- isSkipped = !checkDeflectionAndInsert(pDef, aCenter2d, theIsFirst,
- aSqDef, aSqDefFace, aCircles, aNewVertices, aMaxSqDef, aTempAlloc);
-
- if (isSkipped)
- break;
-
- // Check deflection at triangle links
- for (Standard_Integer i = 0; i < 3 && !isSkipped; ++i)
- {
- if (m[i]) // is a boundary
- continue;
-
- // Check if this link was already processed
- if (aCouples.Add(myStructure->GetLink(e[i])))
- {
- // Check deflection on edge 1
- Standard_Integer j = (i + 1) % 3;
- gp_XY mi2d = (xy[i] + xy[j]) * 0.5;
- gFace->D0(mi2d.X(), mi2d.Y(), pDef);
- gp_Lin aLin(p[i], gp_Vec(p[i], p[j]));
- aSqDef = aLin.SquareDistance(pDef);
-
- isSkipped = !checkDeflectionAndInsert(pDef, mi2d, theIsFirst,
- aSqDef, aSqDefFace, aCircles, aNewVertices, aMaxSqDef, aTempAlloc);
- }
- }
-
- if (isSkipped)
- break;
-
- //check normal on bsplines
- if (theIsFirst && !aBSpline.IsNull())
- {
- gp_Dir N[3] = { gp::DZ(), gp::DZ(), gp::DZ() };
- Standard_Integer aSt[3];
-
- for (Standard_Integer i = 0; i < 3; ++i)
- {
- if (aNorMap.IsBound(v[i]))
- {
- aSt[i] = aStatMap.Find(v[i]);
- N[i] = aNorMap.Find(v[i]);
- }
- else
- {
- aSt[i] = GeomLib::NormEstim(aBSpline, gp_Pnt2d(xy[i]), Precision::Confusion(), N[i]);
- aStatMap.Bind(v[i], aSt[i]);
- aNorMap.Bind(v[i], N[i]);
- }
- }
-
- Standard_Real aAngle[3];
- for (Standard_Integer i = 0; i < 3; ++i)
- aAngle[i] = N[(i + 1) % 3].Angle(N[i]);
-
- if (aSt[0] < 1 && aSt[1] < 1 && aSt[2] < 1)
- {
- if (aAngle[0] > myAngle || aAngle[1] > myAngle || aAngle[2] > myAngle)
- {
- aMaxSqDef = -1.;
- break;
- }
- }
- }
- }
-
- if (theIsFirst)
- continue;
-
-#ifdef DEBUG_MESH
- // append to the file triangles in the form of polyline commands;
- // so the file can be sourced in draw to analyze triangles on each pass of the algorithm.
- // write triangles
- ofstream ftt(DEBUG_MESH, std::ios_base::app);
- Standard_Integer nbElem = myStructure->NbElements();
- for (Standard_Integer i = 1; i <= nbElem; i++)
- {
- const BRepMesh_Triangle& aTri = myStructure->GetElement(i);
- if (aTri.Movability() == BRepMesh_Deleted)
- continue;
- Standard_Integer n[3];
- myStructure->ElementNodes(aTri, n);
- const BRepMesh_Vertex& aV1 = myStructure->GetNode(n[0]);
- const BRepMesh_Vertex& aV2 = myStructure->GetNode(n[1]);
- const BRepMesh_Vertex& aV3 = myStructure->GetNode(n[2]);
- const gp_Pnt& aP1 = myAttribute->GetPoint(aV1);
- const gp_Pnt& aP2 = myAttribute->GetPoint(aV2);
- const gp_Pnt& aP3 = myAttribute->GetPoint(aV3);
- ftt << "polyline t" << aPass << "_" << i << " "
- << aP1.X() << " " << aP1.Y() << " " << aP1.Z() << " "
- << aP2.X() << " " << aP2.Y() << " " << aP2.Z() << " "
- << aP3.X() << " " << aP3.Y() << " " << aP3.Z() << " "
- << aP1.X() << " " << aP1.Y() << " " << aP1.Z() << endl;
- }
- // write points to insert on the current pass
- BRepMesh::ListOfVertex::Iterator it(aNewVertices);
- for (Standard_Integer i=1; it.More(); it.Next(), i++)
- {
- const BRepMesh_Vertex& aVertex = it.Value();
- const gp_Pnt& aP = myAttribute->GetPoint(aVertex);
- ftt << "vertex vt" << aPass << "_" << i << " "
- << aP.X() << " " << aP.Y() << " " << aP.Z() << endl;
- }
-#endif
-
- if (addVerticesToMesh(aNewVertices, theTrigu))
- ++aInsertedNb;
- }
-
- return (aMaxSqDef < 0) ? aMaxSqDef : Sqrt(aMaxSqDef);
-}
-
-//=======================================================================
-//function : add
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::add(const TopoDS_Vertex& theVertex)
-{
- if (theVertex.Orientation() != TopAbs_INTERNAL)
- return;
-
- try
- {
- OCC_CATCH_SIGNALS
-
- gp_Pnt2d aPnt2d = BRep_Tool::Parameters(theVertex, myAttribute->Face());
- // check UV values for internal vertices
- if (myAttribute->ChangeClassifier()->Perform(aPnt2d) != TopAbs_IN)
- return;
-
- NCollection_Handle<FixedVExplorer> aFixedVExplorer = new FixedVExplorer(theVertex);
- Standard_Integer aIndex = myAttribute->GetVertexIndex(aFixedVExplorer);
- gp_XY anUV = BRepMesh_ShapeTool::FindUV(aIndex, aPnt2d,
- BRep_Tool::Tolerance(theVertex), myAttribute);
-
- Standard_Integer aTmpId1, aTmpId2;
- anUV = myAttribute->Scale(anUV, Standard_True);
- myAttribute->AddNode(aIndex, anUV, BRepMesh_Fixed, aTmpId1, aTmpId2);
- }
- catch (Standard_Failure)
- {
- }
-}
-
-//=======================================================================
-//function : insertVertex
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::insertVertex(
- const gp_Pnt& thePnt3d,
- const gp_XY& theUV,
- BRepMesh::ListOfVertex& theVertices)
-{
- Standard_Integer aNbLocat = myAttribute->LastPointId();
- myAttribute->ChangeSurfacePoints()->Bind(++aNbLocat, thePnt3d);
-
- gp_XY aPnt2d = myAttribute->Scale(theUV, Standard_True);
- BRepMesh_Vertex aVertex(aPnt2d, aNbLocat, BRepMesh_Free);
- theVertices.Append(aVertex);
-}
-
-//=======================================================================
-//function : commitSurfaceTriangulation
-//purpose :
-//=======================================================================
-void BRepMesh_FastDiscretFace::commitSurfaceTriangulation()
-{
- if (myAttribute.IsNull() || !myAttribute->IsValid())
- return;
-
- const TopoDS_Face& aFace = myAttribute->Face();
- BRepMesh_ShapeTool::NullifyFace(aFace);
-
- Handle(BRepMesh_DataStructureOfDelaun)& aStructure = myAttribute->ChangeStructure();
- const BRepMesh::MapOfInteger& aTriangles = aStructure->ElementsOfDomain();
-
- if (aTriangles.IsEmpty())
- {
- myAttribute->SetStatus(BRepMesh_Failure);
- return;
- }
-
- BRepMesh::HIMapOfInteger& aVetrexEdgeMap = myAttribute->ChangeVertexEdgeMap();
-
- // Store triangles
- Standard_Integer aVerticesNb = aVetrexEdgeMap->Extent();
- Standard_Integer aTrianglesNb = aTriangles.Extent();
- Handle(Poly_Triangulation) aNewTriangulation =
- new Poly_Triangulation(aVerticesNb, aTrianglesNb, Standard_True);
-
- Poly_Array1OfTriangle& aPolyTrianges = aNewTriangulation->ChangeTriangles();
-
- Standard_Integer aTriangeId = 1;
- BRepMesh::MapOfInteger::Iterator aTriIt(aTriangles);
- for (; aTriIt.More(); aTriIt.Next())
- {
- const BRepMesh_Triangle& aCurElem = aStructure->GetElement(aTriIt.Key());
-
- Standard_Integer aNode[3];
- aStructure->ElementNodes(aCurElem, aNode);
-
- Standard_Integer aNodeId[3];
- for (Standard_Integer i = 0; i < 3; ++i)
- aNodeId[i] = aVetrexEdgeMap->FindIndex(aNode[i]);
-
- aPolyTrianges(aTriangeId++).Set(aNodeId[0], aNodeId[1], aNodeId[2]);
- }
-
- // Store mesh nodes
- TColgp_Array1OfPnt& aNodes = aNewTriangulation->ChangeNodes();
- TColgp_Array1OfPnt2d& aNodes2d = aNewTriangulation->ChangeUVNodes();
-
- for (Standard_Integer i = 1; i <= aVerticesNb; ++i)
- {
- Standard_Integer aVertexId = aVetrexEdgeMap->FindKey(i);
- const BRepMesh_Vertex& aVertex = aStructure->GetNode(aVertexId);
- const gp_Pnt& aPoint = myAttribute->GetPoint(aVertex);
-
- aNodes(i) = aPoint;
- aNodes2d(i) = aVertex.Coord();
- }
-
- aNewTriangulation->Deflection(myAttribute->GetDefFace());
- BRepMesh_ShapeTool::AddInFace(aFace, aNewTriangulation);
-
- // Delete unused data
- myUParam.Clear(0L);
- myVParam.Clear(0L);
- myAttribute->ChangeStructure().Nullify();
- myAttribute->ChangeSurfacePoints().Nullify();
- myAttribute->ChangeSurfaceVertices().Nullify();
-
- myAttribute->ChangeClassifier().Nullify();
- myAttribute->ChangeLocation2D().Nullify();
- myAttribute->ChangeVertexEdgeMap().Nullify();
-}
+++ /dev/null
-// Copyright (c) 2013 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_FastDiscretFace_HeaderFile
-#define _BRepMesh_FastDiscretFace_HeaderFile
-
-#include <Standard.hxx>
-#include <Standard_Type.hxx>
-#include <BRepMesh_FastDiscretFace.hxx>
-#include <BRepMesh_DataStructureOfDelaun.hxx>
-#include <BRepMesh.hxx>
-#include <BRepMesh_FaceAttribute.hxx>
-#include <Standard_Transient.hxx>
-#include <TopTools_MutexForShapeProvider.hxx>
-#include <TopTools_DataMapOfShapeReal.hxx>
-#include <BRepMesh_Delaun.hxx>
-#include <BRepMesh_Triangle.hxx>
-#include <BRepMesh_Classifier.hxx>
-#include <ElSLib.hxx>
-
-class BRepMesh_DataStructureOfDelaun;
-class BRepMesh_FaceAttribute;
-class TopoDS_Face;
-class TopoDS_Vertex;
-class BRepAdaptor_HSurface;
-class TopoDS_Edge;
-class Poly_Triangulation;
-class TopLoc_Location;
-class gp_XY;
-class gp_Pnt2d;
-class BRepMesh_Edge;
-class BRepMesh_Vertex;
-class gp_Pnt;
-
-//! Algorithm to mesh a face with respect of the frontier
-//! the deflection and by option the shared components.
-class BRepMesh_FastDiscretFace : public Standard_Transient
-{
-public:
-
- //! Constructor.
- //! @param theAngle deviation angle to be used for surface tessellation.
- //! @param isInternalVerticesMode flag enabling/disabling internal
- //! vertices mode.
- //! @param isControlSurfaceDeflection enables/disables adaptive
- //! reconfiguration of mesh.
- Standard_EXPORT BRepMesh_FastDiscretFace(
- const Standard_Real theAngle,
- const Standard_Real theMinSize,
- const Standard_Boolean isInternalVerticesMode,
- const Standard_Boolean isControlSurfaceDeflection);
-
- Standard_EXPORT void Perform(const Handle(BRepMesh_FaceAttribute)& theAttribute);
-
- DEFINE_STANDARD_RTTIEXT(BRepMesh_FastDiscretFace,Standard_Transient)
-
-private:
-
- void add(const Handle(BRepMesh_FaceAttribute)& theAttribute);
- void add(const TopoDS_Vertex& theVertex);
-
- Standard_Real control(BRepMesh_Delaun& theMeshBuilder,
- const Standard_Boolean theIsFirst);
-
- //! Registers the given nodes in mesh data structure and
- //! performs refinement of existing mesh.
- //! @param theVertices nodes to be inserted.
- //! @param theMeshBuilder initialized tool refining mesh
- //! in respect to inserting nodes.
- //! @return TRUE if vertices were been inserted, FALSE elewhere.
- Standard_Boolean addVerticesToMesh(
- const BRepMesh::ListOfVertex& theVertices,
- BRepMesh_Delaun& theMeshBuilder);
-
- //! Calculates nodes lying on face's surface and inserts them to a mesh.
- //! @param theMeshBuilder initialized tool refining mesh
- //! in respect to inserting nodes.
- void insertInternalVertices(BRepMesh_Delaun& theMeshBuilder);
-
- //! Calculates nodes lying on spherical surface.
- //! @param theNewVertices list of vertices to be extended and added to mesh.
- void insertInternalVerticesSphere(BRepMesh::ListOfVertex& theNewVertices);
-
- //! Calculates nodes lying on cylindrical surface.
- //! @param theNewVertices list of vertices to be extended and added to mesh.
- void insertInternalVerticesCylinder(BRepMesh::ListOfVertex& theNewVertices);
-
- //! Calculates nodes lying on conical surface.
- //! @param theNewVertices list of vertices to be extended and added to mesh.
- void insertInternalVerticesCone(BRepMesh::ListOfVertex& theNewVertices);
-
- //! Calculates nodes lying on toroidal surface.
- //! @param theNewVertices list of vertices to be extended and added to mesh.
- void insertInternalVerticesTorus(BRepMesh::ListOfVertex& theNewVertices);
-
- //! Calculates nodes lying on custom-type surface.
- //! @param theNewVertices list of vertices to be extended and added to mesh.
- void insertInternalVerticesOther(BRepMesh::ListOfVertex& theNewVertices);
-
- //! Template method trying to insert new internal vertex corresponded to
- //! the given 2d point. Calculates 3d position analytically using the given
- //! surface.
- //! @param thePnt2d 2d point to be inserted to the list.
- //! @param theAnalyticSurface analytic surface to calculate 3d point.
- //! @param[out] theVertices list of vertices to be updated.
- template<class AnalyticSurface>
- void tryToInsertAnalyticVertex(const gp_Pnt2d& thePnt2d,
- const AnalyticSurface& theAnalyticSurface,
- BRepMesh::ListOfVertex& theVertices)
- {
- const BRepMesh::HClassifier& aClassifier = myAttribute->ChangeClassifier();
- if (aClassifier->Perform(thePnt2d) != TopAbs_IN)
- return;
-
- gp_Pnt aPnt;
- ElSLib::D0(thePnt2d.X(), thePnt2d.Y(), theAnalyticSurface, aPnt);
- insertVertex(aPnt, thePnt2d.Coord(), theVertices);
- }
-
- //! Creates new vertex with the given parameters.
- //! @param thePnt3d 3d point corresponded to the vertex.
- //! @param theUV UV point corresponded to the vertex.
- //! @param[out] theVertices list of vertices to be updated.
- void insertVertex(const gp_Pnt& thePnt3d,
- const gp_XY& theUV,
- BRepMesh::ListOfVertex& theVertices);
-
- //! Stores mesh into the face (without internal edges).
- void commitSurfaceTriangulation();
-
- //! Performs initialization of data structure using existing data.
- void initDataStructure();
-
- //! Adds new link to the mesh data structure.
- //! Movability of the link and order of nodes depend on orientation parameter.
- void addLinkToMesh(const Standard_Integer theFirstNodeId,
- const Standard_Integer theLastNodeId,
- const TopAbs_Orientation theOrientation);
-
- //! Inserts new node into a mesh in case if smoothed region build
- //! using the given node has better deflection metrics than source state.
- //! @param thePnt3d 3d point corresponded to the vertex.
- //! @param theUV UV point corresponded to the vertex.
- //! @param isDeflectionCheckOnly if TRUE new node will not be added to a mesh
- //! even if deflection parameter is better.
- //! @param theTriangleDeflection deflection of a triangle from real geometry.
- //! @param theFaceDeflection deflection to be achieved.
- //! @param theCircleTool tool used for fast extraction of triangles
- //! touched by the given point.
- //! @param[out] theVertices list of vertices to be updated.
- //! @param[in out] theMaxTriangleDeflection maximal deflection of a mesh.
- //! @return TRUE in case if the given deflection of triangle is fine and
- //! there is no necessity to insert new node or new node was being inserted
- //! successfully, FALSE in case if new configuration is better but
- //! isDeflectionCheckOnly flag is set.
- Standard_Boolean checkDeflectionAndInsert(
- const gp_Pnt& thePnt3d,
- const gp_XY& theUV,
- const Standard_Boolean isDeflectionCheckOnly,
- const Standard_Real theTriangleDeflection,
- const Standard_Real theFaceDeflection,
- const BRepMesh_CircleTool& theCircleTool,
- BRepMesh::ListOfVertex& theVertices,
- Standard_Real& theMaxTriangleDeflection,
- const Handle(NCollection_IncAllocator)& theTempAlloc);
-
-private:
-
- Standard_Real myAngle;
- Standard_Boolean myInternalVerticesMode;
- BRepMesh::IMapOfReal myUParam;
- BRepMesh::IMapOfReal myVParam;
-
- // Fast access to attributes of current face
- Handle(BRepMesh_FaceAttribute) myAttribute;
- Handle(BRepMesh_DataStructureOfDelaun) myStructure;
-
- Standard_Real myMinSize;
- Standard_Boolean myIsControlSurfaceDeflection;
-};
-
-DEFINE_STANDARD_HANDLE (BRepMesh_FastDiscretFace, Standard_Transient)
-
-#endif
+++ /dev/null
-// Created on: 2014-08-13
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_IEdgeTool.hxx>
-
-
-
-IMPLEMENT_STANDARD_RTTIEXT(BRepMesh_IEdgeTool,Standard_Transient)
\ No newline at end of file
+++ /dev/null
-// Created on: 2014-08-13
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_IEdgeTool_HeaderFile
-#define _BRepMesh_IEdgeTool_HeaderFile
-
-#include <Standard.hxx>
-#include <gp_Pnt.hxx>
-#include <gp_Pnt2d.hxx>
-#include <Standard_Transient.hxx>
-
-//! Interface class providing API for edge tessellation tools.
-class BRepMesh_IEdgeTool : public Standard_Transient
-{
-public:
- //! Returns number of tessellation points.
- virtual Standard_Integer NbPoints() const = 0;
-
- //! Returns parameters of solution with the given index.
- //! @param theIndex index of tessellation point.
- //! @param theParameter parameters on PCurve corresponded to the solution.
- //! @param thePoint tessellation point.
- //! @param theUV coordinates of tessellation point in parametric space of face.
- //! @return True in case of valid result, false elewhere.
- virtual Standard_Boolean Value(
- const Standard_Integer theIndex,
- Standard_Real& theParameter,
- gp_Pnt& thePoint,
- gp_Pnt2d& theUV) = 0;
-
- DEFINE_STANDARD_RTTIEXT(BRepMesh_IEdgeTool,Standard_Transient)
-};
-
-DEFINE_STANDARD_HANDLE(BRepMesh_IEdgeTool, Standard_Transient)
-
-#endif
+++ /dev/null
-// Copyright (c) 2013 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_PairOfPolygon_HeaderFile
-#define _BRepMesh_PairOfPolygon_HeaderFile
-
-#include <Standard.hxx>
-#include <Standard_DefineAlloc.hxx>
-#include <Standard_Macro.hxx>
-
-class Poly_PolygonOnTriangulation;
-
-class BRepMesh_PairOfPolygon
-{
-public:
-
- DEFINE_STANDARD_ALLOC
-
- //! Constructor. Creates empty pair with null fileds.
- BRepMesh_PairOfPolygon()
- {
- }
-
- //! Clears pair handles.
- inline void Clear()
- {
- myFirst.Nullify();
- myLast.Nullify();
- }
-
- //! Sets the first element of the pair.
- //! If last element is empty, also assignes the given polygon to it.
- //! @param thePolygon plygon to be set.
- inline void Prepend(const Handle(Poly_PolygonOnTriangulation)& thePolygon)
- {
- myFirst = thePolygon;
-
- if (myLast.IsNull())
- myLast = thePolygon;
- }
-
- //! Sets the last element of the pair.
- //! If first element is empty, also assignes the given polygon to it.
- //! @param thePolygon plygon to be set.
- inline void Append(const Handle(Poly_PolygonOnTriangulation)& thePolygon)
- {
- if (myFirst.IsNull())
- myFirst = thePolygon;
-
- myLast = thePolygon;
- }
-
- //! Returns first polygon on triangulation.
- inline const Handle(Poly_PolygonOnTriangulation)& First() const
- {
- return myFirst;
- }
-
- //! Returns last polygon on triangulation.
- inline const Handle(Poly_PolygonOnTriangulation)& Last() const
- {
- return myLast;
- }
-
-private:
-
- Handle(Poly_PolygonOnTriangulation) myFirst;
- Handle(Poly_PolygonOnTriangulation) myLast;
-};
-
-#endif
+++ /dev/null
-// Created on: 2011-05-17
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_Status_HeaderFile
-#define _BRepMesh_Status_HeaderFile
-
-//! Discribes the wires discretisation.
-enum BRepMesh_Status
-{
- BRepMesh_NoError = 0x0,
- BRepMesh_OpenWire = 0x1,
- BRepMesh_SelfIntersectingWire = 0x2,
- BRepMesh_Failure = 0x4,
- BRepMesh_ReMesh = 0x8
-};
-
-#endif
+++ /dev/null
-// Created on: 2014-06-03
-// Created by: Oleg AGASHIN
-// Copyright (c) 1997-1999 Matra Datavision
-// Copyright (c) 1999-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_WireChecker.hxx>
-
-#include <Precision.hxx>
-#include <TColStd_Array1OfInteger.hxx>
-#include <gp_Pnt2d.hxx>
-#include <BRepTools_WireExplorer.hxx>
-#include <TopAbs_Orientation.hxx>
-#include <TopoDS.hxx>
-#include <TopoDS_Wire.hxx>
-#include <TopoDS_Iterator.hxx>
-#include <Poly_PolygonOnTriangulation.hxx>
-#include <BRepMesh_PairOfPolygon.hxx>
-#include <TColStd_SequenceOfInteger.hxx>
-#include <TColStd_IndexedMapOfInteger.hxx>
-#include <BRepMesh_DataStructureOfDelaun.hxx>
-#include <BRepMesh_Classifier.hxx>
-#include <BRepMesh_WireInterferenceChecker.hxx>
-#include <OSD_Parallel.hxx>
-
-
-//=======================================================================
-//function : Selector::Constructor
-//purpose :
-//=======================================================================
-BRepMesh_WireChecker::BndBox2dTreeSelector::BndBox2dTreeSelector(
- const Standard_Integer theReservedSize)
- : mySkippedIndex(-1),
- myIndices(0, theReservedSize - 1),
- myIndicesNb(0)
-{
-}
-
-//=======================================================================
-//function : Reject
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_WireChecker::BndBox2dTreeSelector::Reject(
- const Bnd_Box2d& theBox2D) const
-{
- return myBox2D.IsOut(theBox2D);
-}
-
-//=======================================================================
-//function : Accept
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_WireChecker::BndBox2dTreeSelector::Accept(
- const Standard_Integer& theIndex)
-{
- if (theIndex <= mySkippedIndex)
- return Standard_False;
-
- myIndices(myIndicesNb++) = theIndex;
- return Standard_True;
-}
-
-//=======================================================================
-//function : Clear
-//purpose :
-//=======================================================================
-void BRepMesh_WireChecker::BndBox2dTreeSelector::Clear()
-{
- mySkippedIndex = -1;
- myIndicesNb = 0;
-}
-
-//=======================================================================
-//function : SetBox
-//purpose :
-//=======================================================================
-void BRepMesh_WireChecker::BndBox2dTreeSelector::SetBox(
- const Bnd_Box2d& theBox2D)
-{
- myBox2D = theBox2D;
-}
-
-//=======================================================================
-//function : Clear
-//purpose :
-//=======================================================================
-void BRepMesh_WireChecker::BndBox2dTreeSelector::SetSkippedIndex(
- const Standard_Integer theIndex)
-{
- mySkippedIndex = theIndex;
-}
-
-//=======================================================================
-//function : Indices
-//purpose :
-//=======================================================================
-const BRepMesh::Array1OfInteger&
- BRepMesh_WireChecker::BndBox2dTreeSelector::Indices() const
-{
- return myIndices;
-}
-
-//=======================================================================
-//function : IndicesNb
-//purpose :
-//=======================================================================
-Standard_Integer BRepMesh_WireChecker::BndBox2dTreeSelector::IndicesNb() const
-{
- return myIndicesNb;
-}
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_WireChecker::BRepMesh_WireChecker(
- const TopoDS_Face& theFace,
- const Standard_Real theTolUV,
- const BRepMesh::HDMapOfShapePairOfPolygon& theEdges,
- const BRepMesh::HIMapOfInteger& theVertexMap,
- const Handle(BRepMesh_DataStructureOfDelaun)& theStructure,
- const Standard_Real theUmin,
- const Standard_Real theUmax,
- const Standard_Real theVmin,
- const Standard_Real theVmax,
- const Standard_Boolean isInParallel)
- : myTolUV(theTolUV),
- myEdges(theEdges),
- myVertexMap(theVertexMap),
- myStructure(theStructure),
- myUmin(theUmin),
- myUmax(theUmax),
- myVmin(theVmin),
- myVmax(theVmax),
- myStatus(BRepMesh_NoError),
- myIsInParallel(isInParallel)
-{
- TopoDS_Face aFace = theFace;
- aFace.Orientation(TopAbs_FORWARD);
-
- for (TopoDS_Iterator aFaceIt(aFace); aFaceIt.More(); aFaceIt.Next())
- {
- if (aFaceIt.Value().IsNull() || aFaceIt.Value().ShapeType() != TopAbs_WIRE) // may be inner vertex
- continue;
- const TopoDS_Wire& aWire = TopoDS::Wire(aFaceIt.Value());
-
- myWiresEdges.Append(ListOfEdges());
- ListOfEdges& aEdges = myWiresEdges.ChangeLast();
-
- // Start traversing the wires
- BRepTools_WireExplorer aWireExplorer(aWire, aFace);
- for (; aWireExplorer.More(); aWireExplorer.Next())
- {
- const TopoDS_Edge& aEdge = aWireExplorer.Current();
- TopAbs_Orientation aOrient = aEdge.Orientation();
- if (aOrient != TopAbs_FORWARD && aOrient != TopAbs_REVERSED)
- continue;
-
- aEdges.Append(aEdge);
- }
-
- if (aEdges.IsEmpty())
- myWiresEdges.Remove(myWiresEdges.Size());
- }
-}
-
-//=======================================================================
-//function : ReCompute
-//purpose :
-//=======================================================================
-void BRepMesh_WireChecker::ReCompute(BRepMesh::HClassifier& theClassifier)
-{
- if (theClassifier.IsNull())
- return;
-
- theClassifier->Destroy();
- myStatus = BRepMesh_NoError;
-
- SeqOfDWires aDWires;
- if (!collectDiscretizedWires(aDWires))
- return;
-
- const Standard_Integer aNbWires = aDWires.Size();
- BRepMesh::Array1OfSegmentsTree aWiresBiPoints(1, aNbWires);
- fillSegmentsTree(aDWires, aWiresBiPoints);
-
- if (myIsInParallel && aNbWires > 1)
- {
- // Check wires in parallel threads.
- Standard_Mutex aWireMutex;
- BRepMesh_WireInterferenceChecker aIntChecker(aWiresBiPoints, &myStatus, &aWireMutex);
- OSD_Parallel::For(1, aNbWires + 1, aIntChecker);
- }
- else
- {
- BRepMesh_WireInterferenceChecker aIntChecker(aWiresBiPoints, &myStatus);
- OSD_Parallel::For(1, aNbWires + 1, aIntChecker, Standard_True);
- }
-
- if (myStatus == BRepMesh_SelfIntersectingWire)
- return;
-
- // Find holes
- SeqOfDWires::Iterator aDWiresIt(aDWires);
- for (; aDWiresIt.More(); aDWiresIt.Next())
- {
- const SeqOfPnt2d& aDWire = aDWiresIt.Value();
- theClassifier->RegisterWire(aDWire, myTolUV, myUmin, myUmax, myVmin, myVmax);
- }
-}
-
-//=======================================================================
-//function : collectDiscretizedWires
-//purpose :
-//=======================================================================
-Standard_Boolean BRepMesh_WireChecker::collectDiscretizedWires(
- SeqOfDWires& theDWires)
-{
- SeqOfWireEdges::Iterator aWireIt(myWiresEdges);
- for(; aWireIt.More(); aWireIt.Next())
- {
- const ListOfEdges& aEdges = aWireIt.Value();
- // For each wire we create a data map, linking vertices (only
- // the ends of edges) with their positions in the sequence of
- // all 2d points from this wire.
- // When we meet some vertex for the second time - the piece
- // of sequence is treated for a HOLE and quits the sequence.
- // Actually, we must unbind the vertices belonging to the
- // loop from the map, but since they can't appear twice on the
- // valid wire, leave them for a little speed up.
-
- SeqOfPnt2d aSeqPnt2d;
- BRepMesh::MapOfIntegerInteger aNodeInSeq;
- Standard_Integer aFirstIndex = 0, aLastIndex = 0;
-
- // Start traversing the wire
- ListOfEdges::Iterator aEdgeIt(aEdges);
- for (; aEdgeIt.More(); aEdgeIt.Next())
- {
- const TopoDS_Edge& aEdge = aEdgeIt.Value();
- TopAbs_Orientation aOrient = aEdge.Orientation();
- if (!myEdges->IsBound(aEdge))
- continue;
-
- // Retrieve polygon
- // Define the direction for adding points to aSeqPnt2d
- Standard_Integer aStartId, aEndId, aIncrement;
- const BRepMesh_PairOfPolygon& aPair = myEdges->Find(aEdge);
- Handle(Poly_PolygonOnTriangulation) aNOD;
- if (aOrient == TopAbs_FORWARD)
- {
- aNOD = aPair.First();
- aStartId = 1;
- aEndId = aNOD->NbNodes();
- aIncrement = 1;
- }
- else
- {
- aNOD = aPair.Last();
- aStartId = aNOD->NbNodes();
- aEndId = 1;
- aIncrement = -1;
- }
-
- const TColStd_Array1OfInteger& aIndices = aNOD->Nodes();
- const Standard_Integer aFirstVertexId = myVertexMap->FindKey(aIndices(aStartId));
- const Standard_Integer aLastVertexId = myVertexMap->FindKey(aIndices(aEndId) );
-
- if (aFirstVertexId == aLastVertexId && (aEndId - aStartId) == aIncrement)
- {
- // case of continuous set of degenerated edges
- aLastIndex = aLastVertexId;
- continue;
- }
-
- if (aFirstIndex != 0)
- {
- if (aFirstVertexId != aLastIndex)
- {
- // there's a gap between edges
- myStatus = BRepMesh_OpenWire;
- return Standard_False;
- }
- }
- else
- aFirstIndex = aFirstVertexId;
-
- aLastIndex = aLastVertexId;
-
- // Record first vertex (to detect loops)
- aNodeInSeq.Bind(aFirstVertexId, (aSeqPnt2d.Length() + 1));
-
- // Add vertices in sequence
- for (Standard_Integer i = aStartId; i != aEndId; i += aIncrement)
- {
- Standard_Integer aIndex = ((i == aStartId) ?
- aFirstVertexId :
- myVertexMap->FindKey(aIndices(i)));
-
- aSeqPnt2d.Append(gp_Pnt2d(myStructure->GetNode(aIndex).Coord()));
- }
-
- // Now, is there a loop?
- if (aNodeInSeq.IsBound(aLastVertexId))
- {
- // Yes, treat it separately as a hole
- // Divide points into main wire and a loop
- const Standard_Integer aIdxWireStart = aNodeInSeq(aLastVertexId);
- if(aIdxWireStart < aSeqPnt2d.Length())
- {
- theDWires.Append(SeqOfPnt2d());
- SeqOfPnt2d& aWire = theDWires.ChangeLast();
- aSeqPnt2d.Split(aIdxWireStart, aWire);
- }
- }
- }
-
- if (aFirstIndex == 0)
- continue;
-
- // Isn't wire open?
- if (aFirstIndex != aLastIndex || aSeqPnt2d.Length() > 1)
- {
- myStatus = BRepMesh_OpenWire;
- return Standard_False;
- }
- }
-
- return Standard_True;
-}
-
-//=======================================================================
-//function : fillSegmentsTree
-//purpose :
-//=======================================================================
-void BRepMesh_WireChecker::fillSegmentsTree(
- const SeqOfDWires& theDWires,
- BRepMesh::Array1OfSegmentsTree& theWiresSegmentsTree)
-{
- const Standard_Integer aNbWires = theDWires.Size();
- for (Standard_Integer aWireIt = 1; aWireIt <= aNbWires; ++aWireIt)
- {
- const SeqOfPnt2d& aWire = theDWires(aWireIt);
- const Standard_Integer aWireLen = aWire.Size();
-
- BRepMesh::HArray1OfSegments aWireSegments =
- new BRepMesh::Array1OfSegments(1, aWireLen);
-
- BRepMesh::HBndBox2dTree aBndBoxTree =
- new BRepMesh::BndBox2dTree;
-
- BRepMesh::BndBox2dTreeFiller aBndBoxTreeFiller(*aBndBoxTree);
-
- Standard_Real x1 = 0., y1 = 0., aXstart = 0., aYstart = 0.;
- for (Standard_Integer aPntIt = 0; aPntIt <= aWireLen; ++aPntIt)
- {
- Standard_Real x2, y2;
- // Obtain last point of the segment
- if (aPntIt == aWireLen)
- {
- x2 = aXstart;
- y2 = aYstart;
- }
- else
- {
- const gp_Pnt2d& aPnt = aWire(aPntIt + 1);
- x2 = aPnt.X();
- y2 = aPnt.Y();
- }
-
- // Build segment (bi-point)
- if (aPntIt == 0)
- {
- aXstart = x2;
- aYstart = y2;
- }
- else
- {
- gp_Pnt2d aStartPnt(x1, y1);
- gp_Pnt2d aEndPnt(x2, y2);
-
- BRepMesh::Segment& aSegment = aWireSegments->ChangeValue(aPntIt);
- aSegment.StartPnt = aStartPnt.XY();
- aSegment.EndPnt = aEndPnt.XY();
-
- Bnd_Box2d aBox;
- aBox.Add(aStartPnt);
- aBox.Add( aEndPnt);
- aBndBoxTreeFiller.Add(aPntIt, aBox);
- }
- x1 = x2;
- y1 = y2;
- }
- aBndBoxTreeFiller.Fill();
-
- BRepMesh::SegmentsTree& aSegmentsTree = theWiresSegmentsTree(aWireIt);
- aSegmentsTree.first = aWireSegments;
- aSegmentsTree.second = aBndBoxTree;
- }
-}
+++ /dev/null
-// Created on: 2014-06-03
-// Created by: Oleg AGASHIN
-// Copyright (c) 1997-1999 Matra Datavision
-// Copyright (c) 1999-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_WireChecker_HeaderFile
-#define _BRepMesh_WireChecker_HeaderFile
-
-#include <Standard.hxx>
-#include <TopoDS_Face.hxx>
-#include <BRepMesh_Status.hxx>
-#include <BRepMesh_DataStructureOfDelaun.hxx>
-#include <BRepMesh.hxx>
-#include <TColStd_IndexedMapOfInteger.hxx>
-#include <TopoDS_Edge.hxx>
-#include <Bnd_Box2d.hxx>
-#include <gp_Pnt2d.hxx>
-#include <gp_XY.hxx>
-
-#include <vector>
-
-
-//! Auxilary class intended to check correctness of discretized face.
-//! In particular, checks boundaries of discretized face for self
-//! intersections and gaps.
-class BRepMesh_WireChecker
-{
-public:
-
- //! Selector.
- //! Used to identify segments with overlapped bounding boxes.
- //! Note that instance of selector can be used only once due to
- //! unextentable array of indices.
- class BndBox2dTreeSelector : public BRepMesh::BndBox2dTree::Selector
- {
- public:
- Standard_EXPORT BndBox2dTreeSelector(const Standard_Integer theReservedSize);
- Standard_EXPORT virtual Standard_Boolean Reject(const Bnd_Box2d& theBox2D) const;
- Standard_EXPORT virtual Standard_Boolean Accept(const Standard_Integer& theIndex);
-
- Standard_EXPORT void Clear();
- Standard_EXPORT void SetBox(const Bnd_Box2d& theBox2D);
- Standard_EXPORT void SetSkippedIndex(const Standard_Integer theIndex);
- Standard_EXPORT const BRepMesh::Array1OfInteger& Indices() const;
- Standard_EXPORT Standard_Integer IndicesNb() const;
-
- protected:
- Bnd_Box2d myBox2D;
- Standard_Integer mySkippedIndex;
- BRepMesh::Array1OfInteger myIndices;
- Standard_Integer myIndicesNb;
- };
-
-private:
-
- typedef NCollection_List<TopoDS_Edge> ListOfEdges;
- typedef NCollection_Sequence<ListOfEdges> SeqOfWireEdges;
-
- typedef NCollection_Sequence<gp_Pnt2d> SeqOfPnt2d;
- typedef NCollection_Sequence<SeqOfPnt2d> SeqOfDWires;
-
-public:
-
- //! Constructor.
- //! @param theFace Face to be checked.
- //! @param theTolUV Tolerance to be used for calculations in parametric space.
- //! @param theEdges Map of edges with associated polygon on triangulation.
- //! @param theVertexMap Map of face vertices.
- //! @param theStructure Discretized representation of face in parametric space.
- //! @param theUmin Lower U boundary of the face in parametric space.
- //! @param theUmax Upper U boundary of the face in parametric space.
- //! @param theVmin Lower V boundary of the face in parametric space.
- //! @param theVmax Upper V boundary of the face in parametric space.
- Standard_EXPORT BRepMesh_WireChecker(
- const TopoDS_Face& theFace,
- const Standard_Real theTolUV,
- const BRepMesh::HDMapOfShapePairOfPolygon& theEdges,
- const BRepMesh::HIMapOfInteger& theVertexMap,
- const Handle(BRepMesh_DataStructureOfDelaun)& theStructure,
- const Standard_Real theUmin,
- const Standard_Real theUmax,
- const Standard_Real theVmin,
- const Standard_Real theVmax,
- const Standard_Boolean isInParallel);
-
- //! Recompute data using parameters passed in constructor.
- //! @param[out] theClassifier Classifier to be updated using calculated data.
- Standard_EXPORT void ReCompute(BRepMesh::HClassifier& theClassifier);
-
- //! Returns status of the check.
- inline BRepMesh_Status Status() const
- {
- return myStatus;
- }
-
-private:
-
- //! Collects discrete wires.
- //! @param[out] theDWires sequence of discretized wires to be filled.
- //! @return TRUE on success, FALSE in case of open wire.
- Standard_Boolean collectDiscretizedWires(SeqOfDWires& theDWires);
-
- //! Fills array of BiPoints for corresponding wire.
- //! @param theDWires Sequence of wires to be processed.
- //! @param theWiresSegmentsTree Array of segments with corresponding
- //! bounding boxes trees to be filled.
- void fillSegmentsTree(
- const SeqOfDWires& theDWires,
- BRepMesh::Array1OfSegmentsTree& theWiresSegmentsTree);
-
- //! Assignment operator.
- void operator =(BRepMesh_WireChecker& /*theOther*/)
- {
- }
-
-private:
-
- const Standard_Real myTolUV;
- const BRepMesh::HDMapOfShapePairOfPolygon& myEdges;
- const BRepMesh::HIMapOfInteger& myVertexMap;
- const Handle(BRepMesh_DataStructureOfDelaun)& myStructure;
- const Standard_Real myUmin;
- const Standard_Real myUmax;
- const Standard_Real myVmin;
- const Standard_Real myVmax;
- BRepMesh_Status myStatus;
- SeqOfWireEdges myWiresEdges;
- Standard_Boolean myIsInParallel;
-};
-
-#endif
+++ /dev/null
-// Created on: 2014-06-18
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#include <BRepMesh_WireInterferenceChecker.hxx>
-#include <BRepMesh_GeomTool.hxx>
-#include <Precision.hxx>
-
-// TODO: remove this variable after implementation of LoopChecker2d.
-static const Standard_Real MIN_LOOP_S = 2 * M_PI * 2.E-5;
-
-//=======================================================================
-//function : Constructor
-//purpose :
-//=======================================================================
-BRepMesh_WireInterferenceChecker::BRepMesh_WireInterferenceChecker(
- const BRepMesh::Array1OfSegmentsTree& theWires,
- BRepMesh_Status* theStatus,
- Standard_Mutex* theMutex)
-: myWires (theWires),
- myStatus(theStatus),
- myMutex (theMutex)
-{
-}
-
-//=======================================================================
-//function : Checker's body
-//purpose :
-//=======================================================================
-void BRepMesh_WireInterferenceChecker::operator ()(
- const Standard_Integer& theWireId) const
-{
- if (*myStatus == BRepMesh_SelfIntersectingWire)
- return;
-
- const BRepMesh::SegmentsTree& aWireSegTree1 = myWires(theWireId);
- const BRepMesh::HArray1OfSegments& aWireSegments1 = aWireSegTree1.first;
- const BRepMesh::HBndBox2dTree& aWireBoxTree1 = aWireSegTree1.second;
-
- for (Standard_Integer aWireIt = theWireId; aWireIt <= myWires.Upper(); ++aWireIt)
- {
- // Break execution in case if flag was raised by another thread.
- if (*myStatus == BRepMesh_SelfIntersectingWire)
- return;
-
- const Standard_Boolean isSelfIntCheck = (aWireIt == theWireId);
- const BRepMesh::SegmentsTree& aWireSegTree2 =
- isSelfIntCheck ? aWireSegTree1 : myWires(aWireIt);
-
- const BRepMesh::HArray1OfSegments& aWireSegments2 = aWireSegTree2.first;
- const BRepMesh::HBndBox2dTree& aWireBoxTree2 = aWireSegTree2.second;
-
- BRepMesh_WireChecker::BndBox2dTreeSelector aSelector (aWireSegments2->Size());
-
- Standard_Integer aSegmentId1 = aWireSegments1->Lower();
- for (; aSegmentId1 <= aWireSegments1->Upper(); ++aSegmentId1)
- {
- // Break execution in case if flag was raised by another thread
- if (*myStatus == BRepMesh_SelfIntersectingWire)
- return;
-
- aSelector.Clear();
- aSelector.SetBox(aWireBoxTree1->FindNode(aSegmentId1).Bnd());
- if (isSelfIntCheck)
- aSelector.SetSkippedIndex(aSegmentId1);
-
- if (aWireBoxTree2->Select(aSelector) == 0)
- continue;
-
- const BRepMesh::Segment& aSegment1 = aWireSegments1->Value(aSegmentId1);
- const BRepMesh::Array1OfInteger& aSelected = aSelector.Indices();
- const Standard_Integer aSelectedNb = aSelector.IndicesNb();
- for (Standard_Integer aBndIt = 0; aBndIt < aSelectedNb; ++aBndIt)
- {
- // Break execution in case if flag was raised by another thread
- if (*myStatus == BRepMesh_SelfIntersectingWire)
- return;
-
- const Standard_Integer aSegmentId2 = aSelected(aBndIt);
- const BRepMesh::Segment& aSegment2 = aWireSegments2->Value(aSegmentId2);
-
- gp_Pnt2d aIntPnt;
- BRepMesh_GeomTool::IntFlag aIntStatus = BRepMesh_GeomTool::IntSegSeg(
- aSegment1.StartPnt, aSegment1.EndPnt,
- aSegment2.StartPnt, aSegment2.EndPnt,
- Standard_False, Standard_False,
- aIntPnt);
-
- if (aIntStatus == BRepMesh_GeomTool::Cross)
- {
- // TODO: remove this block after implementation of LoopChecker2d.
- if (isSelfIntCheck)
- {
- gp_XY aPrevVec;
- Standard_Real aSumS = 0.;
- const gp_XY& aRefPnt = aIntPnt.Coord();
- for (Standard_Integer i = aSegmentId1; i < aSegmentId2; ++i)
- {
- const BRepMesh::Segment& aSeg = aWireSegments1->Value(i);
- gp_XY aCurVec = aSeg.EndPnt - aRefPnt;
-
- if (aCurVec.SquareModulus() < gp::Resolution())
- continue;
-
- if (aPrevVec.SquareModulus() > gp::Resolution())
- aSumS += aPrevVec ^ aCurVec;
-
- aPrevVec = aCurVec;
- }
-
- if (Abs(aSumS / 2.) < MIN_LOOP_S)
- continue;
- }
-
- Standard_Mutex::Sentry aSentry(myMutex);
- *myStatus = BRepMesh_SelfIntersectingWire;
-
- return;
- }
- }
- }
- }
-}
+++ /dev/null
-// Created on: 2014-06-18
-// Created by: Oleg AGASHIN
-// Copyright (c) 2011-2014 OPEN CASCADE SAS
-//
-// This file is part of Open CASCADE Technology software library.
-//
-// This library is free software; you can redistribute it and/or modify it under
-// the terms of the GNU Lesser General Public License version 2.1 as published
-// by the Free Software Foundation, with special exception defined in the file
-// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
-// distribution for complete text of the license and disclaimer of any warranty.
-//
-// Alternatively, this file may be used under the terms of Open CASCADE
-// commercial license or contractual agreement.
-
-#ifndef _BRepMesh_WireInterferenceChecker_HeaderFile
-#define _BRepMesh_WireInterferenceChecker_HeaderFile
-
-#include <Standard.hxx>
-#include <Standard_Mutex.hxx>
-#include <BRepMesh_WireChecker.hxx>
-#include <BRepMesh_Status.hxx>
-
-//! Auxilary class implementing functionality for
-//! checking interference between two discretized wires.
-class BRepMesh_WireInterferenceChecker
-{
-public:
-
- //! Enumerates states of segments intersection check.
- enum IntFlag
- {
- NoIntersection,
- Cross,
- EndPointTouch,
- PointOnSegment,
- Glued,
- Same
- };
-
- //! Constructor
- //! @param theWires wires that should be checked.
- //! @param theStatus shared flag to set status of the check.
- //! @param theMutex shared mutex for parallel processing.
- BRepMesh_WireInterferenceChecker(
- const BRepMesh::Array1OfSegmentsTree& theWires,
- BRepMesh_Status* theStatus,
- Standard_Mutex* theMutex = NULL);
-
- //! Checker's body.
- //! @param theWireId Id of discretized wire to be checked.
- void operator ()(const Standard_Integer& theWireId) const;
-
-private:
-
- //! Assignment operator.
- void operator =(const BRepMesh_WireInterferenceChecker& /*theOther*/)
- {
- }
-
-private:
- const BRepMesh::Array1OfSegmentsTree& myWires;
- BRepMesh_Status* myStatus;
- Standard_Mutex* myMutex;
-};
-
-#endif
BRepMesh_VertexTool.cxx
BRepMesh_VertexTool.hxx
BRepMesh_Triangle.hxx
-BRepMesh.hxx
-BRepMesh_EdgeParameterProvider.cxx
-BRepMesh_EdgeTessellator.cxx
-BRepMesh_EdgeTessellator.hxx
-BRepMesh_FaceAttribute.cxx
-BRepMesh_FaceAttribute.hxx
-BRepMesh_FastDiscret.cxx
-BRepMesh_FastDiscret.hxx
-BRepMesh_FastDiscretFace.cxx
-BRepMesh_FastDiscretFace.hxx
-BRepMesh_IEdgeTool.cxx
-BRepMesh_IEdgeTool.hxx
-BRepMesh_PairOfPolygon.hxx
-BRepMesh_Status.hxx