From 6bd91d6692dfbfa6462e4b6463ff113ad51b3782 Mon Sep 17 00:00:00 2001 From: dbv Date: Wed, 29 Aug 2018 09:54:52 +0300 Subject: [PATCH] Issue #2593: CEA 2018-2 Geometrical Naming --- src/Config/Config_AttributeMessage.cpp | 11 ++ src/Config/Config_AttributeMessage.h | 5 + src/Config/Config_FeatureReader.cpp | 3 + src/Config/Config_Keywords.h | 2 + .../ConstructionPlugin_Axis.cpp | 67 +++++++-- .../ConstructionPlugin_Plane.cpp | 64 +++++++- .../ConstructionPlugin_Point.cpp | 19 ++- .../ConstructionPlugin_Validators.cpp | 69 ++++++--- src/ConstructionPlugin/axis_widget.xml | 15 +- src/ConstructionPlugin/plane_widget.xml | 15 +- src/ConstructionPlugin/point_widget.xml | 6 +- .../FeaturesPlugin_Extrusion.cpp | 38 ++++- .../FeaturesPlugin_MultiRotation.cpp | 48 ++++-- .../FeaturesPlugin_MultiTranslation.cpp | 140 +++++++++++++----- .../FeaturesPlugin_Placement.cpp | 60 ++++++-- src/FeaturesPlugin/FeaturesPlugin_Placement.h | 3 + .../FeaturesPlugin_Revolution.cpp | 47 ++++-- .../FeaturesPlugin_Rotation.cpp | 48 ++++-- .../FeaturesPlugin_Symmetry.cpp | 99 +++++++++---- .../FeaturesPlugin_Translation.cpp | 49 ++++-- .../FeaturesPlugin_Validators.cpp | 5 + src/FeaturesPlugin/extrusion_widget.xml | 3 + src/FeaturesPlugin/extrusioncut_widget.xml | 3 + src/FeaturesPlugin/extrusionfuse_widget.xml | 3 + src/FeaturesPlugin/multirotation_widget.xml | 3 +- .../multitranslation_widget.xml | 6 +- src/FeaturesPlugin/placement_widget.xml | 6 +- src/FeaturesPlugin/revolution_widget.xml | 3 + src/FeaturesPlugin/revolutioncut_widget.xml | 3 + src/FeaturesPlugin/revolutionfuse_widget.xml | 3 + src/FeaturesPlugin/rotation_widget.xml | 3 +- src/FeaturesPlugin/symmetry_widget.xml | 3 +- src/FeaturesPlugin/translation_widget.xml | 3 +- src/GeomAlgoAPI/GeomAlgoAPI_Placement.cpp | 47 ++++-- src/GeomValidators/GeomValidators_Face.cpp | 71 +++++---- .../GeomValidators_ShapeType.cpp | 40 ++++- src/GeomValidators/GeomValidators_ShapeType.h | 2 + .../GeomValidators_ZeroOffset.cpp | 9 ++ src/Model/Model_AttributeSelection.cpp | 15 +- src/Model/Model_AttributeSelection.h | 8 + src/Model/Model_AttributeSelectionList.cpp | 2 +- src/Model/Model_Session.cpp | 4 + src/Model/Model_Validator.cpp | 24 +++ src/Model/Model_Validator.h | 7 + src/ModelAPI/ModelAPI_AttributeSelection.h | 3 + src/ModelAPI/ModelAPI_Validator.h | 6 + src/ModelHighAPI/ModelHighAPI_Dumper.cpp | 6 + .../PrimitivesPlugin_Cone.cpp | 45 ++++-- .../PrimitivesPlugin_Cylinder.cpp | 48 ++++-- .../PrimitivesPlugin_Torus.cpp | 45 ++++-- src/PrimitivesPlugin/cone_widget.xml | 1 + src/PrimitivesPlugin/cylinder_widget.xml | 2 + src/PrimitivesPlugin/torus_widget.xml | 1 + src/SketchPlugin/SketchPlugin_Sketch.cpp | 10 +- 54 files changed, 980 insertions(+), 271 deletions(-) diff --git a/src/Config/Config_AttributeMessage.cpp b/src/Config/Config_AttributeMessage.cpp index 32051337c..d8f2f23e8 100644 --- a/src/Config/Config_AttributeMessage.cpp +++ b/src/Config/Config_AttributeMessage.cpp @@ -27,6 +27,7 @@ Config_AttributeMessage::Config_AttributeMessage(const Events_ID theId, const vo myFeatureId = std::string(); // Feature unique id myIsObligatory = true; myIsConcealment = false; + myIsGeometricalSelection = false; } Config_AttributeMessage::~Config_AttributeMessage() @@ -94,3 +95,13 @@ void Config_AttributeMessage::setMainArgument(bool isMainArg) { myIsMainArgument = isMainArg; } + +bool Config_AttributeMessage::isGeometricalSelection() const +{ + return myIsGeometricalSelection; +} + +void Config_AttributeMessage::setGeometricalSelection(bool isGeometricalSelection) +{ + myIsGeometricalSelection = isGeometricalSelection; +} diff --git a/src/Config/Config_AttributeMessage.h b/src/Config/Config_AttributeMessage.h index cb4ef232c..4df9cd8b4 100644 --- a/src/Config/Config_AttributeMessage.h +++ b/src/Config/Config_AttributeMessage.h @@ -42,6 +42,7 @@ class Config_AttributeMessage : public Events_Message bool myIsObligatory; ///< Required to be set by user, else it's feature is invalid. bool myIsConcealment; ///< If true, conceals features used as input bool myIsMainArgument; ///< Mark attribute as a main argument of the feature + bool myIsGeometricalSelection; ///< If true selects geometry instead of shape; ///< a list of pairs, if the attribute is placed inside paged containers: (case, switch) std::list > myCases; @@ -69,6 +70,8 @@ public: CONFIG_EXPORT bool isConcealment() const; /// Returns true if attribute is a main argument of the feature CONFIG_EXPORT bool isMainArgument() const; + /// Returns true if attribute selects geometry instead of shape; + CONFIG_EXPORT bool isGeometricalSelection() const; /// Returns container of ids of pair of a case and switches CONFIG_EXPORT const std::list >& getCases() const; /// Sets ids of pair of a case and switches @@ -84,6 +87,8 @@ public: CONFIG_EXPORT void setObligatory(bool isObligatory); /// Set a state that the attribute is a main argument of the feature CONFIG_EXPORT void setMainArgument(bool isMainArg); + /// Set attribute's geometrical selection state + CONFIG_EXPORT void setGeometricalSelection(bool isGeometricalSelection); }; #endif // ATTRIBUTE_MESSAGE_H diff --git a/src/Config/Config_FeatureReader.cpp b/src/Config/Config_FeatureReader.cpp index c76aee821..85638935c 100644 --- a/src/Config/Config_FeatureReader.cpp +++ b/src/Config/Config_FeatureReader.cpp @@ -89,6 +89,9 @@ void Config_FeatureReader::processNode(xmlNodePtr theNode) aMessage->setConcealment(isConcealment); bool isMainArg = isConcealment && getBooleanAttribute(theNode, ATTR_MAIN_ARG, false); aMessage->setMainArgument(isMainArg); + aMessage->setGeometricalSelection(getBooleanAttribute(theNode, + ATTR_GEOMETRICAL_SELECTION, + false)); std::list > aCases; xmlNodePtr aCaseNode = hasParentRecursive(theNode, diff --git a/src/Config/Config_Keywords.h b/src/Config/Config_Keywords.h index beb599b20..eb3085ce6 100644 --- a/src/Config/Config_Keywords.h +++ b/src/Config/Config_Keywords.h @@ -100,6 +100,8 @@ const static char* ATTR_USE_RESET = "use_reset"; const static char* ATTR_GREED = "greed"; const static char* ATTR_MODIFIED_IN_EDIT = "modified_in_edit"; const static char* ATTR_MAIN_ARG = "main_argument"; +const static char* ATTR_GEOMETRICAL_SELECTION = "geometrical_selection"; + // WDG_INFO properties const static char* INFO_WDG_TEXT = FEATURE_TEXT; diff --git a/src/ConstructionPlugin/ConstructionPlugin_Axis.cpp b/src/ConstructionPlugin/ConstructionPlugin_Axis.cpp index 5f4b2f8d6..44dbc0875 100644 --- a/src/ConstructionPlugin/ConstructionPlugin_Axis.cpp +++ b/src/ConstructionPlugin/ConstructionPlugin_Axis.cpp @@ -33,6 +33,7 @@ #include #include #include +#include #include #include #include @@ -162,16 +163,26 @@ void ConstructionPlugin_Axis::createAxisByPointAndDirection() void ConstructionPlugin_Axis::createAxisByCylindricalFace() { - std::shared_ptr aSelection = data()->selection(CYLINDRICAL_FACE())->value(); - // update arguments due to the selection value - if (aSelection && !aSelection->isNull() && aSelection->isFace()) { - std::shared_ptr anEdge = GeomAlgoAPI_EdgeBuilder::cylinderAxis(aSelection); - - ResultConstructionPtr aConstr = document()->createConstruction(data()); - aConstr->setInfinite(true); - aConstr->setShape(anEdge); - setResult(aConstr); - } + std::shared_ptr aSelection = data()->selection(CYLINDRICAL_FACE())->value(); + // update arguments due to the selection value + + if (!aSelection.get() || aSelection->isNull()) { + return; + } + + if (aSelection->isCompound()) { + GeomAPI_ShapeIterator anIt(aSelection); + aSelection = anIt.current(); + } + + if (aSelection->isFace()) { + std::shared_ptr anEdge = GeomAlgoAPI_EdgeBuilder::cylinderAxis(aSelection); + + ResultConstructionPtr aConstr = document()->createConstruction(data()); + aConstr->setInfinite(true); + aConstr->setShape(anEdge); + setResult(aConstr); + } } void ConstructionPlugin_Axis::createAxisByDimensions() @@ -203,7 +214,14 @@ void ConstructionPlugin_Axis::createAxisByLine() if(!aLineShape.get()) { aLineShape = anEdgeSelection->context()->shape(); } - std::shared_ptr anEdge(new GeomAPI_Edge(aLineShape)); + GeomEdgePtr anEdge; + if (aLineShape->isEdge()) { + anEdge = aLineShape->edge(); + } + else if (aLineShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aLineShape); + anEdge = anIt.current()->edge(); + } ResultConstructionPtr aConstr = document()->createConstruction(data()); aConstr->setInfinite(true); @@ -219,7 +237,14 @@ void ConstructionPlugin_Axis::createAxisByPlaneAndPoint() if(!aFaceShape.get()) { aFaceShape = aFaceSelection->context()->shape(); } - std::shared_ptr aFace(new GeomAPI_Face(aFaceShape)); + GeomFacePtr aFace; + if (aFaceShape->isFace()) { + aFace = aFaceShape->face(); + } + else if (aFaceShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape); + aFace = anIt.current()->face(); + } std::shared_ptr aPln = aFace->getPlane(); // Get point. @@ -253,7 +278,14 @@ void ConstructionPlugin_Axis::createAxisByTwoPlanes() if(!aFaceShape1.get()) { aFaceShape1 = aFaceSelection1->context()->shape(); } - std::shared_ptr aFace1(new GeomAPI_Face(aFaceShape1)); + std::shared_ptr aFace1; + if (aFaceShape1->isFace()) { + aFace1 = aFaceShape1->face(); + } + else if (aFaceShape1->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape1); + aFace1 = anIt.current()->face(); + } std::shared_ptr aPln1 = aFace1->getPlane(); std::string useOffset1 = string(USE_OFFSET1())->value(); @@ -272,7 +304,14 @@ void ConstructionPlugin_Axis::createAxisByTwoPlanes() if(!aFaceShape2.get()) { aFaceShape2 = aFaceSelection2->context()->shape(); } - std::shared_ptr aFace2(new GeomAPI_Face(aFaceShape2)); + std::shared_ptr aFace2; + if (aFaceShape2->isFace()) { + aFace2 = aFaceShape2->face(); + } + else if (aFaceShape2->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape2); + aFace2 = anIt.current()->face(); + } std::shared_ptr aPln2 = aFace2->getPlane(); std::string useOffset2 = string(USE_OFFSET2())->value(); diff --git a/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp b/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp index 3680ab503..52e292035 100644 --- a/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp +++ b/src/ConstructionPlugin/ConstructionPlugin_Plane.cpp @@ -33,6 +33,7 @@ #include #include #include +#include #include #include @@ -228,7 +229,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByLineAndPoint() if(!aLineShape.get()) { aLineShape = anEdgeSelection->context()->shape(); } - std::shared_ptr anEdge(new GeomAPI_Edge(aLineShape)); + std::shared_ptr anEdge; + if (aLineShape->isEdge()) { + anEdge = aLineShape->edge(); + } + else if (aLineShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aLineShape); + anEdge = anIt.current()->edge(); + } // Get point. AttributeSelectionPtr aPointSelection = selection(POINT()); @@ -282,7 +290,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByDistanceFromOth return aPlane; } - std::shared_ptr aFace(new GeomAPI_Face(aShape)); + std::shared_ptr aFace; + if (aShape->isFace()) { + aFace = aShape->face(); + } + else if (aShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aShape); + aFace = anIt.current()->face(); + } std::shared_ptr aPln = aFace->getPlane(); std::shared_ptr aOrig = aPln->location(); @@ -305,7 +320,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByCoincidentPoint if(!aFaceShape.get()) { aFaceShape = aFaceSelection->context()->shape(); } - std::shared_ptr aFace(new GeomAPI_Face(aFaceShape)); + std::shared_ptr aFace; + if (aFaceShape->isFace()) { + aFace = aFaceShape->face(); + } + else if (aFaceShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape); + aFace = anIt.current()->face(); + } // Get point. AttributeSelectionPtr aPointSelection = selection(COINCIDENT_POINT()); @@ -333,7 +355,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByRotation() if(!aFaceShape.get()) { aFaceShape = aFaceSelection->context()->shape(); } - std::shared_ptr aFace(new GeomAPI_Face(aFaceShape)); + std::shared_ptr aFace; + if (aFaceShape->isFace()) { + aFace = aFaceShape->face(); + } + else if (aFaceShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape); + aFace = anIt.current()->face(); + } aFace = makeRectangularFace(aFace, aFace->getPlane()); // Get axis. @@ -342,7 +371,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByRotation() if(!anAxisShape.get()) { anAxisShape = anAxisSelection->context()->shape(); } - std::shared_ptr anEdge(new GeomAPI_Edge(anAxisShape)); + std::shared_ptr anEdge; + if (anAxisShape->isEdge()) { + anEdge = anAxisShape->edge(); + } + else if (anAxisShape->isCompound()) { + GeomAPI_ShapeIterator anIt(anAxisShape); + anEdge = anIt.current()->edge(); + } std::shared_ptr anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), @@ -375,7 +411,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByTwoParallelPlan if(!aFaceShape1.get()) { aFaceShape1 = aFaceSelection1->context()->shape(); } - std::shared_ptr aFace1(new GeomAPI_Face(aFaceShape1)); + std::shared_ptr aFace1; + if (aFaceShape1->isFace()) { + aFace1 = aFaceShape1->face(); + } + else if (aFaceShape1->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape1); + aFace1 = anIt.current()->face(); + } std::shared_ptr aPln1 = aFace1->getPlane(); // Get plane 2. @@ -384,7 +427,14 @@ std::shared_ptr ConstructionPlugin_Plane::createByTwoParallelPlan if(!aFaceShape2.get()) { aFaceShape2 = aFaceSelection2->context()->shape(); } - std::shared_ptr aFace2(new GeomAPI_Face(aFaceShape2)); + std::shared_ptr aFace2; + if (aFaceShape2->isFace()) { + aFace2 = aFaceShape2->face(); + } + else if (aFaceShape2->isCompound()) { + GeomAPI_ShapeIterator anIt(aFaceShape2); + aFace2 = anIt.current()->face(); + } std::shared_ptr aPln2 = aFace2->getPlane(); std::shared_ptr anOrig1 = aPln1->location(); diff --git a/src/ConstructionPlugin/ConstructionPlugin_Point.cpp b/src/ConstructionPlugin/ConstructionPlugin_Point.cpp index bb59c3d55..688f25333 100644 --- a/src/ConstructionPlugin/ConstructionPlugin_Point.cpp +++ b/src/ConstructionPlugin/ConstructionPlugin_Point.cpp @@ -36,6 +36,7 @@ #include #include #include +#include //================================================================================================== ConstructionPlugin_Point::ConstructionPlugin_Point() @@ -270,7 +271,14 @@ std::list > if(!aLineShape.get()) { aLineShape = aLineSelection->context()->shape(); } - std::shared_ptr anEdge(new GeomAPI_Edge(aLineShape)); + GeomEdgePtr anEdge; + if (aLineShape->isEdge()) { + anEdge = aLineShape->edge(); + } + else if (aLineShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aLineShape); + anEdge = anIt.current()->edge(); + } // Get plane. AttributeSelectionPtr aPlaneSelection= selection(INTERSECTION_PLANE()); @@ -278,7 +286,14 @@ std::list > if(!aPlaneShape.get()) { aPlaneShape = aPlaneSelection->context()->shape(); } - std::shared_ptr aFace(new GeomAPI_Face(aPlaneShape)); + GeomFacePtr aFace; + if (aPlaneShape->isFace()) { + aFace = aPlaneShape->face(); + } + else if (aPlaneShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aPlaneShape); + aFace = anIt.current()->face(); + } if (!string(USE_OFFSET())->value().empty()) { double anOffset = real(OFFSET())->value(); diff --git a/src/ConstructionPlugin/ConstructionPlugin_Validators.cpp b/src/ConstructionPlugin/ConstructionPlugin_Validators.cpp index 2390b83a4..50047dd69 100644 --- a/src/ConstructionPlugin/ConstructionPlugin_Validators.cpp +++ b/src/ConstructionPlugin/ConstructionPlugin_Validators.cpp @@ -27,6 +27,7 @@ #include #include #include +#include #include #include @@ -35,6 +36,7 @@ #include static std::shared_ptr getEdge(const GeomShapePtr theShape); +static std::shared_ptr getFace(const GeomShapePtr theShape); static std::shared_ptr getLin(const GeomShapePtr theShape); static std::shared_ptr getPln(const GeomShapePtr theShape); static std::shared_ptr getPnt(const GeomShapePtr theShape); @@ -114,7 +116,7 @@ bool ConstructionPlugin_ValidatorPointEdgeAndPlaneNotParallel::isValid( AttributeSelectionPtr anAttribute2 = aFeature->selection(theArguments.front()); std::shared_ptr anEdge; - std::shared_ptr aPln; + std::shared_ptr aFace; GeomShapePtr aShape1 = anAttribute1->value(); ResultPtr aContext1 = anAttribute1->context(); @@ -137,20 +139,20 @@ bool ConstructionPlugin_ValidatorPointEdgeAndPlaneNotParallel::isValid( bool isPlaneFirst = false; anEdge = getEdge(aShape1); - aPln = getPln(aShape2); - if(!anEdge.get() || !aPln.get()) { + + aFace = getFace(aShape2); + if(!anEdge.get() || !aFace.get()) { anEdge = getEdge(aShape2); - aPln = getPln(aShape1); + aFace = getFace(aShape1); isPlaneFirst = true; } - if(!anEdge.get() || !aPln.get()) { + if(!anEdge.get() || !aFace.get()) { theError = "Wrong shape types selected."; return false; } - std::shared_ptr aPlaneFace(new GeomAPI_Face(isPlaneFirst ? aShape1 : aShape2)); - if(GeomAlgoAPI_ShapeTools::isParallel(anEdge, aPlaneFace)) { + if(GeomAlgoAPI_ShapeTools::isParallel(anEdge, aFace)) { theError = "Plane and edge are parallel."; return false; } @@ -474,25 +476,51 @@ bool ConstructionPlugin_ValidatorPointThreeNonParallelPlanes::isValid( std::shared_ptr getEdge(const GeomShapePtr theShape) { - if(!theShape->isEdge()) { - return std::shared_ptr(); - } + GeomEdgePtr anEdge; - std::shared_ptr anEdge(new GeomAPI_Edge(theShape)); + if(theShape->isEdge()) { + anEdge = theShape->edge(); + } + else if (theShape->isCompound()) { + GeomAPI_ShapeIterator anIt(theShape); + anEdge = anIt.current()->edge(); + } return anEdge; } +GeomFacePtr getFace(const GeomShapePtr theShape) +{ + GeomFacePtr aFace; + + if (theShape->isFace()) { + aFace = theShape->face(); + } + else if (theShape->isCompound()) { + GeomAPI_ShapeIterator anIt(theShape); + aFace = anIt.current()->face(); + } + + return aFace; +} + std::shared_ptr getLin(const GeomShapePtr theShape) { std::shared_ptr aLin; - if(!theShape->isEdge()) { + GeomEdgePtr anEdge; + + if (theShape->isEdge()) { + anEdge = theShape->edge(); + } + else if (theShape->isCompound()) { + GeomAPI_ShapeIterator anIt(theShape); + anEdge = anIt.current()->edge(); + } + else { return aLin; } - std::shared_ptr anEdge(new GeomAPI_Edge(theShape)); - if(!anEdge->isLine()) { return aLin; } @@ -506,12 +534,19 @@ std::shared_ptr getPln(const GeomShapePtr theShape) { std::shared_ptr aPln; - if(!theShape->isFace()) { + GeomFacePtr aFace; + + if(theShape->isFace()) { + aFace = theShape->face(); + } + else if (theShape->isCompound()) { + GeomAPI_ShapeIterator anIt(theShape); + aFace = anIt.current()->face(); + } + else { return aPln; } - std::shared_ptr aFace(new GeomAPI_Face(theShape)); - if(!aFace->isPlanar()) { return aPln; } diff --git a/src/ConstructionPlugin/axis_widget.xml b/src/ConstructionPlugin/axis_widget.xml index 928d03022..4ccefe011 100644 --- a/src/ConstructionPlugin/axis_widget.xml +++ b/src/ConstructionPlugin/axis_widget.xml @@ -50,7 +50,8 @@ email : webmaster.salome@opencascade.com + shape_types="edge" + geometrical_selection="true"> @@ -59,7 +60,8 @@ email : webmaster.salome@opencascade.com + shape_types="face" + geometrical_selection="true"> @@ -68,7 +70,8 @@ email : webmaster.salome@opencascade.com + shape_types="face" + geometrical_selection="true"> + shape_types="face" + geometrical_selection="true"> @@ -95,7 +99,8 @@ email : webmaster.salome@opencascade.com + shape_types="face" + geometrical_selection="true"> diff --git a/src/ConstructionPlugin/plane_widget.xml b/src/ConstructionPlugin/plane_widget.xml index f23a4f406..dfe2007b3 100644 --- a/src/ConstructionPlugin/plane_widget.xml +++ b/src/ConstructionPlugin/plane_widget.xml @@ -55,7 +55,8 @@ email : webmaster.salome@opencascade.com + shape_types="edge" + geometrical_selection="true"> @@ -79,7 +80,8 @@ email : webmaster.salome@opencascade.com + shape_types="face" + geometrical_selection="true"> @@ -118,7 +120,8 @@ email : webmaster.salome@opencascade.com + shape_types="edge" + geometrical_selection="true"> + shape_types="face" + geometrical_selection="true"> @@ -148,7 +152,8 @@ email : webmaster.salome@opencascade.com + shape_types="face" + geometrical_selection="true"> diff --git a/src/ConstructionPlugin/point_widget.xml b/src/ConstructionPlugin/point_widget.xml index bd7439f8a..3ccf77550 100644 --- a/src/ConstructionPlugin/point_widget.xml +++ b/src/ConstructionPlugin/point_widget.xml @@ -141,7 +141,8 @@ email : webmaster.salome@opencascade.com + shape_types="edge" + geometrical_selection="true"> @@ -149,7 +150,8 @@ email : webmaster.salome@opencascade.com + shape_types="face" + geometrical_selection="true"> diff --git a/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp b/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp index baf8f6397..ceb01e793 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp @@ -31,6 +31,7 @@ #include #include #include +#include //================================================================================================= FeaturesPlugin_Extrusion::FeaturesPlugin_Extrusion() @@ -95,16 +96,29 @@ bool FeaturesPlugin_Extrusion::makeExtrusions(ListOfShape& theBaseShapes, getBaseShapes(theBaseShapes); //Getting direction. - std::shared_ptr aDir; - std::shared_ptr anEdge; + static const std::string aSelectionError = "Error: The direction shape selection is bad."; AttributeSelectionPtr aSelection = selection(DIRECTION_OBJECT_ID()); - if(aSelection.get() && aSelection->value().get() && aSelection->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(aSelection->value())); - } else if(aSelection->context().get() && - aSelection->context()->shape().get() && - aSelection->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(aSelection->context()->shape())); + GeomShapePtr aShape = aSelection->value(); + if (!aShape.get()) { + if (aSelection->context().get()) { + aShape = aSelection->context()->shape(); + } + } + + GeomEdgePtr anEdge; + if (aShape.get()) { + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); + } } + + std::shared_ptr aDir; if(anEdge.get()) { if(anEdge->isLine()) { aDir = anEdge->line()->direction(); @@ -134,6 +148,10 @@ bool FeaturesPlugin_Extrusion::makeExtrusions(ListOfShape& theBaseShapes, if(!aToShape.get() && aSelection->context().get()) { aToShape = aSelection->context()->shape(); } + if (aToShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aToShape); + aToShape = anIt.current(); + } } aSelection = selection(FROM_OBJECT_ID()); if(aSelection.get()) { @@ -141,6 +159,10 @@ bool FeaturesPlugin_Extrusion::makeExtrusions(ListOfShape& theBaseShapes, if(!aFromShape.get() && aSelection->context().get()) { aFromShape = aSelection->context()->shape(); } + if (aFromShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aFromShape); + aFromShape = anIt.current(); + } } } diff --git a/src/FeaturesPlugin/FeaturesPlugin_MultiRotation.cpp b/src/FeaturesPlugin/FeaturesPlugin_MultiRotation.cpp index 5f8870f59..ea1cf57d7 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_MultiRotation.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_MultiRotation.cpp @@ -15,6 +15,7 @@ #include #include #include +#include #include #include @@ -93,20 +94,43 @@ void FeaturesPlugin_MultiRotation::performRotation1D() } //Getting axis. - std::shared_ptr anAxis; - std::shared_ptr anEdge; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_MultiRotation::AXIS_ANGULAR_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(AXIS_ANGULAR_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + if (!aShape.get()) { + setError(aSelectionError); + return; + } + + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr anAxis(new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); // Getting number of copies. int nbCopies = diff --git a/src/FeaturesPlugin/FeaturesPlugin_MultiTranslation.cpp b/src/FeaturesPlugin/FeaturesPlugin_MultiTranslation.cpp index d23742c6d..76a644c2a 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_MultiTranslation.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_MultiTranslation.cpp @@ -25,6 +25,7 @@ #include #include #include +#include #include #include @@ -101,21 +102,44 @@ void FeaturesPlugin_MultiTranslation::performOneDirection() } //Getting axis. - std::shared_ptr anAxis; - std::shared_ptr anEdge; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_MultiTranslation::AXIS_FIRST_DIR_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(AXIS_FIRST_DIR_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + if (!aShape.get()) { + setError(aSelectionError); + return; + } + + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); + } + else + { + setError(aSelectionError); + return; } + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr anAxis (new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); + // Getting step. double aStep = real(FeaturesPlugin_MultiTranslation::STEP_FIRST_DIR_ID())->value(); @@ -222,32 +246,80 @@ void FeaturesPlugin_MultiTranslation::performTwoDirection() } //Getting axis. - std::shared_ptr aFirstAxis; - std::shared_ptr anEdge; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_MultiTranslation::AXIS_FIRST_DIR_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(AXIS_FIRST_DIR_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } } - if(anEdge) { - aFirstAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + if (!aShape.get()) { + setError(aSelectionError); + return; } - std::shared_ptr aSecondAxis; - anObjRef = selection(FeaturesPlugin_MultiTranslation::AXIS_SECOND_DIR_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); } - if(anEdge) { - aSecondAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr aFirstAxis(new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); + + //Getting axis. + anObjRef = selection(AXIS_SECOND_DIR_ID()); + aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return; + } + + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); + } + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr aSecondAxis(new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); // Getting step. double aFirstStep = real(FeaturesPlugin_MultiTranslation::STEP_FIRST_DIR_ID())->value(); diff --git a/src/FeaturesPlugin/FeaturesPlugin_Placement.cpp b/src/FeaturesPlugin/FeaturesPlugin_Placement.cpp index ab932f01d..187ee252f 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Placement.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Placement.cpp @@ -31,6 +31,7 @@ #include #include #include +#include #include #include @@ -121,21 +122,8 @@ void FeaturesPlugin_Placement::execute() // Verify planarity of faces and linearity of edges std::shared_ptr aShapes[2] = {aStartShape, anEndShape}; for (int i = 0; i < 2; i++) { - if (aShapes[i]->isFace()) { - std::shared_ptr aFace(new GeomAPI_Face(aShapes[i])); - if (!aFace->isPlanar()) { - static const std::string aPlanarityError = "Error: One of selected faces is not planar."; - setError(aPlanarityError); - return; - } - } - else if (aShapes[i]->isEdge()) { - std::shared_ptr anEdge(new GeomAPI_Edge(aShapes[i])); - if (!anEdge->isLine()) { - static const std::string aLinearityError = "Error: One of selected endges is not linear."; - setError(aLinearityError); - return; - } + if (!isShapeValid(aShapes[i])) { + return; } } @@ -199,6 +187,48 @@ void FeaturesPlugin_Placement::execute() removeResults(aResultIndex); } +//================================================================================================== +bool FeaturesPlugin_Placement::isShapeValid(GeomShapePtr theShape) +{ + if (theShape->isCompound()) { + GeomAPI_Shape::ShapeType aShapeType = GeomAPI_Shape::SHAPE; + for (GeomAPI_ShapeIterator anIt(theShape); anIt.more(); anIt.next()) { + GeomShapePtr aCurrentShape = anIt.current(); + if (aShapeType == GeomAPI_Shape::SHAPE) { + aShapeType = aCurrentShape->shapeType(); + } + else if (aShapeType != aCurrentShape->shapeType()) { + static const std::string aLinearityError = + "Error: Selected compound contains shapes with different types."; + setError(aLinearityError); + return false; + } + + if (!isShapeValid(aCurrentShape)) { + return false; + } + } + } + else if (theShape->isFace()) { + std::shared_ptr aFace(new GeomAPI_Face(theShape)); + if (!aFace->isPlanar()) { + static const std::string aPlanarityError = "Error: One of selected faces is not planar."; + setError(aPlanarityError); + return false; + } + } + else if (theShape->isEdge()) { + std::shared_ptr anEdge(new GeomAPI_Edge(theShape)); + if (!anEdge->isLine()) { + static const std::string aLinearityError = "Error: One of selected edges is not linear."; + setError(aLinearityError); + return false; + } + } + + return true; +} + //============================================================================ void FeaturesPlugin_Placement::loadNamingDS(GeomAlgoAPI_Transform& theTransformAlgo, std::shared_ptr theResultBody, diff --git a/src/FeaturesPlugin/FeaturesPlugin_Placement.h b/src/FeaturesPlugin/FeaturesPlugin_Placement.h index 1b8a7b6bd..e40392c14 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Placement.h +++ b/src/FeaturesPlugin/FeaturesPlugin_Placement.h @@ -96,6 +96,9 @@ class FeaturesPlugin_Placement : public ModelAPI_Feature /// Use plugin manager for features creation FeaturesPlugin_Placement(); private: + /// Checks validity of passed shape. + bool isShapeValid(GeomShapePtr theShape); + /// Load Naming data structure of the feature to the document void loadNamingDS(GeomAlgoAPI_Transform& theTransformAlgo, std::shared_ptr theResultBody, diff --git a/src/FeaturesPlugin/FeaturesPlugin_Revolution.cpp b/src/FeaturesPlugin/FeaturesPlugin_Revolution.cpp index 4a6433180..4ac87606e 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Revolution.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Revolution.cpp @@ -30,6 +30,7 @@ #include #include +#include //================================================================================================= FeaturesPlugin_Revolution::FeaturesPlugin_Revolution() @@ -92,17 +93,37 @@ bool FeaturesPlugin_Revolution::makeRevolutions(ListOfShape& theBaseShapes, // Getting base shapes. getBaseShapes(theBaseShapes); - //Getting axis. - std::shared_ptr anAxis; - std::shared_ptr anEdge; + // Getting axis. + static const std::string aSelectionError = "Error: The axis shape selection is bad."; AttributeSelectionPtr aSelection = selection(AXIS_OBJECT_ID()); - if(aSelection.get() && aSelection->value().get() && aSelection->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(aSelection->value())); - } else if(aSelection->context().get() && - aSelection->context()->shape().get() && - aSelection->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(aSelection->context()->shape())); + GeomShapePtr aShape = aSelection->value(); + if (!aShape.get()) { + if (aSelection->context().get()) { + aShape = aSelection->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return false; + } + + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } + else + { + setError(aSelectionError); + return false; + } + + std::shared_ptr anAxis; if(anEdge.get()) { if(anEdge->isLine()) { anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), @@ -137,6 +158,10 @@ bool FeaturesPlugin_Revolution::makeRevolutions(ListOfShape& theBaseShapes, if(!aToShape.get() && aSelection->context().get()) { aToShape = aSelection->context()->shape(); } + if (aToShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aToShape); + aToShape = anIt.current(); + } } aSelection = selection(FROM_OBJECT_ID()); if(aSelection.get()) { @@ -144,6 +169,10 @@ bool FeaturesPlugin_Revolution::makeRevolutions(ListOfShape& theBaseShapes, if(!aFromShape.get() && aSelection->context().get()) { aFromShape = aSelection->context()->shape(); } + if (aFromShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aFromShape); + aFromShape = anIt.current(); + } } } diff --git a/src/FeaturesPlugin/FeaturesPlugin_Rotation.cpp b/src/FeaturesPlugin/FeaturesPlugin_Rotation.cpp index 07d2d575c..81e244802 100755 --- a/src/FeaturesPlugin/FeaturesPlugin_Rotation.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Rotation.cpp @@ -30,6 +30,7 @@ #include #include +#include #include #include @@ -99,20 +100,43 @@ void FeaturesPlugin_Rotation::performTranslationByAxisAndAngle() } //Getting axis. - std::shared_ptr anAxis; - std::shared_ptr anEdge; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_Rotation::AXIS_OBJECT_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(AXIS_OBJECT_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return; } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr anAxis (new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); // Getting angle. double anAngle = real(FeaturesPlugin_Rotation::ANGLE_ID())->value(); diff --git a/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp b/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp index d50b74aa2..ff8988e80 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp @@ -30,6 +30,7 @@ #include #include #include +#include #include #include @@ -195,21 +196,45 @@ void FeaturesPlugin_Symmetry::performSymmetryByAxis() return; //Getting axis. - std::shared_ptr anAxis; - std::shared_ptr anEdge; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_Symmetry::AXIS_OBJECT_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(AXIS_OBJECT_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + if (!aShape.get()) { + setError(aSelectionError); + return; } + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); + } + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr anAxis (new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); + + // Moving each object. int aResultIndex = 0; std::list::iterator aContext = aContextes.begin(); @@ -271,23 +296,45 @@ void FeaturesPlugin_Symmetry::performSymmetryByPlane() if (!collectSourceObjects(anObjects, aContextes)) return; - //Getting axis. - std::shared_ptr aPlane; - std::shared_ptr aPln; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_Symmetry::PLANE_OBJECT_ID()); - if (anObjRef && anObjRef->value() && anObjRef->value()->isFace()) { - aPln = std::shared_ptr(new GeomAPI_Face(anObjRef->value()))->getPlane(); + //Getting plane. + static const std::string aSelectionError = "Error: The plane shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(PLANE_OBJECT_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } } - else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isFace()) { - aPln = - std::shared_ptr(new GeomAPI_Face(anObjRef->context()->shape()))->getPlane(); + if (!aShape.get()) { + setError(aSelectionError); + return; } - if (aPln) { - aPlane = std::shared_ptr(new GeomAPI_Ax2(aPln->location(), - aPln->direction())); + + GeomFacePtr aFace; + if (aShape->isFace()) + { + aFace = aShape->face(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + aFace = anIt.current()->face(); } + else + { + setError(aSelectionError); + return; + } + + if (!aFace.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr aPlane(new GeomAPI_Ax2(aFace->getPlane()->location(), + aFace->getPlane()->direction())); + // Moving each object. int aResultIndex = 0; diff --git a/src/FeaturesPlugin/FeaturesPlugin_Translation.cpp b/src/FeaturesPlugin/FeaturesPlugin_Translation.cpp index 0da4b6acc..f4469d2e9 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Translation.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Translation.cpp @@ -30,6 +30,7 @@ #include #include +#include #include #include @@ -112,21 +113,45 @@ void FeaturesPlugin_Translation::performTranslationByAxisAndDistance() } //Getting axis. - std::shared_ptr anAxis; - std::shared_ptr anEdge; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_Translation::AXIS_OBJECT_ID()); - if(anObjRef && anObjRef->value() && anObjRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->value())); - } else if (anObjRef && !anObjRef->value() && anObjRef->context() && - anObjRef->context()->shape() && anObjRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anObjRef->context()->shape())); + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + AttributeSelectionPtr anObjRef = selection(AXIS_OBJECT_ID()); + GeomShapePtr aShape = anObjRef->value(); + if (!aShape.get()) { + if (anObjRef->context().get()) { + aShape = anObjRef->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return; + } + + GeomEdgePtr anEdge; + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax1(anEdge->line()->location(), - anEdge->line()->direction())); + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; } + std::shared_ptr anAxis(new GeomAPI_Ax1(anEdge->line()->location(), + anEdge->line()->direction())); + + // Getting distance. double aDistance = real(FeaturesPlugin_Translation::DISTANCE_ID())->value(); diff --git a/src/FeaturesPlugin/FeaturesPlugin_Validators.cpp b/src/FeaturesPlugin/FeaturesPlugin_Validators.cpp index b991e38f0..0470dd73e 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Validators.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Validators.cpp @@ -474,6 +474,11 @@ bool FeaturesPlugin_ValidatorExtrusionDir::isValid( if(aContext.get()) { aDirShape = aContext->shape(); } + + if (aDirShape.get() && aDirShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aDirShape); + aDirShape = anIt.current(); + } } } diff --git a/src/FeaturesPlugin/extrusion_widget.xml b/src/FeaturesPlugin/extrusion_widget.xml index 910a623e3..6e14b846e 100644 --- a/src/FeaturesPlugin/extrusion_widget.xml +++ b/src/FeaturesPlugin/extrusion_widget.xml @@ -41,6 +41,7 @@ email : webmaster.salome@opencascade.com @@ -74,6 +75,7 @@ email : webmaster.salome@opencascade.com @@ -90,6 +92,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/FeaturesPlugin/extrusioncut_widget.xml b/src/FeaturesPlugin/extrusioncut_widget.xml index b176ddc18..c8bc95a8e 100755 --- a/src/FeaturesPlugin/extrusioncut_widget.xml +++ b/src/FeaturesPlugin/extrusioncut_widget.xml @@ -43,6 +43,7 @@ email : webmaster.salome@opencascade.com @@ -76,6 +77,7 @@ email : webmaster.salome@opencascade.com @@ -91,6 +93,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/FeaturesPlugin/extrusionfuse_widget.xml b/src/FeaturesPlugin/extrusionfuse_widget.xml index e65b6b4af..0891b5589 100644 --- a/src/FeaturesPlugin/extrusionfuse_widget.xml +++ b/src/FeaturesPlugin/extrusionfuse_widget.xml @@ -43,6 +43,7 @@ email : webmaster.salome@opencascade.com @@ -76,6 +77,7 @@ email : webmaster.salome@opencascade.com @@ -91,6 +93,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/FeaturesPlugin/multirotation_widget.xml b/src/FeaturesPlugin/multirotation_widget.xml index 8396f4869..747af9377 100644 --- a/src/FeaturesPlugin/multirotation_widget.xml +++ b/src/FeaturesPlugin/multirotation_widget.xml @@ -15,7 +15,8 @@ label="Axis" tooltip="Select an edge for the angular direction" shape_types="edge" - default=""> + default="" + geometrical_selection="true"> diff --git a/src/FeaturesPlugin/multitranslation_widget.xml b/src/FeaturesPlugin/multitranslation_widget.xml index b6137c34e..4eed46173 100644 --- a/src/FeaturesPlugin/multitranslation_widget.xml +++ b/src/FeaturesPlugin/multitranslation_widget.xml @@ -34,7 +34,8 @@ email : webmaster.salome@opencascade.com + default="" + geometrical_selection="true"> + default="" + geometrical_selection="true"> + shape_types="face edge vertex" + geometrical_selection="true"> + shape_types="face edge vertex" + geometrical_selection="true"> diff --git a/src/FeaturesPlugin/revolution_widget.xml b/src/FeaturesPlugin/revolution_widget.xml index 3d71c3d84..3bc2c6683 100644 --- a/src/FeaturesPlugin/revolution_widget.xml +++ b/src/FeaturesPlugin/revolution_widget.xml @@ -41,6 +41,7 @@ email : webmaster.salome@opencascade.com @@ -74,6 +75,7 @@ email : webmaster.salome@opencascade.com @@ -90,6 +92,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/FeaturesPlugin/revolutioncut_widget.xml b/src/FeaturesPlugin/revolutioncut_widget.xml index 12f2f247f..297fc706f 100644 --- a/src/FeaturesPlugin/revolutioncut_widget.xml +++ b/src/FeaturesPlugin/revolutioncut_widget.xml @@ -43,6 +43,7 @@ email : webmaster.salome@opencascade.com @@ -76,6 +77,7 @@ email : webmaster.salome@opencascade.com @@ -91,6 +93,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/FeaturesPlugin/revolutionfuse_widget.xml b/src/FeaturesPlugin/revolutionfuse_widget.xml index 6d1bb8394..5e358ee66 100644 --- a/src/FeaturesPlugin/revolutionfuse_widget.xml +++ b/src/FeaturesPlugin/revolutionfuse_widget.xml @@ -43,6 +43,7 @@ email : webmaster.salome@opencascade.com @@ -76,6 +77,7 @@ email : webmaster.salome@opencascade.com @@ -91,6 +93,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/FeaturesPlugin/rotation_widget.xml b/src/FeaturesPlugin/rotation_widget.xml index c07bd8ba8..418998210 100755 --- a/src/FeaturesPlugin/rotation_widget.xml +++ b/src/FeaturesPlugin/rotation_widget.xml @@ -37,7 +37,8 @@ email : webmaster.salome@opencascade.com + default="" + geometrical_selection="true"> + default="" + geometrical_selection="true"> diff --git a/src/FeaturesPlugin/translation_widget.xml b/src/FeaturesPlugin/translation_widget.xml index 28bb25115..3e5ef8260 100644 --- a/src/FeaturesPlugin/translation_widget.xml +++ b/src/FeaturesPlugin/translation_widget.xml @@ -37,7 +37,8 @@ email : webmaster.salome@opencascade.com + default="" + geometrical_selection="true"> +#include #include #include @@ -28,6 +29,7 @@ #include #include #include +#include #include #include @@ -70,29 +72,48 @@ void GeomAlgoAPI_Placement::build(const std::shared_ptr& theSourc GProp_GProps aProps; static const double aPropEps = 1.e-4; + GeomShapePtr aShape; + bool isCompound = false; for (int i = 0; i < aNbObjects; i++) { - if (aShapes[i]->isFace()) { - std::shared_ptr aFace(new GeomAPI_Face(aShapes[i])); + aShape = aShapes[i]; + isCompound = false; + if (aShapes[i]->isCompound()) { + isCompound = true; + GeomAPI_ShapeIterator anIt(aShapes[i]); + aShape = anIt.current(); + + GeomPointPtr aPnt = GeomAlgoAPI_ShapeTools::centreOfMass(aShapes[i]); + aSrcDstPoints[i].SetCoord(aPnt->x(), aPnt->y(), aPnt->z()); + } + + if (aShape->isFace()) { + std::shared_ptr aFace(new GeomAPI_Face(aShape)); std::shared_ptr aPlane = aFace->getPlane(); std::shared_ptr aDir = aPlane->direction(); aSrcDstNormals[i].SetCoord(aDir->x(), aDir->y(), aDir->z()); - BRepGProp::SurfaceProperties(aFace->impl(), aProps, aPropEps); - gp_Pnt aLoc = aProps.CentreOfMass(); - aSrcDstPoints[i].SetCoord(aLoc.X(), aLoc.Y(), aLoc.Z()); + if (!isCompound) { + BRepGProp::SurfaceProperties(aFace->impl(), aProps, aPropEps); + gp_Pnt aLoc = aProps.CentreOfMass(); + aSrcDstPoints[i].SetCoord(aLoc.X(), aLoc.Y(), aLoc.Z()); + } } - else if (aShapes[i]->isEdge()) { - std::shared_ptr anEdge(new GeomAPI_Edge(aShapes[i])); + else if (aShape->isEdge()) { + std::shared_ptr anEdge(new GeomAPI_Edge(aShape)); std::shared_ptr aLine = anEdge->line(); std::shared_ptr aDir = aLine->direction(); - std::shared_ptr aFirstPnt = anEdge->firstPoint(); - std::shared_ptr aLastPnt = anEdge->lastPoint(); - std::shared_ptr aLoc = aFirstPnt->xyz()->added(aLastPnt->xyz())->multiplied(0.5); - aSrcDstPoints[i].SetCoord(aLoc->x(), aLoc->y(), aLoc->z()); aSrcDstDirections[i].SetCoord(aDir->x(), aDir->y(), aDir->z()); + + if (!isCompound) { + std::shared_ptr aFirstPnt = anEdge->firstPoint(); + std::shared_ptr aLastPnt = anEdge->lastPoint(); + std::shared_ptr aLoc = aFirstPnt->xyz()->added(aLastPnt->xyz()) + ->multiplied(0.5); + aSrcDstPoints[i].SetCoord(aLoc->x(), aLoc->y(), aLoc->z()); + } } - else if (aShapes[i]->isVertex()) { - std::shared_ptr aVertex(new GeomAPI_Vertex(aShapes[i])); + else if (aShape->isVertex()) { + std::shared_ptr aVertex(new GeomAPI_Vertex(aShape)); std::shared_ptr aPnt = aVertex->point(); aSrcDstPoints[i].SetCoord(aPnt->x(), aPnt->y(), aPnt->z()); } else // something goes wrong diff --git a/src/GeomValidators/GeomValidators_Face.cpp b/src/GeomValidators/GeomValidators_Face.cpp index 945f9bc34..a5f9d588c 100644 --- a/src/GeomValidators/GeomValidators_Face.cpp +++ b/src/GeomValidators/GeomValidators_Face.cpp @@ -24,6 +24,7 @@ #include "ModelAPI_AttributeSelection.h" #include +#include #include @@ -46,6 +47,40 @@ GeomAbs_SurfaceType faceType(const std::string& theType) return GeomAbs_Plane; } +bool isValidFace(const GeomShapePtr theShape, + const GeomAbs_SurfaceType theFaceType, + Events_InfoMessage& theError) +{ + GeomFacePtr aGeomFace = theShape->face(); + + if (!aGeomFace.get()) { + theError = "The shape is not a face."; + return false; + } + + bool aValid = true; + + switch (theFaceType) { + case GeomAbs_Plane: { + aValid = aGeomFace->isPlanar(); + if (!aValid) theError = "The shape is not a plane."; + break; + } + case GeomAbs_Cylinder: { + aValid = aGeomFace->isCylindrical(); + if (!aValid) theError = "The shape is not a cylinder."; + break; + } + default: { + aValid = false; + theError = "The shape is not an available face."; + break; + } + } + + return aValid; +} + bool GeomValidators_Face::isValid(const AttributePtr& theAttribute, const std::list& theArguments, Events_InfoMessage& theError) const @@ -78,36 +113,22 @@ bool GeomValidators_Face::isValid(const AttributePtr& theAttribute, theError = "The shape is not a face."; } else { - std::shared_ptr aGeomFace(new GeomAPI_Face(aGeomShape)); - if (!aGeomFace.get()) { - aValid = false; - theError = "The shape is not a face."; + GeomAbs_SurfaceType aFaceType = GeomAbs_Plane; + if (theArguments.size() == 1) aFaceType = faceType(theArguments.front()); + if (aGeomShape->isFace()) { + isValidFace(aGeomShape, aFaceType, theError); } - else { - GeomAbs_SurfaceType aFaceType = GeomAbs_Plane; - if (theArguments.size() == 1) - aFaceType = faceType(theArguments.front()); - - switch (aFaceType) { - case GeomAbs_Plane: { - aValid = aGeomFace->isPlanar(); - if (!aValid) - theError = "The shape is not a plane."; - } - break; - case GeomAbs_Cylinder:{ - aValid = aGeomFace->isCylindrical(); - if (!aValid) - theError = "The shape is not a cylinder."; - } - break; - default: { - aValid = false; - theError = "The shape is not an available face."; + else if (aSelectionAttr->isGeometricalSelection() && aGeomShape->isCompound()) { + for (GeomAPI_ShapeIterator anIt(aGeomShape); anIt.more(); anIt.next()) { + if (!isValidFace(anIt.current(), aFaceType, theError)) { break; } } } + else { + aValid = false; + theError = "The shape is not a face."; + } } } return aValid; diff --git a/src/GeomValidators/GeomValidators_ShapeType.cpp b/src/GeomValidators/GeomValidators_ShapeType.cpp index afb7dd0c9..a7638e7be 100755 --- a/src/GeomValidators/GeomValidators_ShapeType.cpp +++ b/src/GeomValidators/GeomValidators_ShapeType.cpp @@ -22,6 +22,7 @@ #include "GeomValidators_Tools.h" #include +#include #include #include @@ -130,18 +131,27 @@ bool GeomValidators_ShapeType::isValidAttribute(const AttributePtr& theAttribute std::dynamic_pointer_cast(theAttribute); GeomShapePtr aShape = anAttr->value(); if (aShape.get()) - aValid = isValidShape(aShape, theShapeType, theError); + aValid = isValidShape(aShape, theShapeType, anAttr->isGeometricalSelection(), theError); else { if (anAttr->context().get()) - aValid = isValidObject(anAttr->context(), theShapeType, theError); + aValid = isValidObject(anAttr->context(), + theShapeType, + anAttr->isGeometricalSelection(), + theError); else - aValid = isValidObject(anAttr->contextFeature(), theShapeType, theError); + aValid = isValidObject(anAttr->contextFeature(), + theShapeType, + anAttr->isGeometricalSelection(), + theError); } } else if (anAttributeType == ModelAPI_AttributeRefAttr::typeId()) { AttributeRefAttrPtr anAttr = std::dynamic_pointer_cast(theAttribute); if (anAttr->isObject()) { - aValid = isValidObject(anAttr->object(), theShapeType, theError); + aValid = isValidObject(anAttr->object(), + theShapeType, + false, + theError); } else if (theShapeType == Vertex) { AttributePtr aRefAttr = anAttr->attr(); @@ -162,7 +172,7 @@ bool GeomValidators_ShapeType::isValidAttribute(const AttributePtr& theAttribute else if (anAttributeType == ModelAPI_AttributeReference::typeId()) { AttributeReferencePtr anAttr = std::dynamic_pointer_cast(theAttribute); - aValid = isValidObject(anAttr->value(), theShapeType, theError); + aValid = isValidObject(anAttr->value(), theShapeType, false, theError); } else if (anAttributeType == ModelAPI_AttributeSelectionList::typeId()) { AttributeSelectionListPtr aListAttr = @@ -190,6 +200,7 @@ bool GeomValidators_ShapeType::isValidAttribute(const AttributePtr& theAttribute bool GeomValidators_ShapeType::isValidObject(const ObjectPtr& theObject, const TypeOfShape theShapeType, + const bool theIsGeometricalSelection, Events_InfoMessage& theError) const { bool aValid = true; @@ -214,7 +225,7 @@ bool GeomValidators_ShapeType::isValidObject(const ObjectPtr& theObject, aValid = false; theError = "The result is empty"; } else { - aValid = isValidShape(aResult->shape(), theShapeType, theError); + aValid = isValidShape(aResult->shape(), theShapeType, theIsGeometricalSelection, theError); } } else { FeaturePtr aFeature = std::dynamic_pointer_cast(theObject); @@ -231,6 +242,7 @@ bool GeomValidators_ShapeType::isValidObject(const ObjectPtr& theObject, bool GeomValidators_ShapeType::isValidShape(const GeomShapePtr theShape, const TypeOfShape theShapeType, + const bool theIsGeometricalSelection, Events_InfoMessage& theError) const { bool aValid = true; @@ -247,9 +259,21 @@ bool GeomValidators_ShapeType::isValidShape(const GeomShapePtr theShape, case Edge: aValid = theShape->isEdge(); break; - case Line: - aValid = theShape->isEdge() && GeomAPI_Curve(theShape).isLine(); + case Line: { + if (theIsGeometricalSelection && theShape->isCompound()) { + aValid = true; + for (GeomAPI_ShapeIterator anIt(theShape); anIt.more(); anIt.next()) { + if (!anIt.current()->isEdge() || !GeomAPI_Curve(anIt.current()).isLine()) { + aValid = false; + break; + } + } + } + else { + aValid = theShape->isEdge() && GeomAPI_Curve(theShape).isLine(); + } break; + } case Circle: aValid = theShape->isEdge() && GeomAPI_Curve(theShape).isCircle(); break; diff --git a/src/GeomValidators/GeomValidators_ShapeType.h b/src/GeomValidators/GeomValidators_ShapeType.h index daf9fda38..0606cd411 100644 --- a/src/GeomValidators/GeomValidators_ShapeType.h +++ b/src/GeomValidators/GeomValidators_ShapeType.h @@ -83,6 +83,7 @@ protected: /// \param[out] theError error message. bool isValidObject(const ObjectPtr& theObject, const TypeOfShape theShapeType, + const bool theIsGeometricalSelection, Events_InfoMessage& theError) const; /// Returns true if the attibute's object type satisfies the argument value @@ -91,6 +92,7 @@ protected: /// \param[out] theError error message. bool isValidShape(const GeomShapePtr theShape, const TypeOfShape theShapeType, + const bool theIsGeometricalSelection, Events_InfoMessage& theError) const; }; diff --git a/src/GeomValidators/GeomValidators_ZeroOffset.cpp b/src/GeomValidators/GeomValidators_ZeroOffset.cpp index 4a919d0c4..d6181783f 100644 --- a/src/GeomValidators/GeomValidators_ZeroOffset.cpp +++ b/src/GeomValidators/GeomValidators_ZeroOffset.cpp @@ -31,6 +31,7 @@ #include #include #include +#include #include #include @@ -131,6 +132,10 @@ bool GeomValidators_ZeroOffset::isValid(const std::shared_ptr& if(aToShape.get() == NULL && anAttrSel->context().get() != NULL) { aToShape = anAttrSel->context()->shape(); } + if (aToShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aToShape); + aToShape = anIt.current(); + } } anIt++; @@ -146,6 +151,10 @@ bool GeomValidators_ZeroOffset::isValid(const std::shared_ptr& if(aFromShape.get() == NULL && anAttrSel->context().get() != NULL) { aFromShape = anAttrSel->context()->shape(); } + if (aFromShape->isCompound()) { + GeomAPI_ShapeIterator anIt(aFromShape); + aFromShape = anIt.current(); + } } anIt++; diff --git a/src/Model/Model_AttributeSelection.cpp b/src/Model/Model_AttributeSelection.cpp index af1020ab5..90cbe4322 100644 --- a/src/Model/Model_AttributeSelection.cpp +++ b/src/Model/Model_AttributeSelection.cpp @@ -40,6 +40,7 @@ #include #include #include +#include #include #include #include @@ -451,6 +452,10 @@ void Model_AttributeSelection::setID(const std::string theID) { myRef.setID(theID); ModelAPI_AttributeSelection::setID(theID); + FeaturePtr aFeature = std::dynamic_pointer_cast(owner()); + // TODO: check if parent list have geometrical selection flag. + myIsGeometricalSelection = + ModelAPI_Session::get()->validators()->isGeometricalSelection(aFeature->getKind(), id()); } ResultPtr Model_AttributeSelection::context() @@ -774,7 +779,7 @@ void Model_AttributeSelection::selectBody( if (aEraseResults) // erase results without flash deleted and redisplay: do it after Select aFeatureOwner->removeResults(0, false, false); } - aSel.Select(aNewSub, aNewContext); + aSel.Select(aNewSub, aNewContext, myIsGeometricalSelection); // face may become divided after the model update, so, new labels may be added to the scope myScope.Clear(); @@ -864,6 +869,14 @@ std::string Model_AttributeSelection::namingName(const std::string& theDefaultNa return ""; } + if (myIsGeometricalSelection + && aSubSh.get() + && aSubSh->isCompound()) + { + GeomAPI_ShapeIterator anIt(aSubSh); + aSubSh = anIt.current(); + } + Model_SelectionNaming aSelNaming(selectionLabel()); std::string aResult = aSelNaming.namingName( aCont, aSubSh, theDefaultName, owner()->document() != aCont->document()); diff --git a/src/Model/Model_AttributeSelection.h b/src/Model/Model_AttributeSelection.h index cafa6ea37..380b998de 100644 --- a/src/Model/Model_AttributeSelection.h +++ b/src/Model/Model_AttributeSelection.h @@ -47,6 +47,9 @@ class Model_AttributeSelection : public ModelAPI_AttributeSelection CenterType myTmpCenterType; /// Reference to the partent attribute, if any (to split selection compounds in issue 1799) Model_AttributeSelectionList* myParent; + /// If true attribute selects geometry instead of shape. + bool myIsGeometricalSelection; + public: /// Defines the result and its selected sub-shape /// \param theContext object where the sub-shape was selected @@ -180,6 +183,11 @@ protected: void computeValues(ResultPtr theOldContext, ResultPtr theNewContext, TopoDS_Shape theValShape, TopTools_ListOfShape& theShapes); + /// Returns true if is geometrical selection. + virtual bool isGeometricalSelection() const { + return myIsGeometricalSelection; + }; + friend class Model_Data; friend class Model_AttributeSelectionList; }; diff --git a/src/Model/Model_AttributeSelectionList.cpp b/src/Model/Model_AttributeSelectionList.cpp index 9fb412407..c231bfd0e 100644 --- a/src/Model/Model_AttributeSelectionList.cpp +++ b/src/Model/Model_AttributeSelectionList.cpp @@ -332,11 +332,11 @@ std::shared_ptr // (if attribute is deleted and created, the abort updates attriute and makes the Attr invalid) std::shared_ptr aNewAttr = std::shared_ptr(new Model_AttributeSelection(aLabel)); - aNewAttr->setID(id()); if (owner()) { aNewAttr->setObject(owner()); aNewAttr->setParent(this); } + aNewAttr->setID(id()); return aNewAttr; } diff --git a/src/Model/Model_Session.cpp b/src/Model/Model_Session.cpp index 2a830e788..a7a032eea 100644 --- a/src/Model/Model_Session.cpp +++ b/src/Model/Model_Session.cpp @@ -471,6 +471,10 @@ void Model_Session::processEvent(const std::shared_ptr& theMessa if (!aCases.empty()) { validators()->registerCase(aMsgAttr->featureId(), aMsgAttr->attributeId(), aCases); } + if (aMsgAttr->isGeometricalSelection()) { + validators()->registerGeometricalSelection(aMsgAttr->featureId(), + aMsgAttr->attributeId()); + } } } // plugins information was started to load, so, it will be loaded diff --git a/src/Model/Model_Validator.cpp b/src/Model/Model_Validator.cpp index 41fa0f701..5bf41b289 100644 --- a/src/Model/Model_Validator.cpp +++ b/src/Model/Model_Validator.cpp @@ -377,3 +377,27 @@ bool Model_ValidatorsFactory::isMainArgument(std::string theFeature, std::string std::map::iterator aFound = myMainArgument.find(theFeature); return aFound != myMainArgument.end() && aFound->second == theAttribute; } + +void Model_ValidatorsFactory::registerGeometricalSelection(std::string theFeature, + std::string theAttribute) +{ + std::map >::iterator aFind = + myGeometricalSelection.find(theFeature); + if (aFind == myGeometricalSelection.end()) { + std::set aNewSet; + aNewSet.insert(theAttribute); + myGeometricalSelection[theFeature] = aNewSet; + } + else { + aFind->second.insert(theAttribute); + } +} + +bool Model_ValidatorsFactory::isGeometricalSelection(std::string theFeature, + std::string theAttribute) +{ + std::map >::iterator aFind = + myGeometricalSelection.find(theFeature); + return aFind != myGeometricalSelection.end() + && aFind->second.find(theAttribute) != aFind->second.end(); +} diff --git a/src/Model/Model_Validator.h b/src/Model/Model_Validator.h index 939cdf213..7dcf2ff98 100644 --- a/src/Model/Model_Validator.h +++ b/src/Model/Model_Validator.h @@ -58,6 +58,7 @@ class Model_ValidatorsFactory : public ModelAPI_ValidatorsFactory std::map > > > myCases; /// Stores main attribute for each feature std::map myMainArgument; + std::map > myGeometricalSelection; public: /// Registers the instance of the validator by the ID @@ -123,6 +124,12 @@ class Model_ValidatorsFactory : public ModelAPI_ValidatorsFactory /// Returns true is the attribute is a main argument of the feature virtual bool isMainArgument(std::string theFeature, std::string theAttribute); + /// Register the selection attribute as geometrical selection + virtual void registerGeometricalSelection(std::string theFeature, std::string theAttribute); + + /// Returns true if the attribute is a geometrical selection + virtual bool isGeometricalSelection(std::string theFeature, std::string theAttribute); + protected: /// Adds the defualt validators that are usefull for all features. diff --git a/src/ModelAPI/ModelAPI_AttributeSelection.h b/src/ModelAPI/ModelAPI_AttributeSelection.h index 53e0151b8..ea37d4173 100644 --- a/src/ModelAPI/ModelAPI_AttributeSelection.h +++ b/src/ModelAPI/ModelAPI_AttributeSelection.h @@ -115,6 +115,9 @@ class ModelAPI_AttributeSelection : public ModelAPI_Attribute /// Returns true if recompute of selection become impossible virtual bool isInvalid() = 0; + /// Returns true if is geometrical selection. + virtual bool isGeometricalSelection() const = 0; + /// To virtually destroy the fields of successors MODELAPI_EXPORT virtual ~ModelAPI_AttributeSelection(); diff --git a/src/ModelAPI/ModelAPI_Validator.h b/src/ModelAPI/ModelAPI_Validator.h index a2c8af67a..e40e05536 100644 --- a/src/ModelAPI/ModelAPI_Validator.h +++ b/src/ModelAPI/ModelAPI_Validator.h @@ -128,6 +128,12 @@ class MODELAPI_EXPORT ModelAPI_ValidatorsFactory /// Returns true if the attribute must be checked (the case is selected) virtual bool isCase(FeaturePtr theFeature, std::string theAttribute) = 0; + /// Register the selection attribute as geometrical selection + virtual void registerGeometricalSelection(std::string theFeature, std::string theAttribute) = 0; + + /// Returns true if the attribute is a geometrical selection + virtual bool isGeometricalSelection(std::string theFeature, std::string theAttribute) = 0; + protected: /// Get instance from Session ModelAPI_ValidatorsFactory() diff --git a/src/ModelHighAPI/ModelHighAPI_Dumper.cpp b/src/ModelHighAPI/ModelHighAPI_Dumper.cpp index 92eaa64f2..7e33d61fe 100644 --- a/src/ModelHighAPI/ModelHighAPI_Dumper.cpp +++ b/src/ModelHighAPI/ModelHighAPI_Dumper.cpp @@ -25,6 +25,7 @@ #include #include #include +#include #include #include @@ -1067,6 +1068,11 @@ ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<( isDumpByGeom = aSelectedFeature && aSelectedFeature->isInHistory(); } + if (theAttrSelect->isGeometricalSelection() && aShape->shapeType() == GeomAPI_Shape::COMPOUND) { + GeomAPI_ShapeIterator anIt(aShape); + aShape = anIt.current(); + } + myDumpBuffer << "\"" << aShape->shapeTypeStr(); bool aStandardDump = true; if (isDumpByGeom) { diff --git a/src/PrimitivesPlugin/PrimitivesPlugin_Cone.cpp b/src/PrimitivesPlugin/PrimitivesPlugin_Cone.cpp index 2c2916586..2da170fd6 100644 --- a/src/PrimitivesPlugin/PrimitivesPlugin_Cone.cpp +++ b/src/PrimitivesPlugin/PrimitivesPlugin_Cone.cpp @@ -9,6 +9,7 @@ #include #include #include +#include #include @@ -82,21 +83,43 @@ void PrimitivesPlugin_Cone::execute() } // Getting axis. - std::shared_ptr anAxis; + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + std::shared_ptr anEdgeRef = selection(AXIS_ID()); + GeomShapePtr aShape = anEdgeRef->value(); + if (!aShape.get()) { + if (anEdgeRef->context().get()) { + aShape = anEdgeRef->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return; + } std::shared_ptr anEdge; - std::shared_ptr anEdgeRef = - selection(PrimitivesPlugin_Cone::AXIS_ID()); - if(anEdgeRef && anEdgeRef->value() && anEdgeRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anEdgeRef->value())); - } else if (anEdgeRef && !anEdgeRef->value() && anEdgeRef->context() && - anEdgeRef->context()->shape() && anEdgeRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anEdgeRef->context()->shape())); + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax2(aBasePoint, - anEdge->line()->direction())); + else + { + setError(aSelectionError); + return; } + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr anAxis(new GeomAPI_Ax2(aBasePoint, + anEdge->line()->direction())); + // Getting base radius, top radius and height double aBaseRadius = real(PrimitivesPlugin_Cone::BASE_RADIUS_ID())->value(); double aTopRadius = real(PrimitivesPlugin_Cone::TOP_RADIUS_ID())->value(); diff --git a/src/PrimitivesPlugin/PrimitivesPlugin_Cylinder.cpp b/src/PrimitivesPlugin/PrimitivesPlugin_Cylinder.cpp index c3d5b8223..9a80ed0ae 100644 --- a/src/PrimitivesPlugin/PrimitivesPlugin_Cylinder.cpp +++ b/src/PrimitivesPlugin/PrimitivesPlugin_Cylinder.cpp @@ -23,6 +23,7 @@ #include #include #include +#include #include @@ -112,21 +113,44 @@ void PrimitivesPlugin_Cylinder::createCylinder(bool withAngle) } // Getting axis. - std::shared_ptr anAxis; + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + std::shared_ptr anEdgeRef = selection(AXIS_ID()); + GeomShapePtr aShape = anEdgeRef->value(); + if (!aShape.get()) { + if (anEdgeRef->context().get()) { + aShape = anEdgeRef->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return; + } std::shared_ptr anEdge; - std::shared_ptr anEdgeRef = - selection(PrimitivesPlugin_Cylinder::AXIS_ID()); - if(anEdgeRef && anEdgeRef->value() && anEdgeRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anEdgeRef->value())); - } else if (anEdgeRef && !anEdgeRef->value() && anEdgeRef->context() && - anEdgeRef->context()->shape() && anEdgeRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anEdgeRef->context()->shape())); - } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax2(aBasePoint, - anEdge->line()->direction())); + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); + } + else + { + setError(aSelectionError); + return; + } + + if (!anEdge.get()) + { + setError(aSelectionError); + return; } + std::shared_ptr anAxis(new GeomAPI_Ax2(aBasePoint, + anEdge->line()->direction())); + + // Getting radius and height double aRadius = real(PrimitivesPlugin_Cylinder::RADIUS_ID())->value(); double aHeight = real(PrimitivesPlugin_Cylinder::HEIGHT_ID())->value(); diff --git a/src/PrimitivesPlugin/PrimitivesPlugin_Torus.cpp b/src/PrimitivesPlugin/PrimitivesPlugin_Torus.cpp index a086def17..cddab69e4 100644 --- a/src/PrimitivesPlugin/PrimitivesPlugin_Torus.cpp +++ b/src/PrimitivesPlugin/PrimitivesPlugin_Torus.cpp @@ -9,6 +9,7 @@ #include #include #include +#include #include @@ -80,21 +81,43 @@ void PrimitivesPlugin_Torus::execute() } // Getting axis. - std::shared_ptr anAxis; + static const std::string aSelectionError = "Error: The axis shape selection is bad."; + std::shared_ptr anEdgeRef = selection(AXIS_ID()); + GeomShapePtr aShape = anEdgeRef->value(); + if (!aShape.get()) { + if (anEdgeRef->context().get()) { + aShape = anEdgeRef->context()->shape(); + } + } + if (!aShape.get()) { + setError(aSelectionError); + return; + } std::shared_ptr anEdge; - std::shared_ptr anEdgeRef = - selection(PrimitivesPlugin_Torus::AXIS_ID()); - if(anEdgeRef && anEdgeRef->value() && anEdgeRef->value()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anEdgeRef->value())); - } else if (anEdgeRef && !anEdgeRef->value() && anEdgeRef->context() && - anEdgeRef->context()->shape() && anEdgeRef->context()->shape()->isEdge()) { - anEdge = std::shared_ptr(new GeomAPI_Edge(anEdgeRef->context()->shape())); + if (aShape->isEdge()) + { + anEdge = aShape->edge(); + } + else if (aShape->isCompound()) + { + GeomAPI_ShapeIterator anIt(aShape); + anEdge = anIt.current()->edge(); } - if(anEdge) { - anAxis = std::shared_ptr(new GeomAPI_Ax2(aBasePoint, - anEdge->line()->direction())); + else + { + setError(aSelectionError); + return; } + if (!anEdge.get()) + { + setError(aSelectionError); + return; + } + + std::shared_ptr anAxis(new GeomAPI_Ax2(aBasePoint, + anEdge->line()->direction())); + // Getting radius and ring radius double aRadius = real(PrimitivesPlugin_Torus::RADIUS_ID())->value(); double aRingRadius = real(PrimitivesPlugin_Torus::RING_RADIUS_ID())->value(); diff --git a/src/PrimitivesPlugin/cone_widget.xml b/src/PrimitivesPlugin/cone_widget.xml index 4f1acd5e4..710134ca0 100644 --- a/src/PrimitivesPlugin/cone_widget.xml +++ b/src/PrimitivesPlugin/cone_widget.xml @@ -16,6 +16,7 @@ label="axis" default="" shape_types="edge" + geometrical_selection="true" icon="icons/Primitives/axis.png" tooltip="Select the axis of the cone"> diff --git a/src/PrimitivesPlugin/cylinder_widget.xml b/src/PrimitivesPlugin/cylinder_widget.xml index 373bafb5f..2474f8bad 100644 --- a/src/PrimitivesPlugin/cylinder_widget.xml +++ b/src/PrimitivesPlugin/cylinder_widget.xml @@ -37,6 +37,7 @@ email : webmaster.salome@opencascade.com @@ -75,6 +76,7 @@ email : webmaster.salome@opencascade.com diff --git a/src/PrimitivesPlugin/torus_widget.xml b/src/PrimitivesPlugin/torus_widget.xml index 44d0ce688..30f6489e4 100644 --- a/src/PrimitivesPlugin/torus_widget.xml +++ b/src/PrimitivesPlugin/torus_widget.xml @@ -16,6 +16,7 @@ label="axis" default="" shape_types="edge" + geometrical_selection="true" icon="icons/Primitives/axis.png" tooltip="Select the axis of the torus"> diff --git a/src/SketchPlugin/SketchPlugin_Sketch.cpp b/src/SketchPlugin/SketchPlugin_Sketch.cpp index d23ad07d0..1b7753423 100755 --- a/src/SketchPlugin/SketchPlugin_Sketch.cpp +++ b/src/SketchPlugin/SketchPlugin_Sketch.cpp @@ -25,6 +25,7 @@ #include #include +#include #include #include @@ -255,7 +256,14 @@ void SketchPlugin_Sketch::attributeChanged(const std::string& theID) { std::shared_ptr aSelection = aSelAttr->value(); if (!aSelection.get()) aSelection = aSelAttr->context()->shape(); // update the sketch plane - std::shared_ptr aFace(new GeomAPI_Face(aSelection)); + std::shared_ptr aFace; + if (aSelection->isFace()) { + aFace = aSelection->face(); + } else if (aSelection->isCompound()) { + GeomAPI_ShapeIterator anIt(aSelection); + aFace = anIt.current()->face(); + } + std::shared_ptr aPlane = aFace->getPlane(); if (aPlane) { double anA, aB, aC, aD; -- 2.39.2