From 4c1678d0da83ae87144effaf9c99545bd30197cd Mon Sep 17 00:00:00 2001 From: azv Date: Wed, 19 Feb 2020 12:05:16 +0300 Subject: [PATCH] =?utf8?q?Task=203.2.=20To=20keep=20compounds=E2=80=99=20s?= =?utf8?q?ub-shapes=20for=20all=20operations=20(issue=20#3139)?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit Refactor the Symmetry feature. --- src/FeaturesAPI/FeaturesAPI.i | 1 + src/FeaturesAPI/FeaturesAPI_Symmetry.cpp | 12 +- src/FeaturesAPI/FeaturesAPI_Symmetry.h | 9 +- src/FeaturesPlugin/CMakeLists.txt | 10 + .../FeaturesPlugin_Symmetry.cpp | 316 +++++++----------- src/FeaturesPlugin/FeaturesPlugin_Symmetry.h | 28 +- .../TestSymmetry_MultiLevelCompound_v0_1.py | 195 +++++++++++ .../TestSymmetry_MultiLevelCompound_v0_2.py | 202 +++++++++++ .../TestSymmetry_MultiLevelCompound_v0_3.py | 206 ++++++++++++ .../TestSymmetry_MultiLevelCompound_v0_4.py | 182 ++++++++++ .../TestSymmetry_MultiLevelCompound_v0_5.py | 195 +++++++++++ .../TestSymmetry_MultiLevelCompound_v95_1.py | 163 +++++++++ .../TestSymmetry_MultiLevelCompound_v95_2.py | 165 +++++++++ .../TestSymmetry_MultiLevelCompound_v95_3.py | 160 +++++++++ .../TestSymmetry_MultiLevelCompound_v95_4.py | 182 ++++++++++ .../TestSymmetry_MultiLevelCompound_v95_5.py | 131 ++++++++ 16 files changed, 1947 insertions(+), 210 deletions(-) create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_1.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_2.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_3.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_4.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_5.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_1.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_2.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_3.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_4.py create mode 100644 src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_5.py diff --git a/src/FeaturesAPI/FeaturesAPI.i b/src/FeaturesAPI/FeaturesAPI.i index c2fc51795..965d8b33f 100644 --- a/src/FeaturesAPI/FeaturesAPI.i +++ b/src/FeaturesAPI/FeaturesAPI.i @@ -46,6 +46,7 @@ %feature("kwargs") addRotation; %feature("kwargs") addSplit; %feature("kwargs") addSmash; +%feature("kwargs") addSymmetry; %feature("kwargs") addTranslation; %feature("kwargs") addUnion; diff --git a/src/FeaturesAPI/FeaturesAPI_Symmetry.cpp b/src/FeaturesAPI/FeaturesAPI_Symmetry.cpp index 4a33af20d..6b27114f2 100644 --- a/src/FeaturesAPI/FeaturesAPI_Symmetry.cpp +++ b/src/FeaturesAPI/FeaturesAPI_Symmetry.cpp @@ -118,16 +118,24 @@ void FeaturesAPI_Symmetry::dump(ModelHighAPI_Dumper& theDumper) const theDumper << ", " << anAttrPlane; } - theDumper << ", " << keepOriginal() << ")" << std::endl; + theDumper << ", keepOriginal = " << keepOriginal(); + + if (!aBase->data()->version().empty()) + theDumper << ", keepSubResults = True"; + + theDumper << ")" << std::endl; } //================================================================================================== SymmetryPtr addSymmetry(const std::shared_ptr& thePart, const std::list& theMainObjects, const ModelHighAPI_Selection& theObject, - bool theKeepOriginal) + const bool theKeepOriginal, + const bool theKeepSubResults) { std::shared_ptr aFeature = thePart->addFeature(FeaturesAPI_Symmetry::ID()); + if (!theKeepSubResults) + aFeature->data()->setVersion(""); return SymmetryPtr(new FeaturesAPI_Symmetry( aFeature, theMainObjects, theObject, theKeepOriginal)); } diff --git a/src/FeaturesAPI/FeaturesAPI_Symmetry.h b/src/FeaturesAPI/FeaturesAPI_Symmetry.h index c760c0914..25c364e6c 100644 --- a/src/FeaturesAPI/FeaturesAPI_Symmetry.h +++ b/src/FeaturesAPI/FeaturesAPI_Symmetry.h @@ -93,9 +93,10 @@ typedef std::shared_ptr SymmetryPtr; /// \ingroup CPPHighAPI /// \brief Create Symmetry feature. FEATURESAPI_EXPORT -SymmetryPtr addSymmetry(const std::shared_ptr& thePart, - const std::list& theMainObjects, - const ModelHighAPI_Selection& theObject, - bool theKeepOriginal = true); +SymmetryPtr addSymmetry(const std::shared_ptr& part, + const std::list& objects, + const ModelHighAPI_Selection& basis, + const bool keepOriginal = true, + const bool keepSubResults = false); #endif // FEATURESAPI_SYMMETRY_H_ diff --git a/src/FeaturesPlugin/CMakeLists.txt b/src/FeaturesPlugin/CMakeLists.txt index 50f6c7b01..e479b26f0 100644 --- a/src/FeaturesPlugin/CMakeLists.txt +++ b/src/FeaturesPlugin/CMakeLists.txt @@ -599,4 +599,14 @@ ADD_UNIT_TESTS(TestExtrusion.py TestRotation_MultiLevelCompound_v95_2.py TestRotation_MultiLevelCompound_v95_3.py TestRotation_MultiLevelCompound_v95_4.py + TestSymmetry_MultiLevelCompound_v0_1.py + TestSymmetry_MultiLevelCompound_v0_2.py + TestSymmetry_MultiLevelCompound_v0_3.py + TestSymmetry_MultiLevelCompound_v0_4.py + TestSymmetry_MultiLevelCompound_v0_5.py + TestSymmetry_MultiLevelCompound_v95_1.py + TestSymmetry_MultiLevelCompound_v95_2.py + TestSymmetry_MultiLevelCompound_v95_3.py + TestSymmetry_MultiLevelCompound_v95_4.py + TestSymmetry_MultiLevelCompound_v95_5.py ) diff --git a/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp b/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp index 74acd252a..9656fc0e8 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Symmetry.cpp @@ -25,6 +25,7 @@ #include #include #include +#include #include #include @@ -43,6 +44,8 @@ #include +static const std::string SCALE_VERSION_1("v9.5"); + //================================================================================================= FeaturesPlugin_Symmetry::FeaturesPlugin_Symmetry() { @@ -69,6 +72,11 @@ void FeaturesPlugin_Symmetry::initAttributes() data()->addAttribute(FeaturesPlugin_Symmetry::KEEP_ORIGINAL_RESULT(), ModelAPI_AttributeBoolean::typeId()); + + if (!aSelection->isInitialized()) { + // new feature, not read from file + data()->setVersion(SCALE_VERSION_1); + } } //================================================================================================= @@ -77,54 +85,23 @@ void FeaturesPlugin_Symmetry::execute() AttributeStringPtr aMethodTypeAttr = string(FeaturesPlugin_Symmetry::CREATION_METHOD()); std::string aMethodType = aMethodTypeAttr->value(); - if (aMethodType == CREATION_METHOD_BY_POINT()) { - performSymmetryByPoint(); - } - - if (aMethodType == CREATION_METHOD_BY_AXIS()) { - performSymmetryByAxis(); - } + GeomTrsfPtr aTrsf; + if (aMethodType == CREATION_METHOD_BY_POINT()) + aTrsf = symmetryByPoint(); + else if (aMethodType == CREATION_METHOD_BY_AXIS()) + aTrsf = symmetryByAxis(); + else if (aMethodType == CREATION_METHOD_BY_PLANE()) + aTrsf = symmetryByPlane(); - if (aMethodType == CREATION_METHOD_BY_PLANE()) { - performSymmetryByPlane(); - } + performSymmetry(aTrsf); } //================================================================================================= -bool FeaturesPlugin_Symmetry::collectSourceObjects(ListOfShape& theSourceShapes, - std::list& theSourceResults) +GeomTrsfPtr FeaturesPlugin_Symmetry::symmetryByPoint() { - AttributeSelectionListPtr anObjectsSelList = - selectionList(FeaturesPlugin_Symmetry::OBJECTS_LIST_ID()); - if (anObjectsSelList->size() == 0) { - return false; - } - for (int anObjectsIndex = 0; anObjectsIndex < anObjectsSelList->size(); anObjectsIndex++) { - std::shared_ptr anObjectAttr = - anObjectsSelList->value(anObjectsIndex); - std::shared_ptr anObject = anObjectAttr->value(); - if (!anObject.get()) { // may be for not-activated parts - return false; - } - theSourceShapes.push_back(anObject); - theSourceResults.push_back(anObjectAttr->context()); - } - return true; -} - -//================================================================================================= -void FeaturesPlugin_Symmetry::performSymmetryByPoint() -{ - // Getting objects. - ListOfShape anObjects; - std::list aContextes; - if (!collectSourceObjects(anObjects, aContextes)) - return; - //Getting point. std::shared_ptr aPoint; - std::shared_ptr anObjRef = - selection(FeaturesPlugin_Symmetry::POINT_OBJECT_ID()); + AttributeSelectionPtr anObjRef = selection(FeaturesPlugin_Symmetry::POINT_OBJECT_ID()); if (anObjRef.get() != NULL) { GeomShapePtr aShape1 = anObjRef->value(); if (!aShape1.get()) { @@ -135,50 +112,14 @@ void FeaturesPlugin_Symmetry::performSymmetryByPoint() } } - // Moving each object. - std::string anError; - int aResultIndex = 0; - std::list::iterator aContext = aContextes.begin(); - for(ListOfShape::iterator anObjectsIt = anObjects.begin(); anObjectsIt != anObjects.end(); - anObjectsIt++, aContext++) { - std::shared_ptr aBaseShape = *anObjectsIt; - bool isPart = aContext->get() && (*aContext)->groupName() == ModelAPI_ResultPart::group(); - - // Setting result. - if (isPart) { - std::shared_ptr aTrsf(new GeomAPI_Trsf()); - aTrsf->setSymmetry(aPoint); - ResultPartPtr anOrigin = std::dynamic_pointer_cast(*aContext); - buildResult(anOrigin, aTrsf, aResultIndex); - } - else { - std::shared_ptr aSymmetryAlgo( - new GeomAlgoAPI_Symmetry(aBaseShape, aPoint)); - - // Checking that the algorithm worked properly. - if (GeomAlgoAPI_Tools::AlgoError::isAlgorithmFailed(aSymmetryAlgo, getKind(), anError)) { - setError(anError); - break; - } - - buildResult(aSymmetryAlgo, aBaseShape, aResultIndex); - } - aResultIndex++; - } - - // Remove the rest results if there were produced in the previous pass. - removeResults(aResultIndex); + GeomTrsfPtr aTrsf(new GeomAPI_Trsf); + aTrsf->setSymmetry(aPoint); + return aTrsf; } //================================================================================================= -void FeaturesPlugin_Symmetry::performSymmetryByAxis() +GeomTrsfPtr FeaturesPlugin_Symmetry::symmetryByAxis() { - // Getting objects. - ListOfShape anObjects; - std::list aContextes; - if (!collectSourceObjects(anObjects, aContextes)) - return; - //Getting axis. static const std::string aSelectionError = "Error: The axis shape selection is bad."; AttributeSelectionPtr anObjRef = selection(AXIS_OBJECT_ID()); @@ -190,7 +131,7 @@ void FeaturesPlugin_Symmetry::performSymmetryByAxis() } if (!aShape.get()) { setError(aSelectionError); - return; + return GeomTrsfPtr(); } GeomEdgePtr anEdge; @@ -207,57 +148,19 @@ void FeaturesPlugin_Symmetry::performSymmetryByAxis() if (!anEdge.get()) { setError(aSelectionError); - return; + return GeomTrsfPtr(); } std::shared_ptr anAxis (new GeomAPI_Ax1(anEdge->line()->location(), anEdge->line()->direction())); - - - // Moving each object. - std::string anError; - int aResultIndex = 0; - std::list::iterator aContext = aContextes.begin(); - for(ListOfShape::iterator anObjectsIt = anObjects.begin(); anObjectsIt != anObjects.end(); - anObjectsIt++, aContext++) { - std::shared_ptr aBaseShape = *anObjectsIt; - bool isPart = aContext->get() && (*aContext)->groupName() == ModelAPI_ResultPart::group(); - - // Setting result. - if (isPart) { - std::shared_ptr aTrsf(new GeomAPI_Trsf()); - aTrsf->setSymmetry(anAxis); - ResultPartPtr anOrigin = std::dynamic_pointer_cast(*aContext); - buildResult(anOrigin, aTrsf, aResultIndex); - } - else { - std::shared_ptr aSymmetryAlgo( - new GeomAlgoAPI_Symmetry(aBaseShape, anAxis)); - - // Checking that the algorithm worked properly. - if (GeomAlgoAPI_Tools::AlgoError::isAlgorithmFailed(aSymmetryAlgo, getKind(), anError)) { - setError(anError); - break; - } - - buildResult(aSymmetryAlgo, aBaseShape, aResultIndex); - } - aResultIndex++; - } - - // Remove the rest results if there were produced in the previous pass. - removeResults(aResultIndex); + GeomTrsfPtr aTrsf(new GeomAPI_Trsf); + aTrsf->setSymmetry(anAxis); + return aTrsf; } //================================================================================================= -void FeaturesPlugin_Symmetry::performSymmetryByPlane() +GeomTrsfPtr FeaturesPlugin_Symmetry::symmetryByPlane() { - // Getting objects. - ListOfShape anObjects; - std::list aContextes; - if (!collectSourceObjects(anObjects, aContextes)) - return; - //Getting plane. static const std::string aSelectionError = "Error: The plane shape selection is bad."; AttributeSelectionPtr anObjRef = selection(PLANE_OBJECT_ID()); @@ -269,7 +172,7 @@ void FeaturesPlugin_Symmetry::performSymmetryByPlane() } if (!aShape.get()) { setError(aSelectionError); - return; + return GeomTrsfPtr(); } GeomFacePtr aFace; @@ -286,77 +189,27 @@ void FeaturesPlugin_Symmetry::performSymmetryByPlane() if (!aFace.get()) { setError(aSelectionError); - return; + return GeomTrsfPtr(); } std::shared_ptr aPlane(new GeomAPI_Ax2(aFace->getPlane()->location(), aFace->getPlane()->direction())); - - - // Moving each object. - std::string anError; - int aResultIndex = 0; - std::list::iterator aContext = aContextes.begin(); - for(ListOfShape::iterator anObjectsIt = anObjects.begin(); anObjectsIt != anObjects.end(); - anObjectsIt++, aContext++) { - std::shared_ptr aBaseShape = *anObjectsIt; - bool isPart = aContext->get() && (*aContext)->groupName() == ModelAPI_ResultPart::group(); - - // Setting result. - if (isPart) { - std::shared_ptr aTrsf(new GeomAPI_Trsf()); - aTrsf->setSymmetry(aPlane); - ResultPartPtr anOrigin = std::dynamic_pointer_cast(*aContext); - buildResult(anOrigin, aTrsf, aResultIndex); - } else { - std::shared_ptr aSymmetryAlgo( - new GeomAlgoAPI_Symmetry(aBaseShape, aPlane)); - - // Checking that the algorithm worked properly. - if (GeomAlgoAPI_Tools::AlgoError::isAlgorithmFailed(aSymmetryAlgo, getKind(), anError)) { - setError(anError); - break; - } - - buildResult(aSymmetryAlgo, aBaseShape, aResultIndex); - } - aResultIndex++; - } - - // Remove the rest results if there were produced in the previous pass. - removeResults(aResultIndex); + GeomTrsfPtr aTrsf(new GeomAPI_Trsf); + aTrsf->setSymmetry(aPlane); + return aTrsf; } //================================================================================================= void FeaturesPlugin_Symmetry::buildResult( - std::shared_ptr& theSymmetryAlgo, - std::shared_ptr theBaseShape, int theResultIndex) + const std::shared_ptr& theAlgo, + const std::list >& theOriginalShapes, + std::shared_ptr theTargetShape, int& theResultIndex) { - std::shared_ptr anAlgoList(new GeomAlgoAPI_MakeShapeList()); - anAlgoList->appendAlgo(theSymmetryAlgo); - // Compose source shape and the result of symmetry. - GeomShapePtr aCompound; - if (boolean(KEEP_ORIGINAL_RESULT())->value()) { - ListOfShape aShapes; - // add a copy of a base shape otherwise selection of this base shape is bad (2592) - std::shared_ptr aCopyAlgo(new GeomAlgoAPI_Copy(theBaseShape)); - aShapes.push_back(aCopyAlgo->shape()); - anAlgoList->appendAlgo(aCopyAlgo); - - aShapes.push_back(theSymmetryAlgo->shape()); - aCompound = GeomAlgoAPI_CompoundBuilder::compound(aShapes); - } else - aCompound = theSymmetryAlgo->shape(); - // Store and name the result. ResultBodyPtr aResultBody = document()->createBody(data(), theResultIndex); - - ListOfShape aBaseShapes; - aBaseShapes.push_back(theBaseShape); - FeaturesPlugin_Tools::loadModifiedShapes(aResultBody, aBaseShapes, ListOfShape(), - anAlgoList, aCompound, "Symmetried"); - - setResult(aResultBody, theResultIndex); + FeaturesPlugin_Tools::loadModifiedShapes(aResultBody, theOriginalShapes, ListOfShape(), + theAlgo, theTargetShape, "Symmetried"); + setResult(aResultBody, theResultIndex++); } //================================================================================================= @@ -368,11 +221,96 @@ void FeaturesPlugin_Symmetry::buildResult(ResultPartPtr theOriginal, std::shared_ptr anIdentity(new GeomAPI_Trsf()); ResultPartPtr aCopy = document()->copyPart(theOriginal, data(), theResultIndex); aCopy->setTrsf(theOriginal, anIdentity); - setResult(aCopy, theResultIndex); - ++theResultIndex; + setResult(aCopy, theResultIndex++); } ResultPartPtr aResultPart = document()->copyPart(theOriginal, data(), theResultIndex); aResultPart->setTrsf(theOriginal, theTrsf); - setResult(aResultPart, theResultIndex); + setResult(aResultPart, theResultIndex++); +} + +//================================================================================================= +static bool performShapeSymmetry(std::shared_ptr& theAlgoList, + GeomAPI_ShapeHierarchy& theHierarchy, + GeomShapePtr theBaseShape, + GeomTrsfPtr theTrsf, + bool isKeepOriginalResult, + const std::string& theFeatureKind, + std::string& theError) +{ + std::shared_ptr aSymmetryAlgo( + new GeomAlgoAPI_Transform(theBaseShape, theTrsf)); + + // Checking that the algorithm worked properly. + if (GeomAlgoAPI_Tools::AlgoError::isAlgorithmFailed(aSymmetryAlgo, theFeatureKind, theError)) + return false; + + theAlgoList->appendAlgo(aSymmetryAlgo); + + // Compose source shape and the result of symmetry. + GeomShapePtr aCompound; + if (isKeepOriginalResult) { + ListOfShape aShapes; + // add a copy of a base shape otherwise selection of this base shape is bad (2592) + std::shared_ptr aCopyAlgo(new GeomAlgoAPI_Copy(theBaseShape)); + aShapes.push_back(aCopyAlgo->shape()); + theAlgoList->appendAlgo(aCopyAlgo); + + aShapes.push_back(aSymmetryAlgo->shape()); + aCompound = GeomAlgoAPI_CompoundBuilder::compound(aShapes); + } + else + aCompound = aSymmetryAlgo->shape(); + + theHierarchy.markModified(theBaseShape, aCompound); + return true; +} + +void FeaturesPlugin_Symmetry::performSymmetry(GeomTrsfPtr theTrsf) +{ + if (!theTrsf) { + setError("Invalid transformation."); + return; + } + + bool isKeepOriginal = boolean(KEEP_ORIGINAL_RESULT())->value(); + bool isKeepSubShapes = data()->version() == SCALE_VERSION_1; + + // Getting objects. + GeomAPI_ShapeHierarchy anObjects; + std::list aParts; + AttributeSelectionListPtr anObjSelList = selectionList(OBJECTS_LIST_ID()); + if (!FeaturesPlugin_Tools::shapesFromSelectionList( + anObjSelList, isKeepSubShapes, anObjects, aParts)) + return; + + std::string anError; + int aResultIndex = 0; + // Symmetrying parts. + for (std::list::iterator aPRes = aParts.begin(); aPRes != aParts.end(); ++aPRes) { + ResultPartPtr anOriginal = std::dynamic_pointer_cast(*aPRes); + buildResult(anOriginal, theTrsf, aResultIndex); + } + + // Collect transformations for each object in a part. + std::shared_ptr aMakeShapeList(new GeomAlgoAPI_MakeShapeList); + for (GeomAPI_ShapeHierarchy::iterator anObjectsIt = anObjects.begin(); + anObjectsIt != anObjects.end(); ++anObjectsIt) { + std::shared_ptr aBaseShape = *anObjectsIt; + if (!performShapeSymmetry(aMakeShapeList, anObjects, aBaseShape, theTrsf, + isKeepOriginal, getKind(), anError)) { + setError(anError); + break; + } + } + + // Build results of the rotation. + const ListOfShape& anOriginalShapes = anObjects.objects(); + ListOfShape aTopLevel; + anObjects.topLevelObjects(aTopLevel); + for (ListOfShape::iterator anIt = aTopLevel.begin(); anIt != aTopLevel.end(); ++anIt) + buildResult(aMakeShapeList, anOriginalShapes, *anIt, aResultIndex); + + // Remove the rest results if there were produced in the previous pass. + removeResults(aResultIndex); } diff --git a/src/FeaturesPlugin/FeaturesPlugin_Symmetry.h b/src/FeaturesPlugin/FeaturesPlugin_Symmetry.h index f91f29a2a..2917835da 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Symmetry.h +++ b/src/FeaturesPlugin/FeaturesPlugin_Symmetry.h @@ -24,10 +24,8 @@ #include -#include -#include - class GeomAPI_Trsf; +class GeomAlgoAPI_MakeShapeList; /** \class FeaturesPlugin_Symmetry * \ingroup Plugins @@ -123,23 +121,23 @@ class FeaturesPlugin_Symmetry : public ModelAPI_Feature FeaturesPlugin_Symmetry(); private: - /// Obtain list of source objects of the mirror - bool collectSourceObjects(ListOfShape& theSourceShapes, - std::list>& theSourceResults); + /// Calculate symmetry with respect to a point. + std::shared_ptr symmetryByPoint(); - /// Perform symmetry with respect to a point. - void performSymmetryByPoint(); + /// Calculate symmetry with respect to an axis. + std::shared_ptr symmetryByAxis(); - /// Perform symmetry with respect to an axis. - void performSymmetryByAxis(); + /// Calculate symmetry with respect to a plane. + std::shared_ptr symmetryByPlane(); - /// Perform symmetry with respect to a plane. - void performSymmetryByPlane(); + /// Perform the transformation + void performSymmetry(std::shared_ptr theTrsf); /// Create new result on given shapes and the index of result - void buildResult(std::shared_ptr& theSymmetryAlgo, - std::shared_ptr theBaseShape, - int theResultIndex); + void buildResult(const std::shared_ptr& theAlgo, + const std::list >& theOriginalShapes, + std::shared_ptr theTargetShape, + int& theResultIndex); /// Create new result for the given part and transformation void buildResult(std::shared_ptr theOriginal, diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_1.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_1.py new file mode 100644 index 000000000..933a2ec23 --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_1.py @@ -0,0 +1,195 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model + +from GeomAPI import * +from SketchAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.standardPlane("XOY")) +SketchEllipse_1 = Sketch_1.addEllipse(11.18033988749894, -50, 22.36067977499789, -50, 10) +[SketchPoint_1, SketchPoint_2, SketchPoint_3, SketchPoint_4, SketchPoint_5, SketchPoint_6, SketchPoint_7, SketchLine_1, SketchLine_2] = SketchEllipse_1.construction(center = "aux", firstFocus = "aux", secondFocus = "aux", majorAxisStart = "aux", majorAxisEnd = "aux", minorAxisStart = "aux", minorAxisEnd = "aux", majorAxis = "aux", minorAxis = "aux") +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_1.result()) +SketchConstraintLength_1 = Sketch_1.setLength(SketchLine_1.result(), 30) +SketchConstraintLength_2 = Sketch_1.setLength(SketchLine_2.result(), 20) +SketchProjection_1 = Sketch_1.addProjection(model.selection("EDGE", "PartSet/OY"), False) +SketchLine_3 = SketchProjection_1.createdFeature() +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchAPI_Point(SketchPoint_3).coordinates(), SketchLine_3.result()) +SketchConstraintDistance_1 = Sketch_1.setDistance(SketchAPI_Line(SketchLine_3).startPoint(), SketchAPI_Point(SketchPoint_3).coordinates(), 50, True) +SketchCircle_1 = Sketch_1.addCircle(41.18033988749897, -50, 5) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchCircle_1.center(), SketchLine_1.result()) +SketchConstraintDistance_2 = Sketch_1.setDistance(SketchEllipse_1.majorAxisPositive(), SketchCircle_1.center(), 15, True) +SketchConstraintRadius_1 = Sketch_1.setRadius(SketchCircle_1.results()[1], 5) +SketchMultiRotation_1 = Sketch_1.addRotation([SketchEllipse_1.result(), SketchCircle_1.results()[1]], SketchAPI_Point(SketchPoint_3).coordinates(), 360, 3, True) +[SketchEllipse_2, SketchEllipse_3, SketchCircle_2, SketchCircle_3] = SketchMultiRotation_1.rotated() +model.do() +Sketch_1.changeFacesOrder([[SketchEllipse_1.result(), SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchCircle_1.results()[1]], + [SketchEllipse_2.result(), SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_3.result(), SketchEllipse_2.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchCircle_2.results()[1]], + [SketchCircle_3.results()[1]] + ]) +model.do() +Extrusion_1 = model.addExtrusion(Part_1_doc, [model.selection("COMPOUND", "Sketch_1")], model.selection(), 10, 0) +Compound_1 = model.addCompound(Part_1_doc, [model.selection("SOLID", "Extrusion_1_2"), model.selection("SOLID", "Extrusion_1_3")]) +Compound_2_objects = [model.selection("COMPSOLID", "Extrusion_1_1"), model.selection("COMPOUND", "Compound_1_1"), model.selection("SOLID", "Extrusion_1_4")] +Compound_2 = model.addCompound(Part_1_doc, Compound_2_objects) +model.end() + +TOLERANCE = 1.e-7 +ORIGIN = GeomAPI_Pnt(0, 0, 0) +CENTER = GeomAPI_Pnt(SketchEllipse_1.center().pnt().x(), SketchEllipse_1.center().pnt().y(), 0) + +def symmetry(thePoint, theCenter): + return GeomAPI_Pnt(2 * theCenter.x() - thePoint.x(), 2 * theCenter.y() - thePoint.y(), 2 * theCenter.z() - thePoint.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Compound_2_1_1_5")], model.selection("VERTEX", "PartSet/Origin"), False) +model.testNbResults(Symmetry_1, 1) +model.testNbSubResults(Symmetry_1, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.FACE, [5]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.EDGE, [18]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.VERTEX, [36]) +model.testResultsVolumes(Symmetry_1, [542.746463956]) + +refPoint = symmetry(Extrusion_1.results()[0].subResult(4).resultSubShapePair()[0].shape().middlePoint(), ORIGIN) +midPoint = Symmetry_1.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_1 = model.addRecover(Part_1_doc, Symmetry_1, [Compound_2.result()], True) +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_1_1_2_1")], model.selection("VERTEX", "PartSet/Origin"), False) +model.testNbResults(Symmetry_2, 1) +model.testNbSubResults(Symmetry_2, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.FACE, [3]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.EDGE, [6]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.VERTEX, [12]) +model.testResultsVolumes(Symmetry_2, [785.39816339745]) + +refPoint = symmetry(Recover_1.result().subResult(1).subResult(0).resultSubShapePair()[0].shape().middlePoint(), ORIGIN) +midPoint = Symmetry_2.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_2 = model.addRecover(Part_1_doc, Symmetry_2, [Recover_1.result()], True) +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_2_1_3")], model.selection("VERTEX", "PartSet/Origin"), False) +model.testNbResults(Symmetry_3, 1) +model.testNbSubResults(Symmetry_3, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.FACE, [3]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.EDGE, [6]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.VERTEX, [12]) +model.testResultsVolumes(Symmetry_3, [785.39816339745]) + +refPoint = symmetry(Recover_2.result().subResult(2).resultSubShapePair()[0].shape().middlePoint(), ORIGIN) +midPoint = Symmetry_3.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_3 = model.addRecover(Part_1_doc, Symmetry_3, [Recover_2.result()], True) +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_3_1_1_1"), model.selection("SOLID", "Recover_3_1_2_2"), model.selection("SOLID", "Recover_3_1_3")], model.selection("VERTEX", "PartSet/Origin"), False) +model.testNbResults(Symmetry_4, 3) +model.testNbSubResults(Symmetry_4, [0, 0, 0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.SOLID, [1, 1, 1]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.FACE, [6, 3, 3]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.EDGE, [24, 6, 6]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.VERTEX, [48, 12, 12]) +model.testResultsVolumes(Symmetry_4, [3444.394198615, 785.39816339745, 785.39816339745]) + +REFERENCE = [Recover_3.result().subResult(0).subResult(0).resultSubShapePair()[0].shape().middlePoint(), + Recover_3.result().subResult(1).subResult(1).resultSubShapePair()[0].shape().middlePoint(), + Recover_3.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()] +for res, ref in zip(Symmetry_4.results(), REFERENCE): + ref = symmetry(ref, ORIGIN) + midPoint = res.resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE) + + +Recover_4 = model.addRecover(Part_1_doc, Symmetry_4, [Recover_3.result()], True) +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_4_1_1_5")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), True) +model.testNbResults(Symmetry_5, 1) +model.testNbSubResults(Symmetry_5, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.FACE, [10]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.EDGE, [36]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.VERTEX, [72]) +model.testResultsVolumes(Symmetry_5, [2 * 542.746463956]) + +midPoint = Symmetry_5.defaultResult().shape().middlePoint() +assert(midPoint.distance(CENTER) < TOLERANCE) + + +Recover_5 = model.addRecover(Part_1_doc, Symmetry_5, [Compound_2.result()], True) +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_5_1_2_1")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), True) +model.testNbResults(Symmetry_6, 1) +model.testNbSubResults(Symmetry_6, [2]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.EDGE, [12]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.VERTEX, [24]) +model.testResultsVolumes(Symmetry_6, [2 * 785.39816339745]) + +midPoint = Symmetry_6.defaultResult().shape().middlePoint() +assert(midPoint.distance(CENTER) < TOLERANCE) + + +Recover_6 = model.addRecover(Part_1_doc, Symmetry_6, [Recover_5.result()], True) +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_6_1_3")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), True) +model.testNbResults(Symmetry_7, 1) +model.testNbSubResults(Symmetry_7, [2]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.EDGE, [12]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.VERTEX, [24]) +model.testResultsVolumes(Symmetry_7, [2 * 785.39816339745]) + +midPoint = Symmetry_7.defaultResult().shape().middlePoint() +assert(midPoint.distance(CENTER) < TOLERANCE) + + +Recover_7 = model.addRecover(Part_1_doc, Symmetry_7, [Recover_6.result()], True) +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_7_1_1_1"), model.selection("SOLID", "Recover_7_1_2_2"), model.selection("SOLID", "Recover_7_1_3")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), True) +model.testNbResults(Symmetry_8, 3) +model.testNbSubResults(Symmetry_8, [2, 2, 2]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.SOLID, [2, 2, 2]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.FACE, [12, 6, 6]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.EDGE, [48, 12, 12]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.VERTEX, [96, 24, 24]) +model.testResultsVolumes(Symmetry_8, [2 * 3444.394198615, 2 * 785.39816339745, 2 * 785.39816339745]) + +for res in Symmetry_8.results(): + midPoint = res.resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(CENTER) < TOLERANCE) + + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_2.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_2.py new file mode 100644 index 000000000..5b7e80690 --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_2.py @@ -0,0 +1,202 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model + +from GeomAPI import * +from SketchAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.standardPlane("XOY")) +SketchEllipse_1 = Sketch_1.addEllipse(11.18033988749894, -50, 22.36067977499789, -50, 10) +[SketchPoint_1, SketchPoint_2, SketchPoint_3, SketchPoint_4, SketchPoint_5, SketchPoint_6, SketchPoint_7, SketchLine_1, SketchLine_2] = SketchEllipse_1.construction(center = "aux", firstFocus = "aux", secondFocus = "aux", majorAxisStart = "aux", majorAxisEnd = "aux", minorAxisStart = "aux", minorAxisEnd = "aux", majorAxis = "aux", minorAxis = "aux") +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_1.result()) +SketchConstraintLength_1 = Sketch_1.setLength(SketchLine_1.result(), 30) +SketchConstraintLength_2 = Sketch_1.setLength(SketchLine_2.result(), 20) +SketchProjection_1 = Sketch_1.addProjection(model.selection("EDGE", "PartSet/OY"), False) +SketchLine_3 = SketchProjection_1.createdFeature() +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchAPI_Point(SketchPoint_3).coordinates(), SketchLine_3.result()) +SketchConstraintDistance_1 = Sketch_1.setDistance(SketchAPI_Line(SketchLine_3).startPoint(), SketchAPI_Point(SketchPoint_3).coordinates(), 50, True) +SketchCircle_1 = Sketch_1.addCircle(41.18033988749897, -50, 5) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchCircle_1.center(), SketchLine_1.result()) +SketchConstraintDistance_2 = Sketch_1.setDistance(SketchEllipse_1.majorAxisPositive(), SketchCircle_1.center(), 15, True) +SketchConstraintRadius_1 = Sketch_1.setRadius(SketchCircle_1.results()[1], 5) +SketchMultiRotation_1 = Sketch_1.addRotation([SketchEllipse_1.result(), SketchCircle_1.results()[1]], SketchAPI_Point(SketchPoint_3).coordinates(), 360, 3, True) +[SketchEllipse_2, SketchEllipse_3, SketchCircle_2, SketchCircle_3] = SketchMultiRotation_1.rotated() +model.do() +Sketch_1.changeFacesOrder([[SketchEllipse_1.result(), SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchCircle_1.results()[1]], + [SketchEllipse_2.result(), SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_3.result(), SketchEllipse_2.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchCircle_2.results()[1]], + [SketchCircle_3.results()[1]] + ]) +model.do() +Extrusion_1 = model.addExtrusion(Part_1_doc, [model.selection("COMPOUND", "Sketch_1")], model.selection(), 10, 0) +Compound_1 = model.addCompound(Part_1_doc, [model.selection("SOLID", "Extrusion_1_2"), model.selection("SOLID", "Extrusion_1_3")]) +Compound_2_objects = [model.selection("COMPSOLID", "Extrusion_1_1"), model.selection("COMPOUND", "Compound_1_1"), model.selection("SOLID", "Extrusion_1_4")] +Compound_2 = model.addCompound(Part_1_doc, Compound_2_objects) +model.end() + +TOLERANCE = 1.e-7 + +def symmetryOX(thePoint): + return GeomAPI_Pnt(thePoint.x(), -thePoint.y(), -thePoint.z()) + +def middleOZ(thePoint): + return GeomAPI_Pnt(0, 0, thePoint.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Compound_2_1_1_5")], model.selection("EDGE", "PartSet/OX"), False) +model.testNbResults(Symmetry_1, 1) +model.testNbSubResults(Symmetry_1, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.FACE, [5]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.EDGE, [18]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.VERTEX, [36]) +model.testResultsVolumes(Symmetry_1, [542.746463956]) + +refPoint = symmetryOX(Extrusion_1.results()[0].subResult(4).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_1.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_1 = model.addRecover(Part_1_doc, Symmetry_1, [Compound_2.result()], True) +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_1_1_2_1")], model.selection("EDGE", "PartSet/OX"), False) +model.testNbResults(Symmetry_2, 1) +model.testNbSubResults(Symmetry_2, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.FACE, [3]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.EDGE, [6]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.VERTEX, [12]) +model.testResultsVolumes(Symmetry_2, [785.39816339745]) + +refPoint = symmetryOX(Recover_1.result().subResult(1).subResult(0).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_2.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_2 = model.addRecover(Part_1_doc, Symmetry_2, [Recover_1.result()], True) +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_2_1_3")], model.selection("EDGE", "PartSet/OX"), False) +model.testNbResults(Symmetry_3, 1) +model.testNbSubResults(Symmetry_3, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.FACE, [3]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.EDGE, [6]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.VERTEX, [12]) +model.testResultsVolumes(Symmetry_3, [785.39816339745]) + +refPoint = symmetryOX(Recover_2.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_3.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_3 = model.addRecover(Part_1_doc, Symmetry_3, [Recover_2.result()], True) +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_3_1_1_1"), model.selection("SOLID", "Recover_3_1_2_2"), model.selection("SOLID", "Recover_3_1_3")], model.selection("EDGE", "PartSet/OX"), False) +model.testNbResults(Symmetry_4, 3) +model.testNbSubResults(Symmetry_4, [0, 0, 0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.SOLID, [1, 1, 1]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.FACE, [6, 3, 3]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.EDGE, [24, 6, 6]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.VERTEX, [48, 12, 12]) +model.testResultsVolumes(Symmetry_4, [3444.394198615, 785.39816339745, 785.39816339745]) + +REFERENCE = [Recover_3.result().subResult(0).subResult(0).resultSubShapePair()[0].shape().middlePoint(), + Recover_3.result().subResult(1).subResult(1).resultSubShapePair()[0].shape().middlePoint(), + Recover_3.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()] +for res, ref in zip(Symmetry_4.results(), REFERENCE): + ref = symmetryOX(ref) + midPoint = res.resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE) + + +Recover_4 = model.addRecover(Part_1_doc, Symmetry_4, [Recover_3.result()], True) +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_4_1_1_5")], model.selection("EDGE", "PartSet/OZ"), True) +model.testNbResults(Symmetry_5, 1) +model.testNbSubResults(Symmetry_5, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.FACE, [10]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.EDGE, [36]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.VERTEX, [72]) +model.testResultsVolumes(Symmetry_5, [2 * 542.746463956]) + +refPoint = middleOZ(Recover_4.results()[0].subResult(0).subResult(4).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_5.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_5 = model.addRecover(Part_1_doc, Symmetry_5, [Compound_2.result()], True) +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_5_1_2_1")], model.selection("EDGE", "PartSet/OZ"), True) +model.testNbResults(Symmetry_6, 1) +model.testNbSubResults(Symmetry_6, [2]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.EDGE, [12]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.VERTEX, [24]) +model.testResultsVolumes(Symmetry_6, [2 * 785.39816339745]) + +refPoint = middleOZ(Recover_5.result().subResult(1).subResult(0).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_6.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_6 = model.addRecover(Part_1_doc, Symmetry_6, [Recover_5.result()], True) +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_6_1_3")], model.selection("EDGE", "PartSet/OZ"), True) +model.testNbResults(Symmetry_7, 1) +model.testNbSubResults(Symmetry_7, [2]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.EDGE, [12]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.VERTEX, [24]) +model.testResultsVolumes(Symmetry_7, [2 * 785.39816339745]) + +refPoint = middleOZ(Recover_6.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_7.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_7 = model.addRecover(Part_1_doc, Symmetry_7, [Recover_6.result()], True) +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_7_1_1_1"), model.selection("SOLID", "Recover_7_1_2_2"), model.selection("SOLID", "Recover_7_1_3")], model.selection("EDGE", "PartSet/OZ"), True) +model.testNbResults(Symmetry_8, 3) +model.testNbSubResults(Symmetry_8, [2, 2, 2]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.SOLID, [2, 2, 2]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.FACE, [12, 6, 6]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.EDGE, [48, 12, 12]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.VERTEX, [96, 24, 24]) +model.testResultsVolumes(Symmetry_8, [2 * 3444.394198615, 2 * 785.39816339745, 2 * 785.39816339745]) + +REFERENCE = [Recover_7.result().subResult(0).subResult(0).resultSubShapePair()[0].shape().middlePoint(), + Recover_7.result().subResult(1).subResult(1).resultSubShapePair()[0].shape().middlePoint(), + Recover_7.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()] +for res, ref in zip(Symmetry_8.results(), REFERENCE): + ref = middleOZ(ref) + midPoint = res.resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_3.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_3.py new file mode 100644 index 000000000..da5d5b3bd --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_3.py @@ -0,0 +1,206 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model + +from GeomAPI import * +from SketchAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.standardPlane("XOY")) +SketchEllipse_1 = Sketch_1.addEllipse(11.18033988749894, -50, 22.36067977499789, -50, 10) +[SketchPoint_1, SketchPoint_2, SketchPoint_3, SketchPoint_4, SketchPoint_5, SketchPoint_6, SketchPoint_7, SketchLine_1, SketchLine_2] = SketchEllipse_1.construction(center = "aux", firstFocus = "aux", secondFocus = "aux", majorAxisStart = "aux", majorAxisEnd = "aux", minorAxisStart = "aux", minorAxisEnd = "aux", majorAxis = "aux", minorAxis = "aux") +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_1.result()) +SketchConstraintLength_1 = Sketch_1.setLength(SketchLine_1.result(), 30) +SketchConstraintLength_2 = Sketch_1.setLength(SketchLine_2.result(), 20) +SketchProjection_1 = Sketch_1.addProjection(model.selection("EDGE", "PartSet/OY"), False) +SketchLine_3 = SketchProjection_1.createdFeature() +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchAPI_Point(SketchPoint_3).coordinates(), SketchLine_3.result()) +SketchConstraintDistance_1 = Sketch_1.setDistance(SketchAPI_Line(SketchLine_3).startPoint(), SketchAPI_Point(SketchPoint_3).coordinates(), 50, True) +SketchCircle_1 = Sketch_1.addCircle(41.18033988749897, -50, 5) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchCircle_1.center(), SketchLine_1.result()) +SketchConstraintDistance_2 = Sketch_1.setDistance(SketchEllipse_1.majorAxisPositive(), SketchCircle_1.center(), 15, True) +SketchConstraintRadius_1 = Sketch_1.setRadius(SketchCircle_1.results()[1], 5) +SketchMultiRotation_1 = Sketch_1.addRotation([SketchEllipse_1.result(), SketchCircle_1.results()[1]], SketchAPI_Point(SketchPoint_3).coordinates(), 360, 3, True) +[SketchEllipse_2, SketchEllipse_3, SketchCircle_2, SketchCircle_3] = SketchMultiRotation_1.rotated() +model.do() +Sketch_1.changeFacesOrder([[SketchEllipse_1.result(), SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchCircle_1.results()[1]], + [SketchEllipse_2.result(), SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_3.result(), SketchEllipse_2.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchCircle_2.results()[1]], + [SketchCircle_3.results()[1]] + ]) +model.do() +Extrusion_1 = model.addExtrusion(Part_1_doc, [model.selection("COMPOUND", "Sketch_1")], model.selection(), 10, 0) +Compound_1 = model.addCompound(Part_1_doc, [model.selection("SOLID", "Extrusion_1_2"), model.selection("SOLID", "Extrusion_1_3")]) +Compound_2_objects = [model.selection("COMPSOLID", "Extrusion_1_1"), model.selection("COMPOUND", "Compound_1_1"), model.selection("SOLID", "Extrusion_1_4")] +Compound_2 = model.addCompound(Part_1_doc, Compound_2_objects) +model.end() + +TOLERANCE = 1.e-7 + +def symmetryXOZ(thePoint): + return GeomAPI_Pnt(thePoint.x(), -thePoint.y(), thePoint.z()) + +def centerBB(theShape): + res = theShape.computeSize() + return GeomAPI_Pnt((res[1] + res[4]) / 2, (res[2] + res[5]) / 2, (res[3] + res[6]) / 2) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Compound_2_1_1_5")], model.selection("FACE", "PartSet/XOZ"), False) +model.testNbResults(Symmetry_1, 1) +model.testNbSubResults(Symmetry_1, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.FACE, [5]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.EDGE, [18]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.VERTEX, [36]) +model.testResultsVolumes(Symmetry_1, [542.746463956]) + +refPoint = symmetryXOZ(Extrusion_1.results()[0].subResult(4).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_1.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_1 = model.addRecover(Part_1_doc, Symmetry_1, [Compound_2.result()], True) +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_1_1_2_1")], model.selection("FACE", "PartSet/XOZ"), False) +model.testNbResults(Symmetry_2, 1) +model.testNbSubResults(Symmetry_2, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.FACE, [3]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.EDGE, [6]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.VERTEX, [12]) +model.testResultsVolumes(Symmetry_2, [785.39816339745]) + +refPoint = symmetryXOZ(Recover_1.result().subResult(1).subResult(0).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_2.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_2 = model.addRecover(Part_1_doc, Symmetry_2, [Recover_1.result()], True) +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_2_1_3")], model.selection("FACE", "PartSet/XOZ"), False) +model.testNbResults(Symmetry_3, 1) +model.testNbSubResults(Symmetry_3, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.FACE, [3]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.EDGE, [6]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.VERTEX, [12]) +model.testResultsVolumes(Symmetry_3, [785.39816339745]) + +refPoint = symmetryXOZ(Recover_2.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()) +midPoint = Symmetry_3.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_3 = model.addRecover(Part_1_doc, Symmetry_3, [Recover_2.result()], True) +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_3_1_1_1"), model.selection("SOLID", "Recover_3_1_2_2"), model.selection("SOLID", "Recover_3_1_3")], model.selection("FACE", "PartSet/XOZ"), False) +model.testNbResults(Symmetry_4, 3) +model.testNbSubResults(Symmetry_4, [0, 0, 0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.SOLID, [1, 1, 1]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.FACE, [6, 3, 3]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.EDGE, [24, 6, 6]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.VERTEX, [48, 12, 12]) +model.testResultsVolumes(Symmetry_4, [3444.394198615, 785.39816339745, 785.39816339745]) + +REFERENCE = [Recover_3.result().subResult(0).subResult(0).resultSubShapePair()[0].shape().middlePoint(), + Recover_3.result().subResult(1).subResult(1).resultSubShapePair()[0].shape().middlePoint(), + Recover_3.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()] +for res, ref in zip(Symmetry_4.results(), REFERENCE): + ref = symmetryXOZ(ref) + midPoint = res.resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE) + + +Recover_4 = model.addRecover(Part_1_doc, Symmetry_4, [Recover_3.result()], True) +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_4_1_1_5")], model.selection("FACE", "PartSet/XOY"), True) +model.testNbResults(Symmetry_5, 1) +model.testNbSubResults(Symmetry_5, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.FACE, [10]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.EDGE, [36]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.VERTEX, [72]) +model.testResultsVolumes(Symmetry_5, [2 * 542.746463956]) + +refPoint = centerBB(Recover_4.results()[0].subResult(0).subResult(4).resultSubShapePair()[0].shape()) +refPoint.setZ(0) +midPoint = Symmetry_5.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_5 = model.addRecover(Part_1_doc, Symmetry_5, [Compound_2.result()], True) +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_5_1_2_1")], model.selection("FACE", "PartSet/XOY"), True) +model.testNbResults(Symmetry_6, 1) +model.testNbSubResults(Symmetry_6, [2]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.EDGE, [12]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.VERTEX, [24]) +model.testResultsVolumes(Symmetry_6, [2 * 785.39816339745]) + +refPoint = Recover_5.result().subResult(1).subResult(0).resultSubShapePair()[0].shape().middlePoint() +refPoint.setZ(0) +midPoint = Symmetry_6.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_6 = model.addRecover(Part_1_doc, Symmetry_6, [Recover_5.result()], True) +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_6_1_3")], model.selection("FACE", "PartSet/XOY"), True) +model.testNbResults(Symmetry_7, 1) +model.testNbSubResults(Symmetry_7, [2]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.SOLID, [2]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.EDGE, [12]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.VERTEX, [24]) +model.testResultsVolumes(Symmetry_7, [2 * 785.39816339745]) + +refPoint = Recover_6.result().subResult(2).resultSubShapePair()[0].shape().middlePoint() +refPoint.setZ(0) +midPoint = Symmetry_7.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + + +Recover_7 = model.addRecover(Part_1_doc, Symmetry_7, [Recover_6.result()], True) +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_7_1_1_1"), model.selection("SOLID", "Recover_7_1_2_2"), model.selection("SOLID", "Recover_7_1_3")], model.selection("FACE", "PartSet/XOY"), True) +model.testNbResults(Symmetry_8, 3) +model.testNbSubResults(Symmetry_8, [2, 2, 2]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.SOLID, [2, 2, 2]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.FACE, [12, 6, 6]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.EDGE, [48, 12, 12]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.VERTEX, [96, 24, 24]) +model.testResultsVolumes(Symmetry_8, [2 * 3444.394198615, 2 * 785.39816339745, 2 * 785.39816339745]) + +REFERENCE = [centerBB(Recover_7.result().subResult(0).subResult(0).resultSubShapePair()[0].shape()), + Recover_7.result().subResult(1).subResult(1).resultSubShapePair()[0].shape().middlePoint(), + Recover_7.result().subResult(2).resultSubShapePair()[0].shape().middlePoint()] +for res, ref in zip(Symmetry_8.results(), REFERENCE): + ref.setZ(0) + midPoint = res.resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_4.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_4.py new file mode 100644 index 000000000..a9027c2ce --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_4.py @@ -0,0 +1,182 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model +from GeomAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.defaultPlane("XOY")) +SketchPoint_1 = Sketch_1.addPoint(44.29784155360136, 17.09942588468031) +SketchArc_1 = Sketch_1.addArc(44.29784155360136, 17.09942588468031, 47.1668727423061, 12.27945348765633, 45.38299232715926, 22.60269052200972, False) +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchPoint_1.coordinates(), SketchArc_1.center()) +SketchLine_1 = Sketch_1.addLine(42.5764228403785, 22.14892077680068, 39.70739165167375, 16.41085839939117) +SketchLine_2 = Sketch_1.addLine(39.70739165167375, 16.41085839939117, 43.03546783057126, 12.04993099255995) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchLine_1.endPoint(), SketchLine_2.startPoint()) +SketchLine_3 = Sketch_1.addLine(28.57555063949931, 12.96802097294547, 15.72229091410204, 12.96802097294547) +SketchLine_4 = Sketch_1.addLine(15.72229091410204, 12.96802097294547, 15.72229091410204, 21.46035329151154) +SketchLine_5 = Sketch_1.addLine(15.72229091410204, 21.46035329151154, 28.57555063949931, 21.46035329151154) +SketchLine_6 = Sketch_1.addLine(28.57555063949931, 21.46035329151154, 28.57555063949931, 12.96802097294547) +SketchConstraintCoincidence_3 = Sketch_1.setCoincident(SketchLine_6.endPoint(), SketchLine_3.startPoint()) +SketchConstraintCoincidence_4 = Sketch_1.setCoincident(SketchLine_3.endPoint(), SketchLine_4.startPoint()) +SketchConstraintCoincidence_5 = Sketch_1.setCoincident(SketchLine_4.endPoint(), SketchLine_5.startPoint()) +SketchConstraintCoincidence_6 = Sketch_1.setCoincident(SketchLine_5.endPoint(), SketchLine_6.startPoint()) +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_3.result()) +SketchConstraintVertical_1 = Sketch_1.setVertical(SketchLine_4.result()) +SketchConstraintHorizontal_2 = Sketch_1.setHorizontal(SketchLine_5.result()) +SketchConstraintVertical_2 = Sketch_1.setVertical(SketchLine_6.result()) +SketchLine_7 = Sketch_1.addLine(-10.67279602198167, 14.78814178154371, -28.34602814440294, 14.78814178154371) +SketchLine_8 = Sketch_1.addLine(-28.34602814440294, 14.78814178154371, -28.34602814440294, 25.13271321305362) +SketchLine_9 = Sketch_1.addLine(-28.34602814440294, 25.13271321305362, -10.67279602198167, 25.13271321305362) +SketchLine_10 = Sketch_1.addLine(-10.67279602198167, 25.13271321305362, -10.67279602198167, 14.78814178154371) +SketchConstraintCoincidence_7 = Sketch_1.setCoincident(SketchLine_10.endPoint(), SketchLine_7.startPoint()) +SketchConstraintCoincidence_8 = Sketch_1.setCoincident(SketchLine_7.endPoint(), SketchLine_8.startPoint()) +SketchConstraintCoincidence_9 = Sketch_1.setCoincident(SketchLine_8.endPoint(), SketchLine_9.startPoint()) +SketchConstraintCoincidence_10 = Sketch_1.setCoincident(SketchLine_9.endPoint(), SketchLine_10.startPoint()) +SketchConstraintHorizontal_3 = Sketch_1.setHorizontal(SketchLine_7.result()) +SketchConstraintVertical_3 = Sketch_1.setVertical(SketchLine_8.result()) +SketchConstraintHorizontal_4 = Sketch_1.setHorizontal(SketchLine_9.result()) +SketchConstraintVertical_4 = Sketch_1.setVertical(SketchLine_10.result()) +SketchLine_11 = Sketch_1.addLine(-17.67323212242127, 25.13271321305362, -21.80463703415611, 14.78814178154371) +SketchConstraintCoincidence_11 = Sketch_1.setCoincident(SketchLine_11.startPoint(), SketchLine_9.result()) +SketchConstraintCoincidence_12 = Sketch_1.setCoincident(SketchLine_11.endPoint(), SketchLine_7.result()) +model.do() +Vertex_1 = model.addVertex(Part_1_doc, [model.selection("VERTEX", "Sketch_1/SketchArc_1")], False) +Edge_1 = model.addEdge(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchArc_1_2")], False) +Wire_1 = model.addWire(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchLine_1"), model.selection("EDGE", "Sketch_1/SketchLine_2")], False) +Face_1 = model.addFace(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_6r-SketchLine_5r-SketchLine_4r-SketchLine_3r")]) +Shell_1 = model.addShell(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_10r-SketchLine_9r-SketchLine_11f-SketchLine_7r"), model.selection("FACE", "Sketch_1/Face-SketchLine_11r-SketchLine_9r-SketchLine_8r-SketchLine_7r")]) +Box_1 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_1 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_1_1")], model.selection("EDGE", "PartSet/OX"), 50) +Box_2 = model.addBox(Part_1_doc, 10, 10, 10) +Cylinder_1 = model.addCylinder(Part_1_doc, model.selection("VERTEX", "PartSet/Origin"), model.selection("EDGE", "PartSet/OZ"), 5, 10) +Partition_1 = model.addPartition(Part_1_doc, [model.selection("SOLID", "Box_2_1"), model.selection("SOLID", "Cylinder_1_1")]) +Box_3 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_2 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_3_1")], model.selection("EDGE", "PartSet/OY"), 50) +AngularCopy_1 = model.addMultiRotation(Part_1_doc, [model.selection("SOLID", "Translation_2_1")], model.selection("EDGE", "PartSet/OZ"), 30, 3) +model.end() + +TOLERANCE = 1.e-7 + +def symmetryOZ(thePoint): + return GeomAPI_Pnt(-thePoint.x(), -thePoint.y(), thePoint.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("VERTEX", "Vertex_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_1, 1) +model.testNbSubResults(Symmetry_1, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.EDGE, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.VERTEX, [1]) +model.testResultsVolumes(Symmetry_1, [0]) +refPoint = symmetryOZ(Vertex_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_1.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("EDGE", "Edge_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_2, 1) +model.testNbSubResults(Symmetry_2, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.EDGE, [1]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.VERTEX, [2]) +model.testResultsVolumes(Symmetry_2, [0]) +refPoint = symmetryOZ(Edge_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_2.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("WIRE", "Wire_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_3, 1) +model.testNbSubResults(Symmetry_3, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.EDGE, [2]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.VERTEX, [4]) +model.testResultsVolumes(Symmetry_3, [0]) +refPoint = symmetryOZ(Wire_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_3.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("FACE", "Face_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_4, 1) +model.testNbSubResults(Symmetry_4, [0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.FACE, [1]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.EDGE, [4]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.VERTEX, [8]) +model.testResultsVolumes(Symmetry_4, [109.154152964914914]) +refPoint = symmetryOZ(Face_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_4.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SHELL", "Shell_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_5, 1) +model.testNbSubResults(Symmetry_5, [0]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.FACE, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.EDGE, [8]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.VERTEX, [16]) +model.testResultsVolumes(Symmetry_5, [182.822012116]) +refPoint = symmetryOZ(Shell_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_5.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Translation_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_6, 1) +model.testNbSubResults(Symmetry_6, [0]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.EDGE, [24]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.VERTEX, [48]) +model.testResultsVolumes(Symmetry_6, [1000]) +refPoint = symmetryOZ(Translation_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_6.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Partition_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_7, 1) +model.testNbSubResults(Symmetry_7, [3]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.SOLID, [3]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.FACE, [17]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.EDGE, [66]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.VERTEX, [132]) +model.testResultsVolumes(Symmetry_7, [1589.0486226]) +refPoint = symmetryOZ(Partition_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_7.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPOUND", "AngularCopy_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_8, 1) +model.testNbSubResults(Symmetry_8, [3]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.SOLID, [3]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.FACE, [18]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.EDGE, [72]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.VERTEX, [144]) +model.testResultsVolumes(Symmetry_8, [3000]) +refPoint = symmetryOZ(AngularCopy_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_8.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_5.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_5.py new file mode 100644 index 000000000..ff02dc40a --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v0_5.py @@ -0,0 +1,195 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model +from GeomAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.defaultPlane("XOY")) +SketchPoint_1 = Sketch_1.addPoint(44.29784155360136, 17.09942588468031) +SketchArc_1 = Sketch_1.addArc(44.29784155360136, 17.09942588468031, 47.1668727423061, 12.27945348765633, 45.38299232715926, 22.60269052200972, False) +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchPoint_1.coordinates(), SketchArc_1.center()) +SketchLine_1 = Sketch_1.addLine(42.5764228403785, 22.14892077680068, 39.70739165167375, 16.41085839939117) +SketchLine_2 = Sketch_1.addLine(39.70739165167375, 16.41085839939117, 43.03546783057126, 12.04993099255995) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchLine_1.endPoint(), SketchLine_2.startPoint()) +SketchLine_3 = Sketch_1.addLine(28.57555063949931, 12.96802097294547, 15.72229091410204, 12.96802097294547) +SketchLine_4 = Sketch_1.addLine(15.72229091410204, 12.96802097294547, 15.72229091410204, 21.46035329151154) +SketchLine_5 = Sketch_1.addLine(15.72229091410204, 21.46035329151154, 28.57555063949931, 21.46035329151154) +SketchLine_6 = Sketch_1.addLine(28.57555063949931, 21.46035329151154, 28.57555063949931, 12.96802097294547) +SketchConstraintCoincidence_3 = Sketch_1.setCoincident(SketchLine_6.endPoint(), SketchLine_3.startPoint()) +SketchConstraintCoincidence_4 = Sketch_1.setCoincident(SketchLine_3.endPoint(), SketchLine_4.startPoint()) +SketchConstraintCoincidence_5 = Sketch_1.setCoincident(SketchLine_4.endPoint(), SketchLine_5.startPoint()) +SketchConstraintCoincidence_6 = Sketch_1.setCoincident(SketchLine_5.endPoint(), SketchLine_6.startPoint()) +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_3.result()) +SketchConstraintVertical_1 = Sketch_1.setVertical(SketchLine_4.result()) +SketchConstraintHorizontal_2 = Sketch_1.setHorizontal(SketchLine_5.result()) +SketchConstraintVertical_2 = Sketch_1.setVertical(SketchLine_6.result()) +SketchLine_7 = Sketch_1.addLine(-10.67279602198167, 14.78814178154371, -28.34602814440294, 14.78814178154371) +SketchLine_8 = Sketch_1.addLine(-28.34602814440294, 14.78814178154371, -28.34602814440294, 25.13271321305362) +SketchLine_9 = Sketch_1.addLine(-28.34602814440294, 25.13271321305362, -10.67279602198167, 25.13271321305362) +SketchLine_10 = Sketch_1.addLine(-10.67279602198167, 25.13271321305362, -10.67279602198167, 14.78814178154371) +SketchConstraintCoincidence_7 = Sketch_1.setCoincident(SketchLine_10.endPoint(), SketchLine_7.startPoint()) +SketchConstraintCoincidence_8 = Sketch_1.setCoincident(SketchLine_7.endPoint(), SketchLine_8.startPoint()) +SketchConstraintCoincidence_9 = Sketch_1.setCoincident(SketchLine_8.endPoint(), SketchLine_9.startPoint()) +SketchConstraintCoincidence_10 = Sketch_1.setCoincident(SketchLine_9.endPoint(), SketchLine_10.startPoint()) +SketchConstraintHorizontal_3 = Sketch_1.setHorizontal(SketchLine_7.result()) +SketchConstraintVertical_3 = Sketch_1.setVertical(SketchLine_8.result()) +SketchConstraintHorizontal_4 = Sketch_1.setHorizontal(SketchLine_9.result()) +SketchConstraintVertical_4 = Sketch_1.setVertical(SketchLine_10.result()) +SketchLine_11 = Sketch_1.addLine(-17.67323212242127, 25.13271321305362, -21.80463703415611, 14.78814178154371) +SketchConstraintCoincidence_11 = Sketch_1.setCoincident(SketchLine_11.startPoint(), SketchLine_9.result()) +SketchConstraintCoincidence_12 = Sketch_1.setCoincident(SketchLine_11.endPoint(), SketchLine_7.result()) +model.do() +Vertex_1 = model.addVertex(Part_1_doc, [model.selection("VERTEX", "Sketch_1/SketchArc_1")], False) +Edge_1 = model.addEdge(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchArc_1_2")], False) +Wire_1 = model.addWire(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchLine_1"), model.selection("EDGE", "Sketch_1/SketchLine_2")], False) +Face_1 = model.addFace(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_6r-SketchLine_5r-SketchLine_4r-SketchLine_3r")]) +Shell_1 = model.addShell(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_10r-SketchLine_9r-SketchLine_11f-SketchLine_7r"), model.selection("FACE", "Sketch_1/Face-SketchLine_11r-SketchLine_9r-SketchLine_8r-SketchLine_7r")]) +Box_1 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_1 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_1_1")], model.selection("EDGE", "PartSet/OX"), 50) +Box_2 = model.addBox(Part_1_doc, 10, 10, 10) +Cylinder_1 = model.addCylinder(Part_1_doc, model.selection("VERTEX", "PartSet/Origin"), model.selection("EDGE", "PartSet/OZ"), 5, 10) +Partition_1 = model.addPartition(Part_1_doc, [model.selection("SOLID", "Box_2_1"), model.selection("SOLID", "Cylinder_1_1")]) +Box_3 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_2 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_3_1")], model.selection("EDGE", "PartSet/OY"), 50) +AngularCopy_1 = model.addMultiRotation(Part_1_doc, [model.selection("SOLID", "Translation_2_1")], model.selection("EDGE", "PartSet/OZ"), 30, 3) +Compound_1_objects = [model.selection("VERTEX", "Vertex_1_1"), model.selection("EDGE", "Edge_1_1"), model.selection("WIRE", "Wire_1_1"), model.selection("FACE", "Face_1_1"), model.selection("SHELL", "Shell_1_1"), model.selection("SOLID", "Translation_1_1"), model.selection("COMPSOLID", "Partition_1_1"), model.selection("COMPOUND", "AngularCopy_1_1")] +Compound_1 = model.addCompound(Part_1_doc, Compound_1_objects) +model.end() + +# collect reference data +REFERENCE = [] +TOLERANCE = 1.e-7 +for ind in range(0, Compound_1.result().numberOfSubs()): + p = Compound_1.result().subResult(ind).resultSubShapePair()[1].middlePoint() + p.setX(-p.x()) + p.setY(-p.y()) + REFERENCE.append(p) + +index = 0 + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("VERTEX", "Compound_1_1_1")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_1, 1) +model.testNbSubResults(Symmetry_1, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.EDGE, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.VERTEX, [1]) +model.testResultsVolumes(Symmetry_1, [0]) +midPoint = Symmetry_1.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_1 = model.addRecover(Part_1_doc, Symmetry_1, [Compound_1.result()], True) +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("EDGE", "Recover_1_1_2")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_2, 1) +model.testNbSubResults(Symmetry_2, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.EDGE, [1]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.VERTEX, [2]) +model.testResultsVolumes(Symmetry_2, [0]) +midPoint = Symmetry_2.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_2 = model.addRecover(Part_1_doc, Symmetry_2, [Recover_1.result()]) +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("WIRE", "Recover_2_1_3")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_3, 1) +model.testNbSubResults(Symmetry_3, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.EDGE, [2]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.VERTEX, [4]) +model.testResultsVolumes(Symmetry_3, [0]) +midPoint = Symmetry_3.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_3 = model.addRecover(Part_1_doc, Symmetry_3, [Recover_2.result()]) +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("FACE", "Recover_3_1_4")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_4, 1) +model.testNbSubResults(Symmetry_4, [0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.FACE, [1]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.EDGE, [4]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.VERTEX, [8]) +model.testResultsVolumes(Symmetry_4, [109.154152964914914]) +midPoint = Symmetry_4.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_4 = model.addRecover(Part_1_doc, Symmetry_4, [Recover_3.result()]) +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SHELL", "Recover_4_1_5")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_5, 1) +model.testNbSubResults(Symmetry_5, [0]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.FACE, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.EDGE, [8]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.VERTEX, [16]) +model.testResultsVolumes(Symmetry_5, [182.822012116]) +midPoint = Symmetry_5.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_5 = model.addRecover(Part_1_doc, Symmetry_5, [Recover_4.result()]) +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Recover_5_1_6")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_6, 1) +model.testNbSubResults(Symmetry_6, [0]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.EDGE, [24]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.VERTEX, [48]) +model.testResultsVolumes(Symmetry_6, [1000]) +midPoint = Symmetry_6.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_6 = model.addRecover(Part_1_doc, Symmetry_6, [Recover_5.result()]) +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Recover_6_1_7")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_7, 1) +model.testNbSubResults(Symmetry_7, [3]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.SOLID, [3]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.FACE, [17]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.EDGE, [66]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.VERTEX, [132]) +model.testResultsVolumes(Symmetry_7, [1589.0486226]) +midPoint = Symmetry_7.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) +index += 1 + +Recover_7 = model.addRecover(Part_1_doc, Symmetry_7, [Recover_6.result()]) +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPOUND", "Recover_7_1_8")], model.selection("EDGE", "PartSet/OZ"), False) +model.testNbResults(Symmetry_8, 1) +model.testNbSubResults(Symmetry_8, [3]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.SOLID, [3]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.FACE, [18]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.EDGE, [72]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.VERTEX, [144]) +model.testResultsVolumes(Symmetry_8, [3000]) +midPoint = Symmetry_8.defaultResult().shape().middlePoint() +assert(midPoint.distance(REFERENCE[index]) < TOLERANCE) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_1.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_1.py new file mode 100644 index 000000000..85d0c46ce --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_1.py @@ -0,0 +1,163 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model + +from GeomAPI import * +from SketchAPI import * + +import math + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.standardPlane("XOY")) +SketchEllipse_1 = Sketch_1.addEllipse(11.18033988749894, -50, 22.36067977499789, -50, 10) +[SketchPoint_1, SketchPoint_2, SketchPoint_3, SketchPoint_4, SketchPoint_5, SketchPoint_6, SketchPoint_7, SketchLine_1, SketchLine_2] = SketchEllipse_1.construction(center = "aux", firstFocus = "aux", secondFocus = "aux", majorAxisStart = "aux", majorAxisEnd = "aux", minorAxisStart = "aux", minorAxisEnd = "aux", majorAxis = "aux", minorAxis = "aux") +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_1.result()) +SketchConstraintLength_1 = Sketch_1.setLength(SketchLine_1.result(), 30) +SketchConstraintLength_2 = Sketch_1.setLength(SketchLine_2.result(), 20) +SketchProjection_1 = Sketch_1.addProjection(model.selection("EDGE", "PartSet/OY"), False) +SketchLine_3 = SketchProjection_1.createdFeature() +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchAPI_Point(SketchPoint_3).coordinates(), SketchLine_3.result()) +SketchConstraintDistance_1 = Sketch_1.setDistance(SketchAPI_Line(SketchLine_3).startPoint(), SketchAPI_Point(SketchPoint_3).coordinates(), 50, True) +SketchCircle_1 = Sketch_1.addCircle(41.18033988749897, -50, 5) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchCircle_1.center(), SketchLine_1.result()) +SketchConstraintDistance_2 = Sketch_1.setDistance(SketchEllipse_1.majorAxisPositive(), SketchCircle_1.center(), 15, True) +SketchConstraintRadius_1 = Sketch_1.setRadius(SketchCircle_1.results()[1], 5) +SketchMultiRotation_1 = Sketch_1.addRotation([SketchEllipse_1.result(), SketchCircle_1.results()[1]], SketchAPI_Point(SketchPoint_3).coordinates(), 360, 3, True) +[SketchEllipse_2, SketchEllipse_3, SketchCircle_2, SketchCircle_3] = SketchMultiRotation_1.rotated() +model.do() +Sketch_1.changeFacesOrder([[SketchEllipse_1.result(), SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchCircle_1.results()[1]], + [SketchEllipse_2.result(), SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_3.result(), SketchEllipse_2.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchCircle_2.results()[1]], + [SketchCircle_3.results()[1]] + ]) +model.do() +Extrusion_1 = model.addExtrusion(Part_1_doc, [model.selection("COMPOUND", "Sketch_1")], model.selection(), 10, 0) +Compound_1 = model.addCompound(Part_1_doc, [model.selection("SOLID", "Extrusion_1_2"), model.selection("SOLID", "Extrusion_1_3")]) +Compound_2_objects = [model.selection("COMPSOLID", "Extrusion_1_1"), model.selection("COMPOUND", "Compound_1_1"), model.selection("SOLID", "Extrusion_1_4")] +Compound_2 = model.addCompound(Part_1_doc, Compound_2_objects) +model.end() + +def symmetry(thePoint, theCenter): + return GeomAPI_Pnt(2 * theCenter.x() - thePoint.x(), 2 * theCenter.y() - thePoint.y(), 2 * theCenter.z() - thePoint.z()) + +def average(thePoints): + x = 0; y = 0; z = 0 + for p in thePoints: + x += p.x(); y += p.y(); z+= p.z() + x /= len(thePoints) + y /= len(thePoints) + z /= len(thePoints) + return GeomAPI_Pnt(x, y, z) + +def subsRefPoints(theResult): + res = [] + for ind in range(0, theResult.numberOfSubs()): + res.append( theResult.subResult(ind).resultSubShapePair()[0].shape().middlePoint()) + return res + + +TOLERANCE = 1.e-7 +ORIGIN = GeomAPI_Pnt(0, 0, 0) +CENTER_1 = GeomAPI_Pnt(SketchEllipse_1.center().pnt().x(), SketchEllipse_1.center().pnt().y(), 0) +CENTER_2 = GeomAPI_Pnt(SketchCircle_1.center().pnt().x(), SketchCircle_1.center().pnt().y(), 0) +REFERENCE = subsRefPoints(Compound_2.result()) + + +def assertResult(theFeature, theNbSolids, theNbFaces, theNbEdges, theNbVertices, theVolume): + model.testNbResults(theFeature, 1) + model.testNbSubResults(theFeature, [3]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.SOLID, [theNbSolids]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.FACE, [theNbFaces]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.EDGE, [theNbEdges]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.VERTEX, [theNbVertices]) + model.testResultsVolumes(theFeature, [theVolume]) + + for ind in range(0, theFeature.result().numberOfSubs()): + ref = REFERENCE[ind] + midPoint = theFeature.result().subResult(ind).resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE), "Sub-result {}; actual ({}, {}, {}) != expected ({}, {}, {})".format(ind, midPoint.x(), midPoint.y(), midPoint.z(), ref.x(), ref.y(), ref.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Compound_2_1_1_5")], model.selection("VERTEX", "PartSet/Origin"), keepOriginal = False, keepSubResults = True) +model.end() +# selection of a compsolid part is prohibited +assert(Symmetry_1.feature().error() != "") + +model.begin() +Symmetry_1.setMainObjects([model.selection("COMPSOLID", "Compound_2_1_1")]) +REFERENCE[0] = symmetry(REFERENCE[0], ORIGIN) +assertResult(Symmetry_1, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_1_1_2_1")], model.selection("VERTEX", "PartSet/Origin"), keepOriginal = False, keepSubResults = True) +subs = subsRefPoints(Compound_2.result().subResult(1)) +subs[0] = symmetry(subs[0], ORIGIN) +REFERENCE[1] = average(subs) +assertResult(Symmetry_2, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_2_1_3")], model.selection("VERTEX", "PartSet/Origin"), keepOriginal = False, keepSubResults = True) +REFERENCE[2] = symmetry(REFERENCE[2], ORIGIN) +assertResult(Symmetry_3, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_3_1_1_1"), model.selection("SOLID", "Symmetry_3_1_2_2"), model.selection("SOLID", "Symmetry_3_1_3")], model.selection("VERTEX", "PartSet/Origin"), keepOriginal = False, keepSubResults = True) +model.end() +# selection of a compsolid part is prohibited +assert(Symmetry_4.feature().error() != "") + +model.begin() +Symmetry_4.setMainObjects([model.selection("COMPSOLID", "Symmetry_3_1_1"), model.selection("SOLID", "Symmetry_3_1_2_2"), model.selection("SOLID", "Symmetry_3_1_3")]) +REFERENCE[0] = symmetry(REFERENCE[0], ORIGIN) +subs = subsRefPoints(Compound_2.result().subResult(1)) +for ind in range(0, len(subs)): + subs[ind] = symmetry(subs[ind], ORIGIN) +REFERENCE[1] = average(subs) +REFERENCE[2] = symmetry(REFERENCE[2], ORIGIN) +assertResult(Symmetry_4, 10, 47, 162, 324, 14319.99602674256) + + +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_4_1_1")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), keepOriginal = True, keepSubResults = True) +REFERENCE[0] = CENTER_1 +assertResult(Symmetry_5, 17, 85, 306, 612, 26283.79756329278) + +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_5_1_2_1")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), keepOriginal = True, keepSubResults = True) +REFERENCE[1] = CENTER_1 +assertResult(Symmetry_6, 18, 88, 312, 624, 27069.19572669) + +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_6_1_3")], model.selection("VERTEX", "Sketch_1/SketchEllipse_1_ellipse_center"), keepOriginal = True, keepSubResults = True) +REFERENCE[2] = CENTER_1 +assertResult(Symmetry_7, 19, 91, 318, 636, 27854.59389) + +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_7_1_1"), model.selection("SOLID", "Symmetry_7_1_2_2"), model.selection("SOLID", "Symmetry_7_1_3")], model.selection("VERTEX", "Sketch_1/SketchCircle_1"), keepOriginal = True, keepSubResults = True) +REFERENCE[0] = CENTER_2 +REFERENCE[2] = CENTER_2 +assertResult(Symmetry_8, 36, 176, 624, 1248, 54138.39145338) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_2.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_2.py new file mode 100644 index 000000000..e3cf18805 --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_2.py @@ -0,0 +1,165 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model + +from GeomAPI import * +from SketchAPI import * + +import math + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.standardPlane("XOY")) +SketchEllipse_1 = Sketch_1.addEllipse(11.18033988749894, -50, 22.36067977499789, -50, 10) +[SketchPoint_1, SketchPoint_2, SketchPoint_3, SketchPoint_4, SketchPoint_5, SketchPoint_6, SketchPoint_7, SketchLine_1, SketchLine_2] = SketchEllipse_1.construction(center = "aux", firstFocus = "aux", secondFocus = "aux", majorAxisStart = "aux", majorAxisEnd = "aux", minorAxisStart = "aux", minorAxisEnd = "aux", majorAxis = "aux", minorAxis = "aux") +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_1.result()) +SketchConstraintLength_1 = Sketch_1.setLength(SketchLine_1.result(), 30) +SketchConstraintLength_2 = Sketch_1.setLength(SketchLine_2.result(), 20) +SketchProjection_1 = Sketch_1.addProjection(model.selection("EDGE", "PartSet/OY"), False) +SketchLine_3 = SketchProjection_1.createdFeature() +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchAPI_Point(SketchPoint_3).coordinates(), SketchLine_3.result()) +SketchConstraintDistance_1 = Sketch_1.setDistance(SketchAPI_Line(SketchLine_3).startPoint(), SketchAPI_Point(SketchPoint_3).coordinates(), 50, True) +SketchCircle_1 = Sketch_1.addCircle(41.18033988749897, -50, 5) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchCircle_1.center(), SketchLine_1.result()) +SketchConstraintDistance_2 = Sketch_1.setDistance(SketchEllipse_1.majorAxisPositive(), SketchCircle_1.center(), 15, True) +SketchConstraintRadius_1 = Sketch_1.setRadius(SketchCircle_1.results()[1], 5) +SketchMultiRotation_1 = Sketch_1.addRotation([SketchEllipse_1.result(), SketchCircle_1.results()[1]], SketchAPI_Point(SketchPoint_3).coordinates(), 360, 3, True) +[SketchEllipse_2, SketchEllipse_3, SketchCircle_2, SketchCircle_3] = SketchMultiRotation_1.rotated() +model.do() +Sketch_1.changeFacesOrder([[SketchEllipse_1.result(), SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchCircle_1.results()[1]], + [SketchEllipse_2.result(), SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_3.result(), SketchEllipse_2.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchCircle_2.results()[1]], + [SketchCircle_3.results()[1]] + ]) +model.do() +Extrusion_1 = model.addExtrusion(Part_1_doc, [model.selection("COMPOUND", "Sketch_1")], model.selection(), 10, 0) +Compound_1 = model.addCompound(Part_1_doc, [model.selection("SOLID", "Extrusion_1_2"), model.selection("SOLID", "Extrusion_1_3")]) +Compound_2_objects = [model.selection("COMPSOLID", "Extrusion_1_1"), model.selection("COMPOUND", "Compound_1_1"), model.selection("SOLID", "Extrusion_1_4")] +Compound_2 = model.addCompound(Part_1_doc, Compound_2_objects) +model.end() + +def symmetryOX(thePoint): + return GeomAPI_Pnt(thePoint.x(), -thePoint.y(), -thePoint.z()) + +def middleOZ(thePoint): + return GeomAPI_Pnt(0, 0, thePoint.z()) + +def average(thePoints): + x = 0; y = 0; z = 0 + for p in thePoints: + x += p.x(); y += p.y(); z+= p.z() + x /= len(thePoints) + y /= len(thePoints) + z /= len(thePoints) + return GeomAPI_Pnt(x, y, z) + +def subsRefPoints(theResult): + res = [] + for ind in range(0, theResult.numberOfSubs()): + res.append( theResult.subResult(ind).resultSubShapePair()[0].shape().middlePoint()) + return res + + +TOLERANCE = 1.e-7 +ORIGIN = GeomAPI_Pnt(0, 0, 0) +REFERENCE = subsRefPoints(Compound_2.result()) + + +def assertResult(theFeature, theNbSolids, theNbFaces, theNbEdges, theNbVertices, theVolume): + model.testNbResults(theFeature, 1) + model.testNbSubResults(theFeature, [3]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.SOLID, [theNbSolids]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.FACE, [theNbFaces]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.EDGE, [theNbEdges]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.VERTEX, [theNbVertices]) + model.testResultsVolumes(theFeature, [theVolume]) + + for ind in range(0, theFeature.result().numberOfSubs()): + ref = REFERENCE[ind] + midPoint = theFeature.result().subResult(ind).resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE), "Sub-result {}; actual ({}, {}, {}) != expected ({}, {}, {})".format(ind, midPoint.x(), midPoint.y(), midPoint.z(), ref.x(), ref.y(), ref.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Compound_2_1_1_5")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +model.end() +# selection of a compsolid part is prohibited +assert(Symmetry_1.feature().error() != "") + +model.begin() +Symmetry_1.setMainObjects([model.selection("COMPSOLID", "Compound_2_1_1")]) +REFERENCE[0] = symmetryOX(REFERENCE[0]) +assertResult(Symmetry_1, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_1_1_2_1")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +subs = subsRefPoints(Compound_2.result().subResult(1)) +subs[0] = symmetryOX(subs[0]) +REFERENCE[1] = average(subs) +assertResult(Symmetry_2, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_2_1_3")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +REFERENCE[2] = symmetryOX(REFERENCE[2]) +assertResult(Symmetry_3, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_3_1_1_1"), model.selection("SOLID", "Symmetry_3_1_2_2"), model.selection("SOLID", "Symmetry_3_1_3")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +model.end() +# selection of a compsolid part is prohibited +assert(Symmetry_4.feature().error() != "") + +model.begin() +Symmetry_4.setMainObjects([model.selection("COMPSOLID", "Symmetry_3_1_1"), model.selection("SOLID", "Symmetry_3_1_2_2"), model.selection("SOLID", "Symmetry_3_1_3")]) +REFERENCE[0] = symmetryOX(REFERENCE[0]) +subs = subsRefPoints(Compound_2.result().subResult(1)) +for ind in range(0, len(subs)): + subs[ind] = symmetryOX(subs[ind]) +REFERENCE[1] = average(subs) +REFERENCE[2] = symmetryOX(REFERENCE[2]) +assertResult(Symmetry_4, 10, 47, 162, 324, 14319.99602674256) + + +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_4_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = True, keepSubResults = True) +REFERENCE[0] = middleOZ(REFERENCE[0]) +assertResult(Symmetry_5, 17, 85, 306, 612, 26283.79756329278) + +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_5_1_2_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = True, keepSubResults = True) +REFERENCE[1] = middleOZ(REFERENCE[1]) +assertResult(Symmetry_6, 18, 88, 312, 624, 27069.19572669) + +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_6_1_3")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = True, keepSubResults = True) +REFERENCE[2] = middleOZ(REFERENCE[2]) +assertResult(Symmetry_7, 19, 91, 318, 636, 27854.59389) + +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_7_1_1"), model.selection("SOLID", "Symmetry_7_1_2_2"), model.selection("SOLID", "Symmetry_7_1_3")], model.selection("EDGE", "PartSet/OY"), keepOriginal = True, keepSubResults = True) +REFERENCE[0] = ORIGIN +REFERENCE[1] = ORIGIN +REFERENCE[2] = ORIGIN +assertResult(Symmetry_8, 36, 176, 624, 1248, 54138.39145338) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_3.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_3.py new file mode 100644 index 000000000..d3093d344 --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_3.py @@ -0,0 +1,160 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model + +from GeomAPI import * +from SketchAPI import * + +import math + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.standardPlane("XOY")) +SketchEllipse_1 = Sketch_1.addEllipse(11.18033988749894, -50, 22.36067977499789, -50, 10) +[SketchPoint_1, SketchPoint_2, SketchPoint_3, SketchPoint_4, SketchPoint_5, SketchPoint_6, SketchPoint_7, SketchLine_1, SketchLine_2] = SketchEllipse_1.construction(center = "aux", firstFocus = "aux", secondFocus = "aux", majorAxisStart = "aux", majorAxisEnd = "aux", minorAxisStart = "aux", minorAxisEnd = "aux", majorAxis = "aux", minorAxis = "aux") +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_1.result()) +SketchConstraintLength_1 = Sketch_1.setLength(SketchLine_1.result(), 30) +SketchConstraintLength_2 = Sketch_1.setLength(SketchLine_2.result(), 20) +SketchProjection_1 = Sketch_1.addProjection(model.selection("EDGE", "PartSet/OY"), False) +SketchLine_3 = SketchProjection_1.createdFeature() +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchAPI_Point(SketchPoint_3).coordinates(), SketchLine_3.result()) +SketchConstraintDistance_1 = Sketch_1.setDistance(SketchAPI_Line(SketchLine_3).startPoint(), SketchAPI_Point(SketchPoint_3).coordinates(), 50, True) +SketchCircle_1 = Sketch_1.addCircle(41.18033988749897, -50, 5) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchCircle_1.center(), SketchLine_1.result()) +SketchConstraintDistance_2 = Sketch_1.setDistance(SketchEllipse_1.majorAxisPositive(), SketchCircle_1.center(), 15, True) +SketchConstraintRadius_1 = Sketch_1.setRadius(SketchCircle_1.results()[1], 5) +SketchMultiRotation_1 = Sketch_1.addRotation([SketchEllipse_1.result(), SketchCircle_1.results()[1]], SketchAPI_Point(SketchPoint_3).coordinates(), 360, 3, True) +[SketchEllipse_2, SketchEllipse_3, SketchCircle_2, SketchCircle_3] = SketchMultiRotation_1.rotated() +model.do() +Sketch_1.changeFacesOrder([[SketchEllipse_1.result(), SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchCircle_1.results()[1]], + [SketchEllipse_2.result(), SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_3.result(), SketchEllipse_2.result(), SketchEllipse_1.result()], + [SketchEllipse_1.result(), SketchEllipse_2.result(), SketchEllipse_3.result()], + [SketchEllipse_1.result(), SketchEllipse_3.result(), SketchEllipse_2.result()], + [SketchEllipse_2.result(), SketchEllipse_3.result(), SketchEllipse_3.result(), SketchEllipse_1.result()], + [SketchCircle_2.results()[1]], + [SketchCircle_3.results()[1]] + ]) +model.do() +Extrusion_1 = model.addExtrusion(Part_1_doc, [model.selection("COMPOUND", "Sketch_1")], model.selection(), 10, 0) +Compound_1 = model.addCompound(Part_1_doc, [model.selection("SOLID", "Extrusion_1_2"), model.selection("SOLID", "Extrusion_1_3")]) +Compound_2_objects = [model.selection("COMPSOLID", "Extrusion_1_1"), model.selection("COMPOUND", "Compound_1_1"), model.selection("SOLID", "Extrusion_1_4")] +Compound_2 = model.addCompound(Part_1_doc, Compound_2_objects) +model.end() + +def symmetryXOZ(thePoint): + return GeomAPI_Pnt(thePoint.x(), -thePoint.y(), thePoint.z()) + +def average(thePoints): + x = 0; y = 0; z = 0 + for p in thePoints: + x += p.x(); y += p.y(); z+= p.z() + x /= len(thePoints) + y /= len(thePoints) + z /= len(thePoints) + return GeomAPI_Pnt(x, y, z) + +def subsRefPoints(theResult): + res = [] + for ind in range(0, theResult.numberOfSubs()): + res.append( theResult.subResult(ind).resultSubShapePair()[0].shape().middlePoint()) + return res + +TOLERANCE = 1.e-7 +REFERENCE = subsRefPoints(Compound_2.result()) + +def assertResult(theFeature, theNbSolids, theNbFaces, theNbEdges, theNbVertices, theVolume): + model.testNbResults(theFeature, 1) + model.testNbSubResults(theFeature, [3]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.SOLID, [theNbSolids]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.FACE, [theNbFaces]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.EDGE, [theNbEdges]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.VERTEX, [theNbVertices]) + model.testResultsVolumes(theFeature, [theVolume]) + + for ind in range(0, theFeature.result().numberOfSubs()): + ref = REFERENCE[ind] + midPoint = theFeature.result().subResult(ind).resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE), "Sub-result {}; actual ({}, {}, {}) != expected ({}, {}, {})".format(ind, midPoint.x(), midPoint.y(), midPoint.z(), ref.x(), ref.y(), ref.z()) + + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Compound_2_1_1_5")], model.selection("FACE", "PartSet/XOZ"), keepOriginal = False, keepSubResults = True) +model.end() +# selection of a compsolid part is prohibited +assert(Symmetry_1.feature().error() != "") + +model.begin() +Symmetry_1.setMainObjects([model.selection("COMPSOLID", "Compound_2_1_1")]) +REFERENCE[0] = symmetryXOZ(REFERENCE[0]) +assertResult(Symmetry_1, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_1_1_2_1")], model.selection("FACE", "PartSet/XOZ"), keepOriginal = False, keepSubResults = True) +subs = subsRefPoints(Compound_2.result().subResult(1)) +subs[0] = symmetryXOZ(subs[0]) +REFERENCE[1] = average(subs) +assertResult(Symmetry_2, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_2_1_3")], model.selection("FACE", "PartSet/XOZ"), keepOriginal = False, keepSubResults = True) +REFERENCE[2] = symmetryXOZ(REFERENCE[2]) +assertResult(Symmetry_3, 10, 47, 162, 324, 14319.99602674256) + +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_3_1_1_1"), model.selection("SOLID", "Symmetry_3_1_2_2"), model.selection("SOLID", "Symmetry_3_1_3")], model.selection("FACE", "PartSet/XOZ"), keepOriginal = False, keepSubResults = True) +model.end() +# selection of a compsolid part is prohibited +assert(Symmetry_4.feature().error() != "") + +model.begin() +Symmetry_4.setMainObjects([model.selection("COMPSOLID", "Symmetry_3_1_1"), model.selection("SOLID", "Symmetry_3_1_2_2"), model.selection("SOLID", "Symmetry_3_1_3")]) +REFERENCE[0] = symmetryXOZ(REFERENCE[0]) +subs = subsRefPoints(Compound_2.result().subResult(1)) +for ind in range(0, len(subs)): + subs[ind] = symmetryXOZ(subs[ind]) +REFERENCE[1] = average(subs) +REFERENCE[2] = symmetryXOZ(REFERENCE[2]) +assertResult(Symmetry_4, 10, 47, 162, 324, 14319.99602674256) + + +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_4_1_1")], model.selection("FACE", "PartSet/XOY"), keepOriginal = True, keepSubResults = True) +REFERENCE[0].setZ(0) +assertResult(Symmetry_5, 17, 85, 306, 612, 26283.79756329278) + +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_5_1_2_1")], model.selection("FACE", "PartSet/XOY"), keepOriginal = True, keepSubResults = True) +REFERENCE[1].setZ(0) +assertResult(Symmetry_6, 18, 88, 312, 624, 27069.19572669) + +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_6_1_3")], model.selection("FACE", "PartSet/XOY"), keepOriginal = True, keepSubResults = True) +REFERENCE[2].setZ(0) +assertResult(Symmetry_7, 19, 91, 318, 636, 27854.59389) + +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_7_1_1"), model.selection("SOLID", "Symmetry_7_1_2_2"), model.selection("SOLID", "Symmetry_7_1_3")], model.selection("FACE", "Symmetry_4_1_2_2/MF:Symmetried&Extrusion_1_3/To_Face"), keepOriginal = True, keepSubResults = True) +REFERENCE[0].setZ(10) +REFERENCE[1].setZ(5) +REFERENCE[2].setZ(10) +assertResult(Symmetry_8, 36, 176, 624, 1248, 54138.39145338) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_4.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_4.py new file mode 100644 index 000000000..68383bd04 --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_4.py @@ -0,0 +1,182 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model +from GeomAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.defaultPlane("XOY")) +SketchPoint_1 = Sketch_1.addPoint(44.29784155360136, 17.09942588468031) +SketchArc_1 = Sketch_1.addArc(44.29784155360136, 17.09942588468031, 47.1668727423061, 12.27945348765633, 45.38299232715926, 22.60269052200972, False) +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchPoint_1.coordinates(), SketchArc_1.center()) +SketchLine_1 = Sketch_1.addLine(42.5764228403785, 22.14892077680068, 39.70739165167375, 16.41085839939117) +SketchLine_2 = Sketch_1.addLine(39.70739165167375, 16.41085839939117, 43.03546783057126, 12.04993099255995) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchLine_1.endPoint(), SketchLine_2.startPoint()) +SketchLine_3 = Sketch_1.addLine(28.57555063949931, 12.96802097294547, 15.72229091410204, 12.96802097294547) +SketchLine_4 = Sketch_1.addLine(15.72229091410204, 12.96802097294547, 15.72229091410204, 21.46035329151154) +SketchLine_5 = Sketch_1.addLine(15.72229091410204, 21.46035329151154, 28.57555063949931, 21.46035329151154) +SketchLine_6 = Sketch_1.addLine(28.57555063949931, 21.46035329151154, 28.57555063949931, 12.96802097294547) +SketchConstraintCoincidence_3 = Sketch_1.setCoincident(SketchLine_6.endPoint(), SketchLine_3.startPoint()) +SketchConstraintCoincidence_4 = Sketch_1.setCoincident(SketchLine_3.endPoint(), SketchLine_4.startPoint()) +SketchConstraintCoincidence_5 = Sketch_1.setCoincident(SketchLine_4.endPoint(), SketchLine_5.startPoint()) +SketchConstraintCoincidence_6 = Sketch_1.setCoincident(SketchLine_5.endPoint(), SketchLine_6.startPoint()) +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_3.result()) +SketchConstraintVertical_1 = Sketch_1.setVertical(SketchLine_4.result()) +SketchConstraintHorizontal_2 = Sketch_1.setHorizontal(SketchLine_5.result()) +SketchConstraintVertical_2 = Sketch_1.setVertical(SketchLine_6.result()) +SketchLine_7 = Sketch_1.addLine(-10.67279602198167, 14.78814178154371, -28.34602814440294, 14.78814178154371) +SketchLine_8 = Sketch_1.addLine(-28.34602814440294, 14.78814178154371, -28.34602814440294, 25.13271321305362) +SketchLine_9 = Sketch_1.addLine(-28.34602814440294, 25.13271321305362, -10.67279602198167, 25.13271321305362) +SketchLine_10 = Sketch_1.addLine(-10.67279602198167, 25.13271321305362, -10.67279602198167, 14.78814178154371) +SketchConstraintCoincidence_7 = Sketch_1.setCoincident(SketchLine_10.endPoint(), SketchLine_7.startPoint()) +SketchConstraintCoincidence_8 = Sketch_1.setCoincident(SketchLine_7.endPoint(), SketchLine_8.startPoint()) +SketchConstraintCoincidence_9 = Sketch_1.setCoincident(SketchLine_8.endPoint(), SketchLine_9.startPoint()) +SketchConstraintCoincidence_10 = Sketch_1.setCoincident(SketchLine_9.endPoint(), SketchLine_10.startPoint()) +SketchConstraintHorizontal_3 = Sketch_1.setHorizontal(SketchLine_7.result()) +SketchConstraintVertical_3 = Sketch_1.setVertical(SketchLine_8.result()) +SketchConstraintHorizontal_4 = Sketch_1.setHorizontal(SketchLine_9.result()) +SketchConstraintVertical_4 = Sketch_1.setVertical(SketchLine_10.result()) +SketchLine_11 = Sketch_1.addLine(-17.67323212242127, 25.13271321305362, -21.80463703415611, 14.78814178154371) +SketchConstraintCoincidence_11 = Sketch_1.setCoincident(SketchLine_11.startPoint(), SketchLine_9.result()) +SketchConstraintCoincidence_12 = Sketch_1.setCoincident(SketchLine_11.endPoint(), SketchLine_7.result()) +model.do() +Vertex_1 = model.addVertex(Part_1_doc, [model.selection("VERTEX", "Sketch_1/SketchArc_1")], False) +Edge_1 = model.addEdge(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchArc_1_2")], False) +Wire_1 = model.addWire(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchLine_1"), model.selection("EDGE", "Sketch_1/SketchLine_2")], False) +Face_1 = model.addFace(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_6r-SketchLine_5r-SketchLine_4r-SketchLine_3r")]) +Shell_1 = model.addShell(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_10r-SketchLine_9r-SketchLine_11f-SketchLine_7r"), model.selection("FACE", "Sketch_1/Face-SketchLine_11r-SketchLine_9r-SketchLine_8r-SketchLine_7r")]) +Box_1 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_1 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_1_1")], model.selection("EDGE", "PartSet/OX"), 50) +Box_2 = model.addBox(Part_1_doc, 10, 10, 10) +Cylinder_1 = model.addCylinder(Part_1_doc, model.selection("VERTEX", "PartSet/Origin"), model.selection("EDGE", "PartSet/OZ"), 5, 10) +Partition_1 = model.addPartition(Part_1_doc, [model.selection("SOLID", "Box_2_1"), model.selection("SOLID", "Cylinder_1_1")], keepSubResults = True) +Box_3 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_2 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_3_1")], model.selection("EDGE", "PartSet/OY"), 50) +AngularCopy_1 = model.addMultiRotation(Part_1_doc, [model.selection("SOLID", "Translation_2_1")], model.selection("EDGE", "PartSet/OZ"), 30, 3) +model.end() + +TOLERANCE = 1.e-7 + +def symmetryOZ(thePoint): + return GeomAPI_Pnt(-thePoint.x(), -thePoint.y(), thePoint.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("VERTEX", "Vertex_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_1, 1) +model.testNbSubResults(Symmetry_1, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.EDGE, [0]) +model.testNbSubShapes(Symmetry_1, GeomAPI_Shape.VERTEX, [1]) +model.testResultsVolumes(Symmetry_1, [0]) +refPoint = symmetryOZ(Vertex_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_1.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("EDGE", "Edge_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_2, 1) +model.testNbSubResults(Symmetry_2, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.EDGE, [1]) +model.testNbSubShapes(Symmetry_2, GeomAPI_Shape.VERTEX, [2]) +model.testResultsVolumes(Symmetry_2, [0]) +refPoint = symmetryOZ(Edge_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_2.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("WIRE", "Wire_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_3, 1) +model.testNbSubResults(Symmetry_3, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.FACE, [0]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.EDGE, [2]) +model.testNbSubShapes(Symmetry_3, GeomAPI_Shape.VERTEX, [4]) +model.testResultsVolumes(Symmetry_3, [0]) +refPoint = symmetryOZ(Wire_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_3.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("FACE", "Face_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_4, 1) +model.testNbSubResults(Symmetry_4, [0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.FACE, [1]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.EDGE, [4]) +model.testNbSubShapes(Symmetry_4, GeomAPI_Shape.VERTEX, [8]) +model.testResultsVolumes(Symmetry_4, [109.154152964914914]) +refPoint = symmetryOZ(Face_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_4.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SHELL", "Shell_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_5, 1) +model.testNbSubResults(Symmetry_5, [0]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.SOLID, [0]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.FACE, [2]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.EDGE, [8]) +model.testNbSubShapes(Symmetry_5, GeomAPI_Shape.VERTEX, [16]) +model.testResultsVolumes(Symmetry_5, [182.822012116]) +refPoint = symmetryOZ(Shell_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_5.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Translation_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_6, 1) +model.testNbSubResults(Symmetry_6, [0]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.SOLID, [1]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.FACE, [6]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.EDGE, [24]) +model.testNbSubShapes(Symmetry_6, GeomAPI_Shape.VERTEX, [48]) +model.testResultsVolumes(Symmetry_6, [1000]) +refPoint = symmetryOZ(Translation_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_6.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Partition_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_7, 1) +model.testNbSubResults(Symmetry_7, [3]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.SOLID, [3]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.FACE, [17]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.EDGE, [66]) +model.testNbSubShapes(Symmetry_7, GeomAPI_Shape.VERTEX, [132]) +model.testResultsVolumes(Symmetry_7, [1589.0486226]) +refPoint = symmetryOZ(Partition_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_7.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPOUND", "AngularCopy_1_1")], model.selection("EDGE", "PartSet/OZ"), keepOriginal = False, keepSubResults = True) +model.testNbResults(Symmetry_8, 1) +model.testNbSubResults(Symmetry_8, [3]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.SOLID, [3]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.FACE, [18]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.EDGE, [72]) +model.testNbSubShapes(Symmetry_8, GeomAPI_Shape.VERTEX, [144]) +model.testResultsVolumes(Symmetry_8, [3000]) +refPoint = symmetryOZ(AngularCopy_1.defaultResult().shape().middlePoint()) +midPoint = Symmetry_8.defaultResult().shape().middlePoint() +assert(midPoint.distance(refPoint) < TOLERANCE) + +model.end() + +assert(model.checkPythonDump()) diff --git a/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_5.py b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_5.py new file mode 100644 index 000000000..10f82ec48 --- /dev/null +++ b/src/FeaturesPlugin/Test/TestSymmetry_MultiLevelCompound_v95_5.py @@ -0,0 +1,131 @@ +# Copyright (C) 2020 CEA/DEN, EDF R&D +# +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +# + +from salome.shaper import model +from GeomAPI import * + +model.begin() +partSet = model.moduleDocument() +Part_1 = model.addPart(partSet) +Part_1_doc = Part_1.document() +Sketch_1 = model.addSketch(Part_1_doc, model.defaultPlane("XOY")) +SketchPoint_1 = Sketch_1.addPoint(44.29784155360136, 17.09942588468031) +SketchArc_1 = Sketch_1.addArc(44.29784155360136, 17.09942588468031, 47.1668727423061, 12.27945348765633, 45.38299232715926, 22.60269052200972, False) +SketchConstraintCoincidence_1 = Sketch_1.setCoincident(SketchPoint_1.coordinates(), SketchArc_1.center()) +SketchLine_1 = Sketch_1.addLine(42.5764228403785, 22.14892077680068, 39.70739165167375, 16.41085839939117) +SketchLine_2 = Sketch_1.addLine(39.70739165167375, 16.41085839939117, 43.03546783057126, 12.04993099255995) +SketchConstraintCoincidence_2 = Sketch_1.setCoincident(SketchLine_1.endPoint(), SketchLine_2.startPoint()) +SketchLine_3 = Sketch_1.addLine(28.57555063949931, 12.96802097294547, 15.72229091410204, 12.96802097294547) +SketchLine_4 = Sketch_1.addLine(15.72229091410204, 12.96802097294547, 15.72229091410204, 21.46035329151154) +SketchLine_5 = Sketch_1.addLine(15.72229091410204, 21.46035329151154, 28.57555063949931, 21.46035329151154) +SketchLine_6 = Sketch_1.addLine(28.57555063949931, 21.46035329151154, 28.57555063949931, 12.96802097294547) +SketchConstraintCoincidence_3 = Sketch_1.setCoincident(SketchLine_6.endPoint(), SketchLine_3.startPoint()) +SketchConstraintCoincidence_4 = Sketch_1.setCoincident(SketchLine_3.endPoint(), SketchLine_4.startPoint()) +SketchConstraintCoincidence_5 = Sketch_1.setCoincident(SketchLine_4.endPoint(), SketchLine_5.startPoint()) +SketchConstraintCoincidence_6 = Sketch_1.setCoincident(SketchLine_5.endPoint(), SketchLine_6.startPoint()) +SketchConstraintHorizontal_1 = Sketch_1.setHorizontal(SketchLine_3.result()) +SketchConstraintVertical_1 = Sketch_1.setVertical(SketchLine_4.result()) +SketchConstraintHorizontal_2 = Sketch_1.setHorizontal(SketchLine_5.result()) +SketchConstraintVertical_2 = Sketch_1.setVertical(SketchLine_6.result()) +SketchLine_7 = Sketch_1.addLine(-10.67279602198167, 14.78814178154371, -28.34602814440294, 14.78814178154371) +SketchLine_8 = Sketch_1.addLine(-28.34602814440294, 14.78814178154371, -28.34602814440294, 25.13271321305362) +SketchLine_9 = Sketch_1.addLine(-28.34602814440294, 25.13271321305362, -10.67279602198167, 25.13271321305362) +SketchLine_10 = Sketch_1.addLine(-10.67279602198167, 25.13271321305362, -10.67279602198167, 14.78814178154371) +SketchConstraintCoincidence_7 = Sketch_1.setCoincident(SketchLine_10.endPoint(), SketchLine_7.startPoint()) +SketchConstraintCoincidence_8 = Sketch_1.setCoincident(SketchLine_7.endPoint(), SketchLine_8.startPoint()) +SketchConstraintCoincidence_9 = Sketch_1.setCoincident(SketchLine_8.endPoint(), SketchLine_9.startPoint()) +SketchConstraintCoincidence_10 = Sketch_1.setCoincident(SketchLine_9.endPoint(), SketchLine_10.startPoint()) +SketchConstraintHorizontal_3 = Sketch_1.setHorizontal(SketchLine_7.result()) +SketchConstraintVertical_3 = Sketch_1.setVertical(SketchLine_8.result()) +SketchConstraintHorizontal_4 = Sketch_1.setHorizontal(SketchLine_9.result()) +SketchConstraintVertical_4 = Sketch_1.setVertical(SketchLine_10.result()) +SketchLine_11 = Sketch_1.addLine(-17.67323212242127, 25.13271321305362, -21.80463703415611, 14.78814178154371) +SketchConstraintCoincidence_11 = Sketch_1.setCoincident(SketchLine_11.startPoint(), SketchLine_9.result()) +SketchConstraintCoincidence_12 = Sketch_1.setCoincident(SketchLine_11.endPoint(), SketchLine_7.result()) +model.do() +Vertex_1 = model.addVertex(Part_1_doc, [model.selection("VERTEX", "Sketch_1/SketchArc_1")], False) +Edge_1 = model.addEdge(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchArc_1_2")], False) +Wire_1 = model.addWire(Part_1_doc, [model.selection("EDGE", "Sketch_1/SketchLine_1"), model.selection("EDGE", "Sketch_1/SketchLine_2")], False) +Face_1 = model.addFace(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_6r-SketchLine_5r-SketchLine_4r-SketchLine_3r")]) +Shell_1 = model.addShell(Part_1_doc, [model.selection("FACE", "Sketch_1/Face-SketchLine_10r-SketchLine_9r-SketchLine_11f-SketchLine_7r"), model.selection("FACE", "Sketch_1/Face-SketchLine_11r-SketchLine_9r-SketchLine_8r-SketchLine_7r")]) +Box_1 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_1 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_1_1")], model.selection("EDGE", "PartSet/OX"), 50) +Box_2 = model.addBox(Part_1_doc, 10, 10, 10) +Cylinder_1 = model.addCylinder(Part_1_doc, model.selection("VERTEX", "PartSet/Origin"), model.selection("EDGE", "PartSet/OZ"), 5, 10) +Partition_1 = model.addPartition(Part_1_doc, [model.selection("SOLID", "Box_2_1"), model.selection("SOLID", "Cylinder_1_1")], keepSubResults = True) +Box_3 = model.addBox(Part_1_doc, 10, 10, 10) +Translation_2 = model.addTranslation(Part_1_doc, [model.selection("SOLID", "Box_3_1")], model.selection("EDGE", "PartSet/OY"), 50) +AngularCopy_1 = model.addMultiRotation(Part_1_doc, [model.selection("SOLID", "Translation_2_1")], model.selection("EDGE", "PartSet/OZ"), 30, 3) +Compound_1_objects = [model.selection("VERTEX", "Vertex_1_1"), model.selection("EDGE", "Edge_1_1"), model.selection("WIRE", "Wire_1_1"), model.selection("FACE", "Face_1_1"), model.selection("SHELL", "Shell_1_1"), model.selection("SOLID", "Translation_1_1"), model.selection("COMPSOLID", "Partition_1_1"), model.selection("COMPOUND", "AngularCopy_1_1")] +Compound_1 = model.addCompound(Part_1_doc, Compound_1_objects) +model.end() + +# collect reference data +REFERENCE = [] +TOLERANCE = 1.e-7 +for ind in range(0, Compound_1.result().numberOfSubs()): + p = Compound_1.result().subResult(ind).resultSubShapePair()[1].middlePoint() + REFERENCE.append(p) + +def assertResult(theFeature, theNbMoved): + model.testNbResults(theFeature, 1) + model.testNbSubResults(theFeature, [8]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.SOLID, [7]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.FACE, [44]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.EDGE, [177]) + model.testNbSubShapes(theFeature, GeomAPI_Shape.VERTEX, [355]) + model.testResultsVolumes(theFeature, [5589.0486226]) + + for ind in range(0, theFeature.result().numberOfSubs()): + ref = GeomAPI_Pnt(REFERENCE[ind].x(), REFERENCE[ind].y(), REFERENCE[ind].z()) + if ind < theNbMoved: + ref.setY(-ref.y()) + ref.setZ(-ref.z()) + midPoint = theFeature.result().subResult(ind).resultSubShapePair()[0].shape().middlePoint() + assert(midPoint.distance(ref) < TOLERANCE), "Sub-result {}; actual ({}, {}, {}) != expected ({}, {}, {})".format(ind, midPoint.x(), midPoint.y(), midPoint.z(), ref.x(), ref.y(), ref.z()) + + +model.begin() +Symmetry_1 = model.addSymmetry(Part_1_doc, [model.selection("VERTEX", "Compound_1_1_1")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_1, 1) + +Symmetry_2 = model.addSymmetry(Part_1_doc, [model.selection("EDGE", "Symmetry_1_1_2")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_2, 2) + +Symmetry_3 = model.addSymmetry(Part_1_doc, [model.selection("WIRE", "Symmetry_2_1_3")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_3, 3) + +Symmetry_4 = model.addSymmetry(Part_1_doc, [model.selection("FACE", "Symmetry_3_1_4")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_4, 4) + +Symmetry_5 = model.addSymmetry(Part_1_doc, [model.selection("SHELL", "Symmetry_4_1_5")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_5, 5) + +Symmetry_6 = model.addSymmetry(Part_1_doc, [model.selection("SOLID", "Symmetry_5_1_6")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_6, 6) + +Symmetry_7 = model.addSymmetry(Part_1_doc, [model.selection("COMPSOLID", "Symmetry_6_1_7")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_7, 7) + +Symmetry_8 = model.addSymmetry(Part_1_doc, [model.selection("COMPOUND", "Symmetry_7_1_8")], model.selection("EDGE", "PartSet/OX"), keepOriginal = False, keepSubResults = True) +assertResult(Symmetry_8, 8) + +model.end() + +assert(model.checkPythonDump()) -- 2.39.2