b311480e |
1 | // Created on: 1999-04-27 |
2 | // Created by: Pavel DURANDIN |
3 | // Copyright (c) 1999-1999 Matra Datavision |
973c2be1 |
4 | // Copyright (c) 1999-2014 OPEN CASCADE SAS |
b311480e |
5 | // |
973c2be1 |
6 | // This file is part of Open CASCADE Technology software library. |
b311480e |
7 | // |
d5f74e42 |
8 | // This library is free software; you can redistribute it and/or modify it under |
9 | // the terms of the GNU Lesser General Public License version 2.1 as published |
973c2be1 |
10 | // by the Free Software Foundation, with special exception defined in the file |
11 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT |
12 | // distribution for complete text of the license and disclaimer of any warranty. |
b311480e |
13 | // |
973c2be1 |
14 | // Alternatively, this file may be used under the terms of Open CASCADE |
15 | // commercial license or contractual agreement. |
b311480e |
16 | |
7fd59977 |
17 | // abv 16.06.99 returning ReShape context; processing shared subshapes in compounds |
18 | // sln 29.11.01 Bug21: in method Perform(..) nullify location of compound's faces only if mode myConsiderLocation is on |
19 | |
42cf5bc1 |
20 | #include <BRep_Builder.hxx> |
21 | #include <Message_Msg.hxx> |
7fd59977 |
22 | #include <Precision.hxx> |
7fd59977 |
23 | #include <ShapeBuild_ReShape.hxx> |
42cf5bc1 |
24 | #include <ShapeExtend.hxx> |
25 | #include <ShapeExtend_BasicMsgRegistrator.hxx> |
26 | #include <ShapeUpgrade_FaceDivide.hxx> |
27 | #include <ShapeUpgrade_ShapeDivide.hxx> |
28 | #include <ShapeUpgrade_WireDivide.hxx> |
29 | #include <Standard_ErrorHandler.hxx> |
30 | #include <Standard_Failure.hxx> |
7fd59977 |
31 | #include <TopExp.hxx> |
42cf5bc1 |
32 | #include <TopExp_Explorer.hxx> |
7fd59977 |
33 | #include <TopoDS.hxx> |
7fd59977 |
34 | #include <TopoDS_Compound.hxx> |
42cf5bc1 |
35 | #include <TopoDS_Edge.hxx> |
7fd59977 |
36 | #include <TopoDS_Iterator.hxx> |
42cf5bc1 |
37 | #include <TopoDS_Shape.hxx> |
7fd59977 |
38 | #include <TopoDS_Vertex.hxx> |
42cf5bc1 |
39 | #include <TopoDS_Wire.hxx> |
7fd59977 |
40 | |
41 | //======================================================================= |
42 | //function : ShapeUpgrade_ShapeDivide |
43 | //purpose : |
44 | //======================================================================= |
7fd59977 |
45 | ShapeUpgrade_ShapeDivide::ShapeUpgrade_ShapeDivide() : myStatus(0) |
46 | { |
47 | myPrecision = myMinTol = Precision::Confusion(); |
48 | myMaxTol = 1; //Precision::Infinite() ?? pdn |
49 | mySplitFaceTool = new ShapeUpgrade_FaceDivide; |
50 | myContext = new ShapeBuild_ReShape; |
da2db6a7 |
51 | //myMsgReg = new ShapeExtend_BasicMsgRegistrator; |
7fd59977 |
52 | mySegmentMode = Standard_True; |
53 | myEdgeMode = 2; |
54 | } |
55 | |
56 | //======================================================================= |
57 | //function : ShapeUpgrade_ShapeDivide |
58 | //purpose : |
59 | //======================================================================= |
60 | |
61 | ShapeUpgrade_ShapeDivide::ShapeUpgrade_ShapeDivide(const TopoDS_Shape &S) : myStatus(0) |
62 | { |
63 | myPrecision = myMinTol = Precision::Confusion(); |
64 | myMaxTol = 1; //Precision::Infinite() ?? pdn |
65 | mySplitFaceTool = new ShapeUpgrade_FaceDivide; |
66 | myContext = new ShapeBuild_ReShape; |
67 | mySegmentMode = Standard_True; |
68 | myEdgeMode = 2; |
69 | Init(S); |
70 | } |
71 | |
72 | //======================================================================= |
73 | //function : Init |
74 | //purpose : |
75 | //======================================================================= |
76 | |
77 | void ShapeUpgrade_ShapeDivide::Init(const TopoDS_Shape &S) |
78 | { |
79 | myShape = S; |
80 | } |
81 | |
82 | //======================================================================= |
e6f550da |
83 | //function : ~ShapeUpgrade_ShapeDivide |
7fd59977 |
84 | //purpose : |
85 | //======================================================================= |
86 | |
e6f550da |
87 | ShapeUpgrade_ShapeDivide::~ShapeUpgrade_ShapeDivide() |
7fd59977 |
88 | {} |
89 | |
90 | |
91 | //======================================================================= |
92 | //function : SetPrecision |
93 | //purpose : |
94 | //======================================================================= |
95 | |
96 | void ShapeUpgrade_ShapeDivide::SetPrecision (const Standard_Real Prec) |
97 | { |
98 | myPrecision = Prec; |
99 | } |
100 | |
101 | //======================================================================= |
102 | //function : SetMaxTolerance |
103 | //purpose : |
104 | //======================================================================= |
105 | |
106 | void ShapeUpgrade_ShapeDivide::SetMaxTolerance (const Standard_Real maxtol) |
107 | { |
108 | myMaxTol = maxtol; |
109 | } |
110 | |
111 | |
112 | //======================================================================= |
113 | //function : SetMinTolerance |
114 | //purpose : |
115 | //======================================================================= |
116 | |
117 | void ShapeUpgrade_ShapeDivide::SetMinTolerance (const Standard_Real mintol) |
118 | { |
119 | myMinTol = mintol; |
120 | } |
121 | |
122 | |
123 | //======================================================================= |
124 | //function : SetSurfaceSegmentMode |
125 | //purpose : |
126 | //======================================================================= |
127 | |
128 | void ShapeUpgrade_ShapeDivide::SetSurfaceSegmentMode(const Standard_Boolean Segment) |
129 | { |
130 | mySegmentMode = Segment; |
131 | } |
132 | //======================================================================= |
133 | //function : Perform |
134 | //purpose : |
135 | //======================================================================= |
136 | |
137 | Standard_Boolean ShapeUpgrade_ShapeDivide::Perform(const Standard_Boolean newContext) |
138 | { |
139 | myStatus = ShapeExtend::EncodeStatus ( ShapeExtend_OK ); |
140 | if(myShape.IsNull()) { |
141 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_FAIL1 ); |
142 | return Standard_False; |
143 | } |
144 | |
145 | if ( newContext || myContext.IsNull() ) |
146 | myContext = new ShapeBuild_ReShape; |
147 | |
148 | // Process COMPOUNDs separately in order to handle sharing in assemblies |
149 | // NOTE: not optimized: subshape can be processed twice (second time - no modif) |
150 | if ( myShape.ShapeType() == TopAbs_COMPOUND ) { |
151 | Standard_Integer locStatus = myStatus; |
152 | TopoDS_Compound C; |
153 | BRep_Builder B; |
154 | B.MakeCompound ( C ); |
155 | TopoDS_Shape savShape = myShape; |
156 | for ( TopoDS_Iterator it(savShape,Standard_False); it.More(); it.Next() ) { |
157 | TopoDS_Shape shape = it.Value(); |
158 | TopLoc_Location L = shape.Location(); |
159 | if(myContext->ModeConsiderLocation()) { |
160 | TopLoc_Location nullLoc; |
161 | shape.Location ( nullLoc ); |
162 | } |
163 | myShape = myContext->Apply ( shape ); |
164 | Perform ( Standard_False ); |
165 | if(myContext->ModeConsiderLocation()) |
166 | myResult.Location ( L ); |
167 | myResult.Orientation(TopAbs::Compose(myResult.Orientation(),savShape.Orientation())); |
168 | B.Add ( C, myResult ); |
169 | locStatus |= myStatus; |
170 | } |
171 | |
172 | myShape = savShape; |
173 | myStatus = locStatus; |
174 | if ( Status ( ShapeExtend_DONE ) ) { |
175 | myResult = myContext->Apply ( C, TopAbs_SHAPE ); |
176 | myContext->Replace ( myShape, myResult ); |
177 | return Standard_True; |
178 | } |
179 | myResult = myShape; |
180 | return Standard_False; |
181 | } |
182 | |
183 | // Process FACEs |
184 | Handle(ShapeUpgrade_FaceDivide) SplitFace = GetSplitFaceTool(); |
185 | if ( ! SplitFace.IsNull() ) { |
186 | SplitFace->SetPrecision( myPrecision ); |
187 | SplitFace->SetMaxTolerance(myMaxTol); |
188 | SplitFace->SetSurfaceSegmentMode(mySegmentMode); |
189 | Handle(ShapeUpgrade_WireDivide) SplitWire = SplitFace->GetWireDivideTool(); |
190 | if ( ! SplitWire.IsNull() ) { |
191 | SplitWire->SetMinTolerance(myMinTol); |
192 | SplitWire->SetEdgeMode(myEdgeMode); |
193 | } |
da2db6a7 |
194 | Message_Msg doneMsg = GetFaceMsg(); |
195 | |
7fd59977 |
196 | for(TopExp_Explorer exp(myShape,TopAbs_FACE); exp.More(); exp.Next()) { |
197 | //smh#8 |
198 | TopoDS_Shape tmpF = exp.Current().Oriented ( TopAbs_FORWARD ); |
199 | TopoDS_Face F = TopoDS::Face (tmpF); // protection against INTERNAL shapes: cts20105a.rle |
200 | TopoDS_Shape sh = myContext->Apply ( F, TopAbs_SHAPE ); |
201 | for (TopExp_Explorer exp2(sh,TopAbs_FACE); exp2.More(); exp2.Next()) { |
202 | //szv: try-catch added |
203 | try { |
204 | OCC_CATCH_SIGNALS |
205 | for (; exp2.More(); exp2.Next()) { |
206 | TopoDS_Face face = TopoDS::Face ( exp2.Current() ); |
207 | SplitFace->Init(face); |
208 | SplitFace->SetContext(myContext); |
209 | SplitFace->Perform(); |
210 | if(SplitFace->Status(ShapeExtend_FAIL)) { |
211 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_FAIL2 ); |
212 | } |
213 | if(SplitFace->Status(ShapeExtend_DONE)) { |
214 | myContext->Replace(face,SplitFace->Result()); |
da2db6a7 |
215 | SendMsg( face, doneMsg, Message_Info ); |
7fd59977 |
216 | if(SplitFace->Status(ShapeExtend_DONE1)) |
217 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_DONE1 ); |
218 | if(SplitFace->Status(ShapeExtend_DONE2)) |
219 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_DONE2 ); |
220 | } |
221 | } |
222 | } |
9775fa61 |
223 | catch (Standard_Failure const& anException) { |
0797d9d3 |
224 | #ifdef OCCT_DEBUG |
7fd59977 |
225 | cout << "\nError: Exception in ShapeUpgrade_FaceDivide::Perform(): "; |
9775fa61 |
226 | anException.Print(cout); cout << endl; |
7fd59977 |
227 | #endif |
9775fa61 |
228 | (void)anException; |
229 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_FAIL2 ); |
7fd59977 |
230 | } |
231 | } |
232 | } |
233 | } |
234 | |
235 | // Process free WIREs |
236 | Handle(ShapeUpgrade_WireDivide) SplitWire = SplitFace->GetWireDivideTool(); |
237 | if ( ! SplitWire.IsNull() ) { |
238 | SplitWire->SetFace (TopoDS_Face()); |
239 | SplitWire->SetPrecision( myPrecision ); |
240 | SplitWire->SetMaxTolerance(myMaxTol); |
241 | SplitWire->SetMinTolerance(myMinTol); |
242 | SplitWire->SetEdgeMode(myEdgeMode); |
da2db6a7 |
243 | Message_Msg doneMsg = GetWireMsg(); |
244 | |
7fd59977 |
245 | TopExp_Explorer exp;//svv Jan 10 2000 : porting on DEC |
246 | for (exp.Init (myShape, TopAbs_WIRE, TopAbs_FACE); exp.More(); exp.Next()) { |
247 | //smh#8 |
248 | TopoDS_Shape tmpW = exp.Current().Oriented ( TopAbs_FORWARD ); |
249 | TopoDS_Wire W = TopoDS::Wire (tmpW ); // protection against INTERNAL shapes |
250 | TopoDS_Shape sh = myContext->Apply ( W, TopAbs_SHAPE ); |
251 | for (TopExp_Explorer exp2 (sh,TopAbs_WIRE); exp2.More(); exp2.Next()) { |
252 | TopoDS_Wire wire = TopoDS::Wire ( exp2.Current() ); |
253 | SplitWire->Load (wire); |
254 | SplitWire->SetContext(myContext); |
255 | SplitWire->Perform(); |
256 | if(SplitWire->Status(ShapeExtend_FAIL)) { |
257 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_FAIL3 ); |
258 | } |
259 | if(SplitWire->Status(ShapeExtend_DONE)) { |
260 | myContext->Replace(wire,SplitWire->Wire()); |
da2db6a7 |
261 | SendMsg( wire, doneMsg, Message_Info ); |
7fd59977 |
262 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_DONE1 ); |
263 | } |
264 | } |
265 | } |
266 | |
267 | // Process free EDGEs |
da2db6a7 |
268 | Message_Msg edgeDoneMsg = GetEdgeMsg(); |
7fd59977 |
269 | for (exp.Init (myShape, TopAbs_EDGE, TopAbs_WIRE); exp.More(); exp.Next()) { |
270 | //smh#8 |
271 | TopoDS_Shape tmpE = exp.Current().Oriented ( TopAbs_FORWARD ); |
272 | TopoDS_Edge E = TopoDS::Edge (tmpE ); // protection against INTERNAL shapes |
273 | TopoDS_Vertex V1,V2; |
274 | TopExp::Vertices(E,V2,V1); |
275 | if( V1.IsNull() && V2.IsNull() ) continue; // skl 27.10.2004 for OCC5624 |
276 | TopoDS_Shape sh = myContext->Apply ( E, TopAbs_SHAPE ); |
277 | for (TopExp_Explorer exp2 (sh,TopAbs_EDGE); exp2.More(); exp2.Next()) { |
278 | TopoDS_Edge edge = TopoDS::Edge ( exp2.Current() ); |
279 | SplitWire->Load (edge); |
280 | SplitWire->SetContext(myContext); |
281 | SplitWire->Perform(); |
282 | if(SplitWire->Status(ShapeExtend_FAIL)) { |
283 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_FAIL3 ); |
284 | } |
285 | if(SplitWire->Status(ShapeExtend_DONE)) { |
286 | myContext->Replace(edge,SplitWire->Wire()); |
da2db6a7 |
287 | SendMsg( edge, edgeDoneMsg, Message_Info ); |
7fd59977 |
288 | myStatus |= ShapeExtend::EncodeStatus ( ShapeExtend_DONE1 ); |
289 | } |
290 | } |
291 | } |
292 | } |
293 | myResult = myContext->Apply ( myShape, TopAbs_SHAPE ); |
294 | return ! myResult.IsSame ( myShape ); |
295 | } |
296 | |
297 | //======================================================================= |
298 | //function : Result |
299 | //purpose : |
300 | //======================================================================= |
301 | |
302 | TopoDS_Shape ShapeUpgrade_ShapeDivide::Result() const |
303 | { |
304 | return myResult; |
305 | } |
306 | |
307 | //======================================================================= |
308 | //function : GetContext |
309 | //purpose : |
310 | //======================================================================= |
311 | |
312 | Handle(ShapeBuild_ReShape) ShapeUpgrade_ShapeDivide::GetContext() const |
313 | { |
314 | //if ( myContext.IsNull() ) myContext = new ShapeBuild_ReShape; |
315 | return myContext; |
316 | } |
317 | |
318 | //======================================================================= |
319 | //function : SetContext |
320 | //purpose : |
321 | //======================================================================= |
322 | |
323 | void ShapeUpgrade_ShapeDivide::SetContext (const Handle(ShapeBuild_ReShape) &context) |
324 | { |
325 | myContext = context; |
326 | } |
327 | |
328 | //======================================================================= |
329 | //function : SetSplitFaceTool |
330 | //purpose : |
331 | //======================================================================= |
332 | |
333 | void ShapeUpgrade_ShapeDivide::SetSplitFaceTool(const Handle(ShapeUpgrade_FaceDivide)& splitFaceTool) |
334 | { |
335 | mySplitFaceTool = splitFaceTool; |
336 | } |
337 | |
338 | //======================================================================= |
339 | //function : GetSplitFaceTool |
340 | //purpose : |
341 | //======================================================================= |
342 | |
343 | Handle(ShapeUpgrade_FaceDivide) ShapeUpgrade_ShapeDivide::GetSplitFaceTool () const |
344 | { |
345 | return mySplitFaceTool; |
346 | } |
347 | |
348 | //======================================================================= |
349 | //function : Status |
350 | //purpose : |
351 | //======================================================================= |
352 | |
353 | Standard_Boolean ShapeUpgrade_ShapeDivide::Status (const ShapeExtend_Status status) const |
354 | { |
355 | return ShapeExtend::DecodeStatus ( myStatus, status ); |
356 | } |
357 | |
358 | //======================================================================= |
359 | //function : SetEdgeMode |
360 | //purpose : |
361 | //======================================================================= |
362 | |
363 | void ShapeUpgrade_ShapeDivide::SetEdgeMode(const Standard_Integer aEdgeMode) |
364 | { |
365 | myEdgeMode = aEdgeMode; |
366 | } |
da2db6a7 |
367 | |
368 | //======================================================================= |
369 | //function : SetMsgRegistrator |
370 | //purpose : |
371 | //======================================================================= |
372 | |
373 | void ShapeUpgrade_ShapeDivide::SetMsgRegistrator(const Handle(ShapeExtend_BasicMsgRegistrator)& msgreg) |
374 | { |
375 | myMsgReg = msgreg; |
376 | } |
377 | |
378 | //======================================================================= |
379 | //function : MsgRegistrator |
380 | //purpose : |
381 | //======================================================================= |
382 | |
383 | Handle(ShapeExtend_BasicMsgRegistrator) ShapeUpgrade_ShapeDivide::MsgRegistrator() const |
384 | { |
385 | return myMsgReg; |
386 | } |
387 | |
388 | //======================================================================= |
389 | //function : SendMsg |
390 | //purpose : |
391 | //======================================================================= |
392 | |
393 | void ShapeUpgrade_ShapeDivide::SendMsg(const TopoDS_Shape& shape, |
394 | const Message_Msg& message, |
395 | const Message_Gravity gravity) const |
396 | { |
397 | if ( !myMsgReg.IsNull() ) |
398 | myMsgReg->Send (shape, message, gravity); |
399 | } |
400 | |
401 | Message_Msg ShapeUpgrade_ShapeDivide::GetFaceMsg() const |
402 | { |
403 | return "ShapeDivide.FaceDivide.MSG0"; |
404 | } |
405 | Message_Msg ShapeUpgrade_ShapeDivide::GetWireMsg() const |
406 | { |
407 | return "ShapeDivide.WireDivide.MSG0"; |
408 | } |
409 | Message_Msg ShapeUpgrade_ShapeDivide::GetEdgeMsg() const |
410 | { |
411 | return "ShapeDivide.EdgeDivide.MSG0"; |
412 | } |