0022535: Cut sphere: invalid shape after reading from STEP
[occt.git] / src / BinMNaming / BinMNaming_NamingDriver.cxx
CommitLineData
b311480e 1// Created on: 2004-05-13
2// Created by: Sergey ZARITCHNY
3// Copyright (c) 2004-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
7fd59977 20
21
22
23#include <BinMNaming_NamingDriver.ixx>
24#include <TopAbs_ShapeEnum.hxx>
25#include <TCollection_ExtendedString.hxx>
26#include <TColStd_Array1OfInteger.hxx>
27#include <CDM_MessageDriver.hxx>
28#include <TDF_Attribute.hxx>
29#include <TNaming_NameType.hxx>
30#include <TNaming_Naming.hxx>
31#include <TNaming_NamedShape.hxx>
32#include <TNaming_ListIteratorOfListOfNamedShape.hxx>
33#include <BinMDF_ADriver.hxx>
34#include <BinObjMgt_Persistent.hxx>
35#include <BinObjMgt_RRelocationTable.hxx>
36#include <BinObjMgt_SRelocationTable.hxx>
37#include <BinMNaming.hxx>
38#include <TCollection_AsciiString.hxx>
39#include <TDF_Tool.hxx>
40#define NULL_ENTRY "0:0"
41#define OBSOLETE_NUM sizeof(Standard_Integer)
42//=======================================================================
43// 'Z' - is reserved for: forfidden to use
44//=======================================================================
45static Standard_Character NameTypeToChar(const TNaming_NameType theNameType)
46{
47 switch(theNameType) {
48 case TNaming_UNKNOWN : return 'N';
49 case TNaming_IDENTITY : return 'I';
50 case TNaming_MODIFUNTIL : return 'M';
51 case TNaming_GENERATION : return 'G';
52 case TNaming_INTERSECTION : return 'S';
53 case TNaming_UNION : return 'U';
54 case TNaming_SUBSTRACTION : return 'B';
55 case TNaming_CONSTSHAPE : return 'C';
56 case TNaming_FILTERBYNEIGHBOURGS : return 'F';
57 case TNaming_ORIENTATION : return 'O';
58 case TNaming_WIREIN : return 'W';
1ec8a59e 59 case TNaming_SHELLIN : return 'H';
7fd59977 60 default:
61 Standard_DomainError::Raise("TNaming_NameType:: Name Type Unknown");
62 }
63 return 'N'; // To avoid compilation error message.
64}
65
66//=======================================================================
67static TNaming_NameType CharTypeToName(const Standard_Character theCharType)
68{
69 switch(theCharType) {
70 case 'N' : return TNaming_UNKNOWN;
71 case 'I' : return TNaming_IDENTITY;
72 case 'M' : return TNaming_MODIFUNTIL;
73 case 'G' : return TNaming_GENERATION;
74 case 'S' : return TNaming_INTERSECTION;
75 case 'U' : return TNaming_UNION;
76 case 'B' : return TNaming_SUBSTRACTION;
77 case 'C' : return TNaming_CONSTSHAPE;
78 case 'F' : return TNaming_FILTERBYNEIGHBOURGS;
79 case 'O' : return TNaming_ORIENTATION;
80 case 'W' : return TNaming_WIREIN;
1ec8a59e 81 case 'H' : return TNaming_SHELLIN;
7fd59977 82 default:
83 Standard_DomainError::Raise("TNaming_NameType:: Name Type Unknown");
84 }
85 return TNaming_UNKNOWN; // To avoid compilation error message.
86}
87
88//=======================================================================
89static Standard_Character ShapeTypeToChar(const TopAbs_ShapeEnum theShapeType)
90{
91 switch (theShapeType)
92 {
93 case TopAbs_COMPOUND : return 'C';
94 case TopAbs_COMPSOLID : return 'O';
95 case TopAbs_SOLID : return 'S';
96 case TopAbs_SHELL : return 'H';
97 case TopAbs_FACE : return 'F';
98 case TopAbs_WIRE : return 'W';
99 case TopAbs_EDGE : return 'E';
100 case TopAbs_VERTEX : return 'V';
101 case TopAbs_SHAPE : return 'A';
102 }
103 return 'A'; // To avoid compilation error message.
104}
105//=======================================================================
106static TopAbs_ShapeEnum CharToShapeType(const Standard_Character theCharType)
107{
108 switch (theCharType)
109 {
110 case 'C' : return TopAbs_COMPOUND;
111 case 'O' : return TopAbs_COMPSOLID;
112 case 'S' : return TopAbs_SOLID;
113 case 'H' : return TopAbs_SHELL;
114 case 'F' : return TopAbs_FACE;
115 case 'W' : return TopAbs_WIRE;
116 case 'E' : return TopAbs_EDGE;
117 case 'V' : return TopAbs_VERTEX;
118 case 'A' : return TopAbs_SHAPE;
119 }
120 return TopAbs_SHAPE; // To avoid compilation error message.
121}
122//=======================================================================
123//function : BinMNaming_NamingDriver
124//purpose : Constructor
125//=======================================================================
126
127BinMNaming_NamingDriver::BinMNaming_NamingDriver
128 (const Handle(CDM_MessageDriver)& theMsgDriver)
129 : BinMDF_ADriver (theMsgDriver, STANDARD_TYPE(TNaming_Naming)->Name())
130{
131}
132
133//=======================================================================
134//function : NewEmpty
135//purpose :
136//=======================================================================
137
138Handle(TDF_Attribute) BinMNaming_NamingDriver::NewEmpty() const
139{
140 return new TNaming_Naming();
141}
142
143//=======================================================================
144//function : Paste
145//purpose : persistent -> transient (retrieve)
146//=======================================================================
147
148Standard_Boolean BinMNaming_NamingDriver::Paste
149 (const BinObjMgt_Persistent& theSource,
150 const Handle(TDF_Attribute)& theTarget,
151 BinObjMgt_RRelocationTable& theRelocTable) const
152{
153 Handle(TNaming_Naming) anAtt = Handle(TNaming_Naming)::DownCast(theTarget);
154 if(anAtt.IsNull()) return Standard_False;
155
156 TNaming_Name& aName = anAtt->ChangeName();
157 TCollection_ExtendedString aMsg;
158//1. NameType
159 Standard_Character aValue;
160 Standard_Boolean ok = theSource >> aValue;
161 Standard_Boolean aNewF = Standard_False;
162 if (ok) {
163 if(aValue == 'Z') { // new format
164 aNewF = Standard_True;
165 ok = theSource >> aValue; //skip the sign & get NameType
166 if(!ok) return ok;
167 }
168
169 aName.Type(CharTypeToName(aValue));
170
171//2. ShapeType
172 ok = theSource >> aValue;
173 if (ok) {
174 aName.ShapeType(CharToShapeType(aValue));
175
176//3. Args
177 Standard_Integer aNbArgs=0;
178 Standard_Integer anIndx;
179 Handle(TNaming_NamedShape) aNS;
180 ok = theSource >> aNbArgs;
181 if (ok) {
182 if(aNbArgs > 0) {
183 Standard_Integer i;
184 // read array
185 for(i=1; i<=aNbArgs;i++) {
186 if(!aNewF && i > OBSOLETE_NUM) break;//interrupt reading as old format can have only 4 items
187 ok = theSource >> anIndx;
188 if (!ok)
189 break;
190 else {
191 if (theRelocTable.IsBound(anIndx))
192 aNS = Handle(TNaming_NamedShape)::DownCast(theRelocTable.Find(anIndx));
193 else {
194 aNS = new TNaming_NamedShape;
195 theRelocTable.Bind(anIndx, aNS);
196 }
197 aName.Append(aNS);
198 }
199 }
200 //patch to release the rest of items
201 if(!aNewF && aNbArgs < OBSOLETE_NUM) {
202 for(i = aNbArgs+1;i <= OBSOLETE_NUM;i++)
203 theSource >> anIndx;
204 }
205 }
206//4. StopNS
207 ok = theSource >> anIndx;
208 if(ok) {
209 if(anIndx > 0) {
210 if (theRelocTable.IsBound(anIndx))
211 aNS = Handle(TNaming_NamedShape)::DownCast(theRelocTable.Find(anIndx));
212 else
213 {
214 aNS = new TNaming_NamedShape;
215 theRelocTable.Bind(anIndx, aNS);
216 }
217 aName.StopNamedShape(aNS);
218 }
219
220//5. Index
221 ok = theSource >> anIndx;
222 if(ok)
223 aName.Index(anIndx);
224 else {
225 aMsg = TCollection_ExtendedString("BinMNaming_NamingDriver: "
226 "Cannot retrieve Index of Name");
227 WriteMessage (aMsg);
228 }
229 } else {
230 aMsg = TCollection_ExtendedString("BinMNaming_NamingDriver: "
231 "Cannot retrieve reference on "
232 "StopNamedShape");
233 WriteMessage (aMsg);
234 }
235 } else {
236 aMsg = TCollection_ExtendedString("BinMNaming_NamingDriver: "
237 "Cannot retrieve reference on "
238 "Arguments of Name");
239 WriteMessage (aMsg);
240 }
241
242#ifdef DEB
243 //cout << "CurDocVersion = " << BinMNaming::DocumentVersion() <<endl;
244#endif
245 if(BinMNaming::DocumentVersion() > 3) {
246 TCollection_AsciiString entry;
247 ok = theSource >> entry;
248 if(ok) {
249#ifdef DEB
250 cout << "NamingDriver:: Retrieved Context Label = " << entry << " Ok = " << theSource.IsOK() <<endl;
251#endif
252
253//6. context label
254 if(!entry.IsEmpty() && !entry.IsEqual(TCollection_AsciiString(NULL_ENTRY)))
255 {
256 TDF_Label tLab; // Null label.
257 TDF_Tool::Label(anAtt->Label().Data(),entry, tLab, Standard_True);
258 if (!tLab.IsNull())
259 aName.ContextLabel(tLab);
260 }
261 }
262 }
263#ifdef DEB
264 else if(BinMNaming::DocumentVersion() == -1)
265 cout << "Current DocVersion field is not initialized. " <<endl;
266 else
267 cout << "Current DocVersion = " << BinMNaming::DocumentVersion() <<endl;
268#endif
269 }
270 }
271 return ok;
272}
273
274//=======================================================================
275//function : Paste
276//purpose : transient -> persistent (store)
277//=======================================================================
278
279void BinMNaming_NamingDriver::Paste (const Handle(TDF_Attribute)& theSource,
280 BinObjMgt_Persistent& theTarget,
281 BinObjMgt_SRelocationTable& theRelocTable) const
282{
283 Handle(TNaming_Naming) anAtt = Handle(TNaming_Naming)::DownCast(theSource);
284 const TNaming_Name& aName = anAtt->GetName();
285
286//0. add the sign of new format (to fix misprint with Array size)
287 theTarget.PutCharacter('Z');
288
289//1. << NameType to Char
290 theTarget << NameTypeToChar(aName.Type());
291
292//2. << ShapeType to Char
293 theTarget << ShapeTypeToChar(aName.ShapeType());
294
295//3. Keep Args
296 Standard_Integer anIndx;
297 Standard_Integer aNbArgs = aName.Arguments().Extent();
298 theTarget << aNbArgs; // keep Number
299 if (aNbArgs > 0) {
300 Standard_Integer i=0;
301 TColStd_Array1OfInteger anArray(1, aNbArgs);
302 //fill array
303 for (TNaming_ListIteratorOfListOfNamedShape it (aName.Arguments()); it.More(); it.Next()) {
304 Handle(TNaming_NamedShape) anArg = it.Value();
305 anIndx = 0; i++;
306 if (!anArg.IsNull()) {
307 anIndx = theRelocTable.FindIndex(anArg);
308 if (anIndx == 0)
309 anIndx = theRelocTable.Add(anArg);
310 }
311 anArray.SetValue(i, anIndx);
312 }
313
314 theTarget.PutIntArray ((BinObjMgt_PInteger) &anArray.Value(1), aNbArgs); // keep Array
315 }
316
317//4. keep StopNS
318 Handle(TNaming_NamedShape) aStopNS = aName.StopNamedShape();
319 if (!aStopNS.IsNull()) {
320 anIndx = theRelocTable.FindIndex(aStopNS);
321 if (anIndx == 0)
322 anIndx = theRelocTable.Add(aStopNS);
323 } else
324 anIndx = 0;
325 theTarget << anIndx;
326
327//5. keep Index
328 theTarget << aName.Index();
329
330//6. keep context label
331 TCollection_AsciiString entry(NULL_ENTRY);
332 if(!aName.ContextLabel().IsNull())
333 TDF_Tool::Entry(aName.ContextLabel(), entry);
334 theTarget << entry;
335}