diff --git a/src/BRepBuilderAPI/BRepBuilderAPI_Copy.cxx b/src/BRepBuilderAPI/BRepBuilderAPI_Copy.cxx index 36c25a41e5..fab7de94b7 100644 --- a/src/BRepBuilderAPI/BRepBuilderAPI_Copy.cxx +++ b/src/BRepBuilderAPI/BRepBuilderAPI_Copy.cxx @@ -15,186 +15,8 @@ // commercial license or contractual agreement. -#include #include -#include -#include -#include -#include -#include -#include -#include -#include - -namespace { - -//! Tool class implementing necessary functionality for copying geometry -class BRepBuilderAPI_Copy_Modification : public BRepTools_Modification -{ -public: - BRepBuilderAPI_Copy_Modification (const Standard_Boolean copyGeom, - const Standard_Boolean copyMesh) - : myCopyGeom(copyGeom), - myCopyMesh(copyMesh) - { - } - - //! Returns true to indicate the need to copy face; - //! copies surface if requested - Standard_Boolean NewSurface (const TopoDS_Face& F, Handle(Geom_Surface)& S, - TopLoc_Location& L, Standard_Real& Tol, - Standard_Boolean& RevWires, Standard_Boolean& RevFace) Standard_OVERRIDE - { - S = BRep_Tool::Surface(F,L); - Tol = BRep_Tool::Tolerance(F); - RevWires = RevFace = Standard_False; - - if ( ! S.IsNull() && myCopyGeom ) - S = Handle(Geom_Surface)::DownCast(S->Copy()); - - return Standard_True; - } - - //! Returns true to indicate the need to copy triangulation; - //! copies it if required - Standard_Boolean NewTriangulation(const TopoDS_Face& F, Handle(Poly_Triangulation)& T) Standard_OVERRIDE - { - if (!myCopyMesh - && BRep_Tool::IsGeometric (F)) - { - return Standard_False; - } - - TopLoc_Location L; - T = BRep_Tool::Triangulation(F, L); - - if (T.IsNull()) - return Standard_False; - - // mesh is copied if and only if the geometry need to be copied too - if (myCopyGeom) - T = T->Copy(); - return Standard_True; - } - - //! Returns true to indicate the need to copy edge; - //! copies curves if requested - Standard_Boolean NewCurve (const TopoDS_Edge& E, Handle(Geom_Curve)& C, - TopLoc_Location& L, Standard_Real& Tol) Standard_OVERRIDE - { - Standard_Real f,l; - C = BRep_Tool::Curve (E, L, f, l); - Tol = BRep_Tool::Tolerance(E); - - if ( ! C.IsNull() && myCopyGeom ) - C = Handle(Geom_Curve)::DownCast(C->Copy()); - - return Standard_True; - } - - //! Returns true to indicate the need to copy polygon; - //! copies it if required - Standard_Boolean NewPolygon(const TopoDS_Edge& E, Handle(Poly_Polygon3D)& P) Standard_OVERRIDE - { - if (!myCopyMesh - && BRep_Tool::IsGeometric (E)) - { - return Standard_False; - } - - TopLoc_Location aLoc; - P = BRep_Tool::Polygon3D(E, aLoc); - - if (P.IsNull()) - return Standard_False; - - // polygon is copied if and only if the geometry need to be copied too - if (myCopyGeom) - P = P->Copy(); - return Standard_True; - } - - //! Returns true to indicate the need to copy polygon; - //! copies it if required - Standard_Boolean NewPolygonOnTriangulation(const TopoDS_Edge& E, const TopoDS_Face& F, - Handle(Poly_PolygonOnTriangulation)& P) Standard_OVERRIDE - { - if (!myCopyMesh - && BRep_Tool::IsGeometric (E)) - { - return Standard_False; - } - - TopLoc_Location aLoc; - Handle(Poly_Triangulation) aTria = BRep_Tool::Triangulation(F, aLoc); - P = BRep_Tool::PolygonOnTriangulation(E, aTria, aLoc); - - if (P.IsNull()) - return Standard_False; - - // polygon is copied if and only if the geometry need to be copied too - if (myCopyGeom) - P = P->Copy(); - return Standard_True; - } - - //! Returns true to indicate the need to copy vertex - Standard_Boolean NewPoint (const TopoDS_Vertex& V, gp_Pnt& P, - Standard_Real& Tol) Standard_OVERRIDE - { - P = BRep_Tool::Pnt(V); - Tol = BRep_Tool::Tolerance(V); - return Standard_True; - } - - //! Returns true to indicate the need to copy edge; - //! copies pcurve if requested - Standard_Boolean NewCurve2d (const TopoDS_Edge& E, - const TopoDS_Face& F, - const TopoDS_Edge& /*NewE*/, - const TopoDS_Face& /*NewF*/, - Handle(Geom2d_Curve)& C, - Standard_Real& Tol) Standard_OVERRIDE - { - Tol = BRep_Tool::Tolerance(E); - Standard_Real f, l; - C = BRep_Tool::CurveOnSurface (E, F, f, l); - - if ( ! C.IsNull() && myCopyGeom ) - C = Handle(Geom2d_Curve)::DownCast (C->Copy()); - - return Standard_True; - } - - //! Returns true to indicate the need to copy vertex - Standard_Boolean NewParameter (const TopoDS_Vertex& V, const TopoDS_Edge& E, - Standard_Real& P, Standard_Real& Tol) Standard_OVERRIDE - { - if (V.IsNull()) return Standard_False; // infinite edge may have Null vertex - - Tol = BRep_Tool::Tolerance(V); - P = BRep_Tool::Parameter (V, E); - - return Standard_True; - } - - //! Returns the continuity of E between F1 and F2 - GeomAbs_Shape Continuity (const TopoDS_Edge& E, const TopoDS_Face& F1, - const TopoDS_Face& F2, const TopoDS_Edge&, - const TopoDS_Face&, const TopoDS_Face&) Standard_OVERRIDE - { - return BRep_Tool::Continuity (E, F1, F2); - } - -public: - DEFINE_STANDARD_RTTI_INLINE(BRepBuilderAPI_Copy_Modification,BRepTools_Modification) - -private: - Standard_Boolean myCopyGeom; - Standard_Boolean myCopyMesh; -}; - -} // anonymous namespace +#include //======================================================================= //function : BRepBuilderAPI_Copy @@ -203,7 +25,7 @@ private: BRepBuilderAPI_Copy::BRepBuilderAPI_Copy () { - myModification = new BRepBuilderAPI_Copy_Modification(Standard_True, Standard_False); + myModification = new BRepTools_CopyModification(Standard_True, Standard_False); } @@ -214,7 +36,7 @@ BRepBuilderAPI_Copy::BRepBuilderAPI_Copy () BRepBuilderAPI_Copy::BRepBuilderAPI_Copy(const TopoDS_Shape& S, const Standard_Boolean copyGeom, const Standard_Boolean copyMesh) { - myModification = new BRepBuilderAPI_Copy_Modification(copyGeom, copyMesh); + myModification = new BRepTools_CopyModification(copyGeom, copyMesh); DoModif(S); } @@ -226,7 +48,7 @@ BRepBuilderAPI_Copy::BRepBuilderAPI_Copy(const TopoDS_Shape& S, const Standard_B void BRepBuilderAPI_Copy::Perform(const TopoDS_Shape& S, const Standard_Boolean copyGeom, const Standard_Boolean copyMesh) { - myModification = new BRepBuilderAPI_Copy_Modification(copyGeom, copyMesh); + myModification = new BRepTools_CopyModification(copyGeom, copyMesh); NotDone(); // on force la copie si on vient deja d`en faire une DoModif(S); } diff --git a/src/BRepTools/BRepTools_CopyModification.cxx b/src/BRepTools/BRepTools_CopyModification.cxx new file mode 100644 index 0000000000..7d9a7b2933 --- /dev/null +++ b/src/BRepTools/BRepTools_CopyModification.cxx @@ -0,0 +1,215 @@ +// Copyright (c) 1999-2022 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 + +#include +#include +#include + +IMPLEMENT_STANDARD_RTTIEXT(BRepTools_CopyModification, BRepTools_Modification) + +//======================================================================= +//function : BRepTools_CopyModification +//purpose : +//======================================================================= +BRepTools_CopyModification::BRepTools_CopyModification(const Standard_Boolean copyGeom, + const Standard_Boolean copyMesh) + : myCopyGeom(copyGeom), + myCopyMesh(copyMesh) +{ +} + +//======================================================================= +//function : NewSurface +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewSurface(const TopoDS_Face& theFace, + Handle(Geom_Surface)& theSurf, + TopLoc_Location& theLoc, + Standard_Real& theTol, + Standard_Boolean& theRevWires, + Standard_Boolean& theRevFace) +{ + theSurf = BRep_Tool::Surface(theFace, theLoc); + theTol = BRep_Tool::Tolerance(theFace); + theRevWires = theRevFace = Standard_False; + + if (!theSurf.IsNull() && myCopyGeom) + theSurf = Handle(Geom_Surface)::DownCast(theSurf->Copy()); + + return Standard_True; +} + +//======================================================================= +//function : NewTriangulation +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewTriangulation(const TopoDS_Face& theFace, + Handle(Poly_Triangulation)& theTri) +{ + if (!myCopyMesh && BRep_Tool::IsGeometric(theFace)) + { + return Standard_False; + } + + TopLoc_Location aLoc; + theTri = BRep_Tool::Triangulation(theFace, aLoc); + + if (theTri.IsNull()) + return Standard_False; + + // mesh is copied if and only if the geometry need to be copied too + if (myCopyGeom) + theTri = theTri->Copy(); + return Standard_True; +} + +//======================================================================= +//function : NewCurve +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewCurve(const TopoDS_Edge& theEdge, + Handle(Geom_Curve)& theCurve, + TopLoc_Location& theLoc, + Standard_Real& theTol) +{ + Standard_Real aFirst, aLast; + theCurve = BRep_Tool::Curve(theEdge, theLoc, aFirst, aLast); + theTol = BRep_Tool::Tolerance(theEdge); + + if (!theCurve.IsNull() && myCopyGeom) + theCurve = Handle(Geom_Curve)::DownCast(theCurve->Copy()); + + return Standard_True; +} + +//======================================================================= +//function : NewPolygon +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewPolygon(const TopoDS_Edge& theEdge, + Handle(Poly_Polygon3D)& thePoly) +{ + if (!myCopyMesh && BRep_Tool::IsGeometric(theEdge)) + { + return Standard_False; + } + + TopLoc_Location aLoc; + thePoly = BRep_Tool::Polygon3D(theEdge, aLoc); + + if (thePoly.IsNull()) + return Standard_False; + + // polygon is copied if and only if the geometry need to be copied too + if (myCopyGeom) + thePoly = thePoly->Copy(); + return Standard_True; +} + +//======================================================================= +//function : NewPolygonOnTriangulation +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewPolygonOnTriangulation( + const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Handle(Poly_PolygonOnTriangulation)& thePoly) +{ + if (!myCopyMesh && BRep_Tool::IsGeometric(theEdge)) + { + return Standard_False; + } + + TopLoc_Location aLoc; + Handle(Poly_Triangulation) aTria = BRep_Tool::Triangulation(theFace, aLoc); + thePoly = BRep_Tool::PolygonOnTriangulation(theEdge, aTria, aLoc); + + if (thePoly.IsNull()) + return Standard_False; + + // polygon is copied if and only if the geometry need to be copied too + if (myCopyGeom) + thePoly = thePoly->Copy(); + return Standard_True; +} + +//======================================================================= +//function : NewPoint +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewPoint(const TopoDS_Vertex& theVertex, + gp_Pnt& thePnt, + Standard_Real& theTol) +{ + thePnt = BRep_Tool::Pnt(theVertex); + theTol = BRep_Tool::Tolerance(theVertex); + return Standard_True; +} + +//======================================================================= +//function : NewCurve2d +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewCurve2d(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + const TopoDS_Edge&, + const TopoDS_Face&, + Handle(Geom2d_Curve)& theCurve, + Standard_Real& theTol) +{ + theTol = BRep_Tool::Tolerance(theEdge); + Standard_Real aFirst, aLast; + theCurve = BRep_Tool::CurveOnSurface(theEdge, theFace, aFirst, aLast); + + if (!theCurve.IsNull() && myCopyGeom) + theCurve = Handle(Geom2d_Curve)::DownCast(theCurve->Copy()); + + return Standard_True; +} + +//======================================================================= +//function : NewParameter +//purpose : +//======================================================================= +Standard_Boolean BRepTools_CopyModification::NewParameter(const TopoDS_Vertex& theVertex, + const TopoDS_Edge& theEdge, + Standard_Real& thePnt, + Standard_Real& theTol) +{ + if (theVertex.IsNull()) + return Standard_False; // infinite edge may have Null vertex + + theTol = BRep_Tool::Tolerance(theVertex); + thePnt = BRep_Tool::Parameter(theVertex, theEdge); + + return Standard_True; +} + +//======================================================================= +//function : Continuity +//purpose : +//======================================================================= +GeomAbs_Shape BRepTools_CopyModification::Continuity(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace1, + const TopoDS_Face& theFace2, + const TopoDS_Edge&, + const TopoDS_Face&, + const TopoDS_Face&) +{ + return BRep_Tool::Continuity(theEdge, theFace1, theFace2); +} + + diff --git a/src/BRepTools/BRepTools_CopyModification.hxx b/src/BRepTools/BRepTools_CopyModification.hxx new file mode 100644 index 0000000000..9caf2fb662 --- /dev/null +++ b/src/BRepTools/BRepTools_CopyModification.hxx @@ -0,0 +1,124 @@ +// Copyright (c) 1999-2022 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 _BRepTools_CopyModification_HeaderFile +#define _BRepTools_CopyModification_HeaderFile + +#include + +class BRepTools_CopyModification; +DEFINE_STANDARD_HANDLE(BRepTools_CopyModification, BRepTools_Modification) + +//! Tool class implementing necessary functionality for copying geometry and triangulation. +class BRepTools_CopyModification : public BRepTools_Modification +{ +public: + //! Constructor. + //! \param[in] theCopyGeom indicates that the geomtery (surfaces and curves) should be copied + //! \param[in] theCopyMesh indicates that the triangulation should be copied + Standard_EXPORT explicit BRepTools_CopyModification(const Standard_Boolean theCopyGeom = Standard_True, + const Standard_Boolean theCopyMesh = Standard_True); + + //! Returns true if theFace has been modified. + //! If the face has been modified: + //! - theSurf is the new geometry of the face, + //! - theLoc is its new location, and + //! - theTol is the new tolerance. + //! theRevWires, theRevFace are always set to false, because the orientaion is not changed. + Standard_EXPORT Standard_Boolean NewSurface(const TopoDS_Face& theFace, + Handle(Geom_Surface)& theSurf, + TopLoc_Location& theLoc, + Standard_Real& theTol, + Standard_Boolean& theRevWires, + Standard_Boolean& theRevFace) Standard_OVERRIDE; + + //! Returns true if theEdge has been modified. + //! If the edge has been modified: + //! - theCurve is the new geometric support of the edge, + //! - theLoc is the new location, and + //! - theTol is the new tolerance. + //! If the edge has not been modified, this function + //! returns false, and the values of theCurve, theLoc and theTol are not significant. + Standard_EXPORT Standard_Boolean NewCurve(const TopoDS_Edge& theEdge, + Handle(Geom_Curve)& theCurve, + TopLoc_Location& theLoc, + Standard_Real& theTol) Standard_OVERRIDE; + + //! Returns true if theVertex has been modified. + //! If the vertex has been modified: + //! - thePnt is the new geometry of the vertex, and + //! - theTol is the new tolerance. + //! If the vertex has not been modified this function + //! returns false, and the values of thePnt and theTol are not significant. + Standard_EXPORT Standard_Boolean NewPoint(const TopoDS_Vertex& theVertex, gp_Pnt& thePnt, Standard_Real& theTol) Standard_OVERRIDE; + + //! Returns true if theEdge has a new curve on surface on theFace. + //! If a new curve exists: + //! - theCurve is the new geometric support of the edge, + //! - theTol the new tolerance. + //! If no new curve exists, this function returns false, and + //! the values of theCurve and theTol are not significant. + Standard_EXPORT Standard_Boolean NewCurve2d(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + const TopoDS_Edge& theNewEdge, + const TopoDS_Face& theNewFace, + Handle(Geom2d_Curve)& theCurve, + Standard_Real& theTol) Standard_OVERRIDE; + + //! Returns true if theVertex has a new parameter on theEdge. + //! If a new parameter exists: + //! - thePnt is the parameter, and + //! - theTol is the new tolerance. + //! If no new parameter exists, this function returns false, + //! and the values of thePnt and theTol are not significant. + Standard_EXPORT Standard_Boolean NewParameter(const TopoDS_Vertex& theVertex, + const TopoDS_Edge& theEdge, + Standard_Real& thePnt, + Standard_Real& theTol) Standard_OVERRIDE; + + //! Returns the continuity of theNewEdge between theNewFace1 and theNewFace2. + //! + //! theNewEdge is the new edge created from theEdge. theNewFace1 + //! (resp. theNewFace2) is the new face created from theFace1 (resp. theFace2). + Standard_EXPORT GeomAbs_Shape Continuity(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace1, + const TopoDS_Face& theFace2, + const TopoDS_Edge& theNewEdge, + const TopoDS_Face& theNewFace1, + const TopoDS_Face& theNewFace2) Standard_OVERRIDE; + + //! Returns true if the face has been modified according to changed triangulation. + //! If the face has been modified: + //! - theTri is a new triangulation on the face + Standard_EXPORT Standard_Boolean NewTriangulation(const TopoDS_Face& theFace, Handle(Poly_Triangulation)& theTri) Standard_OVERRIDE; + + //! Returns true if the edge has been modified according to changed polygon. + //! If the edge has been modified: + //! - thePoly is a new polygon + Standard_EXPORT Standard_Boolean NewPolygon(const TopoDS_Edge& theEdge, Handle(Poly_Polygon3D)& thePoly) Standard_OVERRIDE; + + //! Returns true if the edge has been modified according to changed polygon on triangulation. + //! If the edge has been modified: + //! - thePoly is a new polygon on triangulation + Standard_EXPORT Standard_Boolean NewPolygonOnTriangulation(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Handle(Poly_PolygonOnTriangulation)& thePoly) Standard_OVERRIDE; + + DEFINE_STANDARD_RTTIEXT(BRepTools_CopyModification, BRepTools_Modification) + +private: + Standard_Boolean myCopyGeom; + Standard_Boolean myCopyMesh; +}; + +#endif // _BRepTools_CopyModification_HeaderFile diff --git a/src/BRepTools/BRepTools_GTrsfModification.cxx b/src/BRepTools/BRepTools_GTrsfModification.cxx index dfb116dc88..7f2d9731d6 100644 --- a/src/BRepTools/BRepTools_GTrsfModification.cxx +++ b/src/BRepTools/BRepTools_GTrsfModification.cxx @@ -29,6 +29,7 @@ #include #include #include +#include #include #include #include @@ -88,7 +89,13 @@ Standard_Boolean BRepTools_GTrsfModification::NewSurface gp_GTrsf gtrsf; gtrsf.SetVectorialPart(myGTrsf.VectorialPart()); gtrsf.SetTranslationPart(myGTrsf.TranslationPart()); - S = Handle(Geom_Surface)::DownCast(BRep_Tool::Surface(F,L)->Copy()); + S = BRep_Tool::Surface(F, L); + if (S.IsNull()) + { + //processing the case when there is no geometry + return Standard_False; + } + S = Handle(Geom_Surface)::DownCast(S->Copy()); Tol = BRep_Tool::Tolerance(F); Tol *= myGScale; @@ -173,7 +180,7 @@ Standard_Boolean BRepTools_GTrsfModification::NewCurve C = new Geom_TrimmedCurve(C, f, l); } L.Identity() ; - return Standard_True; + return !C.IsNull(); } //======================================================================= @@ -214,6 +221,11 @@ Standard_Boolean BRepTools_GTrsfModification::NewCurve2d Tol *= myGScale; Standard_Real f,l; C = BRep_Tool::CurveOnSurface(E,F,f,l); + if (C.IsNull()) + { + //processing the case when there is no geometry + return Standard_False; + } C = new Geom2d_TrimmedCurve(C, f, l); return Standard_True; } @@ -251,4 +263,113 @@ GeomAbs_Shape BRepTools_GTrsfModification::Continuity return BRep_Tool::Continuity(E,F1,F2); } +//======================================================================= +//function : NewTriangulation +//purpose : +//======================================================================= +Standard_Boolean BRepTools_GTrsfModification::NewTriangulation(const TopoDS_Face& theFace, + Handle(Poly_Triangulation)& theTriangulation) +{ + TopLoc_Location aLoc; + theTriangulation = BRep_Tool::Triangulation(theFace, aLoc); + if (theTriangulation.IsNull()) + { + return Standard_False; + } + + gp_GTrsf aGTrsf; + aGTrsf.SetVectorialPart(myGTrsf.VectorialPart()); + aGTrsf.SetTranslationPart(myGTrsf.TranslationPart()); + aGTrsf.Multiply(aLoc.Transformation()); + + theTriangulation = theTriangulation->Copy(); + theTriangulation->SetCachedMinMax(Bnd_Box()); // clear bounding box + theTriangulation->Deflection(theTriangulation->Deflection() * Abs(myGScale)); + // apply transformation to 3D nodes + for (Standard_Integer anInd = 1; anInd <= theTriangulation->NbNodes(); ++anInd) + { + gp_Pnt aP = theTriangulation->Node(anInd); + aGTrsf.Transforms(aP.ChangeCoord()); + theTriangulation->SetNode(anInd, aP); + } + // modify triangles orientation in case of mirror transformation + if (myGScale < 0.0) + { + for (Standard_Integer anInd = 1; anInd <= theTriangulation->NbTriangles(); ++anInd) + { + Poly_Triangle aTria = theTriangulation->Triangle(anInd); + Standard_Integer aN1, aN2, aN3; + aTria.Get(aN1, aN2, aN3); + aTria.Set(aN1, aN3, aN2); + theTriangulation->SetTriangle(anInd, aTria); + } + } + // modify normals + if (theTriangulation->HasNormals()) + { + for (Standard_Integer anInd = 1; anInd <= theTriangulation->NbTriangles(); ++anInd) + { + gp_Dir aNormal = theTriangulation->Normal(anInd); + aNormal.Transform(aGTrsf.Trsf()); + theTriangulation->SetNormal(anInd, aNormal); + } + } + + return Standard_True; +} + +//======================================================================= +//function : NewPolygon +//purpose : +//======================================================================= + +Standard_Boolean BRepTools_GTrsfModification::NewPolygon(const TopoDS_Edge& theEdge, + Handle(Poly_Polygon3D)& thePoly) +{ + TopLoc_Location aLoc; + thePoly = BRep_Tool::Polygon3D(theEdge, aLoc); + if (thePoly.IsNull()) + { + return Standard_False; + } + + gp_GTrsf aGTrsf; + aGTrsf.SetVectorialPart(myGTrsf.VectorialPart()); + aGTrsf.SetTranslationPart(myGTrsf.TranslationPart()); + aGTrsf.Multiply(aLoc.Transformation()); + + thePoly = thePoly->Copy(); + thePoly->Deflection(thePoly->Deflection() * Abs(myGScale)); + // transform nodes + TColgp_Array1OfPnt& aNodesArray = thePoly->ChangeNodes(); + for (Standard_Integer anId = aNodesArray.Lower(); anId <= aNodesArray.Upper(); ++anId) + { + gp_Pnt& aP = aNodesArray.ChangeValue(anId); + aGTrsf.Transforms(aP.ChangeCoord()); + } + return Standard_True; +} + +//======================================================================= +//function : NewPolygonOnTriangulation +//purpose : +//======================================================================= + +Standard_Boolean BRepTools_GTrsfModification::NewPolygonOnTriangulation + (const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Handle(Poly_PolygonOnTriangulation)& thePoly) +{ + TopLoc_Location aLoc; + Handle(Poly_Triangulation) aT = BRep_Tool::Triangulation(theFace, aLoc); + if (aT.IsNull()) + { + return Standard_False; + } + + thePoly = BRep_Tool::PolygonOnTriangulation(theEdge, aT, aLoc); + if (!thePoly.IsNull()) + thePoly = thePoly->Copy(); + return Standard_True; +} diff --git a/src/BRepTools/BRepTools_GTrsfModification.hxx b/src/BRepTools/BRepTools_GTrsfModification.hxx index 20c9ca7f72..1494397c61 100644 --- a/src/BRepTools/BRepTools_GTrsfModification.hxx +++ b/src/BRepTools/BRepTools_GTrsfModification.hxx @@ -101,6 +101,25 @@ public: //! (resp. ). Standard_EXPORT GeomAbs_Shape Continuity (const TopoDS_Edge& E, const TopoDS_Face& F1, const TopoDS_Face& F2, const TopoDS_Edge& NewE, const TopoDS_Face& NewF1, const TopoDS_Face& NewF2) Standard_OVERRIDE; + //! Returns true if the face has been modified according to changed triangulation. + //! If the face has been modified: + //! - theTri is a new triangulation on the face + Standard_EXPORT Standard_Boolean NewTriangulation(const TopoDS_Face& theFace, + Handle(Poly_Triangulation)& theTri) Standard_OVERRIDE; + + //! Returns true if the edge has been modified according to changed polygon. + //! If the edge has been modified: + //! - thePoly is a new polygon + Standard_EXPORT Standard_Boolean NewPolygon(const TopoDS_Edge& theEdge, + Handle(Poly_Polygon3D)& thePoly) Standard_OVERRIDE; + + //! Returns true if the edge has been modified according to changed polygon on triangulation. + //! If the edge has been modified: + //! - thePoly is a new polygon on triangulation + Standard_EXPORT Standard_Boolean NewPolygonOnTriangulation(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Handle(Poly_PolygonOnTriangulation)& thePoly) Standard_OVERRIDE; + diff --git a/src/BRepTools/BRepTools_NurbsConvertModification.cxx b/src/BRepTools/BRepTools_NurbsConvertModification.cxx index fff0a4d6b8..85a30c63c6 100644 --- a/src/BRepTools/BRepTools_NurbsConvertModification.cxx +++ b/src/BRepTools/BRepTools_NurbsConvertModification.cxx @@ -20,7 +20,10 @@ #include #include #include +#include +#include #include +#include #include #include #include @@ -47,30 +50,163 @@ #include #include #include -IMPLEMENT_STANDARD_RTTIEXT(BRepTools_NurbsConvertModification,BRepTools_Modification) + +IMPLEMENT_STANDARD_RTTIEXT(BRepTools_NurbsConvertModification,BRepTools_CopyModification) // -static void GeomLib_ChangeUBounds(Handle(Geom_BSplineSurface)& aSurface, - const Standard_Real newU1, - const Standard_Real newU2) +namespace { - TColStd_Array1OfReal knots(1,aSurface->NbUKnots()) ; - aSurface->UKnots(knots) ; - BSplCLib::Reparametrize(newU1, - newU2, - knots) ; - aSurface->SetUKnots(knots) ; -} -static void GeomLib_ChangeVBounds(Handle(Geom_BSplineSurface)& aSurface, - const Standard_Real newV1, - const Standard_Real newV2) -{ - TColStd_Array1OfReal knots(1,aSurface->NbVKnots()) ; - aSurface->VKnots(knots) ; - BSplCLib::Reparametrize(newV1, - newV2, - knots) ; - aSurface->SetVKnots(knots) ; + static void GeomLib_ChangeUBounds(Handle(Geom_BSplineSurface)& aSurface, + const Standard_Real newU1, + const Standard_Real newU2) + { + TColStd_Array1OfReal knots(1, aSurface->NbUKnots()); + aSurface->UKnots(knots); + BSplCLib::Reparametrize(newU1, newU2, knots); + aSurface->SetUKnots(knots); + } + + static void GeomLib_ChangeVBounds(Handle(Geom_BSplineSurface)& aSurface, + const Standard_Real newV1, + const Standard_Real newV2) + { + TColStd_Array1OfReal knots(1, aSurface->NbVKnots()); + aSurface->VKnots(knots); + BSplCLib::Reparametrize(newV1, newV2, knots); + aSurface->SetVKnots(knots); + } + + // find 3D curve from theEdge in theMap, and return the transformed curve or NULL + static Handle(Geom_Curve) newCurve(const TColStd_IndexedDataMapOfTransientTransient& theMap, + const TopoDS_Edge& theEdge, + Standard_Real& theFirst, + Standard_Real& theLast) + { + Handle(Geom_Curve) aNewCurve; + + TopLoc_Location aLoc; + Handle(Geom_Curve) aCurve = BRep_Tool::Curve(theEdge, aLoc, theFirst, theLast); + if (!aCurve.IsNull() && theMap.Contains(aCurve)) + { + aNewCurve = Handle(Geom_Curve)::DownCast(theMap.FindFromKey(aCurve)); + aNewCurve = Handle(Geom_Curve)::DownCast(aNewCurve->Transformed(aLoc.Transformation())); + } + return aNewCurve; + } + + // find 2D curve from theEdge on theFace in theMap, and return the transformed curve or NULL + static Handle(Geom2d_Curve) newCurve(const TColStd_IndexedDataMapOfTransientTransient& theMap, + const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Standard_Real& theFirst, + Standard_Real& theLast) + { + Handle(Geom2d_Curve) aC2d = BRep_Tool::CurveOnSurface(theEdge, theFace, theFirst, theLast); + return (!aC2d.IsNull() && theMap.Contains(aC2d)) ? Handle(Geom2d_Curve)::DownCast(theMap.FindFromKey(aC2d)) + : Handle(Geom2d_Curve)(); + } + + // find surface from theFace in theMap, and return the transformed surface or NULL + static Handle(Geom_Surface) newSurface(const TColStd_IndexedDataMapOfTransientTransient& theMap, + const TopoDS_Face& theFace) + { + Handle(Geom_Surface) aNewSurf; + + TopLoc_Location aLoc; + Handle(Geom_Surface) aSurf = BRep_Tool::Surface(theFace, aLoc); + if (!aSurf.IsNull() && theMap.Contains(aSurf)) + { + aNewSurf = Handle(Geom_Surface)::DownCast(theMap.FindFromKey(aSurf)); + aNewSurf = Handle(Geom_Surface)::DownCast(aNewSurf->Transformed(aLoc.Transformation())); + } + return aNewSurf; + } + + static Standard_Boolean newParameter(const gp_Pnt& thePoint, + const Handle(Geom_Curve)& theCurve, + const Standard_Real theFirst, + const Standard_Real theLast, + const Standard_Real theTol, + Standard_Real& theParam) + { + GeomAdaptor_Curve anAdaptor(theCurve); + Extrema_LocateExtPC proj(thePoint, anAdaptor, theParam, theFirst, theLast, Precision::PConfusion()); + if (proj.IsDone()) + { + Standard_Real aDist2Min = proj.SquareDistance(); + if (aDist2Min < theTol * theTol) + { + theParam = proj.Point().Parameter(); + return Standard_True; + } + } + return Standard_False; + } + + static Standard_Boolean newParameter(const gp_Pnt2d& theUV, + const Handle(Geom2d_Curve)& theCurve2d, + const Standard_Real theFirst, + const Standard_Real theLast, + const Standard_Real theTol, + Standard_Real& theParam) + { + Geom2dAdaptor_Curve anAdaptor(theCurve2d); + Extrema_LocateExtPC2d aProj(theUV, anAdaptor, theParam, Precision::PConfusion()); + if (aProj.IsDone()) + { + Standard_Real aDist2Min = aProj.SquareDistance(); + if (aDist2Min < theTol * theTol) + { + theParam = aProj.Point().Parameter(); + return Standard_True; + } + } + else + { + // Try to use general extrema to find the parameter, because Extrema_LocateExtPC2d + // sometimes could not find a solution if the parameter's first approach is several + // spans away from the expected solution (test bugs/modalg_7/bug28722). + Extrema_ExtPC2d anExt(theUV, anAdaptor, theFirst, theLast); + if (anExt.IsDone()) + { + Standard_Integer aMinInd = 0; + Standard_Real aMinSqDist = Precision::Infinite(); + for (Standard_Integer anIndex = 1; anIndex <= anExt.NbExt(); ++anIndex) + if (anExt.SquareDistance(anIndex) < aMinSqDist) + { + aMinSqDist = anExt.SquareDistance(anIndex); + aMinInd = anIndex; + } + if (aMinSqDist < theTol * theTol) + { + theParam = anExt.Point(aMinInd).Parameter(); + return Standard_True; + } + } + } + return Standard_False; + } + + static Standard_Boolean newUV(const gp_Pnt& thePoint, + const Handle(Geom_Surface)& theSurf, + const Standard_Real theTol, + gp_Pnt2d& theUV) + { + GeomAdaptor_Surface anAdaptor(theSurf); + Extrema_GenLocateExtPS aProj(anAdaptor); + aProj.Perform(thePoint, theUV.X(), theUV.Y()); + if (aProj.IsDone()) + { + Standard_Real aDist2Min = aProj.SquareDistance(); + if (aDist2Min < theTol * theTol) + { + gp_XY& aUV = theUV.ChangeCoord(); + aProj.Point().Parameter(aUV.ChangeCoord(1), aUV.ChangeCoord(2)); + return Standard_True; + } + } + return Standard_False; + } } //======================================================================= @@ -102,6 +238,12 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewSurface RevWires = Standard_False; RevFace = Standard_False; Handle(Geom_Surface) SS = BRep_Tool::Surface(F,L); + if (SS.IsNull()) + { + //processing the case when there is no geometry + return Standard_False; + } + Handle(Standard_Type) TheTypeSS = SS->DynamicType(); if ((TheTypeSS == STANDARD_TYPE(Geom_BSplineSurface)) || (TheTypeSS == STANDARD_TYPE(Geom_BezierSurface))) { @@ -115,7 +257,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewSurface //OCC466(apo)-> U1 = curvU1; U2 = curvU2; V1 = curvV1; V2 = curvV2; - SS->Bounds(surfU1,surfU2,surfV1,surfV2); + S->Bounds(surfU1,surfU2,surfV1,surfV2); if (Abs(U1 - surfU1) <= TolPar) U1 = surfU1; @@ -192,10 +334,10 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewSurface if (Abs(surfU1-U1) > Tol || Abs(surfU2-U2) > Tol || Abs(surfV1-V1) > Tol || Abs(surfV2-V2) > Tol) - SS = new Geom_RectangularTrimmedSurface(S, U1, U2, V1, V2); - SS->Bounds(surfU1,surfU2,surfV1,surfV2); + S = new Geom_RectangularTrimmedSurface(S, U1, U2, V1, V2); + S->Bounds(surfU1,surfU2,surfV1,surfV2); - S = GeomConvert::SurfaceToBSplineSurface(SS); + S = GeomConvert::SurfaceToBSplineSurface(S); Handle(Geom_BSplineSurface) BS = Handle(Geom_BSplineSurface)::DownCast(S) ; BS->Resolution(Tol, UTol, VTol) ; @@ -210,6 +352,9 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewSurface GeomLib_ChangeVBounds(BS, V1, V2) ; } + if (!myMap.Contains(SS)) { + myMap.Add(SS, S); + } return Standard_True; } @@ -234,6 +379,41 @@ static Standard_Boolean IsConvert(const TopoDS_Edge& E) } +//======================================================================= +//function : NewTriangulation +//purpose : +//======================================================================= + +Standard_Boolean BRepTools_NurbsConvertModification::NewTriangulation(const TopoDS_Face& theFace, + Handle(Poly_Triangulation)& theTri) +{ + if (!BRepTools_CopyModification::NewTriangulation(theFace, theTri)) + { + return Standard_False; + } + + // convert UV nodes of the mesh + if (theTri->HasUVNodes()) + { + TopLoc_Location aLoc; + Handle(Geom_Surface) aSurf = BRep_Tool::Surface(theFace, aLoc); + Handle(Geom_Surface) aNewSurf = newSurface(myMap, theFace); + if (!aSurf.IsNull() && !aNewSurf.IsNull()) + { + Standard_Real aTol = BRep_Tool::Tolerance(theFace); + for (Standard_Integer anInd = 1; anInd <= theTri->NbNodes(); ++anInd) + { + gp_Pnt2d aUV = theTri->UVNode(anInd); + gp_Pnt aPoint = aSurf->Value(aUV.X(), aUV.Y()); + if (newUV(aPoint, aNewSurf, aTol, aUV)) + theTri->SetUVNode(anInd, aUV); + } + } + } + + return Standard_True; +} + //======================================================================= //function : NewCurve //purpose : @@ -312,6 +492,40 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve return Standard_True ; } +//======================================================================= +//function : NewPolygon +//purpose : +//======================================================================= + +Standard_Boolean BRepTools_NurbsConvertModification::NewPolygon(const TopoDS_Edge& theEdge, + Handle(Poly_Polygon3D)& thePoly) +{ + if (!BRepTools_CopyModification::NewPolygon(theEdge, thePoly)) + { + return Standard_False; + } + + // update parameters of polygon + if (thePoly->HasParameters()) + { + Standard_Real aTol = BRep_Tool::Tolerance(theEdge); + Standard_Real aFirst, aLast; + Handle(Geom_Curve) aCurve = BRep_Tool::Curve(theEdge, aFirst, aLast); + Handle(Geom_Curve) aNewCurve = newCurve(myMap, theEdge, aFirst, aLast); + if (!aCurve.IsNull() && !aNewCurve.IsNull()) // skip processing degenerated edges + { + TColStd_Array1OfReal& aParams = thePoly->ChangeParameters(); + for (Standard_Integer anInd = aParams.Lower(); anInd <= aParams.Upper(); ++anInd) + { + Standard_Real& aParam = aParams(anInd); + gp_Pnt aPoint = aCurve->Value(aParam); + newParameter(aPoint, aNewCurve, aFirst, aLast, aTol, aParam); + } + } + } + return Standard_True; +} + //======================================================================= //function : NewPoint //purpose : @@ -340,7 +554,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = BRep_Tool::Tolerance(E); Standard_Real f2d,l2d; - Handle(Geom2d_Curve) C2d = BRep_Tool::CurveOnSurface(E,F,f2d,l2d); + Handle(Geom2d_Curve) aBaseC2d = BRep_Tool::CurveOnSurface(E,F,f2d,l2d); Standard_Real f3d,l3d; TopLoc_Location Loc; Handle(Geom_Curve) C3d = BRep_Tool::Curve(E, Loc, f3d,l3d); @@ -348,6 +562,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d !C3d->IsKind(STANDARD_TYPE(Geom_BezierCurve))) || IsConvert(E)); + Handle(Geom2d_Curve) C2d = aBaseC2d; if(BRep_Tool::Degenerated(E)) { //Curve2d = C2d; if(!C2d->IsKind(STANDARD_TYPE(Geom2d_TrimmedCurve))) @@ -356,6 +571,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d C2d = aTrimC; } Curve2d = Geom2dConvert::CurveToBSplineCurve(C2d); + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } if(!BRepTools::IsReallyClosed(E,F)) { @@ -381,9 +597,11 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d if(!newE.IsNull()) { C3d = BRep_Tool::Curve(newE, f3d, l3d); } - else { + if (C3d.IsNull()) { C3d = BRep_Tool::Curve(E,f3d,l3d); } + if (C3d.IsNull()) + return Standard_False; GeomAdaptor_Curve G3dAC(C3d, f3d, l3d); Handle(GeomAdaptor_Curve) G3dAHC = new GeomAdaptor_Curve(G3dAC); @@ -403,13 +621,16 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } return Standard_False; } } else { - S = BRep_Tool::Surface(newF); + Handle(Geom_Surface) aNewS = BRep_Tool::Surface(newF); + if (!aNewS.IsNull()) + S = aNewS; } S->Bounds(Uinf, Usup, Vinf, Vsup); //Uinf -= 1e-9; Usup += 1e-9; Vinf -= 1e-9; Vsup += 1e-9; @@ -451,6 +672,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } Curve2d = ProjOnCurve.BSpline(); @@ -460,6 +682,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } @@ -502,6 +725,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } else { @@ -512,6 +736,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } } @@ -557,6 +782,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } return Standard_False; @@ -582,6 +808,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } return Standard_False; @@ -629,6 +856,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d Tol = newTol; myUpdatedEdges.Append(newE); } + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } else { @@ -640,6 +868,7 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d myUpdatedEdges.Append(newE); } mylcu.Append(C2dBis); + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } } @@ -651,11 +880,58 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewCurve2d return Standard_False; } Curve2d = Geom2dConvert::CurveToBSplineCurve(C2d); + myMap.Add(aBaseC2d, Curve2d); return Standard_True; } } } +//======================================================================= +//function : NewPolygonOnTriangulation +//purpose : +//======================================================================= +Standard_Boolean BRepTools_NurbsConvertModification::NewPolygonOnTriangulation( + const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Handle(Poly_PolygonOnTriangulation)& thePoly) +{ + if (!BRepTools_CopyModification::NewPolygonOnTriangulation(theEdge, theFace, thePoly)) + { + return Standard_False; + } + + // update parameters of 2D polygon + if (thePoly->HasParameters()) + { + Standard_Real aTol = Max(BRep_Tool::Tolerance(theEdge), thePoly->Deflection()); + TopLoc_Location aLoc; + Handle(Geom_Surface) aSurf = BRep_Tool::Surface(theFace, aLoc); + Handle(Geom_Surface) aNewSurf = newSurface(myMap, theFace); + Standard_Real aFirst, aLast; + Handle(Geom2d_Curve) aC2d = BRep_Tool::CurveOnSurface(theEdge, theFace, aFirst, aLast); + Handle(Geom2d_Curve) aNewC2d = newCurve(myMap, theEdge, theFace, aFirst, aLast); + if (!aSurf.IsNull() && !aC2d.IsNull() && !aNewSurf.IsNull() && !aNewC2d.IsNull()) + { + // compute 2D tolerance + GeomAdaptor_Surface aSurfAdapt(aSurf); + Standard_Real aTol2D = Max(aSurfAdapt.UResolution(aTol), aSurfAdapt.VResolution(aTol)); + + for (Standard_Integer anInd = 1; anInd <= thePoly->NbNodes(); ++anInd) + { + Standard_Real aParam = thePoly->Parameter(anInd); + gp_Pnt2d aUV = aC2d->Value(aParam); + gp_Pnt aPoint = aSurf->Value(aUV.X(), aUV.Y()); + if (newUV(aPoint, aNewSurf, aTol, aUV) && + newParameter(aUV, aNewC2d, aFirst, aLast, aTol2D, aParam)) + { + thePoly->SetParameter(anInd, aParam); + } + } + } + } + return Standard_True; +} + //======================================================================= //function : NewParameter //purpose : @@ -670,30 +946,12 @@ Standard_Boolean BRepTools_NurbsConvertModification::NewParameter Tol = BRep_Tool::Tolerance(V); if(BRep_Tool::Degenerated(E)) return Standard_False; - Standard_Real f, l, param = BRep_Tool::Parameter(V,E); - TopLoc_Location L; - Handle(Geom_Curve) gc = BRep_Tool::Curve(E, L, f, l); - if(!myMap.Contains(gc)) - return Standard_False; - - Handle(Geom_BSplineCurve) gcc = - Handle(Geom_BSplineCurve)::DownCast(myMap.FindFromKey(gc)); - - gcc = Handle(Geom_BSplineCurve)::DownCast(gcc->Transformed(L.Transformation())); - - GeomAdaptor_Curve ac(gcc); gp_Pnt pnt = BRep_Tool::Pnt(V); - - Extrema_LocateExtPC proj(pnt, ac, param, f, l, Tol); - if(proj.IsDone()) { - Standard_Real Dist2Min = proj.SquareDistance(); - if (Dist2Min < Tol*Tol) { - P = proj.Point().Parameter(); - return Standard_True; - } - } - return Standard_False; + P = BRep_Tool::Parameter(V,E); + Standard_Real aFirst, aLast; + Handle(Geom_Curve) aNewCurve = newCurve(myMap, E, aFirst, aLast); + return !aNewCurve.IsNull() && newParameter(pnt, aNewCurve, aFirst, aLast, Tol, P); } //======================================================================= diff --git a/src/BRepTools/BRepTools_NurbsConvertModification.hxx b/src/BRepTools/BRepTools_NurbsConvertModification.hxx index 8bed3a7ae5..e12620de2f 100644 --- a/src/BRepTools/BRepTools_NurbsConvertModification.hxx +++ b/src/BRepTools/BRepTools_NurbsConvertModification.hxx @@ -22,7 +22,7 @@ #include #include #include -#include +#include #include #include class TopoDS_Face; @@ -36,12 +36,12 @@ class Geom2d_Curve; class BRepTools_NurbsConvertModification; -DEFINE_STANDARD_HANDLE(BRepTools_NurbsConvertModification, BRepTools_Modification) +DEFINE_STANDARD_HANDLE(BRepTools_NurbsConvertModification, BRepTools_CopyModification) //! Defines a modification of the geometry by a Trsf //! from gp. All methods return True and transform the //! geometry. -class BRepTools_NurbsConvertModification : public BRepTools_Modification +class BRepTools_NurbsConvertModification : public BRepTools_CopyModification { public: @@ -100,11 +100,27 @@ public: //! (resp. ). Standard_EXPORT GeomAbs_Shape Continuity (const TopoDS_Edge& E, const TopoDS_Face& F1, const TopoDS_Face& F2, const TopoDS_Edge& NewE, const TopoDS_Face& NewF1, const TopoDS_Face& NewF2) Standard_OVERRIDE; + //! Returns true if the face has been modified according to changed triangulation. + //! If the face has been modified: + //! - theTri is a new triangulation on the face + Standard_EXPORT Standard_Boolean NewTriangulation(const TopoDS_Face& theFace, Handle(Poly_Triangulation)& theTri) Standard_OVERRIDE; + + //! Returns true if the edge has been modified according to changed polygon. + //! If the edge has been modified: + //! - thePoly is a new polygon + Standard_EXPORT Standard_Boolean NewPolygon(const TopoDS_Edge& theEdge, Handle(Poly_Polygon3D)& thePoly) Standard_OVERRIDE; + + //! Returns true if the edge has been modified according to changed polygon on triangulation. + //! If the edge has been modified: + //! - thePoly is a new polygon on triangulation + Standard_EXPORT Standard_Boolean NewPolygonOnTriangulation(const TopoDS_Edge& theEdge, + const TopoDS_Face& theFace, + Handle(Poly_PolygonOnTriangulation)& thePoly) Standard_OVERRIDE; + Standard_EXPORT const TopTools_ListOfShape& GetUpdatedEdges() const; - - DEFINE_STANDARD_RTTIEXT(BRepTools_NurbsConvertModification,BRepTools_Modification) + DEFINE_STANDARD_RTTIEXT(BRepTools_NurbsConvertModification,BRepTools_CopyModification) protected: diff --git a/src/BRepTools/FILES b/src/BRepTools/FILES index 60a0c86804..3b1286ee80 100644 --- a/src/BRepTools/FILES +++ b/src/BRepTools/FILES @@ -1,5 +1,7 @@ BRepTools.cxx BRepTools.hxx +BRepTools_CopyModification.cxx +BRepTools_CopyModification.hxx BRepTools_DataMapIteratorOfMapOfVertexPnt2d.hxx BRepTools_Debug.cxx BRepTools_GTrsfModification.cxx diff --git a/tests/bugs/mesh/bug22778 b/tests/bugs/mesh/bug22778 index f0ace0936c..078f1d9282 100644 --- a/tests/bugs/mesh/bug22778 +++ b/tests/bugs/mesh/bug22778 @@ -14,6 +14,7 @@ regexp {([0-9]+) triangles} $trinfo_s str nbtri_s # face converted to NURBS nurbsconvert r s checkshape r +tclean r incmesh r 0.001 set trinfo_r [trinfo r] regexp {([0-9]+) triangles} $trinfo_r str nbtri_r diff --git a/tests/bugs/modalg_8/bug31479_1 b/tests/bugs/modalg_8/bug31479_1 new file mode 100644 index 0000000000..a9f80be161 --- /dev/null +++ b/tests/bugs/modalg_8/bug31479_1 @@ -0,0 +1,31 @@ +puts "=================================================================" +puts "0031479: Modeling Algorithms - exceptiion geometry transformation" +puts " of triangulation-only shapes (without geometry surface) " +puts "=================================================================" +puts "" + +restore [locate_data_file bug31479_P-51-Mustang-2.brep] s + +# reference data +regexp {([0-9+-.eE]*) faces.* ([0-9+-.eE]*) triangles.* ([0-9+-.eE]*) nodes} [trinfo s] full nbFaces nbTri nbNodes +regexp {Mass :\s*([0-9+-.eE]*)} [vprops s] full mass + +set scale 2 +set mass [expr $mass * $scale * $scale * $scale] + +# scaling +tscale s 0 0 0 $scale -copymesh +checktrinfo s -face $nbFaces -nod $nbNodes -tri $nbTri +checkprops s -v $mass -eps 1.e-5 + +# rotation +trotate s 0 0 0 0 0 1 90 -copymesh +checktrinfo s -face $nbFaces -nod $nbNodes -tri $nbTri +checkprops s -v $mass -eps 1.e-5 + +# translation +ttranslate s 0 0 10 -copymesh +checktrinfo s -face $nbFaces -nod $nbNodes -tri $nbTri +checkprops s -v $mass -eps 1.e-5 + +checkview -display s -2d -path ${imagedir}/${test_image}.png diff --git a/tests/bugs/modalg_8/bug31479_2 b/tests/bugs/modalg_8/bug31479_2 new file mode 100644 index 0000000000..f3d82b727a --- /dev/null +++ b/tests/bugs/modalg_8/bug31479_2 @@ -0,0 +1,17 @@ +puts "=================================================================" +puts "0031479: Modeling Algorithms - exceptiion geometry transformation" +puts " of triangulation-only shapes (without geometry surface) " +puts "=================================================================" +puts "" + +restore [locate_data_file bug31479_P-51-Mustang-2.brep] s + +# reference data +regexp {([0-9+-.eE]*) faces.* ([0-9+-.eE]*) triangles.* ([0-9+-.eE]*) nodes} [trinfo s] full nbFaces nbTri nbNodes +regexp {Mass :\s*([0-9+-.eE]*)} [vprops s] full mass + +deform res s 2 3 4 +checktrinfo res -face $nbFaces -nod $nbNodes -tri $nbTri +checkprops res -v [expr $mass * 2 * 3 * 4] -eps 1.e-5 + +checkview -display res -2d -path ${imagedir}/${test_image}.png