0031918: Application Framework - New binary format for fast reading part of OCAF...
[occt.git] / src / BinMXCAFDoc / BinMXCAFDoc_LocationDriver.cxx
1 // Created on: 2005-05-17
2 // Created by: Eugeny NAPALKOV
3 // Copyright (c) 2005-2014 OPEN CASCADE SAS
4 //
5 // This file is part of Open CASCADE Technology software library.
6 //
7 // This library is free software; you can redistribute it and/or modify it under
8 // the terms of the GNU Lesser General Public License version 2.1 as published
9 // by the Free Software Foundation, with special exception defined in the file
10 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
11 // distribution for complete text of the license and disclaimer of any warranty.
12 //
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
15
16
17 #include <BinMDataStd.hxx>
18 #include <BinMXCAFDoc_LocationDriver.hxx>
19 #include <BinObjMgt_Persistent.hxx>
20 #include <BinTools_LocationSet.hxx>
21 #include <BinTools_ShapeReader.hxx>
22 #include <BinTools_ShapeWriter.hxx>
23 #include <Message_Messenger.hxx>
24 #include <gp_Mat.hxx>
25 #include <gp_Trsf.hxx>
26 #include <gp_XYZ.hxx>
27 #include <Standard_Type.hxx>
28 #include <TDF_Attribute.hxx>
29 #include <TopLoc_Datum3D.hxx>
30 #include <TopLoc_Location.hxx>
31 #include <XCAFDoc_Location.hxx>
32
33 IMPLEMENT_STANDARD_RTTIEXT(BinMXCAFDoc_LocationDriver,BinMDF_ADriver)
34
35 //#include <Precision.hxx>
36 //=======================================================================
37 //function :
38 //purpose  : 
39 //=======================================================================
40 BinMXCAFDoc_LocationDriver::BinMXCAFDoc_LocationDriver(const Handle(Message_Messenger)& theMsgDriver)
41      : BinMDF_ADriver(theMsgDriver, STANDARD_TYPE(XCAFDoc_Location)->Name())
42 {
43 }
44
45 //=======================================================================
46 //function :
47 //purpose  : 
48 //=======================================================================
49 Handle(TDF_Attribute) BinMXCAFDoc_LocationDriver::NewEmpty() const {
50   return new XCAFDoc_Location();
51 }
52
53 //=======================================================================
54 //function :
55 //purpose  : 
56 //=======================================================================
57 Standard_Boolean BinMXCAFDoc_LocationDriver::Paste(const BinObjMgt_Persistent& theSource,
58                                                    const Handle(TDF_Attribute)& theTarget,
59                                                    BinObjMgt_RRelocationTable& theRelocTable) const
60 {
61   Handle(XCAFDoc_Location) anAtt = Handle(XCAFDoc_Location)::DownCast(theTarget);
62   TopLoc_Location aLoc;
63   Standard_Boolean aRes = Translate(theSource, aLoc, theRelocTable);
64   anAtt->Set(aLoc);
65   return aRes;
66 }
67
68 //=======================================================================
69 //function :
70 //purpose  : 
71 //=======================================================================
72 void BinMXCAFDoc_LocationDriver::Paste(const Handle(TDF_Attribute)& theSource,
73                                        BinObjMgt_Persistent& theTarget,
74                                        BinObjMgt_SRelocationTable& theRelocTable) const
75 {
76   Handle(XCAFDoc_Location) anAtt = Handle(XCAFDoc_Location)::DownCast(theSource);
77   TopLoc_Location aLoc = anAtt->Get();
78   Translate(aLoc, theTarget, theRelocTable);
79 }
80
81 //=======================================================================
82 //function :
83 //purpose  : 
84 //=======================================================================
85 Standard_Boolean BinMXCAFDoc_LocationDriver::Translate(const BinObjMgt_Persistent& theSource,
86                                                        TopLoc_Location& theLoc,
87                                                        BinObjMgt_RRelocationTable& theMap) const
88 {
89   if (!myNSDriver.IsNull() && myNSDriver->IsQuickPart())
90   {
91     BinTools_IStream aDirectStream (*(const_cast<BinObjMgt_Persistent*>(&theSource)->GetIStream()));
92     BinTools_ShapeReader* aReader = static_cast<BinTools_ShapeReader*>(myNSDriver->ShapeSet (Standard_True));
93     theLoc = *(aReader->ReadLocation (aDirectStream));
94     return Standard_True;
95   }
96
97   Standard_Integer anId = 0;
98   theSource >> anId;
99   
100   if(anId == 0)
101   {
102     return Standard_True;
103   }
104
105   if (!myNSDriver.IsNull() && myNSDriver->IsQuickPart())
106   { // read directly from the stream
107
108
109   }
110   
111   Standard_Integer aFileVer = theMap.GetHeaderData()->StorageVersion().IntegerValue();
112   if( aFileVer >= TDocStd_FormatVersion_VERSION_6 && myNSDriver.IsNull() )
113   {
114     return Standard_False;
115   }
116   
117   Standard_Integer aPower (0);
118   Handle(TopLoc_Datum3D) aDatum;
119   
120   if (aFileVer >= TDocStd_FormatVersion_VERSION_6)
121   {
122     const TopLoc_Location& aLoc = myNSDriver->GetShapesLocations().Location (anId);
123     aPower = aLoc.FirstPower();
124     aDatum = aLoc.FirstDatum();
125   } else {
126     theSource >> aPower;
127
128     Standard_Integer aDatumID = -1;
129     Standard_Integer aReadDatum = -1;
130     theSource >> aReadDatum;
131     theSource >> aDatumID;
132     if(aReadDatum != -1) {
133       if(theMap.IsBound(aDatumID)) {
134         aDatum = Handle(TopLoc_Datum3D)::DownCast(theMap.Find(aDatumID));
135       } else
136         return Standard_False;
137     } else {
138       // read the datum's transformation
139       gp_Trsf aTrsf;
140
141       Standard_Real aScaleFactor;
142       theSource >> aScaleFactor;
143       aTrsf.SetScaleFactor(aScaleFactor);
144
145       Standard_Integer aForm;
146       theSource >> aForm;
147       aTrsf.SetForm((gp_TrsfForm)aForm);
148
149       Standard_Integer R, C;
150       gp_Mat& aMat = (gp_Mat&)aTrsf.HVectorialPart();
151       for(R = 1; R <= 3; R++)
152         for(C = 1; C <= 3; C++) {
153           Standard_Real aVal;
154           theSource >> aVal;
155           aMat.SetValue(R, C, aVal);
156         }
157
158       Standard_Real x, y, z;
159       theSource >> x >> y >> z;
160       gp_XYZ& aLoc = (gp_XYZ&)aTrsf.TranslationPart();
161       aLoc.SetX(x);
162       aLoc.SetY(y);
163       aLoc.SetZ(z);
164
165       aDatum = new TopLoc_Datum3D(aTrsf);
166       theMap.Bind(aDatumID, aDatum);
167     }
168   }
169   
170   //  Get Next Location
171   TopLoc_Location aNextLoc;
172   Translate(theSource, aNextLoc, theMap);
173   
174   //  Calculate the result
175   theLoc = aNextLoc * TopLoc_Location(aDatum).Powered(aPower);
176   return Standard_True;
177 }
178
179 //=======================================================================
180 //function :
181 //purpose  : 
182 //=======================================================================
183 void BinMXCAFDoc_LocationDriver::Translate(const TopLoc_Location& theLoc,
184                                            BinObjMgt_Persistent& theTarget,
185                                            BinObjMgt_SRelocationTable& theMap) const
186 {
187   if (!myNSDriver.IsNull() && myNSDriver->IsQuickPart())
188   { // write directly to the stream
189     Standard_OStream* aDirectStream = theTarget.GetOStream();
190     BinTools_ShapeWriter* aWriter = static_cast<BinTools_ShapeWriter*>(myNSDriver->ShapeSet (Standard_False));
191     BinTools_OStream aStream(*aDirectStream);
192     aWriter->WriteLocation (aStream, theLoc);
193     return;
194   }
195   if (theLoc.IsIdentity())
196   {
197     theTarget.PutInteger(0);
198     return;
199   }
200   
201   // The location is not identity
202   if (myNSDriver.IsNull())
203   {
204 #ifdef OCCT_DEBUG
205     std::cout << "NamedShape Driver is NULL\n";
206 #endif
207     return;
208   }
209
210   Standard_Integer anId = myNSDriver->GetShapesLocations().Add (theLoc);
211   theTarget << anId;
212
213   // In earlier version of this driver a datums from location stored in 
214   // the relocation table, but now it's not necessary
215   // (try to uncomment it if some problems appear)
216   /*
217   Handle(TopLoc_Datum3D) aDatum = theLoc.FirstDatum();
218
219   if(!theMap.Contains(aDatum)) {
220     theMap.Add(aDatum);
221   }
222   */
223
224   Translate(theLoc.NextLocation(), theTarget, theMap);
225 }
226