b311480e |
1 | // Created on: 1997-11-20 |
2 | // Created by: Prestataire Mary FABIEN |
3 | // Copyright (c) 1997-1999 Matra Datavision |
4 | // Copyright (c) 1999-2012 OPEN CASCADE SAS |
5 | // |
6 | // The content of this file is subject to the Open CASCADE Technology Public |
7 | // License Version 6.5 (the "License"). You may not use the content of this file |
8 | // except in compliance with the License. Please obtain a copy of the License |
9 | // at http://www.opencascade.org and read it completely before using this file. |
10 | // |
11 | // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its |
12 | // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France. |
13 | // |
14 | // The Original Code and all software distributed under the License is |
15 | // distributed on an "AS IS" basis, without warranty of any kind, and the |
16 | // Initial Developer hereby disclaims all such warranties, including without |
17 | // limitation, any warranties of merchantability, fitness for a particular |
18 | // purpose or non-infringement. Please see the License for the specific terms |
19 | // and conditions governing the rights and limitations under the License. |
20 | |
7fd59977 |
21 | |
22 | |
23 | #include <BRepAlgo_BooleanOperations.ixx> |
24 | #include <TopOpeBRep_DSFiller.hxx> |
25 | #include <TopOpeBRepDS_BuildTool.hxx> |
26 | #include <TopOpeBRepTool_GeomTool.hxx> |
27 | #include <BRep_Tool.hxx> |
28 | #include <BRep_Builder.hxx> |
29 | #include <BRepTools_Substitution.hxx> |
30 | #include <TopoDS.hxx> |
31 | #include <TopoDS_Compound.hxx> |
32 | #include <TopTools_ListOfShape.hxx> |
33 | #include <TopTools_ListIteratorOfListOfShape.hxx> |
34 | #include <Geom_Surface.hxx> |
35 | #include <TopLoc_Location.hxx> |
36 | #include <Bnd_Box.hxx> |
37 | #include <BRepBndLib.hxx> |
38 | |
39 | //======================================================================= |
40 | //function : Create |
41 | //purpose : |
42 | //======================================================================= |
b311480e |
43 | BRepAlgo_BooleanOperations::BRepAlgo_BooleanOperations() : |
7fd59977 |
44 | myApproxNbPntMax (30) , |
45 | myApproxTol3D (1.e-7) , |
46 | myApproxTol2D (1.e-7) , |
47 | myApproxRelativeTol (Standard_True) |
48 | { |
49 | } |
50 | |
51 | //======================================================================= |
52 | //function : Shapes2d |
53 | //purpose : |
54 | //======================================================================= |
55 | void BRepAlgo_BooleanOperations::Shapes2d (const TopoDS_Shape& S1, |
56 | const TopoDS_Shape& S2) |
57 | { |
58 | // S1 doit etre une face ou un ensemble de faces |
59 | // S2 doit etre une edge. |
60 | |
61 | if (S2.ShapeType() != TopAbs_EDGE) return; |
62 | |
63 | BRep_Builder Builder ; |
64 | TopoDS_Wire Wire ; |
65 | Builder.MakeWire (Wire); |
66 | Builder.Add (Wire, S2); |
67 | |
68 | TopExp_Explorer Exp (S1, TopAbs_FACE) ; |
69 | if (!Exp.More()) return ; |
70 | const TopoDS_Face& FirstFace = TopoDS::Face (Exp.Current()) ; |
71 | |
72 | TopLoc_Location Loc; |
73 | const Handle(Geom_Surface)& Surf = BRep_Tool::Surface (FirstFace, Loc) ; |
74 | |
75 | TopoDS_Face Face ; |
76 | Builder.MakeFace (Face, Surf, Loc, BRep_Tool::Tolerance (FirstFace)) ; |
77 | Builder.Add (Face, Wire) ; |
78 | Face.Orientation (FirstFace.Orientation()) ; |
79 | |
80 | myS1 = S1 ; |
81 | myS2 = Face ; |
82 | |
83 | myDSA.Init() ; |
84 | myDSA.Load (myS1, myS2) ; |
85 | Handle (TopOpeBRepDS_HDataStructure)& HDS = myDSA.ChangeDS() ; |
86 | myDSA.myDSFiller.Insert2d (myS1, myS2, HDS) ; |
87 | } |
88 | |
89 | //======================================================================= |
90 | //function : Shapes |
91 | //purpose : Defines the arguments. |
92 | //======================================================================= |
93 | void BRepAlgo_BooleanOperations::Shapes (const TopoDS_Shape& S1, |
94 | const TopoDS_Shape& S2) |
95 | { |
96 | myS1 = S1; |
97 | myS2 = S2; |
98 | myDSA.Init(); |
99 | myDSA.Load(myS1, myS2); |
100 | Handle(TopOpeBRepDS_HDataStructure)& HDS = myDSA.ChangeDS(); |
101 | myDSA.myDSFiller.Insert(myS1,myS2,HDS); |
102 | // const Standard_Boolean CheckShapes = Standard_True; |
103 | // Standard_Boolean esp = HDS->EdgesSameParameter(); |
104 | // Standard_Boolean localcheck = CheckShapes; |
105 | } |
106 | |
107 | //======================================================================= |
108 | //function : SetApproxParameters |
109 | //purpose : Sets the parameters for the approximations. |
110 | //======================================================================= |
111 | void BRepAlgo_BooleanOperations::SetApproxParameters (const Standard_Integer NbPntMax, |
112 | const Standard_Real Tol3D, |
113 | const Standard_Real Tol2D, |
114 | const Standard_Boolean RelativeTol) |
115 | { |
116 | myApproxNbPntMax = NbPntMax ; |
117 | myApproxTol3D = Tol3D ; |
118 | myApproxTol2D = Tol2D ; |
119 | myApproxRelativeTol = RelativeTol ; |
120 | } |
121 | |
122 | //======================================================================= |
123 | //function : Define |
124 | //purpose : |
125 | //======================================================================= |
126 | void BRepAlgo_BooleanOperations::Define (const TopoDS_Shape& S1, |
127 | const TopoDS_Shape& S2, |
128 | Handle(TopOpeBRepDS_HDataStructure)& HDS) |
129 | { |
130 | ChangeDataStructure() = HDS; |
131 | myS1 = S1; |
132 | myS2 = S2; |
133 | } |
134 | |
135 | //======================================================================= |
136 | //function : Perform |
137 | //purpose : Performs the global boolean operation. |
138 | //======================================================================= |
139 | void BRepAlgo_BooleanOperations::Perform () |
140 | { |
141 | TopOpeBRepDS_BuildTool& BTofBuilder = myDSA.myHB->ChangeBuildTool(); |
142 | TopOpeBRepTool_GeomTool& GTofBTofBuilder = BTofBuilder.ChangeGeomTool(); |
143 | GTofBTofBuilder.SetNbPntMax(myApproxNbPntMax); |
144 | GTofBTofBuilder.SetTolerances (myApproxTol3D, myApproxTol2D, myApproxRelativeTol) ; |
145 | Handle(TopOpeBRepBuild_HBuilder)& HB = myDSA.myHB; |
146 | Handle(TopOpeBRepDS_HDataStructure)& HDS = myDSA.ChangeDS(); |
147 | HB->Perform(HDS,myS1,myS2); |
148 | } |
149 | |
150 | //======================================================================= |
151 | //function : Perform |
152 | //purpose : Performs the global boolean operation in regards of the |
153 | // given states. |
154 | //======================================================================= |
155 | void BRepAlgo_BooleanOperations::Perform (const TopAbs_State State1, |
156 | const TopAbs_State State2) |
157 | { |
158 | Perform() ; |
159 | |
160 | myShape.Nullify() ; |
161 | myResult.Nullify() ; |
162 | myMapShape.Clear() ; |
163 | |
164 | Handle(TopOpeBRepBuild_HBuilder)& HBuilder = ChangeBuilder() ; |
165 | HBuilder->MergeShapes (myS1, State1, myS2, State2) ; |
166 | |
167 | const TopTools_ListOfShape& ListResults = HBuilder->Merged (myS1, State1) ; |
168 | Standard_Integer NbResults = ListResults.Extent() ; |
169 | if (NbResults > 0) { |
170 | if (NbResults == 1) { |
171 | myShape = ListResults.First() ; |
172 | } else { |
173 | BRep_Builder Builder ; |
174 | Builder.MakeCompound (TopoDS::Compound (myShape)) ; |
175 | TopTools_ListIteratorOfListOfShape Iter ; |
176 | for (Iter.Initialize (ListResults) ; Iter.More() ; Iter.Next()) |
177 | Builder.Add (myShape, Iter.Value()) ; |
178 | } |
179 | TopExp_Explorer Explorer ; |
180 | for (Explorer.Init (myShape, TopAbs_FACE) ; Explorer.More() ; Explorer.Next()) { |
181 | myMapShape.Add (Explorer.Current()) ; |
182 | } |
183 | for (Explorer.Init (myShape, TopAbs_EDGE) ; Explorer.More() ; Explorer.Next()) { |
184 | myMapShape.Add (Explorer.Current()) ; |
185 | } |
186 | } |
187 | } |
188 | |
189 | //======================================================================= |
190 | //function : Common |
191 | //purpose : |
192 | //======================================================================= |
193 | const TopoDS_Shape& BRepAlgo_BooleanOperations::Common() |
194 | { |
195 | Perform (TopAbs_IN, TopAbs_IN) ; |
196 | return myShape ; |
197 | } |
198 | |
199 | //======================================================================= |
200 | //function : fus |
201 | //purpose : |
202 | //======================================================================= |
203 | const TopoDS_Shape& BRepAlgo_BooleanOperations::Fus() |
204 | { |
205 | Perform (TopAbs_OUT, TopAbs_OUT) ; |
206 | return myShape ; |
207 | } |
208 | |
209 | //======================================================================= |
210 | //function : cut |
211 | //purpose : |
212 | //======================================================================= |
213 | const TopoDS_Shape& BRepAlgo_BooleanOperations::Cut() |
214 | { |
215 | Perform (TopAbs_OUT, TopAbs_IN) ; |
216 | return myShape ; |
217 | } |
218 | |
219 | //======================================================================= |
220 | //function : Section |
221 | //purpose : |
222 | //======================================================================= |
223 | const TopoDS_Shape& BRepAlgo_BooleanOperations::Section() |
224 | { |
225 | // Standard_Boolean bcw = BuilderCanWork(); |
226 | // if ( ! bcw || myshapeisnull) return; |
227 | |
228 | Perform () ; |
229 | |
230 | myShape.Nullify() ; |
231 | myResult.Nullify() ; |
232 | myMapShape.Clear() ; |
233 | |
234 | Handle(TopOpeBRepBuild_HBuilder)& HBuilder = myDSA.myHB ; |
235 | |
236 | const TopTools_ListOfShape& ListResults = HBuilder->Section() ; |
237 | Standard_Integer NbResults = ListResults.Extent() ; |
238 | if (NbResults > 0) { |
239 | if (NbResults == 1) { |
240 | myShape = ListResults.First() ; |
241 | } else { |
242 | BRep_Builder Builder ; |
243 | Builder.MakeCompound (TopoDS::Compound (myShape)) ; |
244 | TopTools_ListIteratorOfListOfShape Iter ; |
245 | for (Iter.Initialize (ListResults) ; Iter.More() ; Iter.Next()) |
246 | Builder.Add (myShape, Iter.Value()) ; |
247 | } |
248 | TopExp_Explorer Explorer ; |
249 | for (Explorer.Init (myShape, TopAbs_EDGE) ; Explorer.More() ; Explorer.Next()) { |
250 | myMapShape.Add (Explorer.Current()) ; |
251 | } |
252 | } |
253 | |
254 | return myShape ; |
255 | } |
256 | |
257 | //======================================================================= |
258 | //function : Shape |
259 | //purpose : |
260 | //======================================================================= |
261 | const TopoDS_Shape& BRepAlgo_BooleanOperations::Shape() |
262 | { |
263 | return myShape; |
264 | } |
265 | |
266 | //======================================================================= |
267 | //function : Shape |
268 | //purpose : |
269 | //======================================================================= |
270 | const TopoDS_Shape& BRepAlgo_BooleanOperations::ShapeFrom (const TopoDS_Shape& Shape) |
271 | { |
272 | myResult.Nullify() ; |
273 | |
274 | if (!myShape.IsNull()) { |
275 | |
276 | TopoDS_Shape ShapeToDel ; |
277 | if (Shape.IsSame (myS1)) { |
278 | ShapeToDel = myS2 ; |
279 | } else { |
280 | ShapeToDel = myS1 ; |
281 | } |
282 | |
283 | BRepTools_Substitution Substitute ; |
284 | |
285 | TopTools_ListOfShape NullFaces ; |
286 | NullFaces.Clear() ; |
287 | |
288 | TopExp_Explorer ExpFac ; |
289 | for (ExpFac.Init (ShapeToDel, TopAbs_FACE) ; ExpFac.More() ; ExpFac.Next()) { |
290 | const TopoDS_Face& Face = TopoDS::Face (ExpFac.Current()) ; |
291 | const TopTools_ListOfShape& ListResults = Modified (Face) ; |
292 | if (ListResults.Extent() == 0) { |
293 | if (myMapShape.Contains (Face)) Substitute.Substitute (Face, NullFaces) ; |
294 | } else { |
295 | TopTools_ListIteratorOfListOfShape ItrFace ; |
296 | for (ItrFace.Initialize (ListResults) ; ItrFace.More() ; ItrFace.Next()) { |
297 | Substitute.Substitute (TopoDS::Face (ItrFace.Value()), NullFaces) ; |
298 | } |
299 | } |
300 | } |
301 | |
302 | Substitute.Build (myShape) ; |
303 | if (Substitute.IsCopied (myShape)) { |
304 | const TopTools_ListOfShape& ListResults = Substitute.Copy (myShape) ; |
305 | Standard_Integer NbResults = ListResults.Extent() ; |
306 | if (NbResults == 1) { |
307 | myResult = ListResults.First() ; |
308 | } else if (NbResults > 1) { |
309 | BRep_Builder Builder ; |
310 | Builder.MakeCompound (TopoDS::Compound (myResult)) ; |
311 | TopTools_ListIteratorOfListOfShape ItrResult ; |
312 | for (ItrResult.Initialize (ListResults) ; ItrResult.More() ; ItrResult.Next()) { |
313 | Builder.Add (myResult, ItrResult.Value()) ; |
314 | } |
315 | } |
316 | } else { |
317 | myResult = myShape ; |
318 | } |
319 | |
320 | } |
321 | return myResult ; |
322 | } |
323 | |
324 | //======================================================================= |
325 | //function : Modified |
326 | //purpose : |
327 | //======================================================================= |
328 | const TopTools_ListOfShape& BRepAlgo_BooleanOperations::Modified (const TopoDS_Shape& Shape) |
329 | { |
330 | return myDSA.Modified(Shape); |
331 | } |
332 | |
333 | //======================================================================= |
334 | //function : IsDeleted |
335 | //purpose : |
336 | //======================================================================= |
337 | Standard_Boolean BRepAlgo_BooleanOperations::IsDeleted (const TopoDS_Shape& Shape) |
338 | { |
339 | Standard_Boolean Deleted = Standard_True ; |
340 | |
341 | Handle(TopOpeBRepBuild_HBuilder)& HBuilder = myDSA.myHB ; |
342 | |
343 | if ( myMapShape.Contains (Shape) |
344 | || HBuilder->IsMerged (Shape, TopAbs_OUT) |
345 | || HBuilder->IsMerged (Shape, TopAbs_IN) |
346 | || HBuilder->IsMerged (Shape, TopAbs_ON) |
347 | || HBuilder->IsSplit (Shape, TopAbs_OUT) |
348 | || HBuilder->IsSplit (Shape, TopAbs_IN) |
349 | || HBuilder->IsSplit (Shape, TopAbs_ON)) |
350 | Deleted = Standard_False ; |
351 | |
352 | return Deleted ; |
353 | } |
354 | |
355 | //======================================================================= |
356 | //function : DataStructure |
357 | //purpose : |
358 | //======================================================================= |
359 | const Handle(TopOpeBRepDS_HDataStructure)& BRepAlgo_BooleanOperations::DataStructure() const |
360 | { |
361 | return myDSA.DS(); |
362 | } |
363 | |
364 | //======================================================================= |
365 | //function : DataStructure |
366 | //purpose : |
367 | //======================================================================= |
368 | Handle(TopOpeBRepDS_HDataStructure)& BRepAlgo_BooleanOperations::ChangeDataStructure() |
369 | { |
370 | return myDSA.ChangeDS(); |
371 | } |
372 | |
373 | //======================================================================= |
374 | //function : Builder |
375 | //purpose : |
376 | //======================================================================= |
377 | const Handle(TopOpeBRepBuild_HBuilder)& BRepAlgo_BooleanOperations::Builder() const |
378 | { |
379 | return myDSA.Builder(); |
380 | } |
381 | |
382 | //======================================================================= |
383 | //function : Builder |
384 | //purpose : |
385 | //======================================================================= |
386 | Handle(TopOpeBRepBuild_HBuilder)& BRepAlgo_BooleanOperations::ChangeBuilder() |
387 | { |
388 | return myDSA.ChangeBuilder(); |
389 | } |
390 | |
391 | //======================================================================= |
392 | //function : DataStructureAccess |
393 | //purpose : returns the member myDSA. |
394 | //======================================================================= |
395 | BRepAlgo_DSAccess& BRepAlgo_BooleanOperations::DataStructureAccess() |
396 | { |
397 | return myDSA; |
398 | } |
399 | |