#include "BuildAPI_Edge.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void BuildAPI_Edge::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addEdge(" << aPartName << ", "
+ << aBase->selectionList(BuildPlugin_Edge::BASE_OBJECTS_ID()) << ")" << std::endl;
+}
+
//==================================================================================================
EdgePtr addEdge(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theBaseObjects)
/// Modify base attribute of the feature.
BUILDAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Dump wrapped feature
+ BUILDAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Edge object.
#include "BuildAPI_Face.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void BuildAPI_Face::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addFace(" << aPartName << ", "
+ << aBase->selectionList(BuildPlugin_Face::BASE_OBJECTS_ID()) << ")" << std::endl;
+}
+
//==================================================================================================
FacePtr addFace(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theBaseObjects)
/// Modify base attribute of the feature.
BUILDAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Dump wrapped feature
+ BUILDAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Face object.
#include "BuildAPI_Shell.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void BuildAPI_Shell::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addShell(" << aPartName << ", "
+ << aBase->selectionList(BuildPlugin_Shell::BASE_OBJECTS_ID()) << ")" << std::endl;
+}
+
//==================================================================================================
ShellPtr addShell(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theBaseObjects)
/// Modify base attribute of the feature.
BUILDAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Dump wrapped feature
+ BUILDAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Shell object.
#include "BuildAPI_SubShapes.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void BuildAPI_SubShapes::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addSubShapes(" << aPartName << ", "
+ << aBase->selection(BuildPlugin_SubShapes::BASE_SHAPE_ID()) << ", "
+ << aBase->selectionList(BuildPlugin_SubShapes::SUBSHAPES_ID()) << ")" << std::endl;
+}
+
//==================================================================================================
SubShapesPtr addSubShapes(const std::shared_ptr<ModelAPI_Document>& thePart,
const ModelHighAPI_Selection& theBaseShape,
/// Modify sub-shapes attribute of the feature.
BUILDAPI_EXPORT
void setSubShapes(const std::list<ModelHighAPI_Selection>& theSubShapes);
+
+ /// Dump wrapped feature
+ BUILDAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on SubShapes object.
#include "BuildAPI_Vertex.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(BuildAPI_Vertex::ID());
return VertexPtr(new BuildAPI_Vertex(aFeature, theBaseObjects));
}
+
+//==================================================================================================
+void BuildAPI_Vertex::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addVertex(" << aPartName << ", "
+ << aBase->selectionList(BuildPlugin_Vertex::BASE_OBJECTS_ID()) << ")" << std::endl;
+}
/// Modify base attribute of the feature.
BUILDAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Dump wrapped feature
+ BUILDAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Vertex object.
#include "BuildAPI_Wire.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void BuildAPI_Wire::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addWire(" << aPartName << ", "
+ << aBase->selectionList(BuildPlugin_Wire::BASE_OBJECTS_ID()) << ")" << std::endl;
+}
+
//==================================================================================================
void BuildAPI_Wire::addContour()
{
/// Adds closed contour.
BUILDAPI_EXPORT
void addContour();
+
+ /// Dump wrapped feature
+ BUILDAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Wire object.
# Test results
assert (len(anEdgeFeature.results()) == aNumOfLines)
+
+import model
+assert(model.checkPythonDump())
# Test results
assert (len(aFaceFeature.results()) > 0)
+
+import model
+assert(model.checkPythonDump())
# Test results
assert (len(aShellFeature.results()) > 0)
+
+import model
+assert(model.checkPythonDump())
# Test results
assert (len(aSubShapesFeature.results()) > 0)
+
+import model
+assert(model.checkPythonDump())
# Test results
assert (len(aVertexFeature.results()) == aNumOfPoints)
+
+import model
+assert(model.checkPythonDump())
# Test results
assert (len(aWireFeature.results()) > 0)
+
+import model
+assert(model.checkPythonDump())
#include "ConstructionAPI_Axis.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void ConstructionAPI_Axis::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addAxis(" << aDocName;
+
+ std::string aCreationMethod = aBase->string(ConstructionPlugin_Axis::METHOD())->value();
+
+ if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_DIMENSIONS()) {
+ AttributeDoublePtr anAttrDX = aBase->real(ConstructionPlugin_Axis::DX());
+ AttributeDoublePtr anAttrDY = aBase->real(ConstructionPlugin_Axis::DY());
+ AttributeDoublePtr anAttrDZ = aBase->real(ConstructionPlugin_Axis::DZ());
+
+ theDumper << ", " << anAttrDX << ", " << anAttrDY << ", " << anAttrDZ;
+ } else if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_TWO_POINTS()) {
+ AttributeSelectionPtr anAttrFirstPnt = aBase->selection(ConstructionPlugin_Axis::POINT_FIRST());
+ AttributeSelectionPtr anAttrSecondPnt = aBase->selection(ConstructionPlugin_Axis::POINT_SECOND());
+
+ theDumper << ", " << anAttrFirstPnt << ", " << anAttrSecondPnt;
+ } else if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_LINE()) {
+ AttributeSelectionPtr anAttrLine = aBase->selection(ConstructionPlugin_Axis::LINE());
+
+ theDumper << ", " << anAttrLine;
+ } else if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_CYLINDRICAL_FACE()) {
+ AttributeSelectionPtr anAttrFace = aBase->selection(ConstructionPlugin_Axis::CYLINDRICAL_FACE());
+
+ theDumper << ", " << anAttrFace;
+ } else if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_PLANE_AND_POINT()) {
+ AttributeSelectionPtr anAttrPlane = aBase->selection(ConstructionPlugin_Axis::PLANE());
+ AttributeSelectionPtr anAttrPoint = aBase->selection(ConstructionPlugin_Axis::POINT());
+
+ theDumper << ", " << anAttrPlane << ", " << anAttrPoint;
+ } else if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_TWO_PLANES()) {
+ AttributeSelectionPtr anAttrPlane1 = aBase->selection(ConstructionPlugin_Axis::PLANE1());
+ AttributeDoublePtr anAttrOffset1 = aBase->real(ConstructionPlugin_Axis::OFFSET1());
+ AttributeBooleanPtr anAttrReverseOffset1 = aBase->boolean(ConstructionPlugin_Axis::REVERSE_OFFSET1());
+ AttributeSelectionPtr anAttrPlane2 = aBase->selection(ConstructionPlugin_Axis::PLANE2());
+ AttributeDoublePtr anAttrOffset2 = aBase->real(ConstructionPlugin_Axis::OFFSET2());
+ AttributeBooleanPtr anAttrReverseOffset2 = aBase->boolean(ConstructionPlugin_Axis::REVERSE_OFFSET2());
+
+ theDumper << ", " << anAttrPlane1 << ", " << anAttrOffset1 << ", " << anAttrReverseOffset1
+ << ", " << anAttrPlane2 << ", " << anAttrOffset2 << ", " << anAttrReverseOffset2;
+ } else if(aCreationMethod == ConstructionPlugin_Axis::CREATION_METHOD_BY_POINT_AND_DIRECTION()) {
+ AttributeSelectionPtr anAttrFirstPnt = aBase->selection(ConstructionPlugin_Axis::POINT_FIRST());
+ AttributeDoublePtr anAttrX = aBase->real(ConstructionPlugin_Axis::X_DIRECTION());
+ AttributeDoublePtr anAttrY = aBase->real(ConstructionPlugin_Axis::Y_DIRECTION());
+ AttributeDoublePtr anAttrZ = aBase->real(ConstructionPlugin_Axis::Z_DIRECTION());
+
+ theDumper << ", " << anAttrFirstPnt << ", " << anAttrX << ", " << anAttrY << ", " << anAttrZ;
+ }
+
+ theDumper << ")" << std::endl;
+}
+
//==================================================================================================
AxisPtr addAxis(const std::shared_ptr<ModelAPI_Document>& thePart,
- const ModelHighAPI_Selection& thePoint1,
- const ModelHighAPI_Selection& thePoint2)
+ const ModelHighAPI_Selection& theObject1,
+ const ModelHighAPI_Selection& theObject2)
{
// TODO(spo): check that thePart is not empty
std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(ConstructionAPI_Axis::ID());
- return AxisPtr(new ConstructionAPI_Axis(aFeature, thePoint1, thePoint2));
+ return AxisPtr(new ConstructionAPI_Axis(aFeature, theObject1, theObject2));
}
//==================================================================================================
const ModelHighAPI_Selection& thePlane2,
const ModelHighAPI_Double& theOffset2,
const bool theReverseOffset2);
+
+ /// Dump wrapped feature
+ CONSTRUCTIONAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Axis object
#include "ConstructionAPI_Plane.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void ConstructionAPI_Plane::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addPlane(" << aDocName;
+
+ std::string aCreationMethod = aBase->string(ConstructionPlugin_Plane::CREATION_METHOD())->value();
+
+ if(aCreationMethod == ConstructionPlugin_Plane::CREATION_METHOD_BY_GENERAL_EQUATION()) {
+ AttributeDoublePtr anAttrA = aBase->real(ConstructionPlugin_Plane::A());
+ AttributeDoublePtr anAttrB = aBase->real(ConstructionPlugin_Plane::B());
+ AttributeDoublePtr anAttrC = aBase->real(ConstructionPlugin_Plane::C());
+ AttributeDoublePtr anAttrD = aBase->real(ConstructionPlugin_Plane::D());
+
+ theDumper << ", " << anAttrA << ", " << anAttrB << ", " << anAttrC << ", " << anAttrD;
+ } else if(aCreationMethod == ConstructionPlugin_Plane::CREATION_METHOD_BY_THREE_POINTS()) {
+ AttributeSelectionPtr anAttrPnt1 = aBase->selection(ConstructionPlugin_Plane::POINT1());
+ AttributeSelectionPtr anAttrPnt2 = aBase->selection(ConstructionPlugin_Plane::POINT2());
+ AttributeSelectionPtr anAttrPnt3 = aBase->selection(ConstructionPlugin_Plane::POINT3());
+
+ theDumper << ", " << anAttrPnt1 << ", " << anAttrPnt2 << ", " << anAttrPnt3;
+ } else if(aCreationMethod == ConstructionPlugin_Plane::CREATION_METHOD_BY_LINE_AND_POINT()) {
+ AttributeSelectionPtr anAttrLine = aBase->selection(ConstructionPlugin_Plane::LINE());
+ AttributeSelectionPtr anAttrPoint = aBase->selection(ConstructionPlugin_Plane::POINT());
+ AttributeBooleanPtr anAttrPerpendicular = aBase->boolean(ConstructionPlugin_Plane::PERPENDICULAR());
+
+ theDumper << ", " << anAttrLine << ", " << anAttrPoint << ", " << anAttrPerpendicular;
+ } else if(aCreationMethod == ConstructionPlugin_Plane::CREATION_METHOD_BY_OTHER_PLANE()) {
+ AttributeSelectionPtr anAttrPlane = aBase->selection(ConstructionPlugin_Plane::PLANE());
+
+ std::string aCreationMethodOption =
+ aBase->string(ConstructionPlugin_Plane::CREATION_METHOD_BY_OTHER_PLANE_OPTION())->value();
+ if(aCreationMethodOption == ConstructionPlugin_Plane::CREATION_METHOD_BY_DISTANCE_FROM_OTHER()) {
+ AttributeDoublePtr anAttrDistance = aBase->real(ConstructionPlugin_Plane::DISTANCE());
+ AttributeBooleanPtr anAttrReverse = aBase->boolean(ConstructionPlugin_Plane::REVERSE());
+
+ theDumper << ", " << anAttrPlane << ", " << anAttrDistance << ", " << anAttrReverse;
+ } else if(aCreationMethodOption == ConstructionPlugin_Plane::CREATION_METHOD_BY_COINCIDENT_TO_POINT()) {
+ AttributeSelectionPtr anAttrPoint = aBase->selection(ConstructionPlugin_Plane::COINCIDENT_POINT());
+
+ theDumper << ", " << anAttrPlane << ", " << anAttrPoint;
+ } else if(aCreationMethodOption == ConstructionPlugin_Plane::CREATION_METHOD_BY_ROTATION()) {
+ AttributeSelectionPtr anAttrAxis = aBase->selection(ConstructionPlugin_Plane::AXIS());
+ AttributeDoublePtr anAttrAngle = aBase->real(ConstructionPlugin_Plane::ANGLE());
+
+ theDumper << ", " << anAttrPlane << ", " << anAttrAxis << ", " << anAttrAngle;
+ }
+ } else if(aCreationMethod == ConstructionPlugin_Plane::CREATION_METHOD_BY_TWO_PARALLEL_PLANES()) {
+ AttributeSelectionPtr anAttrPlane1 = aBase->selection(ConstructionPlugin_Plane::PLANE1());
+ AttributeSelectionPtr anAttrPlane2 = aBase->selection(ConstructionPlugin_Plane::PLANE2());
+
+ theDumper << ", " << anAttrPlane1 << ", " << anAttrPlane2;
+ }
+
+ theDumper << ")" << std::endl;
+}
+
//==================================================================================================
PlanePtr addPlane(const std::shared_ptr<ModelAPI_Document>& thePart,
const ModelHighAPI_Selection& theFace,
const ModelHighAPI_Selection& theAxis,
const ModelHighAPI_Double& theAngle);
+ /// Dump wrapped feature
+ CONSTRUCTIONAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Plane object
#include <GeomAPI_Shape.h>
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
fillAttribute(theY, myy);
fillAttribute(theZ, myz);
- execute();
+ execute(false);
}
/*//==================================================================================================
execute();
}*/
+//==================================================================================================
+void ConstructionAPI_Point::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ // TODO: all types of points
+
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeDoublePtr anAttrX = aBase->real(ConstructionPlugin_Point::X());
+ AttributeDoublePtr anAttrY = aBase->real(ConstructionPlugin_Point::Y());
+ AttributeDoublePtr anAttrZ = aBase->real(ConstructionPlugin_Point::Z());
+ theDumper << aBase << " = model.addPoint(" << aDocName << ", "
+ << anAttrX << ", " << anAttrY << ", " << anAttrZ << ")" << std::endl;
+}
+
//==================================================================================================
PointPtr addPoint(const std::shared_ptr<ModelAPI_Document>& thePart,
const ModelHighAPI_Double& theX,
CONSTRUCTIONAPI_EXPORT
void setByLineAndPlaneIntersection(const ModelHighAPI_Selection& theEdge,
const ModelHighAPI_Selection& theFace);*/
+
+ /// Dump wrapped feature
+ CONSTRUCTIONAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Point object.
import ModelAPI
import ConstructionAPI
+import model
class AxisTestCase(unittest.TestCase):
self.session.finishOperation()
def tearDown(self):
+ assert(model.checkPythonDump())
self.session.closeAll()
def test_ConstructorWithDimensions(self):
import ModelAPI
import ConstructionAPI
+import model
class PointTestCase(unittest.TestCase):
self.doc = self.session.moduleDocument()
self.session.startOperation()
self.feature = self.doc.addFeature("Point")
- self.feature.execute()
- self.session.finishOperation()
def tearDown(self):
+ self.session.finishOperation()
+ assert(model.checkPythonDump())
self.session.closeAll()
def test_ConstructorWithValues(self):
def test_setValue(self):
point = ConstructionAPI.ConstructionAPI_Point(self.feature)
- self.assertEqual(0, point.x().value())
- self.assertEqual(0, point.y().value())
- self.assertEqual(0, point.z().value())
+ assert(point.x().isInitialized() == False)
+ assert(point.y().isInitialized() == False)
+ assert(point.z().isInitialized() == False)
point.setByXYZ(10, "20", "x + 30")
self.assertEqual(10, point.x().value())
ADD_UNIT_TESTS(TestAxisCreation.py
UnitTestAxis.py
- TestPointName.py
TestPoint.py
+ TestPointName.py
TestPlane.py)
anAxis = model.addAxis(aPart, aPlane1.result()[0], 50, False, aPlane2.result()[0], 100, True)
aSession.finishOperation()
assert (len(anAxis.result()) > 0)
+
+#import model
+#assert(model.checkPythonDump())
aPlane = model.addPlane(aDocument, aCoincidentPlane.result()[0], aPlane.result()[0])
aSession.finishOperation()
assert (len(aPlane.result()) > 0)
+
+import model
+assert(model.checkPythonDump())
# aPoint = model.addPoint(aDocument, aSketchLine1.result()[0], aPlane.result()[0])
# aSession.finishOperation()
# assert (len(aPoint.result()) > 0)
+
+assert(model.checkPythonDump())
aFeature1Name = aFeature1.data().name()
assert (aFeatureName == aFeature1Name)
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
{
// TODO(spo): check that thePart is not empty
std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(ExchangePlugin_ExportFeature::ID());
+ fillAttribute("Regular", aFeature->string(ExchangePlugin_ExportFeature::EXPORT_TYPE_ID()));
fillAttribute(theFilePath, aFeature->string(ExchangePlugin_ExportFeature::FILE_PATH_ID()));
fillAttribute(theSelectionList, aFeature->selectionList(ExchangePlugin_ExportFeature::SELECTION_LIST_ID()));
fillAttribute(theFileFormat, aFeature->string(ExchangePlugin_ExportFeature::FILE_FORMAT_ID()));
{
// TODO(spo): check that thePart is not empty
std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(ExchangePlugin_ExportFeature::ID());
- fillAttribute(theFilePath, aFeature->string(ExchangePlugin_ExportFeature::FILE_PATH_ID()));
+ fillAttribute("XAO", aFeature->string(ExchangePlugin_ExportFeature::EXPORT_TYPE_ID()));
+ fillAttribute(theFilePath, aFeature->string(ExchangePlugin_ExportFeature::XAO_FILE_PATH_ID()));
fillAttribute(theAuthor, aFeature->string(ExchangePlugin_ExportFeature::XAO_AUTHOR_ID()));
fillAttribute(theGeometryName, aFeature->string(ExchangePlugin_ExportFeature::XAO_GEOMETRY_NAME_ID()));
+ fillAttribute("XAO", aFeature->string(ExchangePlugin_ExportFeature::FILE_FORMAT_ID()));
aFeature->execute();
}
//--------------------------------------------------------------------------------------
#include "ExchangeAPI_Import.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
+#include <algorithm>
+
ExchangeAPI_Import::ExchangeAPI_Import(
const std::shared_ptr<ModelAPI_Feature> & theFeature)
: ModelHighAPI_Interface(theFeature)
execute();
}
+//--------------------------------------------------------------------------------------
+void ExchangeAPI_Import::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ std::string aPartName = theDumper.name(aBase->document());
+
+ std::string aFilePath = aBase->string(ExchangePlugin_ImportFeature::FILE_PATH_ID())->value();
+ std::string aFrom = "\\";
+ std::string aTo = "\\\\";
+ for(std::size_t aPos = aFilePath.find(aFrom);
+ aPos != std::string::npos;
+ aPos = aFilePath.find(aFrom, aPos)) {
+ aFilePath.replace(aPos, aFrom.size(), aTo);
+ aPos += aTo.size();
+ }
+
+ theDumper << aBase << " = model.addImport(" << aPartName << ", \""
+ << aFilePath << "\")" << std::endl;
+ // to make import have results
+ theDumper << "model.do()" << std::endl;
+
+ CompositeFeaturePtr aCompositeFeature = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(aBase);
+ if(aCompositeFeature.get()) {
+ int aNbOfSubs = aCompositeFeature->numberOfSubs();
+ for(int anIndex = 0; anIndex < aNbOfSubs; ++anIndex) {
+ std::string aSubFeatureGet = theDumper.name(aBase) + ".subFeature(" + std::to_string((long long)anIndex) + ")";
+ theDumper.dumpSubFeatureNameAndColor(aSubFeatureGet, aCompositeFeature->subFeature(anIndex));
+ }
+ }
+}
+
//--------------------------------------------------------------------------------------
ImportPtr addImport(
const std::shared_ptr<ModelAPI_Document> & thePart,
/// Set point values
EXCHANGEAPI_EXPORT
void setFilePath(const std::string & theFilePath);
+
+ /// Dump wrapped feature
+ EXCHANGEAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Import object
import ModelAPI
import ExchangeAPI
+import model
class ExchangeTestCase(unittest.TestCase):
self.doc = self.session.moduleDocument()
def tearDown(self):
+ # assert(model.checkPythonDump())
+ # This test just checks interface of Exchange High API
+ # Export feature stays in the tree because it's invalid, but after dump it is not in the tree.
self.session.closeAll()
def test_addImport(self):
INCLUDE_DIRECTORIES(${PROJECT_SOURCE_DIR}/src/Events
${PROJECT_SOURCE_DIR}/src/Config
${PROJECT_SOURCE_DIR}/src/ModelAPI
+ ${PROJECT_SOURCE_DIR}/src/ModelHighAPI
${PROJECT_SOURCE_DIR}/src/GeomAPI
${PROJECT_SOURCE_DIR}/src/GeomAlgoAPI
${PROJECT_SOURCE_DIR}/src/XAO
ExchangePlugin_ExportFeature.h
ExchangePlugin_Validators.h
ExchangePlugin_Tools.h
+ ExchangePlugin_Dump.h
)
SET(PROJECT_SOURCES
ExchangePlugin_ExportFeature.cpp
ExchangePlugin_Validators.cpp
ExchangePlugin_Tools.cpp
+ ExchangePlugin_Dump.cpp
)
SET(XML_RESOURCES
Events
Config
ModelAPI
+ ModelHighAPI
GeomAPI
GeomAlgoAPI
XAO
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: ExchangePlugin_ExportFeature.cpp
+// Created: May 14, 2015
+// Author: Sergey POKHODENKO
+
+#include <ExchangePlugin_Dump.h>
+
+#include <ModelAPI_AttributeString.h>
+#include <ModelAPI_Document.h>
+#include <ModelAPI_Session.h>
+
+#include <ModelHighAPI_Dumper.h>
+
+#include <Config_ModuleReader.h>
+
+
+ExchangePlugin_Dump::ExchangePlugin_Dump()
+{
+}
+
+ExchangePlugin_Dump::~ExchangePlugin_Dump()
+{
+}
+
+void ExchangePlugin_Dump::initAttributes()
+{
+ data()->addAttribute(ExchangePlugin_Dump::FILE_PATH_ID(), ModelAPI_AttributeString::typeId());
+ data()->addAttribute(ExchangePlugin_Dump::FILE_FORMAT_ID(), ModelAPI_AttributeString::typeId());
+}
+
+void ExchangePlugin_Dump::execute()
+{
+ AttributeStringPtr aFilePathAttr =
+ this->string(ExchangePlugin_Dump::FILE_PATH_ID());
+ std::string aFilePath = aFilePathAttr->value();
+ if (aFilePath.empty())
+ return;
+
+ dump(aFilePath);
+}
+
+void ExchangePlugin_Dump::dump(const std::string& theFileName)
+{
+ // load DumpAssistant from Python side
+ Config_ModuleReader::loadScript("model.dump");
+
+ ModelHighAPI_Dumper* aDumper = ModelHighAPI_Dumper::getInstance();
+ aDumper->clear();
+ DocumentPtr aDoc = ModelAPI_Session::get()->moduleDocument();
+ if (!aDumper || !aDumper->process(aDoc, theFileName))
+ setError("An error occured while dumping to " + theFileName);
+}
--- /dev/null
+// Copyright (C) 2016-20xx CEA/DEN, EDF R&D
+
+// File: ExchangePlugin_Dump.h
+// Created: August 1, 2016
+// Author: Artem ZHIDKOV
+
+#ifndef EXCHANGEPLUGIN_DUMP_H_
+#define EXCHANGEPLUGIN_DUMP_H_
+
+#include <ExchangePlugin.h>
+
+#include <ModelAPI_Feature.h>
+
+/**
+ * \class ExchangePlugin_Dump
+ * \ingroup Plugins
+ * \brief Store full model as a Python script
+ */
+class ExchangePlugin_Dump : public ModelAPI_Feature
+{
+public:
+ /// Feature kind
+ inline static const std::string& ID()
+ {
+ static const std::string MY_DUMP_ID("Dump");
+ return MY_DUMP_ID;
+ }
+ /// attribute name of file path
+ inline static const std::string& FILE_PATH_ID()
+ {
+ static const std::string MY_FILE_PATH_ID("file_path");
+ return MY_FILE_PATH_ID;
+ }
+ /// attribute name of file format
+ inline static const std::string& FILE_FORMAT_ID()
+ {
+ static const std::string MY_FILE_FORMAT_ID("file_format");
+ return MY_FILE_FORMAT_ID;
+ }
+
+ /// Default constructor
+ EXCHANGEPLUGIN_EXPORT ExchangePlugin_Dump();
+ /// Default destructor
+ EXCHANGEPLUGIN_EXPORT virtual ~ExchangePlugin_Dump();
+
+ /// Returns the unique kind of a feature
+ EXCHANGEPLUGIN_EXPORT virtual const std::string& getKind()
+ {
+ return ExchangePlugin_Dump::ID();
+ }
+
+ /// Request for initialization of data model of the feature: adding all attributes
+ EXCHANGEPLUGIN_EXPORT virtual void initAttributes();
+
+ /// Computes or recomputes the results
+ EXCHANGEPLUGIN_EXPORT virtual void execute();
+
+ /// Reimplemented from ModelAPI_Feature::isMacro(). Returns true.
+ EXCHANGEPLUGIN_EXPORT virtual bool isMacro() const { return true; }
+
+ /// Reimplemented from ModelAPI_Feature::isPreviewNeeded(). Returns false.
+ EXCHANGEPLUGIN_EXPORT virtual bool isPreviewNeeded() const { return false; }
+
+protected:
+ /// Performs dump to the file
+ EXCHANGEPLUGIN_EXPORT void dump(const std::string& theFileName);
+};
+
+#endif
// Author: Sergey BELASH
#include <ExchangePlugin_Plugin.h>
+#include <ExchangePlugin_Dump.h>
#include <ExchangePlugin_ImportFeature.h>
#include <ExchangePlugin_ExportFeature.h>
#include <ExchangePlugin_Validators.h>
} else
if (theFeatureID == ExchangePlugin_ExportFeature::ID()) {
return FeaturePtr(new ExchangePlugin_ExportFeature);
+ } else
+ if (theFeatureID == ExchangePlugin_Dump::ID()) {
+ return FeaturePtr(new ExchangePlugin_Dump);
}
// feature of such kind is not found
return FeaturePtr();
aSession.startOperation()
aGroup = model.addGroup(aPart, [])
- aGroup.defaultResult().data().setName("")
aGroup.groupList().setSelectionType("face")
aGroup.groupList().append("Box_1_1/Shape1_1")
aGroup.groupList().append("Box_1_1/Shape2_1")
+ aGroup.defaultResult().data().setName("")
# aGroupFeature = aSession.activeDocument().addFeature("Group")
# aGroupFeature.data().setName("")
# aSelectionListAttr = aGroupFeature.selectionList("group_list")
# aSelectionListAttr.setSelectionType("face")
-# aSelectionListAttr.append("Box_1_1/Shape1_1")
-# aSelectionListAttr.append("Box_1_1/Shape2_1")
+# aSelectionListAttr.append("Box_1_1/Shape1")
+# aSelectionListAttr.append("Box_1_1/Shape2")
# aGroupFeature.execute()
aSession.finishOperation()
#=========================================================================
# End of test
#=========================================================================
+
+assert(model.checkPythonDump())
aSelectionList = aFeature1.selectionList("group_list")
assert aSelectionList.selectionType() == "solid"
assert aSelectionList.size() == 1
- assert aSelectionList.value(0).namingName("") == "mygeom_1_1"
+ assert aSelectionList.value(0).namingName("") == "mygeom_1"
aFeature2 = aCompositeFeature.subFeature(1, False)
assert aFeature2.getKind() == "Group"
aSelectionList = aFeature2.selectionList("group_list")
assert aSelectionList.selectionType() == "face"
assert aSelectionList.size() == 2
- assert aSelectionList.value(0).namingName("") == "mygeom_1/Shape1_1"
- assert aSelectionList.value(1).namingName("") == "mygeom_1/Shape2_1"
+ assert aSelectionList.value(0).namingName("") == "mygeom_1/Shape1"
+ print aSelectionList.value(1).namingName("")
+ assert aSelectionList.value(1).namingName("") == "mygeom_1/Shape2"
if __name__ == '__main__':
#=========================================================================
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
<feature id="Export" title="Export" tooltip="Export to file" icon="icons/Exchange/export.png">
<source path="export_widget.xml" />
</feature>
+ <feature id="Dump" title="Dump" tooltip="Dump python script" icon="icons/Exchange/dump.png">
+ <export_file_selector id="file_path"
+ type="save"
+ title="Dump to file"
+ path="">
+ <validator id="ExchangePlugin_ExportFormat"
+ parameters="py:Python" />
+ </export_file_selector>
+ </feature>
</group>
</workbench>
</plugin>
\ No newline at end of file
FeaturesAPI_RevolutionBoolean.h
FeaturesAPI_Rotation.h
FeaturesAPI_Translation.h
+ FeaturesAPI_Union.h
)
SET(PROJECT_SOURCES
FeaturesAPI_RevolutionBoolean.cpp
FeaturesAPI_Rotation.cpp
FeaturesAPI_Translation.cpp
+ FeaturesAPI_Union.cpp
)
SET(PROJECT_LIBRARIES
%shared_ptr(FeaturesAPI_RevolutionFuse)
%shared_ptr(FeaturesAPI_Rotation)
%shared_ptr(FeaturesAPI_Translation)
+%shared_ptr(FeaturesAPI_Union)
// all supported interfaces
%include "FeaturesAPI_Boolean.h"
%include "FeaturesAPI_RevolutionBoolean.h"
%include "FeaturesAPI_Rotation.h"
%include "FeaturesAPI_Translation.h"
+%include "FeaturesAPI_Union.h"
#include "FeaturesAPI_Boolean.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Integer.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
fillAttribute(theMainObjects, mymainObjects);
fillAttribute(theToolObjects, mytoolObjects);
- execute();
+ execute(false);
}
}
execute();
}
+//==================================================================================================
+void FeaturesAPI_Boolean::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+
+ FeaturesPlugin_Boolean::OperationType aType =
+ (FeaturesPlugin_Boolean::OperationType)aBase->integer(FeaturesPlugin_Boolean::TYPE_ID())->value();
+
+ theDumper << aBase << " = model.add";
+
+ switch(aType) {
+ case FeaturesPlugin_Boolean::BOOL_CUT: theDumper << "Cut"; break;
+ case FeaturesPlugin_Boolean::BOOL_FUSE: theDumper << "Fuse"; break;
+ case FeaturesPlugin_Boolean::BOOL_COMMON: theDumper << "Common"; break;
+ case FeaturesPlugin_Boolean::BOOL_FILL: theDumper << "Fill"; break;
+ case FeaturesPlugin_Boolean::BOOL_SMASH: theDumper << "Smash"; break;
+ }
+
+ const std::string& aDocName = theDumper.name(aBase->document());
+ AttributeSelectionListPtr anObjects = aBase->selectionList(FeaturesPlugin_Boolean::OBJECT_LIST_ID());
+ AttributeSelectionListPtr aTools = aBase->selectionList(FeaturesPlugin_Boolean::TOOL_LIST_ID());
+
+ theDumper << "(" << aDocName << ", " << anObjects << ", " << aTools << ")" << std::endl;
+}
+
//==================================================================================================
BooleanPtr addCut(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theMainObjects,
/// Set tool objects.
FEATURESAPI_EXPORT
void setToolObjects(const std::list<ModelHighAPI_Selection>& theToolObjects);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Boolean object.
#include "FeaturesAPI_Extrusion.h"
#include <ModelHighAPI_Double.h>
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Reference.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
//==================================================================================================
FeaturesAPI_Extrusion::~FeaturesAPI_Extrusion()
{
+}
+
+//==================================================================================================
+void FeaturesAPI_Extrusion::setNestedSketch(const ModelHighAPI_Reference& theSketch)
+{
+ mysketch->setValue(theSketch.feature());
+ mybaseObjects->clear();
+ mybaseObjects->append(theSketch.feature()->firstResult(), GeomShapePtr());
+ execIfBaseNotEmpty();
}
//==================================================================================================
void FeaturesAPI_Extrusion::setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects)
{
+ mysketch->setValue(ObjectPtr());
+ mybaseObjects->clear();
fillAttribute(theBaseObjects, mybaseObjects);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
{
fillAttribute(theDirection, mydirection);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theToSize, mytoSize);
fillAttribute(theFromSize, myfromSize);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theSize, mytoSize);
fillAttribute(ModelHighAPI_Double(), myfromSize);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theFromObject, myfromObject);
fillAttribute(theFromOffset, myfromOffset);
- execute();
+ execIfBaseNotEmpty();
+}
+
+//==================================================================================================
+void FeaturesAPI_Extrusion::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeReferencePtr anAttrSketch = aBase->reference(FeaturesPlugin_Extrusion::SKETCH_ID());
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Extrusion::BASE_OBJECTS_ID());
+ AttributeSelectionPtr anAttrDirection = aBase->selection(FeaturesPlugin_Extrusion::DIRECTION_OBJECT_ID());
+
+ theDumper << aBase << " = model.addExtrusion(" << aDocName << ", ";
+ anAttrSketch->isInitialized() ? theDumper << "[]" : theDumper << anAttrObjects;
+ theDumper << ", " << anAttrDirection;
+
+ std::string aCreationMethod = aBase->string(FeaturesPlugin_Extrusion::CREATION_METHOD())->value();
+
+ if(aCreationMethod == FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES()) {
+ AttributeDoublePtr anAttrToSize = aBase->real(FeaturesPlugin_Extrusion::TO_SIZE_ID());
+ AttributeDoublePtr anAttrFromSize = aBase->real(FeaturesPlugin_Extrusion::FROM_SIZE_ID());
+
+ theDumper << ", " << anAttrToSize << ", " << anAttrFromSize;
+ } else if(aCreationMethod == FeaturesPlugin_Extrusion::CREATION_METHOD_BY_PLANES()) {
+ AttributeSelectionPtr anAttrToObject = aBase->selection(FeaturesPlugin_Extrusion::TO_OBJECT_ID());
+ AttributeDoublePtr anAttrToOffset = aBase->real(FeaturesPlugin_Extrusion::TO_OFFSET_ID());
+ AttributeSelectionPtr anAttrFromObject = aBase->selection(FeaturesPlugin_Extrusion::FROM_OBJECT_ID());
+ AttributeDoublePtr anAttrFromOffset = aBase->real(FeaturesPlugin_Extrusion::FROM_OFFSET_ID());
+
+ theDumper << ", " << anAttrToObject << ", " << anAttrToOffset << ", " << anAttrFromObject << ", " << anAttrFromOffset;
+ }
+
+ theDumper << ")" << std::endl;
+
+ if(anAttrSketch->isInitialized()) {
+ theDumper << aBase << ".setNestedSketch(" << anAttrSketch << ")" << std::endl;
+ }
+}
+
+//==================================================================================================
+void FeaturesAPI_Extrusion::execIfBaseNotEmpty()
+{
+ if(mybaseObjects->size() > 0) {
+ execute();
+ }
}
//==================================================================================================
#include <ModelHighAPI_Macro.h>
class ModelHighAPI_Double;
+class ModelHighAPI_Reference;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Extrusion
virtual ~FeaturesAPI_Extrusion();
INTERFACE_10(FeaturesPlugin_Extrusion::ID(),
+ sketch, FeaturesPlugin_Extrusion::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */,
baseObjects, FeaturesPlugin_Extrusion::BASE_OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Base objects */,
+ direction, FeaturesPlugin_Extrusion::DIRECTION_OBJECT_ID(), ModelAPI_AttributeSelection, /** Direction */,
creationMethod, FeaturesPlugin_Extrusion::CREATION_METHOD(), ModelAPI_AttributeString, /** Creation method */,
toSize, FeaturesPlugin_Extrusion::TO_SIZE_ID(), ModelAPI_AttributeDouble, /** To size */,
fromSize, FeaturesPlugin_Extrusion::FROM_SIZE_ID(), ModelAPI_AttributeDouble, /** From size */,
toObject, FeaturesPlugin_Extrusion::TO_OBJECT_ID(), ModelAPI_AttributeSelection, /** To object */,
toOffset, FeaturesPlugin_Extrusion::TO_OFFSET_ID(), ModelAPI_AttributeDouble, /** To offset */,
fromObject, FeaturesPlugin_Extrusion::FROM_OBJECT_ID(), ModelAPI_AttributeSelection, /** From object */,
- fromOffset, FeaturesPlugin_Extrusion::FROM_OFFSET_ID(), ModelAPI_AttributeDouble, /** From offset */,
- direction, FeaturesPlugin_Extrusion::DIRECTION_OBJECT_ID(), ModelAPI_AttributeSelection, /** Direction */,
- sketchLauncher, FeaturesPlugin_Extrusion::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */)
+ fromOffset, FeaturesPlugin_Extrusion::FROM_OFFSET_ID(), ModelAPI_AttributeDouble, /** From offset */)
+
+ /// Modify base attribute of the feature.
+ FEATURESAPI_EXPORT
+ void setNestedSketch(const ModelHighAPI_Reference& theSketch);
/// Modify base attribute of the feature.
FEATURESAPI_EXPORT
const ModelHighAPI_Double& theToOffset,
const ModelHighAPI_Selection& theFromObject,
const ModelHighAPI_Double& theFromOffset);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
+private:
+ void execIfBaseNotEmpty();
};
/// Pointer on Extrusion object.
#include "FeaturesAPI_ExtrusionBoolean.h"
#include <ModelHighAPI_Double.h>
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Reference.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
{
}
+//==================================================================================================
+void FeaturesAPI_ExtrusionBoolean::setNestedSketch(const ModelHighAPI_Reference& theSketch)
+{
+ mysketch->setValue(theSketch.feature());
+ mybaseObjects->clear();
+ mybaseObjects->append(theSketch.feature()->firstResult(), GeomShapePtr());
+
+ execIfBaseNotEmpty();
+}
+
//==================================================================================================
void FeaturesAPI_ExtrusionBoolean::setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects)
{
+ mysketch->setValue(ObjectPtr());
+ mybaseObjects->clear();
fillAttribute(theBaseObjects, mybaseObjects);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
{
fillAttribute(theDirection, mydirection);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theToSize, mytoSize);
fillAttribute(theFromSize, myfromSize);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theSize, mytoSize);
fillAttribute(ModelHighAPI_Double(), myfromSize);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theFromObject, myfromObject);
fillAttribute(theFromOffset, myfromOffset);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
{
fillAttribute(theBooleanObjects, mybooleanObjects);
- execute();
+ execIfBaseNotEmpty();
+}
+
+//==================================================================================================
+void FeaturesAPI_ExtrusionBoolean::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeReferencePtr anAttrSketch = aBase->reference(FeaturesPlugin_Extrusion::SKETCH_ID());
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Extrusion::BASE_OBJECTS_ID());
+ AttributeSelectionPtr anAttrDirection = aBase->selection(FeaturesPlugin_Extrusion::DIRECTION_OBJECT_ID());
+
+ theDumper << aBase << " = model.addExtrusion";
+ if(aBase->getKind() == FeaturesPlugin_ExtrusionCut::ID()) {
+ theDumper << "Cut";
+ } else if(aBase->getKind() == FeaturesPlugin_ExtrusionFuse::ID()) {
+ theDumper << "Fuse";
+ }
+ theDumper << "(" << aDocName << ", ";
+ anAttrSketch->isInitialized() ? theDumper << "[]" : theDumper << anAttrObjects;
+ theDumper << ", " << anAttrDirection;
+
+ std::string aCreationMethod = aBase->string(FeaturesPlugin_Extrusion::CREATION_METHOD())->value();
+
+ if(aCreationMethod == FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES()) {
+ AttributeDoublePtr anAttrToSize = aBase->real(FeaturesPlugin_Extrusion::TO_SIZE_ID());
+ AttributeDoublePtr anAttrFromSize = aBase->real(FeaturesPlugin_Extrusion::FROM_SIZE_ID());
+
+ theDumper << ", " << anAttrToSize << ", " << anAttrFromSize;
+ } else if(aCreationMethod == FeaturesPlugin_Extrusion::CREATION_METHOD_BY_PLANES()) {
+ AttributeSelectionPtr anAttrToObject = aBase->selection(FeaturesPlugin_Extrusion::TO_OBJECT_ID());
+ AttributeDoublePtr anAttrToOffset = aBase->real(FeaturesPlugin_Extrusion::TO_OFFSET_ID());
+ AttributeSelectionPtr anAttrFromObject = aBase->selection(FeaturesPlugin_Extrusion::FROM_OBJECT_ID());
+ AttributeDoublePtr anAttrFromOffset = aBase->real(FeaturesPlugin_Extrusion::FROM_OFFSET_ID());
+
+ theDumper << ", " << anAttrToObject << ", " << anAttrToOffset << ", " << anAttrFromObject << ", " << anAttrFromOffset;
+ }
+
+ AttributeSelectionListPtr anAttrBoolObjects = aBase->selectionList(FeaturesPlugin_CompositeBoolean::OBJECTS_ID());
+ theDumper << ", " << anAttrBoolObjects << ")" << std::endl;
+
+ if(anAttrSketch->isInitialized()) {
+ theDumper << aBase << ".setNestedSketch(" << anAttrSketch << ")" << std::endl;
+ }
}
+//==================================================================================================
+void FeaturesAPI_ExtrusionBoolean::execIfBaseNotEmpty()
+{
+ if(mybaseObjects->size() > 0) {
+ execute();
+ }
+}
+
+
//==================================================================================================
FeaturesAPI_ExtrusionCut::FeaturesAPI_ExtrusionCut(const std::shared_ptr<ModelAPI_Feature>& theFeature)
: FeaturesAPI_ExtrusionBoolean(theFeature)
{
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theSize, mytoSize);
fillAttribute(ModelHighAPI_Double(), myfromSize);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theDirection, mydirection);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theSize, mytoSize);
fillAttribute(ModelHighAPI_Double(), myfromSize);
setBooleanObjects(theBooleanObjects);
{
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theToSize, mytoSize);
fillAttribute(theFromSize, myfromSize);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theDirection, mydirection);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theToSize, mytoSize);
fillAttribute(theFromSize, myfromSize);
setBooleanObjects(theBooleanObjects);
{
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_PLANES(), mycreationMethod);
fillAttribute(theToObject, mytoObject);
fillAttribute(theToOffset, mytoOffset);
fillAttribute(theFromObject, myfromObject);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theDirection, mydirection);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_PLANES(), mycreationMethod);
fillAttribute(theToObject, mytoObject);
fillAttribute(theToOffset, mytoOffset);
fillAttribute(theFromObject, myfromObject);
{
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theSize, mytoSize);
fillAttribute(ModelHighAPI_Double(), myfromSize);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theDirection, mydirection);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theSize, mytoSize);
fillAttribute(ModelHighAPI_Double(), myfromSize);
setBooleanObjects(theBooleanObjects);
{
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theToSize, mytoSize);
fillAttribute(theFromSize, myfromSize);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theDirection, mydirection);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_SIZES(), mycreationMethod);
fillAttribute(theToSize, mytoSize);
fillAttribute(theFromSize, myfromSize);
setBooleanObjects(theBooleanObjects);
{
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_PLANES(), mycreationMethod);
fillAttribute(theToObject, mytoObject);
fillAttribute(theToOffset, mytoOffset);
fillAttribute(theFromObject, myfromObject);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theDirection, mydirection);
+ fillAttribute(FeaturesPlugin_Extrusion::CREATION_METHOD_BY_PLANES(), mycreationMethod);
fillAttribute(theToObject, mytoObject);
fillAttribute(theToOffset, mytoOffset);
fillAttribute(theFromObject, myfromObject);
#include "FeaturesAPI.h"
-#include <FeaturesPlugin_CompositeBoolean.h>
#include <FeaturesPlugin_ExtrusionCut.h>
#include <FeaturesPlugin_ExtrusionFuse.h>
#include <ModelHighAPI_Macro.h>
class ModelHighAPI_Double;
+class ModelHighAPI_Reference;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_ExtrusionBoolean
virtual ~FeaturesAPI_ExtrusionBoolean();
INTERFACE_11("",
- sketchLauncher, FeaturesPlugin_Extrusion::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */,
+ sketch, FeaturesPlugin_Extrusion::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */,
baseObjects, FeaturesPlugin_Extrusion::BASE_OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Base objects */,
direction, FeaturesPlugin_Extrusion::DIRECTION_OBJECT_ID(), ModelAPI_AttributeSelection, /** Direction */,
creationMethod, FeaturesPlugin_Extrusion::CREATION_METHOD(), ModelAPI_AttributeString, /** Creation method */,
fromOffset, FeaturesPlugin_Extrusion::FROM_OFFSET_ID(), ModelAPI_AttributeDouble, /** From offset */,
booleanObjects, FeaturesPlugin_CompositeBoolean::OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Boolean objects */)
+ /// Modify base attribute of the feature.
+ FEATURESAPI_EXPORT
+ void setNestedSketch(const ModelHighAPI_Reference& theSketch);
+
/// Modify base attribute of the feature.
FEATURESAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
FEATURESAPI_EXPORT
void setBooleanObjects(const std::list<ModelHighAPI_Selection>& theBooleanObjects);
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
protected:
/// Constructor without values.
FEATURESAPI_EXPORT
explicit FeaturesAPI_ExtrusionBoolean(const std::shared_ptr<ModelAPI_Feature>& theFeature);
+
+private:
+ void execIfBaseNotEmpty();
};
class FeaturesAPI_ExtrusionCut: public FeaturesAPI_ExtrusionBoolean
{
public:
- FEATURESAPI_EXPORT
- virtual std::string getID() {
- return FeaturesPlugin_ExtrusionCut::ID();
- }
+
+ static std::string ID() { return FeaturesPlugin_ExtrusionCut::ID(); }
+ virtual std::string getID() { return ID(); }
+
+ //FEATURESAPI_EXPORT
+ //virtual std::string getID() {
+ // return FeaturesPlugin_ExtrusionCut::ID();
+ //}
/// Constructor without values.
FEATURESAPI_EXPORT
class FeaturesAPI_ExtrusionFuse: public FeaturesAPI_ExtrusionBoolean
{
public:
- FEATURESAPI_EXPORT
- virtual std::string getID() {
- return FeaturesPlugin_ExtrusionFuse::ID();
- }
+ static std::string ID() { return FeaturesPlugin_ExtrusionFuse::ID(); }
+ virtual std::string getID() { return ID(); }
/// Constructor without values.
FEATURESAPI_EXPORT
#include "FeaturesAPI_Group.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Integer.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
execute();
}
+//==================================================================================================
+void FeaturesAPI_Group::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrList = aBase->selectionList(FeaturesPlugin_Group::LIST_ID());
+
+ theDumper << aBase << " = model.addGroup(" << aDocName << ", " << anAttrList << ")" << std::endl;
+}
+
//==================================================================================================
GroupPtr addGroup(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theGroupList)
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Group
/// Set main objects.
FEATURESAPI_EXPORT
void setGroupList(const std::list<ModelHighAPI_Selection>& theGroupList);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Group object.
#include "FeaturesAPI_Intersection.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_Intersection::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Intersection::OBJECT_LIST_ID());
+ AttributeSelectionListPtr anAttrTools = aBase->selectionList(FeaturesPlugin_Intersection::TOOL_LIST_ID());
+
+ theDumper << aBase << " = model.addIntersection(" << aDocName << ", "
+ << anAttrObjects << ", " << anAttrTools << ")" << std::endl;
+}
+
//==================================================================================================
IntersectionPtr addIntersection(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theObjects,
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Intersection
/// Modify tools attribute of the feature.
FEATURESAPI_EXPORT
void setTools(const std::list<ModelHighAPI_Selection>& theTools);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Intersection object.
#include "FeaturesAPI_Partition.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_Partition::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Partition::BASE_OBJECTS_ID());
+
+ theDumper << aBase << " = model.addPartition(" << aDocName << ", " << anAttrObjects << ")" << std::endl;
+}
+
//==================================================================================================
PartitionPtr addPartition(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theBaseObjects)
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Partition
/// Modify base attribute of the feature.
FEATURESAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Partition object.
#include "FeaturesAPI_Pipe.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_Pipe::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Pipe::BASE_OBJECTS_ID());
+ AttributeSelectionPtr anAttrPath = aBase->selection(FeaturesPlugin_Pipe::PATH_OBJECT_ID());
+
+ theDumper << aBase << " = model.addPipe(" << aDocName << ", "
+ << anAttrObjects << ", " << anAttrPath;
+
+ std::string aCreationMethod = aBase->string(FeaturesPlugin_Pipe::CREATION_METHOD())->value();
+
+ if(aCreationMethod == FeaturesPlugin_Pipe::CREATION_METHOD_SIMPLE()) {
+ // Do nothing;
+ } else if(aCreationMethod == FeaturesPlugin_Pipe::CREATION_METHOD_BINORMAL()) {
+ AttributeSelectionPtr anAttrBiNormal = aBase->selection(FeaturesPlugin_Pipe::BINORMAL_ID());
+
+ theDumper << ", " << anAttrBiNormal;
+ } else if(aCreationMethod == FeaturesPlugin_Pipe::CREATION_METHOD_LOCATIONS()) {
+ AttributeSelectionListPtr anAttrLocations = aBase->selectionList(FeaturesPlugin_Pipe::LOCATIONS_ID());
+
+ theDumper << ", " << anAttrLocations;
+ }
+
+ theDumper << ")" << std::endl;
+}
+
//==================================================================================================
PipePtr addPipe(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theBaseObjects,
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Pipe
void setByBasePathLocations(const std::list<ModelHighAPI_Selection>& theBaseObjects,
const ModelHighAPI_Selection& thePath,
const std::list<ModelHighAPI_Selection>& theLocations);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Pipe object.
#include "FeaturesAPI_Placement.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_Placement::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Placement::OBJECTS_LIST_ID());
+ AttributeSelectionPtr anAttrStartShape = aBase->selection(FeaturesPlugin_Placement::START_SHAPE_ID());
+ AttributeSelectionPtr anAttrEndShape = aBase->selection(FeaturesPlugin_Placement::END_SHAPE_ID());
+ AttributeBooleanPtr anAttrReverse = aBase->boolean(FeaturesPlugin_Placement::REVERSE_ID());
+ AttributeBooleanPtr anAttrCentering = aBase->boolean(FeaturesPlugin_Placement::CENTERING_ID());
+
+ theDumper << aBase << " = model.addPlacement(" << aDocName << ", "
+ << anAttrObjects << ", " << anAttrStartShape << ", " << anAttrEndShape << ", "
+ << anAttrReverse << ", " << anAttrCentering << ")" << std::endl;
+}
+
//==================================================================================================
PlacementPtr addPlacement(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theObjects,
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Placement
/// Set centering flag.
FEATURESAPI_EXPORT
void setCentering(const bool theCentering);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Placement object.
#include "FeaturesAPI_Recover.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Reference.h>
#include <ModelHighAPI_Tools.h>
+//=================================================================================================
FeaturesAPI_Recover::FeaturesAPI_Recover(const std::shared_ptr<ModelAPI_Feature>& theFeature)
: ModelHighAPI_Interface(theFeature)
{
initialize();
}
+//=================================================================================================
FeaturesAPI_Recover::FeaturesAPI_Recover(const std::shared_ptr<ModelAPI_Feature>& theFeature,
const ModelHighAPI_Reference& theBaseFeature,
const std::list<ModelHighAPI_Selection>& theRecoveredList, const bool thePersistent)
}
}
+//=================================================================================================
FeaturesAPI_Recover::~FeaturesAPI_Recover()
{}
+//=================================================================================================
void FeaturesAPI_Recover::setBaseFeature(const ModelHighAPI_Reference& theBaseFeature)
{
fillAttribute(theBaseFeature, mybaseFeature);
// do not need to execute because on attribute changed it does everything anyway
}
+//=================================================================================================
void FeaturesAPI_Recover::setRecoveredList(const std::list<ModelHighAPI_Selection>& theRecoverList)
{
fillAttribute(theRecoverList, myrecoveredList);
// do not need to execute because on attribute changed it does everything anyway
}
+//=================================================================================================
void FeaturesAPI_Recover::setIsPersistent(bool thePersistent)
{
fillAttribute(thePersistent, myisPersistent);
// do not need to execute because on attribute changed it does everything anyway
}
+//==================================================================================================
+void FeaturesAPI_Recover::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeReferencePtr anAttrBaseFeature = aBase->reference(FeaturesPlugin_Recover::BASE_FEATURE());
+ AttributeRefListPtr anAttrRecoveredEntities = aBase->reflist(FeaturesPlugin_Recover::RECOVERED_ENTITIES());
+ AttributeBooleanPtr anAttrPersistent = aBase->boolean(FeaturesPlugin_Recover::PERSISTENT());
+
+ FeaturePtr aFeature = ModelAPI_Feature::feature(anAttrBaseFeature->value());
+
+ theDumper << aBase << " = model.addRecover(" << aDocName << ", "
+ << aFeature << ", " << anAttrRecoveredEntities << ", "
+ << anAttrPersistent << ")" << std::endl;
+}
+
+//=================================================================================================
RecoverPtr addRecover(const std::shared_ptr<ModelAPI_Document>& thePart,
const ModelHighAPI_Reference& theBaseFeature,
const std::list<ModelHighAPI_Selection>& theRecoveredList, const bool thePersistent)
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Reference;
/// \class FeaturesAPI_Recover
FEATURESAPI_EXPORT
void setIsPersistent(bool thePersistent);
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Recover object.
#include "FeaturesAPI_RemoveSubShapes.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_RemoveSubShapes::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionPtr anAttrBaseShape = aBase->selection(FeaturesPlugin_RemoveSubShapes::BASE_SHAPE_ID());
+ AttributeSelectionListPtr anAttrSubShapes = aBase->selectionList(FeaturesPlugin_RemoveSubShapes::SUBSHAPES_ID());
+
+ theDumper << aBase << " = model.addRemoveSubShapes(" << aDocName << ", " << anAttrBaseShape << ")" << std::endl;
+ theDumper << aBase << ".setSubShapesToKeep(" << anAttrSubShapes << ")" << std::endl;
+}
+
//==================================================================================================
RemoveSubShapesPtr addRemoveSubShapes(const std::shared_ptr<ModelAPI_Document>& thePart,
const ModelHighAPI_Selection& theBase)
#include <ModelHighAPI_Interface.h>
#include <ModelHighAPI_Macro.h>
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_RemoveSubShapes
/// Modify tools attribute of the feature.
FEATURESAPI_EXPORT
void setSubShapesToKeep(const std::list<ModelHighAPI_Selection>& theSubShapes);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on RemoveSubShapes object.
#include "FeaturesAPI_Revolution.h"
#include <ModelHighAPI_Double.h>
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Reference.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
}
+//==================================================================================================
+void FeaturesAPI_Revolution::setNestedSketch(const ModelHighAPI_Reference& theSketch)
+{
+ mysketch->setValue(theSketch.feature());
+ mybaseObjects->clear();
+ mybaseObjects->append(theSketch.feature()->firstResult(), GeomShapePtr());
+
+ execIfBaseNotEmpty();
+}
+
//==================================================================================================
void FeaturesAPI_Revolution::setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects)
{
+ mysketch->setValue(ObjectPtr());
+ mybaseObjects->clear();
fillAttribute(theBaseObjects, mybaseObjects);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
{
fillAttribute(theAxis, myaxis);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theToAngle, mytoAngle);
fillAttribute(theFromAngle, myfromAngle);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theAngle, mytoAngle);
fillAttribute(ModelHighAPI_Double(), myfromAngle);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theFromObject, myfromObject);
fillAttribute(theFromOffset, myfromOffset);
- execute();
+ execIfBaseNotEmpty();
+}
+
+//==================================================================================================
+void FeaturesAPI_Revolution::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeReferencePtr anAttrSketch = aBase->reference(FeaturesPlugin_Revolution::SKETCH_ID());
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Revolution::BASE_OBJECTS_ID());
+ AttributeSelectionPtr anAttrAxis = aBase->selection(FeaturesPlugin_Revolution::AXIS_OBJECT_ID());
+
+ theDumper << aBase << " = model.addRevolution(" << aDocName << ", ";
+ anAttrSketch->isInitialized() ? theDumper << "[]" : theDumper << anAttrObjects;
+ theDumper << ", " << anAttrAxis;
+
+ std::string aCreationMethod = aBase->string(FeaturesPlugin_Revolution::CREATION_METHOD())->value();
+
+ if(aCreationMethod == FeaturesPlugin_Revolution::CREATION_METHOD_BY_ANGLES()) {
+ AttributeDoublePtr anAttrToAngle = aBase->real(FeaturesPlugin_Revolution::TO_ANGLE_ID());
+ AttributeDoublePtr anAttrFromAngle = aBase->real(FeaturesPlugin_Revolution::FROM_ANGLE_ID());
+
+ theDumper << ", " << anAttrToAngle << ", " << anAttrFromAngle;
+ } else if(aCreationMethod == FeaturesPlugin_Revolution::CREATION_METHOD_BY_PLANES()) {
+ AttributeSelectionPtr anAttrToObject = aBase->selection(FeaturesPlugin_Revolution::TO_OBJECT_ID());
+ AttributeDoublePtr anAttrToOffset = aBase->real(FeaturesPlugin_Revolution::TO_OFFSET_ID());
+ AttributeSelectionPtr anAttrFromObject = aBase->selection(FeaturesPlugin_Revolution::FROM_OBJECT_ID());
+ AttributeDoublePtr anAttrFromOffset = aBase->real(FeaturesPlugin_Revolution::FROM_OFFSET_ID());
+
+ theDumper << ", " << anAttrToObject << ", " << anAttrToOffset << ", " << anAttrFromObject << ", " << anAttrFromOffset;
+ }
+
+ theDumper << ")" << std::endl;
+
+ if(anAttrSketch->isInitialized()) {
+ theDumper << aBase << ".setNestedSketch(" << anAttrSketch << ")" << std::endl;
+ }
+}
+
+//==================================================================================================
+void FeaturesAPI_Revolution::execIfBaseNotEmpty()
+{
+ if(mybaseObjects->size() > 0) {
+ execute();
+ }
}
//==================================================================================================
#include <ModelHighAPI_Macro.h>
class ModelHighAPI_Double;
+class ModelHighAPI_Reference;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Revolution
virtual ~FeaturesAPI_Revolution();
INTERFACE_10(FeaturesPlugin_Revolution::ID(),
+ sketch, FeaturesPlugin_Revolution::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */,
baseObjects, FeaturesPlugin_Revolution::BASE_OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Base objects */,
axis, FeaturesPlugin_Revolution::AXIS_OBJECT_ID(), ModelAPI_AttributeSelection, /** Axis */,
creationMethod, FeaturesPlugin_Revolution::CREATION_METHOD(), ModelAPI_AttributeString, /** Creation method */,
toObject, FeaturesPlugin_Revolution::TO_OBJECT_ID(), ModelAPI_AttributeSelection, /** To object */,
toOffset, FeaturesPlugin_Revolution::TO_OFFSET_ID(), ModelAPI_AttributeDouble, /** To offset */,
fromObject, FeaturesPlugin_Revolution::FROM_OBJECT_ID(), ModelAPI_AttributeSelection, /** From object */,
- fromOffset, FeaturesPlugin_Revolution::FROM_OFFSET_ID(), ModelAPI_AttributeDouble, /** From offset */,
- sketchLauncher, FeaturesPlugin_Revolution::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */)
+ fromOffset, FeaturesPlugin_Revolution::FROM_OFFSET_ID(), ModelAPI_AttributeDouble, /** From offset */)
+
+ /// Modify base attribute of the feature.
+ FEATURESAPI_EXPORT
+ void setNestedSketch(const ModelHighAPI_Reference& theSketch);
/// Modify base attribute of the feature.
FEATURESAPI_EXPORT
const ModelHighAPI_Double& theToOffset,
const ModelHighAPI_Selection& theFromObject,
const ModelHighAPI_Double& theFromOffset);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
+private:
+ void execIfBaseNotEmpty();
};
/// Pointer on Revolution object.
#include "FeaturesAPI_RevolutionBoolean.h"
#include <ModelHighAPI_Double.h>
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Reference.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
{
}
+//==================================================================================================
+void FeaturesAPI_RevolutionBoolean::setNestedSketch(const ModelHighAPI_Reference& theSketch)
+{
+ mysketch->setValue(theSketch.feature());
+ mybaseObjects->clear();
+ mybaseObjects->append(theSketch.feature()->firstResult(), GeomShapePtr());
+
+ execIfBaseNotEmpty();
+}
+
//==================================================================================================
void FeaturesAPI_RevolutionBoolean::setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects)
{
+ mysketch->setValue(ObjectPtr());
+ mybaseObjects->clear();
fillAttribute(theBaseObjects, mybaseObjects);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
{
fillAttribute(theAxis, myaxis);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theToAngle, mytoAngle);
fillAttribute(theFromAngle, myfromAngle);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theAngle, mytoAngle);
fillAttribute(ModelHighAPI_Double(), myfromAngle);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
fillAttribute(theFromObject, myfromObject);
fillAttribute(theFromOffset, myfromOffset);
- execute();
+ execIfBaseNotEmpty();
}
//==================================================================================================
{
fillAttribute(theBooleanObjects, mybooleanObjects);
- execute();
+ execIfBaseNotEmpty();
+}
+
+//==================================================================================================
+void FeaturesAPI_RevolutionBoolean::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeReferencePtr anAttrSketch = aBase->reference(FeaturesPlugin_Revolution::SKETCH_ID());
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Revolution::BASE_OBJECTS_ID());
+ AttributeSelectionPtr anAttrAxis = aBase->selection(FeaturesPlugin_Revolution::AXIS_OBJECT_ID());
+
+ theDumper << aBase << " = model.addRevolution";
+ if(aBase->getKind() == FeaturesPlugin_RevolutionCut::ID()) {
+ theDumper << "Cut";
+ } else if(aBase->getKind() == FeaturesPlugin_RevolutionFuse::ID()) {
+ theDumper << "Fuse";
+ }
+ theDumper << "(" << aDocName << ", ";
+ anAttrSketch->isInitialized() ? theDumper << "[]" : theDumper << anAttrObjects;
+ theDumper << ", " << anAttrAxis;
+
+ std::string aCreationMethod = aBase->string(FeaturesPlugin_Revolution::CREATION_METHOD())->value();
+
+ if(aCreationMethod == FeaturesPlugin_Revolution::CREATION_METHOD_BY_ANGLES()) {
+ AttributeDoublePtr anAttrToAngle = aBase->real(FeaturesPlugin_Revolution::TO_ANGLE_ID());
+ AttributeDoublePtr anAttrFromAngle = aBase->real(FeaturesPlugin_Revolution::FROM_ANGLE_ID());
+
+ theDumper << ", " << anAttrToAngle << ", " << anAttrFromAngle;
+ } else if(aCreationMethod == FeaturesPlugin_Revolution::CREATION_METHOD_BY_PLANES()) {
+ AttributeSelectionPtr anAttrToObject = aBase->selection(FeaturesPlugin_Revolution::TO_OBJECT_ID());
+ AttributeDoublePtr anAttrToOffset = aBase->real(FeaturesPlugin_Revolution::TO_OFFSET_ID());
+ AttributeSelectionPtr anAttrFromObject = aBase->selection(FeaturesPlugin_Revolution::FROM_OBJECT_ID());
+ AttributeDoublePtr anAttrFromOffset = aBase->real(FeaturesPlugin_Revolution::FROM_OFFSET_ID());
+
+ theDumper << ", " << anAttrToObject << ", " << anAttrToOffset << ", " << anAttrFromObject << ", " << anAttrFromOffset;
+ }
+
+ AttributeSelectionListPtr anAttrBoolObjects = aBase->selectionList(FeaturesPlugin_CompositeBoolean::OBJECTS_ID());
+ theDumper << ", " << anAttrBoolObjects << ")" << std::endl;
+
+ if(anAttrSketch->isInitialized()) {
+ theDumper << aBase << ".setNestedSketch(" << anAttrSketch << ")" << std::endl;
+ }
+}
+
+//==================================================================================================
+void FeaturesAPI_RevolutionBoolean::execIfBaseNotEmpty()
+{
+ if(mybaseObjects->size() > 0) {
+ execute();
+ }
}
//==================================================================================================
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theAxis, myaxis);
+ fillAttribute(FeaturesPlugin_Revolution::CREATION_METHOD_BY_ANGLES(), mycreationMethod);
fillAttribute(theSize, mytoAngle);
fillAttribute(ModelHighAPI_Double(), myfromAngle);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theAxis, myaxis);
+ fillAttribute(FeaturesPlugin_Revolution::CREATION_METHOD_BY_ANGLES(), mycreationMethod);
fillAttribute(theToAngle, mytoAngle);
fillAttribute(theFromAngle, myfromAngle);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theAxis, myaxis);
+ fillAttribute(FeaturesPlugin_Revolution::CREATION_METHOD_BY_PLANES(), mycreationMethod);
fillAttribute(theToObject, mytoObject);
fillAttribute(theToOffset, mytoOffset);
fillAttribute(theFromObject, myfromObject);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theAxis, myaxis);
+ fillAttribute(FeaturesPlugin_Revolution::CREATION_METHOD_BY_ANGLES(), mycreationMethod);
fillAttribute(theSize, mytoAngle);
fillAttribute(ModelHighAPI_Double(), myfromAngle);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theAxis, myaxis);
+ fillAttribute(FeaturesPlugin_Revolution::CREATION_METHOD_BY_ANGLES(), mycreationMethod);
fillAttribute(theToAngle, mytoAngle);
fillAttribute(theFromAngle, myfromAngle);
setBooleanObjects(theBooleanObjects);
if(initialize()) {
fillAttribute(theBaseObjects, mybaseObjects);
fillAttribute(theAxis, myaxis);
+ fillAttribute(FeaturesPlugin_Revolution::CREATION_METHOD_BY_PLANES(), mycreationMethod);
fillAttribute(theToObject, mytoObject);
fillAttribute(theToOffset, mytoOffset);
fillAttribute(theFromObject, myfromObject);
#include <ModelHighAPI_Macro.h>
class ModelHighAPI_Double;
+class ModelHighAPI_Dumper;
+class ModelHighAPI_Reference;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_RevolutionBoolean
virtual ~FeaturesAPI_RevolutionBoolean();
INTERFACE_11("",
- sketchLauncher, FeaturesPlugin_Revolution::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */,
+ sketch, FeaturesPlugin_Revolution::SKETCH_ID(), ModelAPI_AttributeReference, /** Sketch launcher */,
baseObjects, FeaturesPlugin_Revolution::BASE_OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Base objects */,
axis, FeaturesPlugin_Revolution::AXIS_OBJECT_ID(), ModelAPI_AttributeSelection, /** Axis */,
creationMethod, FeaturesPlugin_Revolution::CREATION_METHOD(), ModelAPI_AttributeString, /** Creation method */,
fromOffset, FeaturesPlugin_Revolution::FROM_OFFSET_ID(), ModelAPI_AttributeDouble, /** From offset */,
booleanObjects, FeaturesPlugin_CompositeBoolean::OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Boolean objects */)
+ /// Modify base attribute of the feature.
+ FEATURESAPI_EXPORT
+ void setNestedSketch(const ModelHighAPI_Reference& theSketch);
+
/// Modify base attribute of the feature.
FEATURESAPI_EXPORT
void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
FEATURESAPI_EXPORT
void setBooleanObjects(const std::list<ModelHighAPI_Selection>& theBooleanObjects);
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
protected:
/// Constructor without values.
FEATURESAPI_EXPORT
explicit FeaturesAPI_RevolutionBoolean(const std::shared_ptr<ModelAPI_Feature>& theFeature);
+
+private:
+ void execIfBaseNotEmpty();
};
class FeaturesAPI_RevolutionCut: public FeaturesAPI_RevolutionBoolean
{
public:
- FEATURESAPI_EXPORT
- virtual std::string getID() {
- return FeaturesPlugin_RevolutionCut::ID();
- }
+
+ static std::string ID() { return FeaturesPlugin_RevolutionCut::ID(); }
+ virtual std::string getID() { return ID(); }
/// Constructor without values.
FEATURESAPI_EXPORT
class FeaturesAPI_RevolutionFuse: public FeaturesAPI_RevolutionBoolean
{
public:
- FEATURESAPI_EXPORT
- virtual std::string getID() {
- return FeaturesPlugin_RevolutionFuse::ID();
- }
+
+ static std::string ID() { return FeaturesPlugin_RevolutionFuse::ID(); }
+ virtual std::string getID() { return ID(); }
/// Constructor without values.
FEATURESAPI_EXPORT
#include "FeaturesAPI_Rotation.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_Rotation::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Rotation::OBJECTS_LIST_ID());
+ AttributeSelectionPtr anAttrAxis = aBase->selection(FeaturesPlugin_Rotation::AXIS_OBJECT_ID());
+ AttributeDoublePtr anAttrAngle = aBase->real(FeaturesPlugin_Rotation::ANGLE_ID());
+
+ theDumper << aBase << " = model.addRotation(" << aDocName << ", "
+ << anAttrObjects << ", " << anAttrAxis << ", " << anAttrAngle << ")" << std::endl;
+}
+
//==================================================================================================
RotationPtr addRotation(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theMainObjects,
const ModelHighAPI_Selection& theAxisObject,
- const ModelHighAPI_Double& theDistance)
+ const ModelHighAPI_Double& theAngle)
{
std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(FeaturesAPI_Rotation::ID());
- return RotationPtr(new FeaturesAPI_Rotation(aFeature, theMainObjects, theAxisObject, theDistance));
+ return RotationPtr(new FeaturesAPI_Rotation(aFeature, theMainObjects, theAxisObject, theAngle));
}
#include <ModelHighAPI_Macro.h>
class ModelHighAPI_Double;
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Rotation
/// Set angle.
FEATURESAPI_EXPORT
void setAngle(const ModelHighAPI_Double& theAngle);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Rotation object.
RotationPtr addRotation(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theMainObjects,
const ModelHighAPI_Selection& theAxisObject,
- const ModelHighAPI_Double& theDistance);
+ const ModelHighAPI_Double& theAngle);
#endif // FeaturesAPI_Rotation_H_
#include "FeaturesAPI_Translation.h"
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//==================================================================================================
execute();
}
+//==================================================================================================
+void FeaturesAPI_Translation::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Translation::OBJECTS_LIST_ID());
+ AttributeSelectionPtr anAttrAxis = aBase->selection(FeaturesPlugin_Translation::AXIS_OBJECT_ID());
+ AttributeDoublePtr anAttrDistance = aBase->real(FeaturesPlugin_Translation::DISTANCE_ID());
+
+ theDumper << aBase << " = model.addTranslation(" << aDocName << ", "
+ << anAttrObjects << ", " << anAttrAxis << ", " << anAttrDistance << ")" << std::endl;
+}
+
//==================================================================================================
TranslationPtr addTranslation(const std::shared_ptr<ModelAPI_Document>& thePart,
const std::list<ModelHighAPI_Selection>& theMainObjects,
#include <ModelHighAPI_Macro.h>
class ModelHighAPI_Double;
+class ModelHighAPI_Dumper;
class ModelHighAPI_Selection;
/// \class FeaturesAPI_Translation
/// Set distance.
FEATURESAPI_EXPORT
void setDistance(const ModelHighAPI_Double& theDistance);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Translation object.
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D -->
+
+// File: FeaturesAPI_Union.cpp
+// Created: 09 June 2016
+// Author: Dmitry Bobylev
+
+#include "FeaturesAPI_Union.h"
+
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Tools.h>
+
+//==================================================================================================
+FeaturesAPI_Union::FeaturesAPI_Union(const std::shared_ptr<ModelAPI_Feature>& theFeature)
+: ModelHighAPI_Interface(theFeature)
+{
+ initialize();
+}
+
+//==================================================================================================
+FeaturesAPI_Union::FeaturesAPI_Union(const std::shared_ptr<ModelAPI_Feature>& theFeature,
+ const std::list<ModelHighAPI_Selection>& theBaseObjects)
+: ModelHighAPI_Interface(theFeature)
+{
+ if(initialize()) {
+ setBase(theBaseObjects);
+ }
+}
+
+//==================================================================================================
+FeaturesAPI_Union::~FeaturesAPI_Union()
+{
+
+}
+
+//==================================================================================================
+void FeaturesAPI_Union::setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects)
+{
+ fillAttribute(theBaseObjects, mybaseObjects);
+
+ execute();
+}
+
+//==================================================================================================
+void FeaturesAPI_Union::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionListPtr anAttrObjects = aBase->selectionList(FeaturesPlugin_Union::BASE_OBJECTS_ID());
+
+ theDumper << aBase << " = model.addUnion(" << aDocName << ", " << anAttrObjects << ")" << std::endl;
+}
+
+//==================================================================================================
+UnionPtr addUnion(const std::shared_ptr<ModelAPI_Document>& thePart,
+ const std::list<ModelHighAPI_Selection>& theBaseObjects)
+{
+ std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(FeaturesAPI_Union::ID());
+ return UnionPtr(new FeaturesAPI_Union(aFeature, theBaseObjects));
+}
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D -->
+
+// File: FeaturesAPI_Union.h
+// Created: 09 June 2016
+// Author: Dmitry Bobylev
+
+#ifndef FeaturesAPI_Union_H_
+#define FeaturesAPI_Union_H_
+
+#include "FeaturesAPI.h"
+
+#include <FeaturesPlugin_Union.h>
+
+#include <ModelHighAPI_Interface.h>
+#include <ModelHighAPI_Macro.h>
+
+class ModelHighAPI_Dumper;
+class ModelHighAPI_Selection;
+
+/// \class FeaturesAPI_Union
+/// \ingroup CPPHighAPI
+/// \brief Interface for Union feature.
+class FeaturesAPI_Union: public ModelHighAPI_Interface
+{
+public:
+ /// Constructor without values.
+ FEATURESAPI_EXPORT
+ explicit FeaturesAPI_Union(const std::shared_ptr<ModelAPI_Feature>& theFeature);
+
+ /// Constructor with values.
+ FEATURESAPI_EXPORT
+ explicit FeaturesAPI_Union(const std::shared_ptr<ModelAPI_Feature>& theFeature,
+ const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Destructor.
+ FEATURESAPI_EXPORT
+ virtual ~FeaturesAPI_Union();
+
+ INTERFACE_1(FeaturesPlugin_Union::ID(),
+ baseObjects, FeaturesPlugin_Union::BASE_OBJECTS_ID(), ModelAPI_AttributeSelectionList, /** Base objects */)
+
+ /// Modify base attribute of the feature.
+ FEATURESAPI_EXPORT
+ void setBase(const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+ /// Dump wrapped feature
+ FEATURESAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+};
+
+/// Pointer on Union object.
+typedef std::shared_ptr<FeaturesAPI_Union> UnionPtr;
+
+/// \ingroup CPPHighAPI
+/// \brief Create Union feature.
+FEATURESAPI_EXPORT
+UnionPtr addUnion(const std::shared_ptr<ModelAPI_Document>& thePart,
+ const std::list<ModelHighAPI_Selection>& theBaseObjects);
+
+#endif // FeaturesAPI_Union_H_
#include "FeaturesAPI_RevolutionBoolean.h"
#include "FeaturesAPI_Rotation.h"
#include "FeaturesAPI_Translation.h"
+ #include "FeaturesAPI_Union.h"
#endif // FeaturesAPI_swig_H_
AttributeSelectionListPtr aSelection =
std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(data()->addAttribute(
FeaturesPlugin_Boolean::OBJECT_LIST_ID(), ModelAPI_AttributeSelectionList::typeId()));
- // extrusion works with faces always
- aSelection->setSelectionType("SOLID");
aSelection = std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(data()->addAttribute(
FeaturesPlugin_Boolean::TOOL_LIST_ID(), ModelAPI_AttributeSelectionList::typeId()));
- // extrusion works with faces always
- aSelection->setSelectionType("SOLID");
ModelAPI_Session::get()->validators()->registerNotObligatory(getKind(), OBJECT_LIST_ID());
ModelAPI_Session::get()->validators()->registerNotObligatory(getKind(), TOOL_LIST_ID());
AttributeSelectionListPtr aSelection =
std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(data()->addAttribute(
OBJECTS_LIST_ID(), ModelAPI_AttributeSelectionList::typeId()));
- // extrusion works with faces always
- aSelection->setSelectionType("SOLID");
data()->addAttribute(START_SHAPE_ID(), ModelAPI_AttributeSelection::typeId());
data()->addAttribute(END_SHAPE_ID(), ModelAPI_AttributeSelection::typeId());
AttributeSelectionListPtr aSelection =
std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(data()->addAttribute(
FeaturesPlugin_Rotation::OBJECTS_LIST_ID(), ModelAPI_AttributeSelectionList::typeId()));
- // revolution works with faces always
- aSelection->setSelectionType("SOLID");
data()->addAttribute(FeaturesPlugin_Rotation::AXIS_OBJECT_ID(), ModelAPI_AttributeSelection::typeId());
data()->addAttribute(FeaturesPlugin_Rotation::ANGLE_ID(), ModelAPI_AttributeDouble::typeId());
AttributeSelectionListPtr aSelection =
std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(data()->addAttribute(
FeaturesPlugin_Translation::OBJECTS_LIST_ID(), ModelAPI_AttributeSelectionList::typeId()));
- // revolution works with faces always
- aSelection->setSelectionType("SOLID");
data()->addAttribute(FeaturesPlugin_Translation::AXIS_OBJECT_ID(), ModelAPI_AttributeSelection::typeId());
data()->addAttribute(FeaturesPlugin_Translation::DISTANCE_ID(), ModelAPI_AttributeDouble::typeId());
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aBoolean = model.addFill(aDocument, [anExtrusion.result()[0]], [anExtrusion.result()[1]])
assert (len(aBoolean.result()) > 0)
aSession.finishOperation()
+
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
assert (len(anRevolutionFuseFt.results()) > 0)
aCurrentResult = modelAPI_ResultBody(anRevolutionFuseFt.firstResult())
assert (aCurrentResult is not None)
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
assert (len(anExtrusionCutFt.results()) > 0)
aCurrentResult = modelAPI_ResultBody(anExtrusionCutFt.firstResult())
assert (aCurrentResult is not None)
+
+import model
+assert(model.checkPythonDump())
assert (len(anExtrusionFuseFt.results()) > 0)
aCurrentResult = modelAPI_ResultBody(anExtrusionFuseFt.firstResult())
assert (aCurrentResult is not None)
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
assert (len(anIntersectionFt.results()) > 0)
anItersectionResult = modelAPI_ResultBody(anIntersectionFt.firstResult())
assert (anItersectionResult is not None)
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
assert (len(aPartitionFt.results()) > 0)
aPartitionResult = modelAPI_ResultBody(aPartitionFt.firstResult())
assert (aPartitionResult is not None)
+
+import model
+assert(model.checkPythonDump())
# Test results
assert (len(aPipeFeature.results()) > 0)
+
+import model
+assert(model.checkPythonDump())
assert (len(aPlacementFt.results()) > 0)
aPlacementResult = modelAPI_ResultBody(aPlacementFt.firstResult())
assert (aPlacementResult is not None)
+
+import model
+assert(model.checkPythonDump())
sk1 = model.addSketch(mypart, model.defaultPlane("XOY"))
c1 = sk1.addCircle(0, 0, 100)
+model.do()
bigcyl = model.addExtrusion(mypart, sk1.selectFace(), 100)
sk2 = model.addSketch(mypart, model.defaultPlane("XOY"))
c2 = sk2.addCircle(20, 30, 30)
+model.do()
smallcyl = model.addExtrusion(mypart, sk2.selectFace(), 150)
cut = model.addCut(mypart, bigcyl.result(), smallcyl.result())
assert(mypart.size("Bodies") == 2)
sk3 = model.addSketch(mypart, model.defaultPlane("XOY"))
c3 = sk3.addCircle(0, 0, 90)
+model.do()
big2 = model.addExtrusion(mypart, sk3.selectFace(), 110)
cut2 = model.addCut(mypart, big2.result(), smallcyl.result())
model.end()
# only two booleans
assert(mypart.size("Bodies") == 2)
+
+assert(model.checkPythonDump())
assert (len(aRemoveSubShapesFeature.results()) > 0)
anUnionResult = modelAPI_ResultCompSolid(modelAPI_ResultBody(aRemoveSubShapesFeature.firstResult()))
assert (anUnionResult.numberOfSubs() == 2)
+
+import model
+assert(model.checkPythonDump())
assert (len(aRevolFt.results()) > 0)
aRevolResult = modelAPI_ResultBody(aRevolFt.firstResult())
assert (aRevolResult is not None)
+
+import model
+assert(model.checkPythonDump())
assert (len(anRevolutionCutFt.results()) > 0)
aCurrentResult = modelAPI_ResultBody(anRevolutionCutFt.firstResult())
assert (aCurrentResult is not None)
+
+import model
+assert(model.checkPythonDump())
assert (len(anRevolutionFuseFt.results()) > 0)
aCurrentResult = modelAPI_ResultBody(anRevolutionFuseFt.firstResult())
assert (aCurrentResult is not None)
+
+import model
+assert(model.checkPythonDump())
aMoveResult = modelAPI_ResultBody(aRotateFt.firstResult())
assert (aMoveResult is not None)
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aMoveResult = modelAPI_ResultBody(aMoveFt.firstResult())
assert (aMoveResult is not None)
+import model
+assert(model.checkPythonDump())
assert (len(aUnionFeature.results()) > 0)
anUnionResult = modelAPI_ResultCompSolid(modelAPI_ResultBody(aUnionFeature.firstResult()))
assert (anUnionResult.numberOfSubs() == 0)
+
+import model
+assert(model.checkPythonDump())
if (aCenter.IsEqual(aPoint, Precision::Confusion()))
return NULL;
- gp_Dir2d aDir(theCenterX - thePointX, theCenterY - thePointY);
+ gp_Dir2d aDir(thePointX - theCenterX, thePointY - theCenterY);
return newCirc2d(theCenterX, theCenterY, aDir, aRadius);
}
switch(aShapeType) {
case COMPOUND: {
- aShapeTypeStr = "Compound";
+ aShapeTypeStr = "COMPOUND";
break;
}
case COMPSOLID: {
- aShapeTypeStr = "CompSolid";
+ aShapeTypeStr = "COMPSOLID";
break;
}
case SOLID: {
- aShapeTypeStr = "Solid";
+ aShapeTypeStr = "SOLID";
break;
}
case SHELL: {
- aShapeTypeStr = "Shell";
+ aShapeTypeStr = "SHELL";
break;
}
case FACE: {
- aShapeTypeStr = "Face";
+ aShapeTypeStr = "FACE";
break;
}
case WIRE: {
- aShapeTypeStr = "Wire";
+ aShapeTypeStr = "WIRE";
break;
}
case EDGE: {
- aShapeTypeStr = "Edge";
+ aShapeTypeStr = "EDGE";
break;
}
case VERTEX: {
- aShapeTypeStr = "Vertex";
+ aShapeTypeStr = "VERTEX";
break;
}
case SHAPE: {
- aShapeTypeStr = "Shape";
+ aShapeTypeStr = "SHAPE";
break;
}
}
void GeomData_Point2D::setText(const std::string& theX,
const std::string& theY)
{
+ if (!myIsInitialized && theX.empty() && theY.empty())
+ return; // empty strings are not good initializers
if (!myIsInitialized || textX() != theX || textY() != theY) {
myExpression[0]->setText(theX);
myExpression[1]->setText(theY);
GEOMDATAAPI_EXPORT virtual ~GeomDataAPI_Dir();
};
+//! Pointer on attribute object
+typedef std::shared_ptr<GeomDataAPI_Dir> AttributeDirPtr;
+
#endif
bool isEqual(const AttributePoint2DPtr& theLeft, const AttributePoint2DPtr& theRight)
{
- return theLeft->pnt()->distance(theRight->pnt()) < tolerance;
+ return theLeft->isInitialized() && theRight->isInitialized() &&
+ theLeft->pnt()->distance(theRight->pnt()) < tolerance;
}
bool isEqualAttributes(const AttributePtr& theLeft, const AttributePtr& theRight)
double aToSize = 0.0;
double aFromSize = 0.0;
- if(theFeature->real(*anIt)) {
+ if(theFeature->real(*anIt) && theFeature->real(*anIt)->isInitialized()) {
aToSize = theFeature->real(*anIt)->value();
}
anIt++;
- if(theFeature->real(*anIt)) {
+ if(theFeature->real(*anIt) && theFeature->real(*anIt)->isInitialized()) {
aFromSize = theFeature->real(*anIt)->value();
}
anIt++;
std::shared_ptr<GeomAPI_Shape> aFromShape;
std::shared_ptr<ModelAPI_AttributeSelection> anAttrSel = theFeature->selection(*anIt);
- if(anAttrSel) {
+ if(anAttrSel && anAttrSel->isInitialized()) {
aToShape = std::dynamic_pointer_cast<GeomAPI_Shape>(anAttrSel->value());
if(aToShape.get() == NULL && anAttrSel->context().get() != NULL) {
aToShape = anAttrSel->context()->shape();
anIt++;
std::shared_ptr<ModelAPI_AttributeDouble> anAttrDouble = theFeature->real(*anIt);
- if(anAttrDouble) {
+ if(anAttrDouble && anAttrDouble->isInitialized()) {
aToSize = anAttrDouble->value();
}
anIt++;
anAttrSel = theFeature->selection(*anIt);
- if(anAttrSel) {
+ if(anAttrSel && anAttrSel->isInitialized()) {
aFromShape = std::dynamic_pointer_cast<GeomAPI_Shape>(anAttrSel->value());
if(aFromShape.get() == NULL && anAttrSel->context().get() != NULL) {
aFromShape = anAttrSel->context()->shape();
anIt++;
anAttrDouble = theFeature->real(*anIt);
- if(anAttrDouble) {
+ if(anAttrDouble && anAttrDouble->isInitialized()) {
aFromSize = anAttrDouble->value();
}
}
}
Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
-
// the viewer update should be unblocked in order to avoid the features blinking before they are
// hidden
aMsg = std::shared_ptr<Events_Message>(
new Events_Message(Events_Loop::eventByName(EVENT_UPDATE_VIEWER_UNBLOCKED)));
Events_Loop::loop()->send(aMsg);
-
- } else if (theMessage.get()) {
- Events_InfoMessage("InitializationPlugin_Plugin",
- "InitializationPlugin_Plugin::processEvent: unhandled message caught: %1")
- .arg(theMessage->eventID().eventText()).send();
}
}
{
Standard_Boolean aValue = theValue ? Standard_True : Standard_False;
if (!myIsInitialized || myBool->Get() != aValue) {
+ if (myBool.IsNull())
+ myBool = TDataStd_Integer::Set(myLab, 0);
myBool->Set(aValue);
owner()->data()->sendAttributeUpdated(this);
}
bool Model_AttributeBoolean::value()
{
- return myBool->Get() == Standard_True ;
+ return myIsInitialized && myBool->Get() == Standard_True ;
}
Model_AttributeBoolean::Model_AttributeBoolean(TDF_Label& theLabel)
{
+ myLab = theLabel;
// check the attribute could be already presented in this doc (after load document)
myIsInitialized = theLabel.FindAttribute(TDataStd_Integer::GetID(), myBool) == Standard_True;
- if (!myIsInitialized) {
- // create attribute: not initialized by value yet, just zero
- myBool = TDataStd_Integer::Set(theLabel, 0);
- }
}
class Model_AttributeBoolean : public ModelAPI_AttributeBoolean
{
Handle_TDataStd_Integer myBool; ///< double is Real attribute
+ TDF_Label myLab; ///< if attribute is not initialized, store label here
public:
/// Defines the double value
MODEL_EXPORT virtual void setValue(bool theValue);
#include <TopoDS_Iterator.hxx>
#include <TNaming_Iterator.hxx>
#include <BRep_Builder.hxx>
+#include <ModelAPI_Session.h>
+
using namespace std;
//#define DEB_NAMING 1
#ifdef DEB_NAMING
aBuilder.Generated(theContext->shape()->impl<TopoDS_Shape>());
std::shared_ptr<Model_Document> aMyDoc =
std::dynamic_pointer_cast<Model_Document>(owner()->document());
- std::string aName = theContext->data()->name();
+ std::string aName = contextName(theContext);
+ // for selection in different document, add the document name
aMyDoc->addNamingName(aSelLab, aName);
TDataStd_Name::Set(aSelLab, aName.c_str());
} else { // for sketch the naming is needed in DS
//myIsInitialized = true;
owner()->data()->sendAttributeUpdated(this);
-
- std::string aSelName = namingName();
- if(!aSelName.empty())
- TDataStd_Name::Set(selectionLabel(), aSelName.c_str()); //set name
}
std::shared_ptr<GeomAPI_Shape> Model_AttributeSelection::value()
return myScope;
}
-/// produces theEdge orientation relatively to theContext face
-int edgeOrientation(const TopoDS_Shape& theContext, TopoDS_Edge& theEdge)
-{
- if (theContext.ShapeType() != TopAbs_FACE)
- return 0;
- TopoDS_Face aContext = TopoDS::Face(theContext);
- if (theEdge.Orientation() == TopAbs_FORWARD)
- return 1;
- if (theEdge.Orientation() == TopAbs_REVERSED)
- return -1;
- return 0; // unknown
-}
-
/// Sets the invalid flag if flag is false, or removes it if "true"
/// Returns theFlag
static bool setInvalidIfFalse(TDF_Label& theLab, const bool theFlag) {
aBuilder.Generated(aContext->shape()->impl<TopoDS_Shape>());
std::shared_ptr<Model_Document> aMyDoc =
std::dynamic_pointer_cast<Model_Document>(owner()->document());
- std::string aName = aContext->data()->name();
+ std::string aName = contextName(aContext);
aMyDoc->addNamingName(aSelLab, aName);
TDataStd_Name::Set(aSelLab, aName.c_str());
}
}
}
}
- int aBestFound = 0; // best number of found edges (not percentage: issue 1019)
- int aBestOrient = 0; // for the equal "BestFound" additional parameter is orientation
- for(int aFaceIndex = 0; aFaceIndex < aConstructionContext->facesNum(); aFaceIndex++) {
- int aFound = 0, aNotFound = 0, aSameOrientation = 0;
- TopoDS_Face aFace =
- TopoDS::Face(aConstructionContext->face(aFaceIndex)->impl<TopoDS_Shape>());
- TopExp_Explorer anEdgesExp(aFace, TopAbs_EDGE);
- TColStd_MapOfTransient alreadyProcessed; // to avoid counting edges with same curved (841)
- for(; anEdgesExp.More(); anEdgesExp.Next()) {
- TopoDS_Edge anEdge = TopoDS::Edge(anEdgesExp.Current());
- if (!anEdge.IsNull()) {
- Standard_Real aFirst, aLast;
- Handle(Geom_Curve) aCurve = BRep_Tool::Curve(anEdge, aFirst, aLast);
- if (alreadyProcessed.Contains(aCurve))
- continue;
- alreadyProcessed.Add(aCurve);
- if (allCurves.IsBound(aCurve)) {
- aFound++;
- int anOrient = allCurves.Find(aCurve);
- if (anOrient != 0) { // extra comparision score is orientation
- if (edgeOrientation(aFace, anEdge) == anOrient)
- aSameOrientation++;
- }
- } else {
- aNotFound++;
- }
- }
- }
- if (aFound + aNotFound != 0) {
- if (aFound > aBestFound ||
- (aFound == aBestFound && aSameOrientation > aBestOrient)) {
- aBestFound = aFound;
- aBestOrient = aSameOrientation;
- aNewSelected = aConstructionContext->face(aFaceIndex);
- }
- }
- }
+ aNewSelected = Model_SelectionNaming::findAppropriateFace(aContext, allCurves);
}
if (aNewSelected) { // store this new selection
if (aShapeType == TopAbs_WIRE) { // just get a wire from face to have wire
static void registerSubShape(TDF_Label theMainLabel, TopoDS_Shape theShape,
const int theID, const FeaturePtr& theContextFeature, std::shared_ptr<Model_Document> theDoc,
std::string theAdditionalName, std::map<int, int>& theOrientations,
+ std::map<int, std::string>& theSubNames, // name of sub-elements by ID to be exported instead of indexes
Handle(TDataStd_IntPackedMap) theRefs = Handle(TDataStd_IntPackedMap)(),
const int theOrientation = 0)
{
TNaming_Builder aBuilder(aLab);
aBuilder.Generated(theShape);
std::stringstream aName;
- aName<<theContextFeature->name()<<"/";
- if (!theAdditionalName.empty())
- aName<<theAdditionalName<<"/";
- if (theShape.ShapeType() == TopAbs_FACE) aName<<"Face";
- else if (theShape.ShapeType() == TopAbs_WIRE) aName<<"Wire";
- else if (theShape.ShapeType() == TopAbs_EDGE) aName<<"Edge";
- else if (theShape.ShapeType() == TopAbs_VERTEX) aName<<"Vertex";
-
- if (theRefs.IsNull()) {
- aName<<theID;
- if (theOrientation == 1)
- aName<<"f";
- else if (theOrientation == -1)
- aName<<"r";
- } else { // make a composite name from all sub-elements indexes: "1_2_3_4"
- TColStd_MapIteratorOfPackedMapOfInteger aRef(theRefs->GetMap());
- for(; aRef.More(); aRef.Next()) {
- aName<<"-"<<aRef.Key();
- if (theOrientations.find(aRef.Key()) != theOrientations.end()) {
- if (theOrientations[aRef.Key()] == 1)
- aName<<"f";
- else if (theOrientations[aRef.Key()] == -1)
- aName<<"r";
+ // add the part name if the selected object is located in other part
+ if (theDoc != theContextFeature->document()) {
+ if (theContextFeature->document() == ModelAPI_Session::get()->moduleDocument()) {
+ aName<<theContextFeature->document()->kind()<<"/";
+ } else {
+ ResultPtr aDocRes = ModelAPI_Tools::findPartResult(
+ ModelAPI_Session::get()->moduleDocument(), theContextFeature->document());
+ if (aDocRes.get()) {
+ aName<<aDocRes->data()->name()<<"/";
+ }
+ }
+ }
+ aName<<theContextFeature->name();
+ if (theShape.ShapeType() != TopAbs_COMPOUND) { // compound means the whole result for construction
+ aName<<"/";
+ if (!theAdditionalName.empty())
+ aName<<theAdditionalName<<"/";
+ if (theShape.ShapeType() == TopAbs_FACE) aName<<"Face";
+ else if (theShape.ShapeType() == TopAbs_WIRE) aName<<"Wire";
+ else if (theShape.ShapeType() == TopAbs_EDGE) aName<<"Edge";
+ else if (theShape.ShapeType() == TopAbs_VERTEX) aName<<"Vertex";
+
+ if (theRefs.IsNull()) {
+ aName<<theID;
+ if (theOrientation == 1)
+ aName<<"f";
+ else if (theOrientation == -1)
+ aName<<"r";
+ } else { // make a composite name from all sub-elements indexes: "1_2_3_4"
+ TColStd_MapIteratorOfPackedMapOfInteger aRef(theRefs->GetMap());
+ for(; aRef.More(); aRef.Next()) {
+ aName<<"-"<<theSubNames[aRef.Key()];
+ if (theOrientations.find(aRef.Key()) != theOrientations.end()) {
+ if (theOrientations[aRef.Key()] == 1)
+ aName<<"f";
+ else if (theOrientations[aRef.Key()] == -1)
+ aName<<"r";
+ }
}
}
}
// saving of context is enough: result construction contains exactly the needed shape
TNaming_Builder aBuilder(selectionLabel());
aBuilder.Generated(aSubShape);
- aMyDoc->addNamingName(selectionLabel(), theContext->data()->name());
- TDataStd_Name::Set(selectionLabel(), theContext->data()->name().c_str());
+ std::string aName = contextName(theContext);
+ aMyDoc->addNamingName(selectionLabel(), aName);
+ TDataStd_Name::Set(selectionLabel(), aName.c_str());
return;
}
std::shared_ptr<Model_Data> aData = std::dynamic_pointer_cast<Model_Data>(owner()->data());
// iterate and store the result ids of sub-elements and sub-elements to sub-labels
Handle(TDataStd_IntPackedMap) aRefs = TDataStd_IntPackedMap::Set(aLab);
std::map<int, int> anOrientations; //map from edges IDs to orientations of these edges in face
+ std::map<int, std::string> aSubNames; //map from edges IDs to names of edges
aRefs->Clear();
const int aSubNum = aComposite->numberOfSubs();
for(int a = 0; a < aSubNum; a++) {
gp_Pnt aPnt = BRep_Tool::Pnt(TopoDS::Vertex(aVertex));
if (aPnt.IsEqual(aVertexPos, Precision::Confusion())) {
aRefs->Add(aComposite->subFeatureId(a));
+ aSubNames[aComposite->subFeatureId(a)] = Model_SelectionNaming::shortName(aConstr);
}
- } else { // get first or last vertex of the edge: last is stored with negative sign
+ } else { // get first or last vertex of the edge: last is stored with additional delta
const TopoDS_Shape& anEdge = aConstr->shape()->impl<TopoDS_Shape>();
int aDelta = kSTART_VERTEX_DELTA;
for(TopExp_Explorer aVExp(anEdge, TopAbs_VERTEX); aVExp.More(); aVExp.Next()) {
gp_Pnt aPnt = BRep_Tool::Pnt(TopoDS::Vertex(aVExp.Current()));
if (aPnt.IsEqual(aVertexPos, Precision::Confusion())) {
aRefs->Add(aDelta + aComposite->subFeatureId(a));
+ aSubNames[aDelta + aComposite->subFeatureId(a)] =
+ Model_SelectionNaming::shortName(aConstr, aDelta / kSTART_VERTEX_DELTA);
break;
}
aDelta += kSTART_VERTEX_DELTA;
if (allCurves.Contains(aCurve)) {
int anID = aComposite->subFeatureId(a);
aRefs->Add(anID);
+ aSubNames[anID] = Model_SelectionNaming::shortName(aConstr);
if (aShapeType != TopAbs_EDGE) { // face needs the sub-edges on sub-labels
// add edges to sub-label to support naming for edges selection
TopExp_Explorer anEdgeExp(aSubShape, TopAbs_EDGE);
Standard_Real aFirst, aLast;
Handle(Geom_Curve) aFaceCurve = BRep_Tool::Curve(anEdge, aFirst, aLast);
if (aFaceCurve == aCurve) {
- int anOrient = edgeOrientation(aSubShape, anEdge);
+ int anOrient = Model_SelectionNaming::edgeOrientation(aSubShape, anEdge);
anOrientations[anID] = anOrient;
registerSubShape(
selectionLabel(), anEdge, anID, aContextFeature, aMyDoc, "", anOrientations,
- Handle(TDataStd_IntPackedMap)(), anOrient);
+ aSubNames, Handle(TDataStd_IntPackedMap)(), anOrient);
}
}
} else { // put vertices of the selected edge to sub-labels
std::stringstream anAdditionalName;
registerSubShape(
- selectionLabel(), aV, aTagIndex, aContextFeature, aMyDoc, "", anOrientations);
+ selectionLabel(), aV, aTagIndex, aContextFeature, aMyDoc, "", anOrientations,
+ aSubNames);
}
}
}
TNaming_Builder aBuilder(selectionLabel());
aBuilder.Generated(aSubShape);
registerSubShape(
- selectionLabel(), aSubShape, 0, aContextFeature, aMyDoc, "", anOrientations, aRefs);
+ selectionLabel(), aSubShape, 0, aContextFeature, aMyDoc, "", anOrientations, aSubNames, aRefs);
}
bool Model_AttributeSelection::selectPart(
std::string aName("");
if(!this->isInitialized())
return !theDefaultName.empty() ? theDefaultName : aName;
- Handle(TDataStd_Name) anAtt;
- if(selectionLabel().FindAttribute(TDataStd_Name::GetID(), anAtt)) {
- aName = TCollection_AsciiString(anAtt->Get()).ToCString();
- return aName;
- }
std::shared_ptr<GeomAPI_Shape> aSubSh = value();
ResultPtr aCont = context();
setValue(aContext, aSelection);
}
+std::string Model_AttributeSelection::contextName(const ResultPtr& theContext) const
+{
+ std::string aResult;
+ if (owner()->document() != theContext->document()) {
+ if (theContext->document() == ModelAPI_Session::get()->moduleDocument()) {
+ aResult = theContext->document()->kind() + "/";
+ } else {
+ ResultPtr aDocRes = ModelAPI_Tools::findPartResult(
+ ModelAPI_Session::get()->moduleDocument(), theContext->document());
+ if (aDocRes.get()) {
+ aResult = aDocRes->data()->name() + "/";
+ }
+ }
+ }
+ aResult += theContext->data()->name();
+ return aResult;
+}
/// Sets the ID of the attribute in Data (called from Data): here it is used for myRef ID setting
MODEL_EXPORT virtual void setID(const std::string theID);
+ /// Returns the name by context. Adds the part name if the context is located in other document
+ std::string contextName(const ResultPtr& theContext) const;
+
friend class Model_Data;
friend class Model_AttributeSelectionList;
};
{
TCollection_ExtendedString aValue(theValue.c_str());
if (!myIsInitialized || myString->Get() != aValue) {
+ if (myString.IsNull())
+ myString = TDataStd_Name::Set(myLab, TCollection_ExtendedString());
myString->Set(aValue);
owner()->data()->sendAttributeUpdated(this);
}
std::string Model_AttributeString::value()
{
+ if (myString.IsNull())
+ return ""; // not initialized
return TCollection_AsciiString(myString->Get()).ToCString();
}
Model_AttributeString::Model_AttributeString(TDF_Label& theLabel)
{
+ myLab = theLabel;
// check the attribute could be already presented in this doc (after load document)
myIsInitialized = theLabel.FindAttribute(TDataStd_Name::GetID(), myString) == Standard_True;
- if (!myIsInitialized) {
- // create attribute: not initialized by value yet, just empty string
- myString = TDataStd_Name::Set(theLabel, TCollection_ExtendedString());
- }
}
class Model_AttributeString : public ModelAPI_AttributeString
{
- Handle_TDataStd_Name myString;
+ Handle_TDataStd_Name myString; ///< container of the string value
+ TDF_Label myLab; ///< if attribute is not initialized, store label here
public:
/// Defines the std::string value
MODEL_EXPORT virtual void setValue(const std::string& theValue);
TDataStd_Name::Set(aSubBuilder.NamedShape()->Label(), aSolidName.c_str());
}
}
+ } else if(!aBuilder.NamedShape()->IsEmpty()) {
+ Handle(TDataStd_Name) anAttr;
+ if(aBuilder.NamedShape()->Label().FindAttribute(TDataStd_Name::GetID(),anAttr)) {
+ std::string aName (TCollection_AsciiString(anAttr->Get()).ToCString());
+ if(!aName.empty()) {
+ std::shared_ptr<Model_Document> aDoc = std::dynamic_pointer_cast<Model_Document>(document());
+ aDoc->addNamingName(aBuilder.NamedShape()->Label(), aName);
+ }
+ }
}
}
}
void Model_BodyBuilder::buildName(const int theTag, const std::string& theName)
{
- std::string aName = data()->name() + "/" + theName;
std::shared_ptr<Model_Document> aDoc = std::dynamic_pointer_cast<Model_Document>(document());
- aDoc->addNamingName(builder(theTag)->NamedShape()->Label(), aName);
- TDataStd_Name::Set(builder(theTag)->NamedShape()->Label(),aName.c_str());
+ //aDoc->addNamingName(builder(theTag)->NamedShape()->Label(), theName);
+ TDataStd_Name::Set(builder(theTag)->NamedShape()->Label(), theName.c_str());
}
void Model_BodyBuilder::generated(
const std::shared_ptr<GeomAPI_Shape>& theNewShape, const std::string& theName, const int theTag)
TDF_Label aChildLabel = aLabel.FindChild(aTag);
TNaming_Builder aBuilder(aChildLabel);
aBuilder.Generated(anOldShape, anExp.Current());
- TCollection_AsciiString aChildName = TCollection_AsciiString((data()->name() + "/" + theName + "_").c_str()) + aTag;
- aDoc->addNamingName(aChildLabel, aChildName.ToCString());
+ TCollection_AsciiString aChildName = TCollection_AsciiString((theName + "_").c_str()) + aTag;
+ //aDoc->addNamingName(aChildLabel, aChildName.ToCString());
TDataStd_Name::Set(aChildLabel, aChildName.ToCString());
aTag++;
}
TDF_Label aChildLabel = aLabel.FindChild(aTag);
TNaming_Builder aBuilder(aChildLabel);
aBuilder.Generated(aRoot, anExp.Current());
- TCollection_AsciiString aChildName = TCollection_AsciiString((data()->name() + "/" + theName + "_").c_str()) + aTag;
- aDoc->addNamingName(aChildLabel, aChildName.ToCString());
+ TCollection_AsciiString aChildName = TCollection_AsciiString((theName + "_").c_str()) + aTag;
+ //aDoc->addNamingName(aChildLabel, aChildName.ToCString());
TDataStd_Name::Set(aChildLabel, aChildName.ToCString());
aTag++;
}
}
}
- /* TopTools_IndexedDataMapOfShapeListOfShape aDM;
- TopExp::MapShapesAndAncestors(aShape, TopAbs_EDGE, TopAbs_FACE, aDM);
- for(int i=1; i <= aDM.Extent(); i++) {
- if(aDM.FindFromIndex(i).Extent() > 1) continue;
- if (BRep_Tool::Degenerated(TopoDS::Edge(aDM.FindKey(i))))
- continue;
- builder(theTag)->Generated(aDM.FindKey(i));
- TCollection_AsciiString aStr(theTag);
- std::string aName = theName + aStr.ToCString();
- buildName(theTag, aName);
- #ifdef DEB_IMPORT
- aName += + ".brep";
- BRepTools::Write(aDM.FindKey(i), aName.c_str());
- #endif
- theTag++;
- }
- */
TopTools_MapOfShape anEdgesToDelete;
TopExp_Explorer anEx(aShape,TopAbs_EDGE);
std::string aName;
}
if (mySendAttributeUpdated && isModified)
ModelAPI_ObjectRenamedMessage::send(myObject, anOldName, theName, this);
+ if (isModified && myObject && myObject->document()) {
+ std::dynamic_pointer_cast<Model_Document>(myObject->document())->
+ changeNamingName(anOldName, theName);
+ }
}
AttributePtr Model_Data::addAttribute(const std::string& theID, const std::string theAttrType)
{
TDF_Label aTargetRoot = std::dynamic_pointer_cast<Model_Data>(theTarget)->label();
copyAttrs(myLab, aTargetRoot);
- // make initialized the initialized attributes
- std::map<std::string, std::shared_ptr<ModelAPI_Attribute> >::iterator aMyIter = myAttrs.begin();
- for(; aMyIter != myAttrs.end(); aMyIter++) {
- if (aMyIter->second->isInitialized()) {
- AttributePtr aTargetAttr = theTarget->attribute(aMyIter->first);
- if (aTargetAttr)
- aTargetAttr->setInitialized();
- }
- }
+ // reinitialize Model_Attributes by TDF_Attributes set
+ std::shared_ptr<Model_Data> aTData = std::dynamic_pointer_cast<Model_Data>(theTarget);
+ aTData->myAttrs.clear();
+ theTarget->owner()->initAttributes(); // reinit feature attributes
}
bool Model_Data::isInHistory()
#include <ModelAPI_AttributeSelectionList.h>
#include <ModelAPI_Tools.h>
#include <ModelAPI_ResultBody.h>
-
#include <Events_Loop.h>
#include <Events_InfoMessage.h>
#include <TDF_ChildIDIterator.hxx>
#include <TDF_LabelMapHasher.hxx>
#include <TDF_Delta.hxx>
-#include <OSD_File.hxx>
-#include <OSD_Path.hxx>
#include <TDF_AttributeDelta.hxx>
#include <TDF_AttributeDeltaList.hxx>
#include <TDF_ListIteratorOfAttributeDeltaList.hxx>
#include <TDF_ListIteratorOfLabelList.hxx>
-#include <TopoDS_Shape.hxx>
+#include <TDF_LabelMap.hxx>
#include <TNaming_SameShapeIterator.hxx>
#include <TNaming_Iterator.hxx>
#include <TNaming_NamedShape.hxx>
#include <TNaming_Tool.hxx>
+
#include <TopExp_Explorer.hxx>
+#include <TopoDS_Shape.hxx>
+
+#include <OSD_File.hxx>
+#include <OSD_Path.hxx>
#include <climits>
#ifndef WIN32
}
}
-/// Compares the content ofthe given attributes, returns true if equal.
+/// Compares the content of the given attributes, returns true if equal.
/// This method is used to avoid empty transactions when only "current" is changed
/// to some value and then comes back in this transaction, so, it compares only
/// references and Boolean and Integer Arrays for the current moment.
bool isNestedClosed = !myDoc->HasOpenCommand() && !myNestedNum.empty();
static std::shared_ptr<Model_Session> aSession =
std::static_pointer_cast<Model_Session>(Model_Session::get());
+
+ // open transaction if nested is closed to fit inside all synchronizeBackRefs and flushed consequences
+ if (isNestedClosed) {
+ myDoc->OpenCommand();
+ }
// do it before flashes to enable and recompute nesting features correctly
if (myNestedNum.empty() || (isNestedClosed && myNestedNum.size() == 1)) {
// if all nested operations are closed, make current the higher level objects (to perform
aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_DELETED));
+
+ if (isNestedClosed) {
+ if (myDoc->CommitCommand())
+ myTransactions.rbegin()->myOCAFNum++;
+ }
+
// this must be here just after everything is finished but before real transaction stop
// to avoid messages about modifications outside of the transaction
// and to rebuild everything after all updates and creates
}
// add also label of the modified attributes
const TDF_AttributeDeltaList& anAttrs = aDelta->AttributeDeltas();
+ TDF_LabelMap anExcludedInt; /// named shape evolution also modifies integer on this label: exclude it
for (TDF_ListIteratorOfAttributeDeltaList anAttr(anAttrs); anAttr.More(); anAttr.Next()) {
- theDelta.Append(anAttr.Value()->Label());
+ if (anAttr.Value()->Attribute()->ID() == TDataStd_BooleanArray::GetID()) {
+ continue; // Boolean array is used for feature auxiliary attributes only, feature args are not modified
+ }
+ if (anAttr.Value()->Attribute()->ID() == TNaming_NamedShape::GetID()) {
+ anExcludedInt.Add(anAttr.Value()->Label());
+ continue; // named shape evolution is changed in history update => skip them, they are not the features arguents
+ }
+ if (anAttr.Value()->Attribute()->ID() == TDataStd_Integer::GetID()) {
+ if (anExcludedInt.Contains(anAttr.Value()->Label()))
+ continue;
+ }
+ theDelta.Append(anAttr.Value()->Label());
+ }
+ TDF_ListIteratorOfLabelList aDeltaIter(theDelta);
+ for(; aDeltaIter.More(); aDeltaIter.Next()) {
+ if (anExcludedInt.Contains(aDeltaIter.Value())) {
+ theDelta.Remove(aDeltaIter);
+ if (!aDeltaIter.More())
+ break;
+ }
}
}
}
if (anIter->setDisabled(aDisabledFlag)) {
- // state of feature is changed => so feature become updated
static Events_ID anUpdateEvent = aLoop->eventByName(EVENT_OBJECT_UPDATED);
- ModelAPI_EventCreator::get()->sendUpdated(anIter, anUpdateEvent);
+ // state of feature is changed => so inform that it must be updated if it has such state
+ if (!aDisabledFlag &&
+ (anIter->data()->execState() == ModelAPI_StateMustBeUpdated || anIter->data()->execState() == ModelAPI_StateInvalidArgument))
+ ModelAPI_EventCreator::get()->sendUpdated(anIter, anUpdateEvent);
// flush is in the end of this method
ModelAPI_EventCreator::get()->sendUpdated(anIter, aRedispEvent /*, false*/);
aWasChanged = true;
myNamingNames[theName] = theLabel;
}
+void Model_Document::changeNamingName(const std::string theOldName, const std::string theNewName)
+{
+ std::map<std::string, TDF_Label>::iterator aFind = myNamingNames.find(theOldName);
+ if (aFind != myNamingNames.end()) {
+ myNamingNames[theNewName] = aFind->second;
+ myNamingNames.erase(theOldName);
+ }
+}
+
TDF_Label Model_Document::findNamingName(std::string theName)
{
std::map<std::string, TDF_Label>::iterator aFind = myNamingNames.find(theName);
- if (aFind == myNamingNames.end())
- return TDF_Label(); // not found
- return aFind->second;
+ if (aFind != myNamingNames.end()) {
+ return aFind->second;
+ }
+ // not found exact name, try to find by sub-components
+ std::string::size_type aSlash = theName.rfind('/');
+ if (aSlash != std::string::npos) {
+ std::string anObjName = theName.substr(0, aSlash);
+ aFind = myNamingNames.find(anObjName);
+ if (aFind != myNamingNames.end()) {
+ TCollection_ExtendedString aSubName(theName.substr(aSlash + 1).c_str());
+ // searching sub-labels with this name
+ TDF_ChildIDIterator aNamesIter(aFind->second, TDataStd_Name::GetID(), Standard_True);
+ for(; aNamesIter.More(); aNamesIter.Next()) {
+ Handle(TDataStd_Name) aName = Handle(TDataStd_Name)::DownCast(aNamesIter.Value());
+ if (aName->Get() == aSubName)
+ return aName->Label();
+ }
+ }
+ }
+ return TDF_Label(); // not found
}
ResultPtr Model_Document::findByName(const std::string theName)
//! Registers the name of the shape for the topological naming needs
void addNamingName(const TDF_Label theLabel, std::string theName);
+ //! Updates the name of some object
+ void changeNamingName(std::string theOldName, const std::string theNewName);
//! Returns the label, keeper of the name for the topological naming needs
TDF_Label findNamingName(std::string theName);
//! Returns the result by name of the result (names of results must be unique, used for naming
friend class Model_AttributeSelection;
friend class Model_ResultPart;
friend class Model_ResultCompSolid;
+ friend class Model_SelectionNaming;
friend class DFBrowser;
private:
#include <TDataStd_RealArray.hxx>
#include <TDataStd_ExtStringArray.hxx>
+#include <limits>
static Standard_GUID kInvalidGUID("caee5ce4-34b1-4b29-abcb-685287d18096");
void Model_Expression::setText(const std::string& theValue)
{
- if (text() != theValue)
+ if (text() != theValue) {
myText->Set(TCollection_ExtendedString(theValue.c_str()));
+ myIsInitialized = true; // the value will be set very soon
+ }
setError(text().empty() ? "" : "Not a double value.");
}
: Model_Expression(theLabel)
{
if (!theLabel.FindAttribute(TDataStd_Real::GetID(), myReal)) {
- myReal = TDataStd_Real::Set(theLabel, 0.);
myIsInitialized = false;
// MPV: temporarily to support the previously saved files (to check and resolve bugs), to be removed
Handle(TDataStd_RealArray) anOldArray;
if (theLabel.Father().FindAttribute(TDataStd_RealArray::GetID(), anOldArray) == Standard_True) {
+ myReal = TDataStd_Real::Set(theLabel, 0.);
myReal->Set(anOldArray->Value(theLabel.Tag() - 1));
myIsInitialized = true;
Handle(TDataStd_ExtStringArray) anOldExp;
Handle(TDataStd_Real) anOldReal;
if (theLabel.Father().FindAttribute(TDataStd_Real::GetID(), anOldReal)) {
myIsInitialized = true;
+ myReal = TDataStd_Real::Set(theLabel, 0.);
myReal->Set(anOldReal->Get());
Handle(TDataStd_Name) aText;
if (theLabel.Father().FindAttribute(TDataStd_Name::GetID(), aText)) {
void Model_ExpressionDouble::setValue(const double theValue)
{
- if (value() != theValue)
+ if (!myIsInitialized || myReal.IsNull()) {
+ myReal = TDataStd_Real::Set(myText->Label(), theValue);
+ myIsInitialized = true;
+ } else if (value() != theValue) {
myReal->Set(theValue);
+ }
}
double Model_ExpressionDouble::value()
{
- return myReal->Get();
+ if (myIsInitialized)
+ return myReal->Get();
+ return std::numeric_limits<double>::max(); // error
}
void Model_ExpressionDouble::setInvalid(const bool theFlag)
{
if (theFlag) {
- TDataStd_UAttribute::Set(myReal->Label(), kInvalidGUID);
+ TDataStd_UAttribute::Set(myText->Label(), kInvalidGUID);
} else {
- myReal->Label().ForgetAttribute(kInvalidGUID);
+ myText->Label().ForgetAttribute(kInvalidGUID);
}
}
bool Model_ExpressionDouble::isInvalid()
{
- return myReal->Label().IsAttribute(kInvalidGUID) == Standard_True;
+ return myText->Label().IsAttribute(kInvalidGUID) == Standard_True;
}
: Model_Expression(theLabel)
{
if (!theLabel.FindAttribute(TDataStd_Integer::GetID(), myInteger)) {
- myInteger = TDataStd_Integer::Set(theLabel, 0);
myIsInitialized = false;
} else
myIsInitialized = true;
void Model_ExpressionInteger::setValue(const int theValue)
{
- if (value() != theValue)
+ if (!myIsInitialized || myInteger.IsNull()) {
+ myInteger = TDataStd_Integer::Set(myText->Label(), theValue);
+ myIsInitialized = true;
+ } else if (value() != theValue) {
myInteger->Set(theValue);
+ }
}
int Model_ExpressionInteger::value()
{
- return myInteger->Get();
+ if (myIsInitialized)
+ return myInteger->Get();
+ return std::numeric_limits<int>::max(); // error
}
void Model_ExpressionInteger::setInvalid(const bool theFlag)
{
if (theFlag) {
- TDataStd_UAttribute::Set(myInteger->Label(), kInvalidGUID);
+ TDataStd_UAttribute::Set(myText->Label(), kInvalidGUID);
} else {
- myInteger->Label().ForgetAttribute(kInvalidGUID);
+ myText->Label().ForgetAttribute(kInvalidGUID);
}
}
bool Model_ExpressionInteger::isInvalid()
{
- return myInteger->Label().IsAttribute(kInvalidGUID) == Standard_True;
+ return myText->Label().IsAttribute(kInvalidGUID) == Standard_True;
}
aFeature = myFeatures.Find(aFeatureLabel);
aKeptFeatures.insert(aFeature);
if (anUpdatedMap.Contains(aFeatureLabel)) {
+ if (!theOpen) { // on abort/undo/redo reinitialize attributes is something is changed
+ std::shared_ptr<Model_Data> aD = std::dynamic_pointer_cast<Model_Data>(aFeature->data());
+ aD->myAttrs.clear();
+ aFeature->initAttributes();
+ }
ModelAPI_EventCreator::get()->sendUpdated(aFeature, anUpdateEvent);
if (aFeature->getKind() == "Parameter") { // if parameters are changed, update the results (issue 937)
const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = aFeature->results();
FeaturePtr& aFeature = anObjIter.ChangeValue();
if (!aFeature.get() || aFeature->isDisabled()) // may be on close
continue;
- const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = aFeature->results();
- std::list<std::shared_ptr<ModelAPI_Result> >::const_iterator aRIter = aResults.begin();
- for (; aRIter != aResults.cend(); aRIter++) {
+ std::list<ResultPtr> allResults;
+ ModelAPI_Tools::allResults(aFeature, allResults);
+ std::list<ResultPtr>::iterator aRIter = allResults.begin();
+ for (; aRIter != allResults.cend(); aRIter++) {
ResultPtr aRes = *aRIter;
if (aRes.get() && aRes->data() && aRes->data()->isValid() && !aRes->isDisabled() &&
aRes->data()->name() == theName) {
friend class Model_AttributeReference;
friend class Model_AttributeRefAttr;
friend class Model_AttributeRefList;
+ friend class Model_AttributeRefList;
+ friend class Model_SelectionNaming;
};
#endif
#include "Model_SelectionNaming.h"
#include "Model_Document.h"
+#include "Model_Objects.h"
#include <ModelAPI_Feature.h>
#include <Events_InfoMessage.h>
+#include <ModelAPI_Session.h>
+#include <ModelAPI_ResultPart.h>
+#include <ModelAPI_ResultConstruction.h>
+#include <ModelAPI_CompositeFeature.h>
+#include <ModelAPI_ResultBody.h>
#include <TopoDS_Iterator.hxx>
#include <TopoDS.hxx>
#include <TNaming_NamedShape.hxx>
#include <TNaming_Localizer.hxx>
#include <TDataStd_Name.hxx>
+#include <TColStd_MapOfTransient.hxx>
+#include <algorithm>
+#include <stdexcept>
#ifdef DEB_NAMING
#include <BRepTools.hxx>
myLab = theSelectionLab;
}
-
std::string Model_SelectionNaming::getShapeName(
- std::shared_ptr<Model_Document> theDoc, const TopoDS_Shape& theShape)
+ std::shared_ptr<Model_Document> theDoc, const TopoDS_Shape& theShape,
+ const bool theAddContextName)
{
std::string aName;
// check if the subShape is already in DF
if(!aNS.IsNull() && !aNS->IsEmpty()) { // in the document
if(aNS->Label().FindAttribute(TDataStd_Name::GetID(), anAttr)) {
aName = TCollection_AsciiString(anAttr->Get()).ToCString();
- if(!aName.empty()) {
- const TDF_Label& aLabel = theDoc->findNamingName(aName);
- /* MPV: the same shape with the same name may be duplicated on different labels (selection of the same construction object)
- if(!aLabel.IsEqual(aNS->Label())) {
- //aName.erase(); //something is wrong, to be checked!!!
- aName += "_SomethingWrong";
- return aName;
- }*/
-
+ // indexes are added to sub-shapes not primitives (primitives must not be located at the same label)
+ if(!aName.empty() && aNS->Evolution() != TNaming_PRIMITIVE && theAddContextName) {
+ const TDF_Label& aLabel = aNS->Label();//theDoc->findNamingName(aName);
static const std::string aPostFix("_");
TNaming_Iterator anItL(aNS);
for(int i = 1; anItL.More(); anItL.Next(), i++) {
break;
}
}
- }
+ }
+ if (theAddContextName && aName.find("/") == std::string::npos) { // searching for the context object
+ for(TDF_Label anObjL = aNS->Label(); anObjL.Depth() > 4; anObjL = anObjL.Father()) {
+ int aDepth = anObjL.Depth();
+ if (aDepth == 5 || aDepth == 7) {
+ ObjectPtr anObj = theDoc->objects()->object(anObjL);
+ if (anObj) {
+ aName = anObj->data()->name() + "/" + aName;
+ }
+ }
+ }
+ }
}
}
return aName;
}
-
-
bool isTrivial (const TopTools_ListOfShape& theAncestors, TopTools_IndexedMapOfShape& theSMap)
{
// a trivial case: F1 & F2, aNumber = 1, i.e. intersection gives 1 edge.
#endif
std::shared_ptr<Model_Document> aDoc =
std::dynamic_pointer_cast<Model_Document>(theContext->document());
+ if (theContext->groupName() == ModelAPI_ResultPart::group()) {
+ ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(theContext);
+ int anIndex;
+ return aPart->data()->name() + "/" + aPart->nameInPart(theSubSh, anIndex);
+ }
+
+ // add the result name to the name of the shape (it was in BodyBuilder, but did not work on Result rename)
+ bool isNeedContextName = theContext->shape().get() && !theContext->shape()->isEqual(theSubSh);
// check if the subShape is already in DF
- aName = getShapeName(aDoc, aSubShape);
+ aName = getShapeName(aDoc, aSubShape, isNeedContextName);
if(aName.empty() ) { // not in the document!
TopAbs_ShapeEnum aType = aSubShape.ShapeType();
switch (aType) {
break;
case TopAbs_EDGE:
{
- // name structure: F1 | F2 [| F3 | F4], where F1 & F2 the faces which gives the Edge in trivial case
+ // name structure: F1 & F2 [& F3 & F4], where F1 & F2 the faces which gives the Edge in trivial case
// if it is not atrivial case we use localization by neighbours. F3 & F4 - neighbour faces
if (BRep_Tool::Degenerated(TopoDS::Edge(aSubShape))) {
aName = "Degenerated_Edge";
// build name of the sub-shape Edge
for(int i=1; i <= aSMap.Extent(); i++) {
const TopoDS_Shape& aFace = aSMap.FindKey(i);
- std::string aFaceName = getShapeName(aDoc, aFace);
+ std::string aFaceName = getShapeName(aDoc, aFace, isNeedContextName);
if(i == 1)
aName = aFaceName;
else
}
TopTools_ListIteratorOfListOfShape itl(aListOfNbs);
for (;itl.More();itl.Next()) {
- std::string aFaceName = getShapeName(aDoc, itl.Value());
+ std::string aFaceName = getShapeName(aDoc, itl.Value(), isNeedContextName);
aName += "&" + aFaceName;
}
}
TopTools_ListIteratorOfListOfShape itl(aListE);
for (int i = 1;itl.More();itl.Next(),i++) {
const TopoDS_Shape& anEdge = itl.Value();
- std::string anEdgeName = getShapeName(aDoc, anEdge);
+ std::string anEdgeName = getShapeName(aDoc, anEdge, isNeedContextName);
if (anEdgeName.empty()) { // edge is not in DS, trying by faces anyway
isByFaces = true;
aName.clear();
TopTools_ListIteratorOfListOfShape itl(aList);
for (int i = 1;itl.More();itl.Next(),i++) {
const TopoDS_Shape& aFace = itl.Value();
- std::string aFaceName = getShapeName(aDoc, aFace);
+ std::string aFaceName = getShapeName(aDoc, aFace, isNeedContextName);
if(i == 1)
aName = aFaceName;
else
}
break;
}
- // register name
- // aDoc->addNamingName(selectionLabel(), aName);
- // the selected sub-shape will not be shared and as result it will not require registration
}
+
return aName;
}
if (n == std::string::npos) n = 0;
std::string aSubString = theSubShapeName.substr(n + 1);
n = aSubString.rfind('_');
- if (n == std::string::npos) return aSelection;
- aSubString = aSubString.substr(n+1);
- int indx = atoi(aSubString.c_str());
+ int indx;
+ if (n == std::string::npos) {// for primitives this is a first
+ indx = 1;
+ } else {
+ aSubString = aSubString.substr(n+1);
+ indx = atoi(aSubString.c_str());
+ }
TNaming_Iterator anItL(theNS);
for(int i = 1; anItL.More(); anItL.Next(), i++) {
const std::string& theSubShapeName, std::shared_ptr<Model_Document> theDoc)
{
TopoDS_Shape aFace;
- std::string::size_type n, nb = theSubShapeName.rfind('/');
- if (nb == std::string::npos) nb = 0;
- std::string aSubString = theSubShapeName.substr(nb + 1);
- n = aSubString.rfind('_');
- if (n != std::string::npos) {
- std::string aSubStr2 = aSubString.substr(0, n);
- aSubString = theSubShapeName.substr(0, nb + 1);
- aSubString = aSubString + aSubStr2;
- } else
- aSubString = theSubShapeName;
-
- const TDF_Label& aLabel = theDoc->findNamingName(aSubString);
+ //std::string::size_type n, nb = theSubShapeName.rfind('/');
+ //if (nb == std::string::npos) nb = 0;
+ //std::string aSubString = theSubShapeName.substr(nb + 1);
+ std::string aSubString = theSubShapeName;
+
+ TDF_Label aLabel = theDoc->findNamingName(aSubString);
+ if (aLabel.IsNull()) { // try to remove additional artificial suffix
+ std::string::size_type n = aSubString.rfind('_');
+ if (n != std::string::npos) {
+ aSubString = aSubString.substr(0, n);
+ aLabel = theDoc->findNamingName(aSubString);
+ }
+ }
if(aLabel.IsNull()) return aFace;
Handle(TNaming_NamedShape) aNS;
if(aLabel.FindAttribute(TNaming_NamedShape::GetID(), aNS)) {
{
std::string aName;
std::string::size_type n = theSubShapeName.find('/');
- if (n == std::string::npos) return aName;
+ if (n == std::string::npos) return theSubShapeName;
aName = theSubShapeName.substr(0, n);
return aName;
}
+/// Parses naming name of sketch sub-elements: takes indices and orientation
+/// (if theOriented = true) from this name. Map theIDs constains indices ->
+/// orientations and start/end vertices: negative is reversed, 2 - start, 3 - end
+bool parseSubIndices(CompositeFeaturePtr theComp, //< to iterate names
+ const std::string& theName, const char* theShapeType,
+ std::map<int, int>& theIDs, const bool theOriented = false)
+{
+ // collect all IDs in the name
+ std::map<std::string, int> aNames; // short name of sub -> ID of sub of theComp
+ const int aSubNum = theComp->numberOfSubs();
+ for(int a = 0; a < aSubNum; a++) {
+ FeaturePtr aSub = theComp->subFeature(a);
+ const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = aSub->results();
+ std::list<std::shared_ptr<ModelAPI_Result> >::const_iterator aRes = aResults.cbegin();
+ // there may be many shapes (circle and center)
+ for(; aRes != aResults.cend(); aRes++) {
+ ResultConstructionPtr aConstr =
+ std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aRes);
+ if (aConstr.get()) {
+ aNames[Model_SelectionNaming::shortName(aConstr)] = theComp->subFeatureId(a);
+ }
+ }
+ }
+
+ size_t aPrevPos = theName.find("/") + 1, aLastNamePos;
+ bool isShape = false; // anyway the first world must be 'Vertex'
+ do {
+ aLastNamePos = theName.find('-', aPrevPos);
+ std::string anID = theName.substr(aPrevPos, aLastNamePos - aPrevPos);
+ if (!isShape) {
+ if (anID != theShapeType)
+ return false;
+ isShape = true;
+ } else {
+ int anOrientation = 1; // default
+ if (theOriented) { // here must be a symbol in the end of digit 'f' or 'r'
+ std::string::iterator aSymbol = anID.end() - 1;
+ if (*aSymbol == 'r') anOrientation = -1;
+ anID.erase(aSymbol); // remove last symbol
+ }
+ // check start/end symbols
+ std::string::iterator aBack = anID.end() - 1;
+ if (*aBack == 's') {
+ anOrientation *= 2;
+ anID.erase(aBack); // remove last symbol
+ } else if (*aBack == 'e') {
+ anOrientation *= 3;
+ anID.erase(aBack); // remove last symbol
+ }
+
+ if (aNames.find(anID) != aNames.end()) {
+ theIDs[aNames[anID]] = anOrientation;
+ }
+ }
+ aPrevPos = aLastNamePos + 1;
+ } while (aLastNamePos != std::string::npos);
+ return true;
+}
+
+/// produces theEdge orientation relatively to theContext face
+int Model_SelectionNaming::edgeOrientation(const TopoDS_Shape& theContext, TopoDS_Edge& theEdge)
+{
+ if (theContext.ShapeType() != TopAbs_FACE && theContext.ShapeType() != TopAbs_WIRE)
+ return 0;
+ if (theEdge.Orientation() == TopAbs_FORWARD)
+ return 1;
+ if (theEdge.Orientation() == TopAbs_REVERSED)
+ return -1;
+ return 0; // unknown
+}
+
+std::shared_ptr<GeomAPI_Shape> Model_SelectionNaming::findAppropriateFace(
+ std::shared_ptr<ModelAPI_Result>& theConstr,
+ NCollection_DataMap<Handle(Geom_Curve), int>& theCurves)
+{
+ int aBestFound = 0; // best number of found edges (not percentage: issue 1019)
+ int aBestOrient = 0; // for the equal "BestFound" additional parameter is orientation
+ std::shared_ptr<GeomAPI_Shape> aResult;
+ ResultConstructionPtr aConstructionContext =
+ std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(theConstr);
+ if (!aConstructionContext.get())
+ return aResult;
+ for(int aFaceIndex = 0; aFaceIndex < aConstructionContext->facesNum(); aFaceIndex++) {
+ int aFound = 0, aNotFound = 0, aSameOrientation = 0;
+ TopoDS_Face aFace =
+ TopoDS::Face(aConstructionContext->face(aFaceIndex)->impl<TopoDS_Shape>());
+ TopExp_Explorer anEdgesExp(aFace, TopAbs_EDGE);
+ TColStd_MapOfTransient alreadyProcessed; // to avoid counting edges with same curved (841)
+ for(; anEdgesExp.More(); anEdgesExp.Next()) {
+ TopoDS_Edge anEdge = TopoDS::Edge(anEdgesExp.Current());
+ if (!anEdge.IsNull()) {
+ Standard_Real aFirst, aLast;
+ Handle(Geom_Curve) aCurve = BRep_Tool::Curve(anEdge, aFirst, aLast);
+ if (alreadyProcessed.Contains(aCurve))
+ continue;
+ alreadyProcessed.Add(aCurve);
+ if (theCurves.IsBound(aCurve)) {
+ aFound++;
+ int anOrient = theCurves.Find(aCurve);
+ if (anOrient != 0) { // extra comparision score is orientation
+ if (edgeOrientation(aFace, anEdge) == anOrient)
+ aSameOrientation++;
+ }
+ } else {
+ aNotFound++;
+ }
+ }
+ }
+ if (aFound + aNotFound != 0) {
+ if (aFound > aBestFound ||
+ (aFound == aBestFound && aSameOrientation > aBestOrient)) {
+ aBestFound = aFound;
+ aBestOrient = aSameOrientation;
+ aResult = aConstructionContext->face(aFaceIndex);
+ }
+ }
+ }
+ return aResult;
+}
+
+std::string Model_SelectionNaming::shortName(
+ std::shared_ptr<ModelAPI_ResultConstruction>& theConstr, const int theEdgeVertexPos)
+{
+ std::string aName = theConstr->data()->name();
+ // remove "-", "/" and "&" command-symbols
+ aName.erase(std::remove(aName.begin(), aName.end(), '-'), aName.end());
+ aName.erase(std::remove(aName.begin(), aName.end(), '/'), aName.end());
+ aName.erase(std::remove(aName.begin(), aName.end(), '&'), aName.end());
+ // remove the last 's', 'e', 'f' and 'r' symbols: they are used as markers of start/end/forward/rewersed indicators
+ static const std::string aSyms("sefr");
+ std::string::iterator aSuffix = aName.end() - 1;
+ while(aSyms.find(*aSuffix) != std::string::npos) {
+ --aSuffix;
+ }
+ aName.erase(aSuffix + 1, aName.end());
+
+ if (theEdgeVertexPos == 1) {
+ aName += "s"; // start
+ } else if (theEdgeVertexPos == 2) {
+ aName += "e"; // end
+ }
+ return aName;
+}
+
// type ::= COMP | COMS | SOLD | SHEL | FACE | WIRE | EDGE | VERT
bool Model_SelectionNaming::selectSubShape(const std::string& theType,
const std::string& theSubShapeName, std::shared_ptr<Model_Document> theDoc,
{
if(theSubShapeName.empty() || theType.empty()) return false;
TopAbs_ShapeEnum aType = translateType(theType);
- std::string aContName = getContextName(theSubShapeName);
+
+ // check that it was selected in another document
+ size_t aSlash = theSubShapeName.find("/");
+ std::string aSubShapeName = theSubShapeName;
+ std::shared_ptr<Model_Document> aDoc = theDoc;
+ if (aSlash != std::string::npos) {
+ std::string aDocName = theSubShapeName.substr(0, aSlash);
+ DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
+ if (aDocName == aRootDoc->kind()) {
+ aDoc = std::dynamic_pointer_cast<Model_Document>(aRootDoc);
+ } else {
+ for (int a = aRootDoc->size(ModelAPI_ResultPart::group()) - 1; a >= 0; a--) {
+ ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(
+ aRootDoc->object(ModelAPI_ResultPart::group(), a));
+ if (aPart.get() && aPart->isActivated() && aPart->data()->name() == aDocName) {
+ aDoc = std::dynamic_pointer_cast<Model_Document>(aPart->partDoc());
+ }
+ }
+ }
+ if (aDoc != theDoc) { // so, the first word is the document name => reduce the string for the next manips
+ aSubShapeName = theSubShapeName.substr(aSlash + 1);
+ }
+ }
+
+ std::string aContName = getContextName(aSubShapeName);
if(aContName.empty()) return false;
- ResultPtr aCont = theDoc->findByName(aContName);
- if(!aCont.get() || aCont->shape()->isNull()) return false;
- TopoDS_Shape aContext = aCont->shape()->impl<TopoDS_Shape>();
- TopAbs_ShapeEnum aContType = aContext.ShapeType();
- if(aType <= aContType) return false; // not applicable
+ ResultPtr aCont = aDoc->findByName(aContName);
+ // possible this is body where postfix is added to distinguish several shapes on the same label
+ int aSubShapeId = -1; // -1 means sub shape not found
+ // for result body the name wihtout "_" has higher priority than with it: it is always added
+ if ((!aCont.get()/* || (aCont->groupName() == ModelAPI_ResultBody::group())*/) &&
+ aContName == aSubShapeName) {
+ size_t aPostIndex = aContName.rfind('_');
+ if (aPostIndex != std::string::npos) {
+ std::string aSubContName = aContName.substr(0, aPostIndex);
+ ResultPtr aSubCont = aDoc->findByName(aSubContName);
+ if (aSubCont.get()) {
+ try {
+ std::string aNum = aContName.substr(aPostIndex + 1);
+ aSubShapeId = std::stoi(aNum);
+ } catch (std::invalid_argument&) {
+ aSubShapeId = -1;
+ }
+ if (aSubShapeId > 0) {
+ aContName = aSubContName;
+ aCont = aSubCont;
+ }
+ }
+ }
+ }
TopoDS_Shape aSelection;
switch (aType)
{
- case TopAbs_COMPOUND:
- break;
- case TopAbs_COMPSOLID:
- break;
- case TopAbs_SOLID:
- break;
- case TopAbs_SHELL:
- break;
case TopAbs_FACE:
+ case TopAbs_WIRE:
{
- const TopoDS_Shape aSelection = findFaceByName(theSubShapeName, theDoc);
- if(!aSelection.IsNull()) {// Select it
- std::shared_ptr<GeomAPI_Shape> aShapeToBeSelected(new GeomAPI_Shape());
- aShapeToBeSelected->setImpl(new TopoDS_Shape(aSelection));
- theShapeToBeSelected = aShapeToBeSelected;
- theCont = aCont;
- return true;
- }
+ aSelection = findFaceByName(aSubShapeName, aDoc);
}
break;
- case TopAbs_WIRE:
- break;
case TopAbs_EDGE:
{
- TopoDS_Shape aSelection;// = findFaceByName(theSubShapeName, aDoc);
- const TDF_Label& aLabel = theDoc->findNamingName(theSubShapeName);
+ const TDF_Label& aLabel = aDoc->findNamingName(aSubShapeName);
if(!aLabel.IsNull()) {
Handle(TNaming_NamedShape) aNS;
if(aLabel.FindAttribute(TNaming_NamedShape::GetID(), aNS)) {
- aSelection = getShapeFromNS(theSubShapeName, aNS);
- }
- }
- if(aSelection.IsNull()) {
- std::list<std::string> aListofNames;
- size_t n = ParseName(theSubShapeName, aListofNames);
- if(n > 1 && n < 5) {
- TopTools_ListOfShape aList;
- std::list<std::string>::iterator it =aListofNames.begin();
- for(;it != aListofNames.end();it++){
- const TopoDS_Shape aFace = findFaceByName(*it, theDoc);
- aList.Append(aFace);
- }
- aSelection = findCommonShape(TopAbs_EDGE, aList);
+ aSelection = getShapeFromNS(aSubShapeName, aNS);
}
}
- if(!aSelection.IsNull()) {// Select it
- std::shared_ptr<GeomAPI_Shape> aShapeToBeSelected(new GeomAPI_Shape());
- aShapeToBeSelected->setImpl(new TopoDS_Shape(aSelection));
- theShapeToBeSelected = aShapeToBeSelected;
- theCont = aCont;
- return true;
- }
}
break;
case TopAbs_VERTEX:
{
- TopoDS_Shape aSelection;
- const TDF_Label& aLabel = theDoc->findNamingName(theSubShapeName);
+ const TDF_Label& aLabel = aDoc->findNamingName(aSubShapeName);
if(!aLabel.IsNull()) {
Handle(TNaming_NamedShape) aNS;
if(aLabel.FindAttribute(TNaming_NamedShape::GetID(), aNS)) {
- aSelection = getShapeFromNS(theSubShapeName, aNS);
+ aSelection = getShapeFromNS(aSubShapeName, aNS);
}
}
- if(aSelection.IsNull()) {
- std::list<std::string> aListofNames;
- size_t n = ParseName(theSubShapeName, aListofNames);
- if(n > 1 && n < 4) { // 2 || 3
- TopTools_ListOfShape aList;
- std::list<std::string>::iterator it = aListofNames.begin();
- for(; it != aListofNames.end(); it++){
- const TopoDS_Shape aFace = findFaceByName(*it, theDoc);
- if(!aFace.IsNull())
- aList.Append(aFace);
- }
- aSelection = findCommonShape(TopAbs_VERTEX, aList);
- }
- }
- if(!aSelection.IsNull()) {// Select it
- std::shared_ptr<GeomAPI_Shape> aShapeToBeSelected(new GeomAPI_Shape());
- aShapeToBeSelected->setImpl(new TopoDS_Shape(aSelection));
- theShapeToBeSelected = aShapeToBeSelected;
+ }
+ break;
+ case TopAbs_COMPOUND:
+ case TopAbs_COMPSOLID:
+ case TopAbs_SOLID:
+ case TopAbs_SHELL:
+ default: {//TopAbs_SHAPE
+ /// case when the whole sketch is selected, so, selection type is compound, but there is no value
+ if (aCont.get() && aCont->shape().get()) {
+ if (aCont->shape()->impl<TopoDS_Shape>().ShapeType() == aType) {
theCont = aCont;
return true;
+ } else if (aSubShapeId > 0) { // try to find sub-shape by the index
+ TopExp_Explorer anExp(aCont->shape()->impl<TopoDS_Shape>(), aType);
+ for(; aSubShapeId > 1 && anExp.More(); aSubShapeId--) {
+ anExp.Next();
+ }
+ if (anExp.More()) {
+ std::shared_ptr<GeomAPI_Shape> aShapeToBeSelected(new GeomAPI_Shape());
+ aShapeToBeSelected->setImpl(new TopoDS_Shape(anExp.Current()));
+ theShapeToBeSelected = aShapeToBeSelected;
+ theCont = aCont;
+ return true;
+ }
}
}
- break;
- default: //TopAbs_SHAPE
return false;
+ }
+ }
+ // another try to find edge or vertex by faces
+ std::list<std::string> aListofNames;
+ size_t aN = aSelection.IsNull() ? ParseName(aSubShapeName, aListofNames) : 0;
+ if (aSelection.IsNull() && (aType == TopAbs_EDGE || aType == TopAbs_VERTEX)) {
+ if(aN > 1 && (aN < 4 || (aType == TopAbs_EDGE && aN < 5))) { // 2 || 3 or 4 for EDGE
+ TopTools_ListOfShape aList;
+ std::list<std::string>::iterator it = aListofNames.begin();
+ for(; it != aListofNames.end(); it++){
+ const TopoDS_Shape aFace = findFaceByName(*it, aDoc);
+ if(!aFace.IsNull())
+ aList.Append(aFace);
+ }
+ aSelection = findCommonShape(aType, aList);
+ }
+ }
+ if (!aSelection.IsNull()) {// Select it
+ std::shared_ptr<GeomAPI_Shape> aShapeToBeSelected(new GeomAPI_Shape());
+ aShapeToBeSelected->setImpl(new TopoDS_Shape(aSelection));
+ theShapeToBeSelected = aShapeToBeSelected;
+ theCont = aCont;
+ return true;
+ }
+ // in case of construction, there is no registered names for all sub-elements,
+ // even for the main element; so, trying to find them by name (without "&" intersections)
+ if (aN == 0) {
+ size_t aConstrNamePos = aSubShapeName.find("/");
+ bool isFullName = aConstrNamePos == std::string::npos;
+ std::string aContrName = aContName;
+ ResultPtr aConstr = aDoc->findByName(aContrName);
+ if (aConstr.get() && aConstr->groupName() == ModelAPI_ResultConstruction::group()) {
+ theCont = aConstr;
+ if (isFullName) {
+ // For the full construction selection shape must be empty.
+ //theShapeToBeSelected = aConstr->shape();
+ return true;
+ }
+ // for sketch sub-elements selected
+ CompositeFeaturePtr aComposite =
+ std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(aDoc->feature(aConstr));
+ if (aComposite.get()) {
+ if (aType == TopAbs_VERTEX || aType == TopAbs_EDGE) {
+ // collect all IDs in the name
+ std::map<int, int> anIDs;
+ if (!parseSubIndices(aComposite, aSubShapeName,
+ aType == TopAbs_EDGE ? "Edge" : "Vertex", anIDs))
+ return false;
+
+ const int aSubNum = aComposite->numberOfSubs();
+ for(int a = 0; a < aSubNum; a++) {
+ int aCompID = aComposite->subFeatureId(a);
+ if (anIDs.find(aCompID) != anIDs.end()) { // found the vertex/edge shape
+ FeaturePtr aSub = aComposite->subFeature(a);
+ const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = aSub->results();
+ std::list<std::shared_ptr<ModelAPI_Result> >::const_iterator aRIt = aResults.cbegin();
+ // there may be many shapes (circle and center)
+ for(; aRIt != aResults.cend(); aRIt++) {
+ ResultConstructionPtr aRes =
+ std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aRIt);
+ if (aRes) {
+ int anOrientation = abs(anIDs[aCompID]);
+ TopoDS_Shape aShape = aRes->shape()->impl<TopoDS_Shape>();
+ if (anOrientation == 1) {
+ if (aType == aShape.ShapeType()) {
+ theShapeToBeSelected = aRes->shape();
+ return true;
+ }
+ } else { // take first or second vertex of the edge
+ TopoDS_Shape aShape = aRes->shape()->impl<TopoDS_Shape>();
+ TopExp_Explorer anExp(aShape, aType);
+ for(; anExp.More() && anOrientation != 2; anOrientation--)
+ anExp.Next();
+ if (anExp.More()) {
+ std::shared_ptr<GeomAPI_Shape> aShapeToBeSelected(new GeomAPI_Shape());
+ aShapeToBeSelected->setImpl(new TopoDS_Shape(anExp.Current()));
+ theShapeToBeSelected = aShapeToBeSelected;
+ return true;
+ }
+ }
+ }
+ }
+ }
+ }
+ // sketch faces is identified by format "Sketch_1/Face-2f-8f-11r"
+ } else if (aType == TopAbs_FACE || aType == TopAbs_WIRE) {
+ std::map<int, int> anIDs;
+ if (!parseSubIndices(aComposite, aSubShapeName,
+ aType == TopAbs_FACE ? "Face" : "Wire", anIDs, true))
+ return false;
+
+ NCollection_DataMap<Handle(Geom_Curve), int> allCurves; // curves and orientations of edges
+ const int aSubNum = aComposite->numberOfSubs();
+ for(int a = 0; a < aSubNum; a++) {
+ int aSubID = aComposite->subFeatureId(a);
+ if (anIDs.find(aSubID) != anIDs.end()) {
+ FeaturePtr aSub = aComposite->subFeature(a);
+ const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = aSub->results();
+ std::list<std::shared_ptr<ModelAPI_Result> >::const_iterator aRes;
+ for(aRes = aResults.cbegin(); aRes != aResults.cend(); aRes++) {
+ ResultConstructionPtr aConstr =
+ std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aRes);
+ if (aConstr->shape() && aConstr->shape()->isEdge()) {
+ const TopoDS_Shape& aResShape = aConstr->shape()->impl<TopoDS_Shape>();
+ TopoDS_Edge anEdge = TopoDS::Edge(aResShape);
+ if (!anEdge.IsNull()) {
+ Standard_Real aFirst, aLast;
+ Handle(Geom_Curve) aCurve = BRep_Tool::Curve(anEdge, aFirst, aLast);
+ allCurves.Bind(aCurve, anIDs[aSubID] > 0 ? 1 : -1);
+ }
+ }
+ }
+ }
+ }
+ std::shared_ptr<GeomAPI_Shape> aFoundFace = findAppropriateFace(aConstr, allCurves);
+ if (aFoundFace.get()) {
+ if (aType == TopAbs_WIRE) { // just get a wire from face to have wire
+ TopExp_Explorer aWireExp(aFoundFace->impl<TopoDS_Shape>(), TopAbs_WIRE);
+ if (aWireExp.More()) {
+ theShapeToBeSelected.reset(new GeomAPI_Shape);
+ theShapeToBeSelected->setImpl<TopoDS_Shape>(new TopoDS_Shape(aWireExp.Current()));
+ } else return false;
+ } else {
+ theShapeToBeSelected = aFoundFace;
+ }
+ return true;
+ }
+ } else if (aType == TopAbs_WIRE) { // sketch faces is identified by format "Sketch_1/Face-2f-8f-11r"
+ std::map<int, int> anIDs;
+ if (!parseSubIndices(aComposite, aSubShapeName, "Wire", anIDs))
+ return false;
+
+ NCollection_DataMap<Handle(Geom_Curve), int> allCurves; // curves and orientations of edges
+ const int aSubNum = aComposite->numberOfSubs();
+ for(int a = 0; a < aSubNum; a++) {
+ int aSubID = aComposite->subFeatureId(a);
+ if (anIDs.find(aSubID) != anIDs.end()) {
+ FeaturePtr aSub = aComposite->subFeature(a);
+ const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = aSub->results();
+ std::list<std::shared_ptr<ModelAPI_Result> >::const_iterator aRes;
+ for(aRes = aResults.cbegin(); aRes != aResults.cend(); aRes++) {
+ ResultConstructionPtr aConstr =
+ std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aRes);
+ if (aConstr->shape() && aConstr->shape()->isEdge()) {
+ const TopoDS_Shape& aResShape = aConstr->shape()->impl<TopoDS_Shape>();
+ TopoDS_Edge anEdge = TopoDS::Edge(aResShape);
+ if (!anEdge.IsNull()) {
+ Standard_Real aFirst, aLast;
+ Handle(Geom_Curve) aCurve = BRep_Tool::Curve(anEdge, aFirst, aLast);
+ allCurves.Bind(aCurve, anIDs[aSubID] > 0 ? 1 : -1);
+ }
+ }
+ }
+ }
+ }
+ std::shared_ptr<GeomAPI_Shape> aFoundFace = findAppropriateFace(aConstr, allCurves);
+ if (aFoundFace.get()) {
+ theShapeToBeSelected = aFoundFace;
+ return true;
+ }
+ }
+ }
+ }
}
return false;
}
-
#include <Model_Document.h>
#include <TDF_Label.hxx>
#include <TopoDS_Shape.hxx>
+#include <NCollection_DataMap.hxx>
+#include <Geom_Curve.hxx>
+#include <TopoDS_Edge.hxx>
/**\class Model_SelectionNaming
* \ingroup DataModel
std::shared_ptr<Model_Document> theDoc, std::shared_ptr<GeomAPI_Shape>& theShapeToBeSelected,
std::shared_ptr<ModelAPI_Result>& theCont);
+ /// Searches the face more appropriate to the given curves (with higher level of matched parameters)
+ /// \param theConstr construction result that contains one or several faces
+ /// \param theCurves map from the face edges curves to orientation (-1 reversed, 0 unknown, 1 forward)
+ /// \returns faces fron this construction if found
+ static std::shared_ptr<GeomAPI_Shape> findAppropriateFace(
+ std::shared_ptr<ModelAPI_Result>& theConstr,
+ NCollection_DataMap<Handle(Geom_Curve), int>& theCurves);
+
+ /// Returns orientation of the edge in the context shape
+ static int edgeOrientation(const TopoDS_Shape& theContext, TopoDS_Edge& theEdge);
+
+ /// Returns the name of sketch sub-element, shortened by exclusion of some symbols and with added
+ /// the vertex position (if needed)
+ /// \param theConstr result with name - basis for the name
+ /// \param theEdgeVertexPos position of the vertex on edge: 1 - first , 2 - second
+ /// \returns the generated name
+ static std::string shortName(std::shared_ptr<ModelAPI_ResultConstruction>& theConstr,
+ const int theEdgeVertexPos = 0);
+
protected:
/// Gets the stored name from the document
- std::string getShapeName(std::shared_ptr<Model_Document> theDoc, const TopoDS_Shape& theShape);
+ std::string getShapeName(std::shared_ptr<Model_Document> theDoc, const TopoDS_Shape& theShape,
+ const bool theAddContextName);
};
#endif
static const Events_ID kPreviewBlockedEvent = aLoop->eventByName(EVENT_PREVIEW_BLOCKED);
static const Events_ID kPreviewRequestedEvent = aLoop->eventByName(EVENT_PREVIEW_REQUESTED);
static const Events_ID kReorderEvent = aLoop->eventByName(EVENT_ORDER_UPDATED);
+ static const Events_ID kRedisplayEvent = aLoop->eventByName(EVENT_OBJECT_TO_REDISPLAY);
#ifdef DEB_UPDATE
std::cout<<"****** Event "<<theMessage->eventID().eventText()<<std::endl;
const std::set<ObjectPtr>& anObjs = aMsg->objects();
std::set<ObjectPtr>::const_iterator anObjIter = anObjs.cbegin();
for(; anObjIter != anObjs.cend(); anObjIter++) {
- if (std::dynamic_pointer_cast<Model_Document>((*anObjIter)->document())->executeFeatures())
- ModelAPI_EventCreator::get()->sendUpdated(*anObjIter, kUpdatedEvent);
+ if (std::dynamic_pointer_cast<Model_Document>((*anObjIter)->document())->executeFeatures()) {
+ if ((*anObjIter)->groupName() == ModelAPI_Feature::group()) { // results creation means enabling, not update
+ ModelAPI_EventCreator::get()->sendUpdated(*anObjIter, kUpdatedEvent);
+ } else {
+ ModelAPI_EventCreator::get()->sendUpdated(*anObjIter, kRedisplayEvent);
+ }
+ }
}
return;
}
// the redisplay signal should be flushed in order to erase the feature presentation in the viewer
// if should be done after removeFeature() of document,
// by this reason, upper processFeatures() do not perform this flush
- Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_TO_REDISPLAY));
+ Events_Loop::loop()->flush(kRedisplayEvent);
// in the end of transaction everything is updated, so clear the old objects
myIsParamUpdated = false;
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aSession.finishOperation()
assert(aSession.moduleDocument().size("Parts") == 0)
assert(aSession.activeDocument())
+
+import model
+assert(model.checkPythonDump())
aPartSet = aSession.moduleDocument()
aSession.startOperation()
aSketchFeature = featureToCompositeFeature(aPartSet.addFeature("Sketch"))
+aXOYPlane = objectToResult(aPartSet.objectByName("Construction", "XOY"))
+aSketchFeature.selection("External").setValue(aXOYPlane, None)
aFeatureData = aSketchFeature.data()
anArray = aFeatureData.addAttribute("IntArray_1", "IntArray")
aFeatureData.intArray("IntArray_1").setSize(5)
+aSession.finishOperation()
+
assert(aFeatureData.intArray("IntArray_1").size() == 5)
#=========================================================================
#=========================================================================
aPartSet = aSession.moduleDocument()
aSession.startOperation()
-aPlaneX = aPartSet.objectByName("Construction", "YOZ");
+aPlaneX = aPartSet.addFeature("Plane")
+aPlaneX.string("creation_method").setValue("by_general_equation")
+aPlaneX.real("A").setValue(1.)
+aPlaneX.real("B").setValue(0.)
+aPlaneX.real("C").setValue(0.)
+aPlaneX.real("D").setValue(0.)
assert(aPlaneX)
-aColors = aPlaneX.data().intArray("Color")
+aSession.finishOperation()
+
+aSession.startOperation()
+aColors = aPlaneX.lastResult().data().intArray("Color")
assert(aColors)
# default colors, not filled array
assert(aColors.size() == 0)
assert(aColors.value(0) == 100)
assert(aColors.value(1) == 200)
assert(aColors.value(2) == 250)
-
aSession.finishOperation()
+import model
+assert(model.checkPythonDump())
assert(aDoc.size("Construction") == 8)\r
assert(aSession.canUndo())\r
assert(not aSession.canRedo())\r
+\r
+import model\r
+assert(model.checkPythonDump())\r
__updated__ = "2016-07-20"
aSession = ModelAPI_Session.get()
+
+import model
+assert(model.checkPythonDump())
SET(PROJECT_HEADERS
ModelHighAPI.h
ModelHighAPI_Double.h
+ ModelHighAPI_Dumper.h
ModelHighAPI_Integer.h
ModelHighAPI_Interface.h
ModelHighAPI_Macro.h
ModelHighAPI_Selection.h
ModelHighAPI_Services.h
ModelHighAPI_Tools.h
+ ModelHighAPI_FeatureStore.h
)
SET(PROJECT_SOURCES
ModelHighAPI_Double.cpp
+ ModelHighAPI_Dumper.cpp
ModelHighAPI_Integer.cpp
ModelHighAPI_Interface.cpp
ModelHighAPI_RefAttr.cpp
ModelHighAPI_Selection.cpp
ModelHighAPI_Services.cpp
ModelHighAPI_Tools.cpp
+ ModelHighAPI_FeatureStore.cpp
)
SET(PROJECT_LIBRARIES
Events
GeomAPI
GeomDataAPI
+ GeomAlgoAPI
ModelAPI
)
-ADD_DEFINITIONS(-DMODELHIGHAPI_EXPORTS)
+ADD_DEFINITIONS(-DMODELHIGHAPI_EXPORTS -DWNT)
ADD_LIBRARY(ModelHighAPI SHARED ${PROJECT_SOURCES} ${PROJECT_HEADERS})
#TODO(spo): is it necessary?
SET_TARGET_PROPERTIES(ModelHighAPI PROPERTIES LINKER_LANGUAGE CXX)
)
INCLUDE_DIRECTORIES(
+ ${PROJECT_SOURCE_DIR}/src/Config
${PROJECT_SOURCE_DIR}/src/Events
${PROJECT_SOURCE_DIR}/src/GeomAPI
+ ${PROJECT_SOURCE_DIR}/src/GeomAlgoAPI
${PROJECT_SOURCE_DIR}/src/GeomDataAPI
${PROJECT_SOURCE_DIR}/src/ModelAPI
+ ${PROJECT_SOURCE_DIR}/src/PartSetPlugin
+ ${CAS_INCLUDE_DIRS}
)
set(SWIG_MODULE_ModelHighAPI_EXTRA_DEPS
/* ModelHighAPI.i */
-%module ModelHighAPI
+%module(directors="1") ModelHighAPI
+%feature("director:except") {
+ if ($error != NULL) {
+ PyErr_Print();
+ std::cerr << std::endl;
+ throw Swig::DirectorMethodException();
+ }
+}
%{
#include "ModelHighAPI_swig.h"
%include "std_string.i"
%include "std_shared_ptr.i"
+// directors
+%feature("director") ModelHighAPI_Dumper;
+
// shared pointers
%shared_ptr(ModelHighAPI_Interface)
}
}
+%typecheck(SWIG_TYPECHECK_POINTER) ModelHighAPI_RefAttr, const ModelHighAPI_RefAttr & {
+ std::shared_ptr<ModelAPI_Attribute> * temp_attribute;
+ std::shared_ptr<ModelAPI_Object> * temp_object;
+ std::shared_ptr<ModelHighAPI_Interface> * temp_interface;
+ int newmem = 0;
+ if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_attribute, $descriptor(std::shared_ptr<ModelAPI_Attribute> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (temp_attribute) {
+ $1 = 1;
+ } else {
+ $1 = 0;
+ }
+ } else if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_object, $descriptor(std::shared_ptr<ModelAPI_Object> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (temp_object) {
+ $1 = 1;
+ } else {
+ $1 = 0;
+ }
+ } else if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_interface, $descriptor(std::shared_ptr<ModelHighAPI_Interface> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (temp_interface) {
+ $1 = 1;
+ } else {
+ $1 = 0;
+ }
+ } else {
+ $1 = 0;
+ }
+}
+
%typemap(in) const ModelHighAPI_Reference & (ModelHighAPI_Reference temp) {
std::shared_ptr<ModelAPI_Object> * temp_object;
std::shared_ptr<ModelHighAPI_Interface> * temp_interface;
%template(RefAttrList) std::list<ModelHighAPI_RefAttr>;
%template(RefList) std::list<ModelHighAPI_Reference>;
+// fix compilarion error: ‘res*’ was not declared in this scope
+%typemap(freearg) const std::list<ModelHighAPI_RefAttr> & {}
+%typemap(freearg) const std::list<std::shared_ptr<ModelAPI_Object> > & {}
+
+%typemap(in) const std::list<ModelHighAPI_RefAttr> & (std::list<ModelHighAPI_RefAttr> temp) {
+ std::shared_ptr<ModelAPI_Attribute> * temp_attribute;
+ int newmem = 0;
+ if (PySequence_Check($input)) {
+ for (Py_ssize_t i = 0; i < PySequence_Size($input); ++i) {
+ PyObject * item = PySequence_GetItem($input, i);
+ if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_attribute, $descriptor(std::shared_ptr<ModelAPI_Attribute> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_attribute) {
+ PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_RefAttr, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ return NULL;
+ }
+ temp.push_back(ModelHighAPI_RefAttr(*temp_attribute));
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_attribute;
+ }
+ }
+ Py_DECREF(item);
+ }
+ $1 = &temp;
+ } else {
+ PyErr_SetString(PyExc_ValueError, "argument must be list of ModelHighAPI_RefAttr, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ return NULL;
+ }
+}
+
+%typemap(in) const std::list<std::shared_ptr<ModelAPI_Object> > & (std::list<std::shared_ptr<ModelAPI_Object> > temp) {
+ std::shared_ptr<ModelAPI_Object> * temp_object;
+ std::shared_ptr<ModelHighAPI_Interface> * temp_interface;
+ int newmem = 0;
+ if (PySequence_Check($input)) {
+ for (Py_ssize_t i = 0; i < PySequence_Size($input); ++i) {
+ PyObject * item = PySequence_GetItem($input, i);
+ if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_object, $descriptor(std::shared_ptr<ModelAPI_Object> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_object) {
+ PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_Interface or ModelAPI_Object.");
+ return NULL;
+ }
+ temp.push_back(*temp_object);
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_object;
+ }
+ } else
+ if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_interface, $descriptor(std::shared_ptr<ModelHighAPI_Interface> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_interface) {
+ PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_Interface or ModelAPI_Object.");
+ return NULL;
+ }
+ temp.push_back((*temp_interface)->defaultResult());
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_interface;
+ }
+ }
+ Py_DECREF(item);
+ }
+ $1 = &temp;
+ } else {
+ PyErr_SetString(PyExc_ValueError, "argument must be list of ModelHighAPI_Interface or ModelAPI_Object.");
+ return NULL;
+ }
+}
+
+%typecheck(SWIG_TYPECHECK_POINTER) std::list<std::shared_ptr<ModelAPI_Object> >, const std::list<std::shared_ptr<ModelAPI_Object> >& {
+ std::shared_ptr<ModelAPI_Object> * temp_object;
+ std::shared_ptr<ModelHighAPI_Interface> * temp_interface;
+ int newmem = 0;
+ if (PySequence_Check($input)) {
+ for (Py_ssize_t i = 0; i < PySequence_Size($input); ++i) {
+ PyObject * item = PySequence_GetItem($input, i);
+ if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_object, $descriptor(std::shared_ptr<ModelAPI_Object> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (temp_object) {
+ $1 = 1;
+ } else {
+ $1 = 0;
+ break;
+ }
+ } else
+ if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_interface, $descriptor(std::shared_ptr<ModelHighAPI_Interface> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (temp_interface) {
+ $1 = 1;
+ } else {
+ $1 = 0;
+ break;
+ }
+ }
+ Py_DECREF(item);
+ }
+ } else {
+ $1 = 0;
+ }
+}
+
// all supported interfaces
%include "ModelHighAPI_Double.h"
+%include "ModelHighAPI_Dumper.h"
%include "ModelHighAPI_Integer.h"
%include "ModelHighAPI_Interface.h"
%include "ModelHighAPI_RefAttr.h"
--- /dev/null
+// Copyright (C) 2016-20xx CEA/DEN, EDF R&D -->
+
+// File: ModelHighAPI_Dumper.cpp
+// Created: 1 August 2016
+// Author: Artem ZHIDKOV
+
+//--------------------------------------------------------------------------------------
+#include "ModelHighAPI_Dumper.h"
+
+#include <GeomAPI_Pnt.h>
+#include <GeomAPI_Dir.h>
+
+#include <GeomDataAPI_Dir.h>
+#include <GeomDataAPI_Point.h>
+#include <GeomDataAPI_Point2D.h>
+
+#include <ModelAPI_AttributeBoolean.h>
+#include <ModelAPI_AttributeDouble.h>
+#include <ModelAPI_AttributeIntArray.h>
+#include <ModelAPI_AttributeInteger.h>
+#include <ModelAPI_AttributeRefAttr.h>
+#include <ModelAPI_AttributeRefAttrList.h>
+#include <ModelAPI_AttributeReference.h>
+#include <ModelAPI_AttributeRefList.h>
+#include <ModelAPI_AttributeSelection.h>
+#include <ModelAPI_AttributeSelectionList.h>
+#include <ModelAPI_AttributeString.h>
+#include <ModelAPI_CompositeFeature.h>
+#include <ModelAPI_Document.h>
+#include <ModelAPI_Entity.h>
+#include <ModelAPI_Feature.h>
+#include <ModelAPI_Result.h>
+#include <ModelAPI_ResultPart.h>
+
+#include <PartSetPlugin_Part.h>
+
+#include <OSD_OpenFile.hxx>
+
+#include <fstream>
+
+static int gCompositeStackDepth = 0;
+
+ModelHighAPI_Dumper* ModelHighAPI_Dumper::mySelf = 0;
+
+ModelHighAPI_Dumper::ModelHighAPI_Dumper()
+{
+ clear();
+}
+
+void ModelHighAPI_Dumper::setInstance(ModelHighAPI_Dumper* theDumper)
+{
+ if (mySelf == 0)
+ mySelf = theDumper;
+}
+
+ModelHighAPI_Dumper* ModelHighAPI_Dumper::getInstance()
+{
+ return mySelf;
+}
+
+void ModelHighAPI_Dumper::clear(bool bufferOnly)
+{
+ myDumpBuffer.str("");
+ myDumpBuffer << std::setprecision(16);
+
+ clearNotDumped();
+
+ if (!bufferOnly) {
+ myFullDump.str("");
+ myFullDump << std::setprecision(16);
+
+ myNames.clear();
+ myModules.clear();
+ myFeatureCount.clear();
+ while (!myEntitiesStack.empty())
+ myEntitiesStack.pop();
+ }
+}
+
+void ModelHighAPI_Dumper::clearNotDumped()
+{
+ myNotDumpedEntities.clear();
+}
+
+const std::string& ModelHighAPI_Dumper::name(const EntityPtr& theEntity,
+ bool theSaveNotDumped,
+ bool theUseEntityName)
+{
+ EntityNameMap::const_iterator aFound = myNames.find(theEntity);
+ if (aFound != myNames.end())
+ return aFound->second.myCurrentName;
+
+ // entity is not found, store it
+ std::string aName;
+ bool isDefaultName = false;
+ std::ostringstream aDefaultName;
+ FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(theEntity);
+ if (aFeature) {
+ aName = aFeature->name();
+ const std::string& aKind = aFeature->getKind();
+ DocumentPtr aDoc = aFeature->document();
+ int& aNbFeatures = myFeatureCount[aDoc][aKind];
+ aNbFeatures += 1;
+
+ size_t anIndex = aName.find(aKind);
+ if (anIndex == 0 && aName[aKind.length()] == '_') { // name starts with "FeatureKind_"
+ std::string anIdStr = aName.substr(aKind.length() + 1);
+ int anId = std::stoi(anIdStr);
+
+ // Check number of already registered objects of such kind. Index of current object
+ // should be the same to identify feature's name as automatically generated.
+ if (aNbFeatures == anId) {
+ // name is not user-defined
+ aName.clear();
+ isDefaultName = true;
+ }
+ }
+
+ // obtain default name for the feature
+ if (theUseEntityName)
+ aDefaultName << aName;
+ else {
+ int aFullIndex = 0;
+ NbFeaturesMap::const_iterator aFIt = myFeatureCount.begin();
+ for (; aFIt != myFeatureCount.end(); ++aFIt) {
+ std::map<std::string, int>::const_iterator aFound = aFIt->second.find(aKind);
+ if (aFound != aFIt->second.end())
+ aFullIndex += aFound->second;
+ }
+ aDefaultName << aKind << "_" << aFullIndex;
+ }
+ }
+
+ myNames[theEntity] = EntityName(aDefaultName.str(), aName, isDefaultName);
+ if (theSaveNotDumped)
+ myNotDumpedEntities.insert(theEntity);
+
+ // store names of results
+ if (aFeature)
+ saveResultNames(aFeature);
+
+ return myNames[theEntity].myCurrentName;
+}
+
+const std::string& ModelHighAPI_Dumper::parentName(const FeaturePtr& theEntity)
+{
+ const std::set<AttributePtr>& aRefs = theEntity->data()->refsToMe();
+ std::set<AttributePtr>::const_iterator aRefIt = aRefs.begin();
+ for (; aRefIt != aRefs.end(); ++aRefIt) {
+ CompositeFeaturePtr anOwner = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(
+ ModelAPI_Feature::feature((*aRefIt)->owner()));
+ if (anOwner)
+ return name(anOwner);
+ }
+
+ static const std::string DUMMY;
+ return DUMMY;
+}
+
+void ModelHighAPI_Dumper::saveResultNames(const FeaturePtr& theFeature)
+{
+ const std::string& aFeatureName = myNames[theFeature].myCurrentName;
+ const std::list<ResultPtr>& aResults = theFeature->results();
+ std::list<ResultPtr>::const_iterator aResIt = aResults.begin();
+ for (int i = 1; aResIt != aResults.end(); ++aResIt, ++i) {
+ bool isUserDefined = true;
+ std::string aResName = (*aResIt)->data()->name();
+ size_t anIndex = aResName.find(aFeatureName);
+ if (anIndex == 0) {
+ std::string aSuffix = aResName.substr(aFeatureName.length());
+ if (aSuffix.empty() && i == 1) // first result may not constain index in the name
+ isUserDefined = false;
+ else {
+ if (aSuffix[0] == '_' && std::stoi(aSuffix.substr(1)) == i)
+ isUserDefined = false;
+ }
+ }
+
+ myNames[*aResIt] = EntityName(aResName,
+ (isUserDefined ? aResName : std::string()), !isUserDefined);
+ }
+}
+
+bool ModelHighAPI_Dumper::process(const std::shared_ptr<ModelAPI_Document>& theDoc,
+ const std::string& theFileName)
+{
+ // dump top level document feature
+ static const std::string aDocName("partSet");
+ myNames[theDoc] = EntityName(aDocName, std::string(), true);
+ *this << aDocName << " = model.moduleDocument()" << std::endl;
+
+ // dump subfeatures and store result to file
+ return process(theDoc) && exportTo(theFileName);
+}
+
+bool ModelHighAPI_Dumper::process(const std::shared_ptr<ModelAPI_Document>& theDoc)
+{
+ bool isOk = true;
+ std::list<FeaturePtr> aFeatures = theDoc->allFeatures();
+ std::list<FeaturePtr>::const_iterator aFeatIt = aFeatures.begin();
+ // firstly, dump all parameters
+ for (; aFeatIt != aFeatures.end(); ++ aFeatIt)
+ dumpParameter(*aFeatIt);
+ // dump all other features
+ for (aFeatIt = aFeatures.begin(); aFeatIt != aFeatures.end(); ++aFeatIt) {
+ CompositeFeaturePtr aCompFeat = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(*aFeatIt);
+ if (aCompFeat) // iteratively process composite features
+ isOk = process(aCompFeat) && isOk;
+ else if (!isDumped(*aFeatIt)) // dump common feature
+ dumpFeature(*aFeatIt);
+ }
+ return isOk;
+}
+
+bool ModelHighAPI_Dumper::process(const std::shared_ptr<ModelAPI_CompositeFeature>& theComposite, bool isForce)
+{
+ // increase composite features stack
+ ++gCompositeStackDepth;
+ // dump composite itself
+ if (!isDumped(theComposite) || isForce)
+ dumpFeature(theComposite, isForce);
+
+ // sub-part is processed independently, because it provides separate document
+ if (theComposite->getKind() == PartSetPlugin_Part::ID()) {
+ // decrease composite features stack because we run into separate document
+ --gCompositeStackDepth;
+
+ ResultPartPtr aPartResult =
+ std::dynamic_pointer_cast<ModelAPI_ResultPart>(theComposite->lastResult());
+ if (!aPartResult)
+ return false;
+ DocumentPtr aSubDoc = aPartResult->partDoc();
+ if (!aSubDoc)
+ return false;
+ // set name of document
+ const std::string& aPartName = myNames[theComposite].myCurrentName;
+ std::string aDocName = aPartName + "_doc";
+ myNames[aSubDoc] = EntityName(aDocName, std::string(), true);
+
+ // dump document in a separate line
+ *this << aDocName << " = " << aPartName << ".document()" << std::endl;
+ // dump features in the document
+ return process(aSubDoc);
+ }
+
+ // dump sub-features
+ bool isOk = processSubs(theComposite);
+ // decrease composite features stack
+ --gCompositeStackDepth;
+
+ return isOk;
+}
+
+bool ModelHighAPI_Dumper::processSubs(const std::shared_ptr<ModelAPI_CompositeFeature>& theComposite,
+ bool theDumpModelDo)
+{
+ bool isOk = true;
+ // dump all sub-features;
+ bool isSubDumped = false;
+ int aNbSubs = theComposite->numberOfSubs();
+ for (int anIndex = 0; anIndex < aNbSubs; ++anIndex) {
+ FeaturePtr aFeature = theComposite->subFeature(anIndex);
+ if (isDumped(aFeature))
+ continue;
+
+ isSubDumped = true;
+ CompositeFeaturePtr aCompFeat = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(aFeature);
+ if (aCompFeat) // iteratively process composite features
+ isOk = process(aCompFeat) && isOk;
+ else
+ dumpFeature(aFeature, true);
+ }
+
+ bool isDumpSetName = !myEntitiesStack.empty() &&
+ myEntitiesStack.top().myEntity == EntityPtr(theComposite);
+ bool isForceModelDo = isSubDumped && isDumpSetName &&
+ (myEntitiesStack.top().myUserName || !myEntitiesStack.top().myResults.empty());
+ // It is necessary for the sketch to create its result when complete (command "model.do()").
+ // This option is set by flat theDumpModelDo.
+ // However, nested sketches are rebuilt by parent feature, so, they do not need
+ // explicit call of "model.do()". This will be controlled by the depth of the stack.
+ if (isForceModelDo || (theDumpModelDo && gCompositeStackDepth <= 1))
+ *this << "model.do()" << std::endl;
+
+ // dump "setName" for composite feature
+ if (isDumpSetName)
+ dumpEntitySetName();
+ return isOk;
+}
+
+void ModelHighAPI_Dumper::dumpSubFeatureNameAndColor(const std::string theSubFeatureGet,
+ const FeaturePtr& theSubFeature)
+{
+ name(theSubFeature, false);
+ myNames[theSubFeature] = EntityName(theSubFeatureGet, theSubFeature->name(), false);
+
+ // store results if they have user-defined names or colors
+ std::list<ResultPtr> aResultsWithNameOrColor;
+ const std::list<ResultPtr>& aResults = theSubFeature->results();
+ std::list<ResultPtr>::const_iterator aResIt = aResults.begin();
+ for (; aResIt != aResults.end(); ++aResIt) {
+ std::string aResName = (*aResIt)->data()->name();
+ myNames[*aResIt] = EntityName(aResName, aResName, false);
+ aResultsWithNameOrColor.push_back(*aResIt);
+ }
+
+ // store just dumped entity to stack
+ myEntitiesStack.push(LastDumpedEntity(theSubFeature, true, aResultsWithNameOrColor));
+
+ dumpEntitySetName();
+}
+
+bool ModelHighAPI_Dumper::exportTo(const std::string& theFileName)
+{
+ std::ofstream aFile;
+ OSD_OpenStream(aFile, theFileName.c_str(), std::ofstream::out);
+ if (!aFile.is_open())
+ return false;
+
+ // standard header
+ for (ModulesMap::const_iterator aModIt = myModules.begin();
+ aModIt != myModules.end(); ++aModIt) {
+ aFile << "from " << aModIt->first << " import ";
+ if (aModIt->second.empty() ||
+ aModIt->second.find(std::string()) != aModIt->second.end())
+ aFile << "*"; // import whole module
+ else {
+ // import specific features
+ std::set<std::string>::const_iterator anObjIt = aModIt->second.begin();
+ aFile << *anObjIt;
+ for (++anObjIt; anObjIt != aModIt->second.end(); ++anObjIt)
+ aFile << ", " << *anObjIt;
+ }
+ aFile << std::endl;
+ }
+ if (!myModules.empty())
+ aFile << std::endl;
+
+ aFile << "import model" << std::endl << std::endl;
+ aFile << "model.begin()" << std::endl;
+
+ // dump collected data
+ aFile << myFullDump.str();
+ aFile << myDumpBuffer.str();
+
+ // standard footer
+ aFile << "model.end()" << std::endl;
+
+ aFile.close();
+ clear();
+
+ return true;
+}
+
+void ModelHighAPI_Dumper::importModule(const std::string& theModuleName,
+ const std::string& theObject)
+{
+ myModules[theModuleName].insert(theObject);
+}
+
+void ModelHighAPI_Dumper::dumpEntitySetName()
+{
+ const LastDumpedEntity& aLastDumped = myEntitiesStack.top();
+
+ // dump "setName" for the entity
+ if (aLastDumped.myUserName) {
+ EntityName& anEntityNames = myNames[aLastDumped.myEntity];
+ if (!anEntityNames.myIsDefault)
+ myDumpBuffer << anEntityNames.myCurrentName << ".setName(\""
+ << anEntityNames.myUserName << "\")" << std::endl;
+ // don't dump "setName" for the entity twice
+ anEntityNames.myUserName.clear();
+ anEntityNames.myIsDefault = true;
+ }
+ // dump "setName" for results
+ std::list<ResultPtr>::const_iterator aResIt = aLastDumped.myResults.begin();
+ std::list<ResultPtr>::const_iterator aResEnd = aLastDumped.myResults.end();
+ for (; aResIt != aResEnd; ++aResIt) {
+ // set result name
+ EntityName& anEntityNames = myNames[*aResIt];
+ if (!anEntityNames.myIsDefault) {
+ *this << *aResIt;
+ myDumpBuffer << ".setName(\"" << anEntityNames.myUserName << "\")" << std::endl;
+ // don't dump "setName" for the entity twice
+ anEntityNames.myUserName.clear();
+ anEntityNames.myIsDefault = true;
+ }
+ // set result color
+ if (!isDefaultColor(*aResIt)) {
+ AttributeIntArrayPtr aColor = (*aResIt)->data()->intArray(ModelAPI_Result::COLOR_ID());
+ if (aColor && aColor->isInitialized()) {
+ *this << *aResIt;
+ myDumpBuffer << ".setColor(" << aColor->value(0) << ", " << aColor->value(1)
+ << ", " << aColor->value(2) << ")" << std::endl;
+ }
+ }
+ }
+
+ myEntitiesStack.pop();
+}
+
+bool ModelHighAPI_Dumper::isDumped(const EntityPtr& theEntity) const
+{
+ EntityNameMap::const_iterator aFound = myNames.find(theEntity);
+ return aFound != myNames.end();
+}
+
+bool ModelHighAPI_Dumper::isDefaultColor(const ResultPtr& theResult) const
+{
+ AttributeIntArrayPtr aColor = theResult->data()->intArray(ModelAPI_Result::COLOR_ID());
+ if (!aColor || !aColor->isInitialized())
+ return true;
+
+ std::string aSection, aName, aDefault;
+ theResult->colorConfigInfo(aSection, aName, aDefault);
+
+ // dump current color
+ std::ostringstream aColorInfo;
+ aColorInfo << aColor->value(0) << "," << aColor->value(1) << "," << aColor->value(2);
+
+ return aDefault == aColorInfo.str();
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const char theChar)
+{
+ myDumpBuffer << theChar;
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const char* theString)
+{
+ myDumpBuffer << theString;
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const std::string& theString)
+{
+ myDumpBuffer << theString;
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const bool theValue)
+{
+ myDumpBuffer << (theValue ? "True" : "False");
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const int theValue)
+{
+ myDumpBuffer << theValue;
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const double theValue)
+{
+ myDumpBuffer << theValue;
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const std::shared_ptr<GeomAPI_Pnt>& thePoint)
+{
+ importModule("GeomAPI", "GeomAPI_Pnt");
+ myDumpBuffer << "GeomAPI_Pnt(" << thePoint->x() << ", "
+ << thePoint->y() << ", " << thePoint->z() << ")";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const std::shared_ptr<GeomAPI_Dir>& theDir)
+{
+ importModule("GeomAPI", "GeomAPI_Dir");
+ myDumpBuffer << "GeomAPI_Dir(" << theDir->x() << ", "
+ << theDir->y() << ", " << theDir->z() << ")";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<GeomDataAPI_Dir>& theDir)
+{
+ myDumpBuffer << theDir->x() << ", " << theDir->y() << ", " << theDir->z();
+ return *this;
+}
+
+static void dumpArray(std::ostringstream& theOutput, int theSize,
+ double* theValues, std::string* theTexts)
+{
+ for (int i = 0; i < theSize; ++i) {
+ if (i > 0)
+ theOutput << ", ";
+ if (theTexts[i].empty())
+ theOutput << theValues[i];
+ else
+ theOutput << "\"" << theTexts[i] << "\"";
+ }
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<GeomDataAPI_Point>& thePoint)
+{
+ static const int aSize = 3;
+ double aValues[aSize] = {thePoint->x(), thePoint->y(), thePoint->z()};
+ std::string aTexts[aSize] = {thePoint->textX(), thePoint->textY(), thePoint->textZ()};
+ dumpArray(myDumpBuffer, aSize, aValues, aTexts);
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<GeomDataAPI_Point2D>& thePoint)
+{
+ static const int aSize = 2;
+ double aValues[aSize] = {thePoint->x(), thePoint->y()};
+ std::string aTexts[aSize] = {thePoint->textX(), thePoint->textY()};
+ dumpArray(myDumpBuffer, aSize, aValues, aTexts);
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeBoolean>& theAttrBool)
+{
+ myDumpBuffer << (theAttrBool->value() ? "True" : "False");
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeInteger>& theAttrInt)
+{
+ std::string aText = theAttrInt->text();
+ if (aText.empty())
+ myDumpBuffer << theAttrInt->value();
+ else
+ myDumpBuffer << "\"" << aText << "\"";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeDouble>& theAttrReal)
+{
+ std::string aText = theAttrReal->text();
+ if (aText.empty())
+ myDumpBuffer << theAttrReal->value();
+ else
+ myDumpBuffer << "\"" << aText << "\"";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeString>& theAttrStr)
+{
+ myDumpBuffer << "\"" << theAttrStr->value() << "\"";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const FeaturePtr& theEntity)
+{
+ myDumpBuffer << name(theEntity);
+
+ bool isUserDefinedName = !myNames[theEntity].myIsDefault;
+ // store results if they have user-defined names or colors
+ std::list<ResultPtr> aResultsWithNameOrColor;
+ const std::list<ResultPtr>& aResults = theEntity->results();
+ std::list<ResultPtr>::const_iterator aResIt = aResults.begin();
+ for (; aResIt != aResults.end(); ++aResIt)
+ if (!myNames[*aResIt].myIsDefault || !isDefaultColor(*aResIt))
+ aResultsWithNameOrColor.push_back(*aResIt);
+ // store just dumped entity to stack
+ myEntitiesStack.push(LastDumpedEntity(theEntity, isUserDefinedName, aResultsWithNameOrColor));
+
+ // remove entity from the list of not dumped items
+ myNotDumpedEntities.erase(theEntity);
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const ResultPtr& theResult)
+{
+ FeaturePtr aFeature = ModelAPI_Feature::feature(theResult);
+ int anIndex = 0;
+ std::list<ResultPtr> aResults = aFeature->results();
+ for(std::list<ResultPtr>::const_iterator anIt = aResults.cbegin(); anIt != aResults.cend(); ++anIt, ++anIndex) {
+ if(theResult->isSame(*anIt)) {
+ break;
+ }
+ }
+ myDumpBuffer << name(aFeature) << ".result()[" << anIndex << "]";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const ObjectPtr& theObject)
+{
+ FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(theObject);
+ if(aFeature.get()) {
+ myDumpBuffer << name(aFeature);
+ return *this;
+ }
+
+ ResultPtr aResult = std::dynamic_pointer_cast<ModelAPI_Result>(theObject);
+ if(aResult.get()) {
+ *this << aResult;
+ return *this;
+ }
+
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(const AttributePtr& theAttr)
+{
+ FeaturePtr anOwner = ModelAPI_Feature::feature(theAttr->owner());
+ myDumpBuffer << name(anOwner) << "." << attributeGetter(anOwner, theAttr->id()) << "()";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeRefAttr>& theRefAttr)
+{
+ if (theRefAttr->isObject())
+ *this << theRefAttr->object();
+ else
+ *this << theRefAttr->attr();
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeRefAttrList>& theRefAttrList)
+{
+ myDumpBuffer << "[";
+ std::list<std::pair<ObjectPtr, AttributePtr> > aList = theRefAttrList->list();
+ bool isAdded = false;
+ std::list<std::pair<ObjectPtr, AttributePtr> >::const_iterator anIt = aList.begin();
+ for (; anIt != aList.end(); ++anIt) {
+ if (isAdded)
+ myDumpBuffer << ", ";
+ else
+ isAdded = true;
+ if (anIt->first)
+ *this << anIt->first;
+ else if (anIt->second)
+ * this << anIt->second;
+ }
+ myDumpBuffer << "]";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeReference>& theReference)
+{
+ *this << theReference->value();
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeRefList>& theRefList)
+{
+ static const int aThreshold = 2;
+ // if number of elements in the list if greater than a threshold,
+ // dump it in a separate line with specific name
+ std::string aDumped = myDumpBuffer.str();
+ if (aDumped.empty() || theRefList->size() <= aThreshold) {
+ myDumpBuffer << "[";
+ std::list<ObjectPtr> aList = theRefList->list();
+ bool isAdded = false;
+ std::list<ObjectPtr>::const_iterator anIt = aList.begin();
+ for (; anIt != aList.end(); ++anIt) {
+ if (isAdded)
+ myDumpBuffer << ", ";
+ else
+ isAdded = true;
+
+ *this << *anIt;
+ }
+ myDumpBuffer << "]";
+ } else {
+ // clear buffer and store list "as is"
+ myDumpBuffer.str("");
+ *this << theRefList;
+ // save buffer and clear it again
+ std::string aDumpedList = myDumpBuffer.str();
+ myDumpBuffer.str("");
+ // obtain name of list
+ FeaturePtr anOwner = ModelAPI_Feature::feature(theRefList->owner());
+ std::string aListName = name(anOwner) + "_objects";
+ // store all previous data
+ myDumpBuffer << aListName << " = " << aDumpedList << std::endl
+ << aDumped << aListName;
+ }
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeSelection>& theAttrSelect)
+{
+ myDumpBuffer << "model.selection(";
+
+ if(!theAttrSelect->isInitialized()) {
+ myDumpBuffer << ")";
+ return *this;
+ }
+
+ GeomShapePtr aShape = theAttrSelect->value();
+ if(!aShape.get()) {
+ aShape = theAttrSelect->context()->shape();
+ }
+
+ if(!aShape.get()) {
+ myDumpBuffer << ")";
+ return *this;
+ }
+
+ myDumpBuffer << "\"" << aShape->shapeTypeStr() << "\", \"" << theAttrSelect->namingName() << "\")";
+ return *this;
+}
+
+ModelHighAPI_Dumper& ModelHighAPI_Dumper::operator<<(
+ const std::shared_ptr<ModelAPI_AttributeSelectionList>& theAttrSelList)
+{
+ myDumpBuffer << "[";
+
+ GeomShapePtr aShape;
+ std::string aShapeTypeStr;
+
+ bool isAdded = false;
+
+ for(int anIndex = 0; anIndex < theAttrSelList->size(); ++anIndex) {
+ AttributeSelectionPtr anAttribute = theAttrSelList->value(anIndex);
+ aShape = anAttribute->value();
+ if(!aShape.get()) {
+ aShape = anAttribute->context()->shape();
+ }
+
+ if(!aShape.get()) {
+ continue;
+ }
+
+ if(isAdded) {
+ myDumpBuffer << ", ";
+ } else {
+ isAdded = true;
+ }
+ myDumpBuffer << "model.selection(\"" << aShape->shapeTypeStr() << "\", \"" << anAttribute->namingName() << "\")";
+ }
+
+ myDumpBuffer << "]";
+ return *this;
+}
+
+/// Dump std::endl
+MODELHIGHAPI_EXPORT
+ModelHighAPI_Dumper& operator<<(ModelHighAPI_Dumper& theDumper,
+ std::basic_ostream<char>& (*theEndl)(std::basic_ostream<char>&))
+{
+ theDumper.myDumpBuffer << theEndl;
+
+ if (!theDumper.myEntitiesStack.empty()) {
+ // Name for composite feature is dumped when all sub-entities are dumped
+ // (see method ModelHighAPI_Dumper::processSubs).
+ const ModelHighAPI_Dumper::LastDumpedEntity& aLastDumped = theDumper.myEntitiesStack.top();
+ CompositeFeaturePtr aComposite =
+ std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(aLastDumped.myEntity);
+ if (!aComposite)
+ theDumper.dumpEntitySetName();
+ }
+
+ // store all not-dumped entities first
+ std::set<EntityPtr> aNotDumped = theDumper.myNotDumpedEntities;
+ std::string aBufCopy = theDumper.myDumpBuffer.str();
+ theDumper.clear(true);
+ std::set<EntityPtr>::const_iterator anIt = aNotDumped.begin();
+ for (; anIt != aNotDumped.end(); ++anIt) {
+ // if the feature is composite, dump it with all subs
+ CompositeFeaturePtr aCompFeat =
+ std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(*anIt);
+ if (aCompFeat)
+ theDumper.process(aCompFeat, true);
+ else {
+ FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(*anIt);
+ theDumper.dumpFeature(aFeature, true);
+ }
+ }
+
+ // avoid multiple empty lines
+ size_t anInd = std::string::npos;
+ while ((anInd = aBufCopy.find("\n\n\n")) != std::string::npos)
+ aBufCopy.erase(anInd, 1);
+ // then store currently dumped string
+ theDumper.myFullDump << aBufCopy;
+
+ return theDumper;
+}
--- /dev/null
+// Copyright (C) 2016-20xx CEA/DEN, EDF R&D -->
+
+// File: ModelHighAPI_Dumper.h
+// Created: 1 August 2016
+// Author: Artem ZHIDKOV
+
+#ifndef ModelHighAPI_Dumper_H_
+#define ModelHighAPI_Dumper_H_
+
+#include "ModelHighAPI.h"
+
+#include <list>
+#include <map>
+#include <memory>
+#include <set>
+#include <sstream>
+#include <stack>
+#include <string>
+
+class GeomAPI_Pnt;
+class GeomAPI_Dir;
+
+class GeomDataAPI_Dir;
+class GeomDataAPI_Point;
+class GeomDataAPI_Point2D;
+
+class ModelAPI_Attribute;
+class ModelAPI_AttributeBoolean;
+class ModelAPI_AttributeDouble;
+class ModelAPI_AttributeInteger;
+class ModelAPI_AttributeRefAttr;
+class ModelAPI_AttributeRefAttrList;
+class ModelAPI_AttributeReference;
+class ModelAPI_AttributeRefList;
+class ModelAPI_AttributeSelection;
+class ModelAPI_AttributeSelectionList;
+class ModelAPI_AttributeString;
+class ModelAPI_CompositeFeature;
+class ModelAPI_Document;
+class ModelAPI_Entity;
+class ModelAPI_Feature;
+class ModelAPI_Object;
+class ModelAPI_Result;
+
+typedef std::shared_ptr<ModelAPI_Document> DocumentPtr;
+typedef std::shared_ptr<ModelAPI_Entity> EntityPtr;
+typedef std::shared_ptr<ModelAPI_Feature> FeaturePtr;
+typedef std::shared_ptr<ModelAPI_Result> ResultPtr;
+
+/**\class ModelHighAPI_Dumper
+ * \ingroup CPPHighAPI
+ * \brief Dump engine for the model
+ */
+class ModelHighAPI_Dumper
+{
+public:
+ /// Default constructor
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper();
+
+ /// Sets instance of a dumper
+ MODELHIGHAPI_EXPORT
+ static void setInstance(ModelHighAPI_Dumper* theDumper);
+
+ /// Returns instance of a dumper
+ MODELHIGHAPI_EXPORT
+ static ModelHighAPI_Dumper* getInstance();
+
+ /// Destructor
+ virtual ~ModelHighAPI_Dumper() {}
+
+ /// Dump given document into the file
+ /// \return \c true, if succeed
+ MODELHIGHAPI_EXPORT
+ bool process(const std::shared_ptr<ModelAPI_Document>& theDoc, const std::string& theFileName);
+
+ /// Add module to list of imported modules
+ /// \param theModuleName name of the module to be imported
+ /// \param theObject name of the entity to be imported from the module (if empty, while module will be imported)
+ MODELHIGHAPI_EXPORT
+ void importModule(const std::string& theModuleName,
+ const std::string& theObject = std::string());
+
+ /// Returns name of specified entity
+ /// \param theEntity [in] named entity
+ /// \param theSaveNotDumped [in] if \c true, the entity should be stored as not dumped (will be dumped automatically)
+ /// \param theUseEntityName [in] if \c true, the entity name should be used "as is" without changing default name
+ /// \return name of the entity
+ MODELHIGHAPI_EXPORT
+ const std::string& name(const EntityPtr& theEntity, bool theSaveNotDumped = true, bool theUseEntityName = false);
+
+ /// Returns name of parent composite feature for specified entity
+ MODELHIGHAPI_EXPORT
+ const std::string& parentName(const FeaturePtr& theFeature);
+
+ /// Dump parameter feature only
+ virtual void dumpParameter(const FeaturePtr& theFeature) = 0;
+ /// Dump given feature
+ virtual void dumpFeature(const FeaturePtr& theFeature, const bool theForce = false) = 0;
+
+ /// Dump sub-feature name and color, without dumping feature creation.
+ /// Used for features which creates sub-features in their execute method.
+ /// \param theSubFeatureGet [in] method for getting sub-feature (e.g. "Feature_1.subFeature(0)")
+ /// \param theSubFeature [in] sub-feature
+ MODELHIGHAPI_EXPORT
+ void dumpSubFeatureNameAndColor(const std::string theSubFeatureGet,
+ const FeaturePtr& theSubFeature);
+
+ /// Return name of getter for corresponding attribute
+ virtual std::string attributeGetter(const FeaturePtr& theFeature,
+ const std::string& theAttrName) const = 0;
+
+ /// Save all dumps into specified file
+ MODELHIGHAPI_EXPORT
+ bool exportTo(const std::string& theFileName);
+
+ /// Dump character
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const char theChar);
+ /// Dump string
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const char* theString);
+ /// Dump string
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::string& theString);
+ /// Dump boolean
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const bool theValue);
+ /// Dump integer
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const int theValue);
+ /// Dump real
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const double theValue);
+ /// Dump std::endl
+ friend
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(ModelHighAPI_Dumper& theDumper,
+ std::basic_ostream<char>& (*theEndl)(std::basic_ostream<char>&));
+
+ /// Dump GeomAPI_Pnt in the following form:
+ /// "GeomAPI_Pnt(X, Y, Z)"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<GeomAPI_Pnt>& thePoint);
+ /// Dump GeomAPI_Dir
+ /// "GeomAPI_Dir(X, Y, Z)"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<GeomAPI_Dir>& theDir);
+
+ /// Dump GeomDataAPI_Dir in the following form:
+ /// "X, Y, Z"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<GeomDataAPI_Dir>& theDir);
+ /// Dump GeomDataAPI_Point in the following form:
+ /// "X, Y, Z"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<GeomDataAPI_Point>& thePoint);
+ /// Dump GeomDataAPI_Point2D in the following form:
+ /// "X, Y"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<GeomDataAPI_Point2D>& thePoint);
+
+ /// Dump AttributeBoolean
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeBoolean>& theAttrBool);
+ /// Dump AttributeInteger
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeInteger>& theAttrInt);
+ /// Dump AttributeDouble
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeDouble>& theAttrReal);
+ /// Dump AttributeString
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeString>& theAttrStr);
+ /// Dump name of entity and remember to dump "setName" if the entity has user-defined name
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const FeaturePtr& theEntity);
+
+ /// Dump result
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const ResultPtr& theResult);
+
+ /// Dump Attribute
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_Attribute>& theAttr);
+ /// Dump Object
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_Object>& theObject);
+
+ /// Dump AttributeRefAttr
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeRefAttr>& theRefAttr);
+ /// Dump AttributeRefAttrList as follows:
+ /// "[obj1, obj2, obj3, ...]"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeRefAttrList>& theRefAttrList);
+ /// Dump AttributeRefList as follows:
+ /// "[obj1, obj2, obj3, ...]"
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeRefList>& theRefList);
+ /// Dump AttributeSelection
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeSelection>& theAttrSelect);
+ /// Dump AttributeSelectionList
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeSelectionList>& theAttrSelList);
+ /// Dump AttributeReference
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Dumper& operator<<(const std::shared_ptr<ModelAPI_AttributeReference>& theReference);
+
+ /// Clear dump buffer
+ MODELHIGHAPI_EXPORT
+ void clear(bool bufferOnly = false);
+ /// clear list of not dumped entities
+ MODELHIGHAPI_EXPORT void clearNotDumped();
+
+protected:
+ /// Dump "setName" command if last entity had user-defined name
+ MODELHIGHAPI_EXPORT void dumpEntitySetName();
+
+private:
+ ModelHighAPI_Dumper(const ModelHighAPI_Dumper&);
+ const ModelHighAPI_Dumper& operator=(const ModelHighAPI_Dumper&);
+
+ /// Iterate all features in document and dump them into intermediate buffer
+ bool process(const std::shared_ptr<ModelAPI_Document>& theDoc);
+
+ /// Dump composite feature and all it sub-features
+ bool process(const std::shared_ptr<ModelAPI_CompositeFeature>& theComposite, bool isForce = false);
+
+ /// Iterate all features in composite feature and dump them into intermediate buffer
+ /// \param theComposite [in] parent composite feature
+ /// \param theDumpModelDo [in] shows that command "model.do()" should be written at the end
+ MODELHIGHAPI_EXPORT
+ bool processSubs(const std::shared_ptr<ModelAPI_CompositeFeature>& theComposite, bool theDumpModelDo = false);
+
+ /// Check the entity is already dumped
+ bool isDumped(const EntityPtr& theEntity) const;
+
+ /// Stores names of results for the given feature
+ void saveResultNames(const FeaturePtr& theFeature);
+
+ /// Check the result feature has default color
+ bool isDefaultColor(const ResultPtr& theResult) const;
+
+private:
+ struct EntityName {
+ std::string myCurrentName; ///< default name of current feature
+ std::string myUserName; ///< user-defined name
+ bool myIsDefault; ///< \c true if the name is default
+
+ EntityName() {}
+
+ EntityName(const std::string& theCurName, const std::string& theUserName, bool theDefault)
+ : myCurrentName(theCurName), myUserName(theUserName), myIsDefault(theDefault)
+ {}
+ };
+
+ typedef std::map<EntityPtr, EntityName> EntityNameMap;
+ typedef std::map<std::string, std::set<std::string> > ModulesMap;
+ typedef std::map<DocumentPtr, std::map<std::string, int> > NbFeaturesMap;
+
+ struct LastDumpedEntity {
+ EntityPtr myEntity; ///< last dumped entity
+ bool myUserName; ///< the entity hase user-defined name
+ std::list<ResultPtr> myResults; ///< results of this entity, which has user-defined names or specific colors
+
+ LastDumpedEntity(EntityPtr theEntity, bool theUserName, const std::list<ResultPtr>& theResults)
+ : myEntity(theEntity), myUserName(theUserName), myResults(theResults)
+ {}
+ };
+ typedef std::stack<LastDumpedEntity> DumpStack;
+
+ static ModelHighAPI_Dumper* mySelf;
+
+ std::ostringstream myDumpBuffer; ///< intermediate buffer to store dumping data
+ std::ostringstream myFullDump; ///< full buffer of dumped data
+
+ ModulesMap myModules; ///< modules and entities to be imported
+ EntityNameMap myNames; ///< names of the entities
+ DumpStack myEntitiesStack; ///< stack of dumped entities
+
+ NbFeaturesMap myFeatureCount; ///< number of features of each kind
+
+protected:
+ std::set<EntityPtr> myNotDumpedEntities; ///< list of entities, used by other features but not dumped yet
+
+ friend class SketchAPI_Sketch;
+};
+
+#endif
--- /dev/null
+// Copyright (C) 2016-20xx CEA/DEN, EDF R&D -->
+
+// File: ModelHighAPI_FeatureStore.cpp
+// Created: 12 August 2016
+// Author: Mikhail PONIKAROV
+
+#include <ModelHighAPI_FeatureStore.h>
+
+#include <ModelAPI_Tools.h>
+#include <ModelAPI_ResultPart.h>
+#include <ModelAPI_Session.h>
+#include <ModelAPI_AttributeBoolean.h>
+#include <ModelAPI_AttributeDocRef.h>
+#include <ModelAPI_AttributeDouble.h>
+#include <ModelAPI_AttributeIntArray.h>
+#include <ModelAPI_AttributeInteger.h>
+#include <ModelAPI_AttributeRefAttr.h>
+#include <ModelAPI_AttributeRefAttrList.h>
+#include <ModelAPI_AttributeReference.h>
+#include <ModelAPI_AttributeRefList.h>
+#include <ModelAPI_AttributeSelection.h>
+#include <ModelAPI_AttributeSelectionList.h>
+#include <ModelAPI_AttributeString.h>
+#include <ModelAPI_AttributeDoubleArray.h>
+#include <ModelAPI_Validator.h>
+
+#include <GeomDataAPI_Dir.h>
+#include <GeomDataAPI_Point.h>
+#include <GeomDataAPI_Point2D.h>
+#include <GeomAlgoAPI_ShapeTools.h>
+#include <GeomAPI_Pnt.h>
+
+#include <TopoDS_Shape.hxx>
+#include <TopExp_Explorer.hxx>
+
+#include <ios>
+#include <cmath>
+
+#define PRECISION 6
+#define TOLERANCE (1.e-7)
+
+ModelHighAPI_FeatureStore::ModelHighAPI_FeatureStore(FeaturePtr theFeature) {
+ storeData(theFeature->data(), myAttrs);
+ // iterate results to store
+ std::list<ResultPtr> allResults;
+ ModelAPI_Tools::allResults(theFeature, allResults);
+ std::list<ResultPtr>::iterator aRes = allResults.begin();
+ for(; aRes != allResults.end(); aRes++) {
+ std::map<std::string, std::string> aResDump;
+ storeData((*aRes)->data(), aResDump);
+ myRes.push_back(aResDump);
+ }
+}
+
+std::string ModelHighAPI_FeatureStore::compare(FeaturePtr theFeature) {
+ std::string anError = compareData(theFeature->data(), myAttrs);
+ if (!anError.empty()) {
+ return "Features '" + theFeature->name() + "' differ:" + anError;
+ }
+ std::list<ResultPtr> allResults;
+ ModelAPI_Tools::allResults(theFeature, allResults);
+ std::list<ResultPtr>::iterator aRes = allResults.begin();
+ std::list<std::map<std::string, std::string> >::iterator aResIter = myRes.begin();
+ for(; aRes != allResults.end() && aResIter != myRes.end(); aRes++, aResIter++) {
+ anError = compareData((*aRes)->data(), *aResIter);
+ if (!anError.empty())
+ return "Results of feature '" + theFeature->name() + "' '" + (*aRes)->data()->name() +
+ "' differ:" + anError;
+ }
+ if (aRes != allResults.end()) {
+ return "Current model has more results '" + (*aRes)->data()->name() + "'";
+ }
+ if (aResIter != myRes.end()) {
+ return "Original model had more results '" + (*aResIter)["__name__"] + "'";
+ }
+ return ""; // ok
+}
+
+void ModelHighAPI_FeatureStore::storeData(std::shared_ptr<ModelAPI_Data> theData,
+ std::map<std::string, std::string>& theAttrs)
+{
+ theAttrs["__name__"] = theData->name(); // store name to keep also this information and output if needed
+ std::list<std::shared_ptr<ModelAPI_Attribute> > allAttrs = theData->attributes("");
+ std::list<std::shared_ptr<ModelAPI_Attribute> >::iterator anAttr = allAttrs.begin();
+ for(; anAttr != allAttrs.end(); anAttr++) {
+ theAttrs[(*anAttr)->id()] = dumpAttr(*anAttr);
+ }
+ ResultPtr aShapeOwner = std::dynamic_pointer_cast<ModelAPI_Result>(theData->owner());
+ if (aShapeOwner.get() && aShapeOwner->shape().get()) {
+ std::shared_ptr<GeomAPI_Shape> aShape = aShapeOwner->shape();
+ theAttrs["__shape__"] = dumpShape(aShape);
+ }
+}
+
+std::string ModelHighAPI_FeatureStore::compareData(std::shared_ptr<ModelAPI_Data> theData,
+ std::map<std::string, std::string>& theAttrs)
+{
+ std::map<std::string, std::string> aThis;
+ storeData(theData, aThis);
+ std::map<std::string, std::string>::iterator aThisIter = aThis.begin();
+ for(; aThisIter != aThis.end(); aThisIter++) {
+ if (theAttrs.find(aThisIter->first) == theAttrs.end()) {
+ return "original model had no attribute '" + aThisIter->first + "'";
+ }
+ if (theAttrs[aThisIter->first] != aThisIter->second) {
+ return "attribute '" + aThisIter->first + "' is different (original != current) '" +
+ theAttrs[aThisIter->first] + "' != '" + aThisIter->second + "'";
+ }
+ }
+ // iterate back to find lack attribute in the current model
+ std::map<std::string, std::string>::iterator anOrigIter = theAttrs.begin();
+ for(; anOrigIter != theAttrs.end(); anOrigIter++) {
+ if (aThis.find(anOrigIter->first) == aThis.end()) {
+ return "current model had no attribute '" + anOrigIter->first + "'";
+ }
+ }
+ return "";
+}
+
+static void dumpArray(std::ostringstream& theOutput, const double theArray[], int theSize, int thePrecision = PRECISION)
+{
+ for (int i = 0; i < theSize; ++i) {
+ if (i > 0)
+ theOutput << " ";
+ theOutput << std::fixed << setprecision(thePrecision)
+ << (fabs(theArray[i]) < TOLERANCE ? 0.0 : theArray[i]);
+ }
+}
+
+std::string ModelHighAPI_FeatureStore::dumpAttr(const AttributePtr& theAttr) {
+ static ModelAPI_ValidatorsFactory* aFactory = ModelAPI_Session::get()->validators();
+ FeaturePtr aFeatOwner = std::dynamic_pointer_cast<ModelAPI_Feature>(theAttr->owner());
+ if (aFeatOwner.get() && !aFactory->isCase(aFeatOwner, theAttr->id())) {
+ return "__notcase__";
+ }
+ std::string aType = theAttr->attributeType();
+ std::ostringstream aResult;
+ if (!theAttr->isInitialized()) {
+ if (aType == ModelAPI_AttributeBoolean::typeId()) {
+ // special case for Boolean attribute (mean it false if not initialized)
+ aResult << false;
+ return aResult.str();
+ } else if (aType == ModelAPI_AttributeString::typeId()) {
+ // special case for attribute "SolverError"
+ if (theAttr->id() == "SolverError" &&
+ std::dynamic_pointer_cast<ModelAPI_Feature>(theAttr->owner())->getKind() == "Sketch")
+ return "";
+ }
+
+ return "__notinitialized__";
+ }
+ if (aType == ModelAPI_AttributeDocRef::typeId()) {
+ AttributeDocRefPtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeDocRef>(theAttr);
+ DocumentPtr aDoc = ModelAPI_Session::get()->moduleDocument();
+ if (anAttr->value() != aDoc) {
+ ResultPtr aRes = ModelAPI_Tools::findPartResult(aDoc, anAttr->value());
+ if (aRes.get()) {
+ aResult<<aRes->data()->name(); // Part result name (the same as saved file name)
+ }
+ } else {
+ aResult<<aDoc->kind(); // PartSet
+ }
+ } else if (aType == ModelAPI_AttributeInteger::typeId()) {
+ AttributeIntegerPtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeInteger>(theAttr);
+ if (anAttr->text().empty())
+ aResult<<anAttr->value();
+ else
+ aResult<<anAttr->text();
+ } else if (aType == ModelAPI_AttributeDouble::typeId()) {
+ AttributeDoublePtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeDouble>(theAttr);
+ int aPrecision = PRECISION;
+ // Special case - precision for the arc angle. It is calculated with tolerance 1e-4,
+ // so the value has only 4 correct digits
+ if (anAttr->id() == "ArcAngle")
+ aPrecision = 1;
+ if (anAttr->text().empty()) {
+ double aVal = anAttr->value();
+ dumpArray(aResult, &aVal, 1, aPrecision);
+ } else
+ aResult<<anAttr->text();
+ } else if (aType == ModelAPI_AttributeBoolean::typeId()) {
+ AttributeBooleanPtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeBoolean>(theAttr);
+ aResult<<anAttr->value();
+ } else if (aType == ModelAPI_AttributeString::typeId()) {
+ AttributeStringPtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeString>(theAttr);
+ aResult<<anAttr->value();
+ } else if (aType == ModelAPI_AttributeReference::typeId()) {
+ AttributeReferencePtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeReference>(theAttr);
+ if (anAttr->value().get()) {
+ aResult<<anAttr->value()->data()->name();
+ } else {
+ aResult<<"__empty__";
+ }
+ } else if (aType == ModelAPI_AttributeSelection::typeId()) {
+ AttributeSelectionPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeSelection>(theAttr);
+ aResult<<anAttr->namingName();
+ } else if (aType == ModelAPI_AttributeSelectionList::typeId()) {
+ AttributeSelectionListPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(theAttr);
+ for(int a = 0; a < anAttr->size(); a++) {
+ if (a != 0)
+ aResult<<" ";
+ aResult<<anAttr->value(a)->namingName();
+ }
+ } else if (aType == ModelAPI_AttributeRefAttr::typeId()) {
+ AttributeRefAttrPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeRefAttr>(theAttr);
+ ObjectPtr anObj = anAttr->isObject() ? anAttr->object() : anAttr->attr()->owner();
+ if (anObj.get()) {
+ aResult<<anObj->data()->name();
+ if (!anAttr->isObject()) {
+ aResult<<" "<<anAttr->attr()->id();
+ }
+ } else {
+ aResult<<"__empty__";
+ }
+ } else if (aType == ModelAPI_AttributeRefList::typeId()) {
+ AttributeRefListPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(theAttr);
+ // for sketch sub-features the empty values may be skipped and order is not important
+ bool isSketchFeatures = anAttr->id() == "Features" &&
+ std::dynamic_pointer_cast<ModelAPI_Feature>(anAttr->owner())->getKind() == "Sketch";
+ std::list<ObjectPtr> aList = anAttr->list();
+ std::list<std::string> aResList; // list of resulting strings
+ for(std::list<ObjectPtr>::iterator aL = aList.begin(); aL != aList.end(); aL++) {
+ if (aL->get()) {
+ aResList.push_back((*aL)->data()->name());
+ } else if (!isSketchFeatures) {
+ aResList.push_back("__empty__");
+ }
+ }
+ if (isSketchFeatures)
+ aResList.sort();
+ for(std::list<std::string>::iterator aR = aResList.begin(); aR != aResList.end(); aR++) {
+ aResult<<*aR<<" ";
+ }
+ } else if (aType == ModelAPI_AttributeRefAttrList::typeId()) {
+ AttributeRefAttrListPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeRefAttrList>(theAttr);
+ std::list<std::pair<ObjectPtr, AttributePtr> > aList = anAttr->list();
+ std::list<std::pair<ObjectPtr, AttributePtr> >::iterator aL = aList.begin();
+ for(; aL != aList.end(); aL++) {
+ if (aL != aList.begin())
+ aResult<<" ";
+ ObjectPtr anObj = aL->second.get() ? aL->second->owner() : aL->first;
+ if (anObj.get()) {
+ aResult<<anObj->data()->name();
+ if (aL->second.get()) {
+ aResult<<" "<<aL->second->id();
+ }
+ } else {
+ aResult<<"__empty__";
+ }
+ }
+ } else if (aType == ModelAPI_AttributeIntArray::typeId()) {
+ AttributeIntArrayPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeIntArray>(theAttr);
+ for(int a = 0; a < anAttr->size(); a++)
+ aResult<<anAttr->value(a)<<" ";
+ } else if (aType == ModelAPI_AttributeDoubleArray::typeId()) {
+ AttributeDoubleArrayPtr anAttr =
+ std::dynamic_pointer_cast<ModelAPI_AttributeDoubleArray>(theAttr);
+ for(int a = 0; a < anAttr->size(); a++)
+ aResult<<anAttr->value(a)<<" ";
+ } else if (aType == GeomDataAPI_Point::typeId()) {
+ AttributePointPtr anAttr = std::dynamic_pointer_cast<GeomDataAPI_Point>(theAttr);
+ double aValues[3] = {anAttr->x(), anAttr->y(), anAttr->z()};
+ dumpArray(aResult, aValues, 3);
+ } else if (aType == GeomDataAPI_Dir::typeId()) {
+ AttributeDirPtr anAttr = std::dynamic_pointer_cast<GeomDataAPI_Dir>(theAttr);
+ double aValues[3] = {anAttr->x(), anAttr->y(), anAttr->z()};
+ dumpArray(aResult, aValues, 3);
+ } else if (aType == GeomDataAPI_Point2D::typeId()) {
+ // do not dump flyout point for constraints as it may be changed unexpectedly
+ if (theAttr->id() == "ConstraintFlyoutValuePnt")
+ return "";
+ AttributePoint2DPtr anAttr = std::dynamic_pointer_cast<GeomDataAPI_Point2D>(theAttr);
+ double aValues[2] = {anAttr->x(), anAttr->y()};
+ dumpArray(aResult, aValues, 2);
+ } else {
+ aResult<<"__unknownattribute__";
+ }
+ return aResult.str();
+}
+
+std::string ModelHighAPI_FeatureStore::dumpShape(std::shared_ptr<GeomAPI_Shape>& theShape) {
+ TopoDS_Shape aShape = theShape->impl<TopoDS_Shape>();
+ if (aShape.IsNull()) {
+ return "null";
+ }
+ std::ostringstream aResult;
+ // output the number of shapes of different types
+ TopAbs_ShapeEnum aType = TopAbs_COMPOUND;
+ for(; aType <= TopAbs_VERTEX; aType = TopAbs_ShapeEnum((int)aType + 1)) {
+ TopExp_Explorer anExp(aShape, aType);
+ int aCount = 0;
+ for(; anExp.More(); anExp.Next()) aCount++;
+ TopAbs::Print(aType, aResult);
+ aResult<<": "<<aCount<<std::endl;
+ }
+ // output the main characteristics
+ if (GeomAlgoAPI_ShapeTools::volume(theShape) > 1.e-7) {
+ aResult<<"Volume: "<<std::fixed<<setprecision(3)<<GeomAlgoAPI_ShapeTools::volume(theShape)<<std::endl;
+ }
+ std::shared_ptr<GeomAPI_Pnt> aCenter = GeomAlgoAPI_ShapeTools::centreOfMass(theShape);
+ aResult<<"Center of mass: ";
+ double aCenterVals[3] = {aCenter->x(), aCenter->y(), aCenter->z()};
+ dumpArray(aResult, aCenterVals, 3);
+ aResult<<std::endl;
+ return aResult.str();
+}
--- /dev/null
+// Copyright (C) 2016-20xx CEA/DEN, EDF R&D -->
+
+// File: ModelHighAPI_FeatureStore.h
+// Created: 12 August 2016
+// Author: Mikhail PONIKAROV
+
+#ifndef ModelHighAPI_FeatureStore_H_
+#define ModelHighAPI_FeatureStore_H_
+
+#include "ModelHighAPI.h"
+
+#include <map>
+#include <list>
+#include <string>
+#include <memory>
+
+class ModelAPI_Feature;
+class ModelAPI_Data;
+class GeomAPI_Shape;
+class ModelAPI_Attribute;
+
+typedef std::shared_ptr<ModelAPI_Feature> FeaturePtr;
+typedef std::shared_ptr<ModelAPI_Attribute> AttributePtr;
+
+/**\class ModelHighAPI_FeatureStore
+ * \ingroup CPPHighAPI
+ * \brief Allows to compare the original and the dumped/executed feature
+ */
+class ModelHighAPI_FeatureStore {
+ /// dumps of attributes of the stored feature (id -> dump)
+ std::map<std::string, std::string> myAttrs;
+ /// dumps of attributes of results (list of results id -> dumps)
+ std::list<std::map<std::string, std::string> > myRes;
+public:
+ // unused constructor for the map container needs
+ ModelHighAPI_FeatureStore() {}
+ // constructor that initializes this object by feature to store
+ ModelHighAPI_FeatureStore(FeaturePtr theFeature);
+ // compares the stored feature information with the given feature
+ std::string compare(FeaturePtr theFeature);
+
+private:
+ /// stores the information about all attributes of data in map
+ void storeData(std::shared_ptr<ModelAPI_Data> theData,
+ std::map<std::string, std::string>& theAttrs);
+ /// compares the information about all attributes of data with map
+ /// returns not empty string with error if something is different
+ std::string compareData(std::shared_ptr<ModelAPI_Data> theData,
+ std::map<std::string, std::string>& theAttrs);
+ /// dumps the attribute content to the string
+ std::string dumpAttr(const AttributePtr& theAttr);
+ /// dumps the shape main charatceristics to string
+ std::string dumpShape(std::shared_ptr<GeomAPI_Shape>& theShape);
+};
+
+#endif
\ No newline at end of file
//--------------------------------------------------------------------------------------
#include <Events_InfoMessage.h>
+#include <ModelAPI_CompositeFeature.h>
+#include <ModelAPI_Events.h>
#include <ModelAPI_Feature.h>
+#include <ModelAPI_Session.h>
+#include <ModelAPI_Validator.h>
#include "ModelHighAPI_Selection.h"
//--------------------------------------------------------------------------------------
return myFeature;
}
+std::shared_ptr<ModelHighAPI_Interface> ModelHighAPI_Interface::subFeature(const int theIndex) const
+{
+ CompositeFeaturePtr aCompositeFeature = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(myFeature);
+ if(!aCompositeFeature.get()) {
+ return InterfacePtr();
+ }
+
+ FeaturePtr aSubFeature = aCompositeFeature->subFeature(theIndex);
+ if(!aSubFeature.get()) {
+ return InterfacePtr();
+ }
+
+ return InterfacePtr(new ModelHighAPI_Interface(aSubFeature));
+}
+
const std::string& ModelHighAPI_Interface::getKind() const
{
return feature()->getKind();
}
-void ModelHighAPI_Interface::execute()
+void ModelHighAPI_Interface::execute(bool isForce)
{
- feature()->execute();
+ if (isForce) {
+ SessionPtr aMgr = ModelAPI_Session::get();
+ ModelAPI_ValidatorsFactory* aFactory = aMgr->validators();
+ FeaturePtr aFeature = feature();
+ if(aFactory->validate(aFeature))
+ aFeature->execute();
+ }
+
+ Events_Loop* aLoop = Events_Loop::loop();
+ aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_CREATED));
+ aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
+ //aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
+ //aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_DELETED));
+}
+
+void ModelHighAPI_Interface::setName(const std::string& theName)
+{
+ feature()->data()->setName(theName);
}
std::list<ModelHighAPI_Selection> ModelHighAPI_Interface::result() const
std::shared_ptr<ModelAPI_Result> ModelHighAPI_Interface::defaultResult() const
{
+ const_cast<ModelHighAPI_Interface*>(this)->execute();
+
return feature()->lastResult();
}
{
Events_InfoMessage("ModelHighAPI_Interface", theDescription).send();
}
+
+const std::string& ModelHighAPI_Interface::attributeGetter(const std::string& theAttrName)
+{
+ return myAttrGetter[theAttrName];
+}
#include "ModelHighAPI.h"
#include <list>
+#include <map>
#include <memory>
#include <string>
#include <iostream>
class ModelAPI_Feature;
class ModelAPI_Result;
class ModelHighAPI_Selection;
+class ModelHighAPI_Dumper;
//--------------------------------------------------------------------------------------
/**\class ModelHighAPI_Interface
* \ingroup CPPHighAPI
MODELHIGHAPI_EXPORT
std::shared_ptr<ModelAPI_Feature> feature() const;
+ /// If feature is composite return intefrace for sub-feature by zero-based index,
+ /// or empty pointer if feature not composite or does not have sub-feature with such index.
+ MODELHIGHAPI_EXPORT
+ std::shared_ptr<ModelHighAPI_Interface> subFeature(const int theIndex) const;
+
/// Shortcut for feature()->getKind()
MODELHIGHAPI_EXPORT
const std::string& getKind() const;
/// Shortcut for feature()->execute()
+ /// \param isForce start execution of feature instead of sending events
MODELHIGHAPI_EXPORT
- void execute();
+ void execute(bool isForce = false);
+
+ /// Shortcut for feature()->data()->setName()
+ MODELHIGHAPI_EXPORT
+ void setName(const std::string& theName);
// TODO(spo): rename to selectAll()
/// Return all objects of the feature
MODELHIGHAPI_EXPORT
void throwException(const std::string & theDescription);
+ /// Return name of getter for specified attribute
+ MODELHIGHAPI_EXPORT
+ const std::string& attributeGetter(const std::string& theAttrName);
+
+ /// Dump wrapped feature
+ MODELHIGHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const {}
+
protected:
std::shared_ptr<ModelAPI_Feature> myFeature;
+
+ std::map<std::string, std::string> myAttrGetter; ///< names of attributes and their getters
};
//! Pointer on Interface object
//--------------------------------------------------------------------------------------
#define VAR_NAME(NAME) my##NAME
+//--------------------------------------------------------------------------------------
+#define TO_STRING_(NAME) #NAME
+#define TO_STRING(NAME) TO_STRING_(NAME)
+
//--------------------------------------------------------------------------------------
// Used in INTERFACE_N for create variable and getter
#define DEFINE_ATTRIBUTE(NAME, TYPE, COMMENT) \
#define SET_ATTRIBUTE(NAME, TYPE, ATT_NAME) \
VAR_NAME(NAME) = std::dynamic_pointer_cast<TYPE>(feature()->attribute(ATT_NAME)); \
if (!VAR_NAME(NAME)) \
- return false;
+ return false; \
+ myAttrGetter[ATT_NAME] = TO_STRING(NAME);
//--------------------------------------------------------------------------------------
#define INTERFACE_COMMON(KIND) \
case VT_OBJECT: theAttribute->append(myObject); return;
}
}
+
+//--------------------------------------------------------------------------------------
+bool ModelHighAPI_RefAttr::isEmpty() const
+{
+ return !(myAttribute && myObject);
+}
MODELHIGHAPI_EXPORT
virtual void appendToList(const std::shared_ptr<ModelAPI_AttributeRefAttrList> & theAttribute) const;
+ /// Check the object is empty
+ MODELHIGHAPI_EXPORT
+ bool isEmpty() const;
+
private:
enum VariantType { VT_ATTRIBUTE, VT_OBJECT } myVariantType;
std::shared_ptr<ModelAPI_Attribute> myAttribute;
const std::shared_ptr<ModelHighAPI_Interface> & theValue)
: myObject(std::shared_ptr<ModelAPI_Object>(theValue->defaultResult()))
{
+ // the result is not constructed yet, forcibly do it
+ if (!myObject) {
+ theValue->execute(true);
+ myObject = std::shared_ptr<ModelAPI_Object>(theValue->defaultResult());
+ }
}
ModelHighAPI_Reference::~ModelHighAPI_Reference()
{
theAttribute->append(myObject);
}
+
+//--------------------------------------------------------------------------------------
+std::shared_ptr<ModelAPI_Feature> ModelHighAPI_Reference::feature() const
+{
+ return ModelAPI_Feature::feature(myObject);
+}
class ModelAPI_Attribute;
class ModelAPI_AttributeReference;
class ModelAPI_AttributeRefList;
+class ModelAPI_Feature;
class ModelAPI_Object;
class ModelHighAPI_Interface;
//--------------------------------------------------------------------------------------
MODELHIGHAPI_EXPORT
virtual void appendToList(const std::shared_ptr<ModelAPI_AttributeRefList> & theAttribute) const;
+ /// Returns feature for this object.
+ MODELHIGHAPI_EXPORT
+ virtual std::shared_ptr<ModelAPI_Feature> feature() const;
+
private:
std::shared_ptr<ModelAPI_Object> myObject;
};
//--------------------------------------------------------------------------------------
#include "ModelHighAPI_Selection.h"
+#include <ModelAPI_AttributeIntArray.h>
#include <ModelAPI_AttributeSelection.h>
#include <ModelAPI_AttributeSelectionList.h>
//--------------------------------------------------------------------------------------
//--------------------------------------------------------------------------------------
+ModelHighAPI_Selection::ModelHighAPI_Selection()
+: myVariantType(VT_Empty)
+{
+}
+
ModelHighAPI_Selection::ModelHighAPI_Selection(const std::shared_ptr<ModelAPI_Result>& theContext,
const std::shared_ptr<GeomAPI_Shape>& theSubShape)
: myVariantType(VT_ResultSubShapePair)
const std::shared_ptr<ModelAPI_AttributeSelection> & theAttribute) const
{
switch(myVariantType) {
+ case VT_Empty: return;
case VT_ResultSubShapePair: theAttribute->setValue(myResultSubShapePair.first, myResultSubShapePair.second); return;
case VT_TypeSubShapeNamePair: theAttribute->selectSubShape(myTypeSubShapeNamePair.first, myTypeSubShapeNamePair.second); return;
}
const std::shared_ptr<ModelAPI_AttributeSelectionList> & theAttribute) const
{
switch(myVariantType) {
+ case VT_Empty: return;
case VT_ResultSubShapePair: theAttribute->append(myResultSubShapePair.first, myResultSubShapePair.second); return;
case VT_TypeSubShapeNamePair:
// Note: the reverse order (first - type, second - sub-shape name)
{
return myTypeSubShapeNamePair;
}
+
+//==================================================================================================
+std::string ModelHighAPI_Selection::shapeType() const
+{
+ switch(myVariantType) {
+ case VT_ResultSubShapePair:
+ return myResultSubShapePair.second.get() ? myResultSubShapePair.second->shapeTypeStr() :
+ myResultSubShapePair.first->shape()->shapeTypeStr();
+ case VT_TypeSubShapeNamePair: return myTypeSubShapeNamePair.first;
+ }
+
+ return "SHAPE";
+}
+
+//==================================================================================================
+void ModelHighAPI_Selection::setName(const std::string& theName)
+{
+ if (myVariantType == VT_ResultSubShapePair)
+ myResultSubShapePair.first->data()->setName(theName);
+}
+
+void ModelHighAPI_Selection::setColor(int theRed, int theGreen, int theBlue)
+{
+ if (myVariantType != VT_ResultSubShapePair)
+ return;
+
+ AttributeIntArrayPtr aColor =
+ myResultSubShapePair.first->data()->intArray(ModelAPI_Result::COLOR_ID());
+ aColor->setSize(3);
+ aColor->setValue(0, theRed);
+ aColor->setValue(1, theGreen);
+ aColor->setValue(2, theBlue);
+}
{
public:
enum VariantType {
+ VT_Empty,
VT_ResultSubShapePair,
VT_TypeSubShapeNamePair
};
public:
+ /// Default constructor with empty selection.
+ MODELHIGHAPI_EXPORT
+ ModelHighAPI_Selection();
+
/// Constructor for result and sub-shape
MODELHIGHAPI_EXPORT
- ModelHighAPI_Selection(const std::shared_ptr<ModelAPI_Result>& theContext = std::shared_ptr<ModelAPI_Result>(),
+ ModelHighAPI_Selection(const std::shared_ptr<ModelAPI_Result>& theContext,
const std::shared_ptr<GeomAPI_Shape>& theSubShape = std::shared_ptr<GeomAPI_Shape>());
/// Constructor for sub-shape by the textual Name
MODELHIGHAPI_EXPORT
MODELHIGHAPI_EXPORT
virtual TypeSubShapeNamePair typeSubShapeNamePair() const;
+ /// \return shape type.
+ MODELHIGHAPI_EXPORT
+ virtual std::string shapeType() const;
+
+ /// Shortcut for result()->data()->setName()
+ MODELHIGHAPI_EXPORT
+ void setName(const std::string& theName);
+
+ /// Change result's color
+ MODELHIGHAPI_EXPORT
+ void setColor(int theRed, int theGreen, int theBlue);
+
private:
VariantType myVariantType;
ResultSubShapePair myResultSubShapePair;
#include <GeomAPI_Ax3.h>
#include <GeomAPI_Pnt.h>
#include <ModelAPI_Session.h>
+#include <ModelAPI_Document.h>
+#include <ModelAPI_ResultConstruction.h>
+
+#include <cmath>
//--------------------------------------------------------------------------------------
std::shared_ptr<ModelAPI_Document> moduleDocument()
return std::shared_ptr<GeomAPI_Ax3>(new GeomAPI_Ax3(o, x, n));
}
+std::string defaultPlane(const std::shared_ptr<GeomAPI_Pnt>& theOrigin,
+ const std::shared_ptr<GeomAPI_Dir>& theNormal,
+ const std::shared_ptr<GeomAPI_Dir>& theDirX)
+{
+ static const double aTol = 1.e-10;
+
+ if (fabs(theOrigin->x()) > aTol || fabs(theOrigin->y()) > aTol || fabs(theOrigin->z()) > aTol)
+ return std::string();
+
+ // XOY or XOZ
+ if (fabs(theNormal->x()) < aTol &&
+ fabs(theDirX->x() - 1.0) < aTol && fabs(theDirX->y()) < aTol && fabs(theDirX->z()) < aTol) {
+ // XOY
+ if (fabs(theNormal->y()) < aTol && fabs(theNormal->z() - 1.0) < aTol)
+ return std::string("XOY");
+ else if (fabs(theNormal->y() + 1.0) < aTol && fabs(theNormal->z()) < aTol)
+ return std::string("XOZ");
+ }
+ // YOZ
+ else if (fabs(theNormal->x() - 1.0) < aTol && fabs(theNormal->y()) < aTol && fabs(theNormal->z()) < aTol &&
+ fabs(theDirX->x()) < aTol && fabs(theDirX->y() - 1.0) < aTol && fabs(theDirX->z()) < aTol)
+ return std::string("YOZ");
+
+ return std::string();
+}
+
+std::shared_ptr<ModelAPI_Result> standardPlane(const std::string & theName){
+ DocumentPtr aPartSet = ModelAPI_Session::get()->moduleDocument();
+ // searching for the construction element
+ return std::dynamic_pointer_cast<ModelAPI_Result>(
+ aPartSet->objectByName(ModelAPI_ResultConstruction::group(), theName));
+}
+
//--------------------------------------------------------------------------------------
void begin()
{
#include <string>
//--------------------------------------------------------------------------------------
class GeomAPI_Ax3;
+class GeomAPI_Dir;
+class GeomAPI_Pnt;
class ModelAPI_Document;
+class ModelAPI_Result;
//--------------------------------------------------------------------------------------
/// Return the main document (the Partset) created or open from the Modeler.
MODELHIGHAPI_EXPORT
MODELHIGHAPI_EXPORT
std::shared_ptr<GeomAPI_Ax3> defaultPlane(const std::string & theName);
+/// Return name of coordinate plane ("XOY", "XOZ" or "YOZ") or empty string for other planes.
+MODELHIGHAPI_EXPORT
+std::string defaultPlane(const std::shared_ptr<GeomAPI_Pnt>& theOrigin,
+ const std::shared_ptr<GeomAPI_Dir>& theNormal,
+ const std::shared_ptr<GeomAPI_Dir>& theDirX);
+
+/** Return one of the three standard results defined in PartSet document.
+ *
+ * These planes are respectively referred to by name "XOY" (Z=0), "XOZ" (Y=0) or "YOZ" (X=0).
+ */
+MODELHIGHAPI_EXPORT
+std::shared_ptr<ModelAPI_Result> standardPlane(const std::string & theName);
+
/** Start a data structure transaction.
*
* Make a control point for being able to discard or undo
//--------------------------------------------------------------------------------------
#include "ModelHighAPI_Tools.h"
+#include <ModelHighAPI_FeatureStore.h>
//--------------------------------------------------------------------------------------
#include <GeomAPI_Dir.h>
#include <GeomAPI_Pnt.h>
#include <ModelAPI_AttributeSelection.h>
#include <ModelAPI_AttributeSelectionList.h>
#include <ModelAPI_AttributeString.h>
+#include <ModelAPI_AttributeDoubleArray.h>
+#include <ModelAPI_Session.h>
+#include <ModelAPI_Tools.h>
+#include <ModelAPI_ResultPart.h>
+//--------------------------------------------------------------------------------------
+#include <Config_ModuleReader.h>
//--------------------------------------------------------------------------------------
#include "ModelHighAPI_Double.h"
#include "ModelHighAPI_Integer.h"
#include "ModelHighAPI_Reference.h"
#include "ModelHighAPI_Selection.h"
+#include <Events_InfoMessage.h>
+
+// Have to be included before std headers
+#include <Python.h>
+
#include <algorithm>
+#include <iostream>
//--------------------------------------------------------------------------------------
void fillAttribute(const std::shared_ptr<GeomAPI_Pnt2d> & theValue,
{
theValue.fillAttribute(theAttribute);
}
+void fillAttribute(int theValue,
+ const std::shared_ptr<ModelAPI_AttributeInteger> & theAttribute)
+{
+ theAttribute->setValue(theValue);
+}
//--------------------------------------------------------------------------------------
void fillAttribute(const ModelHighAPI_RefAttr & theValue,
const std::shared_ptr<ModelAPI_AttributeSelectionList> & theAttribute)
{
theAttribute->clear();
+
+ if(!theValue.empty()) {
+ std::string aSelectionType;
+ const ModelHighAPI_Selection& aSelection = theValue.front();
+ theAttribute->setSelectionType(aSelection.shapeType());
+ }
+
for (auto it = theValue.begin(); it != theValue.end(); ++it)
it->appendToList(theAttribute);
}
}
//==================================================================================================
-GeomAPI_Shape::ShapeType shapeTypeByStr(const std::string& theShapeTypeStr)
+GeomAPI_Shape::ShapeType shapeTypeByStr(std::string theShapeTypeStr)
{
GeomAPI_Shape::ShapeType aShapeType = GeomAPI_Shape::SHAPE;
- std::string aShapeTypeStr = theShapeTypeStr;
- std::transform(aShapeTypeStr.begin(), aShapeTypeStr.end(), aShapeTypeStr.begin(), ::tolower);
+ std::transform(theShapeTypeStr.begin(), theShapeTypeStr.end(), theShapeTypeStr.begin(), ::tolower);
if(theShapeTypeStr == "compound") {
aShapeType = GeomAPI_Shape::COMPOUND;
return aShapeType;
}
+/// stores the features information, recoursively stores sub-documetns features
+std::string storeFeatures(const std::string& theDocName, DocumentPtr theDoc,
+ std::map<std::string, std::map<std::string, ModelHighAPI_FeatureStore> >& theStore,
+ const bool theCompare) // if false => store
+{
+ std::map<std::string, std::map<std::string, ModelHighAPI_FeatureStore> >::iterator aDocFind;
+ if (theCompare) {
+ aDocFind = theStore.find(theDocName);
+ if (aDocFind == theStore.end()) {
+ return "Document '" + theDocName + "' not found";
+ }
+ }
+ // store the model features information: iterate all features
+ int aFeaturesCount = 0; // stores the number of compared features for this document to compate
+ std::set<std::string> aProcessed; // processed features names (that are in the current document)
+ std::list<FeaturePtr> allFeatures = theDoc->allFeatures();
+ std::list<FeaturePtr>::iterator allIter = allFeatures.begin();
+ for(; allIter != allFeatures.end(); allIter++) {
+ FeaturePtr aFeat = *allIter;
+ if (theCompare) {
+ std::map<std::string, ModelHighAPI_FeatureStore>::iterator
+ aFeatFind = aDocFind->second.find(aFeat->name());
+ if (aFeatFind == aDocFind->second.end()) {
+ return "Document '" + theDocName + "' feature '" + aFeat->name() + "' not found";
+ }
+ std::string anError = aFeatFind->second.compare(aFeat);
+ if (!anError.empty()) {
+ return anError;
+ }
+ aFeaturesCount++;
+ aProcessed.insert(aFeat->name());
+ } else {
+ theStore[theDocName][aFeat->name()] = ModelHighAPI_FeatureStore(aFeat);
+ }
+ // iterate all results of this feature
+ std::list<ResultPtr> allResults;
+ ModelAPI_Tools::allResults(aFeat, allResults);
+ std::list<ResultPtr>::iterator aRes = allResults.begin();
+ for(; aRes != allResults.end(); aRes++) {
+ if ((*aRes)->groupName() == ModelAPI_ResultPart::group()) { // recoursively store features of sub-documents
+ DocumentPtr aDoc = std::dynamic_pointer_cast<ModelAPI_ResultPart>(*aRes)->partDoc();
+ if (aDoc.get()) {
+ std::string anError = storeFeatures((*aRes)->data()->name(), aDoc, theStore, theCompare);
+ if (!anError.empty())
+ return anError;
+ }
+ }
+ }
+ }
+ // checks the number of compared features
+ if (theCompare) {
+ if (aDocFind->second.size() != aFeaturesCount) {
+ // search for disappeared feature
+ std::string aLostName;
+ std::map<std::string, ModelHighAPI_FeatureStore>::iterator aLostIter;
+ for(aLostIter = aDocFind->second.begin(); aLostIter != aDocFind->second.end(); aLostIter++) {
+ if (aProcessed.find(aLostIter->first) == aProcessed.end()) {
+ aLostName = aLostIter->first;
+ }
+ }
+ return "For document '" + theDocName +
+ "' the number of features is decreased, there is no feature '" + aLostName + "'";
+ }
+ }
+ return ""; // ok
+}
+
+//==================================================================================================
+bool checkPythonDump()
+{
+ SessionPtr aSession = ModelAPI_Session::get();
+ // dump all to the python file
+ aSession->startOperation("Check python dump");
+ FeaturePtr aDump = aSession->moduleDocument()->addFeature("Dump");
+ if (aDump.get()) {
+ aDump->string("file_path")->setValue("check_dump.py"); // to the current folder
+ aDump->string("file_format")->setValue("py"); // to the current folder
+ aDump->execute();
+ }
+ bool isProblem = !aDump.get() || !aDump->error().empty(); // after "finish" dump will be removed
+ aSession->finishOperation();
+ if (isProblem)
+ return false; // something is wrong during dump
+
+ // map from document name to feature name to feature data
+ std::map<std::string, std::map<std::string, ModelHighAPI_FeatureStore> > aStore;
+ std::string anError = storeFeatures(
+ aSession->moduleDocument()->kind(), aSession->moduleDocument(), aStore, false);
+ if (!anError.empty()) {
+ Events_InfoMessage anErrorMsg(std::string("checkPythonDump"), anError);
+ anErrorMsg.send();
+ return false;
+ }
+ // close all before importation of the script
+ aSession->closeAll();
+ // execute the dumped
+ PyGILState_STATE gstate = PyGILState_Ensure(); /* acquire python thread */
+ PyObject* PyFileObject = PyFile_FromString("./check_dump.py", "r");
+ PyRun_SimpleFileEx(PyFile_AsFile(PyFileObject), "./check_dump.py", 1);
+ PyGILState_Release(gstate); /* release python thread */
+
+ // compare with the stored data
+ anError = storeFeatures(
+ aSession->moduleDocument()->kind(), aSession->moduleDocument(), aStore, true);
+ if (!anError.empty()) {
+ std::cout<<anError<<std::endl;
+ Events_InfoMessage anErrorMsg(std::string("checkPythonDump"), anError);
+ anErrorMsg.send();
+ return false;
+ }
+
+ return true;
+}
+
//--------------------------------------------------------------------------------------
class GeomDataAPI_Point2D;
//--------------------------------------------------------------------------------------
class ModelAPI_AttributeBoolean;
-class ModelAPI_AttributeDocRef;
class ModelAPI_AttributeDouble;
class ModelAPI_AttributeIntArray;
class ModelAPI_AttributeInteger;
void fillAttribute(const ModelHighAPI_Integer & theValue,
const std::shared_ptr<ModelAPI_AttributeInteger> & theAttribute);
+MODELHIGHAPI_EXPORT
+void fillAttribute(int theValue,
+ const std::shared_ptr<ModelAPI_AttributeInteger> & theAttribute);
+
MODELHIGHAPI_EXPORT
void fillAttribute(const ModelHighAPI_RefAttr & theValue,
const std::shared_ptr<ModelAPI_AttributeRefAttr> & theAttribute);
const std::shared_ptr<ModelAPI_AttributeString> & theAttribute);
MODELHIGHAPI_EXPORT
-GeomAPI_Shape::ShapeType shapeTypeByStr(const std::string& theShapeTypeStr);
+GeomAPI_Shape::ShapeType shapeTypeByStr(std::string theShapeTypeStr);
MODELHIGHAPI_EXPORT
GeomAPI_Shape::ShapeType getShapeType(const ModelHighAPI_Selection& theSelection);
+/// Performs the high level API dump, then closes all and executes the script:
+/// model must be recreated fully, with all attributes
+/// \returns true if check is well done
+MODELHIGHAPI_EXPORT
+bool checkPythonDump();
+
//--------------------------------------------------------------------------------------
//--------------------------------------------------------------------------------------
#endif /* SRC_MODELHIGHAPI_MODELHIGHAPI_TOOLS_H_ */
#include "ModelHighAPI.h"
#include "ModelHighAPI_Double.h"
+ #include "ModelHighAPI_Dumper.h"
#include "ModelHighAPI_Integer.h"
#include "ModelHighAPI_Interface.h"
#include "ModelHighAPI_Macro.h"
if (!aTextRepr.empty()) {
ModuleBase_Tools::setSpinText(mySpinBox, QString::fromStdString(aTextRepr));
} else {
- ModuleBase_Tools::setSpinValue(mySpinBox, aRef->value());
+ ModuleBase_Tools::setSpinValue(mySpinBox, aRef->isInitialized() ? aRef->value() : 0);
}
return true;
}
//--------------------------------------------------------------------------------------
#include "ParametersAPI_Parameter.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
ParametersAPI_Parameter::ParametersAPI_Parameter(
if (initialize()) {
fillAttribute(theName, name());
fillAttribute(theExpression, expression());
- fillAttribute(theComment, comment());
+ if (!theComment.empty())
+ fillAttribute(theComment, comment());
execute();
}
{
}
+void ParametersAPI_Parameter::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+ const std::string& aParamName = theDumper.name(aBase, false, true);
+
+ AttributeStringPtr anExpr = aBase->string(ParametersPlugin_Parameter::EXPRESSION_ID());
+ AttributeStringPtr aComment = aBase->string(ParametersPlugin_Parameter::COMMENT_ID());
+
+ theDumper << "model.addParameter(" << aDocName << ", \"" << aParamName << "\", " << anExpr;
+ if (aComment->isInitialized() && !aComment->value().empty())
+ theDumper << ", " << aComment;
+ theDumper << ")" << std::endl;
+}
+
//--------------------------------------------------------------------------------------
ParameterPtr addParameter(const std::shared_ptr<ModelAPI_Document> & thePart,
const std::string & theName,
comment, ParametersPlugin_Parameter::COMMENT_ID(), ModelAPI_AttributeString, /** Comment */
)
+ /// Dump wrapped feature
+ PARAMETERSAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
};
//! Pointer on Parameter object
from ModelAPI import *
import math
import unittest
+import model
__updated__ = "2015-04-27"
self.createFeature()
def tearDown(self):
+ assert(model.checkPythonDump())
self.aSession.closeAll()
def createParameters(self):
aSketchCircle = aSketchFeature.addFeature("SketchCircle")
anCircleCentr = geomDataAPI_Point2D(aSketchCircle.attribute("CircleCenter"))
aRadiusAttr = aSketchCircle.real("CircleRadius")
- anCircleCentr.setText("x1 + 10.0", "x1 + 20.0")
- aRadiusAttr.setText("x1")
+ anCircleCentr.setValue(10., 20.)
+ aRadiusAttr.setValue(10.)
self.aSession.finishOperation()
self.anCircleCentr = anCircleCentr
self.aRadiusAttr = aRadiusAttr
+ # constraints to fix circle position and radius
+ self.aSession.startOperation()
+ # fix X coordinate
+ aDistanceConstraint1 = aSketchFeature.addFeature("SketchConstraintDistance")
+ refattrA = aDistanceConstraint1.refattr("ConstraintEntityA")
+ refattrA.setAttr(anCircleCentr)
+ refattrB = aDistanceConstraint1.refattr("ConstraintEntityB")
+ anOY = aSketchFeature.addFeature("SketchLine")
+ aStartPoint = geomDataAPI_Point2D(anOY.attribute("StartPoint"))
+ anEndPoint = geomDataAPI_Point2D(anOY.attribute("EndPoint"))
+ aStartPoint.setValue(0., 0.)
+ anEndPoint.setValue(0., 100.)
+ anOYRes = modelAPI_Result(self.aDocument.objectByName("Construction", "OY"))
+ anOY.selection("External").setValue(anOYRes, anOYRes.shape())
+ anOY.execute()
+ refattrB.setObject(modelAPI_ResultConstruction(anOY.firstResult()))
+ value = aDistanceConstraint1.real("ConstraintValue")
+ value.setText("x1 + 10.0")
+ aDistanceConstraint1.execute();
+ # fix Y coordinate
+ aDistanceConstraint2 = aSketchFeature.addFeature("SketchConstraintDistance")
+ refattrA = aDistanceConstraint2.refattr("ConstraintEntityA")
+ refattrA.setAttr(anCircleCentr)
+ refattrB = aDistanceConstraint2.refattr("ConstraintEntityB")
+ anOX = aSketchFeature.addFeature("SketchLine")
+ aStartPoint = geomDataAPI_Point2D(anOX.attribute("StartPoint"))
+ anEndPoint = geomDataAPI_Point2D(anOX.attribute("EndPoint"))
+ aStartPoint.setValue(0., 0.)
+ anEndPoint.setValue(100., 0.)
+ anOXRes = modelAPI_Result(self.aDocument.objectByName("Construction", "OX"))
+ anOX.selection("External").setValue(anOXRes, anOXRes.shape())
+ anOX.execute()
+ refattrB.setObject(modelAPI_ResultConstruction(anOX.firstResult()))
+ value = aDistanceConstraint2.real("ConstraintValue")
+ value.setText("x1 + 20.0")
+ aDistanceConstraint2.execute();
+ # fix radius
+ aRadiusConstraint = aSketchFeature.addFeature("SketchConstraintRadius")
+ refattrA = aRadiusConstraint.refattr("ConstraintEntityA")
+ refattrA.setObject(modelAPI_ResultConstruction(aSketchCircle.lastResult()))
+ aRadiusConstrAttr = aRadiusConstraint.real("ConstraintValue")
+ aRadiusConstrAttr.setText("x1")
+ aRadiusConstraint.execute()
+ self.aSession.finishOperation()
+
self.assertEqual(self.anCircleCentr.x(), 160.)
self.assertEqual(self.anCircleCentr.y(), 170.)
self.assertEqual(aRadiusAttr.value(), 150.)
#=========================================================================
# Use parameters to set radius of a circle :
# 1. Create a circle (250., 250), r = 25.
-# 2. Set a 'cr1' as text value of radius attribute
+# 2. Create a radius constraint and set 'cr1' as text value of constraint
#=========================================================================
aSession.startOperation()
aSketchCircle = aSketchFeature.addFeature("SketchCircle")
aSession.finishOperation()
# Apply parameter
aSession.startOperation()
-aRadiusAttr.setText("cr1")
+aRadiusConstraint = aSketchFeature.addFeature("SketchConstraintRadius")
+refattrA = aRadiusConstraint.refattr("ConstraintEntityA")
+refattrA.setObject(modelAPI_ResultConstruction(aSketchCircle.lastResult()))
+aRadiusConstrAttr = aRadiusConstraint.real("ConstraintValue")
+aRadiusConstrAttr.setText("cr1")
+aRadiusConstraint.execute()
aSession.finishOperation()
assert(aRadiusAttr.value() == 100.)
#=========================================================================
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
from ModelAPI import *
import math
import unittest
+import model
__updated__ = "2015-04-27"
self.createFeature()
def tearDown(self):
+ assert(model.checkPythonDump())
self.aSession.closeAll()
def createParameters(self):
aSketchCircle = aSketchFeature.addFeature("SketchCircle")
anCircleCentr = geomDataAPI_Point2D(aSketchCircle.attribute("CircleCenter"))
aRadiusAttr = aSketchCircle.real("CircleRadius")
- anCircleCentr.setText("x1 + 10.0", "x1 + 20.0")
- aRadiusAttr.setText("x1")
+ anCircleCentr.setValue(10., 20.)
+ aRadiusAttr.setValue(10.)
self.aSession.finishOperation()
self.anCircleCentr = anCircleCentr
self.aRadiusAttr = aRadiusAttr
+ # constraints to fix circle position and radius
+ self.aSession.startOperation()
+ # fix X coordinate
+ aDistanceConstraint1 = aSketchFeature.addFeature("SketchConstraintDistance")
+ refattrA = aDistanceConstraint1.refattr("ConstraintEntityA")
+ refattrA.setAttr(anCircleCentr)
+ refattrB = aDistanceConstraint1.refattr("ConstraintEntityB")
+ anOY = aSketchFeature.addFeature("SketchLine")
+ aStartPoint = geomDataAPI_Point2D(anOY.attribute("StartPoint"))
+ anEndPoint = geomDataAPI_Point2D(anOY.attribute("EndPoint"))
+ aStartPoint.setValue(0., 0.)
+ anEndPoint.setValue(0., 100.)
+ anOYRes = modelAPI_Result(self.aDocument.objectByName("Construction", "OY"))
+ anOY.selection("External").setValue(anOYRes, anOYRes.shape())
+ anOY.execute()
+ refattrB.setObject(modelAPI_ResultConstruction(anOY.firstResult()))
+ valueX = aDistanceConstraint1.real("ConstraintValue")
+ valueX.setText("x1 + 10.0")
+ aDistanceConstraint1.execute();
+ # fix Y coordinate
+ aDistanceConstraint2 = aSketchFeature.addFeature("SketchConstraintDistance")
+ refattrA = aDistanceConstraint2.refattr("ConstraintEntityA")
+ refattrA.setAttr(anCircleCentr)
+ refattrB = aDistanceConstraint2.refattr("ConstraintEntityB")
+ anOX = aSketchFeature.addFeature("SketchLine")
+ aStartPoint = geomDataAPI_Point2D(anOX.attribute("StartPoint"))
+ anEndPoint = geomDataAPI_Point2D(anOX.attribute("EndPoint"))
+ aStartPoint.setValue(0., 0.)
+ anEndPoint.setValue(100., 0.)
+ anOXRes = modelAPI_Result(self.aDocument.objectByName("Construction", "OX"))
+ anOX.selection("External").setValue(anOXRes, anOXRes.shape())
+ anOX.execute()
+ refattrB.setObject(modelAPI_ResultConstruction(anOX.firstResult()))
+ valueY = aDistanceConstraint2.real("ConstraintValue")
+ valueY.setText("x1 + 20.0")
+ aDistanceConstraint2.execute();
+ # fix radius
+ aRadiusConstraint = aSketchFeature.addFeature("SketchConstraintRadius")
+ refattrA = aRadiusConstraint.refattr("ConstraintEntityA")
+ refattrA.setObject(modelAPI_ResultConstruction(aSketchCircle.lastResult()))
+ aRadiusConstrAttr = aRadiusConstraint.real("ConstraintValue")
+ aRadiusConstrAttr.setText("x1")
+ aRadiusConstraint.execute()
+ self.aSession.finishOperation()
+
+ self.aCircleCenterX = valueX
+ self.aCircleCenterY = valueY
+ self.aCircleRadius = aRadiusConstrAttr
+
self.assertEqual(self.anCircleCentr.x(), 160.)
self.assertEqual(self.anCircleCentr.y(), 170.)
self.assertEqual(aRadiusAttr.value(), 150.)
aParam = self.dtParams["x2"]
self.assertEqual(aParam.string("expression").value(), "a1 + y1 + 100.0")
# Check rename in the feature
- self.assertEqual(self.anCircleCentr.textX(), "a1 + 10.0")
- self.assertEqual(self.anCircleCentr.textY(), "a1 + 20.0")
- self.assertEqual(self.aRadiusAttr.text(), "a1")
+ self.assertEqual(self.aCircleCenterX.text(), "a1 + 10.0")
+ self.assertEqual(self.aCircleCenterY.text(), "a1 + 20.0")
+ self.assertEqual(self.aCircleRadius.text(), "a1")
+ # Check values
+ self.assertEqual(self.anCircleCentr.x(), 160.)
+ self.assertEqual(self.anCircleCentr.y(), 170.)
+ self.assertEqual(self.aRadiusAttr.value(), 150.)
def test_rename_not_unique(self):
# Rename to not unique name
aParam = self.dtParams["x2"]
self.assertEqual(aParam.string("expression").value(), "x1 + y1 + 100.0")
# Check rename in the feature (Expected: not renamed)
- self.assertEqual(self.anCircleCentr.textX(), "x1 + 10.0")
- self.assertEqual(self.anCircleCentr.textY(), "x1 + 20.0")
- self.assertEqual(self.aRadiusAttr.text(), "x1")
+ self.assertEqual(self.aCircleCenterX.text(), "x1 + 10.0")
+ self.assertEqual(self.aCircleCenterY.text(), "x1 + 20.0")
+ self.assertEqual(self.aCircleRadius.text(), "x1")
+ # Check values
+ self.assertEqual(self.anCircleCentr.x(), 160.)
+ self.assertEqual(self.anCircleCentr.y(), 170.)
+ self.assertEqual(self.aRadiusAttr.value(), 150.)
if __name__ == '__main__':
unittest.main()
/// the selection is not possible if the current feature has no presentation for the current
/// attribute not in AIS not in results. If so, no object in current feature where make
/// coincidence, so selection is not necessary
- std::shared_ptr<ModelAPI_Data> aData = myFeature->data();
- std::shared_ptr<GeomDataAPI_Point2D> aPointAttr = std::dynamic_pointer_cast<GeomDataAPI_Point2D>(
- aData->attribute(attributeID()));
- std::shared_ptr<GeomAPI_Pnt2d> aPoint = aPointAttr->pnt();
-
bool aFoundPoint = false;
GeomShapePtr anAISShape;
GeomPresentablePtr aPrs = std::dynamic_pointer_cast<GeomAPI_IPresentable>(myFeature);
return true;
/// analysis of AIS
+ std::shared_ptr<ModelAPI_Data> aData = myFeature->data();
+ std::shared_ptr<GeomDataAPI_Point2D> aPointAttr = std::dynamic_pointer_cast<GeomDataAPI_Point2D>(
+ aData->attribute(attributeID()));
+ std::shared_ptr<GeomAPI_Pnt2d> aPoint = aPointAttr->pnt();
if (anAISShape.get())
aFoundPoint = shapeContainsPoint(anAISShape, aPoint, mySketch);
std::shared_ptr<ModelAPI_Data> aData = myFeature->data();
std::shared_ptr<GeomDataAPI_Point2D> aPoint = std::dynamic_pointer_cast<GeomDataAPI_Point2D>(
aData->attribute(attributeID()));
- QString aTextX = QString::fromStdString(aPoint->textX());
- QString aTextY = QString::fromStdString(aPoint->textY());
+ QString aTextX = QString::fromStdString(aPoint->isInitialized() ? aPoint->textX() : "0");
+ QString aTextY = QString::fromStdString(aPoint->isInitialized() ? aPoint->textY() : "0");
bool isDouble = false;
double aVal = 0;
#include "PartSetAPI_Part.h"
//--------------------------------------------------------------------------------------
#include <ModelAPI_ResultPart.h>
+#include <ModelHighAPI_Dumper.h>
//--------------------------------------------------------------------------------------
#include <PartSetPlugin_Duplicate.h>
#include <PartSetPlugin_Remove.h>
return std::dynamic_pointer_cast<ModelAPI_ResultPart>(defaultResult())->partDoc();
}
+void PartSetAPI_Part::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ theDumper << aBase << " = model.addPart(" << aDocName << ")" << std::endl;
+}
+
//--------------------------------------------------------------------------------------
PartPtr addPart(const std::shared_ptr<ModelAPI_Document> & thePart)
{
/// Return document
PARTSETAPI_EXPORT
std::shared_ptr<ModelAPI_Document> document() const;
+
+ /// Dump wrapped feature
+ PARTSETAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Part object
def tearDown(self):
model.end()
+ # assert(model.checkPythonDump())
+ # This test checks creation of High API classes from low-level.
+ # It does not set any attributes, so features invalid, and dump also invalid.
model.reset()
#-----------------------------------------------------------------------------
FeaturesAPI.FeaturesAPI_Rotation(self.part.addFeature("Rotation"))
FeaturesAPI.FeaturesAPI_Translation(self.part.addFeature("Translation"))
FeaturesAPI.FeaturesAPI_Group(self.part.addFeature("Group"))
-
+
import PrimitivesAPI
PrimitivesAPI.PrimitivesAPI_Box(self.part.addFeature("Box"))
def tearDown(self):
model.end()
+ assert(model.checkPythonDump())
model.reset()
self.assertEqual(extrusion.toSize().value(), 10)
self.assertEqual(extrusion.fromSize().value(), 0)
self.assertEqual(extrusion.toObject().context(), None)
- self.assertEqual(extrusion.toOffset().value(), 0)
+ self.assertEqual(extrusion.toOffset().isInitialized(), False)
self.assertEqual(extrusion.fromObject().context(), None)
- self.assertEqual(extrusion.fromOffset().value(), 0)
+ self.assertEqual(extrusion.fromOffset().isInitialized(), False)
def test_add_extrusion_by_face_and_planes(self):
# base
from_object, 20)
self.assertEqual(extrusion.creationMethod().value(), "ByPlanesAndOffsets")
- self.assertEqual(extrusion.toSize().value(), 0)
- self.assertEqual(extrusion.fromSize().value(), 0)
+ self.assertEqual(extrusion.toSize().isInitialized(), False)
+ self.assertEqual(extrusion.fromSize().isInitialized(), False)
# self.assertEqual(extrusion.getToObject().context(),
# to_sketch.result())
self.assertEqual(extrusion.toOffset().value(), 15)
self.assertEqual(self.extrusion.toSize().value(), 15)
self.assertEqual(self.extrusion.fromSize().value(), 20)
self.assertEqual(self.extrusion.toObject().context(), None)
- self.assertEqual(self.extrusion.toOffset().value(), 0)
+ self.assertEqual(self.extrusion.toOffset().isInitialized(), False)
self.assertEqual(self.extrusion.fromObject().context(), None)
- self.assertEqual(self.extrusion.fromOffset().value(), 0)
+ self.assertEqual(self.extrusion.fromOffset().isInitialized(), False)
def test_extrusion_set_planes_and_offsets(self):
# to
to_object = to_sketch.selectFace()[0]
from_object = from_sketch.selectFace()[0]
+
+ self.part.moveFeature(self.extrusion.feature(), from_sketch.feature())
+
self.extrusion.setPlanesAndOffsets(to_object, 15, from_object, 20)
def tearDown(self):
model.end()
+ assert(model.checkPythonDump())
model.reset()
def tearDown(self):
model.end()
+ assert(model.checkPythonDump())
def test_add_sketch(self):
plane = model.defaultPlane("XOY")
def tearDown(self):
model.end()
+ assert(model.checkPythonDump())
model.reset()
class SketcherSetParallel(SketcherTestCase):
def runTest(self):
l1 = self.sketch.addLine(0, 0, 0, 1)
- l2 = self.sketch.addLine(0, 1, 1, 1)
+ l2 = self.sketch.addLine(0, 1, 1, 0)
self.sketch.setParallel(l1, l2)
model.do()
mybase = model.addSketch(mypart, model.defaultPlane("XOY"))
-l1 = mybase.addLine(0, 0, 0, 1)
-l2 = mybase.addLine(0, 1, 1, 1)
-l3 = mybase.addLine(1, 1, 1, 0)
-l4 = mybase.addLine(1, 0, 0, 0)
+l1 = mybase.addLine(0, 0, 0, 25)
+l2 = mybase.addLine(0, 25, 25, 25)
+l3 = mybase.addLine(25, 25, 25, 0)
+l4 = mybase.addLine(25, 0, 0, 0)
mybase.setCoincident(l1.endPoint(), l2.startPoint())
mybase.setCoincident(l2.endPoint(), l3.startPoint())
mybase.setPerpendicular(l1, l4)
+mybase.setVertical(l1)
+mybase.setFixed(l1.startPoint())
+
mywidth = mybase.setLength(l1, 50)
mylength = mybase.setDistance(l1.startPoint(), l3, 50)
+model.do()
# Creating the extrusion
mybox = model.addExtrusion(mypart, mybase.selectFace(), 50)
+model.do()
# Creating a cylinder on a face of the box
thisface = "Extrusion_1_1/Generated_Face_2"
-thisxmin = "Extrusion_1_1/Generated_Face_3&Extrusion_1_1/Generated_Face_2"
-thisxmax = "Extrusion_1_1/Generated_Face_2&Extrusion_1_1/Generated_Face_1"
-thiszmin = "Sketch_1/Edge5_1"
+thisxmax = "Extrusion_1_1/Generated_Face_3&Extrusion_1_1/Generated_Face_2"
thiszmax = "Extrusion_1_1/Generated_Face_2&Extrusion_1_1/To_Face_1_1"
mystand = model.addSketch(mypart, thisface)
c1 = mystand.addCircle(0, 25, 5)
-mystand.setDistance(c1.center(), mystand.addLine(thisxmin), 10)
-mystand.setDistance(c1.center(), mystand.addLine(thiszmax), 10)
+l1 = mystand.addLine(thisxmax)
+l2 = mystand.addLine(thiszmax)
+model.do()
+mystand.setDistance(c1.center(), l1, 10)
+mystand.setDistance(c1.center(), l2, 10)
+model.do()
myboss = model.addExtrusion(mypart, mystand.selectFace(), -5)
+model.do()
# Subtracting the cylinder to the box
model.begin()
mybase.setValue(mylength, 100)
+model.do()
mybox.setSize(80)
model.end()
+
+assert(model.checkPythonDump())
mybase = model.addSketch(mypart, model.defaultPlane("XOY"))
p1 = geom.Pnt2d(0, 0)
-p2 = geom.Pnt2d(0, 1)
-p3 = geom.Pnt2d(1, 1)
-p4 = geom.Pnt2d(1, 0)
+p2 = geom.Pnt2d(0, 25)
+p3 = geom.Pnt2d(25, 25)
+p4 = geom.Pnt2d(25, 0)
line = model.addPolygon(mybase, p1, p2, p3, p4)
mybase.setParallel(line[1], line[3])
mybase.setPerpendicular(line[0], line[3])
+mybase.setVertical(line[0])
+mybase.setFixed(line[0].startPoint())
+
mywidth = mybase.setLength(line[0], 50)
mylength = mybase.setDistance(line[0].startPoint(), line[2], 50)
-
+model.do()
# Creating the extrusion
mybox = model.addExtrusion(mypart, mybase.selectFace(), 50)
+model.do()
# Creating a cylinder on a face of the box
circle = mystand.addCircle(0, 25, 5)
mystand.setDistance(circle.center(), mystand.addLine(thisxmin), 10)
mystand.setDistance(circle.center(), mystand.addLine(thiszmax), 10)
+model.do()
myboss = model.addExtrusion(mypart, mystand.selectFace(), -5)
-
+model.do()
# Subtracting the cylinder to the box
model.begin()
mybase.setValue(mylength, 100)
-mybox.setSize(20)
+model.do()
+mybox.setSize(40)
model.end()
+
+assert(model.checkPythonDump())
extension.addBoxScript( mypart, 10, 20, 30 )
model.end()
+assert(model.checkPythonDump())
\ No newline at end of file
boolean = model.addFuse(part, boolean.result() + b4.result())
model.end()
+
+assert(model.checkPythonDump())
# Built-in features
+from build import *
from sketcher import *
from connection import *
from construction import *
--- /dev/null
+"""Package for Build plugin for the Parametric Geometry API of the Modeler.
+"""
+
+from BuildAPI import addVertex, addEdge, addWire, addFace, addShell
+from BuildAPI import addSubShapes
--- /dev/null
+"""Package for dumping purposes.
+"""
+
+import ModelHighAPI
+
+import ModelAPI
+import SketchAPI
+
+import sys
+import inspect
+
+def singleton(cls):
+ instance = cls()
+ instance.__call__ = lambda: instance
+ return instance
+
+
+## @ingroup CPPHighAPI
+# Collect information about features that may be dumped and stores the model as a Python script
+@singleton
+class DumpAssistant(ModelHighAPI.ModelHighAPI_Dumper):
+
+ ## Constructor
+ def __init__(self):
+ ModelHighAPI.ModelHighAPI_Dumper.__init__(self)
+ ModelHighAPI.ModelHighAPI_Dumper.setInstance(self)
+ self.collectFeatures()
+
+ ## Collect feature wrappers, which allow dumping (have method dump)
+ def collectFeatures(self):
+ self.myFeatures = {}
+ for aModule in sys.modules:
+ for aName, anObj in inspect.getmembers(sys.modules[aModule], inspect.isclass):
+ if issubclass(anObj, ModelHighAPI.ModelHighAPI_Interface) and hasattr(anObj, "ID") and anObj.dump != ModelHighAPI.ModelHighAPI_Interface.dump:
+ self.myFeatures[anObj.ID()] = anObj
+
+ ## Create wrapper for a given feature and dump it
+ def dumpFeature(self, theFeature, theForce):
+ aFeatureKind = theFeature.getKind()
+ if aFeatureKind in self.myFeatures:
+ # Dump only feature created by user (in history).
+ # For all other features, just keep their name.
+ if theForce or theFeature.isInHistory():
+ self.myFeatures[aFeatureKind](theFeature).dump(self)
+ else:
+ self.name(theFeature)
+ self.clearNotDumped()
+ else:
+ # Probably the feature is a constraint, try to dump it with SketchAPI_Constraint.
+ # In case of theFeature is not a constraint, it will not be dumped.
+ self.myFeatures[SketchAPI.SketchAPI_Constraint.ID()](theFeature).dump(self)
+
+ ## Dump all parameters
+ def dumpParameter(self, theFeature):
+ aFeatureKind = theFeature.getKind()
+ if aFeatureKind == "Parameter" and aFeatureKind in self.myFeatures:
+ self.myFeatures[aFeatureKind](theFeature).dump(self)
+
+ ## Return getter for specified attribute
+ def attributeGetter(self, theFeature, theAttrName):
+ aFeatureKind = theFeature.getKind()
+ if aFeatureKind in self.myFeatures:
+ return self.myFeatures[aFeatureKind](theFeature).attributeGetter(theAttrName)
+ return std_string()
+
+# Instance of dumper
+dumper = DumpAssistant
\ No newline at end of file
--- /dev/null
+"""Package for dumping purposes.
+"""
+
+from DumpAssistant import *
"""
from FeaturesAPI import addPlacement, addRotation, addTranslation
-
-from FeaturesAPI import addCut, addFuse, addCommon, addSmash, addFill
-
-from FeaturesAPI import addPartition
-
from FeaturesAPI import addExtrusion, addExtrusionCut, addExtrusionFuse
from FeaturesAPI import addRevolution, addRevolutionCut, addRevolutionFuse
-
+from FeaturesAPI import addPipe
+from FeaturesAPI import addCut, addFuse, addCommon, addSmash, addFill
+from FeaturesAPI import addIntersection, addPartition, addUnion, addRemoveSubShapes
from FeaturesAPI import addGroup, addRecover
-
"""
from ModelHighAPI import moduleDocument, activeDocument
-from ModelHighAPI import defaultPlane
+from ModelHighAPI import defaultPlane, standardPlane
from ModelHighAPI import begin, end
from ModelHighAPI import apply as do
from ModelHighAPI import undo, redo
-from ModelHighAPI import reset
\ No newline at end of file
+from ModelHighAPI import reset
+from ModelHighAPI import ModelHighAPI_Selection as selection
+from ModelHighAPI import checkPythonDump as checkPythonDump
line = model.addPolygon(self.base, p1, p2, p3, p4)
- self.base.setParallel(line[0], line[2])
- self.base.setParallel(line[1], line[3])
- self.base.setPerpendicular(line[0], line[3])
+ self.base.setFixed(line[0].startPoint())
+ self.base.setVertical(line[0])
# Setting the size of the base with default values
# Width
- self.width = self.base.setLength(line[0], 50) # Keeps the constraint for edition
+ self.width = self.base.setLength(line[3], 50) # Keeps the constraint for edition
# Length
- self.length = self.base.setLength(line[3], 50) # Keeps the constraint for edition
+ self.length = self.base.setLength(line[0], 50) # Keeps the constraint for edition
+
+ # Keeping the rectangle
+ self.base.setParallel(line[0], line[2])
+ self.base.setParallel(line[1], line[3])
+ self.base.setPerpendicular(line[0], line[3])
+
+ # execute sketch
+ model.do()
# Creating the extrusion (the box) at default size
# A box result
SketchAPI.h
SketchAPI_Arc.h
SketchAPI_Circle.h
+ SketchAPI_Constraint.h
SketchAPI_IntersectionPoint.h
SketchAPI_Line.h
SketchAPI_Mirror.h
SET(PROJECT_SOURCES
SketchAPI_Arc.cpp
SketchAPI_Circle.cpp
+ SketchAPI_Constraint.cpp
SketchAPI_IntersectionPoint.cpp
SketchAPI_Line.cpp
SketchAPI_Mirror.cpp
${PROJECT_SOURCE_DIR}/src/ModelAPI
${PROJECT_SOURCE_DIR}/src/GeomDataAPI
${PROJECT_SOURCE_DIR}/src/ModelHighAPI
+ ${PROJECT_SOURCE_DIR}/src/SketcherPrs
)
# Plugin headers dependency
// shared pointers
%shared_ptr(SketchAPI_Arc)
%shared_ptr(SketchAPI_Circle)
+%shared_ptr(SketchAPI_Constraint)
%shared_ptr(SketchAPI_IntersectionPoint)
%shared_ptr(SketchAPI_Line)
%shared_ptr(SketchAPI_Mirror)
%shared_ptr(SketchAPI_Rotation)
%shared_ptr(SketchAPI_Translation)
-// TODO(spo): move typemaps into ModelHighAPI package
-
-// fix compilarion error: ‘res*’ was not declared in this scope
-%typemap(freearg) const std::list<ModelHighAPI_RefAttr> & {}
-%typemap(freearg) const std::list<std::shared_ptr<ModelAPI_Object> > & {}
-
-%typemap(in) const std::list<ModelHighAPI_RefAttr> & (std::list<ModelHighAPI_RefAttr> temp) {
+%typemap(in) const ModelHighAPI_RefAttr & (ModelHighAPI_RefAttr temp) {
std::shared_ptr<ModelAPI_Attribute> * temp_attribute;
+ std::shared_ptr<ModelAPI_Object> * temp_object;
+ std::shared_ptr<ModelHighAPI_Interface> * temp_interface;
+ ModelHighAPI_Selection* temp_selection;
int newmem = 0;
- if (PySequence_Check($input)) {
- for (Py_ssize_t i = 0; i < PySequence_Size($input); ++i) {
- PyObject * item = PySequence_GetItem($input, i);
- if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_attribute, $descriptor(std::shared_ptr<ModelAPI_Attribute> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
- if (!temp_attribute) {
- PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_RefAttr, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
- return NULL;
- }
- temp.push_back(ModelHighAPI_RefAttr(*temp_attribute));
- if (newmem & SWIG_CAST_NEW_MEMORY) {
- delete temp_attribute;
- }
- }
- Py_DECREF(item);
+ if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_selection, $descriptor(ModelHighAPI_Selection*), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_selection) {
+ PyErr_SetString(PyExc_TypeError, "argument must be ModelHighAPI_RefAttr, ModelHighAPI_Selection, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ return NULL;
+ }
+ temp = ModelHighAPI_RefAttr(std::shared_ptr<ModelAPI_Object>(temp_selection->resultSubShapePair().first));
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_selection;
}
$1 = &temp;
+ } else
+ if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_attribute, $descriptor(std::shared_ptr<ModelAPI_Attribute> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_attribute) {
+ PyErr_SetString(PyExc_TypeError, "argument must be ModelHighAPI_RefAttr, ModelHighAPI_Selection, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ return NULL;
+ }
+ temp = ModelHighAPI_RefAttr(*temp_attribute);
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_attribute;
+ }
+ $1 = &temp;
+ } else
+ if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_object, $descriptor(std::shared_ptr<ModelAPI_Object> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_object) {
+ PyErr_SetString(PyExc_TypeError, "argument must be ModelHighAPI_RefAttr, ModelHighAPI_Selection, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ return NULL;
+ }
+ temp = ModelHighAPI_RefAttr(*temp_object);
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_object;
+ }
+ $1 = &temp;
+ } else
+ if ((SWIG_ConvertPtrAndOwn($input, (void **)&temp_interface, $descriptor(std::shared_ptr<ModelHighAPI_Interface> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_interface) {
+ PyErr_SetString(PyExc_TypeError, "argument must be ModelHighAPI_RefAttr, ModelHighAPI_Selection, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ return NULL;
+ }
+ temp = ModelHighAPI_RefAttr(*temp_interface);
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_interface;
+ }
+ $1 = &temp;
+ } else
+ if ((SWIG_ConvertPtr($input, (void **)&$1, $1_descriptor, SWIG_POINTER_EXCEPTION)) == 0) {
} else {
- PyErr_SetString(PyExc_ValueError, "argument must be list of ModelHighAPI_RefAttr, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
+ PyErr_SetString(PyExc_TypeError, "argument must be ModelHighAPI_RefAttr, ModelHighAPI_Selection, ModelHighAPI_Interface, ModelAPI_Attribute or ModelAPI_Object.");
return NULL;
}
}
%typemap(in) const std::list<std::shared_ptr<ModelAPI_Object> > & (std::list<std::shared_ptr<ModelAPI_Object> > temp) {
std::shared_ptr<ModelAPI_Object> * temp_object;
std::shared_ptr<ModelHighAPI_Interface> * temp_interface;
+ ModelHighAPI_Selection* temp_selection;
int newmem = 0;
if (PySequence_Check($input)) {
for (Py_ssize_t i = 0; i < PySequence_Size($input); ++i) {
PyObject * item = PySequence_GetItem($input, i);
+ if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_selection, $descriptor(ModelHighAPI_Selection*), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
+ if (!temp_selection) {
+ PyErr_SetString(PyExc_TypeError, "argument must be ModelHighAPI_Interface, ModelHighAPI_Selection or ModelAPI_Object.");
+ return NULL;
+ }
+ temp.push_back(temp_selection->resultSubShapePair().first);
+ if (newmem & SWIG_CAST_NEW_MEMORY) {
+ delete temp_selection;
+ }
+ } else
if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_object, $descriptor(std::shared_ptr<ModelAPI_Object> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
if (!temp_object) {
- PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_Interface or ModelAPI_Object.");
+ PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_Interface, ModelHighAPI_Selection or ModelAPI_Object.");
return NULL;
}
temp.push_back(*temp_object);
} else
if ((SWIG_ConvertPtrAndOwn(item, (void **)&temp_interface, $descriptor(std::shared_ptr<ModelHighAPI_Interface> *), SWIG_POINTER_EXCEPTION, &newmem)) == 0) {
if (!temp_interface) {
- PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_Interface or ModelAPI_Object.");
+ PyErr_SetString(PyExc_TypeError, "argument must be list of ModelHighAPI_Interface, ModelHighAPI_Selection or ModelAPI_Object.");
return NULL;
}
temp.push_back((*temp_interface)->defaultResult());
%include "SketchAPI_Rectangle.h"
%include "SketchAPI_Rotation.h"
%include "SketchAPI_Sketch.h"
+%include "SketchAPI_Constraint.h"
#include <GeomAPI_Pnt2d.h>
#include <ModelHighAPI_Double.h>
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
execute();
}
+
+//==================================================================================================
+void SketchAPI_Arc::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ if (isCopy())
+ return; // no need to dump copied feature
+
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeSelectionPtr anExternal = aBase->selection(SketchPlugin_SketchEntity::EXTERNAL_ID());
+ if (anExternal->context()) {
+ // arc is external
+ theDumper << aBase << " = " << aSketchName << ".addArc(" << anExternal << ")" << std::endl;
+ } else {
+ AttributeStringPtr aType = arcType();
+ if (aType->value() == SketchPlugin_Arc::ARC_TYPE_CENTER_START_END()) {
+ // arc given by center and start, end points
+ theDumper << aBase << " = " << aSketchName << ".addArc(" << center() << ", "
+ << startPoint() << ", " << endPoint() << ", " << inversed() << ")" << std::endl;
+ } else if (aType->value() == SketchPlugin_Arc::ARC_TYPE_THREE_POINTS()) {
+ // arc given by three points
+ theDumper << aBase << " = " << aSketchName << ".addArc(" << startPoint() << ", "
+ << endPoint() << ", " << passedPoint() << ")" << std::endl;
+ } else {
+ // tangent arc
+ AttributeRefAttrPtr aTangentPoint = tangentPoint();
+ theDumper << aBase << " = " << aSketchName << ".addArc("
+ << aTangentPoint << ", " << endPoint() << ", " << inversed() << ")" << std::endl;
+ }
+ }
+ // dump "auxiliary" flag if necessary
+ SketchAPI_SketchEntity::dump(theDumper);
+}
/// Set angle.
SKETCHAPI_EXPORT
void setAngle(double theAngle);
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Arc object.
#include <GeomAPI_Pnt2d.h>
#include <ModelHighAPI_Double.h>
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
execute();
}
+
+//==================================================================================================
+void SketchAPI_Circle::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ if (isCopy())
+ return; // no need to dump copied feature
+
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeSelectionPtr anExternal = aBase->selection(SketchPlugin_SketchEntity::EXTERNAL_ID());
+ if (anExternal->context()) {
+ // circle is external
+ theDumper << aBase << " = " << aSketchName << ".addCircle(" << anExternal << ")" << std::endl;
+ } else {
+ AttributeStringPtr aType = circleType();
+ if (aType->value() == SketchPlugin_Circle::CIRCLE_TYPE_CENTER_AND_RADIUS()) {
+ // circle given by center and radius
+ theDumper << aBase << " = " << aSketchName << ".addCircle("
+ << center() << ", " << radius() << ")" << std::endl;
+ } else {
+ // circle given by three points
+ theDumper << aBase << " = " << aSketchName << ".addCircle(" << firstPoint() << ", "
+ << secondPoint() << ", " << thirdPoint() << ")" << std::endl;
+ }
+ }
+ // dump "auxiliary" flag if necessary
+ SketchAPI_SketchEntity::dump(theDumper);
+}
/// Set third point.
SKETCHAPI_EXPORT
void setThirdPoint(const std::shared_ptr<GeomAPI_Pnt2d>& thePoint);
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
/// Pointer on Circle object.
--- /dev/null
+// Name : SketchAPI_Constraint.cpp
+// Purpose:
+//
+// History:
+// 08/08/16 - Artem ZHIDKOV - Creation of the file
+
+#include "SketchAPI_Constraint.h"
+
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Tools.h>
+
+#include <SketchPlugin_Constraint.h>
+#include <SketchPlugin_ConstraintAngle.h>
+#include <SketchPlugin_ConstraintCoincidence.h>
+#include <SketchPlugin_ConstraintCollinear.h>
+#include <SketchPlugin_ConstraintDistance.h>
+#include <SketchPlugin_ConstraintEqual.h>
+#include <SketchPlugin_ConstraintHorizontal.h>
+#include <SketchPlugin_ConstraintLength.h>
+#include <SketchPlugin_ConstraintMiddle.h>
+#include <SketchPlugin_ConstraintParallel.h>
+#include <SketchPlugin_ConstraintPerpendicular.h>
+#include <SketchPlugin_ConstraintRadius.h>
+#include <SketchPlugin_ConstraintRigid.h>
+#include <SketchPlugin_ConstraintTangent.h>
+#include <SketchPlugin_ConstraintVertical.h>
+
+#include <SketcherPrs_Tools.h>
+
+SketchAPI_Constraint::SketchAPI_Constraint(
+ const std::shared_ptr<ModelAPI_Feature> & theFeature)
+: ModelHighAPI_Interface(theFeature)
+{
+ ConstraintPtr aConstraint = std::dynamic_pointer_cast<SketchPlugin_Constraint>(theFeature);
+ if (aConstraint)
+ initialize();
+}
+
+SketchAPI_Constraint::~SketchAPI_Constraint()
+{
+}
+
+bool SketchAPI_Constraint::initialize()
+{
+ if (!feature()) {
+ throwException("Constraint exception: The feature is NULL.");
+ return false;
+ }
+ return true;
+}
+
+static const std::string& constraintTypeToSetter(const std::string& theType)
+{
+ if (theType == SketchPlugin_ConstraintCoincidence::ID()) {
+ static const std::string COINCIDENCE_SETTER("setCoincident");
+ return COINCIDENCE_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintAngle::ID()) {
+ static const std::string ANGLE_SETTER("setAngle");
+ return ANGLE_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintCollinear::ID()) {
+ static const std::string COLLINEAR_SETTER("setCollinear");
+ return COLLINEAR_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintDistance::ID()) {
+ static const std::string DISTANCE_SETTER("setDistance");
+ return DISTANCE_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintEqual::ID()) {
+ static const std::string EQUAL_SETTER("setEqual");
+ return EQUAL_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintHorizontal::ID()) {
+ static const std::string HORIZONTAL_SETTER("setHorizontal");
+ return HORIZONTAL_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintLength::ID()) {
+ static const std::string LENGTH_SETTER("setLength");
+ return LENGTH_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintMiddle::ID()) {
+ static const std::string MIDDLE_SETTER("setMiddlePoint");
+ return MIDDLE_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintParallel::ID()) {
+ static const std::string PARALLEL_SETTER("setParallel");
+ return PARALLEL_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintPerpendicular::ID()) {
+ static const std::string PERPENDICULAR_SETTER("setPerpendicular");
+ return PERPENDICULAR_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintRadius::ID()) {
+ static const std::string RADIUS_SETTER("setRadius");
+ return RADIUS_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintRigid::ID()) {
+ static const std::string FIXED_SETTER("setFixed");
+ return FIXED_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintTangent::ID()) {
+ static const std::string TANGENT_SETTER("setTangent");
+ return TANGENT_SETTER;
+ }
+ if (theType == SketchPlugin_ConstraintVertical::ID()) {
+ static const std::string VERTICAL_SETTER("setVertical");
+ return VERTICAL_SETTER;
+ }
+
+ static const std::string DUMMY;
+ return DUMMY;
+}
+
+static std::string angleTypeToString(int theAngleType)
+{
+ switch (theAngleType) {
+ case SketcherPrs_Tools::ANGLE_COMPLEMENTARY:
+ return std::string("Complementary");
+ case SketcherPrs_Tools::ANGLE_BACKWARD:
+ return std::string("Backward");
+ default:
+ break;
+ }
+ return std::string();
+}
+
+void SketchAPI_Constraint::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ ConstraintPtr aConstraint = std::dynamic_pointer_cast<SketchPlugin_Constraint>(aBase);
+ if (!aConstraint)
+ return; // dump constraints only
+
+ // do not need to dump "Fixed" constraint for external object
+ if (aConstraint->getKind() == SketchPlugin_ConstraintRigid::ID()) {
+ AttributeRefAttrPtr aRefAttr = aConstraint->refattr(SketchPlugin_Constraint::ENTITY_A());
+ std::shared_ptr<SketchPlugin_Feature> aSketchFeature =
+ std::dynamic_pointer_cast<SketchPlugin_Feature>(
+ ModelAPI_Feature::feature(aRefAttr->object()));
+ if (!aSketchFeature || aSketchFeature->isExternal())
+ return;
+ }
+
+ const std::string& aSetter = constraintTypeToSetter(aConstraint->getKind());
+ if (aSetter.empty())
+ return; // incorrect constraint type
+ bool isAngle = aConstraint->getKind() == SketchPlugin_ConstraintAngle::ID();
+ std::string aSetterSuffix;
+ if (isAngle)
+ aSetterSuffix = angleTypeToString(aConstraint->integer(
+ SketchPlugin_ConstraintAngle::TYPE_ID())->value());
+
+ const std::string& aSketchName = theDumper.parentName(aConstraint);
+ theDumper << aBase << " = " << aSketchName << "." << aSetter << aSetterSuffix << "(";
+
+ bool isFirstAttr = true;
+ for (int i = 0; i < CONSTRAINT_ATTR_SIZE; ++i) {
+ AttributeRefAttrPtr aRefAttr = aConstraint->refattr(SketchPlugin_Constraint::ATTRIBUTE(i));
+ if (aRefAttr && aRefAttr->isInitialized()) {
+ theDumper << (isFirstAttr ? "" : ", ") << aRefAttr;
+ isFirstAttr = false;
+ }
+ }
+
+ AttributeDoublePtr aValueAttr = aConstraint->real(
+ isAngle ? SketchPlugin_ConstraintAngle::ANGLE_VALUE_ID() :SketchPlugin_Constraint::VALUE());
+ if (aValueAttr && aValueAttr->isInitialized())
+ theDumper << ", " << aValueAttr;
+
+ theDumper << ")" << std::endl;
+}
--- /dev/null
+// Name : SketchAPI_Constraint.h
+// Purpose:
+//
+// History:
+// 08/08/16 - Artem ZHIDKOV - Creation of the file
+
+#ifndef SRC_SKETCHAPI_SKETCHAPI_CONSTRAINT_H_
+#define SRC_SKETCHAPI_SKETCHAPI_CONSTRAINT_H_
+
+#include "SketchAPI.h"
+
+#include <ModelHighAPI_Interface.h>
+#include <ModelHighAPI_Macro.h>
+#include <ModelHighAPI_RefAttr.h>
+
+#include <SketchPlugin_Constraint.h>
+
+/**\class SketchAPI_Constraint
+ * \ingroup CPPHighAPI
+ * \brief Interface for Constraint feature
+ */
+class SketchAPI_Constraint : public ModelHighAPI_Interface
+{
+public:
+ /// Constructor without values
+ SKETCHAPI_EXPORT
+ explicit SketchAPI_Constraint(const std::shared_ptr<ModelAPI_Feature> & theFeature);
+
+ /// Destructor
+ SKETCHAPI_EXPORT
+ virtual ~SketchAPI_Constraint();
+
+ static std::string ID()
+ {
+ static const std::string DUMMY;
+ return DUMMY;
+ }
+ virtual std::string getID() { return ID(); }
+
+ SKETCHAPI_EXPORT
+ bool initialize();
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+};
+
+#endif
//--------------------------------------------------------------------------------------
#include <GeomAPI_Pnt2d.h>
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
}
//--------------------------------------------------------------------------------------
+
+void SketchAPI_IntersectionPoint::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeSelectionPtr aLine = externalLine();
+ theDumper << aBase << " = " << aSketchName << ".addIntersectionPoint(" << aLine << ")" << std::endl;
+ // dump "auxiliary" flag if necessary
+ SketchAPI_SketchEntity::dump(theDumper);
+}
/// Set by external name
SKETCHAPI_EXPORT
void setByExternalLineName(const std::string & theExternalLineName);
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on IntersectionPoint object
//--------------------------------------------------------------------------------------
#include <GeomAPI_Pnt2d.h>
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
//--------------------------------------------------------------------------------------
+void SketchAPI_Line::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ if (isCopy())
+ return; // no need to dump copied feature
+
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeSelectionPtr anExternal = aBase->selection(SketchPlugin_SketchEntity::EXTERNAL_ID());
+ if (anExternal->context()) {
+ // line is external
+ theDumper << aBase << " = " << aSketchName << ".addLine(" << anExternal << ")" << std::endl;
+ } else {
+ // segment given by its points
+ theDumper << aBase << " = " << aSketchName << ".addLine("
+ << startPoint() << ", " << endPoint() << ")" << std::endl;
+ }
+ // dump "auxiliary" flag if necessary
+ SketchAPI_SketchEntity::dump(theDumper);
+}
/// Set end point
SKETCHAPI_EXPORT
void setEndPoint(const std::shared_ptr<GeomAPI_Pnt2d> & thePoint);
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Line object
//--------------------------------------------------------------------------------------
#include "SketchAPI_Mirror.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
SketchAPI_Mirror::SketchAPI_Mirror(
const std::shared_ptr<ModelAPI_Feature> & theFeature)
-: SketchAPI_SketchEntity(theFeature)
+: ModelHighAPI_Interface(theFeature)
{
initialize();
}
const std::shared_ptr<ModelAPI_Feature> & theFeature,
const ModelHighAPI_RefAttr & theMirrorLine,
const std::list<std::shared_ptr<ModelAPI_Object> > & theObjects)
-: SketchAPI_SketchEntity(theFeature)
+: ModelHighAPI_Interface(theFeature)
{
if (initialize()) {
fillAttribute(theMirrorLine, mirrorLine());
}
//--------------------------------------------------------------------------------------
+
+void SketchAPI_Mirror::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeRefAttrPtr aMirrorLine = mirrorLine();
+ AttributeRefListPtr aMirrorObjects = mirrorList();
+ theDumper << aBase << " = " << aSketchName << ".addMirror(" << aMirrorLine << ", "
+ << aMirrorObjects << ")" << std::endl;
+}
#include <SketchPlugin_ConstraintMirror.h>
-#include "SketchAPI_SketchEntity.h"
+#include <ModelHighAPI_Interface.h>
+#include <ModelHighAPI_Macro.h>
//--------------------------------------------------------------------------------------
class ModelAPI_Object;
class ModelHighAPI_RefAttr;
* \ingroup CPPHighAPI
* \brief Interface for Mirror feature
*/
-class SketchAPI_Mirror : public SketchAPI_SketchEntity
+class SketchAPI_Mirror : public ModelHighAPI_Interface
{
public:
/// Constructor without values
mirroredObjects, SketchPlugin_ConstraintMirror::ENTITY_C(), ModelAPI_AttributeRefList, /** Mirrored objects */
)
+ /// Dump wrapped feature
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Mirror object
//--------------------------------------------------------------------------------------
#include <GeomAPI_Pnt2d.h>
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
}
//--------------------------------------------------------------------------------------
+
+void SketchAPI_Point::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ if (isCopy())
+ return; // no need to dump copied feature
+
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeSelectionPtr anExternal = aBase->selection(SketchPlugin_SketchEntity::EXTERNAL_ID());
+ if (anExternal->context()) {
+ // point is external
+ theDumper << aBase << " = " << aSketchName << ".addPoint(" << anExternal << ")" << std::endl;
+ } else {
+ // point given by coordinates
+ std::shared_ptr<GeomDataAPI_Point2D> aPoint = coordinates();
+ theDumper << aBase << " = " << aSketchName << ".addPoint(" << aPoint << ")" << std::endl;
+ }
+ // dump "auxiliary" flag if necessary
+ SketchAPI_SketchEntity::dump(theDumper);
+}
/// Set by external name
SKETCHAPI_EXPORT
void setByExternalName(const std::string & theExternalName);
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Point object
//--------------------------------------------------------------------------------------
#include "SketchAPI_Projection.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
+#include <ModelHighAPI_Selection.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
SketchAPI_Projection::SketchAPI_Projection(
}
}
+SketchAPI_Projection::SketchAPI_Projection(
+ const std::shared_ptr<ModelAPI_Feature> & theFeature,
+ const std::string & theExternalName)
+: SketchAPI_SketchEntity(theFeature)
+{
+ if (initialize()) {
+ setByExternalName(theExternalName);
+ }
+}
+
SketchAPI_Projection::~SketchAPI_Projection()
{
execute();
}
+void SketchAPI_Projection::setByExternalName(const std::string& theExternalName)
+{
+ fillAttribute(ModelHighAPI_Selection("EDGE", theExternalName), external());
+
+ execute();
+}
+
//--------------------------------------------------------------------------------------
+
+void SketchAPI_Projection::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeSelectionPtr anExternal = externalFeature();
+ theDumper << aBase << " = " << aSketchName << ".addProjection(" << anExternal << ")" << std::endl;
+ // dump "auxiliary" flag if necessary
+ SketchAPI_SketchEntity::dump(theDumper);
+}
SKETCHAPI_EXPORT
SketchAPI_Projection(const std::shared_ptr<ModelAPI_Feature> & theFeature,
const ModelHighAPI_Selection & theExternalFeature);
+ /// Constructor with values
+ SKETCHAPI_EXPORT
+ SketchAPI_Projection(const std::shared_ptr<ModelAPI_Feature> & theFeature,
+ const std::string & theExternalName);
/// Destructor
SKETCHAPI_EXPORT
virtual ~SketchAPI_Projection();
INTERFACE_3(SketchPlugin_Projection::ID(),
externalFeature, SketchPlugin_Projection::EXTERNAL_FEATURE_ID(), ModelAPI_AttributeSelection, /** External feature */,
- projectedFeature, SketchPlugin_Projection::EXTERNAL_FEATURE_ID(), ModelAPI_AttributeRefAttr, /** Projected feature */,
+ projectedFeature, SketchPlugin_Projection::PROJECTED_FEATURE_ID(), ModelAPI_AttributeRefAttr, /** Projected feature */,
external, SketchPlugin_Projection::EXTERNAL_ID(), ModelAPI_AttributeSelection, /** External */
)
/// Set external feature
SKETCHAPI_EXPORT
void setExternalFeature(const ModelHighAPI_Selection & theExternalLine);
+
+ /// Set by external name
+ SKETCHAPI_EXPORT
+ void setByExternalName(const std::string & theExternalName);
+
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Projection object
//--------------------------------------------------------------------------------------
#include "SketchAPI_Rotation.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
SketchAPI_Rotation::SketchAPI_Rotation(
const std::shared_ptr<ModelAPI_Feature> & theFeature)
-: SketchAPI_SketchEntity(theFeature)
+: ModelHighAPI_Interface(theFeature)
{
initialize();
}
const ModelHighAPI_Double & theAngle,
const ModelHighAPI_Integer & theNumberOfObjects,
bool theFullValue)
-: SketchAPI_SketchEntity(theFeature)
+: ModelHighAPI_Interface(theFeature)
{
if (initialize()) {
fillAttribute(theObjects, rotationList());
fillAttribute(theCenter, center());
fillAttribute(theAngle, angle());
fillAttribute(theNumberOfObjects, numberOfObjects());
- if (theFullValue)
- fillAttribute("SingleAngle", valueType());
+ fillAttribute(theFullValue ? "FullAngle" : "SingleAngle", valueType());
- execute();
+ execute(true);
}
}
}
//--------------------------------------------------------------------------------------
+
+void SketchAPI_Rotation::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeRefListPtr aRotObjects = rotationList();
+ AttributeRefAttrPtr aCenter = center();
+ AttributeDoublePtr anAngle = angle();
+ AttributeIntegerPtr aNbCopies = numberOfObjects();
+ bool isFullValue = valueType()->value() != "SingleAngle";
+
+ theDumper << aBase << " = " << aSketchName << ".addRotation("
+ << aRotObjects << ", " << aCenter << ", " << anAngle << ", " << aNbCopies;
+ if (isFullValue)
+ theDumper << ", " << isFullValue;
+ theDumper << ")" << std::endl;
+}
#include <SketchPlugin_MultiRotation.h>
-#include "SketchAPI_SketchEntity.h"
+#include <ModelHighAPI_Interface.h>
+#include <ModelHighAPI_Macro.h>
//--------------------------------------------------------------------------------------
class ModelAPI_Object;
class ModelHighAPI_Double;
* \ingroup CPPHighAPI
* \brief Interface for Rotation feature
*/
-class SketchAPI_Rotation : public SketchAPI_SketchEntity
+class SketchAPI_Rotation : public ModelHighAPI_Interface
{
public:
/// Constructor without values
rotatedObjects, SketchPlugin_MultiRotation::ENTITY_B(), ModelAPI_AttributeRefList, /** Rotated objects */
)
+ /// Dump wrapped feature
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Rotation object
#include <SketchPlugin_ConstraintRigid.h>
#include <SketchPlugin_ConstraintTangent.h>
#include <SketchPlugin_ConstraintVertical.h>
+#include <SketcherPrs_Tools.h>
//--------------------------------------------------------------------------------------
#include <ModelAPI_CompositeFeature.h>
#include <ModelAPI_ResultConstruction.h>
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_RefAttr.h>
#include <ModelHighAPI_Selection.h>
+#include <ModelHighAPI_Services.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
#include "SketchAPI_Arc.h"
}
}
+SketchAPI_Sketch::SketchAPI_Sketch(
+ const std::shared_ptr<ModelAPI_Feature> & theFeature,
+ std::shared_ptr<ModelAPI_Object> thePlaneObject)
+: ModelHighAPI_Interface(theFeature)
+{
+ if (initialize()) {
+ setExternal(thePlaneObject);
+ }
+}
+
SketchAPI_Sketch::~SketchAPI_Sketch()
{
execute();
}
+void SketchAPI_Sketch::setExternal(std::shared_ptr<ModelAPI_Object> thePlaneObject)
+{
+ ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(thePlaneObject);
+ ModelHighAPI_Selection aSel(aRes);
+ setExternal(aSel);
+}
+
//--------------------------------------------------------------------------------------
void SketchAPI_Sketch::setValue(
const std::shared_ptr<ModelAPI_Feature> & theConstraint,
return SketchPtr(new SketchAPI_Sketch(aFeature, ModelHighAPI_Selection("FACE", theExternalName)));
}
+SketchPtr addSketch(const std::shared_ptr<ModelAPI_Document> & thePart,
+ std::shared_ptr<ModelAPI_Object> thePlaneObject)
+{
+ std::shared_ptr<ModelAPI_Feature> aFeature = thePart->addFeature(SketchAPI_Sketch::ID());
+ return SketchPtr(new SketchAPI_Sketch(aFeature, thePlaneObject));
+}
+
+
//--------------------------------------------------------------------------------------
std::shared_ptr<SketchAPI_Point> SketchAPI_Sketch::addPoint(
double theX, double theY)
std::shared_ptr<SketchAPI_Line> SketchAPI_Sketch::addLine(const ModelHighAPI_Selection & theExternal)
{
std::shared_ptr<ModelAPI_Feature> aFeature = compositeFeature()->addFeature(SketchPlugin_Line::ID());
- LinePtr aLine(new SketchAPI_Line(aFeature, theExternal));
- setFixed(InterfacePtr(aLine));
- return aLine;
+ return LinePtr(new SketchAPI_Line(aFeature, theExternal));
}
std::shared_ptr<SketchAPI_Line> SketchAPI_Sketch::addLine(const std::string & theExternalName)
{
std::shared_ptr<ModelAPI_Feature> aFeature = compositeFeature()->addFeature(SketchPlugin_Line::ID());
- LinePtr aLine(new SketchAPI_Line(aFeature, theExternalName));
- setFixed(InterfacePtr(aLine));
- return aLine;
+ return LinePtr(new SketchAPI_Line(aFeature, theExternalName));
}
//--------------------------------------------------------------------------------------
return ProjectionPtr(new SketchAPI_Projection(aFeature, theExternalFeature));
}
+std::shared_ptr<SketchAPI_Projection> SketchAPI_Sketch::addProjection(
+ const std::string & theExternalName)
+{
+ std::shared_ptr<ModelAPI_Feature> aFeature = compositeFeature()->addFeature(SketchPlugin_Projection::ID());
+ return ProjectionPtr(new SketchAPI_Projection(aFeature, theExternalName));
+}
+
//--------------------------------------------------------------------------------------
std::shared_ptr<SketchAPI_Mirror> SketchAPI_Sketch::addMirror(
const ModelHighAPI_RefAttr & theMirrorLine,
const ModelHighAPI_RefAttr & theLine2,
const ModelHighAPI_Double & theValue)
{
- // TODO(spo): is support of angle type necessary?
std::shared_ptr<ModelAPI_Feature> aFeature =
compositeFeature()->addFeature(SketchPlugin_ConstraintAngle::ID());
+ fillAttribute(SketcherPrs_Tools::ANGLE_DIRECT,
+ aFeature->integer(SketchPlugin_ConstraintAngle::TYPE_ID()));
fillAttribute(theLine1, aFeature->refattr(SketchPlugin_Constraint::ENTITY_A()));
fillAttribute(theLine2, aFeature->refattr(SketchPlugin_Constraint::ENTITY_B()));
fillAttribute(theValue, aFeature->real(SketchPlugin_Constraint::VALUE()));
return aFeature;
}
+std::shared_ptr<ModelAPI_Feature> SketchAPI_Sketch::setAngleComplementary(
+ const ModelHighAPI_RefAttr & theLine1,
+ const ModelHighAPI_RefAttr & theLine2,
+ const ModelHighAPI_Double & theValue)
+{
+ std::shared_ptr<ModelAPI_Feature> aFeature =
+ compositeFeature()->addFeature(SketchPlugin_ConstraintAngle::ID());
+ fillAttribute(SketcherPrs_Tools::ANGLE_COMPLEMENTARY,
+ aFeature->integer(SketchPlugin_ConstraintAngle::TYPE_ID()));
+ fillAttribute(theValue, aFeature->real(SketchPlugin_ConstraintAngle::ANGLE_VALUE_ID()));
+ fillAttribute(theLine1, aFeature->refattr(SketchPlugin_Constraint::ENTITY_A()));
+ fillAttribute(theLine2, aFeature->refattr(SketchPlugin_Constraint::ENTITY_B()));
+// fillAttribute(theValue, aFeature->real(SketchPlugin_Constraint::VALUE()));
+ aFeature->execute();
+ return aFeature;
+}
+
+std::shared_ptr<ModelAPI_Feature> SketchAPI_Sketch::setAngleBackward(
+ const ModelHighAPI_RefAttr & theLine1,
+ const ModelHighAPI_RefAttr & theLine2,
+ const ModelHighAPI_Double & theValue)
+{
+ std::shared_ptr<ModelAPI_Feature> aFeature =
+ compositeFeature()->addFeature(SketchPlugin_ConstraintAngle::ID());
+ fillAttribute(SketcherPrs_Tools::ANGLE_BACKWARD,
+ aFeature->integer(SketchPlugin_ConstraintAngle::TYPE_ID()));
+ fillAttribute(theValue, aFeature->real(SketchPlugin_ConstraintAngle::ANGLE_VALUE_ID()));
+ fillAttribute(theLine1, aFeature->refattr(SketchPlugin_Constraint::ENTITY_A()));
+ fillAttribute(theLine2, aFeature->refattr(SketchPlugin_Constraint::ENTITY_B()));
+// fillAttribute(theValue, aFeature->real(SketchPlugin_Constraint::VALUE()));
+ aFeature->execute();
+ return aFeature;
+}
+
std::shared_ptr<ModelAPI_Feature> SketchAPI_Sketch::setCoincident(
const ModelHighAPI_RefAttr & thePoint1,
const ModelHighAPI_RefAttr & thePoint2)
}
//--------------------------------------------------------------------------------------
+
+void SketchAPI_Sketch::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aDocName = theDumper.name(aBase->document());
+
+ AttributeSelectionPtr anExternal = aBase->selection(SketchPlugin_SketchEntity::EXTERNAL_ID());
+ if (anExternal->value()) {
+ theDumper << aBase << " = model.addSketch(" << aDocName << ", " << anExternal << ")" << std::endl;
+ } else {
+ // Sketch is base on a plane.
+ std::shared_ptr<GeomAPI_Pnt> anOrigin = std::dynamic_pointer_cast<GeomDataAPI_Point>(
+ aBase->attribute(SketchPlugin_Sketch::ORIGIN_ID()))->pnt();
+ std::shared_ptr<GeomAPI_Dir> aNormal = std::dynamic_pointer_cast<GeomDataAPI_Dir>(
+ aBase->attribute(SketchPlugin_Sketch::NORM_ID()))->dir();
+ std::shared_ptr<GeomAPI_Dir> aDirX = std::dynamic_pointer_cast<GeomDataAPI_Dir>(
+ aBase->attribute(SketchPlugin_Sketch::DIRX_ID()))->dir();
+
+ // Check the plane is coordinate plane
+ std::string aPlaneName = defaultPlane(anOrigin, aNormal, aDirX);
+ if (anExternal->context()) { // checking for selected planes
+ if (!aPlaneName.empty()) {
+ // dump sketch based on coordinate plane
+ theDumper << aBase << " = model.addSketch(" << aDocName
+ << ", model.standardPlane(\"" << aPlaneName << "\"))" << std::endl;
+ } else { // some other plane
+ theDumper << aBase << " = model.addSketch(" << aDocName << ", " << anExternal<< ")" << std::endl;
+ }
+ } else {
+ if (aPlaneName.empty()) {
+ // needs import additional module
+ theDumper.importModule("GeomAPI");
+ // dump plane parameters
+ const std::string& aSketchName = theDumper.name(aBase);
+ std::string anOriginName = aSketchName + "_origin";
+ std::string aNormalName = aSketchName + "_norm";
+ std::string aDirXName = aSketchName + "_dirx";
+ // use "\n" instead of std::endl to avoid automatic dumping sketch here
+ // and then dumplicate dumping it in the next line
+ theDumper << anOriginName << " = " << anOrigin << "\n"
+ << aNormalName << " = " << aNormal << "\n"
+ << aDirXName << " = " << aDirX << "\n";
+ // dump sketch based on arbitrary plane
+ theDumper << aBase << " = model.addSketch(" << aDocName << ", GeomAPI_Ax3("
+ << anOriginName << ", " << aDirXName << ", " << aNormalName << "))" << std::endl;
+ } else {
+ // dump sketch based on coordinate plane
+ theDumper << aBase << " = model.addSketch(" << aDocName
+ << ", model.defaultPlane(\"" << aPlaneName << "\"))" << std::endl;
+ }
+ }
+ }
+
+ // dump sketch's subfeatures
+ CompositeFeaturePtr aCompFeat = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(aBase);
+ theDumper.processSubs(aCompFeat, true);
+}
SKETCHAPI_EXPORT
SketchAPI_Sketch(const std::shared_ptr<ModelAPI_Feature> & theFeature,
const ModelHighAPI_Selection & theExternal);
+ /// Constructor with values
+ SKETCHAPI_EXPORT
+ SketchAPI_Sketch(const std::shared_ptr<ModelAPI_Feature> & theFeature,
+ std::shared_ptr<ModelAPI_Object> thePlaneObject);
/// Destructor
SKETCHAPI_EXPORT
virtual ~SketchAPI_Sketch();
SKETCHAPI_EXPORT
void setExternal(const ModelHighAPI_Selection & theExternal);
+ /// Set external
+ SKETCHAPI_EXPORT
+ void setExternal(std::shared_ptr<ModelAPI_Object> thePlaneObject);
+
/// Add point
SKETCHAPI_EXPORT
std::shared_ptr<SketchAPI_Point> addPoint(
std::shared_ptr<SketchAPI_Projection> addProjection(
const ModelHighAPI_Selection & theExternalFeature);
+ /// Add projection
+ SKETCHAPI_EXPORT
+ std::shared_ptr<SketchAPI_Projection> addProjection(const std::string & theExternalName);
+
/// Add mirror
SKETCHAPI_EXPORT
std::shared_ptr<SketchAPI_Mirror> addMirror(
const ModelHighAPI_RefAttr & theLine2,
const ModelHighAPI_Double & theValue);
+ /// Set complementary angle
+ SKETCHAPI_EXPORT
+ std::shared_ptr<ModelAPI_Feature> setAngleComplementary(
+ const ModelHighAPI_RefAttr & theLine1,
+ const ModelHighAPI_RefAttr & theLine2,
+ const ModelHighAPI_Double & theValue);
+
+ /// Set backward angle (= 360 - angle)
+ SKETCHAPI_EXPORT
+ std::shared_ptr<ModelAPI_Feature> setAngleBackward(
+ const ModelHighAPI_RefAttr & theLine1,
+ const ModelHighAPI_RefAttr & theLine2,
+ const ModelHighAPI_Double & theValue);
+
/// Set coincident
SKETCHAPI_EXPORT
std::shared_ptr<ModelAPI_Feature> setCoincident(
SKETCHAPI_EXPORT
std::list<ModelHighAPI_Selection> selectFace() const;
+ /// Dump wrapped feature
+ SKETCHAPI_EXPORT
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
protected:
std::shared_ptr<ModelAPI_CompositeFeature> compositeFeature() const;
SketchPtr addSketch(const std::shared_ptr<ModelAPI_Document> & thePart,
const std::string & theExternalName);
+/**\ingroup CPPHighAPI
+ * \brief Create Sketch feature
+ */
+SKETCHAPI_EXPORT
+SketchPtr addSketch(const std::shared_ptr<ModelAPI_Document> & thePart,
+ std::shared_ptr<ModelAPI_Object> thePlaneObject);
+
//--------------------------------------------------------------------------------------
//--------------------------------------------------------------------------------------
#endif /* SRC_SKETCHAPI_SKETCHAPI_SKETCH_H_ */
//--------------------------------------------------------------------------------------
#include "SketchAPI_SketchEntity.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
SketchAPI_SketchEntity::SketchAPI_SketchEntity(
}
//--------------------------------------------------------------------------------------
+void SketchAPI_SketchEntity::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ AttributeBooleanPtr anAux = aBase->boolean(SketchPlugin_SketchEntity::AUXILIARY_ID());
+ if (anAux->value()) {
+ const std::string& aName = theDumper.name(aBase);
+ theDumper << aName << ".setAuxiliary(" << anAux << ")" <<std::endl;
+ }
+}
+
+bool SketchAPI_SketchEntity::isCopy() const
+{
+ // check the feature is a copy of another entity
+ std::shared_ptr<SketchPlugin_SketchEntity> aSketchEntity =
+ std::dynamic_pointer_cast<SketchPlugin_SketchEntity>(feature());
+ return aSketchEntity && aSketchEntity->isCopy();
+}
SKETCHAPI_EXPORT
void setAuxiliary(bool theAuxiliary);
+ /// Dump wrapped feature
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
+
protected:
std::shared_ptr<ModelAPI_AttributeBoolean> myAuxiliary;
bool initialize();
+
+ /// Check the entity is a copy of another feature
+ bool isCopy() const;
};
//! Pointer on SketchEntity object
//--------------------------------------------------------------------------------------
#include "SketchAPI_Translation.h"
//--------------------------------------------------------------------------------------
+#include <ModelHighAPI_Dumper.h>
#include <ModelHighAPI_Tools.h>
//--------------------------------------------------------------------------------------
SketchAPI_Translation::SketchAPI_Translation(
const std::shared_ptr<ModelAPI_Feature> & theFeature)
-: SketchAPI_SketchEntity(theFeature)
+: ModelHighAPI_Interface(theFeature)
{
initialize();
}
const ModelHighAPI_RefAttr & thePoint2,
const ModelHighAPI_Integer & theNumberOfObjects,
bool theFullValue)
-: SketchAPI_SketchEntity(theFeature)
+: ModelHighAPI_Interface(theFeature)
{
if (initialize()) {
fillAttribute(theObjects, translationList());
fillAttribute(thePoint1, startPoint());
fillAttribute(thePoint2, endPoint());
fillAttribute(theNumberOfObjects, numberOfObjects());
- if (theFullValue)
- fillAttribute("SingleValue", valueType());
+ fillAttribute(theFullValue ? "FullValue" : "SingleValue", valueType());
- execute();
+ execute(true);
}
}
}
//--------------------------------------------------------------------------------------
+
+void SketchAPI_Translation::dump(ModelHighAPI_Dumper& theDumper) const
+{
+ FeaturePtr aBase = feature();
+ const std::string& aSketchName = theDumper.parentName(aBase);
+
+ AttributeRefListPtr aTransObjects = translationList();
+ AttributeRefAttrPtr aStart = startPoint();
+ AttributeRefAttrPtr aEnd = endPoint();
+ AttributeIntegerPtr aNbCopies = numberOfObjects();
+ bool isFullValue = valueType()->value() != "SingleValue";
+
+ theDumper << aBase << " = " << aSketchName << ".addTranslation("
+ << aTransObjects << ", " << aStart << ", " << aEnd << ", " << aNbCopies;
+ if (isFullValue)
+ theDumper << ", " << isFullValue;
+ theDumper << ")" << std::endl;
+}
#include <SketchPlugin_MultiTranslation.h>
-#include "SketchAPI_SketchEntity.h"
+#include <ModelHighAPI_Interface.h>
+#include <ModelHighAPI_Macro.h>
//--------------------------------------------------------------------------------------
class ModelAPI_Object;
class ModelHighAPI_Integer;
* \ingroup CPPHighAPI
* \brief Interface for Translation feature
*/
-class SketchAPI_Translation : public SketchAPI_SketchEntity
+class SketchAPI_Translation : public ModelHighAPI_Interface
{
public:
/// Constructor without values
translatedObjects, SketchPlugin_MultiTranslation::ENTITY_B(), ModelAPI_AttributeRefList, /** Translationed objects */
)
+ /// Dump wrapped feature
+ virtual void dump(ModelHighAPI_Dumper& theDumper) const;
};
//! Pointer on Translation object
#include "SketchAPI.h"
#include "SketchAPI_Arc.h"
#include "SketchAPI_Circle.h"
+ #include "SketchAPI_Constraint.h"
#include "SketchAPI_IntersectionPoint.h"
#include "SketchAPI_Line.h"
#include "SketchAPI_Mirror.h"
// the second condition for unability to move external segments anywhere
if (theID == EXTERNAL_ID() || isFixed()) {
std::shared_ptr<GeomAPI_Shape> aSelection = data()->selection(EXTERNAL_ID())->value();
+ if (!aSelection) {
+ // empty shape in selection shows that the shape is equal to context
+ ResultPtr anExtRes = selection(EXTERNAL_ID())->context();
+ if (anExtRes)
+ aSelection = anExtRes->shape();
+ }
// update arguments due to the selection value
if (aSelection && !aSelection->isNull() && aSelection->isEdge()) {
std::shared_ptr<GeomAPI_Edge> anEdge( new GeomAPI_Edge(aSelection));
double aNewAngle = aPassedParam >= aStartParam && aPassedParam <= aEndParam ?
((aEndParam - aStartParam) * 180.0 / PI) :
((aEndParam - aStartParam - 2.0 * PI) * 180.0 / PI);
- if (fabs(aNewAngle - anAngleAttr->value()) > tolerance)
+ if (!anAngleAttr->isInitialized() || fabs(aNewAngle - anAngleAttr->value()) > tolerance)
anAngleAttr->setValue(aNewAngle);
} else {
double aNewAngle = (aEndParam - aStartParam) * 180.0 / PI;
- if (fabs(aNewAngle - anAngleAttr->value()) > tolerance)
+ if (!anAngleAttr->isInitialized() || fabs(aNewAngle - anAngleAttr->value()) > tolerance)
anAngleAttr->setValue(aNewAngle);
}
// do not need to inform that other parameters were changed in this basis mode: these arguments
// the second condition for unability to move external segments anywhere
if (theID == EXTERNAL_ID() || isFixed()) {
std::shared_ptr<GeomAPI_Shape> aSelection = data()->selection(EXTERNAL_ID())->value();
+ if (!aSelection) {
+ // empty shape in selection shows that the shape is equal to context
+ ResultPtr anExtRes = selection(EXTERNAL_ID())->context();
+ if (anExtRes)
+ aSelection = anExtRes->shape();
+ }
// update arguments due to the selection value
if (aSelection && !aSelection->isNull() && aSelection->isEdge()) {
std::shared_ptr<GeomAPI_Edge> anEdge( new GeomAPI_Edge(aSelection));
if (theID == SketchPlugin_Constraint::ENTITY_A() ||
theID == SketchPlugin_Constraint::ENTITY_B()) {
- std::shared_ptr<ModelAPI_AttributeDouble> aValueAttr = std::dynamic_pointer_cast<
- ModelAPI_AttributeDouble>(data()->attribute(SketchPlugin_ConstraintAngle::ANGLE_VALUE_ID()));
- if (!aValueAttr->isInitialized()) { // only if it is not initialized, try to compute the current value
+ AttributeDoublePtr aValueAttr = real(SketchPlugin_ConstraintAngle::ANGLE_VALUE_ID());
+ AttributeDoublePtr aConstrValueAttr = real(SketchPlugin_Constraint::VALUE());
+ // only if one of attributes is not initialized, try to compute the current value
+ if (!aValueAttr->isInitialized() || !aConstrValueAttr->isInitialized()) {
+ if (aValueAttr->isInitialized() && !aConstrValueAttr->isInitialized()) // initialize base value of constraint
+ updateConstraintValueByAngleValue();
double anAngle = calculateAngle();
aValueAttr->setValue(anAngle);
updateConstraintValueByAngleValue();
std::shared_ptr<GeomDataAPI_Point2D> aFlyOutAttr = std::dynamic_pointer_cast<
GeomDataAPI_Point2D>(attribute(theAttributeId));
- if (fabs(aFlyOutAttr->x()) >= tolerance || fabs(aFlyOutAttr->y()) >= tolerance)
+ if (aFlyOutAttr->isInitialized() &&
+ (fabs(aFlyOutAttr->x()) >= tolerance || fabs(aFlyOutAttr->y()) >= tolerance))
return false;
DataPtr aData = data();
#include <GeomAPI_XY.h>
#include <GeomDataAPI_Point2D.h>
#include <ModelAPI_AttributeDouble.h>
-#include <ModelAPI_AttributeRefList.h>
#include <ModelAPI_AttributeRefAttrList.h>
#include <ModelAPI_Data.h>
#include <ModelAPI_Events.h>
std::shared_ptr<GeomAPI_Lin2d> aLine =
std::shared_ptr<GeomAPI_Lin2d>(new GeomAPI_Lin2d(aStartPoint->pnt(), anEndPoint->pnt()));
- if (fabs(aFlyOutAttr->x()) < tolerance && fabs(aFlyOutAttr->y()) < tolerance) {
+ if (!aFlyOutAttr->isInitialized() ||
+ (fabs(aFlyOutAttr->x()) < tolerance && fabs(aFlyOutAttr->y()) < tolerance)) {
double aDist = aPoint1->distance(aPoint2)/5.;
std::shared_ptr<GeomAPI_Pnt2d> aFPnt = aLine->shiftedLocation(aDist);
aFlyOutAttr->setValue(aFPnt);
if (theID == MIRROR_LIST_ID()) {
AttributeRefListPtr aMirrorObjectRefs = reflist(MIRROR_LIST_ID());
if (aMirrorObjectRefs->size() == 0) {
+ DocumentPtr aDoc = document();
// Clear list of objects
AttributeRefListPtr aRefListOfMirrored = std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
data()->attribute(SketchPlugin_Constraint::ENTITY_C()));
std::list<ObjectPtr> aTargetList = aRefListOfMirrored->list();
std::list<ObjectPtr>::iterator aTargetIter = aTargetList.begin();
for (; aTargetIter != aTargetList.end(); aTargetIter++) {
- aRefListOfMirrored->remove(*aTargetIter);
- // remove the corresponding feature from the sketch
- ResultConstructionPtr aRC =
- std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aTargetIter);
- DocumentPtr aDoc = aRC ? aRC->document() : DocumentPtr();
- FeaturePtr aFeature = aDoc ? aDoc->feature(aRC) : FeaturePtr();
+ FeaturePtr aFeature = ModelAPI_Feature::feature(*aTargetIter);
if (aFeature)
aDoc->removeFeature(aFeature);
}
#include "SketchPlugin_ConstraintSplit.h"
-//#include <GeomAPI_Circ2d.h>
-//#include <GeomAPI_Dir2d.h>
-//#include <GeomAPI_Lin2d.h>
#include <GeomAPI_Pnt2d.h>
-//#include <GeomAPI_XY.h>
#include <GeomDataAPI_Point2D.h>
-//#include <ModelAPI_AttributeDouble.h>
#include <ModelAPI_AttributeReference.h>
#include <ModelAPI_AttributeString.h>
-//#include <ModelAPI_AttributeRefList.h>
#include <ModelAPI_AttributeRefAttr.h>
#include <ModelAPI_Tools.h>
#include <ModelAPI_Document.h>
#include <ModelAPI_Data.h>
#include <ModelAPI_Object.h>
-#include <ModelAPI_AttributeRefList.h>
#include <ModelAPI_ResultConstruction.h>
/// It is important.
// to be removed after debug
if ((theID == EXTERNAL_ID() || isFixed()) && !isCopy()) {
std::shared_ptr<GeomAPI_Shape> aSelection = data()->selection(EXTERNAL_ID())->value();
- // update arguments due to the selection value
+ if (!aSelection) {
+ // empty shape in selection shows that the shape is equal to context
+ ResultPtr anExtRes = selection(EXTERNAL_ID())->context();
+ if (anExtRes)
+ aSelection = anExtRes->shape();
+ }
+ // update arguments due to the selection value
if (aSelection && !aSelection->isNull() && aSelection->isEdge()) {
std::shared_ptr<GeomAPI_Edge> anEdge( new GeomAPI_Edge(aSelection));
std::shared_ptr<GeomDataAPI_Point2D> aStartAttr =
return;
// Clear list of objects
- AttributeRefListPtr aRefListOfRotated = std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
- data()->attribute(SketchPlugin_Constraint::ENTITY_B()));
+ AttributeRefListPtr aRefListOfRotated = reflist(SketchPlugin_Constraint::ENTITY_B());
std::list<ObjectPtr> aTargetList = aRefListOfRotated->list();
std::list<ObjectPtr>::iterator aTargetIter = aTargetList.begin();
std::set<FeaturePtr> aFeaturesToBeRemoved;
for (int i = 0; i < aNbCopies && aTargetIter != aTargetList.end(); i++, aTargetIter++) {
aRefListOfRotated->remove(*aTargetIter);
// remove the corresponding feature from the sketch
- ResultConstructionPtr aRC =
- std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aTargetIter);
- DocumentPtr aDoc = aRC ? aRC->document() : DocumentPtr();
- FeaturePtr aFeature = aDoc ? aDoc->feature(aRC) : FeaturePtr();
+ FeaturePtr aFeature = ModelAPI_Feature::feature(*aTargetIter);
if (aFeature)
aFeaturesToBeRemoved.insert(aFeature);
}
ModelAPI_Tools::removeFeaturesAndReferences(aFeaturesToBeRemoved);
aRefListOfRotated->clear();
- std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
- data()->attribute(SketchPlugin_Constraint::ENTITY_A()))->clear();
- std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
- data()->attribute(SketchPlugin_Constraint::ENTITY_B()))->clear();
+ reflist(SketchPlugin_Constraint::ENTITY_A())->clear();
}
}
}
int aNbCopies = integer(NUMBER_OF_OBJECTS_ID())->value()-1;
if (aNbCopies <= 0)
return;
+
+ DocumentPtr aDoc = document();
// Clear list of objects
- AttributeRefListPtr aRefListOfTranslated = std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
- data()->attribute(SketchPlugin_Constraint::ENTITY_B()));
+ AttributeRefListPtr aRefListOfTranslated = reflist(SketchPlugin_Constraint::ENTITY_B());
std::list<ObjectPtr> aTargetList = aRefListOfTranslated->list();
std::list<ObjectPtr>::iterator aTargetIter = aTargetList.begin();
while (aTargetIter != aTargetList.end()) {
aTargetIter++;
for (int i = 0; i < aNbCopies && aTargetIter != aTargetList.end(); i++, aTargetIter++) {
aRefListOfTranslated->remove(*aTargetIter);
- // remove the corresponding feature from the sketch
- ResultConstructionPtr aRC =
- std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(*aTargetIter);
- DocumentPtr aDoc = aRC ? aRC->document() : DocumentPtr();
- FeaturePtr aFeature = aDoc ? aDoc->feature(aRC) : FeaturePtr();
+ FeaturePtr aFeature = ModelAPI_Feature::feature(*aTargetIter);
if (aFeature)
aDoc->removeFeature(aFeature);
}
}
aRefListOfTranslated->clear();
- std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
- data()->attribute(SketchPlugin_Constraint::ENTITY_A()))->clear();
- std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(
- data()->attribute(SketchPlugin_Constraint::ENTITY_B()))->clear();
+ reflist(SketchPlugin_Constraint::ENTITY_A())->clear();
}
}
}
// the second condition for unability to move external point anywhere
if (theID == EXTERNAL_ID() || isFixed()) {
std::shared_ptr<GeomAPI_Shape> aSelection = data()->selection(EXTERNAL_ID())->value();
- // update arguments due to the selection value
+ if (!aSelection) {
+ // empty shape in selection shows that the shape is equal to context
+ ResultPtr anExtRes = selection(EXTERNAL_ID())->context();
+ if (anExtRes)
+ aSelection = anExtRes->shape();
+ }
+ // update arguments due to the selection value
if (aSelection && !aSelection->isNull() && aSelection->isVertex()) {
std::shared_ptr<GeomAPI_Vertex> aVertex(new GeomAPI_Vertex(aSelection));
std::shared_ptr<GeomDataAPI_Point2D> aCoordAttr =
aCenterPnt->setValue(aCenterInSketch);
}
+ aProjection->boolean(COPY_ID())->setValue(true);
aProjection->execute();
aRefAttr->setObject(aProjection);
aFeature->setSketch(this);
// do not include the external edges into the result
if (aFeature->data()->attribute(SketchPlugin_SketchEntity::EXTERNAL_ID())) {
- if (aFeature->data()->selection(SketchPlugin_SketchEntity::EXTERNAL_ID())->value())
+ if (aFeature->data()->selection(SketchPlugin_SketchEntity::EXTERNAL_ID())->context())
continue;
}
// do not include the construction entities in the result
aSketchLineB = aSketchFeature.addFeature("SketchLine")
aStartPoint = geomDataAPI_Point2D(aSketchLineB.attribute("StartPoint"))
aEndPoint = geomDataAPI_Point2D(aSketchLineB.attribute("EndPoint"))
-aStartPoint.setValue(-20., 15.)
+aStartPoint.setValue(-10., 15.)
aEndPoint.setValue(80., 50.)
aSession.finishOperation()
#=========================================================================
refattrA.setObject(aSketchLineA.firstResult())
refattrB.setObject(aSketchLineB.firstResult())
anAngleVal.setValue(ANGLE_DEGREE)
+aConstraint.execute()
+aSession.finishOperation()
+aSession.startOperation()
aFlyoutPoint = geomDataAPI_Point2D(aConstraint.attribute("ConstraintFlyoutValuePnt"))
aFlyoutPoint.setValue(50.0, 100.0)
-aConstraint.execute()
aSession.finishOperation()
+aSession.abortOperation()
assert (anAngleVal.isInitialized())
assert (refattrA.isInitialized())
assert (refattrB.isInitialized())
#=========================================================================
aSession.startOperation()
aStartPoint = geomDataAPI_Point2D(aSketchLineA.attribute("StartPoint"))
-aStartPoint.setValue(0., 30.)
+aStartPoint.setValue(0., -30.)
aConstraint.execute()
aSession.finishOperation()
assert (angle(aSketchLineA, aSketchLineB) == ANGLE_DEGREE)
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aConstraint.execute()
refattrA.setAttr(aSketchPointCoords)
refattrB.setAttr(aLineAStartPoint)
+aSession.finishOperation()
+# set flyout point then abort operation, after that check the Distance is correct
+aSession.startOperation()
aFlyoutPoint = geomDataAPI_Point2D(aConstraint.attribute("ConstraintFlyoutValuePnt"))
aFlyoutPoint.setValue(50.0, 100.0)
aSession.finishOperation()
+aSession.abortOperation()
assert (refattrA.isInitialized())
assert (refattrB.isInitialized())
assert (aDistance.isInitialized())
assert (aLineResult is not None)
refattrA.setObject(aLineResult)
refattrB.setAttr(aSketchPointCoords)
+aSession.finishOperation()
+# set flyout point then abort operation, after that check the Distance is correct
+aSession.startOperation()
aFlyoutPoint = geomDataAPI_Point2D(aConstraint.attribute("ConstraintFlyoutValuePnt"))
aFlyoutPoint.setValue(50.0, 100.0)
aSession.finishOperation()
+aSession.abortOperation()
assert (refattrA.isInitialized())
assert (refattrB.isInitialized())
assert (aDistance.isInitialized())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
# A constraint to make equal radii of arc and external circle
#=========================================================================
aSession.startOperation()
-anExtCircRes = modelAPI_Result(aDocument.objectByName("Construction", "SketchCircle_1"))
-assert(anExtCircRes)
-anExtCircShape = anExtCircRes.shape()
-assert(anExtCircShape)
anExtCircle = aSketchFeature.addFeature("SketchCircle")
anExtCircleCenter = geomDataAPI_Point2D(anExtCircle.attribute("CircleCenter"))
anExtCircleRadius = anExtCircle.real("CircleRadius")
anExtCircleCenter.setValue(-50., 50.)
anExtCircleRadius.setValue(10.)
-anExtCircle.selection("External").setValue(anExtCircRes, anExtCircShape)
+anExtCircle.selection("External").selectSubShape("EDGE", "Sketch_1/Edge-SketchCircle_1_2")
aSession.finishOperation()
aSession.startOperation()
aConstraintEqRad2 = aSketchFeature.addFeature("SketchConstraintEqual")
# A constraint to make equal length of line with external line
#=========================================================================
aSession.startOperation()
-anExtLineRes = modelAPI_Result(aDocument.objectByName("Construction", "SketchLine_1"))
-assert(anExtLineRes)
-anExtLineShape = anExtLineRes.shape()
-assert(anExtLineShape)
anExtLine = aSketchFeature.addFeature("SketchLine")
anExtLineStart = geomDataAPI_Point2D(anExtLine.attribute("StartPoint"))
anExtLineEnd = geomDataAPI_Point2D(anExtLine.attribute("EndPoint"))
anExtLineStart.setValue(-40., 35.)
anExtLineEnd.setValue(-60., 25.)
-anExtLine.selection("External").setValue(anExtLineRes, anExtLineShape)
+anExtLine.selection("External").selectSubShape("EDGE", "Sketch_1/Edge-SketchLine_1")
anExtLineLen = lineLength(anExtLine)
aSession.finishOperation()
aSession.startOperation()
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
return [theDir[0] / aLen, theDir[1] / aLen]
def checkMirror(theListInit, theListMirr, theMirrorLine):
- TOL = 5.e-5
+ TOL = 6.e-5
aListSize = theListInit.size()
aLineStartPoint = geomDataAPI_Point2D(theMirrorLine.attribute("StartPoint"))
#=========================================================================
# End of test
#=========================================================================
+
+
+# make second line fixed
+aSession.startOperation()
+aFixed = aSketchFeature.addFeature("SketchConstraintRigid")
+aRefObjectA = aFixed.refattr("ConstraintEntityA")
+anObjectA = modelAPI_ResultConstruction(aSketchLine2.lastResult())
+assert (anObjectA is not None)
+aRefObjectA.setObject(anObjectA)
+aFixed.execute()
+aSession.finishOperation()
+# set mirror for first line to check dumping
+aSession.startOperation()
+aRefListInitial.clear()
+assert (aRefListB.size() == 0)
+assert (aRefListC.size() == 0)
+aRefListInitial.append(aSketchLine1.lastResult())
+aSession.finishOperation()
+assert (aRefListB.size() == 1)
+assert (aRefListC.size() == 1)
+checkMirror(aRefListB, aRefListC, aMirrorLine)
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
assert(anArc2StartPointNew == anArc2StartPointPrev)
assert(anArc2EndPointNew == anArc2EndPointPrev)
aSession.startOperation()
-aSketchFeature.removeFeature(aTangency)
+aDocument.removeFeature(aTangency)
aSession.finishOperation()
#=========================================================================
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aStartPoint1 = geomDataAPI_Point2D(aSketchLine.attribute("StartPoint"))
aEndPoint1 = geomDataAPI_Point2D(aSketchLine.attribute("EndPoint"))
aStartPoint1.setValue(10., 10.)
- aEndPoint1.setValue(30., 5.)
+ aEndPoint1.setValue(30., 15.)
allFeatures.append(aSketchLine)
# Arc
aSketchArc = theSketch.addFeature("SketchArc")
anArcPoints = []
aPoint = geomDataAPI_Point2D(aFilletArc.attribute("ArcStartPoint"))
- print "ArcStartPoint " + repr(aPoint.x()) + " " + repr(aPoint.y())
+ #print "ArcStartPoint " + repr(aPoint.x()) + " " + repr(aPoint.y())
anArcPoints.append((aPoint.x(), aPoint.y()))
aPoint = geomDataAPI_Point2D(aFilletArc.attribute("ArcEndPoint"))
- print "ArcEndPoint " + repr(aPoint.x()) + " " + repr(aPoint.y())
+ #print "ArcEndPoint " + repr(aPoint.x()) + " " + repr(aPoint.y())
anArcPoints.append((aPoint.x(), aPoint.y()))
aPoint = geomDataAPI_Point2D(aFilletArc.attribute("ArcCenter"))
- print "ArcCenter " + repr(aPoint.x()) + " " + repr(aPoint.y())
+ #print "ArcCenter " + repr(aPoint.x()) + " " + repr(aPoint.y())
aCenterX = aPoint.x()
aCenterY = aPoint.y()
aFilletRadius = math.hypot(anArcPoints[0][0]-aCenterX, anArcPoints[0][1]-aCenterY)
aLinePoints = []
aLinePoints.append((aStartPoint.x(), aStartPoint.y()))
- print "aLineStartPoint " + repr(aStartPoint.x()) + " " + repr(aStartPoint.y())
+ #print "aLineStartPoint " + repr(aStartPoint.x()) + " " + repr(aStartPoint.y())
aLinePoints.append((aEndPoint.x(), aEndPoint.y()))
- print "aLineEndPoint " + repr(aEndPoint.x()) + " " + repr(aEndPoint.y())
+ #print "aLineEndPoint " + repr(aEndPoint.x()) + " " + repr(aEndPoint.y())
aLineDirX = aEndPoint.x() - aStartPoint.x()
aLineDirY = aEndPoint.y() - aStartPoint.y()
aBaseArcPoints = []
aBaseArcPoints.append((aStartPoint.x(), aStartPoint.y()))
- print "anArcStartPoint " + repr(aStartPoint.x()) + " " + repr(aStartPoint.y())
+ #print "anArcStartPoint " + repr(aStartPoint.x()) + " " + repr(aStartPoint.y())
aBaseArcPoints.append((aEndPoint.x(), aEndPoint.y()))
- print "anArcEndPoint " + repr(aEndPoint.x()) + " " + repr(aEndPoint.y())
- print "anArcCenter " + repr(aCenterPoint.x()) + " " + repr(aCenterPoint.y())
+ #print "anArcEndPoint " + repr(aEndPoint.x()) + " " + repr(aEndPoint.y())
+ #print "anArcCenter " + repr(aCenterPoint.x()) + " " + repr(aCenterPoint.y())
aRadius = math.hypot(aStartPoint.x()-aCenterPoint.x(), aStartPoint.y()-aCenterPoint.y())
aDist = math.hypot(aCenterPoint.x() - aCenterX, aCenterPoint.y() - aCenterY)
# Change Fillet radius
#=========================================================================
aRadius.setValue(FILLET_RADIUS2)
+aFillet.execute()
aSession.finishOperation()
checkFillet(aResObjects, FILLET_RADIUS2)
# Change Fillet radius
#=========================================================================
aRadius.setValue(FILLET_RADIUS2)
+aFillet.execute()
aSession.finishOperation()
checkFillet(aResObjects, FILLET_RADIUS2)
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
anEndPoint = geomDataAPI_Point2D(aSketchLine.attribute("EndPoint"))
aStartPoint.setValue(begin[0], begin[1])
anEndPoint.setValue(end[0], end[1])
+ aSketchLine.execute()
allStartPoints.append(aStartPoint)
allEndPoints.append(anEndPoint)
allLines.append(aSketchLine)
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
# Project all features onto the new sketch
#=========================================================================
aSession.startOperation()
-anExtLineRes = modelAPI_Result(aDocument.objectByName("Construction", "SketchLine_1"))
-assert(anExtLineRes)
-anExtLineShape = anExtLineRes.shape()
-assert(anExtLineShape)
aLineProjector = aSketchFeature.addFeature("SketchProjection")
-aLineProjector.selection("ExternalFeature").setValue(anExtLineRes, anExtLineShape)
+aLineProjector.selection("ExternalFeature").selectSubShape("EDGE", "Sketch_1/Edge-SketchLine_1")
aLineProjector.execute()
-anExtCircRes = modelAPI_Result(aDocument.objectByName("Construction", "SketchCircle_1_2"))
-assert(anExtCircRes)
-anExtCircShape = anExtCircRes.shape()
-assert(anExtCircShape)
aCircleProjector = aSketchFeature.addFeature("SketchProjection")
-aCircleProjector.selection("ExternalFeature").setValue(anExtCircRes, anExtCircShape)
+aCircleProjector.selection("ExternalFeature").selectSubShape("EDGE", "Sketch_1/Edge-SketchCircle_1_2")
aCircleProjector.execute()
-anExtArcRes = modelAPI_Result(aDocument.objectByName("Construction", "SketchArc_1_2"))
-assert(anExtArcRes)
-anExtArcShape = anExtArcRes.shape()
-assert(anExtArcShape)
anArcProjector = aSketchFeature.addFeature("SketchProjection")
-anArcProjector.selection("ExternalFeature").setValue(anExtArcRes, anExtArcShape)
+anArcProjector.selection("ExternalFeature").selectSubShape("EDGE", "Sketch_1/Edge-SketchArc_1_2")
anArcProjector.execute()
aSession.finishOperation()
#=========================================================================
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aSketchArc = aSketchFeature.addFeature("SketchArc")
assert (aSketchArc.getKind() == "SketchArc")
anArcCentr = geomDataAPI_Point2D(aSketchArc.attribute("ArcCenter"))
-assert (anArcCentr.x() == 0)
-assert (anArcCentr.y() == 0)
assert (not anArcCentr.isInitialized())
anArcCentr.setValue(10., 10.)
anArcStartPoint = geomDataAPI_Point2D(
aSketchArc.attribute("ArcStartPoint"))
-assert (anArcStartPoint.x() == 0)
-assert (anArcStartPoint.y() == 0)
assert (not anArcStartPoint.isInitialized())
anArcStartPoint.setValue(0., 50.)
anArcEndPoint = geomDataAPI_Point2D(aSketchArc.attribute("ArcEndPoint"))
-assert (anArcEndPoint.x() == 0)
-assert (anArcEndPoint.y() == 0)
assert (not anArcEndPoint.isInitialized())
anArcEndPoint.setValue(50., 0.)
aSession.finishOperation()
aSketchCircle = aSketchFeature.addFeature("SketchCircle")
assert (aSketchCircle.getKind() == "SketchCircle")
anCircleCentr = geomDataAPI_Point2D(aSketchCircle.attribute("CircleCenter"))
-assert (anCircleCentr.x() == 0)
-assert (anCircleCentr.y() == 0)
assert (not anCircleCentr.isInitialized())
aCircleRadius = aSketchCircle.real("CircleRadius")
assert (type(aCircleRadius) == ModelAPI_AttributeDouble)
# ModelAPI_AttributeDouble.typeId() is checked in ModelAPI_TestConstants
assert (aCircleRadius.attributeType() == ModelAPI_AttributeDouble.typeId())
-assert (aCircleRadius.value() == 0)
anCircleCentr.setValue(-25., -25)
aCircleRadius.setValue(25.)
assert (anCircleCentr.x() == -25)
aLineEnd.setValue(50., 0.)
aSession.finishOperation()
aSession.startOperation()
+aFixed = aSketchFeature.addFeature("SketchConstraintRigid")
+aRefObjectA = aFixed.refattr("ConstraintEntityA")
+aRefObjectA.setObject(modelAPI_ResultConstruction(aSketchLine.lastResult()))
+aFixed.execute()
+aSession.finishOperation()
+aSession.startOperation()
aSketchArcTangent = aSketchFeature.addFeature("SketchArc")
aSketchArcTangent.string("ArcType").setValue("Tangent")
anArcEndPoint = geomDataAPI_Point2D(aSketchArcTangent.attribute("ArcEndPoint"))
anArcEndPoint2 = geomDataAPI_Point2D(aSketchArcTangent2.attribute("ArcEndPoint"))
aTangent = aSketchArcTangent2.refattr("ArcTangentPoint")
aTangent.setAttr(anArcEndPoint)
-anArcEndPoint2.setValue(anArcEndPoint.x() + 1, anArcEndPoint.y() + 1)
-aSession.finishOperation()
-aSession.startOperation()
-anArcEndPoint2.setValue(50., 50.)
+anArcEndPoint2.setValue(50., 150.)
aSession.finishOperation()
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aSketchPoint = aSketchFeature.addFeature("SketchPoint")
assert (aSketchPoint.getKind() == "SketchPoint")
coords = geomDataAPI_Point2D(aSketchPoint.attribute("PointCoordindates"))
-assert (coords.x() == 0)
-assert (coords.y() == 0)
assert (not coords.isInitialized())
# Simulate SketchPlugin_Point::move(...)
coords.setValue(10., 10.)
assert (len(aSketchReflist.list()) == 2)
aLineStartPoint = geomDataAPI_Point2D(aSketchLine.attribute("StartPoint"))
aLineEndPoint = geomDataAPI_Point2D(aSketchLine.attribute("EndPoint"))
-assert (aLineStartPoint.x() == 0)
-assert (aLineStartPoint.y() == 0)
assert (not aLineStartPoint.isInitialized())
-assert (aLineEndPoint.x() == 0)
-assert (aLineEndPoint.y() == 0)
assert (not aLineEndPoint.isInitialized())
# Simulate SketchPlugin_Line::move(...)
aLineStartPoint.setValue(50., 50.)
aShape = aResultConstruction.shape()
assert (aShape is not None)
assert (not aShape.isNull())
+
+import model
+assert(model.checkPythonDump())
#=========================================================================
# End of test
#=========================================================================
+
+import model
+assert(model.checkPythonDump())
aConstrList.push_back(GCSConstraintPtr(new GCS::ConstraintPointOnLine(*aPoint, *aLine)));
double aDist = lineLength(*aLine);
std::shared_ptr<PlaneGCSSolver_ParameterWrapper> aDistance =
- std::dynamic_pointer_cast<PlaneGCSSolver_ParameterWrapper>(createParameter(theGroupID, aDist));
+ std::dynamic_pointer_cast<PlaneGCSSolver_ParameterWrapper>(createParameter(theGroupID, aDist * 0.5));
aConstrList.push_back(GCSConstraintPtr(
new GCS::ConstraintP2PDistance(*aPoint, aLine->p1, aDistance->parameter())));
aConstrList.push_back(GCSConstraintPtr(
if (aPoints.size() == 2)
makeMirrorPoints(aPoints[0], aPoints[1], aMirrorLine);
+
+ // update scales of constraints
+ std::shared_ptr<PlaneGCSSolver_ConstraintWrapper> aGCSConstraint =
+ std::dynamic_pointer_cast<PlaneGCSSolver_ConstraintWrapper>(theConstraint);
+ std::list<GCSConstraintPtr>::const_iterator aCIt = aGCSConstraint->constraints().begin();
+ for (; aCIt != aGCSConstraint->constraints().end(); ++aCIt)
+ (*aCIt)->rescale();
}
}
}
- if (theBaseEntities.size() > theMirrorEntities.size())
+ if (theBaseEntities.size() > theMirrorEntities.size() || aMirroredList.empty())
myErrorMsg = SketchSolver_Error::NOT_INITIALIZED();
}
BuilderPtr aBuilder = SketchSolver_Manager::instance()->builder();
std::list<ConstraintWrapperPtr> aMirConstrList;
- std::vector<EntityWrapperPtr>::iterator aBIt = aBaseList.begin();
+ // update mirrored features to be in the current group
std::vector<EntityWrapperPtr>::iterator aMIt = aMirrorList.begin();
- for (; aBIt != aBaseList.end(); ++aBIt, ++aMIt) {
+ for (; aMIt != aMirrorList.end(); ++aMIt)
+ myStorage->update((*aMIt)->baseFeature(), myGroupID);
+
+ std::vector<EntityWrapperPtr>::iterator aBIt = aBaseList.begin();
+ for (aMIt = aMirrorList.begin(); aBIt != aBaseList.end(); ++aBIt, ++aMIt) {
aNewConstraints = aBuilder->createConstraint(
myBaseConstraint, myGroupID, mySketchID, aConstrType,
0.0, *aBIt, *aMIt, aMirrorLine);
aMirConstrList.insert(aMirConstrList.end(), aNewConstraints.begin(), aNewConstraints.end());
}
-
- // update mirrored features to be in the current group
- for (aMIt = aMirrorList.begin(); aMIt != aMirrorList.end(); ++aMIt)
- myStorage->update((*aMIt)->baseFeature(), myGroupID);
myStorage->addConstraint(myBaseConstraint, aMirConstrList);
adjustConstraint();
}
myGroups.push_back(aNewGroup);
}
- return aResult;
+ return aResult || isUpdated;
}
// ============================================================================
std::shared_ptr<GeomDataAPI_Point2D> aFlyoutPoint =
std::dynamic_pointer_cast<GeomDataAPI_Point2D>(
const_cast<ModelAPI_Feature*>(theConstraint)->attribute(SketchPlugin_Constraint::FLYOUT_VALUE_PNT()));
-
+ // for not initialized values return zero distance to avoid Presentation crash
+ if (!aFlyoutPoint->isInitialized())
+ return 0;
return aFlyoutPoint->y();
}