0025748: Parallel version of progress indicator
[occt.git] / src / StepToTopoDS / StepToTopoDS_Builder.cxx
1 // Created on: 1995-01-03
2 // Created by: Frederic MAUPAS
3 // Copyright (c) 1995-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
5 //
6 // This file is part of Open CASCADE Technology software library.
7 //
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
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.
13 //
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
16
17 //:i6 abv 17 Sep 98: ProSTEP TR9 r0601-ct.stp: to be able read GeometricSet
18 //gka 11.01.99 file PRO7755.stp #2018: work-around error in BRepLib_MakeFace
19 //:n4 abv 12.02.99: S4132: treatment of GEOMETRIC_SETs implemented
20 //:o7 abv 18.02.99: bm1_sy_fuel.stp #1427(items 1,2) protection against null entity
21 //abv,gka 05.04.99 S4136: parameter names changed; avoid extra call to FixSameParameter
22
23 #include <BRep_Builder.hxx>
24 #include <BRepBuilderAPI_MakeEdge.hxx>
25 #include <BRepBuilderAPI_MakeFace.hxx>
26 #include <BRepBuilderAPI_MakeVertex.hxx>
27 #include <BRepLib.hxx>
28 #include <Geom_BoundedSurface.hxx>
29 #include <Geom_CartesianPoint.hxx>
30 #include <Geom_Curve.hxx>
31 #include <Geom_RectangularTrimmedSurface.hxx>
32 #include <Geom_Surface.hxx>
33 #include <Interface_Static.hxx>
34 #include <Message_Messenger.hxx>
35 #include <Message_ProgressScope.hxx>
36 #include <Precision.hxx>
37 #include <ShapeFix_ShapeTolerance.hxx>
38 #include <Standard_ErrorHandler.hxx>
39 #include <Standard_Failure.hxx>
40 #include <StdFail_NotDone.hxx>
41 #include <STEPControl_ActorRead.hxx>
42 #include <StepGeom_CartesianPoint.hxx>
43 #include <StepGeom_CompositeCurve.hxx>
44 #include <StepGeom_Curve.hxx>
45 #include <StepGeom_CurveBoundedSurface.hxx>
46 #include <StepGeom_GeometricRepresentationItem.hxx>
47 #include <StepGeom_RectangularCompositeSurface.hxx>
48 #include <StepGeom_Surface.hxx>
49 #include <StepGeom_SurfacePatch.hxx>
50 #include <StepShape_BrepWithVoids.hxx>
51 #include <StepShape_ClosedShell.hxx>
52 #include <StepShape_ConnectedEdgeSet.hxx>
53 #include <StepShape_EdgeBasedWireframeModel.hxx>
54 #include <StepShape_FaceBasedSurfaceModel.hxx>
55 #include <StepShape_FaceSurface.hxx>
56 #include <StepShape_FacetedBrep.hxx>
57 #include <StepShape_FacetedBrepAndBrepWithVoids.hxx>
58 #include <StepShape_GeometricSet.hxx>
59 #include <StepShape_GeometricSetSelect.hxx>
60 #include <StepShape_HArray1OfConnectedEdgeSet.hxx>
61 #include <StepShape_HArray1OfConnectedFaceSet.hxx>
62 #include <StepShape_HArray1OfEdge.hxx>
63 #include <StepShape_HArray1OfFace.hxx>
64 #include <StepShape_ManifoldSolidBrep.hxx>
65 #include <StepShape_OpenShell.hxx>
66 #include <StepShape_OrientedClosedShell.hxx>
67 #include <StepShape_Shell.hxx>
68 #include <StepShape_ShellBasedSurfaceModel.hxx>
69 #include <StepToGeom.hxx>
70 #include <StepToTopoDS_Builder.hxx>
71 #include <StepToTopoDS_DataMapOfTRI.hxx>
72 #include <StepToTopoDS_NMTool.hxx>
73 #include <StepToTopoDS_Tool.hxx>
74 #include <StepToTopoDS_TranslateCompositeCurve.hxx>
75 #include <StepToTopoDS_TranslateCurveBoundedSurface.hxx>
76 #include <StepToTopoDS_TranslateEdge.hxx>
77 #include <StepToTopoDS_TranslateFace.hxx>
78 #include <StepToTopoDS_TranslateShell.hxx>
79 #include <TopExp_Explorer.hxx>
80 #include <TopoDS.hxx>
81 #include <TopoDS_Compound.hxx>
82 #include <TopoDS_Edge.hxx>
83 #include <TopoDS_Face.hxx>
84 #include <TopoDS_Shape.hxx>
85 #include <TopoDS_Shell.hxx>
86 #include <TopoDS_Solid.hxx>
87 #include <Transfer_ActorOfTransientProcess.hxx>
88 #include <Transfer_TransientProcess.hxx>
89 #include <TransferBRep.hxx>
90
91 #include <stdio.h>
92 static void ResetPreci (const TopoDS_Shape& S, Standard_Real maxtol)
93 {
94   //:S4136
95   Standard_Integer modetol = Interface_Static::IVal("read.maxprecision.mode");
96   if (modetol) {
97     ShapeFix_ShapeTolerance STU;
98     STU.LimitTolerance (S,Precision::Confusion(),maxtol);
99   }
100 }
101
102 // ============================================================================
103 // Method  : StepToTopoDS_Builder::StepToTopoDS_Builder
104 // Purpose : Empty constructor
105 // ============================================================================
106
107 StepToTopoDS_Builder::StepToTopoDS_Builder()
108 : myError(StepToTopoDS_BuilderOther)
109 {
110   done = Standard_False;
111 }
112
113 // ============================================================================
114 // Method  : Init
115 // Purpose : Init with a ManifoldSolidBrep
116 // ============================================================================
117
118 void StepToTopoDS_Builder::Init
119 (const Handle(StepShape_ManifoldSolidBrep)& aManifoldSolid,
120  const Handle(Transfer_TransientProcess)& TP,
121  const Message_ProgressRange& theProgress)
122 {
123   Message_Messenger::StreamBuffer sout = TP->Messenger()->SendInfo();
124   // Initialisation of the Tool
125
126   StepToTopoDS_Tool         myTool;
127   StepToTopoDS_DataMapOfTRI aMap;
128
129   myTool.Init(aMap, TP);
130
131   // Start Mapping
132
133   Handle(StepShape_ConnectedFaceSet) aShell;
134   aShell = aManifoldSolid->Outer();
135
136   StepToTopoDS_TranslateShell myTranShell;
137   myTranShell.SetPrecision(Precision());
138   myTranShell.SetMaxTol(MaxTol());
139   // Non-manifold topology is not referenced by ManifoldSolidBrep (ssv; 14.11.2010)
140   StepToTopoDS_NMTool dummyNMTool;
141   myTranShell.Init(aShell, myTool, dummyNMTool, theProgress);
142
143   if (myTranShell.IsDone()) {
144     TopoDS_Shape Sh = myTranShell.Value();
145     Sh.Closed(Standard_True);
146     //BRepLib::SameParameter(Sh);
147     TopoDS_Solid S;
148     BRep_Builder B;
149     B.MakeSolid(S);
150     B.Add(S,Sh);
151     myResult = S;
152     myError  = StepToTopoDS_BuilderDone;
153     done     = Standard_True;
154
155     // Get Statistics :
156
157     if ( TP->TraceLevel() > 2 )
158     {
159       sout << "Geometric Statitics : " << std::endl;
160       sout << "   Surface Continuity : - C0 : " << myTool.C0Surf() << std::endl;
161       sout << "                        - C1 : " << myTool.C1Surf() << std::endl;
162       sout << "                        - C2 : " << myTool.C2Surf() << std::endl;
163       sout << "   Curve Continuity :   - C0 : " << myTool.C0Cur3() << std::endl;
164       sout << "                        - C1 : " << myTool.C1Cur3() << std::endl;
165       sout << "                        - C2 : " << myTool.C2Cur3() << std::endl;
166       sout << "   PCurve Continuity :  - C0 : " << myTool.C0Cur2() << std::endl;
167       sout << "                        - C1 : " << myTool.C1Cur2() << std::endl;
168       sout << "                        - C2 : " << myTool.C2Cur2() << std::endl;
169     }
170
171 //:S4136    ShapeFix::SameParameter (S,Standard_False);
172     ResetPreci (S, MaxTol());
173   }
174   else {
175     TP->AddWarning(aShell," OuterShell from ManifoldSolidBrep not mapped to TopoDS");
176     myError  = StepToTopoDS_BuilderOther;
177     done     = Standard_False;
178   }
179 }
180
181 // ============================================================================
182 // Method  : Init
183 // Purpose : Init with a BrepWithVoids
184 // ============================================================================
185
186 void StepToTopoDS_Builder::Init
187 (const Handle(StepShape_BrepWithVoids)& aBRepWithVoids,
188  const Handle(Transfer_TransientProcess)& TP,
189  const Message_ProgressRange& theProgress)
190 {
191   Message_Messenger::StreamBuffer sout = TP->Messenger()->SendInfo();
192  // Initialisation of the Tool
193   StepToTopoDS_Tool         myTool;
194   StepToTopoDS_DataMapOfTRI aMap;
195
196   myTool.Init(aMap, TP);
197
198   // Start Mapping
199
200   Standard_Integer Nb = aBRepWithVoids->NbVoids();
201   Handle(StepShape_ClosedShell) aCShell;
202   TopoDS_Solid S;
203   TopoDS_Shape Sh;
204   BRep_Builder B;
205   B.MakeSolid(S);
206   
207   Message_ProgressScope PS (theProgress, "Shell", Nb+1);
208
209   StepToTopoDS_TranslateShell myTranShell;
210
211   myTranShell.SetPrecision(Precision());//gka
212   myTranShell.SetMaxTol(MaxTol());
213   // OuterBound
214
215   aCShell = Handle(StepShape_ClosedShell)::DownCast(aBRepWithVoids->Outer());
216   // Non-manifold topology is not referenced by BrepWithVoids (ssv; 14.11.2010)
217   StepToTopoDS_NMTool dummyNMTool;
218   myTranShell.Init(aCShell, myTool, dummyNMTool, PS.Next());
219
220   if (myTranShell.IsDone()) {
221     Sh = myTranShell.Value();
222     Sh.Closed(Standard_True);
223     //BRepLib::SameParameter(Sh);
224     B.MakeSolid(S);
225     B.Add(S,Sh);
226     myResult = S;
227     myError  = StepToTopoDS_BuilderDone;
228     done     = Standard_True;
229   }
230   else {
231     TP->AddWarning(aCShell," OuterShell from BrepWithVoids not mapped to TopoDS");
232     myError  = StepToTopoDS_BuilderOther;
233     done     = Standard_False;
234     return;
235   }
236
237   // Voids
238
239   for (Standard_Integer i=1; i<=Nb && PS.More(); i++) {
240
241     aCShell = aBRepWithVoids->VoidsValue(i);
242     myTranShell.Init(aCShell, myTool, dummyNMTool, PS.Next());
243     if (myTranShell.IsDone()) {
244       Sh = myTranShell.Value();
245       Sh.Closed(Standard_True);
246
247       //:e0 abv 25 Mar 98: void should be an OrientedShell 
248       Handle(StepShape_OrientedClosedShell) aOCShell = aBRepWithVoids->VoidsValue(i);
249       if ( ! aOCShell.IsNull() && ! aOCShell->Orientation() ) Sh.Reverse();
250       
251       //BRepLib::SameParameter(Sh);
252       B.Add(S,Sh);
253     }
254     else {
255       TP->AddWarning
256         (aCShell," A Void from BrepWithVoids not mapped to TopoDS");
257     }
258   }
259   myResult = S;
260
261
262   // Get Statistics :
263   
264   if ( TP->TraceLevel() > 2 )
265   {
266     sout << "Geometric Statitics : " << std::endl;
267     sout << "   Surface Continuity : - C0 : " << myTool.C0Surf() << std::endl;
268     sout << "                        - C1 : " << myTool.C1Surf() << std::endl;
269     sout << "                        - C2 : " << myTool.C2Surf() << std::endl;
270     sout << "   Curve Continuity :   - C0 : " << myTool.C0Cur3() << std::endl;
271     sout << "                        - C1 : " << myTool.C1Cur3() << std::endl;
272     sout << "                        - C2 : " << myTool.C2Cur3() << std::endl;
273     sout << "   PCurve Continuity :  - C0 : " << myTool.C0Cur2() << std::endl;
274     sout << "                        - C1 : " << myTool.C1Cur2() << std::endl;
275     sout << "                        - C2 : " << myTool.C2Cur2() << std::endl;
276   }
277
278 //:S4136  ShapeFix::SameParameter (S,Standard_False);
279   ResetPreci (S, MaxTol());
280 }
281
282 // ============================================================================
283 // Method  : Init
284 // Purpose : Init with a FacetedBrep
285 // ============================================================================
286
287 void StepToTopoDS_Builder::Init(const Handle(StepShape_FacetedBrep)& aFB,
288                                 const Handle(Transfer_TransientProcess)& TP,
289                                 const Message_ProgressRange& theProgress)
290 {
291   // Initialisation of the Tool
292
293   StepToTopoDS_Tool         myTool;
294   StepToTopoDS_DataMapOfTRI aMap;
295
296   myTool.Init(aMap, TP);
297
298   // Start Mapping
299
300   Handle(StepShape_ClosedShell) aCShell;
301   aCShell = Handle(StepShape_ClosedShell)::DownCast(aFB->Outer());
302   TopoDS_Shape Sh;
303
304   StepToTopoDS_TranslateShell myTranShell; 
305   myTranShell.SetPrecision(Precision()); //gka
306   myTranShell.SetMaxTol(MaxTol());  
307   // Non-manifold topology is not referenced by FacetedBrep (ss; 14.11.2010)
308   StepToTopoDS_NMTool dummyNMTool;
309   myTranShell.Init(aCShell, myTool, dummyNMTool, theProgress);
310
311   if (myTranShell.IsDone()) {
312     Sh = myTranShell.Value();
313     Sh.Closed(Standard_True);
314     //BRepLib::SameParameter(Sh);
315     myTool.ClearEdgeMap();
316     myTool.ClearVertexMap();
317     TopoDS_Solid S;
318     BRep_Builder B;
319     B.MakeSolid(S);
320     B.Add(S,Sh);
321     myResult = S;
322     myError  = StepToTopoDS_BuilderDone;
323     done     = Standard_True;
324   }
325   else {
326     TP->AddWarning
327       (aCShell," OuterShell from FacetedBrep not mapped to TopoDS");
328     myError  = StepToTopoDS_BuilderOther;
329     done     = Standard_True;
330   }
331 }
332
333 // ============================================================================
334 // Method  : Init
335 // Purpose : Init with a FacetedBrepAndBrepWithVoids
336 // ============================================================================
337
338 void StepToTopoDS_Builder::Init
339 (const Handle(StepShape_FacetedBrepAndBrepWithVoids)& aFBABWV,
340  const Handle(Transfer_TransientProcess)& TP,
341  const Message_ProgressRange& theProgress)
342 {
343   // Initialisation of the Tool
344
345   StepToTopoDS_Tool         myTool;
346   StepToTopoDS_DataMapOfTRI aMap;
347
348   myTool.Init(aMap, TP);
349
350   // Start Mapping
351
352   Handle(StepShape_ClosedShell) aCShell;
353   aCShell = Handle(StepShape_ClosedShell)::DownCast(aFBABWV->Outer());
354   TopoDS_Shape Sh;
355
356   Message_ProgressScope aPSRoot(theProgress, NULL, 2);
357
358   StepToTopoDS_TranslateShell myTranShell;
359   myTranShell.SetPrecision(Precision()); //gka
360   myTranShell.SetMaxTol(MaxTol());
361   // Non-manifold topology is not referenced by FacetedBrepAndBrepWithVoids (ss; 14.11.2010)
362   StepToTopoDS_NMTool dummyNMTool;
363   myTranShell.Init(aCShell, myTool, dummyNMTool, aPSRoot.Next());
364
365   if (myTranShell.IsDone()) {
366     Sh = myTranShell.Value();
367     Sh.Closed(Standard_True);
368     //BRepLib::SameParameter(Sh);
369     TopoDS_Solid S;
370     BRep_Builder B;
371     B.MakeSolid(S);
372     B.Add(S,Sh);
373     Standard_Integer Nb, i;
374     Nb = aFBABWV->NbVoids();
375     Message_ProgressScope aPS (aPSRoot.Next(), NULL, Nb);
376     for ( i=1; i<=Nb && aPS.More(); i++) {
377       aCShell = aFBABWV->VoidsValue(i);
378       myTranShell.Init(aCShell, myTool, dummyNMTool, aPS.Next());
379       if (myTranShell.IsDone()) {
380         Sh = myTranShell.Value();
381         Sh.Closed(Standard_True);
382         //BRepLib::SameParameter(Sh);
383         B.Add(S, Sh);
384       }
385       else {
386         TP->AddWarning
387           (aCShell," A Void from FacetedBrepAndBrepWithVoids not mapped to TopoDS");
388       }
389     }
390     myResult = S;
391     myError  = StepToTopoDS_BuilderDone;
392     done     = Standard_True;
393   }
394   else {
395     TP->AddWarning
396       (aCShell," OuterShell from FacetedBrepAndBrepWithVoids not mapped to TopoDS");
397     done    = Standard_False;
398     myError = StepToTopoDS_BuilderOther;
399   }
400 }
401
402 // ============================================================================
403 // Method  : Init
404 // Purpose : Init with a ShellBasedSurfaceModel
405 // ============================================================================
406
407 void StepToTopoDS_Builder::Init
408 (const Handle(StepShape_ShellBasedSurfaceModel)& aSBSM,
409  const Handle(Transfer_TransientProcess)& TP,
410  StepToTopoDS_NMTool& NMTool,
411  const Message_ProgressRange& theProgress)
412 {
413   Message_Messenger::StreamBuffer sout = TP->Messenger()->SendInfo();
414   // Initialisation of the Tool
415
416   StepToTopoDS_Tool         myTool;
417   StepToTopoDS_DataMapOfTRI aMap;
418
419   myTool.Init(aMap, TP);
420
421   // Start Mapping
422
423   Standard_Integer Nb = aSBSM->NbSbsmBoundary();
424   StepShape_Shell aShell;
425   //Handle(StepShape_VertexShell) aVertexShell;
426   Handle(StepShape_OpenShell)   aOpenShell;
427   Handle(StepShape_ClosedShell) aClosedShell;
428   TopoDS_Compound S;
429   //TopoDS_Shape Sh;
430   TopoDS_Shape Shl;
431   BRep_Builder B;
432   B.MakeCompound(S);
433   StepToTopoDS_TranslateShell myTranShell;
434   
435   myTranShell.SetPrecision(Precision());
436   myTranShell.SetMaxTol(MaxTol());
437
438   Message_ProgressScope PS ( theProgress, "Shell", Nb);
439   for (Standard_Integer i = 1; i <= Nb && PS.More(); i++)
440   {
441     Message_ProgressRange aRange = PS.Next();
442     aShell = aSBSM->SbsmBoundaryValue(i);
443     aOpenShell = aShell.OpenShell();
444     aClosedShell = aShell.ClosedShell();
445     if (!aOpenShell.IsNull()) {
446       myTranShell.Init(aOpenShell, myTool, NMTool, aRange);
447       if (myTranShell.IsDone()) {
448         Shl = TopoDS::Shell(myTranShell.Value());
449         Shl.Closed(Standard_False);
450         B.Add(S, Shl);
451       }
452       else {
453         TP->AddWarning
454           (aOpenShell, " OpenShell from ShellBasedSurfaceModel not mapped to TopoDS");
455       }
456     }
457     else if (!aClosedShell.IsNull()) {
458       myTranShell.Init(aClosedShell, myTool, NMTool, aRange);
459       if (myTranShell.IsDone()) {
460         Shl = TopoDS::Shell(myTranShell.Value());
461         Shl.Closed(Standard_True);
462         B.Add(S, Shl);
463       }
464       else {
465         TP->AddWarning
466           (aClosedShell, " ClosedShell from ShellBasedSurfaceModel not mapped to TopoDS");
467       }
468     }
469   }
470   if(Nb>1)
471     myResult = S;
472   else
473     myResult = Shl;
474   myError  = StepToTopoDS_BuilderDone;
475   done     = Standard_True;
476
477   // Get Statistics :
478   
479   if ( TP->TraceLevel() > 2 )
480   {
481     sout << "Geometric Statitics : " << std::endl;
482     sout << "   Surface Continuity : - C0 : " << myTool.C0Surf() << std::endl;
483     sout << "                        - C1 : " << myTool.C1Surf() << std::endl;
484     sout << "                        - C2 : " << myTool.C2Surf() << std::endl;
485     sout << "   Curve Continuity :   - C0 : " << myTool.C0Cur3() << std::endl;
486     sout << "                        - C1 : " << myTool.C1Cur3() << std::endl;
487     sout << "                        - C2 : " << myTool.C2Cur3() << std::endl;
488     sout << "   PCurve Continuity :  - C0 : " << myTool.C0Cur2() << std::endl;
489     sout << "                        - C1 : " << myTool.C1Cur2() << std::endl;
490     sout << "                        - C2 : " << myTool.C2Cur2() << std::endl;
491   }
492
493 //:S4136  ShapeFix::SameParameter (S,Standard_False);
494   ResetPreci (S, MaxTol());
495   ResetPreci (Shl, MaxTol()); //skl
496 }
497
498 // ============================================================================
499 // Method  : Init
500 // Purpose : Init with a EdgeBasedWireframeModel
501 // ============================================================================
502
503 void StepToTopoDS_Builder::Init (const Handle(StepShape_EdgeBasedWireframeModel)& aEBWM,
504                                  const Handle(Transfer_TransientProcess)& TP)
505 {
506   myResult.Nullify();
507   
508   Handle(StepShape_HArray1OfConnectedEdgeSet) boundary = aEBWM->EbwmBoundary();
509   if ( boundary.IsNull() || boundary->Length() <1 ) {
510     TP->AddWarning ( aEBWM, "List of boundaries is empty" );
511     return;
512   }
513
514   StepToTopoDS_Tool myTool;
515   StepToTopoDS_DataMapOfTRI aMap;
516   myTool.Init(aMap, TP);
517
518   StepToTopoDS_TranslateEdge myTranEdge;
519   myTranEdge.SetPrecision(Precision());
520   myTranEdge.SetMaxTol(MaxTol());
521   
522   TopoDS_Compound C;
523   BRep_Builder B;
524   B.MakeCompound ( C );
525
526   StepToTopoDS_NMTool dummyNMTool;
527   
528   for ( Standard_Integer i=1; i <= boundary->Length(); i++ ) {
529     Handle(StepShape_ConnectedEdgeSet) ces = boundary->Value(i);
530     if ( ces.IsNull() ) continue;
531     Handle(StepShape_HArray1OfEdge) edges = ces->CesEdges();
532     if ( edges.IsNull() || edges->Length() <1 ) {
533       TP->AddWarning ( ces, "No edges in connected_edge_set" );
534       continue;
535     }
536     TopoDS_Wire W;
537     for ( Standard_Integer j=1; j <= edges->Length(); j++ ) {
538       myTranEdge.Init (edges->Value(j), myTool, dummyNMTool);
539       if ( ! myTranEdge.IsDone() ) continue;
540       TopoDS_Edge E = TopoDS::Edge(myTranEdge.Value());
541       if (E.IsNull()) continue;  // NULL, on saute
542       if ( W.IsNull() ) B.MakeWire ( W );
543       B.Add ( W, E );
544     }
545     if ( W.IsNull() ) continue;
546     W.Closed (BRep_Tool::IsClosed (W));
547     B.Add ( C, W );
548     if ( myResult.IsNull() ) myResult = W;
549     else myResult = C;
550   }
551   
552   myError  = ( myResult.IsNull() ? StepToTopoDS_BuilderDone : StepToTopoDS_BuilderOther );
553   done     = ! myResult.IsNull();
554
555   ResetPreci (myResult, MaxTol());
556 }
557
558 // ============================================================================
559 // Method  : Init
560 // Purpose : Init with a FaceBasedSurfaceModel
561 // ============================================================================
562
563 void StepToTopoDS_Builder::Init (const Handle(StepShape_FaceBasedSurfaceModel)& aFBSM,
564                                  const Handle(Transfer_TransientProcess)& TP)
565 {
566   myResult.Nullify();
567   
568   Handle(StepShape_HArray1OfConnectedFaceSet) boundary = aFBSM->FbsmFaces();
569   if ( boundary.IsNull() || boundary->Length() <1 ) {
570     TP->AddWarning ( aFBSM, "List of faces is empty" );
571     return;
572   }
573
574   StepToTopoDS_Tool myTool;
575   StepToTopoDS_DataMapOfTRI aMap;
576   myTool.Init(aMap, TP);
577
578   StepToTopoDS_TranslateFace myTranFace;
579   myTranFace.SetPrecision(Precision());
580   myTranFace.SetMaxTol(MaxTol());
581   
582   TopoDS_Compound C;
583   BRep_Builder B;
584   B.MakeCompound ( C );
585
586   // Non-manifold topology is not mapped via FaceBasedSurfaceModel (ssv; 14.11.2010)
587   StepToTopoDS_NMTool dummyNMTool;
588   
589   for ( Standard_Integer i=1; i <= boundary->Length(); i++ ) {
590     Handle(StepShape_ConnectedFaceSet) cfs = boundary->Value(i);
591     if ( cfs.IsNull() ) continue;
592     Handle(StepShape_HArray1OfFace) faces = cfs->CfsFaces();
593     if ( faces.IsNull() || faces->Length() <1 ) {
594       TP->AddWarning ( cfs, "No faces in connected_face_set" );
595       continue;
596     }
597     TopoDS_Shell S;
598     for ( Standard_Integer j=1; j <= faces->Length(); j++ ) {
599       Handle(StepShape_FaceSurface) fs = Handle(StepShape_FaceSurface)::DownCast ( faces->Value(j) );
600       myTranFace.Init(fs, myTool, dummyNMTool);
601       if ( ! myTranFace.IsDone() ) continue;
602       TopoDS_Face F = TopoDS::Face(myTranFace.Value());
603       if (F.IsNull()) continue;  // NULL, on saute
604       if ( S.IsNull() ) B.MakeShell ( S );
605       B.Add ( S, F );
606     }
607     if ( S.IsNull() ) continue;
608     S.Closed (BRep_Tool::IsClosed (S));
609     B.Add ( C, S );
610     if ( myResult.IsNull() ) myResult = S;
611     else myResult = C;
612   }
613   
614   myError  = ( myResult.IsNull() ? StepToTopoDS_BuilderDone : StepToTopoDS_BuilderOther );
615   done     = ! myResult.IsNull();
616
617   ResetPreci (myResult, MaxTol());
618 }
619
620
621 // ***start DTH Apr/6
622 // ============================================================================
623 // Method  : Init
624 // Purpose : Init with a GeometricCurveSet
625 // ============================================================================
626 //:i6 abv 17 Sep 98: ProSTEP TR9 r0601-ct.stp: to be able read GS: GeometricCurveSet -> GeometricSet
627
628 static TopoDS_Face TranslateBoundedSurf (const Handle(StepGeom_Surface) &surf,
629                                          const Standard_Real TolDegen)
630 {
631   TopoDS_Face res;
632
633   Handle(Geom_Surface) theSurf = StepToGeom::MakeSurface (surf);
634   if (theSurf.IsNull() || //:i6: protection
635       !theSurf->IsKind(STANDARD_TYPE(Geom_BoundedSurface))) return res;
636
637   BRepBuilderAPI_MakeFace myMkFace;
638   Handle(Geom_RectangularTrimmedSurface) RS = 
639                     Handle(Geom_RectangularTrimmedSurface)::DownCast(theSurf);
640
641   if (!RS.IsNull())
642   {
643     Standard_Real umin, umax, vmin, vmax;
644     theSurf->Bounds(umin, umax, vmin, vmax);
645
646     myMkFace.Init(RS->BasisSurface(), umin, umax, vmin, vmax, TolDegen);
647   }
648   else
649   {
650     myMkFace.Init(theSurf, Standard_True, TolDegen);
651   }
652
653   return myMkFace.Face();
654 }
655
656 void StepToTopoDS_Builder::Init
657 (const Handle(StepShape_GeometricSet)& GCS,
658  const Handle(Transfer_TransientProcess)& TP,
659  const Handle(Transfer_ActorOfTransientProcess)& RA,
660  const Standard_Boolean isManifold,
661  const Message_ProgressRange& theProgress)
662 {
663   // Start Mapping
664   TopoDS_Compound S;
665   BRep_Builder B;
666   B.MakeCompound(S);
667   TopoDS_Edge theEdge;
668   Standard_Integer i;
669   Standard_Real preci = Precision();   //gka
670   Standard_Real maxtol = MaxTol();
671   Standard_Integer nbElem = GCS->NbElements();
672   Message_ProgressScope aPS(theProgress, NULL, nbElem);
673   for (i = 1; i <= nbElem && aPS.More(); i++)
674   {
675     Message_ProgressRange aRange = aPS.Next();
676     StepShape_GeometricSetSelect aGSS = GCS->ElementsValue(i);
677     Handle(Standard_Transient) ent = aGSS.Value();
678
679     TopoDS_Shape res = TransferBRep::ShapeResult ( TP, ent );
680     if ( ! res.IsNull() ) { // already translated
681       B.Add ( S, res );
682       continue;
683     }
684     //:o7 abv 18 Feb 99: bm1_sy_fuel.stp #1427(1,2) protection against null entity
685     if ( ent.IsNull() ) {
686       char buff[100];
687       sprintf ( buff, "Entity %d is a Null entity", i );
688       TP->AddWarning (GCS,buff);
689       continue;
690     } 
691     // try curve
692     else if ( ent->IsKind(STANDARD_TYPE(StepGeom_Curve)) ) {
693       Handle(StepGeom_Curve) aCrv = Handle(StepGeom_Curve)::DownCast ( ent );
694
695       // try composite_curve
696       Handle(StepGeom_CompositeCurve) CC = Handle(StepGeom_CompositeCurve)::DownCast(aCrv);
697       if (!CC.IsNull()) {
698         StepToTopoDS_TranslateCompositeCurve TrCC;
699         TrCC.SetPrecision(preci);
700         TrCC.SetMaxTol(maxtol);
701         TrCC.Init(CC, TP);
702         if (TrCC.IsDone())
703         {
704           if (TrCC.IsInfiniteSegment())
705           {
706             BRep_Builder aB;
707             TopoDS_Compound aComp;
708             aB.MakeCompound(aComp);
709             TopExp_Explorer anExp;
710             for (anExp.Init(TrCC.Value(), TopAbs_EDGE); anExp.More(); anExp.Next())
711               aB.Add(aComp, anExp.Current());
712             res = aComp;
713           }
714           else
715             res = TrCC.Value();
716         }
717       }
718       else { // try other curves
719         Handle(Geom_Curve) aGeomCrv;
720         try {
721           OCC_CATCH_SIGNALS
722             aGeomCrv = StepToGeom::MakeCurve(aCrv);
723         }
724         catch (Standard_Failure const& anException) {
725           Message_Messenger::StreamBuffer sout = TP->Messenger()->SendInfo();
726           sout << "StepToTopoDS, GeometricSet, elem " << i << " of " << nbElem << ": exception ";
727           sout << anException.GetMessageString() << std::endl;
728         }
729         if (!aGeomCrv.IsNull()) {
730           BRepBuilderAPI_MakeEdge anEdge(aGeomCrv, aGeomCrv->FirstParameter(), aGeomCrv->LastParameter());
731           if (anEdge.IsDone()) res = anEdge.Edge();
732         }
733       }
734     }
735     // try point
736     else if ( ent->IsKind(STANDARD_TYPE(StepGeom_CartesianPoint)) ) {
737       Handle(StepGeom_CartesianPoint) aPnt = Handle(StepGeom_CartesianPoint)::DownCast ( ent );
738       Handle(Geom_CartesianPoint) thePnt = StepToGeom::MakeCartesianPoint (aPnt);
739       if (! thePnt.IsNull()) {
740         BRepBuilderAPI_MakeVertex myMkVtx(thePnt->Pnt());
741         if ( myMkVtx.IsDone() ) res = myMkVtx.Vertex();
742       }
743     }
744     // Element should finally be a Surface
745     else if (ent->IsKind(STANDARD_TYPE(StepGeom_Surface))) {
746       Handle(StepGeom_Surface) aSurf =
747         Handle(StepGeom_Surface)::DownCast(ent);
748
749       // try curve_bounded_surf
750       if (ent->IsKind(STANDARD_TYPE(StepGeom_CurveBoundedSurface))) {
751         Handle(StepGeom_CurveBoundedSurface) CBS =
752           Handle(StepGeom_CurveBoundedSurface)::DownCast(aSurf);
753         StepToTopoDS_TranslateCurveBoundedSurface TrCBS;
754         TrCBS.SetPrecision(preci);
755         TrCBS.SetMaxTol(maxtol);
756
757         TrCBS.Init(CBS, TP);
758         if (TrCBS.IsDone()) res = TrCBS.Value();
759       }
760       // try RectangularCompositeSurface
761       else if (ent->IsKind(STANDARD_TYPE(StepGeom_RectangularCompositeSurface))) {
762         Handle(StepGeom_RectangularCompositeSurface) RCS =
763           Handle(StepGeom_RectangularCompositeSurface)::DownCast(aSurf);
764         Standard_Integer nbi = RCS->NbSegmentsI();
765         Standard_Integer nbj = RCS->NbSegmentsJ();
766         TopoDS_Compound C;
767         B.MakeCompound(C);
768         for (Standard_Integer ii = 1; ii <= nbi; ii++)
769           for (Standard_Integer j = 1; j <= nbj; j++) {
770             Handle(StepGeom_SurfacePatch) patch = RCS->SegmentsValue(ii, j);
771             TopoDS_Face f = TranslateBoundedSurf(patch->ParentSurface(), preci);
772             if (!f.IsNull()) B.Add(C, f);
773           }
774         res = C;
775       }
776       // try other surfs
777       else res = TranslateBoundedSurf(aSurf, preci);
778     }
779     else if ( ent->IsKind(STANDARD_TYPE(StepGeom_GeometricRepresentationItem)) )
780     {
781       Handle(StepGeom_GeometricRepresentationItem) GRI = 
782         Handle(StepGeom_GeometricRepresentationItem)::DownCast(ent);
783       if (!RA.IsNull())
784       {
785         Handle(STEPControl_ActorRead) anActor = Handle(STEPControl_ActorRead)::DownCast(RA);
786         Handle(Transfer_Binder) binder;
787         if( !anActor.IsNull())
788           binder = anActor->TransferShape(GRI, TP, isManifold, Standard_False, aRange);
789         if (!binder.IsNull())
790         {
791           res = TransferBRep::ShapeResult(binder);
792         }
793       }
794     }
795     else TP->AddWarning (ent," Entity is not a Curve, Point, Surface or GeometricRepresentationItem");
796     if ( ! res.IsNull() ) {
797       B.Add(S, res);
798       TransferBRep::SetShapeResult ( TP, ent, res );
799     }
800     else TP->AddWarning (ent," Entity not mapped to TopoDS");
801   }
802   myResult = S;
803   myError  = StepToTopoDS_BuilderDone;
804   done     = Standard_True;
805 }
806 // ***end DTH Apr/6 
807
808
809 // ============================================================================
810 // Method  : Value
811 // Purpose : Returns the result of the mapping
812 // ============================================================================
813
814 const TopoDS_Shape& StepToTopoDS_Builder::Value() const 
815 {
816   StdFail_NotDone_Raise_if (!done, "StepToTopoDS_Builder::Value() - no result");
817   return myResult;
818 }
819
820 // ============================================================================
821 // Method  : Error
822 // Purpose : Returns the Builder Error code
823 // ============================================================================
824
825 StepToTopoDS_BuilderError StepToTopoDS_Builder::Error() const 
826 {
827   return myError;
828 }
829