Salome HOME
Merge branch 'master' of newgeom:newgeom
[modules/shaper.git] / src / GeomAlgoAPI / GeomAlgoAPI_Boolean.cpp
1 // File:        GeomAlgoAPI_Boolean.cpp
2 // Created:     02 Sept 2014
3 // Author:      Vitaly Smetannikov
4
5 #include "GeomAlgoAPI_Boolean.h"
6
7 #include <BRepAlgoAPI_Cut.hxx>
8 #include <BRepAlgoAPI_Common.hxx>
9 #include <BRepAlgoAPI_Fuse.hxx>
10 #include <BRepCheck_Analyzer.hxx>
11 #include <TopExp_Explorer.hxx>
12 #include <GeomAlgoAPI_DFLoader.h>
13
14 boost::shared_ptr<GeomAPI_Shape> GeomAlgoAPI_Boolean::makeCut(
15   boost::shared_ptr<GeomAPI_Shape> theShape,
16   boost::shared_ptr<GeomAPI_Shape> theTool)
17 {
18   const TopoDS_Shape& aShape = theShape->impl<TopoDS_Shape>();
19   const TopoDS_Shape& aTool = theTool->impl<TopoDS_Shape>();
20
21   BRepAlgoAPI_Cut aCut(aShape, aTool);
22   if (aCut.IsDone()) {
23     boost::shared_ptr<GeomAPI_Shape> aResult(new GeomAPI_Shape());
24     aResult->setImpl(new TopoDS_Shape(aCut.Shape()));
25     return aResult;
26   }
27   return boost::shared_ptr<GeomAPI_Shape>();
28 }
29
30
31 boost::shared_ptr<GeomAPI_Shape> GeomAlgoAPI_Boolean::makeFuse(
32   boost::shared_ptr<GeomAPI_Shape> theShape,
33   boost::shared_ptr<GeomAPI_Shape> theTool)
34 {
35   const TopoDS_Shape& aShape = theShape->impl<TopoDS_Shape>();
36   const TopoDS_Shape& aTool = theTool->impl<TopoDS_Shape>();
37
38   BRepAlgoAPI_Fuse aFuse(aShape, aTool);
39   if (aFuse.IsDone()) {
40     boost::shared_ptr<GeomAPI_Shape> aResult(new GeomAPI_Shape());
41     aResult->setImpl(new TopoDS_Shape(aFuse.Shape()));
42     return aResult;
43   }
44   return boost::shared_ptr<GeomAPI_Shape>();
45 }
46
47
48 boost::shared_ptr<GeomAPI_Shape> GeomAlgoAPI_Boolean::makeCommon(
49   boost::shared_ptr<GeomAPI_Shape> theShape,
50   boost::shared_ptr<GeomAPI_Shape> theTool)
51 {
52   const TopoDS_Shape& aShape = theShape->impl<TopoDS_Shape>();
53   const TopoDS_Shape& aTool = theTool->impl<TopoDS_Shape>();
54
55   BRepAlgoAPI_Common aCommon(aShape, aTool);
56   if (aCommon.IsDone()) {
57     boost::shared_ptr<GeomAPI_Shape> aResult(new GeomAPI_Shape());
58     aResult->setImpl(new TopoDS_Shape(aCommon.Shape()));
59     return aResult;
60   }
61   return boost::shared_ptr<GeomAPI_Shape>();
62 }
63
64 //============================================================================
65 GeomAlgoAPI_Boolean::GeomAlgoAPI_Boolean(boost::shared_ptr<GeomAPI_Shape> theObject,
66                                          boost::shared_ptr<GeomAPI_Shape> theTool,
67                                          int theType)
68 : myOperation(theType), myDone(false), myShape(new GeomAPI_Shape())
69 {
70   build(theObject, theTool);
71 }
72
73
74 //============================================================================
75 void GeomAlgoAPI_Boolean::build(boost::shared_ptr<GeomAPI_Shape> theObject,
76                                 boost::shared_ptr<GeomAPI_Shape> theTool)
77 {
78   const TopoDS_Shape& anObject = theObject->impl<TopoDS_Shape>();
79   const TopoDS_Shape& aTool    = theTool->impl<TopoDS_Shape>();
80   TopoDS_Shape aResult;
81   switch (myOperation) {
82   case BOOL_FUSE: 
83         {
84           BRepAlgoAPI_Fuse* mkFuse = new BRepAlgoAPI_Fuse(anObject, aTool);
85       if (mkFuse && mkFuse->IsDone()) {
86                 setImpl(mkFuse);
87                 myDone = mkFuse->IsDone() == Standard_True;
88                 myMkShape = new GeomAlgoAPI_MakeShape (mkFuse);
89                 aResult = mkFuse->Shape();//GeomAlgoAPI_DFLoader::refineResult(aFuse->Shape());      
90           }
91           break;
92         }
93   case BOOL_CUT:
94         {
95       BRepAlgoAPI_Cut* mkCut = new BRepAlgoAPI_Cut(anObject, aTool);
96       if (mkCut && mkCut->IsDone()) {
97                 setImpl(mkCut);
98                 myDone = mkCut->IsDone() == Standard_True;
99                 myMkShape = new GeomAlgoAPI_MakeShape (mkCut);
100                 aResult = mkCut->Shape();    
101           }
102           break;
103         }
104   case BOOL_COMMON:
105         {
106       BRepAlgoAPI_Common* mkCom = new BRepAlgoAPI_Common(anObject, aTool);
107       if (mkCom && mkCom->IsDone()) {
108                 setImpl(mkCom);
109                 myDone = mkCom->IsDone() == Standard_True;
110                 myMkShape = new GeomAlgoAPI_MakeShape (mkCom);
111                 aResult = mkCom->Shape(); 
112           }
113           break;
114         }       
115   }
116   if(myDone) {
117         if(aResult.ShapeType() == TopAbs_COMPOUND) 
118       aResult = GeomAlgoAPI_DFLoader::refineResult(aResult);
119         myShape->setImpl(new TopoDS_Shape(aResult));
120         boost::shared_ptr<GeomAPI_Shape> aGeomResult(new GeomAPI_Shape());
121         aGeomResult->setImpl(new TopoDS_Shape(aResult)); 
122
123         // fill data map to keep correct orientation of sub-shapes 
124         for (TopExp_Explorer Exp(aResult,TopAbs_FACE); Exp.More(); Exp.Next()) {
125           boost::shared_ptr<GeomAPI_Shape> aCurrentShape(new GeomAPI_Shape());
126       aCurrentShape->setImpl(new TopoDS_Shape(Exp.Current()));
127           myMap.bind(aCurrentShape, aCurrentShape);
128         }
129   }  
130 }
131
132
133 //============================================================================
134 const bool GeomAlgoAPI_Boolean::isDone() const
135 {return myDone;}
136
137 //============================================================================
138 const bool GeomAlgoAPI_Boolean::isValid() const
139 {
140   BRepCheck_Analyzer aChecker(myShape->impl<TopoDS_Shape>());
141   return (aChecker.IsValid() == Standard_True);
142 }
143
144 //============================================================================
145 const boost::shared_ptr<GeomAPI_Shape>& GeomAlgoAPI_Boolean::shape () const 
146 {
147   return myShape;
148 }
149
150 //============================================================================
151 void GeomAlgoAPI_Boolean::mapOfShapes (GeomAPI_DataMapOfShapeShape& theMap) const
152 {
153   theMap = myMap;
154 }
155
156 //============================================================================
157 GeomAlgoAPI_MakeShape * GeomAlgoAPI_Boolean::makeShape() const
158 {
159   return myMkShape;
160 }
161
162 //============================================================================
163 GeomAlgoAPI_Boolean::~GeomAlgoAPI_Boolean()
164 {
165   if (myImpl) {    
166         myMap.clear();
167   }
168 }