1 // Created on: 1999-10-05
2 // Created by: Vladislav ROMASHKO
3 // Copyright (c) 1999-1999 Matra Datavision
4 // Copyright (c) 1999-2012 OPEN CASCADE SAS
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.
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.
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.
23 #include <QANewBRepNaming_ImportShape.ixx>
25 #include <Standard_NullObject.hxx>
26 #include <BRepTools.hxx>
29 #include <TopoDS_Shape.hxx>
30 #include <TopoDS_Face.hxx>
31 #include <TopoDS_Wire.hxx>
32 #include <TopoDS_Edge.hxx>
33 #include <TopoDS_Iterator.hxx>
35 #include <TopExp_Explorer.hxx>
37 #include <TopTools_ListOfShape.hxx>
38 #include <TopTools_ListIteratorOfListOfShape.hxx>
39 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
40 #include <TopTools_IndexedMapOfShape.hxx>
41 #include <TopTools_DataMapOfShapeShape.hxx>
42 #include <TopTools_DataMapOfShapeListOfShape.hxx>
43 #include <TopTools_DataMapIteratorOfDataMapOfShapeListOfShape.hxx>
44 #include <ShapeExtend_WireData.hxx>
46 #include <TDF_Label.hxx>
47 #include <TDF_LabelMap.hxx>
48 #include <TDF_TagSource.hxx>
49 #include <TDF_ChildIterator.hxx>
50 #include <TNaming_Builder.hxx>
51 #include <TNaming_NamedShape.hxx>
52 #include <QANewBRepNaming_LoaderParent.hxx>
53 //=======================================================================
54 //function : QANewBRepNaming_ImportShape
55 //purpose : Constructor
56 //=======================================================================
58 QANewBRepNaming_ImportShape::QANewBRepNaming_ImportShape() {}
60 //=======================================================================
61 //function : QANewBRepNaming_ImportShape
62 //purpose : Constructor
63 //=======================================================================
65 QANewBRepNaming_ImportShape::QANewBRepNaming_ImportShape(const TDF_Label& L):QANewBRepNaming_TopNaming(L) {}
67 //=======================================================================
69 //purpose : Initialization
70 //=======================================================================
72 void QANewBRepNaming_ImportShape::Init(const TDF_Label& Label) {
74 Standard_NullObject::Raise("QANewBRepNaming_ImportShape::Init The Result label is Null ...");
75 myResultLabel = Label;
78 //=======================================================================
80 //purpose : To load an ImportShape
81 // Use this method for a topological naming of an imported shape
82 //=======================================================================
84 void QANewBRepNaming_ImportShape::Load(const TopoDS_Shape& theShape) const {
85 ResultLabel().ForgetAllAttributes();
86 TNaming_Builder b(ResultLabel());
87 b.Generated(theShape);
89 Handle(TDF_TagSource) Tagger = TDF_TagSource::Set(ResultLabel());
90 if (Tagger.IsNull()) return;
93 LoadFirstLevel(theShape, Tagger);
94 LoadC0Edges(theShape, Tagger);
95 LoadC0Vertices(theShape, Tagger);
98 //=======================================================================
99 //function : LoadPrime
101 //=======================================================================
103 void QANewBRepNaming_ImportShape::LoadPrime(const TopoDS_Shape& theShape) const {
105 Handle(TDF_TagSource) Tagger = TDF_TagSource::Set(ResultLabel());
106 if (Tagger.IsNull()) return;
109 LoadFirstLevel(theShape, Tagger);
110 LoadC0Edges(theShape, Tagger);
111 LoadC0Vertices(theShape, Tagger);
114 //=======================================================================
115 //function : LoadFirstLevel
116 //purpose : Method for internal use. Is used by Load()
117 //=======================================================================
119 void QANewBRepNaming_ImportShape::LoadFirstLevel(const TopoDS_Shape& S,
120 const Handle(TDF_TagSource)& Tagger) const {
121 if (S.ShapeType() == TopAbs_COMPOUND || S.ShapeType() == TopAbs_COMPSOLID) {
122 TopoDS_Iterator itr(S);
123 for (; itr.More(); itr.Next()) {
124 TNaming_Builder bIndependantShapes(Tagger->NewChild());
125 bIndependantShapes.Generated(itr.Value());
126 if (itr.Value().ShapeType() == TopAbs_COMPOUND || itr.Value().ShapeType() == TopAbs_COMPSOLID) {
127 LoadFirstLevel(itr.Value(), Tagger);
128 } else LoadNextLevels(itr.Value(), Tagger);
130 } else LoadNextLevels(S, Tagger);
133 //=======================================================================
134 //function : LoadNextLevels
135 //purpose : Method for internal use. Is used by LoadFirstLevel()
136 //=======================================================================
138 void QANewBRepNaming_ImportShape::LoadNextLevels(const TopoDS_Shape& S,
139 const Handle(TDF_TagSource)& Tagger) const {
141 if (S.ShapeType() == TopAbs_SOLID) {
142 TopExp_Explorer expl(S, TopAbs_FACE);
143 for (; expl.More(); expl.Next()) {
144 TNaming_Builder bFace(Tagger->NewChild());
145 bFace.Generated(expl.Current());
147 } else if (S.ShapeType() == TopAbs_SHELL || S.ShapeType() == TopAbs_FACE) {
148 // load faces and all the free edges
149 TopTools_IndexedMapOfShape Faces;
150 TopExp::MapShapes(S, TopAbs_FACE, Faces);
151 if (Faces.Extent() > 1 || (S.ShapeType() == TopAbs_SHELL && Faces.Extent() == 1)) {
152 TopExp_Explorer expl(S, TopAbs_FACE);
153 for (; expl.More(); expl.Next()) {
154 TNaming_Builder bFace(Tagger->NewChild());
155 bFace.Generated(expl.Current());
158 TopTools_IndexedDataMapOfShapeListOfShape anEdgeAndNeighbourFaces;
159 TopExp::MapShapesAndAncestors(S, TopAbs_EDGE, TopAbs_FACE, anEdgeAndNeighbourFaces);
160 for (Standard_Integer i = 1; i <= anEdgeAndNeighbourFaces.Extent(); i++) {
161 const TopTools_ListOfShape& aLL = anEdgeAndNeighbourFaces.FindFromIndex(i);
162 if (aLL.Extent() < 2) {
163 TNaming_Builder bFreeEdges(Tagger->NewChild());
164 bFreeEdges.Generated(anEdgeAndNeighbourFaces.FindKey(i));
166 TopTools_ListIteratorOfListOfShape anIter(aLL);
167 const TopoDS_Face aFace = TopoDS::Face(anIter.Value());
169 if(aFace.IsEqual(anIter.Value())) {
170 TNaming_Builder bFreeEdges(Tagger->NewChild());
171 bFreeEdges.Generated(anEdgeAndNeighbourFaces.FindKey(i));
175 } else if (S.ShapeType() == TopAbs_WIRE) {
176 TopTools_IndexedMapOfShape Edges;
177 BRepTools::Map3DEdges(S, Edges);
178 if (Edges.Extent() == 1) {
179 TNaming_Builder bEdge(Tagger->NewChild());
180 bEdge.Generated(Edges.FindKey(1));
181 TopExp_Explorer expl(S, TopAbs_VERTEX);
182 for (; expl.More(); expl.Next()) {
183 TNaming_Builder bVertex(Tagger->NewChild());
184 bVertex.Generated(expl.Current());
187 TopExp_Explorer expl(S, TopAbs_EDGE);
188 for (; expl.More(); expl.Next()) {
189 TNaming_Builder bEdge(Tagger->NewChild());
190 bEdge.Generated(expl.Current());
192 // and load generated vertices.
193 TopTools_DataMapOfShapeShape generated;
194 if (QANewBRepNaming_LoaderParent::GetDangleShapes(S, TopAbs_EDGE, generated)) {
195 TNaming_Builder bGenVertices(Tagger->NewChild());
196 QANewBRepNaming_LoaderParent::LoadGeneratedDangleShapes(S, TopAbs_EDGE, bGenVertices);
199 } else if (S.ShapeType() == TopAbs_EDGE) {
200 TopExp_Explorer expl(S, TopAbs_VERTEX);
201 for (; expl.More(); expl.Next()) {
202 TNaming_Builder bVertex(Tagger->NewChild());
203 bVertex.Generated(expl.Current());
209 //=======================================================================
210 //function : LoadC0Edges
211 //purpose : Method for internal use. It is used by Load() method.
212 //=======================================================================
214 void QANewBRepNaming_ImportShape::LoadC0Edges(const TopoDS_Shape& S,
215 const Handle(TDF_TagSource)& Tagger) const
217 // vro: It sets vertices twicely:
218 // TopTools_IndexedDataMapOfShapeListOfShape vertexNaborFaces;
219 // TopExp::MapShapesAndAncestors(S, TopAbs_VERTEX, TopAbs_FACE, vertexNaborFaces);
220 TopTools_DataMapOfShapeListOfShape edgeNaborFaces;
221 TopTools_ListOfShape empty;
222 TopExp_Explorer explF(S, TopAbs_FACE);
223 for (; explF.More(); explF.Next()) {
224 const TopoDS_Shape& aFace = explF.Current();
225 TopExp_Explorer explV(aFace, TopAbs_EDGE);
226 for (; explV.More(); explV.Next()) {
227 const TopoDS_Shape& anEdge = explV.Current();
228 if (!edgeNaborFaces.IsBound(anEdge)) edgeNaborFaces.Bind(anEdge, empty);
229 Standard_Boolean faceIsNew = Standard_True;
230 TopTools_ListIteratorOfListOfShape itrF(edgeNaborFaces.Find(anEdge));
231 for (; itrF.More(); itrF.Next()) {
232 if (itrF.Value().IsSame(aFace)) {
233 faceIsNew = Standard_False;
238 edgeNaborFaces.ChangeFind(anEdge).Append(aFace);
243 TopExp_Explorer anEx(S,TopAbs_EDGE); // mpv: new explorer iterator becouse we need keep edges order
244 for(;anEx.More();anEx.Next()) {
245 Standard_Boolean aC0 = Standard_False;
246 TopoDS_Shape anEdge1 = anEx.Current();
247 if (edgeNaborFaces.IsBound(anEdge1)) {
248 const TopTools_ListOfShape& aList1 = edgeNaborFaces.Find(anEdge1);
249 TopTools_DataMapIteratorOfDataMapOfShapeListOfShape itr(edgeNaborFaces);
250 for (; itr.More(); itr.Next()) {
251 TopoDS_Shape anEdge2 = itr.Key();
252 if (anEdge1.IsSame(anEdge2)) continue;
253 const TopTools_ListOfShape& aList2 = itr.Value();
254 // compare lists of the neighbour faces of edge1 and edge2
255 if (aList1.Extent() == aList2.Extent()) {
256 Standard_Integer aMatches = 0;
257 for(TopTools_ListIteratorOfListOfShape aLIter1(aList1);aLIter1.More();aLIter1.Next())
258 for(TopTools_ListIteratorOfListOfShape aLIter2(aList2);aLIter2.More();aLIter2.Next())
259 if (aLIter1.Value().IsSame(aLIter2.Value())) aMatches++;
260 if (aMatches == aList1.Extent()) {
262 TNaming_Builder bC0Edge(Tagger->NewChild());
263 bC0Edge.Generated(anEdge2);
264 edgeNaborFaces.UnBind(anEdge2);
268 edgeNaborFaces.UnBind(anEdge1);
271 TNaming_Builder bC0Edge(Tagger->NewChild());
272 bC0Edge.Generated(anEdge1);
278 //=======================================================================
279 //function : LoadC0Vertices
280 //purpose : Method for internal use. It is used by Load() method.
281 //=======================================================================
283 void QANewBRepNaming_ImportShape::LoadC0Vertices(const TopoDS_Shape& S,
284 const Handle(TDF_TagSource)& Tagger) const
286 TopTools_DataMapOfShapeListOfShape vertexNaborFaces;
287 TopTools_ListOfShape empty;
288 TopExp_Explorer explF(S, TopAbs_FACE);
289 for (; explF.More(); explF.Next()) {
290 const TopoDS_Shape& aFace = explF.Current();
291 TopExp_Explorer explV(aFace, TopAbs_VERTEX);
292 for (; explV.More(); explV.Next()) {
293 const TopoDS_Shape& aVertex = explV.Current();
294 if (!vertexNaborFaces.IsBound(aVertex)) vertexNaborFaces.Bind(aVertex, empty);
295 Standard_Boolean faceIsNew = Standard_True;
296 TopTools_ListIteratorOfListOfShape itrF(vertexNaborFaces.Find(aVertex));
297 for (; itrF.More(); itrF.Next()) {
298 if (itrF.Value().IsSame(aFace)) {
299 faceIsNew = Standard_False;
304 vertexNaborFaces.ChangeFind(aVertex).Append(aFace);
309 TopTools_DataMapIteratorOfDataMapOfShapeListOfShape itr(vertexNaborFaces);
310 for (; itr.More(); itr.Next()) {
311 const TopTools_ListOfShape& naborFaces = itr.Value();
312 if (naborFaces.Extent() < 3) {
313 TNaming_Builder bC0Vertex(Tagger->NewChild());
314 bC0Vertex.Generated(itr.Key());
319 //=======================================================================
320 //function : NamedFaces
321 //purpose : Returns the labels of all the named faces. Returns the number of faces.
322 //=======================================================================
324 Standard_Integer QANewBRepNaming_ImportShape::NamedFaces(TDF_LabelMap& theNamedFaces) const {
325 theNamedFaces.Clear();
326 Handle(TNaming_NamedShape) aFace;
327 TDF_ChildIterator itr(ResultLabel());
328 for (; itr.More(); itr.Next()) {
329 if (itr.Value().FindAttribute(TNaming_NamedShape::GetID(), aFace) &&
330 !aFace->IsEmpty() && aFace->Get().ShapeType() == TopAbs_FACE)
331 theNamedFaces.Add(itr.Value());
333 return theNamedFaces.Extent();
336 //=======================================================================
337 //function : NamedEdges
338 //purpose : Returns the labels of all the named free edges.
339 // Returns the number of edges.
340 //=======================================================================
342 Standard_Integer QANewBRepNaming_ImportShape::NamedEdges(TDF_LabelMap& theNamedEdges) const {
343 theNamedEdges.Clear();
344 Handle(TNaming_NamedShape) anEdge;
345 TDF_ChildIterator itr(ResultLabel());
346 for (; itr.More(); itr.Next()) {
347 if (itr.Value().FindAttribute(TNaming_NamedShape::GetID(), anEdge) &&
348 !anEdge->IsEmpty() && anEdge->Get().ShapeType() == TopAbs_EDGE)
349 theNamedEdges.Add(itr.Value());
351 return theNamedEdges.Extent();
354 //=======================================================================
355 //function : NamedVertices
356 //purpose : Returns the labels of all the named free vertices.
357 // Returns the number of verices.
358 //=======================================================================
360 Standard_Integer QANewBRepNaming_ImportShape::NamedVertices(TDF_LabelMap& theNamedVertices) const {
361 theNamedVertices.Clear();
362 Handle(TNaming_NamedShape) aVertex;
363 TDF_ChildIterator itr(ResultLabel());
364 for (; itr.More(); itr.Next()) {
365 if (itr.Value().FindAttribute(TNaming_NamedShape::GetID(), aVertex) &&
366 !aVertex->IsEmpty() && aVertex->Get().ShapeType() == TopAbs_VERTEX)
367 theNamedVertices.Add(itr.Value());
369 return theNamedVertices.Extent();