0023205: Patch for Naming improvement
[occt.git] / src / TNaming / TNaming_NamingTool.cxx
1 // Created on: 2000-02-14
2 // Created by: Denis PASCAL
3 // Copyright (c) 2000-2012 OPEN CASCADE SAS
4 //
5 // The content of this file is subject to the Open CASCADE Technology Public
6 // License Version 6.5 (the "License"). You may not use the content of this file
7 // except in compliance with the License. Please obtain a copy of the License
8 // at http://www.opencascade.org and read it completely before using this file.
9 //
10 // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
11 // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
12 //
13 // The Original Code and all software distributed under the License is
14 // distributed on an "AS IS" basis, without warranty of any kind, and the
15 // Initial Developer hereby disclaims all such warranties, including without
16 // limitation, any warranties of merchantability, fitness for a particular
17 // purpose or non-infringement. Please see the License for the specific terms
18 // and conditions governing the rights and limitations under the License.
19
20
21
22 #include <TNaming_NamingTool.ixx>
23 #include <TNaming_Tool.hxx>
24 #include <TNaming_NewShapeIterator.hxx> 
25 #include <TNaming_Iterator.hxx>
26 #include <TopTools_MapIteratorOfMapOfShape.hxx>
27 #include <TNaming_OldShapeIterator.hxx>
28 #include <TNaming_Tool.hxx>
29 #ifdef DEB
30 //#define MDTV_DEB_DESC
31 //#define MDTV_DEB_APPLY
32 #ifdef MDTV_DEB_DESC
33 #include <TCollection_AsciiString.hxx>
34 #include <TDF_Tool.hxx>
35 #include <BRepTools.hxx>
36 static void WriteS(const TopoDS_Shape& shape,
37                       const Standard_CString filename) 
38 {
39   char buf[256];
40   if(strlen(filename) > 255) return;
41 #ifdef WNT
42   strcpy_s (buf, filename);
43 #else
44   strcpy (buf, filename);
45 #endif
46   char* p = buf;
47   while (*p) {
48     if(*p == ':')
49       *p = '-';
50     p++;
51   }
52   ofstream save (buf);
53   if(!save) 
54     cout << "File " << buf << " was not created: rdstate = " << save.rdstate() << endl;
55   save << "DBRep_DrawableShape" << endl << endl;
56   if(!shape.IsNull()) BRepTools::Write(shape, save);
57   save.close();
58 }
59 #endif
60 #endif
61 //=======================================================================
62 //function : IsForbiden
63 //purpose  : ANaming voir NamingTool
64 //=======================================================================
65
66 static Standard_Boolean IsForbiden(const TDF_LabelMap& Forbiden,
67                                    const TDF_Label&    Lab)
68 {
69   if (Lab.IsRoot()) {
70     return Standard_False;
71   }
72   if (Forbiden.Contains(Lab)) 
73     return Standard_True;
74   else {
75     return IsForbiden(Forbiden,Lab.Father());
76   }
77 }
78
79 //=======================================================================
80 //function : LastModif 
81 //purpose  : ANaming 
82 //=======================================================================
83 static void LastModif(      TNaming_NewShapeIterator& it,
84                       const TopoDS_Shape&             S,
85                             TopTools_MapOfShape&      MS,
86                       const TDF_LabelMap&             Updated,
87                       const TDF_LabelMap&             Forbiden)
88
89   Standard_Boolean YaModif = Standard_False;
90   for (; it.More(); it.Next()) {
91     const TDF_Label&    Lab = it.Label();
92 #ifdef MDTV_DEB
93     TCollection_AsciiString entry;
94     TDF_Tool::Entry(Lab, entry);
95     cout << "NamingTool:: LastModif LabelEntry = "<< entry <<  endl;
96 #endif
97     if (!Updated.IsEmpty() && !Updated.Contains(Lab))  continue;
98     if (IsForbiden(Forbiden, Lab))                     continue; 
99     if (it.IsModification()) {
100       YaModif = Standard_True;
101       TNaming_NewShapeIterator it2(it);
102       if (!it2.More()) {
103         const TopoDS_Shape& S   = it.Shape();
104         MS.Add (S);  // Modified
105       }
106       else
107         LastModif(it2,it.Shape(),MS,Updated,Forbiden);
108     } 
109   }
110   if (!YaModif) 
111     MS.Add(S);    
112 }
113 //=======================================================================
114 static void ApplyOrientation (TopTools_MapOfShape& MS, 
115                               const TopAbs_Orientation OrientationToApply)
116 {
117  if (!MS.IsEmpty ()) {
118 #ifdef MDTV_DEB_APPLY
119    cout <<"OrientationToApply = " <<OrientationToApply <<endl;
120    TopTools_MapIteratorOfMapOfShape it1(MS);
121    for (; it1.More(); it1.Next()) {
122      cout << "ApplyOrientation: TShape = " << it1.Key().TShape()->This() << " OR = " <<it1.Key().Orientation() <<endl;
123    }
124 #endif
125    TopTools_MapOfShape aMS;
126    aMS.Assign(MS);
127    TopTools_MapIteratorOfMapOfShape it(aMS);
128    for (; it.More(); it.Next()) {
129      if(it.Key().Orientation() != OrientationToApply) {
130        TopoDS_Shape aS = it.Key();
131        MS.Remove(aS);
132        aS.Orientation(OrientationToApply);
133        MS.Add(aS);
134      }
135    }
136  }
137 }
138 //=======================================================================
139 //function : CurrentShape
140 //purpose  : ANaming
141 //=======================================================================
142 void TNaming_NamingTool::CurrentShape(const TDF_LabelMap&               Valid,
143                                       const TDF_LabelMap&               Forbiden,
144                                       const Handle(TNaming_NamedShape)& Att,
145                                       TopTools_MapOfShape&              MS)
146 {
147   TDF_Label Lab = Att->Label();
148 #ifdef MDTV_DEB
149     TCollection_AsciiString entry;
150     TDF_Tool::Entry(Lab, entry);
151     cout << "NamingTool:: LabelEntry = "<< entry <<  endl;
152 #endif
153   if (!Valid.IsEmpty() && !Valid.Contains(Lab)) {
154 #ifdef MDTV_DEB
155     TCollection_AsciiString entry;
156     TDF_Tool::Entry(Lab, entry);
157     cout << "NamingTool:: LabelEntry = "<< entry << " is out of Valid map" <<  endl;
158 #endif
159     return;
160   }
161
162   TNaming_Iterator itL (Att);
163   for (; itL.More(); itL.Next()) {
164     const TopoDS_Shape& S = itL.NewShape();
165     if (S.IsNull()) continue;
166 #ifdef MDTV_DEB
167     WriteS(S, "CS_NewShape.brep");
168     if(itL.OldShape().IsNull())
169       cout <<"OldShape is Null" <<endl;
170     else 
171         WriteS(itL.OldShape(), "CS_OldShape.brep");
172 #endif
173     Standard_Boolean YaOrientationToApply(Standard_False);
174     TopAbs_Orientation OrientationToApply(TopAbs_FORWARD);
175     if(Att->Evolution() == TNaming_SELECTED) {
176       if (itL.More() && itL.NewShape().ShapeType() != TopAbs_VERTEX &&
177           !itL.OldShape().IsNull() && itL.OldShape().ShapeType() == TopAbs_VERTEX) {
178         YaOrientationToApply = Standard_True;
179         OrientationToApply = itL.OldShape().Orientation();
180       }
181     }
182     TNaming_NewShapeIterator it(itL);
183     if (!it.More()) {
184       if (YaOrientationToApply)
185         MS.Add(S.Oriented(OrientationToApply));
186       else
187         MS.Add(S);
188     }
189     else {      
190 //     LastModif(it, S, MS, Valid, Forbiden);
191       TopTools_MapOfShape MS2; 
192       LastModif(it, S, MS2, Valid, Forbiden);
193       if (YaOrientationToApply) ApplyOrientation (MS2, OrientationToApply);//the solution to be refined
194       for (TopTools_MapIteratorOfMapOfShape itMS2(MS2); itMS2.More();itMS2.Next()) 
195         MS.Add(itMS2.Key());
196     }
197   }
198 }
199
200 //=======================================================================
201 //function : CurrentShapeFromShape
202 //purpose  : ANaming
203 //=======================================================================
204              
205 void TNaming_NamingTool::CurrentShapeFromShape(const TDF_LabelMap&               Valid,
206                                                const TDF_LabelMap&               Forbiden,
207                                                const TDF_Label&                  Acces,
208                                                const TopoDS_Shape&               S,
209                                                TopTools_MapOfShape&              MS)
210 {
211   TNaming_NewShapeIterator it(S,Acces);
212
213   Handle(TNaming_NamedShape) NS = it.NamedShape(); 
214   if(!NS.IsNull() && NS->Evolution() == TNaming_SELECTED)
215     MS.Add(TNaming_Tool::GetShape(NS));
216   else {
217     if (!it.More()) 
218       MS.Add(S);
219     else 
220       LastModif(it, S, MS, Valid, Forbiden);
221   }
222 }
223
224 //=======================================================================
225 //function : MakeDescendants
226 //purpose  : ANaming
227 //=======================================================================
228
229 static void MakeDescendants (TNaming_NewShapeIterator&         it,
230                              TDF_LabelMap&                     Descendants)
231 {
232   for (; it.More(); it.Next()) {
233     Descendants.Add(it.Label());
234 #ifdef MDTV_DEB_DESC
235     TCollection_AsciiString entry;
236     TDF_Tool::Entry(it.Label(), entry);
237     cout<< "MakeDescendants: Label = " <<entry <<endl;
238 #endif
239     if (!it.Shape().IsNull()) {
240       TNaming_NewShapeIterator it2(it);
241       MakeDescendants (it2,Descendants);
242     }
243   }
244 }
245 //=======================================================================
246 void BuildDescendants2 (const Handle(TNaming_NamedShape)& NS, const TDF_Label& ForbLab, TDF_LabelMap& Descendants)
247 {
248   if (NS.IsNull()) return;
249   TNaming_NewShapeIterator it(NS); 
250   for(;it.More();it.Next()) {
251     if(!it.NamedShape().IsNull()) {
252 #ifdef MDTV_DEB_DESC
253       TCollection_AsciiString entry;
254       TDF_Tool::Entry(it.Label(), entry);
255       cout<< "MakeDescendants2: Label = " <<entry <<endl;
256 #endif      
257       if(ForbLab == it.Label()) continue;
258       Descendants.Add(it.Label());
259       TNaming_NewShapeIterator it2(it); 
260       MakeDescendants (it2,Descendants); 
261     }
262   }
263 }
264 //=======================================================================
265 //function : BuildDescendants
266 //purpose  : ANaming
267 //=======================================================================
268
269 void TNaming_NamingTool::BuildDescendants (const Handle(TNaming_NamedShape)& NS,
270                                            TDF_LabelMap&                     Descendants)
271 {
272   if (NS.IsNull()) return;
273   Descendants.Add(NS->Label());
274   TNaming_NewShapeIterator it(NS); 
275 #ifdef MDTV_DEB_DESC
276     TCollection_AsciiString entry;
277     TDF_Tool::Entry(NS->Label(), entry);
278     cout<< "MakeDescendants: Label = " <<entry <<endl;
279 #endif
280   MakeDescendants (it,Descendants);
281   TNaming_OldShapeIterator it2(NS); 
282   for (; it2.More(); it2.Next()) {
283     if(!it2.Shape().IsNull()) {
284       Handle(TNaming_NamedShape) ONS = TNaming_Tool::NamedShape(it2.Shape(), NS->Label());
285       if(!ONS.IsNull()) {
286 #ifdef MDTV_DEB_DESC
287         TCollection_AsciiString entry;
288         TDF_Tool::Entry(ONS->Label(), entry);
289         cout<< "MakeDescendants_Old: Label = " <<entry <<endl;    
290 #endif
291         BuildDescendants2(ONS, NS->Label(), Descendants);
292       }
293     }  
294   }
295 }