b311480e |
1 | // Created on: 1993-01-19 |
2 | // Created by: Remi LEQUETTE |
3 | // Copyright (c) 1993-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. |
7fd59977 |
16 | |
17 | #define No_Standard_NoMoreObject |
18 | #define No_Standard_NoSuchObject |
19 | #define No_Standard_TypeMismatch |
20 | |
42cf5bc1 |
21 | |
22 | #include <TopExp.hxx> |
7fd59977 |
23 | #include <TopExp_Explorer.hxx> |
42cf5bc1 |
24 | #include <TopoDS.hxx> |
25 | #include <TopoDS_Edge.hxx> |
7fd59977 |
26 | #include <TopoDS_Iterator.hxx> |
42cf5bc1 |
27 | #include <TopoDS_Shape.hxx> |
28 | #include <TopoDS_Vertex.hxx> |
29 | #include <TopoDS_Wire.hxx> |
7fd59977 |
30 | #include <TopTools_ListOfShape.hxx> |
7fd59977 |
31 | #include <TopTools_MapIteratorOfMapOfShape.hxx> |
42cf5bc1 |
32 | #include <TopTools_MapOfShape.hxx> |
7fd59977 |
33 | |
34 | //======================================================================= |
35 | //function : MapShapes |
36 | //purpose : |
37 | //======================================================================= |
7fd59977 |
38 | void TopExp::MapShapes(const TopoDS_Shape& S, |
39 | const TopAbs_ShapeEnum T, |
40 | TopTools_IndexedMapOfShape& M) |
41 | { |
42 | TopExp_Explorer Ex(S,T); |
43 | while (Ex.More()) { |
44 | M.Add(Ex.Current()); |
45 | Ex.Next(); |
46 | } |
47 | } |
48 | |
49 | //======================================================================= |
50 | //function : MapShapes |
51 | //purpose : |
52 | //======================================================================= |
53 | |
54 | void TopExp::MapShapes(const TopoDS_Shape& S, |
55 | TopTools_IndexedMapOfShape& M) |
56 | { |
57 | M.Add(S); |
58 | TopoDS_Iterator It(S); |
59 | while (It.More()) { |
60 | MapShapes(It.Value(),M); |
61 | It.Next(); |
62 | } |
63 | } |
64 | |
1155d05a |
65 | //======================================================================= |
66 | //function : MapShapes |
67 | //purpose : |
68 | //======================================================================= |
69 | void TopExp::MapShapes(const TopoDS_Shape& S, |
70 | TopTools_MapOfShape& M) |
71 | { |
72 | M.Add(S); |
73 | for (TopoDS_Iterator it(S); it.More(); it.Next()) |
74 | MapShapes(it.Value(), M); |
75 | } |
76 | |
7fd59977 |
77 | //======================================================================= |
78 | //function : MapShapesAndAncestors |
79 | //purpose : |
80 | //======================================================================= |
81 | |
82 | void TopExp::MapShapesAndAncestors |
83 | (const TopoDS_Shape& S, |
84 | const TopAbs_ShapeEnum TS, |
85 | const TopAbs_ShapeEnum TA, |
86 | TopTools_IndexedDataMapOfShapeListOfShape& M) |
87 | { |
88 | TopTools_ListOfShape empty; |
89 | |
90 | // visit ancestors |
91 | TopExp_Explorer exa(S,TA); |
92 | while (exa.More()) { |
93 | // visit shapes |
94 | const TopoDS_Shape& anc = exa.Current(); |
95 | TopExp_Explorer exs(anc,TS); |
96 | while (exs.More()) { |
97 | Standard_Integer index = M.FindIndex(exs.Current()); |
98 | if (index == 0) index = M.Add(exs.Current(),empty); |
99 | M(index).Append(anc); |
100 | exs.Next(); |
101 | } |
102 | exa.Next(); |
103 | } |
104 | |
105 | // visit shapes not under ancestors |
106 | TopExp_Explorer ex(S,TS,TA); |
107 | while (ex.More()) { |
108 | Standard_Integer index = M.FindIndex(ex.Current()); |
109 | if (index == 0) index = M.Add(ex.Current(),empty); |
110 | ex.Next(); |
111 | } |
112 | } |
113 | |
f1191d30 |
114 | //======================================================================= |
115 | //function : MapShapesAndUniqueAncestors |
116 | //purpose : |
117 | //======================================================================= |
118 | |
119 | void TopExp::MapShapesAndUniqueAncestors |
120 | (const TopoDS_Shape& S, |
121 | const TopAbs_ShapeEnum TS, |
122 | const TopAbs_ShapeEnum TA, |
123 | TopTools_IndexedDataMapOfShapeListOfShape& M, |
124 | const Standard_Boolean useOrientation) |
125 | { |
126 | TopTools_ListOfShape empty; |
127 | |
128 | // visit ancestors |
129 | TopExp_Explorer exa(S,TA); |
130 | while (exa.More()) |
131 | { |
132 | // visit shapes |
133 | const TopoDS_Shape& anc = exa.Current(); |
134 | TopExp_Explorer exs(anc,TS); |
135 | while (exs.More()) |
136 | { |
137 | Standard_Integer index = M.FindIndex(exs.Current()); |
138 | if (index == 0) |
139 | index = M.Add(exs.Current(),empty); |
140 | TopTools_ListOfShape& aList = M(index); |
141 | // check if anc already exists in a list |
142 | TopTools_ListIteratorOfListOfShape it(aList); |
143 | for (; it.More(); it.Next()) |
144 | if (useOrientation? anc.IsEqual(it.Value()) : anc.IsSame(it.Value())) |
145 | break; |
146 | if (!it.More()) |
147 | aList.Append(anc); |
148 | exs.Next(); |
149 | } |
150 | exa.Next(); |
151 | } |
7fd59977 |
152 | |
f1191d30 |
153 | // visit shapes not under ancestors |
154 | TopExp_Explorer ex(S,TS,TA); |
155 | while (ex.More()) |
156 | { |
157 | Standard_Integer index = M.FindIndex(ex.Current()); |
158 | if (index == 0) |
159 | M.Add(ex.Current(),empty); |
160 | ex.Next(); |
161 | } |
162 | } |
7fd59977 |
163 | |
164 | //======================================================================= |
165 | //function : FirstVertex |
166 | //purpose : |
167 | //======================================================================= |
168 | |
169 | TopoDS_Vertex TopExp::FirstVertex(const TopoDS_Edge& E, |
170 | const Standard_Boolean CumOri) |
171 | { |
172 | TopoDS_Iterator ite(E,CumOri); |
173 | while (ite.More()) { |
174 | if (ite.Value().Orientation() == TopAbs_FORWARD) |
175 | return TopoDS::Vertex(ite.Value()); |
176 | ite.Next(); |
177 | } |
178 | return TopoDS_Vertex(); |
179 | } |
180 | |
181 | |
182 | //======================================================================= |
183 | //function : LastVertex |
184 | //purpose : |
185 | //======================================================================= |
186 | |
187 | TopoDS_Vertex TopExp::LastVertex(const TopoDS_Edge& E, |
188 | const Standard_Boolean CumOri) |
189 | { |
190 | TopoDS_Iterator ite(E,CumOri); |
191 | while (ite.More()) { |
192 | if (ite.Value().Orientation() == TopAbs_REVERSED) |
193 | return TopoDS::Vertex(ite.Value()); |
194 | ite.Next(); |
195 | } |
196 | return TopoDS_Vertex(); |
197 | } |
198 | |
199 | |
200 | //======================================================================= |
201 | //function : Vertices |
202 | //purpose : |
203 | //======================================================================= |
204 | |
205 | void TopExp::Vertices(const TopoDS_Edge& E, |
206 | TopoDS_Vertex& Vfirst, |
207 | TopoDS_Vertex& Vlast, |
208 | const Standard_Boolean CumOri) |
209 | { |
8447359f |
210 | // minor optimization for case when Vfirst and Vlast are non-null: |
211 | // at least for VC++ 10, it is faster if we use boolean flags than |
212 | // if we nullify vertices at that point (see #27021) |
213 | Standard_Boolean isFirstDefined = Standard_False; |
214 | Standard_Boolean isLastDefined = Standard_False; |
215 | |
216 | TopoDS_Iterator ite(E, CumOri); |
7fd59977 |
217 | while (ite.More()) { |
8447359f |
218 | const TopoDS_Shape& aV = ite.Value(); |
219 | if (aV.Orientation() == TopAbs_FORWARD) |
220 | { |
221 | Vfirst = TopoDS::Vertex (aV); |
222 | isFirstDefined = Standard_True; |
223 | } |
224 | else if (aV.Orientation() == TopAbs_REVERSED) |
225 | { |
226 | Vlast = TopoDS::Vertex (aV); |
227 | isLastDefined = Standard_True; |
228 | } |
7fd59977 |
229 | ite.Next(); |
230 | } |
8447359f |
231 | |
232 | if (!isFirstDefined) |
233 | Vfirst.Nullify(); |
234 | |
235 | if (!isLastDefined) |
236 | Vlast.Nullify(); |
7fd59977 |
237 | } |
238 | |
239 | |
240 | //======================================================================= |
241 | //function : Vertices |
242 | //purpose : |
243 | //======================================================================= |
244 | |
245 | void TopExp::Vertices(const TopoDS_Wire& W, |
246 | TopoDS_Vertex& Vfirst, |
247 | TopoDS_Vertex& Vlast) |
248 | { |
249 | Vfirst = Vlast = TopoDS_Vertex(); // nullify |
250 | |
251 | TopTools_MapOfShape vmap; |
252 | TopoDS_Iterator it(W); |
253 | TopoDS_Vertex V1,V2; |
254 | |
255 | while (it.More()) { |
256 | const TopoDS_Edge& E = TopoDS::Edge(it.Value()); |
257 | if (E.Orientation() == TopAbs_REVERSED) |
258 | TopExp::Vertices(E,V2,V1); |
259 | else |
260 | TopExp::Vertices(E,V1,V2); |
261 | // add or remove in the vertex map |
262 | V1.Orientation(TopAbs_FORWARD); |
263 | V2.Orientation(TopAbs_REVERSED); |
264 | if (!vmap.Add(V1)) vmap.Remove(V1); |
265 | if (!vmap.Add(V2)) vmap.Remove(V2); |
266 | |
267 | it.Next(); |
268 | } |
269 | if (vmap.IsEmpty()) { // closed |
270 | TopoDS_Shape aLocalShape = V2.Oriented(TopAbs_FORWARD); |
271 | Vfirst = TopoDS::Vertex(aLocalShape); |
272 | aLocalShape = V2.Oriented(TopAbs_REVERSED); |
273 | Vlast = TopoDS::Vertex(aLocalShape); |
274 | // Vfirst = TopoDS::Vertex(V2.Oriented(TopAbs_FORWARD)); |
275 | // Vlast = TopoDS::Vertex(V2.Oriented(TopAbs_REVERSED)); |
276 | } |
277 | else if (vmap.Extent() == 2) { //open |
278 | TopTools_MapIteratorOfMapOfShape ite(vmap); |
279 | |
280 | while (ite.More() && ite.Key().Orientation() != TopAbs_FORWARD) |
281 | ite.Next(); |
282 | if (ite.More()) Vfirst = TopoDS::Vertex(ite.Key()); |
283 | ite.Initialize(vmap); |
284 | while (ite.More() && ite.Key().Orientation() != TopAbs_REVERSED) |
285 | ite.Next(); |
286 | if (ite.More()) Vlast = TopoDS::Vertex(ite.Key()); |
287 | } |
288 | } |
289 | |
290 | |
291 | //======================================================================= |
292 | //function : CommonVertex |
293 | //purpose : |
294 | //======================================================================= |
295 | Standard_Boolean TopExp::CommonVertex(const TopoDS_Edge& E1, |
296 | const TopoDS_Edge& E2, |
297 | TopoDS_Vertex& V) |
298 | { |
299 | TopoDS_Vertex firstVertex1, lastVertex1, firstVertex2, lastVertex2; |
300 | TopExp::Vertices(E1, firstVertex1, lastVertex1); |
301 | TopExp::Vertices(E2, firstVertex2, lastVertex2); |
302 | |
303 | if (firstVertex1.IsSame(firstVertex2) || |
304 | firstVertex1.IsSame(lastVertex2)) { |
305 | V = firstVertex1; |
306 | return Standard_True; |
307 | } |
308 | if (lastVertex1.IsSame(firstVertex2) || |
309 | lastVertex1.IsSame(lastVertex2)) { |
310 | V = lastVertex1; |
311 | return Standard_True; |
312 | } |
313 | return Standard_False; |
314 | } // CommonVertex |
315 | |