#include <BuildPlugin_Edge.h>
#include <BuildPlugin_Wire.h>
#include <BuildPlugin_Face.h>
+#include <BuildPlugin_Shell.h>
#include <BuildPlugin_Validators.h>
// the only created instance of this plugin
return FeaturePtr(new BuildPlugin_Wire());
} else if(theFeatureID == BuildPlugin_Face::ID()) {
return FeaturePtr(new BuildPlugin_Face());
+ } else if(theFeatureID == BuildPlugin_Shell::ID()) {
+ return FeaturePtr(new BuildPlugin_Shell());
}
// Feature of such kind is not found.
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: BuildPlugin_Shell.cpp
+// Created: 14 April 2016
+// Author: Dmitry Bobylev
+
+#include "BuildPlugin_Shell.h"
+
+#include <ModelAPI_AttributeSelectionList.h>
+#include <ModelAPI_ResultBody.h>
+#include <ModelAPI_ResultConstruction.h>
+
+#include <GeomAlgoAPI_Sewing.h>
+#include <GeomAPI_ShapeExplorer.h>
+
+//=================================================================================================
+BuildPlugin_Shell::BuildPlugin_Shell()
+{
+}
+
+//=================================================================================================
+void BuildPlugin_Shell::initAttributes()
+{
+ data()->addAttribute(BASE_OBJECTS_ID(), ModelAPI_AttributeSelectionList::typeId());
+}
+
+//=================================================================================================
+void BuildPlugin_Shell::execute()
+{
+ // Get base objects list.
+ AttributeSelectionListPtr aSelectionList = selectionList(BASE_OBJECTS_ID());
+
+ // Collect base shapes.
+ ListOfShape aShapes;
+ for(int anIndex = 0; anIndex < aSelectionList->size(); ++anIndex) {
+ AttributeSelectionPtr aSelection = aSelectionList->value(anIndex);
+ GeomShapePtr aShape = aSelection->value();
+ if(!aShape.get()) {
+ aShape = aSelection->context()->shape();
+ }
+ aShapes.push_back(aShape);
+ }
+
+ // Sew faces.
+ GeomAlgoAPI_Sewing aSewingAlgo(aShapes);
+
+ // Check that algo is done.
+ if(!aSewingAlgo.isDone()) {
+ setError("Error: " + getKind() + " algorithm failed.");
+ return;
+ }
+
+ // Check if shape is not null.
+ if(!aSewingAlgo.shape().get() || aSewingAlgo.shape()->isNull()) {
+ setError("Error: Resulting shape is null.");
+ return;
+ }
+
+ // Check that resulting shape is valid.
+ if(!aSewingAlgo.isValid()) {
+ setError("Error: Resulting shape is not valid.");
+ return;
+ }
+
+ // Store result.
+ GeomShapePtr aResult = aSewingAlgo.shape();
+ std::shared_ptr<GeomAPI_DataMapOfShapeShape> aMapOfShapes = aSewingAlgo.mapOfSubShapes();
+
+ int anIndex = 0;
+ for(GeomAPI_ShapeExplorer anExp(aResult, GeomAPI_Shape::SHELL); anExp.more(); anExp.next()) {
+ GeomShapePtr aShell = anExp.current();
+ ResultBodyPtr aResultBody = document()->createBody(data(), anIndex);
+ aResultBody->store(aShell);
+ for(ListOfShape::const_iterator anIt = aShapes.cbegin(); anIt != aShapes.cend(); ++anIt) {
+ for(GeomAPI_ShapeExplorer aFaceExp(*anIt, GeomAPI_Shape::FACE); aFaceExp.more(); aFaceExp.next()) {
+ GeomShapePtr aFace = aFaceExp.current();
+ ListOfShape aHistory;
+ aSewingAlgo.modified(aFace, aHistory);
+ for(ListOfShape::const_iterator aHistoryIt = aHistory.cbegin();
+ aHistoryIt != aHistory.cend();
+ ++aHistoryIt) {
+ if(aShell->isSubShape(*aHistoryIt)) {
+ aResultBody->loadAndOrientModifiedShapes(&aSewingAlgo, aFace, GeomAPI_Shape::EDGE,
+ 1, "Modified", *aMapOfShapes.get());
+ }
+ }
+ }
+ }
+ setResult(aResultBody, anIndex);
+ ++anIndex;
+ }
+
+ removeResults(anIndex);
+}
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: BuildPlugin_Shell.h
+// Created: 14 April 2016
+// Author: Dmitry Bobylev
+
+#ifndef BuildPlugin_Shell_H_
+#define BuildPlugin_Shell_H_
+
+#include "BuildPlugin.h"
+
+#include <ModelAPI_Feature.h>
+
+/// \class BuildPlugin_Shell
+/// \ingroup Plugins
+/// \brief Feature for creation of shell from faces and shells.
+class BuildPlugin_Shell: public ModelAPI_Feature
+{
+public:
+ /// Use plugin manager for features creation
+ BuildPlugin_Shell();
+
+ /// Feature kind.
+ inline static const std::string& ID()
+ {
+ static const std::string MY_ID("Shell");
+ return MY_ID;
+ }
+
+ /// Attribute name of base objects.
+ inline static const std::string& BASE_OBJECTS_ID()
+ {
+ static const std::string MY_BASE_OBJECTS_ID("base_objects");
+ return MY_BASE_OBJECTS_ID;
+ }
+
+ /// \return the kind of a feature.
+ BUILDPLUGIN_EXPORT virtual const std::string& getKind()
+ {
+ static std::string MY_KIND = BuildPlugin_Shell::ID();
+ return MY_KIND;
+ }
+
+ /// Request for initialization of data model of the feature: adding all attributes.
+ BUILDPLUGIN_EXPORT virtual void initAttributes();
+
+ /// Creates a new part document if needed.
+ BUILDPLUGIN_EXPORT virtual void execute();
+};
+
+#endif
AttributeSelectionPtr aSelection = *aListIt;
std::shared_ptr<GeomAPI_Edge> anEdgeInList(new GeomAPI_Edge(aSelection->value()));
- ListOfShape::const_iterator anEdgesIt = anAddedEdges.cbegin();
- for(; anEdgesIt != anAddedEdges.cend(); ++anEdgesIt) {
- if(anEdgeInList->isEqual(*anEdgesIt)) {
- break;
- }
- }
-
ResultConstructionPtr aConstruction = std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(aSelection->context());
std::shared_ptr<GeomAPI_PlanarEdges> aPlanarEdges = std::dynamic_pointer_cast<GeomAPI_PlanarEdges>(aConstruction->shape());
if(aFoundFace.get()) {
for(GeomAPI_ShapeExplorer anExp(aFoundFace, GeomAPI_Shape::EDGE); anExp.more(); anExp.next()) {
std::shared_ptr<GeomAPI_Edge> anEdgeOnFace(new GeomAPI_Edge(anExp.current()));
- anEdgesIt = anAddedEdges.cbegin();
+ ListOfShape::const_iterator anEdgesIt = anAddedEdges.cbegin();
for(; anEdgesIt != anAddedEdges.cend(); ++anEdgesIt) {
if(anEdgeOnFace->isEqual(*anEdgesIt)) {
break;
BuildPlugin_Edge.h
BuildPlugin_Wire.h
BuildPlugin_Face.h
+ BuildPlugin_Shell.h
BuildPlugin_Validators.h
)
BuildPlugin_Edge.cpp
BuildPlugin_Wire.cpp
BuildPlugin_Face.cpp
+ BuildPlugin_Shell.cpp
BuildPlugin_Validators.cpp
)
edge_widget.xml
wire_widget.xml
face_widget.xml
+ shell_widget.xml
)
SET(PROJECT_LIBRARIES
<feature id="Edge" title="Edge" tooltip ="Create an edge from sketch edges and edge objects" icon="icons/Build/feature_edge.png">
<source path="edge_widget.xml"/>
</feature>
- <feature id="Wire" title="Wire" tooltip ="Create a wire from sketch edges and wires objects" icon="icons/Build/feature_wire.png">
+ <feature id="Wire" title="Wire" tooltip ="Create a wire from sketch edges, edges and wires objects" icon="icons/Build/feature_wire.png">
<source path="wire_widget.xml"/>
</feature>
- <feature id="Face" title="Face" tooltip ="Create a face from sketch edges and wires objects" icon="icons/Build/feature_face.png">
+ <feature id="Face" title="Face" tooltip ="Create a face from sketch edges, edges and wires objects" icon="icons/Build/feature_face.png">
<source path="face_widget.xml"/>
</feature>
+ <feature id="Shell" title="Shell" tooltip ="Create a shell from faces or shells objects" icon="icons/Build/feature_shell.png">
+ <source path="shell_widget.xml"/>
+ </feature>
</group>
</workbench>
</plugin>
--- /dev/null
+<!-- Copyright (C) 2014-20xx CEA/DEN, EDF R&D -->
+
+<source>
+ <multi_selector id="base_objects"
+ label="Faces and shells:"
+ tooltip="Select faces or shells objects."
+ type_choice="objects">
+ <validator id="GeomValidators_ShapeType" parameters="face,shell"/>
+ </multi_selector>
+ <!--<validator id="BuildPlugin_ValidatorBaseForShell" parameters="base_objects"/>-->
+</source>
#include <Geom_Plane.hxx>
#include <Geom_RectangularTrimmedSurface.hxx>
#include <Geom_TrimmedCurve.hxx>
+#include <TopExp_Explorer.hxx>
#include <TopoDS.hxx>
#include <TopoDS_Iterator.hxx>
#include <TopoDS_Shape.hxx>
return aShapeTypeStr;
}
+bool GeomAPI_Shape::isSubShape(const std::shared_ptr<GeomAPI_Shape> theShape) const
+{
+ if(!theShape.get()) {
+ return false;
+ }
+
+ const TopoDS_Shape& aShapeToSearch = theShape->impl<TopoDS_Shape>();
+ if(aShapeToSearch.IsNull()) {
+ return false;
+ }
+
+ for(TopExp_Explorer anExp(*MY_SHAPE, aShapeToSearch.ShapeType()); anExp.More(); anExp.Next()) {
+ if(aShapeToSearch.IsEqual(anExp.Current())) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
bool GeomAPI_Shape::computeSize(double& theXmin, double& theYmin, double& theZmin,
double& theXmax, double& theYmax, double& theZmax) const
{
GEOMAPI_EXPORT
virtual std::string shapeTypeStr() const;
+ /// \return true if passed shape is a sub-shape of this shape.
+ /// \param theShape shape to search.
+ GEOMAPI_EXPORT virtual bool isSubShape(const std::shared_ptr<GeomAPI_Shape> theShape) const;
+
+
/// Computes boundary dimensions of the shape
/// Returns False if it is not possible
GEOMAPI_EXPORT
GeomAlgoAPI_Intersection.h
GeomAlgoAPI_Pipe.h
GeomAlgoAPI_WireBuilder.h
+ GeomAlgoAPI_Sewing.h
)
SET(PROJECT_SOURCES
GeomAlgoAPI_Intersection.cpp
GeomAlgoAPI_Pipe.cpp
GeomAlgoAPI_WireBuilder.cpp
+ GeomAlgoAPI_Sewing.cpp
)
SET(PROJECT_LIBRARIES
%include "GeomAlgoAPI_Intersection.h"
%include "GeomAlgoAPI_Pipe.h"
%include "GeomAlgoAPI_WireBuilder.h"
+%include "GeomAlgoAPI_Sewing.h"
%typemap(out) std::list< std::shared_ptr< GeomAPI_Shape > >::value_type & {
$result = SWIG_NewPointerObj(SWIG_as_voidptr(new std::shared_ptr<GeomAPI_Shape>(*$1)), $descriptor(std::shared_ptr<GeomAPI_Shape> *), SWIG_POINTER_OWN | 0 );
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: GeomAlgoAPI_Sewing.cpp
+// Created: 25 April 2016
+// Author: Dmitry Bobylev
+
+
+#include "GeomAlgoAPI_Sewing.h"
+
+#include <BRep_Builder.hxx>
+#include <BRepBuilderAPI_MakeShell.hxx>
+#include <BRepBuilderAPI_Sewing.hxx>
+#include <TopExp_Explorer.hxx>
+#include <TopoDS_Iterator.hxx>
+#include <TopoDS_Shape.hxx>
+
+//==================================================================================================
+GeomAlgoAPI_Sewing::GeomAlgoAPI_Sewing(const ListOfShape& theShapes)
+{
+ build(theShapes);
+}
+
+void GeomAlgoAPI_Sewing::build(const ListOfShape& theShapes)
+{
+ if(theShapes.empty()) {
+ return;
+ }
+
+ BRepBuilderAPI_Sewing* aSewingBuilder = new BRepBuilderAPI_Sewing();
+ this->setImpl(aSewingBuilder);
+
+ for(ListOfShape::const_iterator anIt = theShapes.cbegin(); anIt != theShapes.cend(); ++anIt) {
+ const TopoDS_Shape& aShape = (*anIt)->impl<TopoDS_Shape>();
+ aSewingBuilder->Add(aShape);
+ }
+
+ aSewingBuilder->Perform();
+
+ TopoDS_Shape aResult = aSewingBuilder->SewedShape();
+ BRep_Builder aBuilder;
+ TopoDS_Compound aResultCompound;
+ aBuilder.MakeCompound(aResultCompound);
+ for(TopoDS_Iterator anIt(aResult); anIt.More(); anIt.Next()) {
+ const TopoDS_Shape aSubShape = anIt.Value();
+ if(aSubShape.ShapeType() == TopAbs_SHELL) {
+ aBuilder.Add(aResultCompound, aSubShape);
+ } else if (aSubShape.ShapeType() == TopAbs_FACE) {
+ TopoDS_Shell aShell;
+ aBuilder.MakeShell(aShell);
+ aBuilder.Add(aShell, aSubShape);
+ aBuilder.Add(aResultCompound, aShell);
+ }
+ }
+ TopoDS_Iterator anIt(aResultCompound);
+ if(anIt.More()) {
+ aResult = aResultCompound;
+ }
+
+ std::shared_ptr<GeomAPI_Shape> aShape(new GeomAPI_Shape());
+ aShape->setImpl(new TopoDS_Shape(aResult));
+ this->setShape(aShape);
+ this->setDone(true);
+}
+
+//==================================================================================================
+void GeomAlgoAPI_Sewing::modified(const std::shared_ptr<GeomAPI_Shape> theShape,
+ ListOfShape& theHistory)
+{
+ static int anIndex = 0;
+ if(!theShape.get()) {
+ return;
+ }
+
+ const TopoDS_Shape& aShape = theShape->impl<TopoDS_Shape>();
+ const BRepBuilderAPI_Sewing& aSewingBuilder = this->impl<BRepBuilderAPI_Sewing>();
+
+ TopoDS_Shape aModifiedShape = aSewingBuilder.Modified(aShape);
+ if(aModifiedShape.IsEqual(aShape)) {
+ aModifiedShape = aSewingBuilder.ModifiedSubShape(aShape);
+ }
+
+ for(TopExp_Explorer anExp(aModifiedShape, aShape.ShapeType()); anExp.More(); anExp.Next()) {
+ GeomShapePtr aGeomShape(new GeomAPI_Shape());
+ aGeomShape->setImpl(new TopoDS_Shape(anExp.Current()));
+ theHistory.push_back(aGeomShape);
+ }
+}
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: GeomAlgoAPI_Sewing.h
+// Created: 25 April 2016
+// Author: Dmitry Bobylev
+
+#ifndef GeomAlgoAPI_Sewing_H_
+#define GeomAlgoAPI_Sewing_H_
+
+#include "GeomAlgoAPI.h"
+#include "GeomAlgoAPI_MakeShape.h"
+
+#include <GeomAPI_Shape.h>
+
+/// \class GeomAlgoAPI_Sewing
+/// \ingroup DataAlgo
+/// \brief Allows creation of connected topology (shells) from a set of separate topological elements (faces).
+class GeomAlgoAPI_Sewing : public GeomAlgoAPI_MakeShape
+{
+public:
+ /// Constructor.
+ GEOMALGOAPI_EXPORT GeomAlgoAPI_Sewing(const ListOfShape& theShapes);
+
+ /// \return the list of shapes modified from the shape \a theShape.
+ /// \param[in] theShape base shape.
+ /// \param[out] theHistory modified shapes.
+ GEOMALGOAPI_EXPORT virtual void modified(const std::shared_ptr<GeomAPI_Shape> theShape,
+ ListOfShape& theHistory);
+
+private:
+ /// Builds resulting shape.
+ void build(const ListOfShape& theShapes);
+};
+
+#endif
#include "GeomAlgoAPI_Intersection.h"
#include "GeomAlgoAPI_Pipe.h"
#include "GeomAlgoAPI_WireBuilder.h"
-
+ #include "GeomAlgoAPI_Sewing.h"
+
#include <memory>
#include <string>
#include <list>