From: jfa Date: Wed, 28 Dec 2011 11:30:48 +0000 (+0000) Subject: Mantis issue 0021425: Accepted object types in 'fillet 2D' X-Git-Tag: V6_5_0a1~106 X-Git-Url: http://git.salome-platform.org/gitweb/?a=commitdiff_plain;h=2fba9e59a7a545a4afecb4faff16614ab66e57da;p=modules%2Fgeom.git Mantis issue 0021425: Accepted object types in 'fillet 2D' --- diff --git a/doc/salome/gui/GEOM/input/fillet2d_operation.doc b/doc/salome/gui/GEOM/input/fillet2d_operation.doc index bb0ba1bce..b6d8bfb5e 100755 --- a/doc/salome/gui/GEOM/input/fillet2d_operation.doc +++ b/doc/salome/gui/GEOM/input/fillet2d_operation.doc @@ -2,17 +2,22 @@ \page fillet2d_operation_page Fillet 2D -This operation creates fillets on the corners of a 2D Planar Face. +This operation creates fillets on the corners of a 2D Planar Face +or a Shell, made of 2D Planar Faces. \image html fillet2d_2.png -To produce a \b Fillet 2D in the Main Menu select +To produce a Fillet 2D in the Main Menu select Operations - > Fillet 2D -Define the Planar Face to create a fillet on, select the necessary -vertexes on this face in the OCC Viewer and define the \b Radius of the Fillet. +Define the Planar Face or the Shell to create a fillet +on, select the necessary vertexes on this shape in the OCC Viewer and +define the \b Radius of the Fillet. -\b Note: This Operation Works for the Planar 2D Faces Only. +\b Note: This operation works only for Planar 2D Faces and +shells, made of such faces. For shells, only corner vertexes are +available for fillet building, i.e. the vertexes that belong to only +one face of this shell. TUI Command: geompy.MakeFillet2D(Shape, R, ListVertexes) \n Arguments: Name + 1 shape + one or several vertexes + 1 value (Fillet radius). diff --git a/idl/GEOM_Gen.idl b/idl/GEOM_Gen.idl index 136310506..3da8faec1 100644 --- a/idl/GEOM_Gen.idl +++ b/idl/GEOM_Gen.idl @@ -2762,7 +2762,7 @@ module GEOM in ListOfLong theFaces); /*! - * Perform a fillet on face of the specified vertexes of the given shape. + * Perform a fillet on a face or a shell at the specified vertexes. * \param theShape Shape, to perform fillet on. * \param theR Fillet radius. * \param theVertexes Global indices of vertexes to perform fillet on. diff --git a/src/GEOMImpl/GEOMImpl_Fillet2dDriver.cxx b/src/GEOMImpl/GEOMImpl_Fillet2dDriver.cxx index 82827eb4d..0fb59351e 100755 --- a/src/GEOMImpl/GEOMImpl_Fillet2dDriver.cxx +++ b/src/GEOMImpl/GEOMImpl_Fillet2dDriver.cxx @@ -15,7 +15,6 @@ // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA // // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com -// #include @@ -23,17 +22,22 @@ #include #include #include +#include #include #include #include #include +#include #include #include #include +#include #include #include +#include +#include #include #include @@ -75,29 +79,96 @@ Standard_Integer GEOMImpl_Fillet2dDriver::Execute(TFunction_Logbook& log) const TopoDS_Shape aShape; Handle(GEOM_Function) aRefShape = aCI.GetShape(); - TopoDS_Face aFaceShape = TopoDS::Face(aRefShape->GetValue()); - - if (aFaceShape.ShapeType() != TopAbs_FACE) - Standard_ConstructionError::Raise("Wrong arguments: two faces must be given"); - - BRepFilletAPI_MakeFillet2d fillet2d (aFaceShape); + TopoDS_Shape aFaceShape = aRefShape->GetValue(); int aLen = aCI.GetLength(); - int ind = 1; double rad = aCI.GetR(); - for (; ind <= aLen; ind++) { - TopoDS_Shape aShapeVertex; - if (GEOMImpl_ILocalOperations::GetSubShape - (aFaceShape, aCI.GetVertex(ind), aShapeVertex)) { - fillet2d.AddFillet(TopoDS::Vertex(aShapeVertex), rad); + + if (aFaceShape.ShapeType() == TopAbs_FACE) { + BRepFilletAPI_MakeFillet2d fillet2d (TopoDS::Face(aFaceShape)); + + int ind = 1; + for (; ind <= aLen; ind++) { + TopoDS_Shape aShapeVertex; + if (GEOMImpl_ILocalOperations::GetSubShape + (aFaceShape, aCI.GetVertex(ind), aShapeVertex)) { + fillet2d.AddFillet(TopoDS::Vertex(aShapeVertex), rad); + } + } + + fillet2d.Build(); + if (!fillet2d.IsDone()) { + StdFail_NotDone::Raise("2D Fillet can't be computed on the given shape with the given radius"); } + aShape = fillet2d.Shape(); } + else if (aFaceShape.ShapeType() == TopAbs_SHELL) { + // 1. Map vertices to faces to build fillets only on corner vertices + TopTools_IndexedDataMapOfShapeListOfShape mapVertexFaces; + GEOMImpl_Block6Explorer::MapShapesAndAncestors + (aFaceShape, TopAbs_VERTEX, TopAbs_FACE, mapVertexFaces); + + // 2. Map faces to vertices + TopTools_IndexedDataMapOfShapeListOfShape mapFaceVertices; + TopTools_ListOfShape empty; + int ind = 1; + for (; ind <= aLen; ind++) { + TopoDS_Shape aVi; + if (GEOMImpl_ILocalOperations::GetSubShape(aFaceShape, aCI.GetVertex(ind), aVi)) { + Standard_Integer aVi_index = mapVertexFaces.FindIndex(aVi); + if (aVi_index > 0) { + const TopTools_ListOfShape& aFacesOfVi = mapVertexFaces(aVi_index); + if (aFacesOfVi.Extent() == 1) { // we use only corner vertices of shell + TopoDS_Shape aFi = aFacesOfVi.First(); + Standard_Integer aFi_index = mapFaceVertices.FindIndex(aFi); + if (aFi_index == 0) aFi_index = mapFaceVertices.Add(aFi, empty); + mapFaceVertices(aFi_index).Append(aVi); + } + } + } + } + + // 3. Build fillet on each given vertex + TopoDS_Shell aResult; + BRep_Builder B; + B.MakeShell(aResult); + + TopoDS_Iterator It (aFaceShape, Standard_True, Standard_True); + TopTools_MapOfShape mapShape; + for (; It.More(); It.Next()) { + if (mapShape.Add(It.Value())) { + Standard_Integer aFi_index = mapFaceVertices.FindIndex(It.Value()); + if (aFi_index == 0) { + // No fillets requested on this face, add it as is + B.Add(aResult, It.Value()); + } + else { + // Build a fillet and add the changed face + BRepFilletAPI_MakeFillet2d fillet2d (TopoDS::Face(It.Value())); + const TopTools_ListOfShape& aVertsOfFi = mapFaceVertices(aFi_index); + TopTools_ListIteratorOfListOfShape itV (aVertsOfFi); + for (; itV.More(); itV.Next()) { + fillet2d.AddFillet(TopoDS::Vertex(itV.Value()), rad); + } + + fillet2d.Build(); + if (!fillet2d.IsDone()) { + StdFail_NotDone::Raise("2D Fillet can't be computed on the given shape with the given radius"); + } + TopoDS_Shape aFillet = fillet2d.Shape(); + + B.Add(aResult, aFillet); + } + } + } - fillet2d.Build(); - if (!fillet2d.IsDone()) { - StdFail_NotDone::Raise("2D Fillet can't be computed on the given shape with the given radius"); + // 4. Build a shell + // ?TODO? + aShape = aResult; + } + else { + Standard_ConstructionError::Raise("Wrong arguments: a face or a shell must be given"); } - aShape = fillet2d.Shape(); if (aShape.IsNull()) return 0; @@ -114,7 +185,6 @@ Standard_Integer GEOMImpl_Fillet2dDriver::Execute(TFunction_Logbook& log) const //======================================================================= Standard_EXPORT Handle_Standard_Type& GEOMImpl_Fillet2dDriver_Type_() { - static Handle_Standard_Type aType1 = STANDARD_TYPE(TFunction_Driver); if ( aType1.IsNull()) aType1 = STANDARD_TYPE(TFunction_Driver); static Handle_Standard_Type aType2 = STANDARD_TYPE(MMgt_TShared); @@ -122,7 +192,6 @@ Standard_EXPORT Handle_Standard_Type& GEOMImpl_Fillet2dDriver_Type_() static Handle_Standard_Type aType3 = STANDARD_TYPE(Standard_Transient); if ( aType3.IsNull()) aType3 = STANDARD_TYPE(Standard_Transient); - static Handle_Standard_Transient _Ancestors[]= {aType1,aType2,aType3,NULL}; static Handle_Standard_Type _aType = new Standard_Type("GEOMImpl_Fillet2dDriver", sizeof(GEOMImpl_Fillet2dDriver), @@ -137,7 +206,8 @@ Standard_EXPORT Handle_Standard_Type& GEOMImpl_Fillet2dDriver_Type_() //function : DownCast //purpose : //======================================================================= -const Handle(GEOMImpl_Fillet2dDriver) Handle(GEOMImpl_Fillet2dDriver)::DownCast(const Handle(Standard_Transient)& AnObject) +const Handle(GEOMImpl_Fillet2dDriver) Handle(GEOMImpl_Fillet2dDriver)::DownCast + (const Handle(Standard_Transient)& AnObject) { Handle(GEOMImpl_Fillet2dDriver) _anOtherObject; @@ -147,5 +217,5 @@ const Handle(GEOMImpl_Fillet2dDriver) Handle(GEOMImpl_Fillet2dDriver)::DownCast( } } - return _anOtherObject ; + return _anOtherObject; } diff --git a/src/GEOMImpl/GEOMImpl_FilletDriver.cxx b/src/GEOMImpl/GEOMImpl_FilletDriver.cxx index 93ed1eafd..355f4f95d 100644 --- a/src/GEOMImpl/GEOMImpl_FilletDriver.cxx +++ b/src/GEOMImpl/GEOMImpl_FilletDriver.cxx @@ -88,7 +88,8 @@ Standard_Integer GEOMImpl_FilletDriver::Execute(TFunction_Logbook& log) const TopoDS_Edge E = TopoDS::Edge(Exp.Current()); fill.Add(E); } - } else if (aType == FILLET_SHAPE_EDGES || aType == FILLET_SHAPE_EDGES_2R) { + } + else if (aType == FILLET_SHAPE_EDGES || aType == FILLET_SHAPE_EDGES_2R) { int aLen = aCI.GetLength(); int ind = 1; for (; ind <= aLen; ind++) { @@ -98,7 +99,8 @@ Standard_Integer GEOMImpl_FilletDriver::Execute(TFunction_Logbook& log) const fill.Add(TopoDS::Edge(aShapeEdge)); } } - } else if (aType == FILLET_SHAPE_FACES || aType == FILLET_SHAPE_FACES_2R) { + } + else if (aType == FILLET_SHAPE_FACES || aType == FILLET_SHAPE_FACES_2R) { int aLen = aCI.GetLength(); int ind = 1; for (; ind <= aLen; ind++) { @@ -111,16 +113,19 @@ Standard_Integer GEOMImpl_FilletDriver::Execute(TFunction_Logbook& log) const } } } - } else { } - if (aType == FILLET_SHAPE_FACES || aType == FILLET_SHAPE_EDGES || aType == FILLET_SHAPE_ALL) + else { + } + + if (aType == FILLET_SHAPE_FACES || aType == FILLET_SHAPE_EDGES || aType == FILLET_SHAPE_ALL) { for (int i = 1; i <= fill.NbContours(); i++) fill.SetRadius(aCI.GetR(), i, 1); - else if (aType == FILLET_SHAPE_FACES_2R || aType == FILLET_SHAPE_EDGES_2R) - for (int i = 1; i <= fill.NbContours(); i++) - { - fill.SetRadius(aCI.GetR1(), aCI.GetR2(), i, 1); - } + } + else if (aType == FILLET_SHAPE_FACES_2R || aType == FILLET_SHAPE_EDGES_2R) { + for (int i = 1; i <= fill.NbContours(); i++) { + fill.SetRadius(aCI.GetR1(), aCI.GetR2(), i, 1); + } + } fill.Build(); if (!fill.IsDone()) { diff --git a/src/GEOM_SWIG/geompyDC.py b/src/GEOM_SWIG/geompyDC.py index 5936e3b29..4ea478a23 100644 --- a/src/GEOM_SWIG/geompyDC.py +++ b/src/GEOM_SWIG/geompyDC.py @@ -3283,15 +3283,15 @@ class geompyDC(GEOM._objref_GEOM_Gen): anObj.SetParameters(Parameters) return anObj - ## Perform a fillet on the specified edges/faces of the given shape - # @param theShape - Face Shape to perform fillet on. + ## Perform a fillet at the specified vertices of the given face/shell. + # @param theShape - Face or Shell shape to perform fillet on. # @param theR - Fillet radius. # @param theListOfVertexes Global indices of vertexes to perform fillet on. # \note Global index of sub-shape can be obtained, using method geompy.GetSubShapeID(). # @return New GEOM_Object, containing the result shape. # # @ref tui_fillet2d "Example" - def MakeFillet2D(self,theShape, theR, theListOfVertexes): + def MakeFillet2D(self, theShape, theR, theListOfVertexes): # Example: see GEOM_TestAll.py theR,Parameters = ParseParameters(theR) anObj = self.LocalOp.MakeFillet2D(theShape, theR, theListOfVertexes) diff --git a/src/OperationGUI/OperationGUI_Fillet1d2dDlg.cxx b/src/OperationGUI/OperationGUI_Fillet1d2dDlg.cxx index 4d769e28d..04eb64733 100644 --- a/src/OperationGUI/OperationGUI_Fillet1d2dDlg.cxx +++ b/src/OperationGUI/OperationGUI_Fillet1d2dDlg.cxx @@ -15,12 +15,11 @@ // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA // // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com -// // GEOM GEOMGUI : GUI for Geometry component // File : OperationGUI_Fillet1d2dDlg.cxx // Author : DMV, OCN. -// + #include "OperationGUI_Fillet1d2dDlg.h" #include @@ -215,7 +214,8 @@ void OperationGUI_Fillet1d2dDlg::SelectionIntoArgument() anObj = aFindedObject; // get Object from study } else { // Global Selection - if ( aShape.ShapeType() != (myIs1D ? TopAbs_WIRE : TopAbs_FACE) ) { + if ((myIs1D && aShape.ShapeType() != TopAbs_WIRE) || + (!myIs1D && aShape.ShapeType() != TopAbs_FACE && aShape.ShapeType() != TopAbs_SHELL)) { anObj = GEOM::GEOM_Object::_nil(); aName = ""; } @@ -349,8 +349,15 @@ void OperationGUI_Fillet1d2dDlg::activateSelection() disconnect(myGeomGUI->getApp()->selectionMgr(), 0, this, 0); globalSelection(); if (myEditCurrentArgument == GroupVertexes->LineEdit1) - globalSelection( myIs1D ? GEOM_WIRE : GEOM_FACE ); // localSelection(myShape, myIs1D ? TopAbs_WIRE - // : TopAbs_FACE); + //localSelection(myShape, myIs1D ? TopAbs_WIRE : TopAbs_FACE); + if (myIs1D) + globalSelection(GEOM_WIRE); + else { + TColStd_MapOfInteger aMap; + aMap.Add(GEOM_FACE); + aMap.Add(GEOM_SHELL); + globalSelection(aMap); + } else if (!myShape->_is_nil() && myEditCurrentArgument == GroupVertexes->LineEdit2) localSelection(myShape, TopAbs_VERTEX);