0027932: Improvement of standard attributes usability.
[occt.git] / src / XCAFDoc / XCAFDoc_Dimension.cxx
1 // Copyright (c) 1999-2014 OPEN CASCADE SAS
2 //
3 // This file is part of Open CASCADE Technology software library.
4 //
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.
10 //
11 // Alternatively, this file may be used under the terms of Open CASCADE
12 // commercial license or contractual agreement.
13
14 #include <XCAFDoc_Dimension.hxx>
15
16 #include <TDF_RelocationTable.hxx>
17 #include <TDF_ChildIterator.hxx>
18 #include <XCAFDoc.hxx>
19 #include <TDataStd_TreeNode.hxx>
20 #include <Precision.hxx>
21 #include <TColgp_HArray1OfPnt.hxx>
22 #include <TDataStd_Integer.hxx>
23 #include <TDataStd_IntegerArray.hxx>
24 #include <TDataStd_ExtStringArray.hxx>
25 #include <TDataStd_Real.hxx>
26 #include <TDataStd_RealArray.hxx>
27 #include <TNaming_Builder.hxx>
28 #include <TNaming_NamedShape.hxx>
29 #include <TColStd_HArray1OfReal.hxx>
30 #include <TopoDS.hxx>
31 #include <XCAFDimTolObjects_DimensionObject.hxx>
32 #include <TNaming_Tool.hxx>
33 #include <TDataStd_Name.hxx>
34
35 IMPLEMENT_STANDARD_RTTIEXT(XCAFDoc_Dimension,TDF_Attribute)
36
37 enum ChildLab
38 {
39   ChildLab_Type = 1,
40   ChildLab_Value,
41   ChildLab_Qualifier,
42   ChildLab_Class,
43   ChildLab_Dec,
44   ChildLab_Modifiers,
45   ChildLab_Path,
46   ChildLab_Dir,
47   ChildLab_Pnt1,
48   ChildLab_Pnt2,
49   ChildLab_PlaneLoc,
50   ChildLab_PlaneN,
51   ChildLab_PlaneRef,
52   ChildLab_PntText,
53   ChildLab_Presentation,
54   ChildLab_Descriptions,
55   ChildLab_DescriptionNames
56 };
57
58 //=======================================================================
59 //function : XCAFDoc_Dimension
60 //purpose  : 
61 //=======================================================================
62
63 XCAFDoc_Dimension::XCAFDoc_Dimension()
64 {
65 }
66
67
68 //=======================================================================
69 //function : GetID
70 //purpose  : 
71 //=======================================================================
72
73 const Standard_GUID& XCAFDoc_Dimension::GetID() 
74 {
75   static Standard_GUID DGTID ("58ed092c-44de-11d8-8776-001083004c77");
76   //static Standard_GUID ID("efd212e9-6dfd-11d4-b9c8-0060b0ee281b");
77   return DGTID; 
78   //return ID;
79 }
80
81 //=======================================================================
82 //function : Set
83 //purpose  : 
84 //=======================================================================
85 Handle(XCAFDoc_Dimension) XCAFDoc_Dimension::Set(const TDF_Label& theLabel) 
86 {
87   Handle(XCAFDoc_Dimension) A;
88   if (!theLabel.FindAttribute(XCAFDoc_Dimension::GetID(), A)) {
89     A = new XCAFDoc_Dimension();
90     theLabel.AddAttribute(A);
91   }
92   return A;
93 }
94
95 //=======================================================================
96 //function : SetObject
97 //purpose  : 
98 //=======================================================================
99 void XCAFDoc_Dimension::SetObject (const Handle(XCAFDimTolObjects_DimensionObject)& theObject)
100 {
101   Backup();
102
103   //Label().ForForgetAllAttributes();
104   TDF_ChildIterator anIter(Label());
105   for(;anIter.More(); anIter.Next())
106   {
107     anIter.Value().ForgetAllAttributes();
108   }
109   Handle(TDataStd_Integer) aType = TDataStd_Integer::Set(Label().FindChild(ChildLab_Type), theObject->GetType());
110
111   if(!theObject->GetValues().IsNull())
112   {
113     Handle(TDataStd_RealArray) aVal = new TDataStd_RealArray();
114     Label().FindChild(ChildLab_Value).AddAttribute(aVal);
115     aVal->ChangeArray(theObject->GetValues());
116   }
117
118   Handle(TDataStd_Integer) aQualifier = TDataStd_Integer::Set(Label().FindChild(ChildLab_Qualifier), theObject->GetQualifier());
119  
120   Standard_Boolean aH;
121   XCAFDimTolObjects_DimensionFormVariance aF;
122   XCAFDimTolObjects_DimensionGrade aG;
123   theObject->GetClassOfTolerance(aH,aF,aG);
124   Handle(TColStd_HArray1OfInteger) anArrI;
125   if(aF != XCAFDimTolObjects_DimensionFormVariance_None)
126   {
127     Handle(TDataStd_IntegerArray) aClass = new TDataStd_IntegerArray();
128     Label().FindChild(ChildLab_Class).AddAttribute(aClass);
129     anArrI = new TColStd_HArray1OfInteger(1,3);
130     anArrI->SetValue(1,aH);
131     anArrI->SetValue(2,aF);
132     anArrI->SetValue(3,aG);
133     aClass->ChangeArray(anArrI);
134   }
135
136   Standard_Integer aL, aR;
137   theObject->GetNbOfDecimalPlaces(aL, aR);
138   if (aL > 0 || aR > 0)
139   {
140     Handle(TDataStd_IntegerArray) aDec = new TDataStd_IntegerArray();
141     Label().FindChild(ChildLab_Dec).AddAttribute(aDec);
142     anArrI = new TColStd_HArray1OfInteger(1,2);
143     anArrI->SetValue(1,aL);
144     anArrI->SetValue(2,aR);
145     aDec->ChangeArray(anArrI);
146   }
147
148   if(theObject->GetModifiers().Length() > 0)
149   {
150     Handle(TDataStd_IntegerArray) aModifiers = new TDataStd_IntegerArray();
151     Label().FindChild(ChildLab_Modifiers).AddAttribute(aModifiers);
152     anArrI = new TColStd_HArray1OfInteger(1,theObject->GetModifiers().Length());
153     for(Standard_Integer i = 1; i <= theObject->GetModifiers().Length(); i++)
154       anArrI->SetValue(i,theObject->GetModifiers().Value(i));
155     aModifiers->ChangeArray(anArrI);
156   }
157
158   if(!theObject->GetPath().IsNull())
159   {
160     TNaming_Builder tnBuild(Label().FindChild(ChildLab_Path));
161     tnBuild.Generated(theObject->GetPath());
162   }
163
164   Handle(TColStd_HArray1OfReal) anArrR;
165   if(theObject->GetType() == XCAFDimTolObjects_DimensionType_Location_Oriented)
166   {
167     gp_Dir aD;
168     theObject->GetDirection(aD);
169     Handle(TDataStd_RealArray) aDir = new TDataStd_RealArray();
170     Label().FindChild(ChildLab_Dir).AddAttribute(aDir);
171     anArrR = new TColStd_HArray1OfReal(1,3);
172     anArrR->SetValue(1,aD.X());
173     anArrR->SetValue(2,aD.Y());
174     anArrR->SetValue(3,aD.Z());
175     aDir->ChangeArray(anArrR);
176   }
177
178   if (theObject->HasPoint())
179   {
180     Handle(TDataStd_RealArray) aPnt = new TDataStd_RealArray();
181     gp_Pnt aPnt1 = theObject->GetPoint();
182
183     Handle(TColStd_HArray1OfReal) aPntArr = new TColStd_HArray1OfReal(1, 3);
184     for (Standard_Integer i = 1; i <= 3; i++)
185       aPntArr->SetValue(i, aPnt1.Coord(i));
186     aPnt->ChangeArray(aPntArr);
187
188     Label().FindChild(ChildLab_Pnt1).AddAttribute(aPnt);
189   }
190
191   if (theObject->HasPoint2())
192   {
193     Handle(TDataStd_RealArray) aPnt = new TDataStd_RealArray();
194     gp_Pnt aPnt2 = theObject->GetPoint2();
195
196     Handle(TColStd_HArray1OfReal) aPntArr = new TColStd_HArray1OfReal(1, 3);
197     for (Standard_Integer i = 1; i <= 3; i++)
198       aPntArr->SetValue(i, aPnt2.Coord(i));
199     aPnt->ChangeArray(aPntArr);
200
201     Label().FindChild(ChildLab_Pnt2).AddAttribute(aPnt);
202   }
203
204   if (theObject->HasPlane())
205   {
206     Handle(TDataStd_RealArray) aLoc = new TDataStd_RealArray();
207     Handle(TDataStd_RealArray) aN = new TDataStd_RealArray();
208     Handle(TDataStd_RealArray) aRAtt = new TDataStd_RealArray();
209     gp_Ax2 anAx = theObject->GetPlane();
210
211     Handle(TColStd_HArray1OfReal) aLocArr = new TColStd_HArray1OfReal(1, 3);
212     for (Standard_Integer i = 1; i <= 3; i++)
213       aLocArr->SetValue(i, anAx.Location().Coord(i));
214     aLoc->ChangeArray(aLocArr);
215
216     Handle(TColStd_HArray1OfReal) aNArr = new TColStd_HArray1OfReal(1, 3);
217     for (Standard_Integer i = 1; i <= 3; i++)
218       aNArr->SetValue(i, anAx.Direction().Coord(i));
219     aN->ChangeArray(aNArr);
220
221     Handle(TColStd_HArray1OfReal) aRArr = new TColStd_HArray1OfReal(1, 3);
222     for (Standard_Integer i = 1; i <= 3; i++)
223       aRArr->SetValue(i, anAx.XDirection().Coord(i));
224     aRAtt->ChangeArray(aRArr);
225
226     Label().FindChild(ChildLab_PlaneLoc).AddAttribute(aLoc);
227     Label().FindChild(ChildLab_PlaneN).AddAttribute(aN);
228     Label().FindChild(ChildLab_PlaneRef).AddAttribute(aRAtt);
229   }
230
231   if (theObject->HasTextPoint())
232   {
233     Handle(TDataStd_RealArray) aLoc = new TDataStd_RealArray();
234     gp_Pnt aPntText = theObject->GetPointTextAttach();
235
236     Handle(TColStd_HArray1OfReal) aLocArr = new TColStd_HArray1OfReal(1, 3);
237     for (Standard_Integer i = 1; i <= 3; i++)
238       aLocArr->SetValue(i, aPntText.Coord(i));
239     aLoc->ChangeArray(aLocArr);
240
241     Label().FindChild(ChildLab_PntText).AddAttribute(aLoc);
242   }
243
244   TopoDS_Shape aPresentation = theObject->GetPresentation();
245   if( !aPresentation.IsNull())
246   {
247     TDF_Label aLPres = Label().FindChild( ChildLab_Presentation);
248     TNaming_Builder tnBuild(aLPres);
249     tnBuild.Generated(aPresentation);
250     Handle(TCollection_HAsciiString) aName =  theObject->GetPresentationName();
251     if( !aName.IsNull() )
252     {
253       TCollection_ExtendedString str ( aName->String() );
254       TDataStd_Name::Set ( aLPres, str );
255     }
256   }
257
258   if (theObject->HasDescriptions())
259   {
260     Handle(TDataStd_ExtStringArray) aDescriptions = new TDataStd_ExtStringArray();
261     Handle(TDataStd_ExtStringArray) aDescriptionNames = new TDataStd_ExtStringArray();
262     Handle(TColStd_HArray1OfExtendedString) aDescrArr = new TColStd_HArray1OfExtendedString(1, theObject->NbDescriptions());
263     Handle(TColStd_HArray1OfExtendedString) aDescrNameArr = new TColStd_HArray1OfExtendedString(1, theObject->NbDescriptions());
264     for (Standard_Integer i = 0; i < theObject->NbDescriptions(); i++) {
265       TCollection_ExtendedString aDescr(theObject->GetDescription(i)->String());
266       aDescrArr->SetValue(i + 1, aDescr);
267       TCollection_ExtendedString aDescrName(theObject->GetDescriptionName(i)->String());
268       aDescrNameArr->SetValue(i + 1, aDescrName);
269     }
270     aDescriptions->ChangeArray(aDescrArr);
271     aDescriptionNames->ChangeArray(aDescrNameArr);
272     Label().FindChild(ChildLab_Descriptions).AddAttribute(aDescriptions);
273     Label().FindChild(ChildLab_DescriptionNames).AddAttribute(aDescriptionNames);
274   }
275 }
276
277 //=======================================================================
278 //function : GetObject
279 //purpose  : 
280 //=======================================================================
281 Handle(XCAFDimTolObjects_DimensionObject) XCAFDoc_Dimension::GetObject()  const
282 {
283   Handle(XCAFDimTolObjects_DimensionObject) anObj = new XCAFDimTolObjects_DimensionObject();
284
285   Handle(TDataStd_Integer) aType;
286   if(Label().FindChild(ChildLab_Type).FindAttribute(TDataStd_Integer::GetID(), aType))
287   {
288     anObj->SetType((XCAFDimTolObjects_DimensionType)aType->Get());
289   }
290
291   Handle(TDataStd_RealArray) aVal;
292   if(Label().FindChild(ChildLab_Value).FindAttribute(TDataStd_RealArray::GetID(), aVal) 
293      && !aVal->Array().IsNull())
294   {
295     anObj->SetValues(aVal->Array());
296   }
297
298   Handle(TDataStd_Integer) aQualifier;
299   if(Label().FindChild(ChildLab_Qualifier).FindAttribute(TDataStd_Integer::GetID(), aQualifier))
300   {
301     anObj->SetQualifier((XCAFDimTolObjects_DimensionQualifier)aQualifier->Get());
302   }
303  
304   Handle(TDataStd_IntegerArray) aClass;
305   if(Label().FindChild(ChildLab_Class).FindAttribute(TDataStd_IntegerArray::GetID(), aClass) 
306      && !aClass->Array().IsNull() && aClass->Array()->Length() > 0)
307   {
308     anObj->SetClassOfTolerance(aClass->Array()->Value(1) != 0, (XCAFDimTolObjects_DimensionFormVariance)aClass->Array()->Value(2), (XCAFDimTolObjects_DimensionGrade)aClass->Array()->Value(3));
309   }
310
311   Handle(TDataStd_IntegerArray) aDec;
312   if(Label().FindChild(ChildLab_Dec).FindAttribute(TDataStd_IntegerArray::GetID(), aDec)
313      && !aDec->Array().IsNull() && aDec->Array()->Length() > 0)
314   {
315       anObj->SetNbOfDecimalPlaces(aDec->Array()->Value(1), aDec->Array()->Value(2));
316   }
317  
318   Handle(TDataStd_IntegerArray) aModifiers;
319   if(Label().FindChild(ChildLab_Modifiers).FindAttribute(TDataStd_IntegerArray::GetID(), aModifiers) 
320      && !aModifiers->Array().IsNull())
321   {
322     XCAFDimTolObjects_DimensionModifiersSequence aM;
323     for(Standard_Integer i = 1; i <= aModifiers->Array()->Length(); i++)
324       aM.Append((XCAFDimTolObjects_DimensionModif)aModifiers->Array()->Value(i));
325     anObj->SetModifiers(aM);
326   }
327
328   Handle(TNaming_NamedShape) aShape;
329   if(Label().FindChild(ChildLab_Path).FindAttribute(TNaming_NamedShape::GetID(), aShape)
330     && !aShape.IsNull())
331   {
332     anObj->SetPath(TopoDS::Edge(aShape->Get()));
333   }
334
335
336   Handle(TDataStd_RealArray) aDir;
337   if(Label().FindChild(ChildLab_Dir).FindAttribute(TDataStd_RealArray::GetID(), aDir)
338      && !aDir->Array().IsNull() && aDir->Array()->Length() > 0)
339   {
340     gp_Dir aD(aDir->Array()->Value(1), aDir->Array()->Value(2), aDir->Array()->Value(3));
341     anObj->SetDirection(aD);
342   }
343
344   Handle(TDataStd_RealArray) aPnt1;
345   if(Label().FindChild(ChildLab_Pnt1).FindAttribute(TDataStd_RealArray::GetID(), aPnt1) && aPnt1->Length() == 3 )
346   {
347     gp_Pnt aP(aPnt1->Value(aPnt1->Lower()), aPnt1->Value(aPnt1->Lower()+1), aPnt1->Value(aPnt1->Lower()+2));
348     anObj->SetPoint(aP);
349   }
350
351   Handle(TDataStd_RealArray) aPnt2;
352   if(Label().FindChild(ChildLab_Pnt2).FindAttribute(TDataStd_RealArray::GetID(), aPnt2) && aPnt2->Length() == 3 )
353   {
354     gp_Pnt aP(aPnt2->Value(aPnt2->Lower()), aPnt2->Value(aPnt2->Lower()+1), aPnt2->Value(aPnt2->Lower()+2));
355     anObj->SetPoint2(aP);
356   }
357
358   Handle(TDataStd_RealArray) aLoc, aN, aR;
359   if(Label().FindChild(ChildLab_PlaneLoc).FindAttribute(TDataStd_RealArray::GetID(), aLoc) && aLoc->Length() == 3 &&
360     Label().FindChild(ChildLab_PlaneN).FindAttribute(TDataStd_RealArray::GetID(), aN) && aN->Length() == 3 &&
361     Label().FindChild(ChildLab_PlaneRef).FindAttribute(TDataStd_RealArray::GetID(), aR) && aR->Length() == 3 )
362   {
363     gp_Pnt aL(aLoc->Value(aLoc->Lower()), aLoc->Value(aLoc->Lower()+1), aLoc->Value(aLoc->Lower()+2));
364     gp_Dir aD(aN->Value(aN->Lower()), aN->Value(aN->Lower()+1), aN->Value(aN->Lower()+2));
365     gp_Dir aDR(aR->Value(aR->Lower()), aR->Value(aR->Lower()+1), aR->Value(aR->Lower()+2));
366     gp_Ax2 anAx(aL, aD, aDR);
367     anObj->SetPlane(anAx);
368   }
369
370   Handle(TDataStd_RealArray) aPntText;
371   if(Label().FindChild(ChildLab_PntText).FindAttribute(TDataStd_RealArray::GetID(), aPntText) && aPntText->Length() == 3 )
372   {
373     gp_Pnt aP(aPntText->Value(aPntText->Lower()), aPntText->Value(aPntText->Lower()+1), aPntText->Value(aPntText->Lower()+2));
374     anObj->SetPointTextAttach(aP);
375   }
376
377   Handle(TNaming_NamedShape) aNS;
378   TDF_Label aLPres = Label().FindChild( ChildLab_Presentation);
379   if ( aLPres.FindAttribute(TNaming_NamedShape::GetID(), aNS) ) 
380   {
381
382     TopoDS_Shape aPresentation = TNaming_Tool::GetShape(aNS);
383     if( !aPresentation.IsNull())
384     {
385      
386       Handle(TDataStd_Name) aNameAtrr;
387       Handle(TCollection_HAsciiString) aPresentName;
388       if (aLPres.FindAttribute(TDataStd_Name::GetID(),aNameAtrr))
389       {
390         const TCollection_ExtendedString& aName = aNameAtrr->Get();
391
392         if( !aName.IsEmpty())
393           aPresentName = new TCollection_HAsciiString(aName);
394       }
395
396       anObj->SetPresentation(aPresentation, aPresentName);
397     }
398   }
399
400   Handle(TDataStd_ExtStringArray) aDescriptions, aDescriptionNames;
401   if (Label().FindChild(ChildLab_Descriptions).FindAttribute(TDataStd_ExtStringArray::GetID(), aDescriptions) &&
402     Label().FindChild(ChildLab_DescriptionNames).FindAttribute(TDataStd_ExtStringArray::GetID(), aDescriptionNames)) {
403     for (Standard_Integer i = 1; i <= aDescriptions->Length(); i++) {
404       Handle(TCollection_HAsciiString) aDescription, aDescriptionName;
405       aDescription = new TCollection_HAsciiString(TCollection_AsciiString(aDescriptions->Value(i)));
406       aDescriptionName = new TCollection_HAsciiString(TCollection_AsciiString(aDescriptionNames->Value(i)));
407       anObj->AddDescription(aDescription, aDescriptionName);
408     }
409   }
410   return anObj;
411 }
412
413 //=======================================================================
414 //function : ID
415 //purpose  : 
416 //=======================================================================
417
418 const Standard_GUID& XCAFDoc_Dimension::ID() const
419 {
420   return GetID();
421 }
422
423 //=======================================================================
424 //function : Restore
425 //purpose  : 
426 //=======================================================================
427
428 void XCAFDoc_Dimension::Restore(const Handle(TDF_Attribute)& /*With*/) 
429 {
430 }
431
432
433 //=======================================================================
434 //function : NewEmpty
435 //purpose  : 
436 //=======================================================================
437
438 Handle(TDF_Attribute) XCAFDoc_Dimension::NewEmpty() const
439 {
440   return new XCAFDoc_Dimension();
441 }
442
443
444 //=======================================================================
445 //function : Paste
446 //purpose  : 
447 //=======================================================================
448
449 void XCAFDoc_Dimension::Paste(const Handle(TDF_Attribute)& /*Into*/,
450                            const Handle(TDF_RelocationTable)& /*RT*/) const
451 {
452 }