+bool GeomAPI_Shape::isCompSolid() const
+{
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ return !aShape.IsNull() && aShape.ShapeType() == TopAbs_COMPSOLID;
+}
+
+bool GeomAPI_Shape::isPlanar() const
+{
+ TopoDS_Shape aShape = impl<TopoDS_Shape>();
+
+ if(aShape.IsNull()) {
+ return false;
+ }
+
+ TopAbs_ShapeEnum aShapeType = aShape.ShapeType();
+ if(aShapeType == TopAbs_COMPOUND) {
+ TopoDS_Iterator anIt(aShape);
+ int aShNum = 0;
+ for(; anIt.More(); anIt.Next()) {
+ ++aShNum;
+ }
+ if(aShNum == 1) {
+ anIt.Initialize(aShape);
+ aShape = anIt.Value();
+ }
+ }
+
+ aShapeType = aShape.ShapeType();
+ if(aShapeType == TopAbs_VERTEX) {
+ return true;
+ } else if(aShapeType == TopAbs_FACE) {
+ const Handle(Geom_Surface)& aSurface = BRep_Tool::Surface(TopoDS::Face(aShape));
+ Handle(Standard_Type) aType = aSurface->DynamicType();
+
+ if(aType == STANDARD_TYPE(Geom_RectangularTrimmedSurface)) {
+ Handle(Geom_RectangularTrimmedSurface) aTrimSurface =
+ Handle(Geom_RectangularTrimmedSurface)::DownCast(aSurface);
+ aType = aTrimSurface->BasisSurface()->DynamicType();
+ }
+ return (aType == STANDARD_TYPE(Geom_Plane)) == Standard_True;
+ } else {
+ BRepBuilderAPI_FindPlane aFindPlane(aShape);
+ bool isFound = aFindPlane.Found() == Standard_True;
+
+ if(!isFound && aShapeType == TopAbs_EDGE) {
+ Standard_Real aFirst, aLast;
+ Handle(Geom_Curve) aCurve = BRep_Tool::Curve(TopoDS::Edge(aShape), aFirst, aLast);
+ Handle(Standard_Type) aType = aCurve->DynamicType();
+
+ if(aType == STANDARD_TYPE(Geom_TrimmedCurve)) {
+ Handle(Geom_TrimmedCurve) aTrimCurve = Handle(Geom_TrimmedCurve)::DownCast(aCurve);
+ aType = aTrimCurve->BasisCurve()->DynamicType();
+ }
+
+ if(aType == STANDARD_TYPE(Geom_Line)
+ || aType == STANDARD_TYPE(Geom_Conic)
+ || aType == STANDARD_TYPE(Geom_Circle)
+ || aType == STANDARD_TYPE(Geom_Ellipse)
+ || aType == STANDARD_TYPE(Geom_Hyperbola)
+ || aType == STANDARD_TYPE(Geom_Parabola)) {
+ isFound = true;
+ }
+ }
+
+ return isFound;
+ }
+
+ return false;
+}
+
+std::shared_ptr<GeomAPI_Vertex> GeomAPI_Shape::vertex() const
+{
+ GeomVertexPtr aVertex;
+ if (isVertex()) {
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ aVertex = GeomVertexPtr(new GeomAPI_Vertex);
+ aVertex->setImpl(new TopoDS_Shape(aShape));
+ }
+ return aVertex;
+}
+
+std::shared_ptr<GeomAPI_Edge> GeomAPI_Shape::edge() const
+{
+ GeomEdgePtr anEdge;
+ if (isEdge()) {
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ anEdge = GeomEdgePtr(new GeomAPI_Edge);
+ anEdge->setImpl(new TopoDS_Shape(aShape));
+ }
+ return anEdge;
+}
+
+std::shared_ptr<GeomAPI_Wire> GeomAPI_Shape::wire() const
+{
+ GeomWirePtr aWire;
+ if (isWire()) {
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ aWire = GeomWirePtr(new GeomAPI_Wire);
+ aWire->setImpl(new TopoDS_Shape(aShape));
+ }
+ return aWire;
+}
+
+std::shared_ptr<GeomAPI_Face> GeomAPI_Shape::face() const
+{
+ GeomFacePtr aFace;
+ if (isFace()) {
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ aFace = GeomFacePtr(new GeomAPI_Face);
+ aFace->setImpl(new TopoDS_Shape(aShape));
+ }
+ return aFace;
+}
+
+std::shared_ptr<GeomAPI_Shell> GeomAPI_Shape::shell() const
+{
+ GeomShellPtr aShell;
+ if (isShell()) {
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ aShell = GeomShellPtr(new GeomAPI_Shell);
+ aShell->setImpl(new TopoDS_Shape(aShape));
+ }
+ return aShell;
+}
+
+std::shared_ptr<GeomAPI_Solid> GeomAPI_Shape::solid() const
+{
+ GeomSolidPtr aSolid;
+ if (isSolid()) {
+ const TopoDS_Shape& aShape = const_cast<GeomAPI_Shape*>(this)->impl<TopoDS_Shape>();
+ aSolid = GeomSolidPtr(new GeomAPI_Solid);
+ aSolid->setImpl(new TopoDS_Shape(aShape));
+ }
+ return aSolid;
+}
+
+std::list<std::shared_ptr<GeomAPI_Shape> >
+GeomAPI_Shape::subShapes(ShapeType theSubShapeType) const
+{
+ ListOfShape aSubs;
+ const TopoDS_Shape& aShape = impl<TopoDS_Shape>();
+ if (aShape.IsNull())
+ return aSubs;
+
+ // process multi-level compounds
+ if (shapeType() == COMPOUND && theSubShapeType == COMPOUND) {
+ for (TopoDS_Iterator anIt(aShape); anIt.More(); anIt.Next()) {
+ const TopoDS_Shape& aCurrent = anIt.Value();
+ if (aCurrent.ShapeType() == TopAbs_COMPOUND) {
+ GeomShapePtr aSub(new GeomAPI_Shape);
+ aSub->setImpl(new TopoDS_Shape(aCurrent));
+ aSubs.push_back(aSub);
+ }
+ }
+ // add self
+ GeomShapePtr aSub(new GeomAPI_Shape);
+ aSub->setImpl(new TopoDS_Shape(aShape));
+ aSubs.push_back(aSub);
+ }
+ else {
+ for (TopExp_Explorer anExp(aShape, (TopAbs_ShapeEnum)theSubShapeType);
+ anExp.More(); anExp.Next()) {
+ GeomShapePtr aSub(new GeomAPI_Shape);
+ aSub->setImpl(new TopoDS_Shape(anExp.Current()));
+ aSubs.push_back(aSub);
+ }
+ }
+ return aSubs;
+}
+
+GeomAPI_Shape::ShapeType GeomAPI_Shape::shapeType() const
+{
+ const TopoDS_Shape& aShape = impl<TopoDS_Shape>();
+ if (aShape.IsNull())
+ return GeomAPI_Shape::SHAPE;
+
+ ShapeType aST = GeomAPI_Shape::SHAPE;
+
+ switch(aShape.ShapeType()) {
+ case TopAbs_COMPOUND:
+ aST = GeomAPI_Shape::COMPOUND;
+ break;
+ case TopAbs_COMPSOLID:
+ aST = GeomAPI_Shape::COMPSOLID;
+ break;
+ case TopAbs_SOLID:
+ aST = GeomAPI_Shape::SOLID;
+ break;
+ case TopAbs_SHELL:
+ aST = GeomAPI_Shape::SHELL;
+ break;
+ case TopAbs_FACE:
+ aST = GeomAPI_Shape::FACE;
+ break;
+ case TopAbs_WIRE:
+ aST = GeomAPI_Shape::WIRE;
+ break;
+ case TopAbs_EDGE:
+ aST = GeomAPI_Shape::EDGE;
+ break;
+ case TopAbs_VERTEX:
+ aST = GeomAPI_Shape::VERTEX;
+ break;
+ case TopAbs_SHAPE:
+ aST = GeomAPI_Shape::SHAPE;
+ break;
+ }
+
+ return aST;
+}
+
+GeomAPI_Shape::ShapeType GeomAPI_Shape::shapeTypeByStr(std::string theType)
+{
+ std::transform(theType.begin(), theType.end(), theType.begin(), ::toupper);
+ if (theType == "COMPOUND" || theType == "COMPOUNDS")
+ return COMPOUND;
+ if (theType == "COMPSOLID" || theType == "COMPSOLIDS")
+ return COMPSOLID;
+ if (theType == "SOLID" || theType == "SOLIDS")
+ return SOLID;
+ if (theType == "SHELL" || theType == "SHELLS")
+ return SHELL;
+ if (theType == "FACE" || theType == "FACES")
+ return FACE;
+ if (theType == "WIRE" || theType == "WIRES")
+ return WIRE;
+ if (theType == "EDGE" || theType == "EDGES")
+ return EDGE;
+ if (theType == "VERTEX" || theType == "VERTICES")
+ return VERTEX;
+ return SHAPE; // default
+}
+
+std::string GeomAPI_Shape::shapeTypeStr() const
+{
+ ShapeType aShapeType = shapeType();
+ std::string aShapeTypeStr;
+
+ switch(aShapeType) {
+ case COMPOUND: {
+ aShapeTypeStr = "COMPOUND";
+ break;
+ }
+ case COMPSOLID: {
+ aShapeTypeStr = "COMPSOLID";
+ break;
+ }
+ case SOLID: {
+ aShapeTypeStr = "SOLID";
+ break;
+ }
+ case SHELL: {
+ aShapeTypeStr = "SHELL";
+ break;
+ }
+ case FACE: {
+ aShapeTypeStr = "FACE";
+ break;
+ }
+ case WIRE: {
+ aShapeTypeStr = "WIRE";
+ break;
+ }
+ case EDGE: {
+ aShapeTypeStr = "EDGE";
+ break;
+ }
+ case VERTEX: {
+ aShapeTypeStr = "VERTEX";
+ break;
+ }
+ case SHAPE: {
+ aShapeTypeStr = "SHAPE";
+ break;
+ }
+ }
+
+ return aShapeTypeStr;
+}
+
+GeomAPI_Shape::Orientation GeomAPI_Shape::orientation() const
+{
+ TopAbs_Orientation anOrientation = MY_SHAPE->Orientation();
+
+ switch(anOrientation) {
+ case TopAbs_FORWARD: return FORWARD;
+ case TopAbs_REVERSED: return REVERSED;
+ case TopAbs_INTERNAL: return INTERNAL;
+ case TopAbs_EXTERNAL: return EXTERNAL;
+ default: return FORWARD;
+ }
+}
+
+void GeomAPI_Shape::setOrientation(const GeomAPI_Shape::Orientation theOrientation)
+{
+ TopAbs_Orientation anOrientation = MY_SHAPE->Orientation();
+
+ switch(theOrientation) {
+ case FORWARD: MY_SHAPE->Orientation(TopAbs_FORWARD); break;
+ case REVERSED: MY_SHAPE->Orientation(TopAbs_REVERSED); break;
+ case INTERNAL: MY_SHAPE->Orientation(TopAbs_INTERNAL); break;
+ case EXTERNAL: MY_SHAPE->Orientation(TopAbs_EXTERNAL); break;
+ }
+}
+
+void GeomAPI_Shape::reverse()
+{
+ MY_SHAPE->Reverse();
+}
+
+bool GeomAPI_Shape::isSubShape(const std::shared_ptr<GeomAPI_Shape> theShape,
+ const bool theCheckOrientation) 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(theCheckOrientation ?
+ aShapeToSearch.IsEqual(anExp.Current()) : aShapeToSearch.IsSame(anExp.Current())) {
+ return true;
+ }
+ }
+
+ return false;
+}
+