Implemented validator which deny referring to generated features by Multi-Rotation, Multi-Translation and Mirror
TestDistanceSignedVsUnsigned05.py
TestSignedDistancePointPoint.py
TestSignedDistancePointLine.py
+ Test2273.py
)
if(${SKETCHER_CHANGE_RADIUS_WHEN_MOVE})
aFactory->registerValidator("SketchPlugin_ArcEndPointIntersectionValidator",
new SketchPlugin_ArcEndPointIntersectionValidator);
aFactory->registerValidator("SketchPlugin_HasNoConstraint", new SketchPlugin_HasNoConstraint);
+ aFactory->registerValidator("SketchPlugin_ReplicationReference",
+ new SketchPlugin_ReplicationReferenceValidator);
// register this plugin
ModelAPI_Session::get()->registerPlugin(this);
}
return true;
}
+
+bool SketchPlugin_ReplicationReferenceValidator::isValid(
+ const AttributePtr& theAttribute,
+ const std::list<std::string>& theArguments,
+ Events_InfoMessage& theError) const
+{
+ AttributeRefAttrPtr aRefAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeRefAttr>(theAttribute);
+ if (!aRefAttr)
+ {
+ theError = "Incorrect attribute";
+ return false;
+ }
+
+ ObjectPtr anOwner;
+ if (aRefAttr->isObject())
+ anOwner = aRefAttr->object();
+ else
+ {
+ AttributePtr anAttr = aRefAttr->attr();
+ anOwner = anAttr->owner();
+ }
+ FeaturePtr anAttrOwnerFeature = ModelAPI_Feature::feature(anOwner);
+ if (!anAttrOwnerFeature)
+ return true;
+ AttributeBooleanPtr aCopyAttr = anAttrOwnerFeature->boolean(SketchPlugin_SketchEntity::COPY_ID());
+ if (!aCopyAttr || !aCopyAttr->value())
+ return true; // feature is not a copy, thus valid
+
+ // check the copy feature is already referred by the "Multi" feature
+ FeaturePtr aMultiFeature = ModelAPI_Feature::feature(theAttribute->owner());
+ AttributeRefListPtr aRefList = aMultiFeature->reflist(theArguments.front());
+ for (int i = 0; i < aRefList->size(); ++i)
+ {
+ FeaturePtr aRefOwner = ModelAPI_Feature::feature(aRefList->object(i));
+ if (aRefOwner == anAttrOwnerFeature)
+ {
+ theError = "Attribute refers to the object generated by this feature";
+ return false;
+ }
+ }
+
+ return true;
+}
Events_InfoMessage& theError) const;
};
+/**\class SketchPlugin_ReplicationReferenceValidator
+ * \ingroup Validators
+ * \brief Validator checking that the replications features (Mirror,
+ * Multi-Rotation, Mutli-Translation) do not refer to the shapes they produce.
+ */
+class SketchPlugin_ReplicationReferenceValidator: public ModelAPI_AttributeValidator
+{
+ public:
+ //! returns true if attribute is valid
+ //! \param theAttribute the checked attribute
+ //! \param theArguments arguments of the attribute
+ //! \param theError error message
+ virtual bool isValid(const AttributePtr& theAttribute,
+ const std::list<std::string>& theArguments,
+ Events_InfoMessage& theError) const;
+};
+
#endif
--- /dev/null
+## Copyright (C) 2014-2017 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<mailto:webmaster.salome@opencascade.com>
+##
+
+"""
+ Test2273.py
+ Test case for issue #2273 "Error when reading HDF and Python dump"
+ (multi-rotation center refers to a feature produced by itself)
+"""
+
+from salome.shaper import model
+from SketchAPI import *
+
+model.begin()
+partSet = model.moduleDocument()
+Sketch_1 = model.addSketch(partSet, model.defaultPlane("XOY"))
+SketchLine_1 = Sketch_1.addLine(-65.36884900412264, 10.74954405845571, -18.59380593895045, 62.75409504395774)
+SketchProjection_1 = Sketch_1.addProjection(model.selection("VERTEX", "Origin"), False)
+SketchPoint_1 = SketchProjection_1.createdFeature()
+
+
+# Test 1. Check MultiRotation error
+
+SketchMultiRotation_1 = Sketch_1.addRotation([SketchLine_1.result()], SketchAPI_Point(SketchPoint_1).coordinates(), 90, 3)
+[SketchLine_2, SketchLine_3] = SketchMultiRotation_1.rotated()
+model.do()
+# check MultiRotation has NO error
+assert(SketchMultiRotation_1.feature().error() == "")
+# change center of MultiRotation to extremity of generated feature, check an error appears
+SketchMultiRotation_1.center().setAttr(SketchAPI_Line(SketchLine_2).startPoint())
+model.do()
+assert(SketchMultiRotation_1.feature().error() != "")
+# revert changes => no error
+SketchMultiRotation_1.center().setAttr(SketchAPI_Point(SketchPoint_1).coordinates())
+model.do()
+assert(SketchMultiRotation_1.feature().error() == "")
+
+
+# Test 2. Check MultiRotation error
+
+SketchMultiTranslation_1 = Sketch_1.addTranslation([SketchLine_1.result()], SketchLine_1.startPoint(), SketchAPI_Line(SketchLine_2).endPoint(), 2)
+[SketchLine_4] = SketchMultiTranslation_1.translated()
+model.do()
+# check MultiTranslation has NO error
+assert(SketchMultiTranslation_1.feature().error() == "")
+# change start point to extremity of generated feature, check an error appears
+SketchMultiTranslation_1.startPoint().setAttr(SketchAPI_Line(SketchLine_4).endPoint())
+model.do()
+assert(SketchMultiTranslation_1.feature().error() != "")
+# revert changes => no error
+SketchMultiTranslation_1.startPoint().setAttr(SketchLine_1.startPoint())
+model.do()
+assert(SketchMultiTranslation_1.feature().error() == "")
+# change end point to extremity of generated feature, check an error appears
+SketchMultiTranslation_1.endPoint().setAttr(SketchAPI_Line(SketchLine_4).endPoint())
+model.do()
+assert(SketchMultiTranslation_1.feature().error() != "")
+# revert changes => no error
+SketchMultiTranslation_1.endPoint().setAttr(SketchAPI_Line(SketchLine_2).endPoint())
+model.do()
+assert(SketchMultiTranslation_1.feature().error() == "")
+
+
+# Test 3. Check Mirror error
+
+SketchConstraintMirror_1 = Sketch_1.addMirror(SketchLine_2.result(), [SketchLine_1.result(), SketchLine_3.result()])
+[SketchLine_5, SketchLine_6] = SketchConstraintMirror_1.mirrored()
+model.do()
+# check Mirror has NO error
+assert(SketchConstraintMirror_1.feature().error() == "")
+# change mirror line to generated feature, check an error appears
+SketchConstraintMirror_1.mirrorLine().setObject(SketchLine_5.feature().firstResult())
+model.do()
+assert(SketchConstraintMirror_1.feature().error() != "")
+# revert changes => no error
+SketchConstraintMirror_1.mirrorLine().setObject(SketchLine_2.feature().firstResult())
+model.do()
+assert(SketchConstraintMirror_1.feature().error() == "")
+
+model.end()
+
+
+assert(model.checkPythonDump())
<sketch_shape_selector id="ConstraintEntityA"
label="Mirror line" tooltip="Select mirror line" shape_types="edge">
<validator id="GeomValidators_ShapeType" parameters="line"/>
+ <validator id="SketchPlugin_ReplicationReference" parameters="ConstraintEntityC"/>
</sketch_shape_selector>
<sketch_multi_selector id="ConstraintMirrorList"
label="Segments:"
shape_types="vertex">
<validator id="PartSet_DifferentObjects"/>
<validator id="GeomValidators_ShapeType" parameters="vertex"/>
+ <validator id="SketchPlugin_ReplicationReference" parameters="ConstraintEntityB"/>
</sketch_shape_selector>
<sketch_shape_selector
id="MultiTranslationEndPoint"
shape_types="vertex">
<validator id="PartSet_DifferentObjects"/>
<validator id="GeomValidators_ShapeType" parameters="vertex"/>
+ <validator id="SketchPlugin_ReplicationReference" parameters="ConstraintEntityB"/>
</sketch_shape_selector>
</groupbox>
</box>
shape_types="vertex">
<validator id="PartSet_DifferentObjects"/>
<validator id="GeomValidators_ShapeType" parameters="vertex"/>
+ <validator id="SketchPlugin_ReplicationReference" parameters="ConstraintEntityB"/>
</sketch_shape_selector>
<sketch_shape_selector
id="MultiTranslationEndPoint"
shape_types="vertex">
<validator id="PartSet_DifferentObjects"/>
<validator id="GeomValidators_ShapeType" parameters="vertex"/>
+ <validator id="SketchPlugin_ReplicationReference" parameters="ConstraintEntityB"/>
</sketch_shape_selector>
</groupbox>
</box>
tooltip="Center of rotation"
shape_types="vertex">
<validator id="GeomValidators_ShapeType" parameters="vertex"/>
+ <validator id="SketchPlugin_ReplicationReference" parameters="ConstraintEntityB"/>
</sketch_shape_selector>
<toolbox id="AngleType">
<box id="SingleAngle" title="Single angle" icon="icons/Sketch/angle_up_32x32.png">
}
// Obtain coordinates of rotation center
+ AttributeRefAttrPtr aCenterAttr =
+ myBaseConstraint->refattr(SketchPlugin_MultiRotation::CENTER_ID());
std::shared_ptr<PlaneGCSSolver_PointWrapper> aRotCenter =
- std::dynamic_pointer_cast<PlaneGCSSolver_PointWrapper>(myStorage->entity(
- myBaseConstraint->attribute(SketchPlugin_MultiRotation::CENTER_ID())));
- GCSPointPtr aCenterPoint = aRotCenter->point();
- myCenterCoord[0] = *(aCenterPoint->x);
- myCenterCoord[1] = *(aCenterPoint->y);
+ std::dynamic_pointer_cast<PlaneGCSSolver_PointWrapper>(myStorage->entity(aCenterAttr));
+ if (aRotCenter)
+ {
+ GCSPointPtr aCenterPoint = aRotCenter->point();
+ myCenterCoord[0] = *(aCenterPoint->x);
+ myCenterCoord[1] = *(aCenterPoint->y);
+ }
+ else
+ {
+ AttributePoint2DPtr aCenterPnt =
+ std::dynamic_pointer_cast<GeomDataAPI_Point2D>(aCenterAttr->attr());
+ myCenterCoord[0] = aCenterPnt->x();
+ myCenterCoord[1] = aCenterPnt->y();
+ }
if (myIsFullValue && myNumberOfCopies > 0)
anAngleValue /= myNumberOfCopies;
return;
// Obtain delta between start and end points of translation
- std::shared_ptr<PlaneGCSSolver_PointWrapper> aStartWrapper =
- std::dynamic_pointer_cast<PlaneGCSSolver_PointWrapper>(myStorage->entity(
- myBaseConstraint->attribute(SketchPlugin_MultiTranslation::START_POINT_ID())));
- std::shared_ptr<PlaneGCSSolver_PointWrapper> aEndWrapper =
- std::dynamic_pointer_cast<PlaneGCSSolver_PointWrapper>(myStorage->entity(
- myBaseConstraint->attribute(SketchPlugin_MultiTranslation::END_POINT_ID())));
-
- GCSPointPtr aStart = aStartWrapper->point();
- GCSPointPtr aEnd = aEndWrapper->point();
-
- myDelta[0] = *(aEnd->x) - *(aStart->x);
- myDelta[1] = *(aEnd->y) - *(aStart->y);
+ AttributeRefAttrPtr aStartEnd[2] = {
+ myBaseConstraint->refattr(SketchPlugin_MultiTranslation::START_POINT_ID()),
+ myBaseConstraint->refattr(SketchPlugin_MultiTranslation::END_POINT_ID())
+ };
+ double aCoords[2][2];
+ for (int i = 0; i < 2; ++i)
+ {
+ std::shared_ptr<PlaneGCSSolver_PointWrapper> aPointWrapper =
+ std::dynamic_pointer_cast<PlaneGCSSolver_PointWrapper>(myStorage->entity(aStartEnd[i]));
+ if (aPointWrapper)
+ {
+ GCSPointPtr aPnt = aPointWrapper->point();
+ aCoords[i][0] = *(aPnt->x);
+ aCoords[i][1] = *(aPnt->y);
+ }
+ else
+ {
+ AttributePoint2DPtr aPnt =
+ std::dynamic_pointer_cast<GeomDataAPI_Point2D>(aStartEnd[i]->attr());
+ aCoords[i][0] = aPnt->x();
+ aCoords[i][1] = aPnt->y();
+ }
+ }
+
+ myDelta[0] = aCoords[1][0] - aCoords[0][0];
+ myDelta[1] = aCoords[1][1] - aCoords[0][1];
if (myIsFullValue && myNumberOfCopies > 0) {
myDelta[0] /= myNumberOfCopies;