1 // Copyright (c) 1999-2014 OPEN CASCADE SAS
3 // This file is part of Open CASCADE Technology software library.
5 // This library is free software; you can redistribute it and/or modify it under
6 // the terms of the GNU Lesser General Public License version 2.1 as published
7 // by the Free Software Foundation, with special exception defined in the file
8 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
9 // distribution for complete text of the license and disclaimer of any warranty.
11 // Alternatively, this file may be used under the terms of Open CASCADE
12 // commercial license or contractual agreement.
16 #include <BRep_Builder.hxx>
17 #include <ShapeExtend_Explorer.hxx>
18 #include <TopExp_Explorer.hxx>
19 #include <TopoDS_Compound.hxx>
20 #include <TopoDS_Iterator.hxx>
21 #include <TopoDS_Shape.hxx>
22 #include <TopoDS_Shell.hxx>
23 #include <TopoDS_Wire.hxx>
24 #include <TopTools_ListIteratorOfListOfShape.hxx>
26 //=======================================================================
27 //function : ShapeExtend_Explorer
29 //=======================================================================
30 ShapeExtend_Explorer::ShapeExtend_Explorer()
34 //=======================================================================
35 //function : CompoundFromSeq
37 //=======================================================================
39 TopoDS_Shape ShapeExtend_Explorer::CompoundFromSeq
40 (const Handle(TopTools_HSequenceOfShape)& seqval) const
45 Standard_Integer i,n = seqval->Length();
46 for (i = 1; i <= n ; i ++) B.Add(C,seqval->Value(i));
50 //=======================================================================
51 //function : SeqFromCompound
53 //=======================================================================
55 static void FillList (const Handle(TopTools_HSequenceOfShape)& list,
56 const TopoDS_Shape& comp, const Standard_Boolean expcomp)
58 for (TopoDS_Iterator it (comp); it.More(); it.Next()) {
59 TopoDS_Shape sub = it.Value();
60 if (sub.ShapeType() != TopAbs_COMPOUND) list->Append (sub);
61 else if (!expcomp) list->Append (sub);
62 else FillList (list,sub,expcomp);
66 Handle(TopTools_HSequenceOfShape) ShapeExtend_Explorer::SeqFromCompound
67 (const TopoDS_Shape& comp, const Standard_Boolean expcomp) const
69 Handle(TopTools_HSequenceOfShape) list = new TopTools_HSequenceOfShape();
70 if (comp.IsNull()) return list;
71 if (comp.ShapeType() != TopAbs_COMPOUND) {
75 FillList (list,comp,expcomp);
79 //=======================================================================
80 //function : ListFromSeq
82 //=======================================================================
84 void ShapeExtend_Explorer::ListFromSeq (const Handle(TopTools_HSequenceOfShape)& seqval,
85 TopTools_ListOfShape& lisval,
86 const Standard_Boolean clear) const
88 if (clear) lisval.Clear();
89 if (seqval.IsNull()) return;
90 Standard_Integer i, nb = seqval->Length();
91 for (i = 1; i <= nb; i ++) lisval.Append (seqval->Value(i));
94 //=======================================================================
95 //function : SeqFromList
97 //=======================================================================
99 Handle(TopTools_HSequenceOfShape) ShapeExtend_Explorer::SeqFromList
100 (const TopTools_ListOfShape& lisval) const
102 Handle(TopTools_HSequenceOfShape) seqval = new TopTools_HSequenceOfShape();
103 TopTools_ListIteratorOfListOfShape it;
104 for (it.Initialize(lisval); it.More(); it.Next()) seqval->Append (it.Value());
108 //=======================================================================
109 //function : ShapeType
111 //=======================================================================
113 TopAbs_ShapeEnum ShapeExtend_Explorer::ShapeType (const TopoDS_Shape& shape,
114 const Standard_Boolean compound) const
116 if (shape.IsNull()) return TopAbs_SHAPE;
117 TopAbs_ShapeEnum res = shape.ShapeType();
118 if (!compound || res != TopAbs_COMPOUND) return res;
120 for (TopoDS_Iterator iter(shape); iter.More(); iter.Next()) {
121 TopoDS_Shape sh = iter.Value();
122 if (sh.IsNull()) continue;
123 TopAbs_ShapeEnum typ = sh.ShapeType();
124 if (typ == TopAbs_COMPOUND) typ = ShapeType (sh,compound);
125 if (res == TopAbs_SHAPE) res = typ;
126 // Egalite : OK; Pseudo-Egalite : EDGE/WIRE ou FACE/SHELL
127 else if (res == TopAbs_EDGE && typ == TopAbs_WIRE) res = typ;
128 else if (res == TopAbs_WIRE && typ == TopAbs_EDGE) continue;
129 else if (res == TopAbs_FACE && typ == TopAbs_SHELL) res = typ;
130 else if (res == TopAbs_SHELL && typ == TopAbs_FACE) continue;
131 else if (res != typ) return TopAbs_COMPOUND;
136 //=======================================================================
137 //function : SortedCompound
139 //=======================================================================
141 TopoDS_Shape ShapeExtend_Explorer::SortedCompound (const TopoDS_Shape& shape,
142 const TopAbs_ShapeEnum type,
143 const Standard_Boolean explore,
144 const Standard_Boolean compound) const
146 if (shape.IsNull()) return shape;
147 TopAbs_ShapeEnum typ = shape.ShapeType();
148 TopoDS_Shape sh, sh0;
149 Standard_Integer nb = 0;
151 // Compound : on le prend, soit tel quel, soit son contenu
152 if (typ == TopAbs_COMPOUND || typ == TopAbs_COMPSOLID) {
156 for (TopoDS_Iterator it(shape); it.More(); it.Next()) {
157 sh0 = SortedCompound (it.Value(),type,explore,compound);
158 if (sh0.IsNull()) continue;
160 typ = sh.ShapeType();
161 if (typ == TopAbs_COMPOUND && !compound) {
162 for (TopoDS_Iterator it2 (sh); it2.More(); it2.Next())
163 { nb ++; sh = it2.Value(); B.Add (C, sh); }
165 else { nb ++; B.Add (C,sh); }
167 if (nb == 0) C.Nullify();
168 else if (nb == 1) return sh;
172 // Egalite : OK; Pseudo-Egalite : EDGE/WIRE ou FACE/SHELL
173 if (typ == type) return shape;
174 if (typ == TopAbs_EDGE && type == TopAbs_WIRE) {
181 if (typ == TopAbs_FACE && type == TopAbs_SHELL) {
189 // Le reste : selon exploration
195 // Ici, on doit explorer
196 // SOLID + mode COMPOUND : reconduire les SHELLs
197 if (typ == TopAbs_SOLID && compound) {
201 for (TopoDS_Iterator it(shape); it.More(); it.Next()) {
202 sh0 = SortedCompound (it.Value(),type,explore,compound);
203 if (sh0.IsNull()) continue;
207 if (nb == 0) C.Nullify();
208 else if (nb == 1) return sh;
212 // Exploration classique
216 //Standard_Integer iena = Standard_False; //szv#4:S4163:12Mar99 unused
217 for (TopExp_Explorer aExp (shape,type); aExp.More(); aExp.Next()) {
218 nb ++; sh = aExp.Current();
221 if (nb == 0) CC.Nullify();
222 else if (nb == 1) return sh;
226 //=======================================================================
227 //function : DispatchList
229 //=======================================================================
231 void ShapeExtend_Explorer::DispatchList (const Handle(TopTools_HSequenceOfShape)& list,
232 Handle(TopTools_HSequenceOfShape)& vertices,
233 Handle(TopTools_HSequenceOfShape)& edges,
234 Handle(TopTools_HSequenceOfShape)& wires,
235 Handle(TopTools_HSequenceOfShape)& faces,
236 Handle(TopTools_HSequenceOfShape)& shells,
237 Handle(TopTools_HSequenceOfShape)& solids,
238 Handle(TopTools_HSequenceOfShape)& compsols,
239 Handle(TopTools_HSequenceOfShape)& compounds) const
241 if (list.IsNull()) return;
242 if (vertices.IsNull()) vertices = new TopTools_HSequenceOfShape();
243 if (edges.IsNull()) edges = new TopTools_HSequenceOfShape();
244 if (wires.IsNull()) wires = new TopTools_HSequenceOfShape();
245 if (faces.IsNull()) faces = new TopTools_HSequenceOfShape();
246 if (shells.IsNull()) shells = new TopTools_HSequenceOfShape();
247 if (solids.IsNull()) solids = new TopTools_HSequenceOfShape();
248 if (compsols.IsNull()) compsols = new TopTools_HSequenceOfShape();
249 if (compounds.IsNull()) compounds = new TopTools_HSequenceOfShape();
251 Standard_Integer i,nb = list->Length();
252 for (i = 1; i <= nb; i ++) {
253 TopoDS_Shape sh = list->Value(i);
254 if (sh.IsNull()) continue;
255 switch (sh.ShapeType()) {
256 case TopAbs_VERTEX : vertices->Append(sh); break;
257 case TopAbs_EDGE : edges->Append(sh); break;
258 case TopAbs_WIRE : wires->Append(sh); break;
259 case TopAbs_FACE : faces->Append(sh); break;
260 case TopAbs_SHELL : shells->Append(sh); break;
261 case TopAbs_SOLID : solids->Append(sh); break;
262 case TopAbs_COMPSOLID : compsols->Append(sh); break;
263 case TopAbs_COMPOUND : compounds->Append(sh); break;