1
0
mirror of https://git.dev.opencascade.org/repos/occt.git synced 2025-04-10 18:51:21 +03:00

0031918: Application Framework - New binary format for fast reading part of OCAF document

Implementation of new format for quick reading and writing parts of the documents (sub-set of labels and sub-set of attributes). It consists in writing shapes and all their contents right in the TNaming_NamedShape attribute placement and skipping the shape section. New format 12 for Binary file types is assigned to this version.

Added PCDM_ReaderFilter class that could be used in Open methods of TDocStd_Application. If it is defined, it allows to read:
- into already opened document in append mode AppendMode_Protect (do not overwrite existing attributes) or AppendMode_Overwrite
- only specified sub-trees of the document using AddPath (const TCollection_AsciiString& theEntryToRead)
- only specified attributes using AddRead (const TCollection_AsciiString& theRead) where theRead could be "TDataStd_Name", for example
- to skip specified attributes read using AddSkipped (const TCollection_AsciiString& theSkipped) where theSkipped could be "TDF_Reference", for example

The current limitations:
- only in Bin format
- if shapes have in the document shared topology, loaded in "append" mode in different "load" operations, they will have no shared topology anymore

Modifications:
BinLDrivers and BinDrivers packages - modifications related to the quick part tree format flag usage, skipping shape section writing and adding labels sizes into the document to be able to pass labels during the reading quickly.
BinObjMgt_Persistent and BinObjMgt_Position - to add possibility to write directly into the stream some data just after the attribute. Before this record a data-size is recorded.
BinMXCAFDoc package modifications to write BinMXCAFDoc_LocationDriver location in the same way as shapes write location data right after the attribute (empty) data in this new format.
BinTools package: creation of ShapeReader and ShapeWriter classes with same root class ShapeSetBase with ShapeSet class. These classes allows to write/read shapes directly to the stream. If some object is already in the stream, write a reference - relative position of the duplicated object. The old format of documents is still supported by Bin_ToolsShapeSet class.
PCDM_ReaderFilter - Allows the user to create a reading filter. It contains algorithm to browse labels tree quickly, without usage of referencing by entry-strings.
TDocStd, CDF and some other packages are changed for supporting reading filters API and options.

Tests, documentation and upgrade information are also added for both issues: 31839 and 31918 related to this commit.
This commit is contained in:
mpv 2021-06-24 17:26:52 +03:00 committed by bugmaster
parent 9e5e4c0c84
commit d5c71e2057
74 changed files with 4628 additions and 1120 deletions

View File

@ -2211,6 +2211,15 @@ BRep and Binary BRep Shape formats (only in case of triangulation-only Faces, wi
Versions of formats have been changed (11 for BinOCAF, 10 for XmlOCAF, 4 for BRep Shape and 3 for Binary BRep Shape). Versions of formats have been changed (11 for BinOCAF, 10 for XmlOCAF, 4 for BRep Shape and 3 for Binary BRep Shape).
Files written with the new version will not be readable by applications of old versions. Files written with the new version will not be readable by applications of old versions.
@subsection upgrade_760_changesBinaryFormat Changes in storage of binary document format
All kinds of binary document formats since the new version 12 saved with support of partial reading (sub-set of labels and sub-set of attributes).
For that the shapes data structures are stored with the related NamedShape attributes in the file, not in the particular section in the start of the document.
Also, size allocated for each label is stored in the file. This allows to skip big parts of document in partial reading mode if needed.
As a result, the new binary files become some smaller, but default reading and writing of documents may take some more time (depenging on the environment), up to 15 percents slower in the worse cases.
Backward compatibility (loading of old documents in the newer version) is still fully supported, as well as writing the older versions of the document.
@subsection upgrade_occt760_poly Changes in *Poly* package and *Poly_Triangulation* class @subsection upgrade_occt760_poly Changes in *Poly* package and *Poly_Triangulation* class
*Poly_Triangulation* does no more provide access to internal array structures: methods Nodes(), ChangeNode(), Triangles(), ChangeTriangle(), UVNodes(), ChangeUVNode(), Normals() have been removed. *Poly_Triangulation* does no more provide access to internal array structures: methods Nodes(), ChangeNode(), Triangles(), ChangeTriangle(), UVNodes(), ChangeUVNode(), Normals() have been removed.

View File

@ -745,6 +745,32 @@ To open the document from a file where it has been previously saved, you can use
app->Open("/tmp/example.caf", doc); app->Open("/tmp/example.caf", doc);
~~~~ ~~~~
For binary formats only the part of the stored document can be loaded. For that the *PCDM_ReadingFilter* class could be used. It is possible to define which attributes must be loaded or omitted,
or to define one or several entries for sub-tree that must be loaded only. The following example opens document *doc*, but reads only "0:1:2" label and its sub-labels and only *TDataStd_Name* attributes on them.
~~~~{.cpp}
Handle(PCDM_ReaderFilter) filter = new PCDM_ReaderFilter("0:1:2");
filter->AddRead("TDataStd_Name");
app->Open("example.cbf", doc, filter);
~~~~
Also, using filters, part of the document can be appended into the already loaded document from the same file. For an example, to read into the previously opened *doc* all attributes, except *TDataStd_Name* and *TDataStd_Integer*:
~~~~{.cpp}
Handle(PCDM_ReaderFilter) filter2 = new PCDM_ReaderFilter(PCDM_ReaderFilter::AppendMode_Protect);
filter2->AddSkipped("TDataStd_Name");
filter2->AddSkipped("TDataStd_Integer");
app->Open("example.cbf", doc, filter2);
~~~~
*PCDM_ReaderFilter::AppendMode_Protect* means that if the loading algorithm finds already existing attribute in the document, it will not be overwritten by attibute from the loading file. If it is needed to
substitute the existing attributes, the reading mode *PCDM_ReaderFilter::AppendMode_Overwrite* must be used instead.
*AddRead* and *AddSkipped* methods for attributes should not be used in one filter. If it is so, *AddSkipped* attributes are ignored during the read.
Appending to the document content of already loaded file may be performed several times with the same or different parts of the document loaded. For that the filter reading mode must be *PCDM_ReaderFilter::AppendMode_Protect*
or *PCDM_ReaderFilter::AppendMode_Overwrite*, which enables the "append" mode of document open. If the filter is empty or null or skipped in arguments, it opens document with "append" mode disabled and any loading limitations.
@subsubsection occt_ocaf_4_3_5 Cutting, copying and pasting inside a document @subsubsection occt_ocaf_4_3_5 Cutting, copying and pasting inside a document
To cut, copy and paste inside a document, use the class *TDF_CopyLabel*. To cut, copy and paste inside a document, use the class *TDF_CopyLabel*.

View File

@ -26,6 +26,7 @@
#include <Standard_Failure.hxx> #include <Standard_Failure.hxx>
#include <Standard_IStream.hxx> #include <Standard_IStream.hxx>
#include <Standard_Type.hxx> #include <Standard_Type.hxx>
#include <Standard_NotImplemented.hxx>
#include <TCollection_ExtendedString.hxx> #include <TCollection_ExtendedString.hxx>
#include <TNaming_NamedShape.hxx> #include <TNaming_NamedShape.hxx>
@ -64,7 +65,7 @@ void BinDrivers_DocumentRetrievalDriver::ReadShapeSection
{ {
// Read Shapes // Read Shapes
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
if (myDrivers->GetDriver(STANDARD_TYPE(TNaming_NamedShape),aDriver)) if (myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape),aDriver))
{ {
try { try {
OCC_CATCH_SIGNALS OCC_CATCH_SIGNALS
@ -75,7 +76,7 @@ void BinDrivers_DocumentRetrievalDriver::ReadShapeSection
catch(Standard_Failure const& anException) { catch(Standard_Failure const& anException) {
const TCollection_ExtendedString aMethStr const TCollection_ExtendedString aMethStr
("BinDrivers_DocumentRetrievalDriver: "); ("BinDrivers_DocumentRetrievalDriver: ");
myMsgDriver ->Send(aMethStr + "error of Shape Section " + myMsgDriver->Send(aMethStr + "error of Shape Section " +
anException.GetMessageString(), Message_Fail); anException.GetMessageString(), Message_Fail);
} }
} }
@ -85,7 +86,7 @@ void BinDrivers_DocumentRetrievalDriver::ReadShapeSection
//function : CheckShapeSection //function : CheckShapeSection
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinDrivers_DocumentRetrievalDriver::CheckShapeSection( void BinDrivers_DocumentRetrievalDriver::CheckShapeSection (
const Storage_Position& /*ShapeSectionPos*/, const Storage_Position& /*ShapeSectionPos*/,
Standard_IStream& /*IS*/) Standard_IStream& /*IS*/)
{} {}
@ -98,13 +99,32 @@ void BinDrivers_DocumentRetrievalDriver::Clear()
{ {
// Clear NamedShape driver // Clear NamedShape driver
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
if (myDrivers->GetDriver(STANDARD_TYPE(TNaming_NamedShape), aDriver)) if (myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver))
{ {
Handle(BinMNaming_NamedShapeDriver) aNamedShapeDriver = Handle(BinMNaming_NamedShapeDriver) aNamedShapeDriver =
Handle(BinMNaming_NamedShapeDriver)::DownCast(aDriver); Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
aNamedShapeDriver->Clear(); aNamedShapeDriver->Clear();
} }
BinLDrivers_DocumentRetrievalDriver::Clear(); BinLDrivers_DocumentRetrievalDriver::Clear();
} }
//=======================================================================
//function : EnableQuickPartReading
//purpose :
//=======================================================================
void BinDrivers_DocumentRetrievalDriver::EnableQuickPartReading (
const Handle(Message_Messenger)& theMessageDriver, Standard_Boolean theValue)
{
if (myDrivers.IsNull())
myDrivers = AttributeDrivers (theMessageDriver);
if (myDrivers.IsNull())
return;
Handle(BinMDF_ADriver) aDriver;
myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver);
Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
if (aShapesDriver.IsNull())
throw Standard_NotImplemented ("Internal Error - TNaming_NamedShape is not found!");
aShapesDriver->EnableQuickPart (theValue);
}

View File

@ -57,6 +57,10 @@ public:
//! Clears the NamedShape driver //! Clears the NamedShape driver
Standard_EXPORT virtual void Clear() Standard_OVERRIDE; Standard_EXPORT virtual void Clear() Standard_OVERRIDE;
//! Enables reading in the quick part access mode.
Standard_EXPORT virtual void EnableQuickPartReading
(const Handle(Message_Messenger)& theMessageDriver, Standard_Boolean theValue) Standard_OVERRIDE;
DEFINE_STANDARD_RTTIEXT(BinDrivers_DocumentRetrievalDriver,BinLDrivers_DocumentRetrievalDriver) DEFINE_STANDARD_RTTIEXT(BinDrivers_DocumentRetrievalDriver,BinLDrivers_DocumentRetrievalDriver)

View File

@ -33,7 +33,7 @@ IMPLEMENT_STANDARD_RTTIEXT(BinDrivers_DocumentStorageDriver,BinLDrivers_Document
//function : BinDrivers_DocumentStorageDriver //function : BinDrivers_DocumentStorageDriver
//purpose : Constructor //purpose : Constructor
//======================================================================= //=======================================================================
BinDrivers_DocumentStorageDriver::BinDrivers_DocumentStorageDriver () BinDrivers_DocumentStorageDriver::BinDrivers_DocumentStorageDriver()
{ {
} }
@ -61,7 +61,7 @@ Standard_Boolean BinDrivers_DocumentStorageDriver::IsWithTriangles() const
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver); myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver);
Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast(aDriver); Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
return !aShapesDriver.IsNull() return !aShapesDriver.IsNull()
&& aShapesDriver->IsWithTriangles(); && aShapesDriver->IsWithTriangles();
} }
@ -84,15 +84,55 @@ void BinDrivers_DocumentStorageDriver::SetWithTriangles (const Handle(Message_Me
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver); myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver);
Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast(aDriver); Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
if (aShapesDriver.IsNull()) if (aShapesDriver.IsNull())
{ {
throw Standard_NotImplemented("Internal Error - TNaming_NamedShape is not found!"); throw Standard_NotImplemented ("Internal Error - TNaming_NamedShape is not found!");
} }
aShapesDriver->SetWithTriangles (theWithTriangulation); aShapesDriver->SetWithTriangles (theWithTriangulation);
} }
void BinDrivers_DocumentStorageDriver::EnableQuickPartWriting (const Handle(Message_Messenger)& theMessageDriver,
const Standard_Boolean theValue)
{
if (myDrivers.IsNull())
{
myDrivers = AttributeDrivers (theMessageDriver);
}
if (myDrivers.IsNull())
{
return;
}
Handle(BinMDF_ADriver) aDriver;
myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver);
Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
if (aShapesDriver.IsNull())
{
throw Standard_NotImplemented ("Internal Error - TNaming_NamedShape is not found!");
}
aShapesDriver->EnableQuickPart (theValue);
}
//=======================================================================
//function : Clear
//purpose :
//=======================================================================
void BinDrivers_DocumentStorageDriver::Clear()
{
// Clear NamedShape driver
Handle(BinMDF_ADriver) aDriver;
if (myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver))
{
Handle(BinMNaming_NamedShapeDriver) aNamedShapeDriver =
Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
aNamedShapeDriver->Clear();
}
BinLDrivers_DocumentStorageDriver::Clear();
}
//======================================================================= //=======================================================================
//function : IsWithNormals //function : IsWithNormals
//purpose : //purpose :
@ -105,8 +145,8 @@ Standard_Boolean BinDrivers_DocumentStorageDriver::IsWithNormals() const
} }
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
myDrivers->GetDriver(STANDARD_TYPE(TNaming_NamedShape), aDriver); myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver);
Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast(aDriver); Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
return !aShapesDriver.IsNull() return !aShapesDriver.IsNull()
&& aShapesDriver->IsWithNormals(); && aShapesDriver->IsWithNormals();
} }
@ -115,12 +155,12 @@ Standard_Boolean BinDrivers_DocumentStorageDriver::IsWithNormals() const
//function : SetWithNormals //function : SetWithNormals
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinDrivers_DocumentStorageDriver::SetWithNormals(const Handle(Message_Messenger)& theMessageDriver, void BinDrivers_DocumentStorageDriver::SetWithNormals (const Handle(Message_Messenger)& theMessageDriver,
const Standard_Boolean theWithNormals) const Standard_Boolean theWithNormals)
{ {
if (myDrivers.IsNull()) if (myDrivers.IsNull())
{ {
myDrivers = AttributeDrivers(theMessageDriver); myDrivers = AttributeDrivers (theMessageDriver);
} }
if (myDrivers.IsNull()) if (myDrivers.IsNull())
{ {
@ -128,14 +168,14 @@ void BinDrivers_DocumentStorageDriver::SetWithNormals(const Handle(Message_Messe
} }
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
myDrivers->GetDriver(STANDARD_TYPE(TNaming_NamedShape), aDriver); myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver);
Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast(aDriver); Handle(BinMNaming_NamedShapeDriver) aShapesDriver = Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
if (aShapesDriver.IsNull()) if (aShapesDriver.IsNull())
{ {
throw Standard_NotImplemented("Internal Error - TNaming_NamedShape is not found!"); throw Standard_NotImplemented ("Internal Error - TNaming_NamedShape is not found!");
} }
aShapesDriver->SetWithNormals(theWithNormals); aShapesDriver->SetWithNormals (theWithNormals);
} }
//======================================================================= //=======================================================================
@ -151,7 +191,7 @@ void BinDrivers_DocumentStorageDriver::WriteShapeSection
const Standard_Size aShapesSectionOffset = (Standard_Size) theOS.tellp(); const Standard_Size aShapesSectionOffset = (Standard_Size) theOS.tellp();
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
if (myDrivers->GetDriver(STANDARD_TYPE(TNaming_NamedShape), aDriver)) if (myDrivers->GetDriver (STANDARD_TYPE(TNaming_NamedShape), aDriver))
{ {
try { try {
OCC_CATCH_SIGNALS OCC_CATCH_SIGNALS
@ -159,7 +199,7 @@ void BinDrivers_DocumentStorageDriver::WriteShapeSection
Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver); Handle(BinMNaming_NamedShapeDriver)::DownCast (aDriver);
aNamedShapeDriver->WriteShapeSection (theOS, theDocVer, theRange); aNamedShapeDriver->WriteShapeSection (theOS, theDocVer, theRange);
} }
catch(Standard_Failure const& anException) { catch (Standard_Failure const& anException) {
TCollection_ExtendedString anErrorStr ("BinDrivers_DocumentStorageDriver, Shape Section :"); TCollection_ExtendedString anErrorStr ("BinDrivers_DocumentStorageDriver, Shape Section :");
myMsgDriver->Send (anErrorStr + anException.GetMessageString(), Message_Fail); myMsgDriver->Send (anErrorStr + anException.GetMessageString(), Message_Fail);
} }

View File

@ -61,6 +61,13 @@ public:
Standard_EXPORT void SetWithNormals(const Handle(Message_Messenger)& theMessageDriver, Standard_EXPORT void SetWithNormals(const Handle(Message_Messenger)& theMessageDriver,
const Standard_Boolean theWithTriangulation); const Standard_Boolean theWithTriangulation);
//! Enables writing in the quick part access mode.
Standard_EXPORT void EnableQuickPartWriting(const Handle(Message_Messenger)& theMessageDriver,
const Standard_Boolean theValue) Standard_OVERRIDE;
//! Clears the NamedShape driver
Standard_EXPORT virtual void Clear() Standard_OVERRIDE;
DEFINE_STANDARD_RTTIEXT(BinDrivers_DocumentStorageDriver,BinLDrivers_DocumentStorageDriver) DEFINE_STANDARD_RTTIEXT(BinDrivers_DocumentStorageDriver,BinLDrivers_DocumentStorageDriver)
}; };

View File

@ -40,15 +40,18 @@
#include <TDF_Attribute.hxx> #include <TDF_Attribute.hxx>
#include <TDF_Data.hxx> #include <TDF_Data.hxx>
#include <TDF_Label.hxx> #include <TDF_Label.hxx>
#include <TDF_Tool.hxx>
#include <TDocStd_Document.hxx> #include <TDocStd_Document.hxx>
#include <TDocStd_FormatVersion.hxx> #include <TDocStd_FormatVersion.hxx>
#include <TDocStd_Owner.hxx> #include <TDocStd_Owner.hxx>
#include <Message_ProgressScope.hxx> #include <Message_ProgressScope.hxx>
#include <PCDM_ReaderFilter.hxx>
IMPLEMENT_STANDARD_RTTIEXT(BinLDrivers_DocumentRetrievalDriver,PCDM_RetrievalDriver) IMPLEMENT_STANDARD_RTTIEXT(BinLDrivers_DocumentRetrievalDriver,PCDM_RetrievalDriver)
#define SHAPESECTION_POS "SHAPE_SECTION_POS:" #define SHAPESECTION_POS "SHAPE_SECTION_POS:"
#define ENDSECTION_POS ":"
#define SIZEOFSHAPELABEL 18 #define SIZEOFSHAPELABEL 18
#define DATATYPE_MIGRATION #define DATATYPE_MIGRATION
@ -71,6 +74,7 @@ void BinLDrivers_DocumentRetrievalDriver::Read
(const TCollection_ExtendedString& theFileName, (const TCollection_ExtendedString& theFileName,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
std::ifstream aFileStream; std::ifstream aFileStream;
@ -81,7 +85,7 @@ void BinLDrivers_DocumentRetrievalDriver::Read
Handle(Storage_Data) dData; Handle(Storage_Data) dData;
TCollection_ExtendedString aFormat = PCDM_ReadWriter::FileFormat (aFileStream, dData); TCollection_ExtendedString aFormat = PCDM_ReadWriter::FileFormat (aFileStream, dData);
Read(aFileStream, dData, theNewDocument, theApplication, theRange); Read (aFileStream, dData, theNewDocument, theApplication, theFilter, theRange);
if (!theRange.More()) if (!theRange.More())
{ {
myReaderStatus = PCDM_RS_UserBreak; myReaderStatus = PCDM_RS_UserBreak;
@ -108,6 +112,7 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
const Handle(Storage_Data)& theStorageData, const Handle(Storage_Data)& theStorageData,
const Handle(CDM_Document)& theDoc, const Handle(CDM_Document)& theDoc,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
myReaderStatus = PCDM_RS_DriverFailure; myReaderStatus = PCDM_RS_DriverFailure;
@ -176,7 +181,6 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
Standard_Boolean begin = Standard_False; Standard_Boolean begin = Standard_False;
Standard_Integer i; Standard_Integer i;
for (i=1; i <= aUserInfo.Length(); i++) { for (i=1; i <= aUserInfo.Length(); i++) {
//const TCollection_AsciiString& aStr = aUserInfo(i);
TCollection_AsciiString aStr = aUserInfo(i); TCollection_AsciiString aStr = aUserInfo(i);
if (aStr == START_TYPES) if (aStr == START_TYPES)
begin = Standard_True; begin = Standard_True;
@ -221,10 +225,11 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
myRelocTable.SetHeaderData(aHeaderData); myRelocTable.SetHeaderData(aHeaderData);
mySections.Clear(); mySections.Clear();
myPAtt.Init(); myPAtt.Init();
Handle(TDF_Data) aData = new TDF_Data(); Handle(TDF_Data) aData = (!theFilter.IsNull() && theFilter->IsAppendMode()) ? aDoc->GetData() : new TDF_Data();
std::streampos aDocumentPos = -1; std::streampos aDocumentPos = -1;
Message_ProgressScope aPS(theRange, "Reading data", 3); Message_ProgressScope aPS (theRange, "Reading data", 3);
Standard_Boolean aQuickPart = IsQuickPart (aFileVer);
// 2b. Read the TOC of Sections // 2b. Read the TOC of Sections
if (aFileVer >= TDocStd_FormatVersion_VERSION_3) { if (aFileVer >= TDocStd_FormatVersion_VERSION_3) {
@ -232,7 +237,7 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
do { do {
BinLDrivers_DocumentSection::ReadTOC (aSection, theIStream, aFileVer); BinLDrivers_DocumentSection::ReadTOC (aSection, theIStream, aFileVer);
mySections.Append(aSection); mySections.Append(aSection);
} while(!aSection.Name().IsEqual((Standard_CString)SHAPESECTION_POS) && !theIStream.eof()); } while (!aSection.Name().IsEqual (aQuickPart ? ENDSECTION_POS : SHAPESECTION_POS) && !theIStream.eof());
if (theIStream.eof()) { if (theIStream.eof()) {
// There is no shape section in the file. // There is no shape section in the file.
@ -248,7 +253,7 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
BinLDrivers_DocumentSection& aCurSection = anIterS.ChangeValue(); BinLDrivers_DocumentSection& aCurSection = anIterS.ChangeValue();
if (aCurSection.IsPostRead() == Standard_False) { if (aCurSection.IsPostRead() == Standard_False) {
theIStream.seekg ((std::streampos) aCurSection.Offset()); theIStream.seekg ((std::streampos) aCurSection.Offset());
if (aCurSection.Name().IsEqual ((Standard_CString)SHAPESECTION_POS)) if (aCurSection.Name().IsEqual (SHAPESECTION_POS))
{ {
ReadShapeSection (aCurSection, theIStream, false, aPS.Next()); ReadShapeSection (aCurSection, theIStream, false, aPS.Next());
if (!aPS.More()) if (!aPS.More())
@ -257,7 +262,7 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
return; return;
} }
} }
else else if (!aCurSection.Name().IsEqual (ENDSECTION_POS))
ReadSection (aCurSection, theDoc, theIStream); ReadSection (aCurSection, theDoc, theIStream);
} }
} }
@ -313,8 +318,14 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
Standard_Integer aTag; Standard_Integer aTag;
theIStream.read ((char*)&aTag, sizeof(Standard_Integer)); theIStream.read ((char*)&aTag, sizeof(Standard_Integer));
if (aQuickPart)
myPAtt.SetIStream (theIStream); // for reading shapes data from the stream directly
EnableQuickPartReading (myMsgDriver, aQuickPart);
// read sub-tree of the root label // read sub-tree of the root label
Standard_Integer nbRead = ReadSubTree (theIStream, aData->Root(), aPS.Next()); if (!theFilter.IsNull())
theFilter->StartIteration();
Standard_Integer nbRead = ReadSubTree (theIStream, aData->Root(), theFilter, aQuickPart, aPS.Next());
if (!aPS.More()) if (!aPS.More())
{ {
myReaderStatus = PCDM_RS_UserBreak; myReaderStatus = PCDM_RS_UserBreak;
@ -331,9 +342,12 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
if (nbRead > 0) { if (nbRead > 0) {
// attach data to the document // attach data to the document
aDoc->SetData (aData); if (theFilter.IsNull() || !theFilter->IsAppendMode())
TDocStd_Owner::SetDocument (aData, aDoc); {
aDoc->SetData(aData);
TDocStd_Owner::SetDocument(aData, aDoc);
aDoc->SetComments(aHeaderData->Comments()); aDoc->SetComments(aHeaderData->Comments());
}
myReaderStatus = PCDM_RS_OK; myReaderStatus = PCDM_RS_OK;
} }
@ -356,8 +370,10 @@ void BinLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
//======================================================================= //=======================================================================
Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree
(Standard_IStream& theIS, (Standard_IStream& theIS,
const TDF_Label& theLabel, const TDF_Label& theLabel,
const Handle(PCDM_ReaderFilter)& theFilter,
const Standard_Boolean& theQuickPart,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
Standard_Integer nbRead = 0; Standard_Integer nbRead = 0;
@ -366,23 +382,56 @@ Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree
Message_ProgressScope aPS(theRange, "Reading sub tree", 2, true); Message_ProgressScope aPS(theRange, "Reading sub tree", 2, true);
bool aSkipAttrs = Standard_False;
if (!theFilter.IsNull() && theFilter->IsPartTree())
aSkipAttrs = !theFilter->IsPassed();
if (theQuickPart)
{
uint64_t aLabelSize = 0;
theIS.read((char*)&aLabelSize, sizeof(uint64_t));
#if DO_INVERSE
aLabelSize = InverseUint64(aLabelSize);
#endif
// no one sub-label is needed, so, skip everything
if (aSkipAttrs && !theFilter->IsSubPassed())
{
aLabelSize -= sizeof (uint64_t);
theIS.seekg (aLabelSize, std::ios_base::cur);
if (!theFilter.IsNull())
theFilter->Up();
return 0;
}
}
// Read attributes: // Read attributes:
theIS >> myPAtt; for (theIS >> myPAtt;
while (theIS && myPAtt.TypeId() > 0 && // not an end marker ? theIS && myPAtt.TypeId() > 0 && // not an end marker ?
myPAtt.Id() > 0 && // not a garbage ? myPAtt.Id() > 0 && // not a garbage ?
!theIS.eof()) !theIS.eof();
theIS >> myPAtt)
{ {
if (!aPS.More()) if (!aPS.More())
{ {
myReaderStatus = PCDM_RS_UserBreak; myReaderStatus = PCDM_RS_UserBreak;
return -1; return -1;
} }
if (aSkipAttrs)
{
if (myPAtt.IsDirect()) // skip direct written stream
{
uint64_t aStreamSize = 0;
theIS.read ((char*)&aStreamSize, sizeof (uint64_t));
aStreamSize -= sizeof (uint64_t); // size is already passed, so, reduce it by size
theIS.seekg (aStreamSize, std::ios_base::cur);
}
continue;
}
// get a driver according to TypeId // get a driver according to TypeId
Handle(BinMDF_ADriver) aDriver = myDrivers->GetDriver (myPAtt.TypeId()); Handle(BinMDF_ADriver) aDriver = myDrivers->GetDriver(myPAtt.TypeId());
if (!aDriver.IsNull()) { if (!aDriver.IsNull()) {
// create transient attribute // create transient attribute
nbRead++;
Standard_Integer anID = myPAtt.Id(); Standard_Integer anID = myPAtt.Id();
Handle(TDF_Attribute) tAtt; Handle(TDF_Attribute) tAtt;
Standard_Boolean isBound = myRelocTable.IsBound(anID); Standard_Boolean isBound = myRelocTable.IsBound(anID);
@ -391,11 +440,30 @@ Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree
else else
tAtt = aDriver->NewEmpty(); tAtt = aDriver->NewEmpty();
if (!theFilter.IsNull() && !theFilter->IsPassed (tAtt->DynamicType())) {
if (myPAtt.IsDirect()) // skip direct written stream
{
uint64_t aStreamSize = 0;
theIS.read ((char*)&aStreamSize, sizeof (uint64_t));
aStreamSize -= sizeof (uint64_t); // size is already passed, so, reduce it by size
theIS.seekg (aStreamSize, std::ios_base::cur);
}
continue;
}
nbRead++;
if (tAtt->Label().IsNull()) if (tAtt->Label().IsNull())
{ {
if (!theFilter.IsNull() && theFilter->Mode() != PCDM_ReaderFilter::AppendMode_Forbid && theLabel.IsAttribute(tAtt->ID()))
{
if (theFilter->Mode() == PCDM_ReaderFilter::AppendMode_Protect)
continue; // do not overwrite the existing attribute
if (theFilter->Mode() == PCDM_ReaderFilter::AppendMode_Overwrite)
theLabel.ForgetAttribute(tAtt->ID()); // forget old attribute to write a new one
}
try try
{ {
theLabel.AddAttribute (tAtt); theLabel.AddAttribute(tAtt);
} }
catch (const Standard_DomainError&) catch (const Standard_DomainError&)
{ {
@ -404,34 +472,32 @@ Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree
// present on the same label; the reason is that actual GUID will be read later. // present on the same label; the reason is that actual GUID will be read later.
// To avoid this, set invalid (null) GUID to the newly added attribute (see #29669) // To avoid this, set invalid (null) GUID to the newly added attribute (see #29669)
static const Standard_GUID fbidGuid; static const Standard_GUID fbidGuid;
tAtt->SetID (fbidGuid); tAtt->SetID(fbidGuid);
theLabel.AddAttribute (tAtt); theLabel.AddAttribute(tAtt);
} }
} }
else else
myMsgDriver->Send (aMethStr + myMsgDriver->Send(aMethStr +
"warning: attempt to attach attribute " + "warning: attempt to attach attribute " +
aDriver->TypeName() + " to a second label", Message_Warning); aDriver->TypeName() + " to a second label", Message_Warning);
Standard_Boolean ok = aDriver->Paste (myPAtt, tAtt, myRelocTable); Standard_Boolean ok = aDriver->Paste(myPAtt, tAtt, myRelocTable);
if (!ok) { if (!ok) {
// error converting persistent to transient // error converting persistent to transient
myMsgDriver->Send (aMethStr + "warning: failure reading attribute " + myMsgDriver->Send(aMethStr + "warning: failure reading attribute " +
aDriver->TypeName(), Message_Warning); aDriver->TypeName(), Message_Warning);
} }
else if (!isBound) else if (!isBound)
myRelocTable.Bind (anID, tAtt); myRelocTable.Bind(anID, tAtt);
} }
else if (!myMapUnsupported.Contains(myPAtt.TypeId())) else if (!myMapUnsupported.Contains(myPAtt.TypeId()))
myMsgDriver->Send (aMethStr + "warning: type ID not registered in header: " myMsgDriver->Send(aMethStr + "warning: type ID not registered in header: "
+ myPAtt.TypeId(), Message_Warning); + myPAtt.TypeId(), Message_Warning);
// read next attribute
theIS >> myPAtt;
} }
if (!theIS || myPAtt.TypeId() != BinLDrivers_ENDATTRLIST) { if (!theIS || myPAtt.TypeId() != BinLDrivers_ENDATTRLIST) {
// unexpected EOF or garbage data // unexpected EOF or garbage data
myMsgDriver->Send (aMethStr + "error: unexpected EOF or garbage data", Message_Fail); myMsgDriver->Send(aMethStr + "error: unexpected EOF or garbage data", Message_Fail);
myReaderStatus = PCDM_RS_UnrecognizedFileFormat; myReaderStatus = PCDM_RS_UnrecognizedFileFormat;
return -1; return -1;
} }
@ -439,14 +505,14 @@ Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree
// Read children: // Read children:
// read the tag of a child label // read the tag of a child label
Standard_Integer aTag = BinLDrivers_ENDLABEL; Standard_Integer aTag = BinLDrivers_ENDLABEL;
theIS.read ((char*) &aTag, sizeof(Standard_Integer)); theIS.read((char*)&aTag, sizeof(Standard_Integer));
#ifdef DO_INVERSE #ifdef DO_INVERSE
aTag = InverseInt (aTag); aTag = InverseInt(aTag);
#endif #endif
while (theIS && aTag >= 0 && !theIS.eof()) { // not an end marker ? while (theIS && aTag >= 0 && !theIS.eof()) { // not an end marker ?
// create sub-label // create sub-label
TDF_Label aLab = theLabel.FindChild (aTag, Standard_True); TDF_Label aLab = theLabel.FindChild(aTag, Standard_True);
if (!aPS.More()) if (!aPS.More())
{ {
myReaderStatus = PCDM_RS_UserBreak; myReaderStatus = PCDM_RS_UserBreak;
@ -455,25 +521,29 @@ Standard_Integer BinLDrivers_DocumentRetrievalDriver::ReadSubTree
// read sub-tree // read sub-tree
Standard_Integer nbSubRead = ReadSubTree (theIS, aLab, aPS.Next()); if (!theFilter.IsNull())
theFilter->Down (aTag);
Standard_Integer nbSubRead = ReadSubTree (theIS, aLab, theFilter, theQuickPart, aPS.Next());
// check for error // check for error
if (nbSubRead == -1) if (nbSubRead == -1)
return -1; return -1;
nbRead += nbSubRead; nbRead += nbSubRead;
// read the tag of the next child // read the tag of the next child
theIS.read ((char*) &aTag, sizeof(Standard_Integer)); theIS.read((char*)&aTag, sizeof(Standard_Integer));
#ifdef DO_INVERSE #ifdef DO_INVERSE
aTag = InverseInt (aTag); aTag = InverseInt(aTag);
#endif #endif
} }
if (aTag != BinLDrivers_ENDLABEL) { if (aTag != BinLDrivers_ENDLABEL) {
// invalid end label marker // invalid end label marker
myMsgDriver->Send (aMethStr + "error: invalid end label marker", Message_Fail); myMsgDriver->Send(aMethStr + "error: invalid end label marker", Message_Fail);
myReaderStatus = PCDM_RS_UnrecognizedFileFormat; myReaderStatus = PCDM_RS_UnrecognizedFileFormat;
return -1; return -1;
} }
if (!theFilter.IsNull())
theFilter->Up();
return nbRead; return nbRead;
} }
@ -524,13 +594,12 @@ void BinLDrivers_DocumentRetrievalDriver::ReadShapeSection
//function : CheckShapeSection //function : CheckShapeSection
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinLDrivers_DocumentRetrievalDriver::CheckShapeSection( void BinLDrivers_DocumentRetrievalDriver::CheckShapeSection
const Storage_Position& ShapeSectionPos, (const Storage_Position& ShapeSectionPos, Standard_IStream& IS)
Standard_IStream& IS)
{ {
if (!IS.eof()) if (!IS.eof())
{ {
const std::streamoff endPos = IS.rdbuf()->pubseekoff(0L, std::ios_base::end, std::ios_base::in); const std::streamoff endPos = IS.rdbuf()->pubseekoff (0L, std::ios_base::end, std::ios_base::in);
#ifdef OCCT_DEBUG #ifdef OCCT_DEBUG
std::cout << "endPos = " << endPos <<std::endl; std::cout << "endPos = " << endPos <<std::endl;
#endif #endif
@ -556,9 +625,8 @@ void BinLDrivers_DocumentRetrievalDriver::Clear()
//function : CheckDocumentVersion //function : CheckDocumentVersion
//purpose : //purpose :
//======================================================================= //=======================================================================
Standard_Boolean BinLDrivers_DocumentRetrievalDriver::CheckDocumentVersion( Standard_Boolean BinLDrivers_DocumentRetrievalDriver::CheckDocumentVersion
const Standard_Integer theFileVersion, (const Standard_Integer theFileVersion, const Standard_Integer theCurVersion)
const Standard_Integer theCurVersion)
{ {
if (theFileVersion < TDocStd_FormatVersion_LOWER || theFileVersion > theCurVersion) { if (theFileVersion < TDocStd_FormatVersion_LOWER || theFileVersion > theCurVersion) {
// file was written with another version // file was written with another version
@ -566,3 +634,12 @@ Standard_Boolean BinLDrivers_DocumentRetrievalDriver::CheckDocumentVersion(
} }
return Standard_True; return Standard_True;
} }
//=======================================================================
//function : IsQuickPart
//purpose :
//=======================================================================
Standard_Boolean BinLDrivers_DocumentRetrievalDriver::IsQuickPart (const Standard_Integer theFileVer)
{
return theFileVer >= TDocStd_FormatVersion_VERSION_12;
}

View File

@ -59,12 +59,14 @@ public:
Standard_EXPORT virtual void Read (const TCollection_ExtendedString& theFileName, Standard_EXPORT virtual void Read (const TCollection_ExtendedString& theFileName,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theProgress = Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theProgress = Message_ProgressRange()) Standard_OVERRIDE;
Standard_EXPORT virtual void Read (Standard_IStream& theIStream, Standard_EXPORT virtual void Read (Standard_IStream& theIStream,
const Handle(Storage_Data)& theStorageData, const Handle(Storage_Data)& theStorageData,
const Handle(CDM_Document)& theDoc, const Handle(CDM_Document)& theDoc,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theProgress = Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theProgress = Message_ProgressRange()) Standard_OVERRIDE;
Standard_EXPORT virtual Handle(BinMDF_ADriverTable) AttributeDrivers (const Handle(Message_Messenger)& theMsgDriver); Standard_EXPORT virtual Handle(BinMDF_ADriverTable) AttributeDrivers (const Handle(Message_Messenger)& theMsgDriver);
@ -81,6 +83,8 @@ protected:
Standard_EXPORT virtual Standard_Integer ReadSubTree Standard_EXPORT virtual Standard_Integer ReadSubTree
(Standard_IStream& theIS, (Standard_IStream& theIS,
const TDF_Label& theData, const TDF_Label& theData,
const Handle(PCDM_ReaderFilter)& theFilter,
const Standard_Boolean& theQuickPart,
const Message_ProgressRange& theRanges = Message_ProgressRange()); const Message_ProgressRange& theRanges = Message_ProgressRange());
@ -110,6 +114,12 @@ protected:
//! current or lesser than 2, then return false, else true //! current or lesser than 2, then return false, else true
Standard_EXPORT virtual Standard_Boolean CheckDocumentVersion (const Standard_Integer theFileVersion, const Standard_Integer theCurVersion); Standard_EXPORT virtual Standard_Boolean CheckDocumentVersion (const Standard_Integer theFileVersion, const Standard_Integer theCurVersion);
//! Return true if retrieved document allows to read parts quickly.
static Standard_Boolean IsQuickPart (const Standard_Integer theFileVer);
//! Enables reading in the quick part access mode.
Standard_EXPORT virtual void EnableQuickPartReading (const Handle(Message_Messenger)& /*theMessageDriver*/, Standard_Boolean /*theValue*/) {}
Handle(BinMDF_ADriverTable) myDrivers; Handle(BinMDF_ADriverTable) myDrivers;
BinObjMgt_RRelocationTable myRelocTable; BinObjMgt_RRelocationTable myRelocTable;
Handle(Message_Messenger) myMsgDriver; Handle(Message_Messenger) myMsgDriver;

View File

@ -228,6 +228,7 @@ void BinLDrivers_DocumentSection::ReadTOC
#endif #endif
if (aNameBufferSize > 0) { if (aNameBufferSize > 0) {
theStream.read ((char *)&aBuf[0], (Standard_Size)aNameBufferSize); theStream.read ((char *)&aBuf[0], (Standard_Size)aNameBufferSize);
aBuf[aNameBufferSize] = '\0';
theSection.myName = (Standard_CString)&aBuf[0]; theSection.myName = (Standard_CString)&aBuf[0];
uint64_t aValue[3]; uint64_t aValue[3];

View File

@ -21,6 +21,7 @@
#include <BinMDF_ADriver.hxx> #include <BinMDF_ADriver.hxx>
#include <BinMDF_ADriverTable.hxx> #include <BinMDF_ADriverTable.hxx>
#include <BinObjMgt_Persistent.hxx> #include <BinObjMgt_Persistent.hxx>
#include <BinObjMgt_Position.hxx>
#include <CDM_Application.hxx> #include <CDM_Application.hxx>
#include <CDM_Document.hxx> #include <CDM_Document.hxx>
#include <Message_Messenger.hxx> #include <Message_Messenger.hxx>
@ -47,13 +48,14 @@
IMPLEMENT_STANDARD_RTTIEXT(BinLDrivers_DocumentStorageDriver,PCDM_StorageDriver) IMPLEMENT_STANDARD_RTTIEXT(BinLDrivers_DocumentStorageDriver,PCDM_StorageDriver)
#define SHAPESECTION_POS (Standard_CString)"SHAPE_SECTION_POS:" #define SHAPESECTION_POS (Standard_CString)"SHAPE_SECTION_POS:"
#define ENDSECTION_POS (Standard_CString)":"
//======================================================================= //=======================================================================
//function : BinLDrivers_DocumentStorageDriver //function : BinLDrivers_DocumentStorageDriver
//purpose : Constructor //purpose : Constructor
//======================================================================= //=======================================================================
BinLDrivers_DocumentStorageDriver::BinLDrivers_DocumentStorageDriver () BinLDrivers_DocumentStorageDriver::BinLDrivers_DocumentStorageDriver()
{ {
} }
@ -97,9 +99,9 @@ void BinLDrivers_DocumentStorageDriver::Write (const Handle(CDM_Document)& theD
{ {
myMsgDriver = theDoc->Application()->MessageDriver(); myMsgDriver = theDoc->Application()->MessageDriver();
myMapUnsupported.Clear(); myMapUnsupported.Clear();
mySizesToWrite.Clear();
Handle(TDocStd_Document) aDoc = Handle(TDocStd_Document) aDoc = Handle(TDocStd_Document)::DownCast (theDoc);
Handle(TDocStd_Document)::DownCast(theDoc);
if (aDoc.IsNull()) { if (aDoc.IsNull()) {
SetIsError(Standard_True); SetIsError(Standard_True);
SetStoreStatus(PCDM_SS_Doc_IsNull); SetStoreStatus(PCDM_SS_Doc_IsNull);
@ -129,20 +131,33 @@ void BinLDrivers_DocumentStorageDriver::Write (const Handle(CDM_Document)& theD
for (; anIterS.More(); anIterS.Next()) for (; anIterS.More(); anIterS.Next())
anIterS.ChangeValue().WriteTOC (theOStream, aDocVer); anIterS.ChangeValue().WriteTOC (theOStream, aDocVer);
EnableQuickPartWriting (myMsgDriver, IsQuickPart (aDocVer));
BinLDrivers_DocumentSection* aShapesSection = 0;
Standard_Boolean aQuickPart = IsQuickPart (aDocVer);
if (!aQuickPart)
{
// Shapes Section is the last one, it indicates the end of the table. // Shapes Section is the last one, it indicates the end of the table.
BinLDrivers_DocumentSection aShapesSection (SHAPESECTION_POS, aShapesSection = new BinLDrivers_DocumentSection (SHAPESECTION_POS, Standard_False);
Standard_False); aShapesSection->WriteTOC (theOStream, aDocVer);
aShapesSection.WriteTOC (theOStream, aDocVer); }
else
{
// End Section is the last one, it indicates the end of the table.
BinLDrivers_DocumentSection anEndSection (ENDSECTION_POS, Standard_False);
anEndSection.WriteTOC (theOStream, aDocVer);
}
// 3. Write document contents // 3. Write document contents
// (Storage data to the stream) // (Storage data to the stream)
myRelocTable.Clear(); myRelocTable.Clear();
myPAtt.Init(); myPAtt.Init();
if (aQuickPart)
myPAtt.SetOStream (theOStream); // for writing shapes data into the stream directly
Message_ProgressScope aPS(theRange, "Writing document", 3); Message_ProgressScope aPS(theRange, "Writing document", 3);
// Write Doc structure // Write Doc structure
WriteSubTree (aData->Root(), theOStream, aPS.Next()); // Doc is written WriteSubTree (aData->Root(), theOStream, aQuickPart, aPS.Next()); // Doc is written
if (!aPS.More()) if (!aPS.More())
{ {
SetIsError(Standard_True); SetIsError(Standard_True);
@ -151,11 +166,18 @@ void BinLDrivers_DocumentStorageDriver::Write (const Handle(CDM_Document)& theD
} }
// 4. Write Shapes section // 4. Write Shapes section
WriteShapeSection (aShapesSection, theOStream, aDocVer, aPS.Next()); if (!aQuickPart)
{
WriteShapeSection (*aShapesSection, theOStream, aDocVer, aPS.Next());
delete aShapesSection;
}
else
Clear();
if (!aPS.More()) if (!aPS.More())
{ {
SetIsError(Standard_True); SetIsError (Standard_True);
SetStoreStatus(PCDM_SS_UserBreak); SetStoreStatus (PCDM_SS_UserBreak);
return; return;
} }
@ -167,6 +189,10 @@ void BinLDrivers_DocumentStorageDriver::Write (const Handle(CDM_Document)& theD
aSection.Write (theOStream, aSectionOffset, aDocVer); aSection.Write (theOStream, aSectionOffset, aDocVer);
} }
// 5. Write sizes along the file where it is needed for quick part mode
if (aQuickPart)
WriteSizes (theOStream);
// End of processing: close structures and check the status // End of processing: close structures and check the status
myPAtt.Destroy(); // free buffer myPAtt.Destroy(); // free buffer
myEmptyLabels.Clear(); myEmptyLabels.Clear();
@ -211,7 +237,7 @@ void BinLDrivers_DocumentStorageDriver::UnsupportedAttrMsg
{ {
#ifdef OCCT_DEBUG #ifdef OCCT_DEBUG
TCollection_ExtendedString aMsg TCollection_ExtendedString aMsg
("BinDrivers_DocumentStorageDriver: warning: attribute driver for type "); ("BinLDrivers_DocumentStorageDriver: warning: attribute driver for type ");
#endif #endif
if (!myMapUnsupported.Contains(theType)) { if (!myMapUnsupported.Contains(theType)) {
myMapUnsupported.Add(theType); myMapUnsupported.Add(theType);
@ -229,6 +255,7 @@ void BinLDrivers_DocumentStorageDriver::UnsupportedAttrMsg
void BinLDrivers_DocumentStorageDriver::WriteSubTree void BinLDrivers_DocumentStorageDriver::WriteSubTree
(const TDF_Label& theLabel, (const TDF_Label& theLabel,
Standard_OStream& theOS, Standard_OStream& theOS,
const Standard_Boolean& theQuickPart,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
// Skip empty labels // Skip empty labels
@ -244,6 +271,13 @@ void BinLDrivers_DocumentStorageDriver::WriteSubTree
#endif #endif
theOS.write ((char*)&aTag, sizeof(Standard_Integer)); theOS.write ((char*)&aTag, sizeof(Standard_Integer));
Handle(BinObjMgt_Position) aPosition;
if (theQuickPart)
{
aPosition = mySizesToWrite.Append (new BinObjMgt_Position (theOS));
aPosition->WriteSize (theOS, Standard_True);
}
// Write attributes // Write attributes
TDF_AttributeIterator itAtt (theLabel); TDF_AttributeIterator itAtt (theLabel);
for ( ; itAtt.More() && theOS && aPS.More(); itAtt.Next()) { for ( ; itAtt.More() && theOS && aPS.More(); itAtt.Next()) {
@ -251,7 +285,7 @@ void BinLDrivers_DocumentStorageDriver::WriteSubTree
const Handle(Standard_Type)& aType = tAtt->DynamicType(); const Handle(Standard_Type)& aType = tAtt->DynamicType();
// Get type ID and driver // Get type ID and driver
Handle(BinMDF_ADriver) aDriver; Handle(BinMDF_ADriver) aDriver;
const Standard_Integer aTypeId = myDrivers->GetDriver (aType,aDriver); const Standard_Integer aTypeId = myDrivers->GetDriver (aType, aDriver);
if (aTypeId > 0) { if (aTypeId > 0) {
// Add source to relocation table // Add source to relocation table
const Standard_Integer anId = myRelocTable.Add (tAtt); const Standard_Integer anId = myRelocTable.Add (tAtt);
@ -260,6 +294,12 @@ void BinLDrivers_DocumentStorageDriver::WriteSubTree
myPAtt.SetTypeId (aTypeId); myPAtt.SetTypeId (aTypeId);
myPAtt.SetId (anId); myPAtt.SetId (anId);
aDriver->Paste (tAtt, myPAtt, myRelocTable); aDriver->Paste (tAtt, myPAtt, myRelocTable);
if (!myPAtt.StreamStart().IsNull())
{
Handle(BinObjMgt_Position) anAttrPosition = myPAtt.StreamStart();
anAttrPosition->StoreSize (theOS);
mySizesToWrite.Append (anAttrPosition);
}
// Write data to the stream -->!!! // Write data to the stream -->!!!
theOS << myPAtt; theOS << myPAtt;
@ -297,16 +337,16 @@ void BinLDrivers_DocumentStorageDriver::WriteSubTree
SetStoreStatus(PCDM_SS_UserBreak); SetStoreStatus(PCDM_SS_UserBreak);
return; return;
} }
WriteSubTree (aChildLab, theOS, aPS.Next()); WriteSubTree (aChildLab, theOS, theQuickPart, aPS.Next());
} }
// Write the end label marker // Write the end label marker
BinLDrivers_Marker anEndLabel = BinLDrivers_ENDLABEL; BinLDrivers_Marker anEndLabel = BinLDrivers_ENDLABEL;
#ifdef DO_INVERSE #ifdef DO_INVERSE
anEndLabel = (BinLDrivers_Marker) InverseInt (anEndLabel); anEndLabel = (BinLDrivers_Marker)InverseInt (anEndLabel);
#endif #endif
theOS.write ((char*)&anEndLabel, sizeof(anEndLabel)); theOS.write ((char*)&anEndLabel, sizeof (anEndLabel));
if (theQuickPart)
aPosition->StoreSize (theOS);
} }
//======================================================================= //=======================================================================
@ -553,3 +593,34 @@ void BinLDrivers_DocumentStorageDriver::WriteShapeSection
const Standard_Size aShapesSectionOffset = (Standard_Size) theOS.tellp(); const Standard_Size aShapesSectionOffset = (Standard_Size) theOS.tellp();
theSection.Write (theOS, aShapesSectionOffset, theDocVer); theSection.Write (theOS, aShapesSectionOffset, theDocVer);
} }
//=======================================================================
//function : IsQuickPart
//purpose : Return true if document should be stored in quick mode for partial reading
//=======================================================================
Standard_Boolean BinLDrivers_DocumentStorageDriver::IsQuickPart (const Standard_Integer theVersion) const
{
return theVersion >= TDocStd_FormatVersion_VERSION_12;
}
//=======================================================================
//function : Clear
//purpose :
//=======================================================================
void BinLDrivers_DocumentStorageDriver::Clear()
{
// empty; should be redefined in subclasses
}
//=======================================================================
//function : WriteSizes
//purpose :
//=======================================================================
void BinLDrivers_DocumentStorageDriver::WriteSizes (Standard_OStream& theOS)
{
NCollection_List<Handle(BinObjMgt_Position)>::Iterator anIter (mySizesToWrite);
for (; anIter.More() && theOS; anIter.Next())
anIter.Value()->WriteSize (theOS);
mySizesToWrite.Clear();
}

View File

@ -37,6 +37,7 @@ class CDM_Document;
class TDF_Label; class TDF_Label;
class TCollection_AsciiString; class TCollection_AsciiString;
class BinLDrivers_DocumentSection; class BinLDrivers_DocumentSection;
class BinObjMgt_Position;
class BinLDrivers_DocumentStorageDriver; class BinLDrivers_DocumentStorageDriver;
@ -67,7 +68,8 @@ public:
//! Create a section that should be written after the OCAF data //! Create a section that should be written after the OCAF data
Standard_EXPORT void AddSection (const TCollection_AsciiString& theName, const Standard_Boolean isPostRead = Standard_True); Standard_EXPORT void AddSection (const TCollection_AsciiString& theName, const Standard_Boolean isPostRead = Standard_True);
//! Return true if document should be stored in quick mode for partial reading
Standard_EXPORT Standard_Boolean IsQuickPart (const Standard_Integer theVersion) const;
DEFINE_STANDARD_RTTIEXT(BinLDrivers_DocumentStorageDriver,PCDM_StorageDriver) DEFINE_STANDARD_RTTIEXT(BinLDrivers_DocumentStorageDriver,PCDM_StorageDriver)
@ -78,6 +80,7 @@ protected:
//! Write the tree under <theLabel> to the stream <theOS> //! Write the tree under <theLabel> to the stream <theOS>
Standard_EXPORT void WriteSubTree (const TDF_Label& theData, Standard_EXPORT void WriteSubTree (const TDF_Label& theData,
Standard_OStream& theOS, Standard_OStream& theOS,
const Standard_Boolean& theQuickPart,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! define the procedure of writing a section to file. //! define the procedure of writing a section to file.
@ -91,6 +94,13 @@ protected:
const TDocStd_FormatVersion theDocVer, const TDocStd_FormatVersion theDocVer,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Enables writing in the quick part access mode.
Standard_EXPORT virtual void EnableQuickPartWriting (
const Handle(Message_Messenger)& /*theMessageDriver*/, const Standard_Boolean /*theValue*/) {}
//! clears the writing-cash data in drivers if any.
Standard_EXPORT virtual void Clear();
Handle(BinMDF_ADriverTable) myDrivers; Handle(BinMDF_ADriverTable) myDrivers;
BinObjMgt_SRelocationTable myRelocTable; BinObjMgt_SRelocationTable myRelocTable;
Handle(Message_Messenger) myMsgDriver; Handle(Message_Messenger) myMsgDriver;
@ -108,13 +118,17 @@ private:
Standard_EXPORT void UnsupportedAttrMsg (const Handle(Standard_Type)& theType); Standard_EXPORT void UnsupportedAttrMsg (const Handle(Standard_Type)& theType);
//! Writes sizes along the file where it is needed for quick part mode
Standard_EXPORT void WriteSizes (Standard_OStream& theOS);
BinObjMgt_Persistent myPAtt; BinObjMgt_Persistent myPAtt;
TDF_LabelList myEmptyLabels; TDF_LabelList myEmptyLabels;
TColStd_MapOfTransient myMapUnsupported; TColStd_MapOfTransient myMapUnsupported;
TColStd_IndexedMapOfTransient myTypesMap; TColStd_IndexedMapOfTransient myTypesMap;
BinLDrivers_VectorOfDocumentSection mySections; BinLDrivers_VectorOfDocumentSection mySections;
TCollection_ExtendedString myFileName; TCollection_ExtendedString myFileName;
//! Sizes of labels and some attributes that will be stored in the second pass
NCollection_List<Handle(BinObjMgt_Position)> mySizesToWrite;
}; };
#endif // _BinLDrivers_DocumentStorageDriver_HeaderFile #endif // _BinLDrivers_DocumentStorageDriver_HeaderFile

View File

@ -18,6 +18,8 @@
#include <BinObjMgt_Persistent.hxx> #include <BinObjMgt_Persistent.hxx>
#include <BinTools_LocationSet.hxx> #include <BinTools_LocationSet.hxx>
#include <BinTools_ShapeSet.hxx> #include <BinTools_ShapeSet.hxx>
#include <BinTools_ShapeWriter.hxx>
#include <BinTools_ShapeReader.hxx>
#include <Message_Messenger.hxx> #include <Message_Messenger.hxx>
#include <Standard_DomainError.hxx> #include <Standard_DomainError.hxx>
#include <Standard_Type.hxx> #include <Standard_Type.hxx>
@ -36,7 +38,7 @@ IMPLEMENT_STANDARD_RTTIEXT(BinMNaming_NamedShapeDriver,BinMDF_ADriver)
#define SHAPESET "SHAPE_SECTION" #define SHAPESET "SHAPE_SECTION"
//======================================================================= //=======================================================================
static Standard_Character EvolutionToChar(const TNaming_Evolution theEvol) static Standard_Character EvolutionToChar (const TNaming_Evolution theEvol)
{ {
switch(theEvol) { switch(theEvol) {
case TNaming_PRIMITIVE : return 'P'; case TNaming_PRIMITIVE : return 'P';
@ -51,7 +53,7 @@ static Standard_Character EvolutionToChar(const TNaming_Evolution theEvol)
} }
//======================================================================= //=======================================================================
static TNaming_Evolution EvolutionToEnum(const Standard_Character theEvol) static TNaming_Evolution EvolutionToEnum (const Standard_Character theEvol)
{ {
switch(theEvol) { switch(theEvol) {
case 'P': return TNaming_PRIMITIVE; case 'P': return TNaming_PRIMITIVE;
@ -65,7 +67,7 @@ static TNaming_Evolution EvolutionToEnum(const Standard_Character theEvol)
} }
} }
//======================================================================= //=======================================================================
static Standard_Character OrientationToChar(const TopAbs_Orientation theOrient) static Standard_Character OrientationToChar (const TopAbs_Orientation theOrient)
{ {
switch(theOrient) { switch(theOrient) {
case TopAbs_FORWARD : return 'F'; case TopAbs_FORWARD : return 'F';
@ -77,7 +79,7 @@ static Standard_Character OrientationToChar(const TopAbs_Orientation theOrient)
} }
} }
//======================================================================= //=======================================================================
static TopAbs_Orientation CharToOrientation(const Standard_Character theCharOrient) static TopAbs_Orientation CharToOrientation (const Standard_Character theCharOrient)
{ {
switch(theCharOrient) { switch(theCharOrient) {
case 'F': return TopAbs_FORWARD; case 'F': return TopAbs_FORWARD;
@ -92,45 +94,45 @@ static TopAbs_Orientation CharToOrientation(const Standard_Character theCharOri
//======================================================================= //=======================================================================
static void TranslateTo (const TopoDS_Shape& theShape, static void TranslateTo (const TopoDS_Shape& theShape,
BinObjMgt_Persistent& theResult, BinObjMgt_Persistent& theResult,
BinTools_ShapeSet& theShapeSet) BinTools_ShapeSet* theShapeSet)
{ {
// Check for empty shape // Check for empty shape
if (theShape.IsNull()) { if (theShape.IsNull()) {
theResult.PutInteger(-1); theResult.PutInteger (-1);
theResult.PutInteger(-1); theResult.PutInteger (-1);
theResult.PutInteger(-1); theResult.PutInteger (-1);
return; return;
} }
// Add to shape set both TShape and Location contained in <theShape> // Add to shape set both TShape and Location contained in <theShape>
const Standard_Integer aTShapeID = theShapeSet.Add (theShape); const Standard_Integer aTShapeID = theShapeSet->Add (theShape);
const Standard_Integer aLocID = const Standard_Integer aLocID =
theShapeSet.Locations().Index (theShape.Location()); theShapeSet->Locations().Index (theShape.Location());
// Fill theResult with shape parameters: TShape ID, Location, Orientation // Fill theResult with shape parameters: TShape ID, Location, Orientation
theResult << aTShapeID; theResult << aTShapeID;
theResult << aLocID; theResult << aLocID;
theResult << OrientationToChar(theShape.Orientation()); theResult << OrientationToChar (theShape.Orientation());
} }
//======================================================================= //=======================================================================
static int TranslateFrom (const BinObjMgt_Persistent& theSource, static int TranslateFrom (const BinObjMgt_Persistent& theSource,
TopoDS_Shape& theResult, TopoDS_Shape& theResult,
BinTools_ShapeSet& theShapeSet) BinTools_ShapeSet* theShapeSet)
{ {
Standard_Integer aShapeID, aLocID; Standard_Integer aShapeID, aLocID;
Standard_Character aCharOrient; Standard_Character aCharOrient;
Standard_Boolean Ok = theSource >> aShapeID; //TShapeID; Standard_Boolean Ok = theSource >> aShapeID; //TShapeID;
if(!Ok) return 1; if(!Ok) return 1;
// Read TShape and Orientation // Read TShape and Orientation
if (aShapeID <= 0 || aShapeID > theShapeSet.NbShapes()) if (aShapeID <= 0 || aShapeID > theShapeSet->NbShapes())
return 1; return 1;
Ok = theSource >> aLocID; Ok = theSource >> aLocID;
if(!Ok) return 1; if(!Ok) return 1;
Ok = theSource >> aCharOrient; Ok = theSource >> aCharOrient;
if(!Ok) return 1; if(!Ok) return 1;
TopAbs_Orientation anOrient = CharToOrientation(aCharOrient); TopAbs_Orientation anOrient = CharToOrientation (aCharOrient);
theResult.TShape (theShapeSet.Shape(aShapeID).TShape());//TShape theResult.TShape (theShapeSet->Shape (aShapeID).TShape());//TShape
theResult.Location (theShapeSet.Locations().Location (aLocID)); //Location theResult.Location (theShapeSet->Locations().Location (aLocID)); //Location
theResult.Orientation (anOrient);//Orientation theResult.Orientation (anOrient);//Orientation
return 0; return 0;
} }
@ -142,7 +144,11 @@ static int TranslateFrom (const BinObjMgt_Persistent& theSource,
BinMNaming_NamedShapeDriver::BinMNaming_NamedShapeDriver BinMNaming_NamedShapeDriver::BinMNaming_NamedShapeDriver
(const Handle(Message_Messenger)& theMsgDriver) (const Handle(Message_Messenger)& theMsgDriver)
: BinMDF_ADriver (theMsgDriver, STANDARD_TYPE(TNaming_NamedShape)->Name()) : BinMDF_ADriver (theMsgDriver, STANDARD_TYPE(TNaming_NamedShape)->Name()),
myShapeSet (NULL),
myWithTriangles (Standard_False),
myWithNormals (Standard_False),
myIsQuickPart (Standard_False)
{ {
} }
@ -166,7 +172,7 @@ Standard_Boolean BinMNaming_NamedShapeDriver::Paste
const Handle(TDF_Attribute)& theTarget, const Handle(TDF_Attribute)& theTarget,
BinObjMgt_RRelocationTable& ) const BinObjMgt_RRelocationTable& ) const
{ {
Handle(TNaming_NamedShape) aTAtt= Handle(TNaming_NamedShape)::DownCast(theTarget); Handle(TNaming_NamedShape) aTAtt= Handle(TNaming_NamedShape)::DownCast (theTarget);
Standard_Integer aNbShapes; Standard_Integer aNbShapes;
theSource >> aNbShapes; theSource >> aNbShapes;
TDF_Label aLabel = theTarget->Label (); TDF_Label aLabel = theTarget->Label ();
@ -178,10 +184,13 @@ Standard_Boolean BinMNaming_NamedShapeDriver::Paste
Standard_Character aCharEvol; Standard_Character aCharEvol;
ok = theSource >> aCharEvol; ok = theSource >> aCharEvol;
if(!ok) return Standard_False; if(!ok) return Standard_False;
TNaming_Evolution anEvol = EvolutionToEnum(aCharEvol); //Evolution TNaming_Evolution anEvol = EvolutionToEnum (aCharEvol); //Evolution
aTAtt->SetVersion(anEvol); aTAtt->SetVersion (anEvol);
BinTools_ShapeSet& aShapeSet = (BinTools_ShapeSet&) myShapeSet; BinTools_ShapeSetBase* aShapeSet = const_cast<BinMNaming_NamedShapeDriver*>(this)->ShapeSet (Standard_True);
Standard_IStream* aDirectStream = NULL;
if (myIsQuickPart) // enables direct reading of shapes from the stream
aDirectStream = const_cast<BinObjMgt_Persistent*>(&theSource)->GetIStream();
NCollection_List<TopoDS_Shape> anOldShapes, aNewShapes; NCollection_List<TopoDS_Shape> anOldShapes, aNewShapes;
for (Standard_Integer i = 1; i <= aNbShapes; i++) for (Standard_Integer i = 1; i <= aNbShapes; i++)
@ -189,10 +198,20 @@ Standard_Boolean BinMNaming_NamedShapeDriver::Paste
TopoDS_Shape anOldShape, aNewShape; TopoDS_Shape anOldShape, aNewShape;
if (anEvol != TNaming_PRIMITIVE) if (anEvol != TNaming_PRIMITIVE)
if (TranslateFrom (theSource, anOldShape, aShapeSet)) return Standard_False; {
if (myIsQuickPart)
aShapeSet->Read (*aDirectStream, anOldShape);
else
if (TranslateFrom (theSource, anOldShape, static_cast<BinTools_ShapeSet*>(aShapeSet))) return Standard_False;
}
if (anEvol != TNaming_DELETE) if (anEvol != TNaming_DELETE)
if (TranslateFrom (theSource, aNewShape, aShapeSet)) return Standard_False; {
if (myIsQuickPart)
aShapeSet->Read (*aDirectStream, aNewShape);
else
if (TranslateFrom (theSource, aNewShape, static_cast<BinTools_ShapeSet*>(aShapeSet))) return Standard_False;
}
// Here we add shapes in reverse order because TNaming_Builder also adds them in reverse order. // Here we add shapes in reverse order because TNaming_Builder also adds them in reverse order.
anOldShapes.Prepend (anOldShape); anOldShapes.Prepend (anOldShape);
@ -246,24 +265,38 @@ void BinMNaming_NamedShapeDriver::Paste (const Handle(TDF_Attribute)& theSource,
for (TNaming_Iterator SItr (aSAtt); SItr.More (); SItr.Next ()) NbShapes++; for (TNaming_Iterator SItr (aSAtt); SItr.More (); SItr.Next ()) NbShapes++;
//-------------------------------------------------------------- //--------------------------------------------------------------
BinTools_ShapeSet& aShapeSet = (BinTools_ShapeSet&) myShapeSet; BinTools_ShapeSetBase* aShapeSet = const_cast<BinMNaming_NamedShapeDriver*>(this)->ShapeSet (Standard_False);
TNaming_Evolution anEvol = aSAtt->Evolution(); TNaming_Evolution anEvol = aSAtt->Evolution();
theTarget << NbShapes; theTarget << NbShapes;
theTarget << aSAtt->Version(); theTarget << aSAtt->Version();
theTarget << EvolutionToChar(anEvol); theTarget << EvolutionToChar (anEvol);
Standard_OStream* aDirectStream = NULL;
if (myIsQuickPart) // enables direct writing of shapes to the stream
aDirectStream = theTarget.GetOStream();
Standard_Integer i = 1; Standard_Integer i = 1;
for (TNaming_Iterator SIterator(aSAtt) ;SIterator.More(); SIterator.Next()) { for (TNaming_Iterator SIterator(aSAtt); SIterator.More(); SIterator.Next()) {
const TopoDS_Shape& OldShape = SIterator.OldShape(); const TopoDS_Shape& anOldShape = SIterator.OldShape();
const TopoDS_Shape& NewShape = SIterator.NewShape(); const TopoDS_Shape& aNewShape = SIterator.NewShape();
if ( anEvol != TNaming_PRIMITIVE ) if (anEvol != TNaming_PRIMITIVE)
TranslateTo (OldShape, theTarget, aShapeSet); {
if (myIsQuickPart)
aShapeSet->Write (anOldShape, *aDirectStream);
else
TranslateTo (anOldShape, theTarget, static_cast<BinTools_ShapeSet*>(aShapeSet));
}
if (anEvol != TNaming_DELETE) if (anEvol != TNaming_DELETE)
TranslateTo (NewShape, theTarget, aShapeSet); {
if (myIsQuickPart)
aShapeSet->Write (aNewShape, *aDirectStream);
else
TranslateTo (aNewShape, theTarget, static_cast<BinTools_ShapeSet*>(aShapeSet));
}
i++; i++;
} }
@ -280,18 +313,18 @@ void BinMNaming_NamedShapeDriver::WriteShapeSection (Standard_OStream& theOS,
const Standard_Integer theDocVer, const Standard_Integer theDocVer,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
myIsQuickPart = Standard_False;
theOS << SHAPESET; theOS << SHAPESET;
if (theDocVer >= TDocStd_FormatVersion_VERSION_11) if (theDocVer >= TDocStd_FormatVersion_VERSION_11)
{ {
myShapeSet.SetFormatNb(BinTools_FormatVersion_VERSION_4); ShapeSet (Standard_False)->SetFormatNb (BinTools_FormatVersion_VERSION_4);
} }
else else
{ {
myShapeSet.SetFormatNb(BinTools_FormatVersion_VERSION_1); ShapeSet (Standard_False)->SetFormatNb (BinTools_FormatVersion_VERSION_1);
} }
ShapeSet (Standard_False)->Write (theOS, theRange);
myShapeSet.Write (theOS, theRange); ShapeSet (Standard_False)->Clear();
myShapeSet.Clear();
} }
//======================================================================= //=======================================================================
@ -301,7 +334,12 @@ void BinMNaming_NamedShapeDriver::WriteShapeSection (Standard_OStream& theOS,
void BinMNaming_NamedShapeDriver::Clear() void BinMNaming_NamedShapeDriver::Clear()
{ {
myShapeSet.Clear(); if (myShapeSet)
{
myShapeSet->Clear();
delete myShapeSet;
myShapeSet = NULL;
}
} }
//======================================================================= //=======================================================================
@ -312,15 +350,51 @@ void BinMNaming_NamedShapeDriver::Clear()
void BinMNaming_NamedShapeDriver::ReadShapeSection (Standard_IStream& theIS, void BinMNaming_NamedShapeDriver::ReadShapeSection (Standard_IStream& theIS,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
myIsQuickPart = Standard_False;
// check section title string; note that some versions of OCCT (up to 6.3.1) // check section title string; note that some versions of OCCT (up to 6.3.1)
// might avoid writing shape section if it is empty // might avoid writing shape section if it is empty
std::streamoff aPos = theIS.tellg(); std::streamoff aPos = theIS.tellg();
TCollection_AsciiString aSectionTitle; TCollection_AsciiString aSectionTitle;
theIS >> aSectionTitle; theIS >> aSectionTitle;
if(aSectionTitle.Length() > 0 && aSectionTitle == SHAPESET) { if(aSectionTitle.Length() > 0 && aSectionTitle == SHAPESET) {
myShapeSet.Clear(); BinTools_ShapeSetBase* aShapeSet = ShapeSet (Standard_True);
myShapeSet.Read (theIS, theRange); aShapeSet->Clear();
aShapeSet->Read (theIS, theRange);
} }
else else
theIS.seekg(aPos); // no shape section is present, try to return to initial point theIS.seekg (aPos); // no shape section is present, try to return to initial point
}
//=======================================================================
//function : ShapeSet
//purpose :
//=======================================================================
BinTools_ShapeSetBase* BinMNaming_NamedShapeDriver::ShapeSet (const Standard_Boolean theReading)
{
if (!myShapeSet)
{
if (myIsQuickPart)
{
if (theReading)
myShapeSet = new BinTools_ShapeReader();
else
myShapeSet = new BinTools_ShapeWriter();
}
else
myShapeSet = new BinTools_ShapeSet();
myShapeSet->SetWithTriangles(myWithTriangles);
myShapeSet->SetWithNormals(myWithNormals);
}
return myShapeSet;
}
//=======================================================================
//function : GetShapesLocations
//purpose :
//=======================================================================
BinTools_LocationSet& BinMNaming_NamedShapeDriver::GetShapesLocations() const
{
BinTools_ShapeSetBase* aShapeSet = const_cast<BinMNaming_NamedShapeDriver*>(this)->ShapeSet (Standard_False);
return static_cast<BinTools_ShapeSet*>(aShapeSet)->ChangeLocations();
} }

View File

@ -64,33 +64,35 @@ public:
Standard_EXPORT void Clear(); Standard_EXPORT void Clear();
//! Return true if shape should be stored with triangles. //! Return true if shape should be stored with triangles.
Standard_Boolean IsWithTriangles() const { return myShapeSet.IsWithTriangles(); } Standard_Boolean IsWithTriangles() const { return myWithTriangles; }
//! Return true if shape should be stored with triangulation normals. //! Return true if shape should be stored with triangulation normals.
Standard_Boolean IsWithNormals() const { return myShapeSet.IsWithNormals(); } Standard_Boolean IsWithNormals() const { return myWithNormals; }
//! set whether to store triangulation //! set whether to store triangulation
void SetWithTriangles (const Standard_Boolean isWithTriangles) { myShapeSet.SetWithTriangles(isWithTriangles); } void SetWithTriangles (const Standard_Boolean isWithTriangles);
//! set whether to store triangulation with normals //! set whether to store triangulation with normals
void SetWithNormals (const Standard_Boolean isWithNormals) { myShapeSet.SetWithNormals(isWithNormals); } void SetWithNormals (const Standard_Boolean isWithNormals);
//! get the shapes locations //! get the shapes locations
BinTools_LocationSet& GetShapesLocations(); Standard_EXPORT BinTools_LocationSet& GetShapesLocations() const;
//! Sets the flag for quick part of the document access: shapes are stored in the attribute.
Standard_EXPORT void EnableQuickPart(const Standard_Boolean theValue) { myIsQuickPart = theValue; }
//! Returns true if quick part of the document access is enabled: shapes are stored in the attribute.
Standard_EXPORT Standard_Boolean IsQuickPart() { return myIsQuickPart; }
//! Returns shape-set of the needed type
Standard_EXPORT BinTools_ShapeSetBase* ShapeSet (const Standard_Boolean theReading);
DEFINE_STANDARD_RTTIEXT(BinMNaming_NamedShapeDriver,BinMDF_ADriver) DEFINE_STANDARD_RTTIEXT(BinMNaming_NamedShapeDriver,BinMDF_ADriver)
protected:
private: private:
BinTools_ShapeSet myShapeSet; BinTools_ShapeSetBase *myShapeSet;
Standard_Boolean myWithTriangles;
Standard_Boolean myWithNormals;
//! Enables storing of whole shape data just in the attribute, not in a separated shapes section
Standard_Boolean myIsQuickPart;
}; };

View File

@ -13,13 +13,27 @@
// Alternatively, this file may be used under the terms of Open CASCADE // Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement. // commercial license or contractual agreement.
//======================================================================= //=======================================================================
//function : GetShapesLocations //function : SetWithTriangles
//purpose : //purpose :
//======================================================================= //=======================================================================
inline BinTools_LocationSet& BinMNaming_NamedShapeDriver::GetShapesLocations()
inline void BinMNaming_NamedShapeDriver::SetWithTriangles(const Standard_Boolean isWithTriangles)
{ {
return myShapeSet.ChangeLocations(); myWithTriangles = isWithTriangles;
if (myShapeSet)
myShapeSet->SetWithTriangles (isWithTriangles);
} }
//=======================================================================
//function : SetWithNormals
//purpose :
//=======================================================================
inline void BinMNaming_NamedShapeDriver::SetWithNormals(const Standard_Boolean isWithNormals)
{
myWithNormals = isWithNormals;
if (myShapeSet)
myShapeSet->SetWithNormals (isWithNormals);
}

View File

@ -51,9 +51,9 @@ void BinMXCAFDoc::AddDrivers(const Handle(BinMDF_ADriverTable)& theDriverTable,
Handle(BinMNaming_NamedShapeDriver)::DownCast (aNSDriver); Handle(BinMNaming_NamedShapeDriver)::DownCast (aNSDriver);
Handle(BinMXCAFDoc_LocationDriver) aLocationDriver = new BinMXCAFDoc_LocationDriver (theMsgDrv); Handle(BinMXCAFDoc_LocationDriver) aLocationDriver = new BinMXCAFDoc_LocationDriver (theMsgDrv);
if( !aNamedShapeDriver.IsNull() ) if (!aNamedShapeDriver.IsNull())
{ {
aLocationDriver->SetSharedLocations( &(aNamedShapeDriver->GetShapesLocations()) ); aLocationDriver->SetNSDriver (aNamedShapeDriver);
} }
theDriverTable->AddDriver( aLocationDriver); theDriverTable->AddDriver( aLocationDriver);

View File

@ -18,6 +18,8 @@
#include <BinMXCAFDoc_LocationDriver.hxx> #include <BinMXCAFDoc_LocationDriver.hxx>
#include <BinObjMgt_Persistent.hxx> #include <BinObjMgt_Persistent.hxx>
#include <BinTools_LocationSet.hxx> #include <BinTools_LocationSet.hxx>
#include <BinTools_ShapeReader.hxx>
#include <BinTools_ShapeWriter.hxx>
#include <Message_Messenger.hxx> #include <Message_Messenger.hxx>
#include <gp_Mat.hxx> #include <gp_Mat.hxx>
#include <gp_Trsf.hxx> #include <gp_Trsf.hxx>
@ -37,7 +39,7 @@ IMPLEMENT_STANDARD_RTTIEXT(BinMXCAFDoc_LocationDriver,BinMDF_ADriver)
//======================================================================= //=======================================================================
BinMXCAFDoc_LocationDriver::BinMXCAFDoc_LocationDriver(const Handle(Message_Messenger)& theMsgDriver) BinMXCAFDoc_LocationDriver::BinMXCAFDoc_LocationDriver(const Handle(Message_Messenger)& theMsgDriver)
: BinMDF_ADriver(theMsgDriver, STANDARD_TYPE(XCAFDoc_Location)->Name()) : BinMDF_ADriver(theMsgDriver, STANDARD_TYPE(XCAFDoc_Location)->Name())
, myLocations(0) { {
} }
//======================================================================= //=======================================================================
@ -84,6 +86,14 @@ Standard_Boolean BinMXCAFDoc_LocationDriver::Translate(const BinObjMgt_Persisten
TopLoc_Location& theLoc, TopLoc_Location& theLoc,
BinObjMgt_RRelocationTable& theMap) const BinObjMgt_RRelocationTable& theMap) const
{ {
if (!myNSDriver.IsNull() && myNSDriver->IsQuickPart())
{
BinTools_IStream aDirectStream (*(const_cast<BinObjMgt_Persistent*>(&theSource)->GetIStream()));
BinTools_ShapeReader* aReader = static_cast<BinTools_ShapeReader*>(myNSDriver->ShapeSet (Standard_True));
theLoc = *(aReader->ReadLocation (aDirectStream));
return Standard_True;
}
Standard_Integer anId = 0; Standard_Integer anId = 0;
theSource >> anId; theSource >> anId;
@ -92,18 +102,24 @@ Standard_Boolean BinMXCAFDoc_LocationDriver::Translate(const BinObjMgt_Persisten
return Standard_True; return Standard_True;
} }
if (!myNSDriver.IsNull() && myNSDriver->IsQuickPart())
{ // read directly from the stream
}
Standard_Integer aFileVer = theMap.GetHeaderData()->StorageVersion().IntegerValue(); Standard_Integer aFileVer = theMap.GetHeaderData()->StorageVersion().IntegerValue();
if( aFileVer >= TDocStd_FormatVersion_VERSION_6 && myLocations == 0 ) if( aFileVer >= TDocStd_FormatVersion_VERSION_6 && myNSDriver.IsNull() )
{ {
return Standard_False; return Standard_False;
} }
Standard_Integer aPower; Standard_Integer aPower (0);
Handle(TopLoc_Datum3D) aDatum; Handle(TopLoc_Datum3D) aDatum;
if( aFileVer >= TDocStd_FormatVersion_VERSION_6) if (aFileVer >= TDocStd_FormatVersion_VERSION_6)
{ {
const TopLoc_Location& aLoc = myLocations->Location(anId); const TopLoc_Location& aLoc = myNSDriver->GetShapesLocations().Location (anId);
aPower = aLoc.FirstPower(); aPower = aLoc.FirstPower();
aDatum = aLoc.FirstDatum(); aDatum = aLoc.FirstDatum();
} else { } else {
@ -168,22 +184,30 @@ void BinMXCAFDoc_LocationDriver::Translate(const TopLoc_Location& theLoc,
BinObjMgt_Persistent& theTarget, BinObjMgt_Persistent& theTarget,
BinObjMgt_SRelocationTable& theMap) const BinObjMgt_SRelocationTable& theMap) const
{ {
if(theLoc.IsIdentity()) if (!myNSDriver.IsNull() && myNSDriver->IsQuickPart())
{ // write directly to the stream
Standard_OStream* aDirectStream = theTarget.GetOStream();
BinTools_ShapeWriter* aWriter = static_cast<BinTools_ShapeWriter*>(myNSDriver->ShapeSet (Standard_False));
BinTools_OStream aStream(*aDirectStream);
aWriter->WriteLocation (aStream, theLoc);
return;
}
if (theLoc.IsIdentity())
{ {
theTarget.PutInteger(0); theTarget.PutInteger(0);
return; return;
} }
// The location is not identity // The location is not identity
if( myLocations == 0 ) if (myNSDriver.IsNull())
{ {
#ifdef OCCT_DEBUG #ifdef OCCT_DEBUG
std::cout<<"Pointer to LocationSet is NULL\n"; std::cout << "NamedShape Driver is NULL\n";
#endif #endif
return; return;
} }
Standard_Integer anId = myLocations->Add(theLoc); Standard_Integer anId = myNSDriver->GetShapesLocations().Add (theLoc);
theTarget << anId; theTarget << anId;
// In earlier version of this driver a datums from location stored in // In earlier version of this driver a datums from location stored in

View File

@ -19,7 +19,7 @@
#include <Standard.hxx> #include <Standard.hxx>
#include <Standard_Type.hxx> #include <Standard_Type.hxx>
#include <BinTools_LocationSetPtr.hxx> #include <BinMNaming_NamedShapeDriver.hxx>
#include <BinMDF_ADriver.hxx> #include <BinMDF_ADriver.hxx>
#include <Standard_Boolean.hxx> #include <Standard_Boolean.hxx>
#include <BinObjMgt_RRelocationTable.hxx> #include <BinObjMgt_RRelocationTable.hxx>
@ -53,7 +53,7 @@ public:
//! Translate transient location to storable //! Translate transient location to storable
Standard_EXPORT void Translate (const TopLoc_Location& theLoc, BinObjMgt_Persistent& theTarget, BinObjMgt_SRelocationTable& theMap) const; Standard_EXPORT void Translate (const TopLoc_Location& theLoc, BinObjMgt_Persistent& theTarget, BinObjMgt_SRelocationTable& theMap) const;
void SetSharedLocations (const BinTools_LocationSetPtr& theLocations); void SetNSDriver (const Handle(BinMNaming_NamedShapeDriver)& theNSDriver) { myNSDriver = theNSDriver; }
@ -68,16 +68,10 @@ protected:
private: private:
BinTools_LocationSetPtr myLocations; Handle(BinMNaming_NamedShapeDriver) myNSDriver;
}; };
#include <BinMXCAFDoc_LocationDriver.lxx>
#endif // _BinMXCAFDoc_LocationDriver_HeaderFile #endif // _BinMXCAFDoc_LocationDriver_HeaderFile

View File

@ -1,26 +0,0 @@
// Created on: 2011-02-08
// Created by: Oleg AGASHIN
// Copyright (c) 2011-2014 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
//=======================================================================
//function : SetSharedLocations
//purpose :
//=======================================================================
inline void BinMXCAFDoc_LocationDriver::SetSharedLocations(const BinTools_LocationSetPtr& theLocations)
{
if( myLocations != theLocations )
{
myLocations = theLocations;
}
}

View File

@ -14,7 +14,6 @@ BinMXCAFDoc_GraphNodeDriver.cxx
BinMXCAFDoc_GraphNodeDriver.hxx BinMXCAFDoc_GraphNodeDriver.hxx
BinMXCAFDoc_LocationDriver.cxx BinMXCAFDoc_LocationDriver.cxx
BinMXCAFDoc_LocationDriver.hxx BinMXCAFDoc_LocationDriver.hxx
BinMXCAFDoc_LocationDriver.lxx
BinMXCAFDoc_MaterialDriver.cxx BinMXCAFDoc_MaterialDriver.cxx
BinMXCAFDoc_MaterialDriver.hxx BinMXCAFDoc_MaterialDriver.hxx
BinMXCAFDoc_NoteDriver.cxx BinMXCAFDoc_NoteDriver.cxx

View File

@ -15,6 +15,7 @@
#include <BinObjMgt_Persistent.hxx> #include <BinObjMgt_Persistent.hxx>
#include <BinObjMgt_Position.hxx>
#include <FSD_FileHeader.hxx> #include <FSD_FileHeader.hxx>
#include <Standard_GUID.hxx> #include <Standard_GUID.hxx>
#include <TCollection_AsciiString.hxx> #include <TCollection_AsciiString.hxx>
@ -52,7 +53,10 @@ BinObjMgt_Persistent::BinObjMgt_Persistent ()
: myIndex (1), : myIndex (1),
myOffset(BP_HEADSIZE), myOffset(BP_HEADSIZE),
mySize (BP_HEADSIZE), mySize (BP_HEADSIZE),
myIsError (Standard_False) myIsError (Standard_False),
myOStream (NULL),
myIStream (NULL),
myDirectWritingIsEnabled (Standard_False)
{ {
Init(); Init();
} }
@ -76,6 +80,7 @@ void BinObjMgt_Persistent::Init ()
myOffset = BP_HEADSIZE; myOffset = BP_HEADSIZE;
mySize = BP_HEADSIZE; mySize = BP_HEADSIZE;
myIsError = Standard_False; myIsError = Standard_False;
myDirectWritingIsEnabled = Standard_False;
} }
//======================================================================= //=======================================================================
@ -85,13 +90,20 @@ void BinObjMgt_Persistent::Init ()
// const BinObjMgt_Persistent&) is also available // const BinObjMgt_Persistent&) is also available
//======================================================================= //=======================================================================
Standard_OStream& BinObjMgt_Persistent::Write (Standard_OStream& theOS) Standard_OStream& BinObjMgt_Persistent::Write (Standard_OStream& theOS, const Standard_Boolean theDirectStream)
{ {
if (myDirectWritingIsEnabled)
{ // if direct writing was enabled, everything is already written, just pass this stage
myDirectWritingIsEnabled = Standard_False;
return theOS;
}
Standard_Integer nbWritten = 0; Standard_Integer nbWritten = 0;
Standard_Integer *aData = (Standard_Integer*) myData(1); Standard_Integer *aData = (Standard_Integer*) myData(1);
// update data length // update data length
aData[2] = mySize - BP_HEADSIZE; aData[2] = mySize - BP_HEADSIZE;
#ifdef DO_INVERSE if (theDirectStream)
aData[1] = -aData[1];
#if DO_INVERSE
aData[0] = InverseInt (aData[0]); aData[0] = InverseInt (aData[0]);
aData[1] = InverseInt (aData[1]); aData[1] = InverseInt (aData[1]);
aData[2] = InverseInt (aData[2]); aData[2] = InverseInt (aData[2]);
@ -141,7 +153,10 @@ Standard_IStream& BinObjMgt_Persistent::Read (Standard_IStream& theIS)
aData[1] = InverseInt (aData[1]); aData[1] = InverseInt (aData[1]);
aData[2] = InverseInt (aData[2]); aData[2] = InverseInt (aData[2]);
#endif #endif
if (theIS && aData[1] > 0 && aData[2] > 0) { myDirectWritingIsEnabled = aData[1] < 0;
if (myDirectWritingIsEnabled)
aData[1] = -aData[1];
if (theIS && aData[2] > 0) {
mySize += aData[2]; mySize += aData[2];
// read remaining data // read remaining data
Standard_Integer nbRead = BP_HEADSIZE; Standard_Integer nbRead = BP_HEADSIZE;
@ -1164,3 +1179,28 @@ void BinObjMgt_Persistent::inverseShortRealData
} }
} }
} }
//=======================================================================
//function : GetOStream
//purpose : Gets the stream for and enables direct writing
//=======================================================================
Standard_OStream* BinObjMgt_Persistent::GetOStream()
{
Write (*myOStream, Standard_True); // finishes already stored data save
myStreamStart = new BinObjMgt_Position (*myOStream);
myStreamStart->WriteSize (*myOStream, Standard_True);
myDirectWritingIsEnabled = Standard_True;
return myOStream;
}
//=======================================================================
//function : GetOStream
//purpose : Gets the stream for and enables direct writing
//=======================================================================
Standard_IStream* BinObjMgt_Persistent::GetIStream()
{
// skip the stream size first
myIStream->seekg (sizeof (uint64_t), std::ios_base::cur);
return myIStream;
}

View File

@ -35,6 +35,7 @@
#include <BinObjMgt_PInteger.hxx> #include <BinObjMgt_PInteger.hxx>
#include <BinObjMgt_PReal.hxx> #include <BinObjMgt_PReal.hxx>
#include <BinObjMgt_PShortReal.hxx> #include <BinObjMgt_PShortReal.hxx>
#include <BinObjMgt_Position.hxx>
#include <Standard_OStream.hxx> #include <Standard_OStream.hxx>
#include <Standard_IStream.hxx> #include <Standard_IStream.hxx>
#include <Standard_Address.hxx> #include <Standard_Address.hxx>
@ -261,13 +262,13 @@ const BinObjMgt_Persistent& operator >> (Standard_GUID& theValue) const
//! Indicates an error after Get methods or SetPosition //! Indicates an error after Get methods or SetPosition
Standard_Boolean IsError() const; Standard_Boolean IsError() const;
Standard_Boolean operator !() const Standard_Boolean operator !() const
{ {
return IsError(); return IsError();
} }
//! Indicates a good state after Get methods or SetPosition //! Indicates a good state after Get methods or SetPosition
Standard_Boolean IsOK() const; Standard_Boolean IsOK() const;
operator Standard_Boolean () const { return IsOK(); } operator Standard_Boolean () const { return IsOK(); }
//! Initializes me to reuse again //! Initializes me to reuse again
Standard_EXPORT void Init(); Standard_EXPORT void Init();
@ -289,8 +290,9 @@ operator Standard_Boolean () const { return IsOK(); }
//! Stores <me> to the stream. //! Stores <me> to the stream.
//! inline Standard_OStream& operator<< (Standard_OStream&, //! inline Standard_OStream& operator<< (Standard_OStream&,
//! BinObjMgt_Persistent&) is also available //! BinObjMgt_Persistent&) is also available.
Standard_EXPORT Standard_OStream& Write (Standard_OStream& theOS); //! If theDirectStream is true, after this data the direct stream data is stored.
Standard_EXPORT Standard_OStream& Write (Standard_OStream& theOS, const Standard_Boolean theDirectStream = Standard_False);
//! Retrieves <me> from the stream. //! Retrieves <me> from the stream.
//! inline Standard_IStream& operator>> (Standard_IStream&, //! inline Standard_IStream& operator>> (Standard_IStream&,
@ -300,19 +302,23 @@ operator Standard_Boolean () const { return IsOK(); }
//! Frees the allocated memory; //! Frees the allocated memory;
//! This object can be reused after call to Init //! This object can be reused after call to Init
Standard_EXPORT void Destroy(); Standard_EXPORT void Destroy();
~BinObjMgt_Persistent() ~BinObjMgt_Persistent()
{ {
Destroy(); Destroy();
} }
protected:
//! Sets the stream for direct writing
Standard_EXPORT void SetOStream (Standard_OStream& theStream) { myOStream = &theStream; }
//! Sets the stream for direct reading
Standard_EXPORT void SetIStream (Standard_IStream& theStream) { myIStream = &theStream; }
//! Gets the stream for and enables direct writing
Standard_EXPORT Standard_OStream* GetOStream();
//! Gets the stream for and enables direct reading
Standard_EXPORT Standard_IStream* GetIStream();
//! Returns true if after this record a direct writing to the stream is performed.
Standard_EXPORT Standard_Boolean IsDirect() { return myDirectWritingIsEnabled; }
//! Returns the start position of the direct writing in the stream
Standard_EXPORT Handle(BinObjMgt_Position) StreamStart() { return myStreamStart; }
private: private:
@ -358,8 +364,10 @@ private:
Standard_Integer myOffset; Standard_Integer myOffset;
Standard_Integer mySize; Standard_Integer mySize;
Standard_Boolean myIsError; Standard_Boolean myIsError;
Standard_OStream* myOStream; ///< stream to write in case direct writing is enabled
Standard_IStream* myIStream; ///< stream to write in case direct reading is enabled
Standard_Boolean myDirectWritingIsEnabled;
Handle(BinObjMgt_Position) myStreamStart; ///< position where the direct writing to the script is started
}; };

View File

@ -34,6 +34,7 @@ inline void BinObjMgt_Persistent::SetId (const Standard_Integer theId)
inline void BinObjMgt_Persistent::SetTypeId (const Standard_Integer theTypeId) inline void BinObjMgt_Persistent::SetTypeId (const Standard_Integer theTypeId)
{ {
((Standard_Integer*) myData(1)) [0] = theTypeId; ((Standard_Integer*) myData(1)) [0] = theTypeId;
myStreamStart.Nullify();
} }
//======================================================================= //=======================================================================

View File

@ -0,0 +1,48 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <BinObjMgt_Position.hxx>
IMPLEMENT_STANDARD_RTTIEXT (BinObjMgt_Position, Standard_Transient)
//=======================================================================
//function : BinObjMgt_Position
//purpose :
//=======================================================================
BinObjMgt_Position::BinObjMgt_Position (Standard_OStream& theStream) :
myPosition (theStream.tellp()), mySize(0)
{}
//=======================================================================
//function : StoreSize
//purpose :
//=======================================================================
void BinObjMgt_Position::StoreSize (Standard_OStream& theStream)
{
mySize = uint64_t (theStream.tellp() - myPosition);
}
//=======================================================================
//function : WriteSize
//purpose :
//=======================================================================
void BinObjMgt_Position::WriteSize (Standard_OStream& theStream, const Standard_Boolean theDummy)
{
if (!theDummy && theStream.tellp() != myPosition)
theStream.seekp (myPosition);
uint64_t aSize = theDummy ? 0 : mySize;
#if DO_INVERSE
aSize = FSD_BinaryFile::InverseUint64 (aSize);
#endif
theStream.write ((char*)&aSize, sizeof (uint64_t));
}

View File

@ -0,0 +1,45 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinObjMgt_Position_HeaderFile
#define _BinObjMgt_Position_HeaderFile
#include <Standard_Type.hxx>
class BinObjMgt_Position;
DEFINE_STANDARD_HANDLE (BinObjMgt_Position, Standard_Transient)
//! Stores and manipulates position in the stream.
class BinObjMgt_Position : public Standard_Transient
{
public:
DEFINE_STANDARD_ALLOC
//! Creates position using the current stream position.
Standard_EXPORT BinObjMgt_Position (Standard_OStream& theStream);
//! Stores the difference between the current position and the stored one.
Standard_EXPORT void StoreSize (Standard_OStream& theStream);
//! Writes stored size at the stored position. Changes the current stream position.
//! If theDummy is true, is writes to the current position zero size.
Standard_EXPORT void WriteSize (Standard_OStream& theStream, const Standard_Boolean theDummy = Standard_False);
DEFINE_STANDARD_RTTIEXT (BinObjMgt_Position, Standard_Transient)
private:
std::streampos myPosition;
uint64_t mySize;
};
#endif // _BinObjMgt_Position_HeaderFile

View File

@ -5,6 +5,8 @@ BinObjMgt_Persistent.hxx
BinObjMgt_Persistent.lxx BinObjMgt_Persistent.lxx
BinObjMgt_PExtChar.hxx BinObjMgt_PExtChar.hxx
BinObjMgt_PInteger.hxx BinObjMgt_PInteger.hxx
BinObjMgt_Position.cxx
BinObjMgt_Position.hxx
BinObjMgt_PReal.hxx BinObjMgt_PReal.hxx
BinObjMgt_PShortReal.hxx BinObjMgt_PShortReal.hxx
BinObjMgt_RRelocationTable.cxx BinObjMgt_RRelocationTable.cxx

View File

@ -42,7 +42,7 @@ Standard_OStream& BinTools::PutInteger(Standard_OStream& OS, const Standard_Inte
#ifdef DO_INVERSE #ifdef DO_INVERSE
anIntValue = InverseInt (aValue); anIntValue = InverseInt (aValue);
#endif #endif
OS.write((char*)&anIntValue, sizeof(Standard_Integer)); OS.write ((char*)&anIntValue, sizeof (Standard_Integer));
return OS; return OS;
} }
@ -56,9 +56,9 @@ Standard_OStream& BinTools::PutReal (Standard_OStream& theOS,
{ {
#ifdef DO_INVERSE #ifdef DO_INVERSE
const Standard_Real aRValue = InverseReal (theValue); const Standard_Real aRValue = InverseReal (theValue);
theOS.write((char*)&aRValue, sizeof(Standard_Real)); theOS.write ((char*)&aRValue, sizeof (Standard_Real));
#else #else
theOS.write((char*)&theValue, sizeof(Standard_Real)); theOS.write ((char*)&theValue, sizeof (Standard_Real));
#endif #endif
return theOS; return theOS;
} }
@ -200,7 +200,7 @@ void BinTools::Read (TopoDS_Shape& theShape, Standard_IStream& theStream,
BinTools_ShapeSet aShapeSet; BinTools_ShapeSet aShapeSet;
aShapeSet.SetWithTriangles(Standard_True); aShapeSet.SetWithTriangles(Standard_True);
aShapeSet.Read (theStream, theRange); aShapeSet.Read (theStream, theRange);
aShapeSet.Read (theShape, theStream, aShapeSet.NbShapes()); aShapeSet.ReadSubs (theShape, theStream, aShapeSet.NbShapes());
} }
//======================================================================= //=======================================================================

View File

@ -105,35 +105,12 @@ Standard_Integer BinTools_Curve2dSet::Index
return myMap.FindIndex(S); return myMap.FindIndex(S);
} }
//=======================================================================
//function : operator << (gp_Pnt2d)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Pnt2d P)
{
BinTools::PutReal(OS, P.X());
return BinTools::PutReal(OS, P.Y());
}
//=======================================================================
//function : operator << (gp_Dir2d D)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Dir2d D)
{
BinTools::PutReal(OS, D.X());
return BinTools::PutReal(OS, D.Y());
}
//======================================================================= //=======================================================================
//function : operator << ((Geom2d_Line)& L) //function : operator << ((Geom2d_Line)& L)
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_Line)& L) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_Line)& L)
{ {
OS << (Standard_Byte)LINE; OS << (Standard_Byte)LINE;
@ -148,14 +125,14 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_L
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_Circle)& C) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_Circle)& C)
{ {
OS << (Standard_Byte)CIRCLE; OS << (Standard_Byte)CIRCLE;
gp_Circ2d C2d = C->Circ2d(); gp_Circ2d C2d = C->Circ2d();
OS << C2d.Location(); OS << C2d.Location();
OS << C2d.XAxis().Direction(); OS << C2d.XAxis().Direction();
OS << C2d.YAxis().Direction(); OS << C2d.YAxis().Direction();
BinTools::PutReal(OS, C2d.Radius()); OS << C2d.Radius();
return OS; return OS;
} }
@ -164,15 +141,15 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_C
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_Ellipse)& E) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_Ellipse)& E)
{ {
OS << (Standard_Byte)ELLIPSE; OS << (Standard_Byte)ELLIPSE;
gp_Elips2d C2d = E->Elips2d(); gp_Elips2d C2d = E->Elips2d();
OS << C2d.Location(); OS << C2d.Location();
OS << C2d.XAxis().Direction(); OS << C2d.XAxis().Direction();
OS << C2d.YAxis().Direction(); OS << C2d.YAxis().Direction();
BinTools::PutReal(OS, C2d.MajorRadius()); OS << C2d.MajorRadius();
BinTools::PutReal(OS, C2d.MinorRadius()); OS << C2d.MinorRadius();
return OS; return OS;
} }
@ -181,14 +158,14 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_E
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_Parabola)& P) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_Parabola)& P)
{ {
OS << (Standard_Byte)PARABOLA; OS << (Standard_Byte)PARABOLA;
gp_Parab2d C2d = P->Parab2d(); gp_Parab2d C2d = P->Parab2d();
OS << C2d.Location();//Loc OS << C2d.Location(); // Loc
OS << C2d.Axis().XAxis().Direction();//XDir OS << C2d.Axis().XAxis().Direction(); // XDir
OS << C2d.Axis().YAxis().Direction();//YDir OS << C2d.Axis().YAxis().Direction(); // YDir
BinTools::PutReal(OS, C2d.Focal());//Focal OS << C2d.Focal(); // Focal
return OS; return OS;
} }
@ -197,15 +174,15 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_P
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_Hyperbola)& H) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_Hyperbola)& H)
{ {
OS << (Standard_Byte)HYPERBOLA; OS << (Standard_Byte)HYPERBOLA;
gp_Hypr2d C2d = H->Hypr2d(); gp_Hypr2d C2d = H->Hypr2d();
OS << C2d.Location(); //Loc OS << C2d.Location(); // Loc
OS << C2d.XAxis().Direction();//XDir OS << C2d.XAxis().Direction(); // XDir
OS << C2d.YAxis().Direction();//YDir OS << C2d.YAxis().Direction(); // YDir
BinTools::PutReal(OS, C2d.MajorRadius());//MajR OS << C2d.MajorRadius(); // MajR
BinTools::PutReal(OS, C2d.MinorRadius()); OS << C2d.MinorRadius();
return OS; return OS;
} }
@ -214,18 +191,18 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_H
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_BezierCurve)& B) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_BezierCurve)& B)
{ {
OS << (Standard_Byte)BEZIER; OS << (Standard_Byte)BEZIER;
Standard_Boolean aRational = B->IsRational() ? 1:0; Standard_Boolean aRational = B->IsRational() ? 1:0;
BinTools::PutBool(OS, aRational); //rational OS << aRational; // rational
// poles and weights // poles and weights
Standard_Integer i,aDegree = B->Degree(); Standard_Integer i,aDegree = B->Degree();
BinTools::PutExtChar(OS, (Standard_ExtCharacter)aDegree); //Degree OS << (Standard_ExtCharacter)aDegree; // Degree
for (i = 1; i <= aDegree+1; i++) { for (i = 1; i <= aDegree+1; i++) {
OS << B->Pole(i); //Pnt2d OS << B->Pole(i); // Pnt2d
if (aRational) if (aRational)
BinTools::PutReal(OS, B->Weight(i));//Real OS << B->Weight(i); // Real
} }
return OS; return OS;
} }
@ -235,30 +212,30 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_B
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_BSplineCurve)& B) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_BSplineCurve)& B)
{ {
OS << (Standard_Byte)BSPLINE; OS << (Standard_Byte)BSPLINE;
Standard_Boolean aRational = B->IsRational() ? 1:0; Standard_Boolean aRational = B->IsRational() ? 1:0;
BinTools::PutBool(OS, aRational); //rational OS << aRational; //rational
Standard_Boolean aPeriodic = B->IsPeriodic() ? 1:0; Standard_Boolean aPeriodic = B->IsPeriodic() ? 1:0;
BinTools::PutBool(OS, aPeriodic); //periodic OS << aPeriodic; //periodic
// poles and weights // poles and weights
Standard_Integer i,aDegree,aNbPoles,aNbKnots; Standard_Integer i,aDegree,aNbPoles,aNbKnots;
aDegree = B->Degree(); aDegree = B->Degree();
aNbPoles = B->NbPoles(); aNbPoles = B->NbPoles();
aNbKnots = B->NbKnots(); aNbKnots = B->NbKnots();
BinTools::PutExtChar(OS, (Standard_ExtCharacter) aDegree); OS << (Standard_ExtCharacter) aDegree;
BinTools::PutInteger(OS, aNbPoles); OS << aNbPoles;
BinTools::PutInteger(OS, aNbKnots); OS << aNbKnots;
for (i = 1; i <= aNbPoles; i++) { for (i = 1; i <= aNbPoles; i++) {
OS << B->Pole(i); // Pnt2d OS << B->Pole(i); // Pnt2d
if (aRational) if (aRational)
BinTools::PutReal(OS, B->Weight(i)); OS << B->Weight(i);
} }
for (i = 1; i <= aNbKnots; i++) { for (i = 1; i <= aNbKnots; i++) {
BinTools::PutReal(OS, B->Knot(i)); OS << B->Knot(i);
BinTools::PutInteger(OS, B->Multiplicity(i)); OS << B->Multiplicity(i);
} }
return OS; return OS;
@ -269,12 +246,12 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_B
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_TrimmedCurve)& C) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_TrimmedCurve)& C)
{ {
OS << (Standard_Byte)TRIMMED; OS << (Standard_Byte)TRIMMED;
BinTools::PutReal(OS, C->FirstParameter()); OS << C->FirstParameter();
BinTools::PutReal(OS, C->LastParameter()); OS << C->LastParameter();
BinTools_Curve2dSet::WriteCurve2d(C->BasisCurve(),OS); BinTools_Curve2dSet::WriteCurve2d (C->BasisCurve(), OS);
return OS; return OS;
} }
@ -283,11 +260,11 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_T
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_OffsetCurve)& C) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom2d_OffsetCurve)& C)
{ {
OS << (Standard_Byte)OFFSET; OS << (Standard_Byte)OFFSET;
BinTools::PutReal(OS,C->Offset());//Offset OS << C->Offset(); // Offset
BinTools_Curve2dSet::WriteCurve2d(C->BasisCurve(),OS); BinTools_Curve2dSet::WriteCurve2d (C->BasisCurve(), OS);
return OS; return OS;
} }
@ -296,8 +273,8 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom2d_O
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_Curve2dSet::WriteCurve2d(const Handle(Geom2d_Curve)& C, void BinTools_Curve2dSet::WriteCurve2d(
Standard_OStream& OS) const Handle(Geom2d_Curve)& C, BinTools_OStream& OS)
{ {
Handle(Standard_Type) TheType = C->DynamicType(); Handle(Standard_Type) TheType = C->DynamicType();
try { try {
@ -352,8 +329,9 @@ void BinTools_Curve2dSet::Write (Standard_OStream& OS,
Standard_Integer i, aNbCurves = myMap.Extent(); Standard_Integer i, aNbCurves = myMap.Extent();
Message_ProgressScope aPS(theRange, "Writing 2D curves",aNbCurves); Message_ProgressScope aPS(theRange, "Writing 2D curves",aNbCurves);
OS << "Curve2ds "<< aNbCurves << "\n"; OS << "Curve2ds "<< aNbCurves << "\n";
BinTools_OStream aStream (OS);
for (i = 1; i <= aNbCurves && aPS.More(); i++, aPS.Next()) { for (i = 1; i <= aNbCurves && aPS.More(); i++, aPS.Next()) {
WriteCurve2d(Handle(Geom2d_Curve)::DownCast(myMap(i)),OS); WriteCurve2d (Handle(Geom2d_Curve)::DownCast (myMap (i)), aStream);
} }
} }

View File

@ -26,6 +26,7 @@
#include <Standard_IStream.hxx> #include <Standard_IStream.hxx>
#include <Message_ProgressRange.hxx> #include <Message_ProgressRange.hxx>
#include <BinTools_OStream.hxx>
class Standard_OutOfRange; class Standard_OutOfRange;
class Geom2d_Curve; class Geom2d_Curve;
@ -69,7 +70,7 @@ public:
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Dumps the curve on the binary stream, that can be read back. //! Dumps the curve on the binary stream, that can be read back.
Standard_EXPORT static void WriteCurve2d(const Handle(Geom2d_Curve)& C, Standard_OStream& OS); Standard_EXPORT static void WriteCurve2d(const Handle(Geom2d_Curve)& C, BinTools_OStream& OS);
//! Reads the curve from the stream. The curve is //! Reads the curve from the stream. The curve is
//! assumed to have been written with the Write //! assumed to have been written with the Write

View File

@ -110,44 +110,17 @@ Standard_Integer BinTools_CurveSet::Index
} }
//=======================================================================
//function : operator << (gp_Pnt)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Pnt P)
{
BinTools::PutReal(OS, P.X());
BinTools::PutReal(OS, P.Y());
BinTools::PutReal(OS, P.Z());
return OS;
}
//=======================================================================
//function : operator << (gp_Dir)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Dir D)
{
BinTools::PutReal(OS, D.X());
BinTools::PutReal(OS, D.Y());
BinTools::PutReal(OS, D.Z());
return OS;
}
//======================================================================= //=======================================================================
//function : operator << (Geom_Line) //function : operator << (Geom_Line)
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Line)& L) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_Line)& L)
{ {
OS << (Standard_Byte)LINE; OS << (Standard_Byte)LINE;
gp_Lin C = L->Lin(); gp_Lin C = L->Lin();
OS << C.Location();//Pnt OS << C.Location(); // Pnt
OS << C.Direction();//Dir OS << C.Direction(); // Dir
return OS; return OS;
} }
@ -157,7 +130,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Lin
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Circle)& CC) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_Circle)& CC)
{ {
OS << (Standard_Byte)CIRCLE; OS << (Standard_Byte)CIRCLE;
gp_Circ C = CC->Circ(); gp_Circ C = CC->Circ();
@ -165,7 +138,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Cir
OS << C.Axis().Direction(); OS << C.Axis().Direction();
OS << C.XAxis().Direction(); OS << C.XAxis().Direction();
OS << C.YAxis().Direction(); OS << C.YAxis().Direction();
BinTools::PutReal(OS, C.Radius()); OS << C.Radius();
return OS; return OS;
} }
@ -174,7 +147,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Cir
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Ellipse)& E) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_Ellipse)& E)
{ {
OS << (Standard_Byte)ELLIPSE; OS << (Standard_Byte)ELLIPSE;
gp_Elips C = E->Elips(); gp_Elips C = E->Elips();
@ -182,8 +155,8 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Ell
OS << C.Axis().Direction(); OS << C.Axis().Direction();
OS << C.XAxis().Direction(); OS << C.XAxis().Direction();
OS << C.YAxis().Direction(); OS << C.YAxis().Direction();
BinTools::PutReal(OS, C.MajorRadius()); OS << C.MajorRadius();
BinTools::PutReal(OS, C.MinorRadius()); OS << C.MinorRadius();
return OS; return OS;
} }
@ -192,7 +165,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Ell
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Parabola)& P) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_Parabola)& P)
{ {
OS << (Standard_Byte)PARABOLA; OS << (Standard_Byte)PARABOLA;
gp_Parab C = P->Parab(); gp_Parab C = P->Parab();
@ -200,7 +173,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Par
OS << C.Axis().Direction(); OS << C.Axis().Direction();
OS << C.XAxis().Direction(); OS << C.XAxis().Direction();
OS << C.YAxis().Direction(); OS << C.YAxis().Direction();
BinTools::PutReal(OS, C.Focal()); OS << C.Focal();
return OS; return OS;
} }
@ -209,7 +182,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Par
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Hyperbola)& H) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_Hyperbola)& H)
{ {
OS << (Standard_Byte)HYPERBOLA; OS << (Standard_Byte)HYPERBOLA;
gp_Hypr C = H->Hypr(); gp_Hypr C = H->Hypr();
@ -217,8 +190,8 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Hyp
OS << C.Axis().Direction(); OS << C.Axis().Direction();
OS << C.XAxis().Direction(); OS << C.XAxis().Direction();
OS << C.YAxis().Direction(); OS << C.YAxis().Direction();
BinTools::PutReal(OS, C.MajorRadius()); OS << C.MajorRadius();
BinTools::PutReal(OS, C.MinorRadius()); OS << C.MinorRadius();
return OS; return OS;
} }
@ -227,18 +200,18 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Hyp
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BezierCurve)& B) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_BezierCurve)& B)
{ {
OS << (Standard_Byte)BEZIER; OS << (Standard_Byte)BEZIER;
Standard_Boolean aRational = B->IsRational() ? 1:0; Standard_Boolean aRational = B->IsRational() ? 1:0;
BinTools::PutBool(OS, aRational); //rational OS << aRational; // rational
// poles and weights // poles and weights
Standard_Integer i,aDegree = B->Degree(); Standard_Integer i, aDegree = B->Degree();
BinTools::PutExtChar(OS, (Standard_ExtCharacter)aDegree); //<< Degree OS << (Standard_ExtCharacter)aDegree; //<< Degree
for (i = 1; i <= aDegree+1; i++) { for (i = 1; i <= aDegree+1; i++) {
OS << B->Pole(i); //Pnt OS << B->Pole(i); // Pnt
if (aRational) if (aRational)
BinTools::PutReal(OS, B->Weight(i));//Real OS << B->Weight(i); // Real
} }
return OS; return OS;
} }
@ -248,30 +221,30 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Bez
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BSplineCurve)& B) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_BSplineCurve)& B)
{ {
OS << (Standard_Byte)BSPLINE; OS << (Standard_Byte)BSPLINE;
Standard_Boolean aRational = B->IsRational() ? 1:0; Standard_Boolean aRational = B->IsRational() ? 1:0;
BinTools::PutBool(OS, aRational); //rational OS << aRational; // rational
Standard_Boolean aPeriodic = B->IsPeriodic() ? 1:0; Standard_Boolean aPeriodic = B->IsPeriodic() ? 1:0;
BinTools::PutBool(OS, aPeriodic); //periodic OS << aPeriodic; // periodic
// poles and weights // poles and weights
Standard_Integer i,aDegree,aNbPoles,aNbKnots; Standard_Integer i,aDegree,aNbPoles,aNbKnots;
aDegree = B->Degree(); aDegree = B->Degree();
aNbPoles = B->NbPoles(); aNbPoles = B->NbPoles();
aNbKnots = B->NbKnots(); aNbKnots = B->NbKnots();
BinTools::PutExtChar(OS, (Standard_ExtCharacter) aDegree); OS << (Standard_ExtCharacter) aDegree;
BinTools::PutInteger(OS, aNbPoles); OS << aNbPoles;
BinTools::PutInteger(OS, aNbKnots); OS << aNbKnots;
for (i = 1; i <= aNbPoles; i++) { for (i = 1; i <= aNbPoles; i++) {
OS << B->Pole(i); // Pnt OS << B->Pole(i); // Pnt
if (aRational) if (aRational)
BinTools::PutReal(OS, B->Weight(i)); OS << B->Weight(i);
} }
for (i = 1; i <= aNbKnots; i++) { for (i = 1; i <= aNbKnots; i++) {
BinTools::PutReal(OS, B->Knot(i)); OS << B->Knot(i);
BinTools::PutInteger(OS, B->Multiplicity(i)); OS << B->Multiplicity(i);
} }
return OS; return OS;
} }
@ -281,11 +254,11 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BSp
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_TrimmedCurve)& C) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_TrimmedCurve)& C)
{ {
OS << (Standard_Byte)TRIMMED; OS << (Standard_Byte)TRIMMED;
BinTools::PutReal(OS, C->FirstParameter()); OS << C->FirstParameter();
BinTools::PutReal(OS, C->LastParameter()); OS << C->LastParameter();
BinTools_CurveSet::WriteCurve(C->BasisCurve(),OS); BinTools_CurveSet::WriteCurve(C->BasisCurve(),OS);
return OS; return OS;
} }
@ -295,10 +268,10 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Tri
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_OffsetCurve)& C) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_OffsetCurve)& C)
{ {
OS << (Standard_Byte)OFFSET; OS << (Standard_Byte)OFFSET;
BinTools::PutReal(OS,C->Offset());//Offset OS << C->Offset(); // Offset
OS << C->Direction(); OS << C->Direction();
BinTools_CurveSet::WriteCurve(C->BasisCurve(),OS); BinTools_CurveSet::WriteCurve(C->BasisCurve(),OS);
return OS; return OS;
@ -310,7 +283,7 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Off
//======================================================================= //=======================================================================
void BinTools_CurveSet::WriteCurve(const Handle(Geom_Curve)& C, void BinTools_CurveSet::WriteCurve(const Handle(Geom_Curve)& C,
Standard_OStream& OS) BinTools_OStream& OS)
{ {
Handle(Standard_Type) TheType = C->DynamicType(); Handle(Standard_Type) TheType = C->DynamicType();
try { try {
@ -363,10 +336,11 @@ void BinTools_CurveSet::Write (Standard_OStream& OS,
const Message_ProgressRange& theRange)const const Message_ProgressRange& theRange)const
{ {
Standard_Integer i, nbcurv = myMap.Extent(); Standard_Integer i, nbcurv = myMap.Extent();
Message_ProgressScope aPS(theRange, "Writing curves", nbcurv); Message_ProgressScope aPS (theRange, "Writing curves", nbcurv);
OS << "Curves "<< nbcurv << "\n"; OS << "Curves "<< nbcurv << "\n";
BinTools_OStream aStream (OS);
for (i = 1; i <= nbcurv &&aPS.More(); i++, aPS.Next()) { for (i = 1; i <= nbcurv &&aPS.More(); i++, aPS.Next()) {
WriteCurve(Handle(Geom_Curve)::DownCast(myMap(i)),OS); WriteCurve(Handle(Geom_Curve)::DownCast(myMap(i)), aStream);
} }
} }

View File

@ -26,6 +26,7 @@
#include <Standard_IStream.hxx> #include <Standard_IStream.hxx>
#include <Message_ProgressRange.hxx> #include <Message_ProgressRange.hxx>
#include <BinTools_OStream.hxx>
class Standard_OutOfRange; class Standard_OutOfRange;
class Geom_Curve; class Geom_Curve;
@ -67,7 +68,7 @@ public:
//! Dumps the curve on the stream in binary format //! Dumps the curve on the stream in binary format
//! that can be read back. //! that can be read back.
Standard_EXPORT static void WriteCurve (const Handle(Geom_Curve)& C, Standard_OStream& OS); Standard_EXPORT static void WriteCurve (const Handle(Geom_Curve)& C, BinTools_OStream& OS);
//! Reads the curve from the stream. The curve is //! Reads the curve from the stream. The curve is
//! assumed to have been written with the Write //! assumed to have been written with the Write

View File

@ -0,0 +1,257 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <BinTools_IStream.hxx>
#include <Storage_StreamTypeMismatchError.hxx>
//=======================================================================
//function : BinTools_IStream
//purpose :
//=======================================================================
BinTools_IStream::BinTools_IStream (Standard_IStream& theStream)
: myStream (&theStream), myPosition (theStream.tellg()), myLastType (BinTools_ObjectType_Unknown)
{}
//=======================================================================
//function : ReadType
//purpose :
//=======================================================================
BinTools_ObjectType BinTools_IStream::ReadType()
{
myLastType = BinTools_ObjectType (myStream->get());
myPosition++;
return myLastType;
}
//=======================================================================
//function : IsReference
//purpose :
//=======================================================================
Standard_Boolean BinTools_IStream::IsReference()
{
return myLastType == BinTools_ObjectType_Reference8 || myLastType == BinTools_ObjectType_Reference16 ||
myLastType == BinTools_ObjectType_Reference32 || myLastType == BinTools_ObjectType_Reference64;
}
//=======================================================================
//function : ReadReference
//purpose :
//=======================================================================
uint64_t BinTools_IStream::ReadReference()
{
uint64_t aDelta = 0;
uint64_t aCurrentPos = uint64_t (myStream->tellg());
switch (myLastType)
{
case BinTools_ObjectType_Reference8:
aDelta = uint64_t (myStream->get());
myPosition++;
break;
case BinTools_ObjectType_Reference16:
{
uint16_t aDelta16 = 0;
myStream->read ((char*)&aDelta16, sizeof (uint16_t));
myPosition += 2;
#if DO_INVERSE
aDelta16 = (0 | ((aDelta16 & 0x00FF) << 8)
| ((aDelta16 & 0xFF00) >> 8));
#endif
aDelta = uint64_t (aDelta16);
break;
}
case BinTools_ObjectType_Reference32:
{
uint32_t aDelta32 = 0;
myStream->read ((char*)&aDelta32, sizeof (uint32_t));
myPosition += 4;
#if DO_INVERSE
aDelta32 = (0 | ((aDelta32 & 0x000000ff) << 24)
| ((aDelta32 & 0x0000ff00) << 8)
| ((aDelta32 & 0x00ff0000) >> 8)
| ((aDelta32 >> 24) & 0x000000ff));
#endif
aDelta = uint64_t (aDelta32);
break;
}
case BinTools_ObjectType_Reference64:
myStream->read ((char*)&aDelta, sizeof (uint64_t));
myPosition += 8;
#if DO_INVERSE
aDelta = InverseUint64 (aDelta);
#endif
break;
default:
break;
}
if (aDelta == 0)
{
Standard_SStream aMsg;
aMsg << "BinTools_IStream::ReadReference: invalid reference " << (char)myLastType << std::endl;
throw Standard_Failure (aMsg.str().c_str());
}
return aCurrentPos - aDelta - 1; // add a type-byte
}
//=======================================================================
//function : GoTo
//purpose :
//=======================================================================
void BinTools_IStream::GoTo (const uint64_t& thePosition)
{
myStream->seekg (std::streampos (thePosition));
myPosition = thePosition;
}
//=======================================================================
//function : ShapeType
//purpose :
//=======================================================================
TopAbs_ShapeEnum BinTools_IStream::ShapeType()
{
return TopAbs_ShapeEnum ((Standard_Byte (myLastType) - Standard_Byte (BinTools_ObjectType_EndShape) - 1) >> 2);
}
//=======================================================================
//function : ShapeOrientation
//purpose :
//=======================================================================
TopAbs_Orientation BinTools_IStream::ShapeOrientation()
{
return TopAbs_Orientation ((Standard_Byte (myLastType) - Standard_Byte (BinTools_ObjectType_EndShape) - 1) & 3);
}
//=======================================================================
//function : operator bool
//purpose :
//=======================================================================
BinTools_IStream::operator bool() const
{
return *myStream ? Standard_True : Standard_False;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_IStream& BinTools_IStream::operator >> (Standard_Real& theValue)
{
if (!myStream->read ((char*)&theValue, sizeof (Standard_Real)))
throw Storage_StreamTypeMismatchError();
myPosition += sizeof (Standard_Real);
#if DO_INVERSE
theValue = InverseReal (theValue);
#endif
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_IStream& BinTools_IStream::operator >> (Standard_Integer& theValue)
{
if (!myStream->read ((char*)&theValue, sizeof (Standard_Integer)))
throw Storage_StreamTypeMismatchError();
myPosition += sizeof (Standard_Integer);
#if DO_INVERSE
theValue = InverseInt (theValue);
#endif
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_IStream& BinTools_IStream::operator >> (gp_Pnt& theValue)
{
Standard_Real aValue;
for (int aCoord = 1; aCoord <= 3; aCoord++)
{
if (!myStream->read ((char*)&aValue, sizeof (Standard_Real)))
throw Storage_StreamTypeMismatchError();
#if DO_INVERSE
aValue = InverseReal (aValue);
#endif
theValue.SetCoord (aCoord, aValue);
}
myPosition += 3 * sizeof (Standard_Real);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_IStream& BinTools_IStream::operator >> (Standard_Byte& theValue)
{
myStream->read ((char*)&theValue, sizeof (Standard_Byte));
myPosition += sizeof (Standard_Byte);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_IStream& BinTools_IStream::operator >> (Standard_ShortReal& theValue)
{
myStream->read ((char*)&theValue, sizeof (Standard_ShortReal));
myPosition += sizeof (Standard_ShortReal);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_IStream& BinTools_IStream::operator >> (gp_Trsf& theValue)
{
Standard_Real aV1[3], aV2[3], aV3[3], aV[3];
*this >> aV1[0] >> aV1[1] >> aV1[2] >> aV[0];
*this >> aV2[0] >> aV2[1] >> aV2[2] >> aV[1];
*this >> aV3[0] >> aV3[1] >> aV3[2] >> aV[2];
theValue.SetValues (aV1[0], aV1[1], aV1[2], aV[0],
aV2[0], aV2[1], aV2[2], aV[1],
aV3[0], aV3[1], aV3[2], aV[2]);
return *this;
}
//=======================================================================
//function : ReadBools
//purpose :
//=======================================================================
void BinTools_IStream::ReadBools (Standard_Boolean& theBool1, Standard_Boolean& theBool2, Standard_Boolean& theBool3)
{
Standard_Byte aByte = ReadByte();
theBool1 = (aByte & 1) == 1;
theBool2 = (aByte & 2) == 2;
theBool3 = (aByte & 4) == 4;
}
//=======================================================================
//function : ReadBools
//purpose :
//=======================================================================
void BinTools_IStream::ReadBools (Standard_Boolean& theBool1, Standard_Boolean& theBool2, Standard_Boolean& theBool3,
Standard_Boolean& theBool4, Standard_Boolean& theBool5, Standard_Boolean& theBool6, Standard_Boolean& theBool7)
{
Standard_Byte aByte = ReadByte();
theBool1 = (aByte & 1) == 1;
theBool2 = (aByte & 2) == 2;
theBool3 = (aByte & 4) == 4;
theBool4 = (aByte & 8) == 8;
theBool5 = (aByte & 16) == 16;
theBool6 = (aByte & 32) == 32;
theBool7 = (aByte & 64) == 64;
}

View File

@ -0,0 +1,90 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinTools_IStream_HeaderFile
#define _BinTools_IStream_HeaderFile
#include <BinTools.hxx>
#include <BinTools_ObjectType.hxx>
#include <TopAbs_ShapeEnum.hxx>
#include <TopAbs_Orientation.hxx>
#include <gp_Pnt.hxx>
//! Substitution of IStream for shape reader for fast management of position in the file (get and go)
//! and operation on all reading types.
class BinTools_IStream
{
public:
//! Creates IStream using the current stream IStream.
Standard_EXPORT BinTools_IStream (Standard_IStream& theStream);
//! Reads and returns the type.
Standard_EXPORT BinTools_ObjectType ReadType();
//! Returns the last read type.
Standard_EXPORT const BinTools_ObjectType& LastType() { return myLastType; }
//! Returns the shape type by the last retrieved type.
Standard_EXPORT TopAbs_ShapeEnum ShapeType();
//! Returns the shape orientation by the last retrieved type.
Standard_EXPORT TopAbs_Orientation ShapeOrientation();
//! Returns the current position in the stream.
Standard_EXPORT uint64_t Position() { return myPosition; }
//! Moves the current stream position to the given one.
Standard_EXPORT void GoTo (const uint64_t& thePosition);
//! Returns true if the last restored type is one of a reference
Standard_EXPORT Standard_Boolean IsReference();
//! Reads a reference IStream using the last restored type.
Standard_EXPORT uint64_t ReadReference();
//! Returns the original IStream.
Standard_EXPORT Standard_IStream& Stream() { return *myStream; }
//! Makes up to date the myPosition because myStream was used outside and position is changed.
Standard_EXPORT void UpdatePosition() { myPosition = uint64_t (myStream->tellg()); }
//! Returns false if stream reading is failed.
Standard_EXPORT operator bool() const;
//! Reads real value from the stream.
Standard_EXPORT Standard_Real ReadReal() { Standard_Real aValue; *this >> aValue; return aValue; }
Standard_EXPORT BinTools_IStream& operator >> (Standard_Real& theValue);
//! Reads integer value from the stream.
Standard_EXPORT Standard_Integer ReadInteger() { Standard_Integer aValue; *this >> aValue; return aValue; }
Standard_EXPORT BinTools_IStream& operator >> (Standard_Integer& theValue);
//! Reads point coordinates value from the stream.
Standard_EXPORT gp_Pnt ReadPnt() { gp_Pnt aValue; *this >> aValue; return aValue; }
Standard_EXPORT BinTools_IStream& operator >> (gp_Pnt& theValue);
//! Reads byte value from the stream.
Standard_EXPORT Standard_Byte ReadByte() { Standard_Byte aValue; *this >> aValue; return aValue; }
Standard_EXPORT BinTools_IStream& operator >> (Standard_Byte& theValue);
//! Reads boolean value from the stream (stored as one byte).
Standard_EXPORT Standard_Boolean ReadBool() { return ReadByte() != 0; }
Standard_EXPORT BinTools_IStream& operator >> (Standard_Boolean& theValue) { theValue = ReadByte() != 0; return *this; }
//! Reads short real value from the stream.
Standard_EXPORT Standard_ShortReal ReadShortReal() { Standard_ShortReal aValue; *this >> aValue; return aValue; }
Standard_EXPORT BinTools_IStream& operator >> (Standard_ShortReal& theValue);
//! Reads transformation value from the stream.
Standard_EXPORT BinTools_IStream& operator >> (gp_Trsf& theValue);
//! Reads 3 boolean values from one byte
Standard_EXPORT void ReadBools (Standard_Boolean& theBool1, Standard_Boolean& theBool2, Standard_Boolean& theBool3);
//! Reads 7 boolean values from one byte
Standard_EXPORT void ReadBools (Standard_Boolean& theBool1, Standard_Boolean& theBool2, Standard_Boolean& theBool3,
Standard_Boolean& theBool4, Standard_Boolean& theBool5, Standard_Boolean& theBool6, Standard_Boolean& theBool7);
private:
Standard_IStream* myStream; ///< pointer to the stream
uint64_t myPosition; ///< equivalent to tellg returned value for fast access
BinTools_ObjectType myLastType; ///< last type that was read
};
#endif // _BinTools_IStream_HeaderFile

View File

@ -57,7 +57,7 @@ static Standard_IStream& operator >>(Standard_IStream& IS, gp_Trsf& T)
//function : operator << (gp_Trsf& T) //function : operator << (gp_Trsf& T)
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS,const gp_Trsf& T) Standard_OStream& operator <<(Standard_OStream& OS,const gp_Trsf& T)
{ {
gp_XYZ V = T.TranslationPart(); gp_XYZ V = T.TranslationPart();
gp_Mat M = T.VectorialPart(); gp_Mat M = T.VectorialPart();

View File

@ -27,6 +27,8 @@
class Standard_OutOfRange; class Standard_OutOfRange;
class TopLoc_Location; class TopLoc_Location;
//! Operator for writing transformation into the stream
Standard_OStream& operator << (Standard_OStream& OS, const gp_Trsf& T);
//! The class LocationSet stores a set of location in //! The class LocationSet stores a set of location in
//! a relocatable state. //! a relocatable state.
@ -68,9 +70,6 @@ public:
//! is first cleared. //! is first cleared.
Standard_EXPORT void Read (Standard_IStream& IS); Standard_EXPORT void Read (Standard_IStream& IS);
protected: protected:

View File

@ -0,0 +1,352 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <BinTools_OStream.hxx>
#include <Storage_StreamTypeMismatchError.hxx>
#if DO_INVERSE
#include <FSD_BinaryFile.hxx>
#endif
//=======================================================================
//function : BinTools_OStream
//purpose :
//=======================================================================
BinTools_OStream::BinTools_OStream (Standard_OStream& theStream)
: myStream (&theStream), myPosition (theStream.tellp())
{}
//=======================================================================
//function : WriteReference
//purpose :
//=======================================================================
void BinTools_OStream::WriteReference (const uint64_t& thePosition)
{
uint64_t aDelta = myPosition - thePosition;
if (aDelta <= 0xFF)
{
*myStream << (Standard_Byte)BinTools_ObjectType_Reference8;
*myStream << (Standard_Byte)aDelta;
myPosition += sizeof (Standard_Byte) * 2;
}
else if (aDelta <= 0xFFFF)
{
*myStream << (Standard_Byte)BinTools_ObjectType_Reference16;
uint16_t aDelta16 = uint16_t (aDelta);
#if DO_INVERSE
aDelta16 = (0 | ((aDelta16 & 0x00FF) << 8)
| ((aDelta16 & 0xFF00) >> 8));
#endif
myStream->write ((char*)&aDelta16, sizeof (uint16_t));
myPosition += sizeof (Standard_Byte) + sizeof (uint16_t);
}
else if (aDelta <= 0xFFFFFFFF)
{
*myStream << (Standard_Byte)BinTools_ObjectType_Reference32;
uint32_t aDelta32 = uint32_t (aDelta);
#if DO_INVERSE
aDelta32 = (0 | ((aDelta32 & 0x000000ff) << 24)
| ((aDelta32 & 0x0000ff00) << 8)
| ((aDelta32 & 0x00ff0000) >> 8)
| ((aDelta32 >> 24) & 0x000000ff) );
#endif
myStream->write ((char*)&aDelta32, sizeof (uint32_t));
myPosition += sizeof (Standard_Byte) + sizeof (uint32_t);
}
else
{
*myStream << (Standard_Byte)BinTools_ObjectType_Reference64;
#if DO_INVERSE
aDelta = FSD_BinaryFile::InverseUint64 (aDelta);
#endif
myStream->write ((char*)&aDelta, sizeof (uint64_t));
myPosition += sizeof (Standard_Byte) + sizeof (uint64_t);
}
}
//=======================================================================
//function : WriteShape
//purpose :
//=======================================================================
void BinTools_OStream::WriteShape (const TopAbs_ShapeEnum& theType, const TopAbs_Orientation& theOrientation)
{
Standard_Byte aType = Standard_Byte (BinTools_ObjectType_EndShape) + 1 + // taking into account that orientation <= 3
(Standard_Byte (theType) << 2) + Standard_Byte (theOrientation); // and type <= 8
myStream->put ((Standard_Byte)aType);
myPosition += sizeof (Standard_Byte);
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const BinTools_ObjectType& theType)
{
myStream->put ((Standard_Byte)theType);
myPosition += sizeof (Standard_Byte);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const Standard_Byte& theValue)
{
myStream->put (theValue);
myPosition += sizeof (Standard_Byte);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const Standard_Real& theValue)
{
#if DO_INVERSE
const Standard_Real aRValue = FSD_BinaryFile::InverseReal (theValue);
myStream->write ((char*)&aRValue, sizeof (Standard_Real));
#else
myStream->write ((char*)&theValue, sizeof (Standard_Real));
#endif
myPosition += sizeof (Standard_Real);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const Standard_Boolean& theValue)
{
myStream->put ((Standard_Byte)(theValue ? 1 : 0));
myPosition += sizeof (Standard_Byte);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const Standard_Integer& theValue)
{
#if DO_INVERSE
const Standard_Integer aRValue = FSD_BinaryFile::InverseInt (theValue);
myStream->write ((char*)&aRValue, sizeof (Standard_Integer));
#else
myStream->write ((char*)&theValue, sizeof (Standard_Integer));
#endif
myPosition += sizeof (Standard_Integer);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const Standard_ExtCharacter& theValue)
{
#if DO_INVERSE
const Standard_ExtCharacter aRValue = FSD_BinaryFile::InverseExtChar (theValue);
myStream->write ((char*)&aRValue, sizeof (Standard_ExtCharacter));
#else
myStream->write ((char*)&theValue, sizeof (Standard_ExtCharacter));
#endif
myPosition += sizeof (Standard_ExtCharacter);
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const gp_Pnt& theValue)
{
#if DO_INVERSE
myRealBuf[0] = FSD_BinaryFile::InverseReal (theValue.X());
myRealBuf[1] = FSD_BinaryFile::InverseReal (theValue.Y());
myRealBuf[2] = FSD_BinaryFile::InverseReal (theValue.Z());
#else
myRealBuf[0] = theValue.X();
myRealBuf[1] = theValue.Y();
myRealBuf[2] = theValue.Z();
#endif
myStream->write ((char*)myRealBuf, sizeof (Standard_Real) * 3);
myPosition += sizeof (Standard_Real) * 3;
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const gp_Dir& theValue)
{
#if DO_INVERSE
myRealBuf[0] = FSD_BinaryFile::InverseReal (theValue.X());
myRealBuf[1] = FSD_BinaryFile::InverseReal (theValue.Y());
myRealBuf[2] = FSD_BinaryFile::InverseReal (theValue.Z());
#else
myRealBuf[0] = theValue.X();
myRealBuf[1] = theValue.Y();
myRealBuf[2] = theValue.Z();
#endif
myStream->write ((char*)myRealBuf, sizeof (Standard_Real) * 3);
myPosition += sizeof (Standard_Real) * 3;
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const gp_Pnt2d& theValue)
{
#if DO_INVERSE
myRealBuf[0] = FSD_BinaryFile::InverseReal (theValue.X());
myRealBuf[1] = FSD_BinaryFile::InverseReal (theValue.Y());
#else
myRealBuf[0] = theValue.X();
myRealBuf[1] = theValue.Y();
#endif
myStream->write ((char*)myRealBuf, sizeof (Standard_Real) * 2);
myPosition += sizeof (Standard_Real) * 2;
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const gp_Dir2d& theValue)
{
#if DO_INVERSE
myRealBuf[0] = FSD_BinaryFile::InverseReal (theValue.X());
myRealBuf[1] = FSD_BinaryFile::InverseReal (theValue.Y());
#else
myRealBuf[0] = theValue.X();
myRealBuf[1] = theValue.Y();
#endif
myStream->write ((char*)myRealBuf, sizeof (Standard_Real) * 2);
myPosition += sizeof (Standard_Real) * 2;
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const gp_Trsf& theValue)
{
gp_XYZ aTr = theValue.TranslationPart();
gp_Mat aMat = theValue.VectorialPart();
#if DO_INVERSE
myRealBuf[0] = FSD_BinaryFile::InverseReal (aMat (1, 1));
myRealBuf[1] = FSD_BinaryFile::InverseReal (aMat (1, 2));
myRealBuf[2] = FSD_BinaryFile::InverseReal (aMat (1, 3));
myRealBuf[3] = FSD_BinaryFile::InverseReal (aTr.Coord (1));
myRealBuf[4] = FSD_BinaryFile::InverseReal (aMat (2, 1));
myRealBuf[5] = FSD_BinaryFile::InverseReal (aMat (2, 2));
myRealBuf[6] = FSD_BinaryFile::InverseReal (aMat (2, 3));
myRealBuf[7] = FSD_BinaryFile::InverseReal (aTr.Coord (2));
myRealBuf[8] = FSD_BinaryFile::InverseReal (aMat (3, 1));
myRealBuf[9] = FSD_BinaryFile::InverseReal (aMat (3, 2));
myRealBuf[10] = FSD_BinaryFile::InverseReal (aMat (3, 3));
myRealBuf[11] = FSD_BinaryFile::InverseReal (aTr.Coord (3));
#else
myRealBuf[0] = aMat (1, 1);
myRealBuf[1] = aMat (1, 2);
myRealBuf[2] = aMat (1, 3);
myRealBuf[3] = aTr.Coord (1);
myRealBuf[4] = aMat (2, 1);
myRealBuf[5] = aMat (2, 2);
myRealBuf[6] = aMat (2, 3);
myRealBuf[7] = aTr.Coord (2);
myRealBuf[8] = aMat (3, 1);
myRealBuf[9] = aMat (3, 2);
myRealBuf[10] = aMat (3, 3);
myRealBuf[11] = aTr.Coord (3);
#endif
myStream->write ((char*)myRealBuf, sizeof (Standard_Real) * 12);
myPosition += sizeof (Standard_Real) * 12;
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const Poly_Triangle& theValue)
{
theValue.Value(1);
#if DO_INVERSE
myIntBuf[0] = FSD_BinaryFile::InverseInt (theValue.Value(1));
myIntBuf[1] = FSD_BinaryFile::InverseInt (theValue.Value(2));
myIntBuf[2] = FSD_BinaryFile::InverseInt (theValue.Value(3));
#else
myIntBuf[0] = theValue.Value(1);
myIntBuf[1] = theValue.Value(2);
myIntBuf[2] = theValue.Value(3);
#endif
myStream->write ((char*)myIntBuf, sizeof (Standard_Integer) * 3);
myPosition += sizeof (Standard_Integer) * 3;
return *this;
}
//=======================================================================
//function : operator <<
//purpose :
//=======================================================================
BinTools_OStream& BinTools_OStream::operator << (const gp_Vec3f& theValue)
{
#if DO_INVERSE
myFloatBuf[0] = FSD_BinaryFile::InverseShortReal (theValue.x());
myFloatBuf[1] = FSD_BinaryFile::InverseShortReal (theValue.y());
myFloatBuf[2] = FSD_BinaryFile::InverseShortReal (theValue.z());
#else
myFloatBuf[0] = theValue.x();
myFloatBuf[1] = theValue.y();
myFloatBuf[2] = theValue.z();
#endif
myStream->write ((char*)myFloatBuf, sizeof (float) * 3);
myPosition += sizeof (float) * 3;
return *this;
}
//=======================================================================
//function : PutBools
//purpose :
//=======================================================================
void BinTools_OStream::PutBools (
const Standard_Boolean theValue1, const Standard_Boolean theValue2, const Standard_Boolean theValue3)
{
Standard_Byte aValue = (theValue1 ? 1 : 0) | (theValue2 ? 2 : 0) | (theValue3 ? 4 : 0);
myStream->write((char*)&aValue, sizeof(Standard_Byte));
myPosition += sizeof(Standard_Byte);
}
//=======================================================================
//function : PutBools
//purpose :
//=======================================================================
void BinTools_OStream::PutBools (
const Standard_Boolean theValue1, const Standard_Boolean theValue2, const Standard_Boolean theValue3,
const Standard_Boolean theValue4, const Standard_Boolean theValue5, const Standard_Boolean theValue6,
const Standard_Boolean theValue7)
{
Standard_Byte aValue = (theValue1 ? 1 : 0) | (theValue2 ? 2 : 0) | (theValue3 ? 4 : 0) | (theValue4 ? 8 : 0) |
(theValue5 ? 16 : 0) | (theValue6 ? 32 : 0) | (theValue7 ? 64 : 0);
myStream->write((char*)&aValue, sizeof(Standard_Byte));
myPosition += sizeof(Standard_Byte);
}

View File

@ -0,0 +1,87 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinTools_OStream_HeaderFile
#define _BinTools_OStream_HeaderFile
#include <BinTools.hxx>
#include <BinTools_ObjectType.hxx>
#include <TopAbs_ShapeEnum.hxx>
#include <TopAbs_Orientation.hxx>
#include <gp_Pnt.hxx>
#include <Poly_Triangle.hxx>
#include <gp_Vec3f.hxx>
//! Substitution of OStream for shape writer for fast management of position in the file
//! and operation on all writing types.
class BinTools_OStream
{
public:
//! Creates OStream using the current stream OStream.
Standard_EXPORT BinTools_OStream (Standard_OStream& theStream);
//! Returns the current position of the stream
Standard_EXPORT const uint64_t& Position() { return myPosition; }
//! Writes the reference to the given position (an offset between the current and the given one).
Standard_EXPORT void WriteReference (const uint64_t& thePosition);
//! Writes an identifier of shape type and orientation into the stream.
Standard_EXPORT void WriteShape (const TopAbs_ShapeEnum& theType, const TopAbs_Orientation& theOrientation);
//! Writes an object type to the stream.
Standard_EXPORT BinTools_OStream& operator << (const BinTools_ObjectType& theType);
//! Writes a byte to the stream.
Standard_EXPORT BinTools_OStream& operator << (const Standard_Byte& theValue);
//! Writes a real to the stream.
Standard_EXPORT BinTools_OStream& operator << (const Standard_Real& theValue);
//! Writes a boolean to the stream.
Standard_EXPORT BinTools_OStream& operator << (const Standard_Boolean& theValue);
//! Writes a integer to the stream.
Standard_EXPORT BinTools_OStream& operator << (const Standard_Integer& theValue);
//! Writes a extended character to the stream.
Standard_EXPORT BinTools_OStream& operator << (const Standard_ExtCharacter& theValue);
//! Writes a 3D point to the stream.
Standard_EXPORT BinTools_OStream& operator << (const gp_Pnt& theValue);
//! Writes a 3D direction to the stream.
Standard_EXPORT BinTools_OStream& operator << (const gp_Dir& theValue);
//! Writes a 2D point to the stream.
Standard_EXPORT BinTools_OStream& operator << (const gp_Pnt2d& theValue);
//! Writes a 2D direction to the stream.
Standard_EXPORT BinTools_OStream& operator << (const gp_Dir2d& theValue);
//! Writes a transformation matrix to the stream.
Standard_EXPORT BinTools_OStream& operator << (const gp_Trsf& theValue);
//! Writes triangle nodes indices to the stream.
Standard_EXPORT BinTools_OStream& operator << (const Poly_Triangle& theValue);
//! Writes a vector to the stream.
Standard_EXPORT BinTools_OStream& operator << (const gp_Vec3f& theValue);
//! Writes 3 booleans as one byte to the stream.
Standard_EXPORT void PutBools (
const Standard_Boolean theValue1, const Standard_Boolean theValue2, const Standard_Boolean theValue3);
//! Writes 7 booleans as one byte to the stream.
Standard_EXPORT void PutBools (
const Standard_Boolean theValue1, const Standard_Boolean theValue2, const Standard_Boolean theValue3,
const Standard_Boolean theValue4, const Standard_Boolean theValue5, const Standard_Boolean theValue6,
const Standard_Boolean theValue7);
private:
Standard_OStream* myStream; ///< pointer to the stream
uint64_t myPosition; ///< the current position relatively to the OStream position at the moment of creation of this class instance
Standard_Real myRealBuf[12]; ///< buffer for 12 reals storage
Standard_Integer myIntBuf[3]; ///< buffer for 3 integers storage
float myFloatBuf[3]; ///< buffer for 3 floats storage
};
#endif // _BinTools_OStream_HeaderFile

View File

@ -0,0 +1,46 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinTools_ObjectType_HeaderFile
#define _BinTools_ObjectType_HeaderFile
//! Enumeration defining objects identifiers in the shape read/write format.
enum BinTools_ObjectType
{
BinTools_ObjectType_Unknown = 0,
BinTools_ObjectType_Reference8, //!< 8-bits reference
BinTools_ObjectType_Reference16, //!< 16-bits reference
BinTools_ObjectType_Reference32, //!< 32-bits reference
BinTools_ObjectType_Reference64, //!< 64-bits reference
BinTools_ObjectType_Location,
BinTools_ObjectType_SimpleLocation,
BinTools_ObjectType_EmptyLocation,
BinTools_ObjectType_LocationEnd,
BinTools_ObjectType_Curve,
BinTools_ObjectType_EmptyCurve,
BinTools_ObjectType_Curve2d,
BinTools_ObjectType_EmptyCurve2d,
BinTools_ObjectType_Surface,
BinTools_ObjectType_EmptySurface,
BinTools_ObjectType_Polygon3d,
BinTools_ObjectType_EmptyPolygon3d,
BinTools_ObjectType_PolygonOnTriangulation,
BinTools_ObjectType_EmptyPolygonOnTriangulation,
BinTools_ObjectType_Triangulation,
BinTools_ObjectType_EmptyTriangulation,
BinTools_ObjectType_EmptyShape = 198, //!< identifier of the null shape
BinTools_ObjectType_EndShape = 199, //!< identifier of the shape record end
// here is the space for TopAbs_ShapeEnum+Orientation types
};
#endif // _BinTools_ObjectType_HeaderFile

View File

@ -0,0 +1,602 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <BinTools_ShapeReader.hxx>
#include <TopoDS.hxx>
#include <BRep_PointOnCurve.hxx>
#include <BRep_PointOnCurveOnSurface.hxx>
#include <BRep_PointOnSurface.hxx>
#include <BRep_Polygon3D.hxx>
#include <BRep_Builder.hxx>
#include <BinTools_CurveSet.hxx>
#include <BinTools_Curve2dSet.hxx>
#include <BinTools_SurfaceSet.hxx>
//=======================================================================
//function : BinTools_ShapeReader
//purpose :
//=======================================================================
BinTools_ShapeReader::BinTools_ShapeReader()
{}
//=======================================================================
//function : ~BinTools_ShapeReader
//purpose :
//=======================================================================
BinTools_ShapeReader::~BinTools_ShapeReader()
{}
//=======================================================================
//function : Clear
//purpose :
//=======================================================================
void BinTools_ShapeReader::Clear()
{
BinTools_ShapeSetBase::Clear();
myShapePos.Clear();
myLocationPos.Clear();
myCurvePos.Clear();
myCurve2dPos.Clear();
mySurfacePos.Clear();
myPolygon3dPos.Clear();
myPolygonPos.Clear();
myTriangulationPos.Clear();
}
//=======================================================================
//function : Read
//purpose :
//=======================================================================
void BinTools_ShapeReader::Read (Standard_IStream& theStream, TopoDS_Shape& theShape)
{
BinTools_IStream aStream(theStream);
theShape = ReadShape(aStream);
}
//=======================================================================
//function : ReadShape
//purpose :
//=======================================================================
TopoDS_Shape BinTools_ShapeReader::ReadShape (BinTools_IStream& theStream)
{
TopoDS_Shape aResult;
uint64_t aPosition = theStream.Position();
const BinTools_ObjectType& aType = theStream.ReadType();
if (aType == BinTools_ObjectType_EmptyShape || aType == BinTools_ObjectType_EndShape)
return aResult;
if (theStream.IsReference())
{
uint64_t aRef = theStream.ReadReference();
const TopoDS_Shape* aFound = myShapePos.Seek(aRef);
if (aFound) // the shape is already retrieved, just add location
{
aResult = *aFound;
}
else
{
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadShape (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
aResult.Location (*ReadLocation (theStream));
aResult.Orientation (TopAbs_Orientation (theStream.ReadByte()));
return aResult;
}
// read the shape
TopAbs_ShapeEnum aShapeType = theStream.ShapeType();
TopAbs_Orientation aShapeOrientation = theStream.ShapeOrientation();
const TopLoc_Location* aShapeLocation = ReadLocation (theStream);
Standard_Real aTol;
static BRep_Builder aBuilder;
try {
OCC_CATCH_SIGNALS
switch (aShapeType) {
case TopAbs_VERTEX:
{
TopoDS_Vertex& aV = TopoDS::Vertex (aResult);
// Read the point geometry
theStream >> aTol;
gp_Pnt aPnt = theStream.ReadPnt();
aBuilder.MakeVertex (aV, aPnt, aTol);
Handle(BRep_TVertex) aTV = Handle(BRep_TVertex)::DownCast (aV.TShape());
BRep_ListOfPointRepresentation& aLpr = aTV->ChangePoints();
static TopLoc_Location anEmptyLoc;
while (theStream) {
Standard_Byte aPrsType = theStream.ReadByte();
if (aPrsType == 0) // end of the cycle
break;
Standard_Real aParam = theStream.ReadReal();
Handle(BRep_PointRepresentation) aPR;
switch (aPrsType) {
case 1:
{
Handle(Geom_Curve) aCurve = ReadCurve (theStream);
if (!aCurve.IsNull())
aPR = new BRep_PointOnCurve (aParam, aCurve, anEmptyLoc);
break;
}
case 2:
{
Handle(Geom2d_Curve) aCurve2d = ReadCurve2d (theStream);
Handle(Geom_Surface) aSurface = ReadSurface (theStream);
if (!aCurve2d.IsNull() && aSurface.IsNull())
aPR = new BRep_PointOnCurveOnSurface (aParam, aCurve2d, aSurface, anEmptyLoc);
break;
}
case 3:
{
Standard_Real aParam2 = theStream.ReadReal();
Handle(Geom_Surface) aSurface = ReadSurface (theStream);
if (!aSurface.IsNull())
aPR = new BRep_PointOnSurface (aParam, aParam2, aSurface, anEmptyLoc);
break;
}
default:
{
Standard_SStream aMsg;
aMsg << "BinTools_ShapeReader::Read: UnExpected BRep_PointRepresentation = " << aPrsType << std::endl;
throw Standard_Failure (aMsg.str().c_str());
}
}
const TopLoc_Location* aPRLoc = ReadLocation (theStream);
if (!aPR.IsNull())
{
aPR->Location (*aPRLoc);
aLpr.Append (aPR);
}
}
break;
}
case TopAbs_EDGE:
{
TopoDS_Edge& aE = TopoDS::Edge (aResult);
aBuilder.MakeEdge(aE);
// Read the curve geometry
theStream >> aTol;
Standard_Boolean aSameParameter, aSameRange, aDegenerated;
theStream.ReadBools (aSameParameter, aSameRange, aDegenerated);
aBuilder.SameParameter (aE, aSameParameter);
aBuilder.SameRange (aE, aSameRange);
aBuilder.Degenerated (aE, aDegenerated);
Standard_Real aFirst, aLast;
while (theStream) {
Standard_Byte aPrsType = theStream.ReadByte(); //{0|1|2|3|4|5|6|7}
if (aPrsType == 0)
break;
switch (aPrsType)
{
case 1: // -1- Curve 3D
{
Handle(Geom_Curve) aCurve = ReadCurve (theStream);
const TopLoc_Location* aLoc = ReadLocation (theStream);
theStream >> aFirst;
theStream >> aLast;
if (!aCurve.IsNull())
{
aBuilder.UpdateEdge (aE, aCurve, *aLoc, aTol);
aBuilder.Range (aE, aFirst, aLast, Standard_True);
}
break;
}
case 2: // -2- Curve on surf
case 3: // -3- Curve on closed surf
{
Standard_Boolean aClosed = (aPrsType == 3);
Handle(Geom2d_Curve) aCurve2d_2, aCurve2d_1 = ReadCurve2d (theStream);
GeomAbs_Shape aReg = GeomAbs_C0;
if (aClosed) {
aCurve2d_2 = ReadCurve2d (theStream);
aReg = (GeomAbs_Shape)theStream.ReadByte();
}
Handle(Geom_Surface) aSurface = ReadSurface (theStream);
const TopLoc_Location* aLoc = ReadLocation (theStream);
// range
theStream >> aFirst;
theStream >> aLast;
if (!aCurve2d_1.IsNull() && (!aClosed || !aCurve2d_2.IsNull()) && !aSurface.IsNull())
{
if (aClosed)
{
aBuilder.UpdateEdge (aE, aCurve2d_1, aCurve2d_2, aSurface, *aLoc, aTol);
aBuilder.Continuity (aE, aSurface, aSurface, *aLoc, *aLoc, aReg);
}
else
aBuilder.UpdateEdge (aE, aCurve2d_1, aSurface, *aLoc, aTol);
aBuilder.Range (aE, aSurface, *aLoc, aFirst, aLast);
}
break;
}
case 4: // -4- Regularity
{
GeomAbs_Shape aReg = (GeomAbs_Shape)theStream.ReadByte();
Handle(Geom_Surface) aSurface1 = ReadSurface (theStream);
const TopLoc_Location* aLoc1 = ReadLocation (theStream);
Handle(Geom_Surface) aSurface2 = ReadSurface (theStream);
const TopLoc_Location* aLoc2 = ReadLocation (theStream);
if (!aSurface1.IsNull() && !aSurface2.IsNull())
aBuilder.Continuity (aE, aSurface1, aSurface2, *aLoc1, *aLoc2, aReg);
break;
}
case 5: // -5- Polygon3D
{
Handle(Poly_Polygon3D) aPolygon = ReadPolygon3d (theStream);
const TopLoc_Location* aLoc = ReadLocation (theStream);
aBuilder.UpdateEdge (aE, aPolygon, *aLoc);
break;
}
case 6: // -6- Polygon on triangulation
case 7: // -7- Polygon on closed triangulation
{
Standard_Boolean aClosed = (aPrsType == 7);
Handle(Poly_PolygonOnTriangulation) aPoly2, aPoly1 = ReadPolygon (theStream);
if (aClosed)
aPoly2 = ReadPolygon (theStream);
Handle(Poly_Triangulation) aTriangulation = ReadTriangulation (theStream);
const TopLoc_Location* aLoc = ReadLocation (theStream);
if (aClosed)
aBuilder.UpdateEdge (aE, aPoly1, aPoly2, aTriangulation, *aLoc);
else
aBuilder.UpdateEdge (aE, aPoly1, aTriangulation, *aLoc);
// range
break;
}
default:
{
Standard_SStream aMsg;
aMsg << "Unexpected Curve Representation =" << aPrsType << std::endl;
throw Standard_Failure (aMsg.str().c_str());
}
}
}
break;
}
case TopAbs_WIRE:
aBuilder.MakeWire (TopoDS::Wire (aResult));
break;
case TopAbs_FACE:
{
TopoDS_Face& aF = TopoDS::Face (aResult);
aBuilder.MakeFace (aF);
Standard_Boolean aNatRes = theStream.ReadBool();
theStream >> aTol;
Handle(Geom_Surface) aSurface = ReadSurface (theStream);
const TopLoc_Location* aLoc = ReadLocation (theStream);
aBuilder.UpdateFace (aF, aSurface, *aLoc, aTol);
aBuilder.NaturalRestriction (aF, aNatRes);
if (theStream.ReadByte() == 2) // triangulation
aBuilder.UpdateFace (aF, ReadTriangulation (theStream));
break;
}
case TopAbs_SHELL:
aBuilder.MakeShell (TopoDS::Shell (aResult));
break;
case TopAbs_SOLID:
aBuilder.MakeSolid (TopoDS::Solid (aResult));
break;
case TopAbs_COMPSOLID:
aBuilder.MakeCompSolid (TopoDS::CompSolid (aResult));
break;
case TopAbs_COMPOUND:
aBuilder.MakeCompound (TopoDS::Compound (aResult));
break;
default:
{
Standard_SStream aMsg;
aMsg << "Unexpected topology type = " << aShapeType << std::endl;
throw Standard_Failure (aMsg.str().c_str());
break;
}
}
}
catch (Standard_Failure const& anException)
{
Standard_SStream aMsg;
aMsg << "EXCEPTION in BinTools_ShapeReader::Read" << std::endl;
aMsg << anException << std::endl;
throw Standard_Failure (aMsg.str().c_str());
}
// read flags and subs
Standard_Boolean aFree, aMod, aChecked, anOrient, aClosed, anInf, aConv;
theStream.ReadBools (aFree, aMod, aChecked, anOrient, aClosed, anInf, aConv);
// sub-shapes
for(TopoDS_Shape aSub = ReadShape (theStream); !aSub.IsNull(); aSub = ReadShape (theStream))
aBuilder.Add (aResult, aSub);
aResult.Free (aFree);
aResult.Modified (aMod);
aResult.Checked (aChecked);
aResult.Orientable (anOrient);
aResult.Closed (aClosed);
aResult.Infinite (anInf);
aResult.Convex (aConv);
myShapePos.Bind (aPosition, aResult);
aResult.Orientation (aShapeOrientation);
aResult.Location (*aShapeLocation);
return aResult;
}
//=======================================================================
//function : ReadLocation
//purpose :
//=======================================================================
const TopLoc_Location* BinTools_ShapeReader::ReadLocation (BinTools_IStream& theStream)
{
static const TopLoc_Location* anEmptyLoc = new TopLoc_Location;
uint64_t aPosition = theStream.Position();
const BinTools_ObjectType& aType = theStream.ReadType();
if (aType == BinTools_ObjectType_EmptyLocation || aType == BinTools_ObjectType_LocationEnd)
return anEmptyLoc;
if (theStream.IsReference())
{
uint64_t aRef = theStream.ReadReference();
const TopLoc_Location* aFound = myLocationPos.Seek (aRef);
if (aFound) // the location is already retrieved
return aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
const TopLoc_Location* aResult = ReadLocation (theStream);
theStream.GoTo (aCurrent); // returns to the current position
return aResult;
}
// read the location directly from the stream
TopLoc_Location aLoc;
if (aType == BinTools_ObjectType_SimpleLocation)
{
gp_Trsf aTrsf;
theStream >> aTrsf;
aLoc = aTrsf;
}
else if (aType == BinTools_ObjectType_Location)
{
for(const TopLoc_Location* aNextLoc = ReadLocation (theStream); !aNextLoc->IsIdentity();
aNextLoc = ReadLocation (theStream))
aLoc = aNextLoc->Powered (theStream.ReadInteger()) * aLoc;
}
myLocationPos.Bind (aPosition, aLoc);
return myLocationPos.Seek (aPosition);
}
//=======================================================================
//function : ReadCurve
//purpose :
//=======================================================================
Handle(Geom_Curve) BinTools_ShapeReader::ReadCurve (BinTools_IStream& theStream)
{
Handle(Geom_Curve) aResult;
uint64_t aPosition = theStream.Position();
theStream.ReadType();
if (theStream.IsReference())
{ // get by reference
uint64_t aRef = theStream.ReadReference();
const Handle(Geom_Curve)* aFound = myCurvePos.Seek (aRef);
if (aFound) // the location is already retrieved
return *aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadCurve (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
else if (theStream.LastType() == BinTools_ObjectType_Curve)
{ // read from the stream
BinTools_CurveSet::ReadCurve (theStream.Stream(), aResult);
theStream.UpdatePosition();
myCurvePos.Bind (aPosition, aResult);
}
return aResult;
}
//=======================================================================
//function : ReadCurve2d
//purpose :
//=======================================================================
Handle(Geom2d_Curve) BinTools_ShapeReader::ReadCurve2d (BinTools_IStream& theStream)
{
Handle(Geom2d_Curve) aResult;
uint64_t aPosition = theStream.Position();
theStream.ReadType();
if (theStream.IsReference())
{ // get by reference
uint64_t aRef = theStream.ReadReference();
const Handle(Geom2d_Curve)* aFound = myCurve2dPos.Seek (aRef);
if (aFound) // the location is already retrieved
return *aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadCurve2d (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
else if (theStream.LastType() == BinTools_ObjectType_Curve2d)
{ // read from the stream
BinTools_Curve2dSet::ReadCurve2d (theStream.Stream(), aResult);
theStream.UpdatePosition();
myCurve2dPos.Bind (aPosition, aResult);
}
return aResult;
}
//=======================================================================
//function : ReadSurface
//purpose :
//=======================================================================
Handle(Geom_Surface) BinTools_ShapeReader::ReadSurface (BinTools_IStream& theStream)
{
Handle(Geom_Surface) aResult;
uint64_t aPosition = theStream.Position();
theStream.ReadType();
if (theStream.IsReference())
{ // get by reference
uint64_t aRef = theStream.ReadReference();
const Handle(Geom_Surface)* aFound = mySurfacePos.Seek (aRef);
if (aFound) // the location is already retrieved
return *aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadSurface (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
else if (theStream.LastType() == BinTools_ObjectType_Surface)
{ // read from the stream
BinTools_SurfaceSet::ReadSurface (theStream.Stream(), aResult);
theStream.UpdatePosition();
mySurfacePos.Bind (aPosition, aResult);
}
return aResult;
}
//=======================================================================
//function : ReadPolygon3d
//purpose :
//=======================================================================
Handle(Poly_Polygon3D) BinTools_ShapeReader::ReadPolygon3d (BinTools_IStream& theStream)
{
Handle(Poly_Polygon3D) aResult;
uint64_t aPosition = theStream.Position();
theStream.ReadType();
if (theStream.IsReference())
{ // get by reference
uint64_t aRef = theStream.ReadReference();
const Handle(Poly_Polygon3D)* aFound = myPolygon3dPos.Seek (aRef);
if (aFound) // the location is already retrieved
return *aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadPolygon3d (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
else if (theStream.LastType() == BinTools_ObjectType_Polygon3d)
{ // read from the stream
Standard_Integer aNbNodes = theStream.ReadInteger();
Standard_Boolean aHasParameters = theStream.ReadBool();
aResult = new Poly_Polygon3D (aNbNodes, aHasParameters);
aResult->Deflection (theStream.ReadReal());
TColgp_Array1OfPnt& aNodes = aResult->ChangeNodes();
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream >> aNodes.ChangeValue (aNodeIter);
if (aHasParameters)
{
TColStd_Array1OfReal& aParam = aResult->ChangeParameters();
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream >> aParam.ChangeValue (aNodeIter);
}
myPolygon3dPos.Bind (aPosition, aResult);
}
return aResult;
}
//=======================================================================
//function : ReadPolygon
//purpose :
//=======================================================================
Handle(Poly_PolygonOnTriangulation) BinTools_ShapeReader::ReadPolygon (BinTools_IStream& theStream)
{
Handle(Poly_PolygonOnTriangulation) aResult;
uint64_t aPosition = theStream.Position();
theStream.ReadType();
if (theStream.IsReference())
{ // get by reference
uint64_t aRef = theStream.ReadReference();
const Handle(Poly_PolygonOnTriangulation)* aFound = myPolygonPos.Seek (aRef);
if (aFound) // the location is already retrieved
return *aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadPolygon (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
else if (theStream.LastType() == BinTools_ObjectType_PolygonOnTriangulation)
{ // read from the stream
Standard_Integer aNbNodes = theStream.ReadInteger();
aResult = new Poly_PolygonOnTriangulation (aNbNodes, Standard_False);
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
aResult->SetNode(aNodeIter, theStream.ReadInteger());
aResult->Deflection (theStream.ReadReal());
if (theStream.ReadBool())
{
Handle(TColStd_HArray1OfReal) aParams = new TColStd_HArray1OfReal (1, aNbNodes);
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream >> aParams->ChangeValue (aNodeIter);
aResult->SetParameters (aParams);
}
myPolygonPos.Bind (aPosition, aResult);
}
return aResult;
}
//=======================================================================
//function : ReadTriangulation
//purpose :
//=======================================================================
Handle(Poly_Triangulation) BinTools_ShapeReader::ReadTriangulation (BinTools_IStream& theStream)
{
Handle(Poly_Triangulation) aResult;
uint64_t aPosition = theStream.Position();
const BinTools_ObjectType& aType = theStream.ReadType();
if (theStream.IsReference())
{ // get by reference
uint64_t aRef = theStream.ReadReference();
const Handle(Poly_Triangulation)* aFound = myTriangulationPos.Seek (aRef);
if (aFound) // the location is already retrieved
return *aFound;
uint64_t aCurrent = theStream.Position();
theStream.GoTo (aRef); // go to the referenced position
aResult = ReadTriangulation (theStream);
theStream.GoTo (aCurrent); // returns to the current position
}
else if (aType == BinTools_ObjectType_Triangulation)
{ // read from the stream
Standard_Integer aNbNodes = theStream.ReadInteger();
Standard_Integer aNbTriangles = theStream.ReadInteger();
Standard_Boolean aHasUV = theStream.ReadBool();
Standard_Boolean aHasNormals = theStream.ReadBool();
aResult = new Poly_Triangulation (aNbNodes, aNbTriangles, aHasUV, aHasNormals);
aResult->Deflection (theStream.ReadReal());
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
aResult->SetNode(aNodeIter, theStream.ReadPnt());
if (aHasUV)
{
gp_Pnt2d anUV;
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
{
theStream >> anUV.ChangeCoord().ChangeCoord (1);
theStream >> anUV.ChangeCoord().ChangeCoord (2);
aResult->SetUVNode(aNodeIter, anUV);
}
}
// read the triangles
Poly_Triangle aTriangle;
for (Standard_Integer aTriIter = 1; aTriIter <= aNbTriangles; ++aTriIter)
{
theStream >> aTriangle.ChangeValue (1);
theStream >> aTriangle.ChangeValue (2);
theStream >> aTriangle.ChangeValue (3);
aResult->SetTriangle(aTriIter, aTriangle);
}
if (aHasNormals)
{
gp_Vec3f aNormal;
for (Standard_Integer aNormalIter = 1; aNormalIter <= aNbNodes; ++aNormalIter)
{
theStream >> aNormal.x();
theStream >> aNormal.y();
theStream >> aNormal.z();
aResult->SetNormal (aNormalIter, aNormal);
}
}
myTriangulationPos.Bind (aPosition, aResult);
}
return aResult;
}

View File

@ -0,0 +1,78 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinTools_ShapeReader_HeaderFile
#define _BinTools_ShapeReader_HeaderFile
#include <BinTools_ShapeSetBase.hxx>
#include <BinTools_IStream.hxx>
#include <NCollection_DataMap.hxx>
class TopLoc_Location;
class Geom_Curve;
class Geom2d_Curve;
class Geom_Surface;
class Poly_Polygon3D;
class Poly_PolygonOnTriangulation;
class Poly_Triangulation;
//! Reads topology from IStream in binary format without grouping of objects by types
//! and using relative positions in a file as references.
class BinTools_ShapeReader : public BinTools_ShapeSetBase
{
public:
DEFINE_STANDARD_ALLOC
//! Initializes a shape reader.
Standard_EXPORT BinTools_ShapeReader();
Standard_EXPORT virtual ~BinTools_ShapeReader();
//! Clears the content of the set.
Standard_EXPORT virtual void Clear() Standard_OVERRIDE;
//! Reads the shape from stream using previously restored shapes and objects by references.
Standard_EXPORT void Read (Standard_IStream& theStream, TopoDS_Shape& theShape) Standard_OVERRIDE;
//! Reads location from the stream.
Standard_EXPORT const TopLoc_Location* ReadLocation (BinTools_IStream& theStream);
private:
//! Reads the shape from stream using previously restored shapes and objects by references.
TopoDS_Shape ReadShape (BinTools_IStream& theStream);
//! Reads curve from the stream.
Handle(Geom_Curve) ReadCurve (BinTools_IStream& theStream);
//! Reads curve2d from the stream.
Handle(Geom2d_Curve) ReadCurve2d (BinTools_IStream& theStream);
//! Reads surface from the stream.
Handle(Geom_Surface) ReadSurface (BinTools_IStream& theStream);
//! Reads ploygon3d from the stream.
Handle(Poly_Polygon3D) ReadPolygon3d (BinTools_IStream& theStream);
//! Reads polygon on triangulation from the stream.
Handle(Poly_PolygonOnTriangulation) ReadPolygon (BinTools_IStream& theStream);
//! Reads triangulation from the stream.
Handle(Poly_Triangulation) ReadTriangulation (BinTools_IStream& theStream);
/// position of the shape previously restored
NCollection_DataMap<uint64_t, TopoDS_Shape> myShapePos;
NCollection_DataMap<uint64_t, TopLoc_Location> myLocationPos;
NCollection_DataMap<uint64_t, Handle(Geom_Curve)> myCurvePos;
NCollection_DataMap<uint64_t, Handle(Geom2d_Curve)> myCurve2dPos;
NCollection_DataMap<uint64_t, Handle(Geom_Surface)> mySurfacePos;
NCollection_DataMap<uint64_t, Handle(Poly_Polygon3D)> myPolygon3dPos;
NCollection_DataMap<uint64_t, Handle(Poly_PolygonOnTriangulation)> myPolygonPos;
NCollection_DataMap<uint64_t, Handle(Poly_Triangulation)> myTriangulationPos;
};
#endif // _BinTools_ShapeReader_HeaderFile

View File

@ -54,37 +54,13 @@
#include <Message_ProgressRange.hxx> #include <Message_ProgressRange.hxx>
#include <string.h> #include <string.h>
//#define MDTV_DEB 1
const Standard_CString BinTools_ShapeSet::THE_ASCII_VERSIONS[BinTools_FormatVersion_UPPER + 1] =
{
"",
"Open CASCADE Topology V1 (c)",
"Open CASCADE Topology V2 (c)",
"Open CASCADE Topology V3 (c)",
"Open CASCADE Topology V4, (c) Open Cascade"
};
//=======================================================================
//function : operator << (gp_Pnt)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Pnt P)
{
BinTools::PutReal(OS, P.X());
BinTools::PutReal(OS, P.Y());
BinTools::PutReal(OS, P.Z());
return OS;
}
//======================================================================= //=======================================================================
//function : BinTools_ShapeSet //function : BinTools_ShapeSet
//purpose : //purpose :
//======================================================================= //=======================================================================
BinTools_ShapeSet::BinTools_ShapeSet () BinTools_ShapeSet::BinTools_ShapeSet ()
: myFormatNb (BinTools_FormatVersion_CURRENT), : BinTools_ShapeSetBase ()
myWithTriangles (Standard_False),
myWithNormals(Standard_False)
{} {}
//======================================================================= //=======================================================================
@ -95,28 +71,6 @@ BinTools_ShapeSet::BinTools_ShapeSet ()
BinTools_ShapeSet::~BinTools_ShapeSet() BinTools_ShapeSet::~BinTools_ShapeSet()
{} {}
//=======================================================================
//function : SetFormatNb
//purpose :
//=======================================================================
void BinTools_ShapeSet::SetFormatNb(const Standard_Integer theFormatNb)
{
Standard_ASSERT_RETURN(theFormatNb >= BinTools_FormatVersion_LOWER &&
theFormatNb <= BinTools_FormatVersion_UPPER,
"Error: unsupported BinTools version.", );
myFormatNb = theFormatNb;
}
//=======================================================================
//function : FormatNb
//purpose :
//=======================================================================
Standard_Integer BinTools_ShapeSet::FormatNb() const
{
return myFormatNb;
}
//======================================================================= //=======================================================================
//function : Clear //function : Clear
//purpose : //purpose :
@ -139,18 +93,18 @@ void BinTools_ShapeSet::Clear()
//purpose : //purpose :
//======================================================================= //=======================================================================
Standard_Integer BinTools_ShapeSet::Add(const TopoDS_Shape& theShape) Standard_Integer BinTools_ShapeSet::Add (const TopoDS_Shape& theShape)
{ {
if (theShape.IsNull()) return 0; if (theShape.IsNull()) return 0;
myLocations.Add(theShape.Location()); myLocations.Add(theShape.Location());
TopoDS_Shape aS2 = theShape; TopoDS_Shape aS2 = theShape;
aS2.Location(TopLoc_Location()); aS2.Location (TopLoc_Location());
Standard_Integer anIndex = myShapes.FindIndex(aS2); Standard_Integer anIndex = myShapes.FindIndex (aS2);
if (anIndex == 0) { if (anIndex == 0) {
AddGeometry(aS2); AddShape (aS2);
for (TopoDS_Iterator its(aS2,Standard_False,Standard_False);its.More(); its.Next()) for (TopoDS_Iterator its (aS2, Standard_False, Standard_False); its.More(); its.Next())
Add(its.Value()); Add (its.Value());
anIndex = myShapes.Add(aS2); anIndex = myShapes.Add (aS2);
} }
return anIndex; return anIndex;
} }
@ -161,9 +115,9 @@ Standard_Integer BinTools_ShapeSet::Add(const TopoDS_Shape& theShape)
//purpose : //purpose :
//======================================================================= //=======================================================================
const TopoDS_Shape& BinTools_ShapeSet::Shape(const Standard_Integer theIndx)const const TopoDS_Shape& BinTools_ShapeSet::Shape (const Standard_Integer theIndx)
{ {
return myShapes(theIndx); return myShapes (theIndx);
} }
//======================================================================= //=======================================================================
@ -171,9 +125,9 @@ const TopoDS_Shape& BinTools_ShapeSet::Shape(const Standard_Integer theIndx)con
//purpose : //purpose :
//======================================================================= //=======================================================================
Standard_Integer BinTools_ShapeSet::Index(const TopoDS_Shape& theShape) const Standard_Integer BinTools_ShapeSet::Index (const TopoDS_Shape& theShape) const
{ {
return myShapes.FindIndex(theShape); return myShapes.FindIndex (theShape);
} }
//======================================================================= //=======================================================================
@ -181,7 +135,7 @@ Standard_Integer BinTools_ShapeSet::Index(const TopoDS_Shape& theShape) const
//purpose : //purpose :
//======================================================================= //=======================================================================
const BinTools_LocationSet& BinTools_ShapeSet::Locations()const const BinTools_LocationSet& BinTools_ShapeSet::Locations() const
{ {
return myLocations; return myLocations;
} }
@ -202,7 +156,7 @@ BinTools_LocationSet& BinTools_ShapeSet::ChangeLocations()
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_ShapeSet::AddGeometry(const TopoDS_Shape& S) void BinTools_ShapeSet::AddShape (const TopoDS_Shape& S)
{ {
// Add the geometry // Add the geometry
@ -259,7 +213,7 @@ void BinTools_ShapeSet::AddGeometry(const TopoDS_Shape& S)
mySurfaces.Add(CR->Surface2()); mySurfaces.Add(CR->Surface2());
ChangeLocations().Add(CR->Location2()); ChangeLocations().Add(CR->Location2());
} }
else if (myWithTriangles) { else if (IsWithTriangles()) {
if (CR->IsPolygon3D()) { if (CR->IsPolygon3D()) {
if (!CR->Polygon3D().IsNull()) { if (!CR->Polygon3D().IsNull()) {
myPolygons3D.Add(CR->Polygon3D()); myPolygons3D.Add(CR->Polygon3D());
@ -292,7 +246,7 @@ void BinTools_ShapeSet::AddGeometry(const TopoDS_Shape& S)
else if (S.ShapeType() == TopAbs_FACE) { else if (S.ShapeType() == TopAbs_FACE) {
// Add the surface geometry // Add the surface geometry
Standard_Boolean needNormals(myWithNormals); Standard_Boolean needNormals (IsWithNormals());
Handle(BRep_TFace) TF = Handle(BRep_TFace)::DownCast(S.TShape()); Handle(BRep_TFace) TF = Handle(BRep_TFace)::DownCast(S.TShape());
if (!TF->Surface().IsNull()) if (!TF->Surface().IsNull())
{ {
@ -302,8 +256,7 @@ void BinTools_ShapeSet::AddGeometry(const TopoDS_Shape& S)
{ {
needNormals = Standard_True; needNormals = Standard_True;
} }
if (myWithTriangles if (IsWithTriangles() || TF->Surface().IsNull())
|| TF->Surface().IsNull())
{ {
Handle(Poly_Triangulation) Tr = TF->Triangulation(); Handle(Poly_Triangulation) Tr = TF->Triangulation();
if (!Tr.IsNull()) myTriangulations.Add(Tr, needNormals); if (!Tr.IsNull()) myTriangulations.Add(Tr, needNormals);
@ -346,10 +299,10 @@ void BinTools_ShapeSet::WriteGeometry (Standard_OStream& OS,
//======================================================================= //=======================================================================
void BinTools_ShapeSet::Write (Standard_OStream& OS, void BinTools_ShapeSet::Write (Standard_OStream& OS,
const Message_ProgressRange& theRange)const const Message_ProgressRange& theRange)
{ {
// write the copyright // write the copyright
OS << "\n" << THE_ASCII_VERSIONS[myFormatNb] << "\n"; OS << "\n" << THE_ASCII_VERSIONS[FormatNb()] << "\n";
//----------------------------------------- //-----------------------------------------
// write the locations // write the locations
@ -378,13 +331,13 @@ void BinTools_ShapeSet::Write (Standard_OStream& OS,
// subshapes are written first // subshapes are written first
for (i = 1; i <= nbShapes && aPSinner.More(); i++, aPSinner.Next()) { for (i = 1; i <= nbShapes && aPSinner.More(); i++, aPSinner.Next()) {
const TopoDS_Shape& S = myShapes(i); const TopoDS_Shape& S = myShapes (i);
// Type // Type
OS << (Standard_Byte)S.ShapeType(); OS << (Standard_Byte)S.ShapeType();
// Geometry // Geometry
WriteGeometry(S,OS); WriteShape (S, OS);
// Flags // Flags
BinTools::PutBool(OS, S.Free()? 1:0); BinTools::PutBool(OS, S.Free()? 1:0);
@ -410,11 +363,9 @@ void BinTools_ShapeSet::Write (Standard_OStream& OS,
//function : Read //function : Read
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_ShapeSet::Read (Standard_IStream& IS, void BinTools_ShapeSet::Read (Standard_IStream& IS,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
Clear(); Clear();
// Check the version // Check the version
@ -454,7 +405,6 @@ void BinTools_ShapeSet::Read (Standard_IStream& IS,
//----------------------------------------- //-----------------------------------------
// read the locations // read the locations
//----------------------------------------- //-----------------------------------------
myLocations.Read(IS); myLocations.Read(IS);
//----------------------------------------- //-----------------------------------------
// read the geometry // read the geometry
@ -479,16 +429,43 @@ void BinTools_ShapeSet::Read (Standard_IStream& IS,
IS >> nbShapes; IS >> nbShapes;
IS.get();//remove lf IS.get();//remove lf
Message_ProgressScope aPSinner(aPSouter.Next(), "Reading Shapes", nbShapes); Message_ProgressScope aPSinner(aPSouter.Next(), "Reading Shapes", nbShapes);
for (int i = 1; i <= nbShapes && aPSinner.More(); i++, aPSinner.Next()) { for (int i = 1; i <= nbShapes && aPSinner.More(); i++, aPSinner.Next())
{
TopoDS_Shape S; TopoDS_Shape S;
TopAbs_ShapeEnum T = (TopAbs_ShapeEnum)IS.get();
ReadShape (T, IS, S);
ReadFlagsAndSubs (S, T, IS, nbShapes);
myShapes.Add (S);
}
}
//Read type and create empty shape. //=======================================================================
//function : Write
//purpose :
//=======================================================================
TopAbs_ShapeEnum T = (TopAbs_ShapeEnum) IS.get(); void BinTools_ShapeSet::Write (const TopoDS_Shape& S,
Standard_OStream& OS)
{
if (S.IsNull())
ReadGeometry(T,IS,S); OS << '*';
else {
// {TopAbs_FORWARD, TopAbs_REVERSED, TopAbs_INTERNAL, TopAbs_EXTERNAL}
OS << (Standard_Byte) S.Orientation();
BinTools::PutInteger (OS, myShapes.Extent() - myShapes.FindIndex (S.Located (TopLoc_Location())) + 1);
BinTools::PutInteger (OS, Locations().Index (S.Location()));
}
}
//=======================================================================
//function : ReadFlagsAndSubs
//purpose :
//=======================================================================
void BinTools_ShapeSet::ReadFlagsAndSubs(TopoDS_Shape& S, const TopAbs_ShapeEnum T,
Standard_IStream& IS, const Standard_Integer nbShapes)
{
// Set the flags // Set the flags
Standard_Boolean aFree, aMod, aChecked, anOrient, aClosed, anInf, aConv; Standard_Boolean aFree, aMod, aChecked, anOrient, aClosed, anInf, aConv;
BinTools::GetBool(IS, aFree); BinTools::GetBool(IS, aFree);
@ -502,71 +479,49 @@ void BinTools_ShapeSet::Read (Standard_IStream& IS,
// sub-shapes // sub-shapes
TopoDS_Shape SS; TopoDS_Shape SS;
do { do {
Read(SS,IS,nbShapes); ReadSubs(SS, IS, nbShapes);
if (!SS.IsNull()) if (!SS.IsNull())
AddShapes(S,SS); AddShapes(S, SS);
} while(!SS.IsNull()); } while (!SS.IsNull());
S.Free(aFree); S.Free(aFree);
S.Modified(aMod); S.Modified(aMod);
if (myFormatNb != BinTools_FormatVersion_VERSION_2 if (FormatNb() != BinTools_FormatVersion_VERSION_2 &&
&& myFormatNb != BinTools_FormatVersion_VERSION_3) FormatNb() != BinTools_FormatVersion_VERSION_3)
{ {
aChecked = false; // force check at reading aChecked = false; // force check at reading
} }
S.Checked (aChecked); S.Checked (aChecked);
S.Orientable(anOrient); S.Orientable (anOrient);
S.Closed (aClosed); S.Closed (aClosed);
S.Infinite (anInf); S.Infinite (anInf);
S.Convex (aConv); S.Convex (aConv);
// check // check
if (myFormatNb == BinTools_FormatVersion_VERSION_1) if (FormatNb() == BinTools_FormatVersion_VERSION_1)
if(T == TopAbs_FACE) { if (T == TopAbs_FACE) {
const TopoDS_Face& F = TopoDS::Face(S); const TopoDS_Face& F = TopoDS::Face(S);
BRepTools::Update(F); BRepTools::Update(F);
} }
myShapes.Add(S);
}
} }
//======================================================================= //=======================================================================
//function : Write //function : ReadSubs
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_ShapeSet::ReadSubs(TopoDS_Shape& S, Standard_IStream& IS,
void BinTools_ShapeSet::Write (const TopoDS_Shape& S, const Standard_Integer nbshapes)
Standard_OStream& OS)const
{
if (S.IsNull())
OS << '*';
else {
// {TopAbs_FORWARD, TopAbs_REVERSED, TopAbs_INTERNAL, TopAbs_EXTERNAL}
OS << (Standard_Byte) S.Orientation();
BinTools::PutInteger(OS, myShapes.Extent() - myShapes.FindIndex(S.Located(TopLoc_Location())) + 1);
BinTools::PutInteger(OS, Locations().Index(S.Location()));
}
}
//=======================================================================
//function : Read
//purpose :
//=======================================================================
void BinTools_ShapeSet::Read (TopoDS_Shape& S, Standard_IStream& IS,
const Standard_Integer nbshapes)const
{ {
Standard_Character aChar = '\0'; Standard_Character aChar = '\0';
IS >> aChar; IS >> aChar;
if(aChar == '*') if (aChar == '*')
S = TopoDS_Shape(); S = TopoDS_Shape();
else { else {
TopAbs_Orientation anOrient; TopAbs_Orientation anOrient;
anOrient = (TopAbs_Orientation)aChar; anOrient = (TopAbs_Orientation)aChar;
Standard_Integer anIndx; Standard_Integer anIndx;
BinTools::GetInteger(IS, anIndx); BinTools::GetInteger(IS, anIndx);
S = myShapes(nbshapes - anIndx + 1); S = Shape (nbshapes - anIndx + 1);
S.Orientation(anOrient); S.Orientation(anOrient);
Standard_Integer l; Standard_Integer l;
@ -583,22 +538,28 @@ void BinTools_ShapeSet::Read (TopoDS_Shape& S, Standard_IStream& IS,
void BinTools_ShapeSet::ReadGeometry (Standard_IStream& IS, void BinTools_ShapeSet::ReadGeometry (Standard_IStream& IS,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
Message_ProgressScope aPS(theRange, "Reading geomentry", 6);
Message_ProgressScope aPS(theRange, "Reading geometry", 6);
myCurves2d.Read(IS, aPS.Next()); myCurves2d.Read(IS, aPS.Next());
if (!aPS.More()) if (!aPS.More())
return; return;
myCurves.Read(IS, aPS.Next()); myCurves.Read(IS, aPS.Next());
if (!aPS.More()) if (!aPS.More())
return; return;
ReadPolygon3D(IS, aPS.Next()); ReadPolygon3D(IS, aPS.Next());
if (!aPS.More()) if (!aPS.More())
return; return;
ReadPolygonOnTriangulation(IS, aPS.Next()); ReadPolygonOnTriangulation(IS, aPS.Next());
if (!aPS.More()) if (!aPS.More())
return; return;
mySurfaces.Read(IS, aPS.Next()); mySurfaces.Read(IS, aPS.Next());
if (!aPS.More()) if (!aPS.More())
return; return;
ReadTriangulation(IS, aPS.Next()); ReadTriangulation(IS, aPS.Next());
} }
@ -607,8 +568,8 @@ void BinTools_ShapeSet::ReadGeometry (Standard_IStream& IS,
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_ShapeSet::WriteGeometry (const TopoDS_Shape& S, void BinTools_ShapeSet::WriteShape (const TopoDS_Shape& S,
Standard_OStream& OS)const Standard_OStream& OS) const
{ {
// Write the geometry // Write the geometry
try { try {
@ -714,8 +675,8 @@ void BinTools_ShapeSet::WriteGeometry (const TopoDS_Shape& S,
BinTools::PutReal(OS, last); BinTools::PutReal(OS, last);
// Write UV Points for higher performance // Write UV Points for higher performance
if (myFormatNb == BinTools_FormatVersion_VERSION_2 if (FormatNb() == BinTools_FormatVersion_VERSION_2
|| myFormatNb == BinTools_FormatVersion_VERSION_3) || FormatNb() == BinTools_FormatVersion_VERSION_3)
{ {
gp_Pnt2d Pf,Pl; gp_Pnt2d Pf,Pl;
if (CR->IsCurveOnClosedSurface()) { if (CR->IsCurveOnClosedSurface()) {
@ -743,7 +704,7 @@ void BinTools_ShapeSet::WriteGeometry (const TopoDS_Shape& S,
} }
else if (myWithTriangles) { else if (IsWithTriangles()) {
if (CR->IsPolygon3D()) { if (CR->IsPolygon3D()) {
Handle(BRep_Polygon3D) GC = Handle(BRep_Polygon3D)::DownCast(itrc.Value()); Handle(BRep_Polygon3D) GC = Handle(BRep_Polygon3D)::DownCast(itrc.Value());
if (!GC->Polygon3D().IsNull()) { if (!GC->Polygon3D().IsNull()) {
@ -793,8 +754,7 @@ void BinTools_ShapeSet::WriteGeometry (const TopoDS_Shape& S,
: 0); : 0);
BinTools::PutInteger (OS, Locations().Index (TF->Location())); BinTools::PutInteger (OS, Locations().Index (TF->Location()));
if (myWithTriangles if (IsWithTriangles() || TF->Surface().IsNull())
|| TF->Surface().IsNull())
{ {
if (!(TF->Triangulation()).IsNull()) { if (!(TF->Triangulation()).IsNull()) {
OS << (Standard_Byte) 2; OS << (Standard_Byte) 2;
@ -815,19 +775,19 @@ void BinTools_ShapeSet::WriteGeometry (const TopoDS_Shape& S,
} }
//======================================================================= //=======================================================================
//function : ReadGeometry //function : ReadShape
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T, void BinTools_ShapeSet::ReadShape (const TopAbs_ShapeEnum T,
Standard_IStream& IS, Standard_IStream& IS,
TopoDS_Shape& S) TopoDS_Shape& S)
{ {
// Read the geometry // Read the geometry
Standard_Integer val, c,pc,pc2 = 0,s,s2,l,l2,t, pt, pt2 = 0; Standard_Integer val, c, pc, pc2 = 0, s, s2, l, l2, t, pt, pt2 = 0;
Standard_Real tol,X,Y,Z,first,last,p1 = 0.,p2; Standard_Real tol, X, Y, Z, first, last, p1 = 0., p2;
Standard_Real PfX,PfY,PlX,PlY; Standard_Real PfX, PfY, PlX, PlY;
gp_Pnt2d aPf, aPl; gp_Pnt2d aPf, aPl;
Standard_Boolean closed, bval; Standard_Boolean closed, bval;
GeomAbs_Shape reg = GeomAbs_C0; GeomAbs_Shape reg = GeomAbs_C0;
@ -840,10 +800,8 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// vertex // vertex
//--------- //---------
case TopAbs_VERTEX : case TopAbs_VERTEX:
{ {
// Standard_Integer aPos = IS.tellg();
// std::cout << "\nPOS = " << aPos << std::endl;
TopoDS_Vertex& V = TopoDS::Vertex(S); TopoDS_Vertex& V = TopoDS::Vertex(S);
// Read the point geometry // Read the point geometry
@ -851,25 +809,26 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
BinTools::GetReal(IS, X); BinTools::GetReal(IS, X);
BinTools::GetReal(IS, Y); BinTools::GetReal(IS, Y);
BinTools::GetReal(IS, Z); BinTools::GetReal(IS, Z);
gp_Pnt aPnt (X, Y, Z); gp_Pnt aPnt(X, Y, Z);
myBuilder.MakeVertex (V, aPnt, tol); myBuilder.MakeVertex(V, aPnt, tol);
Handle(BRep_TVertex) TV = Handle(BRep_TVertex)::DownCast(V.TShape()); Handle(BRep_TVertex) TV = Handle(BRep_TVertex)::DownCast(V.TShape());
BRep_ListOfPointRepresentation& lpr = TV->ChangePoints(); BRep_ListOfPointRepresentation& lpr = TV->ChangePoints();
TopLoc_Location L; TopLoc_Location L;
do { do {
if(myFormatNb == BinTools_FormatVersion_VERSION_3) { if (FormatNb() == BinTools_FormatVersion_VERSION_3) {
val = (Standard_Integer)IS.get();//case {0|1|2|3} val = (Standard_Integer)IS.get();//case {0|1|2|3}
if (val > 0 && val <= 3) if (val > 0 && val <= 3)
BinTools::GetReal(IS, p1); BinTools::GetReal(IS, p1);
} else { }
else {
std::streampos aPos = IS.tellg(); std::streampos aPos = IS.tellg();
BinTools::GetReal(IS, p1); BinTools::GetReal(IS, p1);
val = (Standard_Integer)IS.get();//case {0|1|2|3} val = (Standard_Integer)IS.get();//case {0|1|2|3}
#ifdef OCCT_DEBUG #ifdef OCCT_DEBUG
std::cout << "\nVal = " << val <<std::endl; std::cout << "\nVal = " << val << std::endl;
#endif #endif
if(val != 1 && val !=2 && val !=3){ if (val != 1 && val != 2 && val != 3) {
IS.seekg(aPos); IS.seekg(aPos);
val = (Standard_Integer)IS.get(); val = (Standard_Integer)IS.get();
if (val > 0 && val <= 3) if (val > 0 && val <= 3)
@ -878,10 +837,10 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
} }
Handle(BRep_PointRepresentation) PR; Handle(BRep_PointRepresentation) PR;
switch (val) { switch (val) {
case 0 : case 0:
break; break;
case 1 : case 1:
{ {
BinTools::GetInteger(IS, c); BinTools::GetInteger(IS, c);
if (myCurves.Curve(c).IsNull()) if (myCurves.Curve(c).IsNull())
@ -894,7 +853,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
} }
break; break;
case 2 : case 2:
{ {
BinTools::GetInteger(IS, pc); BinTools::GetInteger(IS, pc);
BinTools::GetInteger(IS, s); BinTools::GetInteger(IS, s);
@ -911,7 +870,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
} }
break; break;
case 3 : case 3:
{ {
BinTools::GetReal(IS, p2); BinTools::GetReal(IS, p2);
BinTools::GetInteger(IS, s); BinTools::GetInteger(IS, s);
@ -919,7 +878,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
break; break;
Handle(BRep_PointOnSurface) POC = Handle(BRep_PointOnSurface) POC =
new BRep_PointOnSurface(p1,p2, new BRep_PointOnSurface(p1, p2,
mySurfaces.Surface(s), mySurfaces.Surface(s),
L); L);
PR = POC; PR = POC;
@ -929,7 +888,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
default: default:
{ {
Standard_SStream aMsg; Standard_SStream aMsg;
aMsg << "BinTools_SurfaceSet::ReadGeometry: UnExpected BRep_PointRepresentation = "<< val <<std::endl; aMsg << "BinTools_SurfaceSet::ReadGeometry: UnExpected BRep_PointRepresentation = " << val << std::endl;
throw Standard_Failure(aMsg.str().c_str()); throw Standard_Failure(aMsg.str().c_str());
} }
} }
@ -952,7 +911,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
//--------- //---------
case TopAbs_EDGE : case TopAbs_EDGE:
// Create an edge // Create an edge
{ {
@ -966,10 +925,10 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
myBuilder.SameParameter(E, bval); myBuilder.SameParameter(E, bval);
BinTools::GetBool(IS, bval); BinTools::GetBool(IS, bval);
myBuilder.SameRange(E,bval); myBuilder.SameRange(E, bval);
BinTools::GetBool(IS, bval); BinTools::GetBool(IS, bval);
myBuilder.Degenerated(E,bval); myBuilder.Degenerated(E, bval);
do { do {
val = (Standard_Integer)IS.get();//{0|1|2|3|4|5|6|7} val = (Standard_Integer)IS.get();//{0|1|2|3|4|5|6|7}
@ -986,24 +945,24 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
case 0: case 0:
break; break;
case 1 : // -1- Curve 3D case 1: // -1- Curve 3D
BinTools::GetInteger(IS, c); BinTools::GetInteger(IS, c);
BinTools::GetInteger(IS, l); BinTools::GetInteger(IS, l);
if (!myCurves.Curve(c).IsNull()) { if (!myCurves.Curve(c).IsNull()) {
myBuilder.UpdateEdge(E,myCurves.Curve(c), myBuilder.UpdateEdge(E, myCurves.Curve(c),
Locations().Location(l),tol); Locations().Location(l), tol);
} }
BinTools::GetReal(IS, first); BinTools::GetReal(IS, first);
BinTools::GetReal(IS, last); BinTools::GetReal(IS, last);
if (!myCurves.Curve(c).IsNull()) { if (!myCurves.Curve(c).IsNull()) {
Standard_Boolean Only3d = Standard_True; Standard_Boolean Only3d = Standard_True;
myBuilder.Range(E,first,last,Only3d); myBuilder.Range(E, first, last, Only3d);
} }
break; break;
case 2 : // -2- Curve on surf case 2: // -2- Curve on surf
case 3 : // -3- Curve on closed surf case 3: // -3- Curve on closed surf
closed = (val == 3); closed = (val == 3);
BinTools::GetInteger(IS, pc); BinTools::GetInteger(IS, pc);
if (closed) { if (closed) {
@ -1020,15 +979,15 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
BinTools::GetReal(IS, last); BinTools::GetReal(IS, last);
// read UV Points // for XML Persistence higher performance // read UV Points // for XML Persistence higher performance
if (myFormatNb == BinTools_FormatVersion_VERSION_2 if (FormatNb() == BinTools_FormatVersion_VERSION_2
|| myFormatNb == BinTools_FormatVersion_VERSION_3) || FormatNb() == BinTools_FormatVersion_VERSION_3)
{ {
BinTools::GetReal(IS, PfX); BinTools::GetReal(IS, PfX);
BinTools::GetReal(IS, PfY); BinTools::GetReal(IS, PfY);
BinTools::GetReal(IS, PlX); BinTools::GetReal(IS, PlX);
BinTools::GetReal(IS, PlY); BinTools::GetReal(IS, PlY);
aPf = gp_Pnt2d(PfX,PfY); aPf = gp_Pnt2d(PfX, PfY);
aPl = gp_Pnt2d(PlX,PlY); aPl = gp_Pnt2d(PlX, PlY);
} }
if (myCurves2d.Curve2d(pc).IsNull() || if (myCurves2d.Curve2d(pc).IsNull() ||
@ -1037,21 +996,21 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
break; break;
if (closed) { if (closed) {
if (myFormatNb == BinTools_FormatVersion_VERSION_2 if (FormatNb() == BinTools_FormatVersion_VERSION_2
|| myFormatNb == BinTools_FormatVersion_VERSION_3) || FormatNb() == BinTools_FormatVersion_VERSION_3)
{ {
myBuilder.UpdateEdge(E,myCurves2d.Curve2d(pc), myBuilder.UpdateEdge(E, myCurves2d.Curve2d(pc),
myCurves2d.Curve2d(pc2), myCurves2d.Curve2d(pc2),
mySurfaces.Surface(s), mySurfaces.Surface(s),
Locations().Location(l),tol, Locations().Location(l), tol,
aPf, aPl); aPf, aPl);
} }
else else
{ {
myBuilder.UpdateEdge(E,myCurves2d.Curve2d(pc), myBuilder.UpdateEdge(E, myCurves2d.Curve2d(pc),
myCurves2d.Curve2d(pc2), myCurves2d.Curve2d(pc2),
mySurfaces.Surface(s), mySurfaces.Surface(s),
Locations().Location(l),tol); Locations().Location(l), tol);
} }
myBuilder.Continuity(E, myBuilder.Continuity(E,
@ -1063,28 +1022,28 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
} }
else else
{ {
if (myFormatNb == BinTools_FormatVersion_VERSION_2 if (FormatNb() == BinTools_FormatVersion_VERSION_2
|| myFormatNb == BinTools_FormatVersion_VERSION_3) || FormatNb() == BinTools_FormatVersion_VERSION_3)
{ {
myBuilder.UpdateEdge(E,myCurves2d.Curve2d(pc), myBuilder.UpdateEdge(E, myCurves2d.Curve2d(pc),
mySurfaces.Surface(s), mySurfaces.Surface(s),
Locations().Location(l),tol, Locations().Location(l), tol,
aPf, aPl); aPf, aPl);
} }
else else
{ {
myBuilder.UpdateEdge(E,myCurves2d.Curve2d(pc), myBuilder.UpdateEdge(E, myCurves2d.Curve2d(pc),
mySurfaces.Surface(s), mySurfaces.Surface(s),
Locations().Location(l),tol); Locations().Location(l), tol);
} }
} }
myBuilder.Range(E, myBuilder.Range(E,
mySurfaces.Surface(s), mySurfaces.Surface(s),
Locations().Location(l), Locations().Location(l),
first,last); first, last);
break; break;
case 4 : // -4- Regularity case 4: // -4- Regularity
reg = (GeomAbs_Shape)IS.get(); reg = (GeomAbs_Shape)IS.get();
BinTools::GetInteger(IS, s); BinTools::GetInteger(IS, s);
BinTools::GetInteger(IS, l); BinTools::GetInteger(IS, l);
@ -1101,15 +1060,15 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
reg); reg);
break; break;
case 5 : // -5- Polygon3D case 5: // -5- Polygon3D
BinTools::GetInteger(IS, c); BinTools::GetInteger(IS, c);
BinTools::GetInteger(IS, l); BinTools::GetInteger(IS, l);
//??? Bug? myBuilder.UpdateEdge(E,myPolygons3D(c)); //??? Bug? myBuilder.UpdateEdge(E,myPolygons3D(c));
myBuilder.UpdateEdge(E, myPolygons3D(c), Locations().Location(l)); myBuilder.UpdateEdge(E, myPolygons3D(c), Locations().Location(l));
break; break;
case 6 : // -6- Polygon on triangulation case 6: // -6- Polygon on triangulation
case 7 : // -7- Polygon on closed triangulation case 7: // -7- Polygon on closed triangulation
closed = (val == 7); closed = (val == 7);
BinTools::GetInteger(IS, pt); BinTools::GetInteger(IS, pt);
if (closed) if (closed)
@ -1130,7 +1089,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
default: default:
{ {
Standard_SStream aMsg; Standard_SStream aMsg;
aMsg <<"Unexpected Curve Representation ="<< val << std::endl; aMsg << "Unexpected Curve Representation =" << val << std::endl;
throw Standard_Failure(aMsg.str().c_str()); throw Standard_Failure(aMsg.str().c_str());
} }
@ -1144,7 +1103,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// wire // wire
//--------- //---------
case TopAbs_WIRE : case TopAbs_WIRE:
myBuilder.MakeWire(TopoDS::Wire(S)); myBuilder.MakeWire(TopoDS::Wire(S));
break; break;
@ -1153,7 +1112,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// face // face
//--------- //---------
case TopAbs_FACE : case TopAbs_FACE:
{ {
// create a face : // create a face :
TopoDS_Face& F = TopoDS::Face(S); TopoDS_Face& F = TopoDS::Face(S);
@ -1162,15 +1121,15 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
BinTools::GetReal(IS, tol); BinTools::GetReal(IS, tol);
BinTools::GetInteger(IS, s); //surface indx BinTools::GetInteger(IS, s); //surface indx
BinTools::GetInteger(IS, l); //location indx BinTools::GetInteger(IS, l); //location indx
myBuilder.UpdateFace (F, myBuilder.UpdateFace(F,
s > 0 ? mySurfaces.Surface(s) : Handle(Geom_Surface)(), s > 0 ? mySurfaces.Surface(s) : Handle(Geom_Surface)(),
Locations().Location(l), Locations().Location(l),
tol); tol);
myBuilder.NaturalRestriction (F, bval); myBuilder.NaturalRestriction(F, bval);
Standard_Byte aByte = (Standard_Byte)IS.get(); Standard_Byte aByte = (Standard_Byte)IS.get();
// cas triangulation // cas triangulation
if(aByte == 2) { if (aByte == 2) {
BinTools::GetInteger(IS, s); BinTools::GetInteger(IS, s);
myBuilder.UpdateFace(TopoDS::Face(S), myTriangulations.FindKey(s)); myBuilder.UpdateFace(TopoDS::Face(S), myTriangulations.FindKey(s));
} }
@ -1182,7 +1141,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// shell // shell
//--------- //---------
case TopAbs_SHELL : case TopAbs_SHELL:
myBuilder.MakeShell(TopoDS::Shell(S)); myBuilder.MakeShell(TopoDS::Shell(S));
break; break;
@ -1191,7 +1150,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// solid // solid
//--------- //---------
case TopAbs_SOLID : case TopAbs_SOLID:
myBuilder.MakeSolid(TopoDS::Solid(S)); myBuilder.MakeSolid(TopoDS::Solid(S));
break; break;
@ -1200,7 +1159,7 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// compsolid // compsolid
//--------- //---------
case TopAbs_COMPSOLID : case TopAbs_COMPSOLID:
myBuilder.MakeCompSolid(TopoDS::CompSolid(S)); myBuilder.MakeCompSolid(TopoDS::CompSolid(S));
break; break;
@ -1209,20 +1168,20 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
// compound // compound
//--------- //---------
case TopAbs_COMPOUND : case TopAbs_COMPOUND:
myBuilder.MakeCompound(TopoDS::Compound(S)); myBuilder.MakeCompound(TopoDS::Compound(S));
break; break;
default: default:
{ {
Standard_SStream aMsg; Standard_SStream aMsg;
aMsg << "Unexpected topology type = "<< T <<std::endl; aMsg << "Unexpected topology type = " << T << std::endl;
throw Standard_Failure(aMsg.str().c_str()); throw Standard_Failure(aMsg.str().c_str());
break; break;
} }
} }
} }
catch(Standard_Failure const& anException) { catch (Standard_Failure const& anException) {
Standard_SStream aMsg; Standard_SStream aMsg;
aMsg << "EXCEPTION in BinTools_ShapeSet::ReadGeometry(S,OS)" << std::endl; aMsg << "EXCEPTION in BinTools_ShapeSet::ReadGeometry(S,OS)" << std::endl;
aMsg << anException << std::endl; aMsg << anException << std::endl;
@ -1230,8 +1189,6 @@ void BinTools_ShapeSet::ReadGeometry(const TopAbs_ShapeEnum T,
} }
} }
//======================================================================= //=======================================================================
//function : AddShapes //function : AddShapes
//purpose : //purpose :
@ -1243,7 +1200,6 @@ void BinTools_ShapeSet::AddShapes(TopoDS_Shape& S1,
myBuilder.Add(S1,S2); myBuilder.Add(S1,S2);
} }
//======================================================================= //=======================================================================
//function : WritePolygonOnTriangulation //function : WritePolygonOnTriangulation
//purpose : //purpose :
@ -1492,7 +1448,7 @@ void BinTools_ShapeSet::WriteTriangulation (Standard_OStream& OS,
BinTools::PutInteger(OS, aNbNodes); BinTools::PutInteger(OS, aNbNodes);
BinTools::PutInteger(OS, aNbTriangles); BinTools::PutInteger(OS, aNbTriangles);
BinTools::PutBool(OS, aTriangulation->HasUVNodes() ? 1 : 0); BinTools::PutBool(OS, aTriangulation->HasUVNodes() ? 1 : 0);
if (myFormatNb >= BinTools_FormatVersion_VERSION_4) if (FormatNb() >= BinTools_FormatVersion_VERSION_4)
{ {
BinTools::PutBool(OS, (aTriangulation->HasNormals() && NeedToWriteNormals) ? 1 : 0); BinTools::PutBool(OS, (aTriangulation->HasNormals() && NeedToWriteNormals) ? 1 : 0);
} }
@ -1526,7 +1482,7 @@ void BinTools_ShapeSet::WriteTriangulation (Standard_OStream& OS,
} }
// write the normals // write the normals
if (myFormatNb >= BinTools_FormatVersion_VERSION_4) if (FormatNb() >= BinTools_FormatVersion_VERSION_4)
{ {
if (aTriangulation->HasNormals() && NeedToWriteNormals) if (aTriangulation->HasNormals() && NeedToWriteNormals)
{ {
@ -1581,7 +1537,7 @@ void BinTools_ShapeSet::ReadTriangulation (Standard_IStream& IS,
BinTools::GetInteger(IS, aNbNodes); BinTools::GetInteger(IS, aNbNodes);
BinTools::GetInteger(IS, aNbTriangles); BinTools::GetInteger(IS, aNbTriangles);
BinTools::GetBool(IS, hasUV); BinTools::GetBool(IS, hasUV);
if (myFormatNb >= BinTools_FormatVersion_VERSION_4) if (FormatNb() >= BinTools_FormatVersion_VERSION_4)
{ {
BinTools::GetBool(IS, hasNormals); BinTools::GetBool(IS, hasNormals);
} }
@ -1618,6 +1574,7 @@ void BinTools_ShapeSet::ReadTriangulation (Standard_IStream& IS,
BinTools::GetInteger(IS, aTriNodes[2]); BinTools::GetInteger(IS, aTriNodes[2]);
aTriangulation->SetTriangle (aTriIter, Poly_Triangle (aTriNodes[0], aTriNodes[1], aTriNodes[2])); aTriangulation->SetTriangle (aTriIter, Poly_Triangle (aTriNodes[0], aTriNodes[1], aTriNodes[2]));
} }
//IS.ignore(sizeof(Standard_Real) * (hasUV ? 5 : 3) * aNbNodes + sizeof(Standard_Integer) * 3 * aNbTriangles);
if (hasNormals) if (hasNormals)
{ {

View File

@ -16,30 +16,21 @@
#ifndef _BinTools_ShapeSet_HeaderFile #ifndef _BinTools_ShapeSet_HeaderFile
#define _BinTools_ShapeSet_HeaderFile #define _BinTools_ShapeSet_HeaderFile
#include <Standard.hxx> #include <BinTools_ShapeSetBase.hxx>
#include <Standard_DefineAlloc.hxx>
#include <Standard_Handle.hxx>
#include <TopTools_IndexedMapOfShape.hxx> #include <TopTools_IndexedMapOfShape.hxx>
#include <BinTools_FormatVersion.hxx>
#include <BinTools_LocationSet.hxx> #include <BinTools_LocationSet.hxx>
#include <Standard_Integer.hxx>
#include <BRep_Builder.hxx> #include <BRep_Builder.hxx>
#include <BinTools_SurfaceSet.hxx> #include <BinTools_SurfaceSet.hxx>
#include <BinTools_CurveSet.hxx> #include <BinTools_CurveSet.hxx>
#include <BinTools_Curve2dSet.hxx> #include <BinTools_Curve2dSet.hxx>
#include <TColStd_IndexedMapOfTransient.hxx> #include <TColStd_IndexedMapOfTransient.hxx>
#include <Standard_Boolean.hxx>
#include <Standard_OStream.hxx> #include <Standard_OStream.hxx>
#include <Standard_IStream.hxx> #include <Standard_IStream.hxx>
#include <TopAbs_ShapeEnum.hxx>
class TopoDS_Shape;
class BinTools_LocationSet;
//! Writes topology in OStream in binary format //! Writes topology in OStream in binary format
class BinTools_ShapeSet class BinTools_ShapeSet : public BinTools_ShapeSetBase
{ {
public: public:
@ -51,25 +42,6 @@ public:
Standard_EXPORT virtual ~BinTools_ShapeSet(); Standard_EXPORT virtual ~BinTools_ShapeSet();
//! Return true if shape should be stored with triangles.
Standard_Boolean IsWithTriangles() const { return myWithTriangles; }
//! Return true if shape should be stored triangulation with normals.
Standard_Boolean IsWithNormals() const { return myWithNormals; }
//! Define if shape will be stored with triangles.
//! Ignored (always written) if face defines only triangulation (no surface).
void SetWithTriangles (const Standard_Boolean theWithTriangles) { myWithTriangles = theWithTriangles; }
//! Define if shape will be stored triangulation with normals.
//! Ignored (always written) if face defines only triangulation (no surface).
void SetWithNormals(const Standard_Boolean theWithNormals) { myWithNormals = theWithNormals; }
//! Sets the BinTools_FormatVersion.
Standard_EXPORT void SetFormatNb (const Standard_Integer theFormatNb);
//! Returns the BinTools_FormatVersion.
Standard_EXPORT Standard_Integer FormatNb() const;
//! Clears the content of the set. //! Clears the content of the set.
Standard_EXPORT virtual void Clear(); Standard_EXPORT virtual void Clear();
@ -78,7 +50,7 @@ public:
Standard_EXPORT Standard_Integer Add (const TopoDS_Shape& S); Standard_EXPORT Standard_Integer Add (const TopoDS_Shape& S);
//! Returns the sub-shape of index <I>. //! Returns the sub-shape of index <I>.
Standard_EXPORT const TopoDS_Shape& Shape (const Standard_Integer I) const; Standard_EXPORT const TopoDS_Shape& Shape (const Standard_Integer I);
//! Returns the index of <S>. //! Returns the index of <S>.
Standard_EXPORT Standard_Integer Index (const TopoDS_Shape& S) const; Standard_EXPORT Standard_Integer Index (const TopoDS_Shape& S) const;
@ -104,7 +76,7 @@ public:
//! Write the flags, the subshapes. //! Write the flags, the subshapes.
Standard_EXPORT virtual void Write Standard_EXPORT virtual void Write
(Standard_OStream& OS, (Standard_OStream& OS,
const Message_ProgressRange& theRange = Message_ProgressRange()) const; const Message_ProgressRange& theRange = Message_ProgressRange());
//! Reads the content of me from the binary stream <IS>. me //! Reads the content of me from the binary stream <IS>. me
//! is first cleared. //! is first cleared.
@ -125,7 +97,7 @@ public:
//! Writes on <OS> the shape <S>. Writes the //! Writes on <OS> the shape <S>. Writes the
//! orientation, the index of the TShape and the index //! orientation, the index of the TShape and the index
//! of the Location. //! of the Location.
Standard_EXPORT virtual void Write (const TopoDS_Shape& S, Standard_OStream& OS) const; Standard_EXPORT virtual void Write (const TopoDS_Shape& S, Standard_OStream& OS);
//! Writes the geometry of me on the stream <OS> in a //! Writes the geometry of me on the stream <OS> in a
//! binary format that can be read back by Read. //! binary format that can be read back by Read.
@ -138,22 +110,28 @@ public:
(Standard_IStream& IS, (Standard_IStream& IS,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Reads from <IS> a shape flags and sub-shapes and modifies S.
Standard_EXPORT virtual void ReadFlagsAndSubs
(TopoDS_Shape& S, const TopAbs_ShapeEnum T,
Standard_IStream& IS, const Standard_Integer NbShapes);
//! Reads from <IS> a shape and returns it in S. //! Reads from <IS> a shape and returns it in S.
//! <NbShapes> is the number of tshapes in the set. //! <NbShapes> is the number of tshapes in the set.
Standard_EXPORT virtual void Read Standard_EXPORT virtual void ReadSubs
(TopoDS_Shape& S, (TopoDS_Shape& S, Standard_IStream& IS, const Standard_Integer NbShapes);
Standard_IStream& IS, const Standard_Integer NbShapes) const;
//! Writes the geometry of <S> on the stream <OS> in a //! An empty virtual method for redefinition in shape-reader.
Standard_EXPORT virtual void Read (Standard_IStream& /*theStream*/, TopoDS_Shape& /*theShape*/) {};
//! Writes the shape <S> on the stream <OS> in a
//! binary format that can be read back by Read. //! binary format that can be read back by Read.
Standard_EXPORT virtual void WriteGeometry (const TopoDS_Shape& S, Standard_OStream& OS) const; Standard_EXPORT virtual void WriteShape (const TopoDS_Shape& S, Standard_OStream& OS) const;
//! Reads the geometry of a shape of type <T> from the //! Reads a shape of type <T> from the stream <IS> and returns it in <S>.
//! stream <IS> and returns it in <S>. Standard_EXPORT virtual void ReadShape (const TopAbs_ShapeEnum T, Standard_IStream& IS, TopoDS_Shape& S);
Standard_EXPORT virtual void ReadGeometry (const TopAbs_ShapeEnum T, Standard_IStream& IS, TopoDS_Shape& S);
//! Stores the goemetry of <S>. //! Stores the shape <S>.
Standard_EXPORT virtual void AddGeometry (const TopoDS_Shape& S); Standard_EXPORT virtual void AddShape (const TopoDS_Shape& S);
//! Inserts the shape <S2> in the shape <S1>. //! Inserts the shape <S2> in the shape <S1>.
Standard_EXPORT virtual void AddShapes (TopoDS_Shape& S1, const TopoDS_Shape& S2); Standard_EXPORT virtual void AddShapes (TopoDS_Shape& S1, const TopoDS_Shape& S2);
@ -197,15 +175,10 @@ public:
(Standard_OStream& OS, (Standard_OStream& OS,
const Message_ProgressRange& theRange = Message_ProgressRange()) const; const Message_ProgressRange& theRange = Message_ProgressRange()) const;
public:
static const Standard_CString THE_ASCII_VERSIONS[BinTools_FormatVersion_UPPER + 1];
private: private:
TopTools_IndexedMapOfShape myShapes; TopTools_IndexedMapOfShape myShapes; ///< index and its shape (started from 1)
BinTools_LocationSet myLocations; BinTools_LocationSet myLocations;
Standard_Integer myFormatNb;
BRep_Builder myBuilder; BRep_Builder myBuilder;
BinTools_SurfaceSet mySurfaces; BinTools_SurfaceSet mySurfaces;
BinTools_CurveSet myCurves; BinTools_CurveSet myCurves;
@ -216,9 +189,6 @@ private:
Standard_Boolean> myTriangulations; //!< Contains a boolean flag with information Standard_Boolean> myTriangulations; //!< Contains a boolean flag with information
//! to save normals for triangulation //! to save normals for triangulation
NCollection_IndexedMap<Handle(Poly_PolygonOnTriangulation), TColStd_MapTransientHasher> myNodes; NCollection_IndexedMap<Handle(Poly_PolygonOnTriangulation), TColStd_MapTransientHasher> myNodes;
Standard_Boolean myWithTriangles;
Standard_Boolean myWithNormals;
}; };
#endif // _BinTools_ShapeSet_HeaderFile #endif // _BinTools_ShapeSet_HeaderFile

View File

@ -0,0 +1,69 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <BinTools.hxx>
#include <BinTools_ShapeSetBase.hxx>
#include <TopoDS_Shape.hxx>
const Standard_CString BinTools_ShapeSetBase::THE_ASCII_VERSIONS[BinTools_FormatVersion_UPPER + 1] =
{
"",
"Open CASCADE Topology V1 (c)",
"Open CASCADE Topology V2 (c)",
"Open CASCADE Topology V3 (c)",
"Open CASCADE Topology V4, (c) Open Cascade"
};
//=======================================================================
//function : operator << (gp_Pnt)
//purpose :
//=======================================================================
Standard_OStream& operator << (Standard_OStream& OS, const gp_Pnt P)
{
BinTools::PutReal (OS, P.X());
BinTools::PutReal (OS, P.Y());
BinTools::PutReal (OS, P.Z());
return OS;
}
//=======================================================================
//function : BinTools_ShapeSetBase
//purpose :
//=======================================================================
BinTools_ShapeSetBase::BinTools_ShapeSetBase()
: myFormatNb (BinTools_FormatVersion_CURRENT),
myWithTriangles (Standard_False),
myWithNormals (Standard_False)
{}
//=======================================================================
//function : ~BinTools_ShapeSetBase
//purpose :
//=======================================================================
BinTools_ShapeSetBase::~BinTools_ShapeSetBase()
{}
//=======================================================================
//function : SetFormatNb
//purpose :
//=======================================================================
void BinTools_ShapeSetBase::SetFormatNb (const Standard_Integer theFormatNb)
{
Standard_ASSERT_RETURN(theFormatNb >= BinTools_FormatVersion_LOWER &&
theFormatNb <= BinTools_FormatVersion_UPPER,
"Error: unsupported BinTools version.", );
myFormatNb = theFormatNb;
}

View File

@ -0,0 +1,118 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinTools_ShapeSetBase_HeaderFile
#define _BinTools_ShapeSetBase_HeaderFile
#include <Standard.hxx>
#include <Standard_DefineAlloc.hxx>
#include <Standard_Handle.hxx>
#include <Standard_OStream.hxx>
#include <Standard_IStream.hxx>
#include <Message_ProgressRange.hxx>
#include <BinTools_FormatVersion.hxx>
class TopoDS_Shape;
class gp_Pnt;
//! Writes to the stream a gp_Pnt data
Standard_OStream& operator << (Standard_OStream& OS, const gp_Pnt P);
//! Computes a hash code for the given value of the uint64_t type, in range [1, theUpperBound]
inline Standard_Integer HashCode (const uint64_t theValue, const Standard_Integer theUpperBound)
{
return IntegerHashCode(theValue, 0xffffffffffffffff, theUpperBound);
}
//! A base class for all readers/writers of TopoDS_Shape into/from stream.
class BinTools_ShapeSetBase
{
public:
DEFINE_STANDARD_ALLOC
//! A default constructor.
Standard_EXPORT BinTools_ShapeSetBase();
Standard_EXPORT virtual ~BinTools_ShapeSetBase();
//! Return true if shape should be stored with triangles.
Standard_Boolean IsWithTriangles() const { return myWithTriangles; }
//! Return true if shape should be stored triangulation with normals.
Standard_Boolean IsWithNormals() const { return myWithNormals; }
//! Define if shape will be stored with triangles.
//! Ignored (always written) if face defines only triangulation (no surface).
void SetWithTriangles (const Standard_Boolean theWithTriangles) { myWithTriangles = theWithTriangles; }
//! Define if shape will be stored triangulation with normals.
//! Ignored (always written) if face defines only triangulation (no surface).
void SetWithNormals(const Standard_Boolean theWithNormals) { myWithNormals = theWithNormals; }
//! Sets the BinTools_FormatVersion.
Standard_EXPORT void SetFormatNb (const Standard_Integer theFormatNb);
//! Returns the BinTools_FormatVersion.
Standard_EXPORT Standard_Integer FormatNb() const { return myFormatNb; }
//! Clears the content of the set.
Standard_EXPORT virtual void Clear() {}
//! Writes the content of me on the stream <OS> in binary
//! format that can be read back by Read.
//!
//! Writes the locations.
//!
//! Writes the geometry calling WriteGeometry.
//!
//! Dumps the shapes from last to first.
//! For each shape :
//! Write the type.
//! calls WriteGeometry(S).
//! Write the flags, the subshapes.
Standard_EXPORT virtual void Write
(Standard_OStream& /*OS*/, const Message_ProgressRange& /*theRange*/ = Message_ProgressRange()) {}
//! Reads the content of me from the binary stream <IS>. me
//! is first cleared.
//!
//! Reads the locations.
//!
//! Reads the geometry calling ReadGeometry.
//!
//! Reads the shapes.
//! For each shape
//! Reads the type.
//! calls ReadGeometry(T,S).
//! Reads the flag, the subshapes.
Standard_EXPORT virtual void Read
(Standard_IStream& /*IS*/, const Message_ProgressRange& /*theRange*/ = Message_ProgressRange()) {}
//! Writes on <OS> the shape <S>. Writes the
//! orientation, the index of the TShape and the index
//! of the Location.
Standard_EXPORT virtual void Write (const TopoDS_Shape& /*theShape*/, Standard_OStream& /*theStream*/) {}
//! An empty virtual method for redefinition in shape-reader.
Standard_EXPORT virtual void Read (Standard_IStream& /*theStream*/, TopoDS_Shape& /*theShape*/) {}
static const Standard_CString THE_ASCII_VERSIONS[BinTools_FormatVersion_UPPER + 1];
private:
Standard_Integer myFormatNb;
Standard_Boolean myWithTriangles;
Standard_Boolean myWithNormals;
};
#endif // _BinTools_ShapeSet_HeaderFile

View File

@ -0,0 +1,496 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <BinTools_ShapeWriter.hxx>
#include <BinTools_LocationSet.hxx>
#include <TopoDS.hxx>
#include <BRep_TEdge.hxx>
#include <BRep_GCurve.hxx>
#include <BRep_Polygon3D.hxx>
#include <BRep_PolygonOnTriangulation.hxx>
#include <TopoDS_Iterator.hxx>
#include <TopoDS_Vertex.hxx>
#include <BRep_Tool.hxx>
#include <BRep_TVertex.hxx>
#include <BRep_PointRepresentation.hxx>
#include <BRep_TFace.hxx>
#include <BinTools_CurveSet.hxx>
#include <BinTools_Curve2dSet.hxx>
#include <BinTools_SurfaceSet.hxx>
#include <BinTools_OStream.hxx>
//=======================================================================
//function : BinTools_ShapeWriter
//purpose :
//=======================================================================
BinTools_ShapeWriter::BinTools_ShapeWriter()
: BinTools_ShapeSetBase()
{}
//=======================================================================
//function : ~BinTools_ShapeWriter
//purpose :
//=======================================================================
BinTools_ShapeWriter::~BinTools_ShapeWriter()
{}
//=======================================================================
//function : Clear
//purpose :
//=======================================================================
void BinTools_ShapeWriter::Clear()
{
BinTools_ShapeSetBase::Clear();
myShapePos.Clear();
myLocationPos.Clear();
myCurvePos.Clear();
myCurve2dPos.Clear();
mySurfacePos.Clear();
myPolygon3dPos.Clear();
myPolygonPos.Clear();
myTriangulationPos.Clear();
}
//=======================================================================
//function : Write
//purpose :
//=======================================================================
void BinTools_ShapeWriter::Write (const TopoDS_Shape& theShape, Standard_OStream& theStream)
{
BinTools_OStream anOStream(theStream);
WriteShape (anOStream, theShape);
}
//=======================================================================
//function : WriteShape
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WriteShape (BinTools_OStream& theStream, const TopoDS_Shape& theShape)
{
if (theShape.IsNull())
{
theStream << BinTools_ObjectType_EmptyShape;
return;
}
TopoDS_Shape aShape = theShape.Located (TopLoc_Location());
const uint64_t* anExisting = myShapePos.Seek (aShape);
if (anExisting) // shape is already there, so, write reference to it
{
theStream.WriteReference(*anExisting);
WriteLocation (theStream, theShape.Location());
theStream << Standard_Byte (theShape.Orientation ());
return;
}
uint64_t aNewPos = theStream.Position();
myShapePos.Bind (aShape, aNewPos);
theStream.WriteShape (aShape.ShapeType(), aShape.Orientation());
WriteLocation (theStream, theShape.Location());
try {
OCC_CATCH_SIGNALS
switch (aShape.ShapeType())
{
case TopAbs_VERTEX:
{
TopoDS_Vertex aV = TopoDS::Vertex (aShape);
theStream << BRep_Tool::Tolerance (aV);
gp_Pnt aP = BRep_Tool::Pnt (aV);
theStream << aP;
Handle(BRep_TVertex) aTV = Handle(BRep_TVertex)::DownCast (aShape.TShape());
for(BRep_ListIteratorOfListOfPointRepresentation anIter (aTV->Points()); anIter.More(); anIter.Next())
{
const Handle(BRep_PointRepresentation)& aPR = anIter.Value();
if (aPR->IsPointOnCurve())
{
theStream << (Standard_Byte)1; // 1
theStream << aPR->Parameter();
WriteCurve (theStream, aPR->Curve());
}
else if (aPR->IsPointOnCurveOnSurface())
{
theStream << (Standard_Byte)2;// 2
theStream << aPR->Parameter();
WriteCurve (theStream, aPR->PCurve());
WriteSurface (theStream, aPR->Surface());
}
else if (aPR->IsPointOnSurface())
{
theStream << (Standard_Byte)3;// 3
theStream << aPR->Parameter2() << aPR->Parameter();
WriteSurface (theStream, aPR->Surface());
}
WriteLocation (theStream, aPR->Location());
}
theStream << (Standard_Byte)0;
}
break;
case TopAbs_EDGE:
{
Handle(BRep_TEdge) aTE = Handle(BRep_TEdge)::DownCast (aShape.TShape());
theStream << aTE->Tolerance();
theStream.PutBools (aTE->SameParameter(), aTE->SameRange(), aTE->Degenerated());
Standard_Real aFirst, aLast;
for(BRep_ListIteratorOfListOfCurveRepresentation anIter = aTE->Curves(); anIter.More(); anIter.Next())
{
const Handle(BRep_CurveRepresentation)& aCR = anIter.Value();
if (aCR->IsCurve3D())
{
if (!aCR->Curve3D().IsNull())
{
Handle(BRep_GCurve) aGC = Handle(BRep_GCurve)::DownCast (aCR);
aGC->Range (aFirst, aLast);
theStream << (Standard_Byte)1; // -1- CURVE_3D;
WriteCurve (theStream, aCR->Curve3D());
WriteLocation (theStream, aCR->Location());
theStream << aFirst << aLast;
}
}
else if (aCR->IsCurveOnSurface()) {
Handle(BRep_GCurve) GC = Handle(BRep_GCurve)::DownCast (aCR);
GC->Range (aFirst, aLast);
if (!aCR->IsCurveOnClosedSurface())
theStream << (Standard_Byte)2; // -2- Curve on surf
else
theStream << (Standard_Byte)3; // -3- Curve on closed surf
WriteCurve (theStream, aCR->PCurve());
if (aCR->IsCurveOnClosedSurface()) { //+ int|char
WriteCurve (theStream, aCR->PCurve2());
theStream << (Standard_Byte)aCR->Continuity();
}
WriteSurface (theStream, aCR->Surface());
WriteLocation (theStream, aCR->Location());
theStream << aFirst << aLast;
}
else if (aCR->IsRegularity())
{
theStream << (Standard_Byte)4; // -4- Regularity
theStream << (Standard_Byte)aCR->Continuity();
WriteSurface (theStream, aCR->Surface());
WriteLocation (theStream, aCR->Location());
WriteSurface (theStream, aCR->Surface2());
WriteLocation (theStream, aCR->Location2());
}
else if (IsWithTriangles())
{
if (aCR->IsPolygon3D())
{
Handle(BRep_Polygon3D) aGC = Handle(BRep_Polygon3D)::DownCast (aCR);
if (!aGC->Polygon3D().IsNull())
{
theStream << (Standard_Byte)5; // -5- Polygon3D
WritePolygon (theStream, aCR->Polygon3D());
WriteLocation (theStream, aCR->Location());
}
}
else if (aCR->IsPolygonOnTriangulation())
{
Handle(BRep_PolygonOnTriangulation) aPT = Handle(BRep_PolygonOnTriangulation)::DownCast (aCR);
if (!aCR->IsPolygonOnClosedTriangulation())
theStream << (Standard_Byte)6; // -6- Polygon on triangulation
else
theStream << (Standard_Byte)7; // -7- Polygon on closed triangulation
WritePolygon (theStream, aPT->PolygonOnTriangulation());
if (aCR->IsPolygonOnClosedTriangulation())
WritePolygon (theStream, aPT->PolygonOnTriangulation2());
// edge triangulation does not need normals
WriteTriangulation (theStream, aPT->Triangulation(), Standard_False);
WriteLocation (theStream, aCR->Location());
}
}
}
theStream << (Standard_Byte)0;
}
break;
case TopAbs_FACE:
{
Handle(BRep_TFace) aTF = Handle(BRep_TFace)::DownCast (aShape.TShape());
const TopoDS_Face& aF = TopoDS::Face (aShape);
// Write the surface geometry
theStream << BRep_Tool::NaturalRestriction (aF) << aTF->Tolerance();
WriteSurface (theStream, aTF->Surface());
WriteLocation (theStream, aTF->Location());
if (IsWithTriangles() || aTF->Surface().IsNull())
{
if (!(aTF->Triangulation()).IsNull())
{
theStream << (Standard_Byte)2;
WriteTriangulation (theStream, aTF->Triangulation(),
aTF->Triangulation()->HasNormals() && (IsWithNormals() || aTF->Surface().IsNull()));
}
else
theStream << (Standard_Byte)1;
}
else
theStream << (Standard_Byte)0; //without triangulation
}
break;
default:
{}
}
}
catch (Standard_Failure const& anException)
{
Standard_SStream aMsg;
aMsg << "EXCEPTION in BinTools_ShapeWriter::WriteShape" << std::endl;
aMsg << anException << std::endl;
throw Standard_Failure(aMsg.str().c_str());
}
theStream.PutBools (aShape.Free(), aShape.Modified(), aShape.Checked(),
aShape.Orientable(), aShape.Closed(), aShape.Infinite(), aShape.Convex());
// process sub-shapes
for (TopoDS_Iterator aSub (aShape, Standard_False, Standard_False); aSub.More(); aSub.Next())
WriteShape (theStream, aSub.Value());
theStream << BinTools_ObjectType_EndShape;
}
//=======================================================================
//function : WriteLocation
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WriteLocation (BinTools_OStream& theStream, const TopLoc_Location& theLocation)
{
if (theLocation.IsIdentity())
{
theStream << BinTools_ObjectType_EmptyLocation;
return;
}
const uint64_t* aLoc = myLocationPos.Seek (theLocation);
if (aLoc)
{
theStream.WriteReference (*aLoc);
return;
}
uint64_t aNewLoc = theStream.Position();
try
{
OCC_CATCH_SIGNALS
TopLoc_Location aL2 = theLocation.NextLocation();
Standard_Boolean isSimple = aL2.IsIdentity();
Standard_Integer aPower = theLocation.FirstPower();
TopLoc_Location aL1 = theLocation.FirstDatum();
Standard_Boolean elementary = (isSimple && aPower == 1);
if (elementary)
{
theStream << BinTools_ObjectType_SimpleLocation << theLocation.Transformation();
}
else
{
theStream << BinTools_ObjectType_Location;
WriteLocation (theStream, aL1);
theStream << aPower;
while (!aL2.IsIdentity()) {
aL1 = aL2.FirstDatum();
aPower = aL2.FirstPower();
aL2 = aL2.NextLocation();
WriteLocation (theStream, aL1);
theStream << aPower;
}
theStream << BinTools_ObjectType_LocationEnd;
}
myLocationPos.Bind (theLocation, aNewLoc);
}
catch (Standard_Failure const& anException) {
Standard_SStream aMsg;
aMsg << "EXCEPTION in BinTools_ShapeWriter::WriteLocation" << std::endl;
aMsg << anException << std::endl;
throw Standard_Failure (aMsg.str().c_str());
}
}
//=======================================================================
//function : WriteCurve
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WriteCurve (BinTools_OStream& theStream, const Handle(Geom_Curve)& theCurve)
{
if (theCurve.IsNull())
{
theStream << BinTools_ObjectType_EmptyCurve;
return;
}
const uint64_t* aCurve = myCurvePos.Seek (theCurve);
if (aCurve)
{
theStream.WriteReference (*aCurve);
return;
}
myCurvePos.Bind (theCurve, theStream.Position());
theStream << BinTools_ObjectType_Curve;
BinTools_CurveSet::WriteCurve (theCurve, theStream);
}
//=======================================================================
//function : WriteCurve
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WriteCurve (BinTools_OStream& theStream, const Handle(Geom2d_Curve)& theCurve)
{
if (theCurve.IsNull())
{
theStream << BinTools_ObjectType_EmptyCurve2d;
return;
}
const uint64_t* aCurve = myCurve2dPos.Seek (theCurve);
if (aCurve)
{
theStream.WriteReference (*aCurve);
return;
}
myCurve2dPos.Bind (theCurve, theStream.Position());
theStream << BinTools_ObjectType_Curve2d;
BinTools_Curve2dSet::WriteCurve2d (theCurve, theStream);
}
//=======================================================================
//function : WriteSurface
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WriteSurface (BinTools_OStream& theStream, const Handle(Geom_Surface)& theSurface)
{
if (theSurface.IsNull())
{
theStream << BinTools_ObjectType_EmptySurface;
return;
}
const uint64_t* aSurface = mySurfacePos.Seek (theSurface);
if (aSurface)
{
theStream.WriteReference (*aSurface);
return;
}
mySurfacePos.Bind (theSurface, theStream.Position());
theStream << BinTools_ObjectType_Surface;
BinTools_SurfaceSet::WriteSurface (theSurface, theStream);
}
//=======================================================================
//function : WritePolygon
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WritePolygon (BinTools_OStream& theStream, const Handle(Poly_Polygon3D)& thePolygon)
{
if (thePolygon.IsNull())
{
theStream << BinTools_ObjectType_EmptyPolygon3d;
return;
}
const uint64_t* aPolygon = myPolygon3dPos.Seek (thePolygon);
if (aPolygon)
{
theStream.WriteReference (*aPolygon);
return;
}
myPolygon3dPos.Bind (thePolygon, theStream.Position());
theStream << BinTools_ObjectType_Polygon3d;
const Standard_Integer aNbNodes = thePolygon->NbNodes();
theStream << aNbNodes << thePolygon->HasParameters() << thePolygon->Deflection();
const TColgp_Array1OfPnt& aNodes = thePolygon->Nodes();
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream << aNodes.Value (aNodeIter);
if (thePolygon->HasParameters())
{
const TColStd_Array1OfReal& aParam = thePolygon->Parameters();
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream << aParam.Value (aNodeIter);
}
}
//=======================================================================
//function : WritePolygon
//purpose :
//=======================================================================
void BinTools_ShapeWriter::WritePolygon (BinTools_OStream& theStream,
const Handle(Poly_PolygonOnTriangulation)& thePolygon)
{
if (thePolygon.IsNull())
{
theStream << BinTools_ObjectType_EmptyPolygonOnTriangulation;
return;
}
const uint64_t* aPolygon = myPolygonPos.Seek (thePolygon);
if (aPolygon)
{
theStream.WriteReference (*aPolygon);
return;
}
myPolygonPos.Bind (thePolygon, theStream.Position());
theStream << BinTools_ObjectType_PolygonOnTriangulation;
const TColStd_Array1OfInteger& aNodes = thePolygon->Nodes();
theStream << aNodes.Length();
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNodes.Length(); ++aNodeIter)
theStream << aNodes.Value(aNodeIter);
theStream << thePolygon->Deflection();
if (const Handle(TColStd_HArray1OfReal)& aParam = thePolygon->Parameters())
{
theStream << Standard_True;
for (Standard_Integer aNodeIter = 1; aNodeIter <= aParam->Length(); ++aNodeIter)
theStream << aParam->Value(aNodeIter);
}
else
theStream << Standard_False;
}
void BinTools_ShapeWriter::WriteTriangulation (BinTools_OStream& theStream,
const Handle(Poly_Triangulation)& theTriangulation,
const Standard_Boolean theNeedToWriteNormals)
{
if (theTriangulation.IsNull())
{
theStream << BinTools_ObjectType_EmptyTriangulation;
return;
}
const uint64_t* aTriangulation = myTriangulationPos.Seek (theTriangulation);
if (aTriangulation)
{
theStream.WriteReference (*aTriangulation);
return;
}
myTriangulationPos.Bind (theTriangulation, theStream.Position());
theStream << BinTools_ObjectType_Triangulation;
const Standard_Integer aNbNodes = theTriangulation->NbNodes();
const Standard_Integer aNbTriangles = theTriangulation->NbTriangles();
theStream << aNbNodes << aNbTriangles << theTriangulation->HasUVNodes();
theStream << theNeedToWriteNormals << theTriangulation->Deflection();
// write the 3d nodes
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream << theTriangulation->Node (aNodeIter);
//theStream.write ((char*)(theTriangulation->InternalNodes().value(0)) , sizeof (gp_Pnt) * aNbNodes);
if (theTriangulation->HasUVNodes())
{
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbNodes; ++aNodeIter)
theStream << theTriangulation->UVNode (aNodeIter);
}
for (Standard_Integer aTriIter = 1; aTriIter <= aNbTriangles; ++aTriIter)
theStream << theTriangulation->Triangle (aTriIter);
if (theNeedToWriteNormals)
{
gp_Vec3f aNormal;
for (Standard_Integer aNormalIter = 1; aNormalIter <= aNbNodes; ++aNormalIter)
{
theTriangulation->Normal (aNormalIter, aNormal);
theStream << aNormal;
}
}
}

View File

@ -0,0 +1,82 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _BinTools_ShapeWriter_HeaderFile
#define _BinTools_ShapeWriter_HeaderFile
#include <BinTools_ShapeSetBase.hxx>
#include <BinTools_OStream.hxx>
#include <NCollection_DataMap.hxx>
#include <NCollection_Map.hxx>
#include <TopTools_ShapeMapHasher.hxx>
class TopLoc_Location;
class Geom_Curve;
class Geom2d_Curve;
class Geom_Surface;
class Poly_Polygon3D;
class Poly_PolygonOnTriangulation;
class Poly_Triangulation;
//! Writes topology in OStream in binary format without grouping of objects by types
//! and using relative positions in a file as references.
class BinTools_ShapeWriter : public BinTools_ShapeSetBase
{
public:
DEFINE_STANDARD_ALLOC
//! Builds an empty ShapeSet.
//! Parameter <theWithTriangles> is added for XML Persistence
Standard_EXPORT BinTools_ShapeWriter();
Standard_EXPORT virtual ~BinTools_ShapeWriter();
//! Clears the content of the set.
Standard_EXPORT virtual void Clear() Standard_OVERRIDE;
//! Writes the shape to stream using previously stored shapes and objects to refer them.
Standard_EXPORT virtual void Write (const TopoDS_Shape& theShape, Standard_OStream& theStream) Standard_OVERRIDE;
//! Writes location to the stream (all the needed sub-information or reference if it is already used).
Standard_EXPORT virtual void WriteLocation (BinTools_OStream& theStream, const TopLoc_Location& theLocation);
private:
//! Writes shape to the stream (all the needed sub-information or reference if it is already used).
virtual void WriteShape (BinTools_OStream& theStream, const TopoDS_Shape& theShape);
//! Writes curve to the stream (all the needed sub-information or reference if it is already used).
void WriteCurve (BinTools_OStream& theStream, const Handle(Geom_Curve)& theCurve);
//! Writes curve2d to the stream (all the needed sub-information or reference if it is already used).
void WriteCurve (BinTools_OStream& theStream, const Handle(Geom2d_Curve)& theCurve);
//! Writes surface to the stream.
void WriteSurface (BinTools_OStream& theStream, const Handle(Geom_Surface)& theSurface);
//! Writes ploygon3d to the stream.
void WritePolygon (BinTools_OStream& theStream, const Handle(Poly_Polygon3D)& thePolygon);
//! Writes polygon on triangulation to the stream.
void WritePolygon (BinTools_OStream& theStream, const Handle(Poly_PolygonOnTriangulation)& thePolygon);
//! Writes triangulation to the stream.
void WriteTriangulation (BinTools_OStream& theStream, const Handle(Poly_Triangulation)& theTriangulation,
const Standard_Boolean theNeedToWriteNormals);
/// position of the shape previously stored
NCollection_DataMap<TopoDS_Shape, uint64_t, TopTools_ShapeMapHasher> myShapePos;
NCollection_DataMap<TopLoc_Location, uint64_t> myLocationPos;
NCollection_DataMap<Handle(Geom_Curve), uint64_t> myCurvePos;
NCollection_DataMap<Handle(Geom2d_Curve), uint64_t> myCurve2dPos;
NCollection_DataMap<Handle(Geom_Surface), uint64_t> mySurfacePos;
NCollection_DataMap<Handle(Poly_Polygon3D), uint64_t> myPolygon3dPos;
NCollection_DataMap<Handle(Poly_PolygonOnTriangulation), uint64_t> myPolygonPos;
NCollection_DataMap<Handle(Poly_Triangulation), uint64_t> myTriangulationPos;
};
#endif // _BinTools_ShapeWriter_HeaderFile

View File

@ -111,43 +111,16 @@ Standard_Integer BinTools_SurfaceSet::Index
return myMap.FindIndex(S); return myMap.FindIndex(S);
} }
//=======================================================================
//function : operator << (gp_Pnt)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Pnt P)
{
BinTools::PutReal(OS, P.X());
BinTools::PutReal(OS, P.Y());
BinTools::PutReal(OS, P.Z());
return OS;
}
//=======================================================================
//function : operator << (gp_Dir)
//purpose :
//=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const gp_Dir D)
{
BinTools::PutReal(OS, D.X());
BinTools::PutReal(OS, D.Y());
BinTools::PutReal(OS, D.Z());
return OS;
}
//======================================================================= //=======================================================================
//function : operator <<(Geom_Plane) //function : operator <<(Geom_Plane)
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Plane)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_Plane)& S)
{ {
OS << (Standard_Byte)PLANE; OS << (Standard_Byte)PLANE;
gp_Pln P = S->Pln(); gp_Pln P = S->Pln();
OS << P.Location();//Pnt OS << P.Location(); // Pnt
OS << P.Axis().Direction(); OS << P.Axis().Direction();
OS << P.XAxis().Direction(); OS << P.XAxis().Direction();
OS << P.YAxis().Direction(); OS << P.YAxis().Direction();
@ -160,15 +133,15 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Pla
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_CylindricalSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_CylindricalSurface)& S)
{ {
OS << (Standard_Byte)CYLINDER; OS << (Standard_Byte)CYLINDER;
gp_Cylinder P = S->Cylinder(); gp_Cylinder P = S->Cylinder();
OS << P.Location();//Pnt OS << P.Location(); // Pnt
OS << P.Axis().Direction(); OS << P.Axis().Direction();
OS << P.XAxis().Direction(); OS << P.XAxis().Direction();
OS << P.YAxis().Direction(); OS << P.YAxis().Direction();
BinTools::PutReal(OS, P.Radius()); OS << P.Radius();
return OS; return OS;
} }
@ -178,16 +151,16 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Cyl
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_ConicalSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_ConicalSurface)& S)
{ {
OS << (Standard_Byte)CONE; OS << (Standard_Byte)CONE;
gp_Cone P = S->Cone(); gp_Cone P = S->Cone();
OS << P.Location();//Pnt OS << P.Location(); // Pnt
OS << P.Axis().Direction(); OS << P.Axis().Direction();
OS << P.XAxis().Direction(); OS << P.XAxis().Direction();
OS << P.YAxis().Direction(); OS << P.YAxis().Direction();
BinTools::PutReal(OS, P.RefRadius()); OS << P.RefRadius();
BinTools::PutReal(OS, P.SemiAngle()); OS << P.SemiAngle();
return OS; return OS;
} }
@ -197,15 +170,15 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Con
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_SphericalSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_SphericalSurface)& S)
{ {
OS << (Standard_Byte)SPHERE; OS << (Standard_Byte)SPHERE;
gp_Sphere P = S->Sphere(); gp_Sphere P = S->Sphere();
OS << P.Location();//Pnt OS << P.Location(); // Pnt
OS << P.Position().Axis().Direction(); OS << P.Position().Axis().Direction();
OS << P.XAxis().Direction(); OS << P.XAxis().Direction();
OS << P.YAxis().Direction(); OS << P.YAxis().Direction();
BinTools::PutReal(OS, P.Radius()); OS << P.Radius();
return OS; return OS;
} }
@ -215,16 +188,16 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Sph
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_ToroidalSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_ToroidalSurface)& S)
{ {
OS << (Standard_Byte)TORUS; OS << (Standard_Byte)TORUS;
gp_Torus P = S->Torus(); gp_Torus P = S->Torus();
OS << P.Location();//Pnt OS << P.Location(); // Pnt
OS << P.Axis().Direction(); OS << P.Axis().Direction();
OS << P.XAxis().Direction(); OS << P.XAxis().Direction();
OS << P.YAxis().Direction(); OS << P.YAxis().Direction();
BinTools::PutReal(OS, P.MajorRadius()); OS << P.MajorRadius();
BinTools::PutReal(OS, P.MinorRadius()); OS << P.MinorRadius();
return OS; return OS;
} }
@ -234,11 +207,11 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Tor
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_SurfaceOfLinearExtrusion)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_SurfaceOfLinearExtrusion)& S)
{ {
OS << (Standard_Byte)LINEAREXTRUSION; OS << (Standard_Byte)LINEAREXTRUSION;
OS << S->Direction(); OS << S->Direction();
BinTools_CurveSet::WriteCurve(S->BasisCurve(),OS); BinTools_CurveSet::WriteCurve (S->BasisCurve(), OS);
return OS; return OS;
} }
@ -248,12 +221,12 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Sur
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_SurfaceOfRevolution)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_SurfaceOfRevolution)& S)
{ {
OS << (Standard_Byte)REVOLUTION; OS << (Standard_Byte)REVOLUTION;
OS << S->Location(); OS << S->Location();
OS << S->Direction(); OS << S->Direction();
BinTools_CurveSet::WriteCurve(S->BasisCurve(),OS); BinTools_CurveSet::WriteCurve (S->BasisCurve(), OS);
return OS; return OS;
} }
@ -263,27 +236,25 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Sur
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BezierSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_BezierSurface)& S)
{ {
OS << (Standard_Byte)BEZIER; OS << (Standard_Byte)BEZIER;
Standard_Boolean urational = S->IsURational() ? 1:0; Standard_Boolean urational = S->IsURational() ? 1:0;
Standard_Boolean vrational = S->IsVRational() ? 1:0; Standard_Boolean vrational = S->IsVRational() ? 1:0;
BinTools::PutBool(OS, urational); //rational OS << urational; // rational
BinTools::PutBool(OS, vrational); OS << vrational;
// std::cout << "Bezier Surface:"<< std::endl;
// std::cout << "\turational = "<<urational<<" vrational = " <<vrational<<std::endl;
// poles and weights // poles and weights
Standard_Integer i,j,udegree,vdegree; Standard_Integer i,j,udegree,vdegree;
udegree = S->UDegree(); udegree = S->UDegree();
vdegree = S->VDegree(); vdegree = S->VDegree();
BinTools::PutExtChar(OS, (Standard_ExtCharacter)udegree); OS << (Standard_ExtCharacter)udegree;
BinTools::PutExtChar(OS, (Standard_ExtCharacter)vdegree); OS << (Standard_ExtCharacter)vdegree;
for (i = 1; i <= udegree+1; i++) { for (i = 1; i <= udegree+1; i++) {
for (j = 1; j <= vdegree+1; j++) { for (j = 1; j <= vdegree+1; j++) {
OS << S->Pole(i,j); //Pnt OS << S->Pole (i,j); // Pnt
if (urational || vrational) { if (urational || vrational) {
BinTools::PutReal(OS, S->Weight(i,j));//Real OS << S->Weight (i,j); // Real
} }
} }
} }
@ -296,17 +267,17 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Bez
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BSplineSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_BSplineSurface)& S)
{ {
OS << (Standard_Byte)BSPLINE; OS << (Standard_Byte)BSPLINE;
Standard_Boolean urational = S->IsURational() ? 1:0; Standard_Boolean urational = S->IsURational() ? 1:0;
Standard_Boolean vrational = S->IsVRational() ? 1:0; Standard_Boolean vrational = S->IsVRational() ? 1:0;
Standard_Boolean uperiodic = S->IsUPeriodic() ? 1:0; Standard_Boolean uperiodic = S->IsUPeriodic() ? 1:0;
Standard_Boolean vperiodic = S->IsVPeriodic() ? 1:0; Standard_Boolean vperiodic = S->IsVPeriodic() ? 1:0;
BinTools::PutBool(OS, urational); OS << urational;
BinTools::PutBool(OS, vrational); OS << vrational;
BinTools::PutBool(OS, uperiodic); OS << uperiodic;
BinTools::PutBool(OS, vperiodic); OS << vperiodic;
// poles and weights // poles and weights
Standard_Integer i,j,udegree,vdegree,nbupoles,nbvpoles,nbuknots,nbvknots; Standard_Integer i,j,udegree,vdegree,nbupoles,nbvpoles,nbuknots,nbvknots;
@ -316,28 +287,28 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BSp
nbvpoles = S->NbVPoles(); nbvpoles = S->NbVPoles();
nbuknots = S->NbUKnots(); nbuknots = S->NbUKnots();
nbvknots = S->NbVKnots(); nbvknots = S->NbVKnots();
BinTools::PutExtChar(OS, (Standard_ExtCharacter) udegree); OS << (Standard_ExtCharacter) udegree;
BinTools::PutExtChar(OS, (Standard_ExtCharacter) vdegree); OS << (Standard_ExtCharacter) vdegree;
BinTools::PutInteger(OS, nbupoles); OS << nbupoles;
BinTools::PutInteger(OS, nbvpoles); OS << nbvpoles;
BinTools::PutInteger(OS, nbuknots); OS << nbuknots;
BinTools::PutInteger(OS, nbvknots); OS << nbvknots;
for (i = 1; i <= nbupoles; i++) { for (i = 1; i <= nbupoles; i++) {
for (j = 1; j <= nbvpoles; j++) { for (j = 1; j <= nbvpoles; j++) {
OS << S->Pole(i,j); //Pnt OS << S->Pole (i,j); // Pnt
if (urational || vrational) if (urational || vrational)
BinTools::PutReal(OS, S->Weight(i,j));//Real OS << S->Weight (i,j); // Real
} }
} }
for (i = 1; i <= nbuknots; i++) { for (i = 1; i <= nbuknots; i++) {
BinTools::PutReal(OS,S->UKnot(i)); OS << S->UKnot (i);
BinTools::PutInteger(OS, S->UMultiplicity(i)); OS << S->UMultiplicity (i);
} }
for (i = 1; i <= nbvknots; i++) { for (i = 1; i <= nbvknots; i++) {
BinTools::PutReal(OS,S->VKnot(i)); OS << S->VKnot (i);
BinTools::PutInteger(OS, S->VMultiplicity(i)); OS << S->VMultiplicity (i);
} }
return OS; return OS;
} }
@ -348,16 +319,13 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_BSp
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_RectangularTrimmedSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_RectangularTrimmedSurface)& S)
{ {
OS << (Standard_Byte)RECTANGULAR; OS << (Standard_Byte)RECTANGULAR;
Standard_Real U1,U2,V1,V2; Standard_Real U1,U2,V1,V2;
S->Bounds(U1,U2,V1,V2); S->Bounds(U1,U2,V1,V2);
BinTools::PutReal(OS, U1); OS << U1 << U2 << V1 << V2;
BinTools::PutReal(OS, U2); BinTools_SurfaceSet::WriteSurface (S->BasisSurface(), OS);
BinTools::PutReal(OS, V1);
BinTools::PutReal(OS, V2);
BinTools_SurfaceSet::WriteSurface(S->BasisSurface(),OS);
return OS; return OS;
} }
@ -367,11 +335,11 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Rec
//purpose : //purpose :
//======================================================================= //=======================================================================
static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_OffsetSurface)& S) static BinTools_OStream& operator <<(BinTools_OStream& OS, const Handle(Geom_OffsetSurface)& S)
{ {
OS << (Standard_Byte)OFFSET; OS << (Standard_Byte)OFFSET;
BinTools::PutReal(OS, S->Offset()); OS << S->Offset();
BinTools_SurfaceSet::WriteSurface(S->BasisSurface(),OS); BinTools_SurfaceSet::WriteSurface (S->BasisSurface(), OS);
return OS; return OS;
} }
@ -381,8 +349,8 @@ static Standard_OStream& operator <<(Standard_OStream& OS, const Handle(Geom_Off
//purpose : //purpose :
//======================================================================= //=======================================================================
void BinTools_SurfaceSet::WriteSurface(const Handle(Geom_Surface)& S, void BinTools_SurfaceSet::WriteSurface (const Handle(Geom_Surface)& S,
Standard_OStream& OS) BinTools_OStream& OS)
{ {
Handle(Standard_Type) TheType = S->DynamicType(); Handle(Standard_Type) TheType = S->DynamicType();
try { try {
@ -442,10 +410,11 @@ void BinTools_SurfaceSet::Write (Standard_OStream& OS,
{ {
Standard_Integer i, nbsurf = myMap.Extent(); Standard_Integer i, nbsurf = myMap.Extent();
Message_ProgressScope aPS(theRange, "Writing surfases", nbsurf); Message_ProgressScope aPS(theRange, "Writing surfaces", nbsurf);
OS << "Surfaces "<< nbsurf << "\n"; OS << "Surfaces "<< nbsurf << "\n";
BinTools_OStream aStream (OS);
for (i = 1; i <= nbsurf && aPS.More(); i++, aPS.Next()) { for (i = 1; i <= nbsurf && aPS.More(); i++, aPS.Next()) {
WriteSurface(Handle(Geom_Surface)::DownCast(myMap(i)),OS); WriteSurface(Handle(Geom_Surface)::DownCast(myMap(i)), aStream);
} }
} }

View File

@ -26,6 +26,7 @@
#include <Standard_IStream.hxx> #include <Standard_IStream.hxx>
#include <Message_ProgressRange.hxx> #include <Message_ProgressRange.hxx>
#include <BinTools_OStream.hxx>
class Standard_OutOfRange; class Standard_OutOfRange;
class Geom_Surface; class Geom_Surface;
@ -67,7 +68,7 @@ public:
//! Dumps the surface on the stream in binary //! Dumps the surface on the stream in binary
//! format that can be read back. //! format that can be read back.
Standard_EXPORT static void WriteSurface (const Handle(Geom_Surface)& S, Standard_OStream& OS); Standard_EXPORT static void WriteSurface (const Handle(Geom_Surface)& S, BinTools_OStream& OS);
//! Reads the surface from the stream. The surface is //! Reads the surface from the stream. The surface is
//! assumed to have been written with the Write //! assumed to have been written with the Write

View File

@ -5,10 +5,21 @@ BinTools_Curve2dSet.hxx
BinTools_CurveSet.cxx BinTools_CurveSet.cxx
BinTools_CurveSet.hxx BinTools_CurveSet.hxx
BinTools_FormatVersion.hxx BinTools_FormatVersion.hxx
BinTools_IStream.cxx
BinTools_IStream.hxx
BinTools_LocationSet.cxx BinTools_LocationSet.cxx
BinTools_LocationSet.hxx BinTools_LocationSet.hxx
BinTools_LocationSetPtr.hxx BinTools_LocationSetPtr.hxx
BinTools_ShapeSet.cxx BinTools_ShapeSet.cxx
BinTools_ShapeSet.hxx BinTools_ShapeSet.hxx
BinTools_ShapeSetBase.cxx
BinTools_ShapeSetBase.hxx
BinTools_SurfaceSet.cxx BinTools_SurfaceSet.cxx
BinTools_SurfaceSet.hxx BinTools_SurfaceSet.hxx
BinTools_ObjectType.hxx
BinTools_OStream.cxx
BinTools_OStream.hxx
BinTools_ShapeReader.hxx
BinTools_ShapeReader.cxx
BinTools_ShapeWriter.hxx
BinTools_ShapeWriter.cxx

View File

@ -26,6 +26,7 @@
#include <PCDM_ReadWriter.hxx> #include <PCDM_ReadWriter.hxx>
#include <PCDM_RetrievalDriver.hxx> #include <PCDM_RetrievalDriver.hxx>
#include <PCDM_StorageDriver.hxx> #include <PCDM_StorageDriver.hxx>
#include <PCDM_ReaderFilter.hxx>
#include <Plugin.hxx> #include <Plugin.hxx>
#include <Standard_ErrorHandler.hxx> #include <Standard_ErrorHandler.hxx>
#include <Standard_GUID.hxx> #include <Standard_GUID.hxx>
@ -104,10 +105,11 @@ void CDF_Application::Close(const Handle(CDM_Document)& aDocument) {
Handle(CDM_Document) CDF_Application::Retrieve (const TCollection_ExtendedString& aFolder, Handle(CDM_Document) CDF_Application::Retrieve (const TCollection_ExtendedString& aFolder,
const TCollection_ExtendedString& aName, const TCollection_ExtendedString& aName,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
TCollection_ExtendedString nullVersion; TCollection_ExtendedString nullVersion;
return Retrieve(aFolder, aName, nullVersion, UseStorageConfiguration, theRange); return Retrieve(aFolder, aName, nullVersion, UseStorageConfiguration, theFilter, theRange);
} }
//======================================================================= //=======================================================================
@ -118,6 +120,7 @@ Handle(CDM_Document) CDF_Application::Retrieve (const TCollection_ExtendedStrin
const TCollection_ExtendedString& aName, const TCollection_ExtendedString& aName,
const TCollection_ExtendedString& aVersion, const TCollection_ExtendedString& aVersion,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
Handle(CDM_MetaData) theMetaData; Handle(CDM_MetaData) theMetaData;
@ -129,7 +132,7 @@ Handle(CDM_Document) CDF_Application::Retrieve (const TCollection_ExtendedStrin
CDF_TypeOfActivation theTypeOfActivation=TypeOfActivation(theMetaData); CDF_TypeOfActivation theTypeOfActivation=TypeOfActivation(theMetaData);
Handle(CDM_Document) theDocument = Retrieve(theMetaData, UseStorageConfiguration, Handle(CDM_Document) theDocument = Retrieve(theMetaData, UseStorageConfiguration,
Standard_False, theRange); Standard_False, theFilter, theRange);
myDirectory->Add(theDocument); myDirectory->Add(theDocument);
Activate(theDocument,theTypeOfActivation); Activate(theDocument,theTypeOfActivation);
@ -142,36 +145,48 @@ Handle(CDM_Document) CDF_Application::Retrieve (const TCollection_ExtendedStrin
//function : CanRetrieve //function : CanRetrieve
//purpose : //purpose :
//======================================================================= //=======================================================================
PCDM_ReaderStatus CDF_Application::CanRetrieve(const TCollection_ExtendedString& aFolder, const TCollection_ExtendedString& aName) { PCDM_ReaderStatus CDF_Application::CanRetrieve(const TCollection_ExtendedString& theFolder,
const TCollection_ExtendedString& theName,
const bool theAppendMode)
{
TCollection_ExtendedString aVersion; TCollection_ExtendedString aVersion;
return CanRetrieve(aFolder,aName,aVersion); return CanRetrieve(theFolder, theName, aVersion, theAppendMode);
} }
//======================================================================= //=======================================================================
//function : CanRetrieve //function : CanRetrieve
//purpose : //purpose :
//======================================================================= //=======================================================================
PCDM_ReaderStatus CDF_Application::CanRetrieve(const TCollection_ExtendedString& aFolder, const TCollection_ExtendedString& aName, const TCollection_ExtendedString& aVersion) { PCDM_ReaderStatus CDF_Application::CanRetrieve(const TCollection_ExtendedString& theFolder,
const TCollection_ExtendedString& theName,
const TCollection_ExtendedString& theVersion,
const bool theAppendMode)
{
if (!myMetaDataDriver->Find(aFolder,aName,aVersion)) if (!myMetaDataDriver->Find(theFolder, theName, theVersion))
return PCDM_RS_UnknownDocument; return PCDM_RS_UnknownDocument;
else if (!myMetaDataDriver->HasReadPermission(aFolder,aName,aVersion)) else if (!myMetaDataDriver->HasReadPermission(theFolder, theName, theVersion))
return PCDM_RS_PermissionDenied; return PCDM_RS_PermissionDenied;
else { else {
Handle(CDM_MetaData) theMetaData = myMetaDataDriver->MetaData(aFolder,aName,aVersion); Handle(CDM_MetaData) theMetaData = myMetaDataDriver->MetaData(theFolder, theName, theVersion);
if(theMetaData->IsRetrieved()) { if (!theAppendMode && theMetaData->IsRetrieved())
return theMetaData->Document()->IsModified() {
? PCDM_RS_AlreadyRetrievedAndModified : PCDM_RS_AlreadyRetrieved; return theMetaData->Document()->IsModified() ? PCDM_RS_AlreadyRetrievedAndModified : PCDM_RS_AlreadyRetrieved;
} }
else { else if (theAppendMode && !theMetaData->IsRetrieved())
TCollection_ExtendedString theFileName=theMetaData->FileName(); {
TCollection_ExtendedString theFormat=PCDM_ReadWriter::FileFormat(theFileName); return PCDM_RS_NoDocument;
if(theFormat.Length()==0) { }
TCollection_ExtendedString ResourceName=UTL::Extension(theFileName); else
ResourceName+=".FileFormat"; {
if(UTL::Find(Resources(),ResourceName)) { TCollection_ExtendedString theFileName = theMetaData->FileName();
theFormat=UTL::Value(Resources(),ResourceName); TCollection_ExtendedString theFormat = PCDM_ReadWriter::FileFormat(theFileName);
if (theFormat.Length() == 0) {
TCollection_ExtendedString ResourceName = UTL::Extension(theFileName);
ResourceName += ".FileFormat";
if (UTL::Find(Resources(), ResourceName)) {
theFormat = UTL::Value(Resources(), ResourceName);
} }
else else
return PCDM_RS_UnrecognizedFileFormat; return PCDM_RS_UnrecognizedFileFormat;
@ -227,8 +242,9 @@ Standard_Boolean CDF_Application::SetDefaultFolder(const Standard_ExtString aFol
//======================================================================= //=======================================================================
Handle(CDM_Document) CDF_Application::Retrieve(const Handle(CDM_MetaData)& aMetaData, Handle(CDM_Document) CDF_Application::Retrieve(const Handle(CDM_MetaData)& aMetaData,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) { const Message_ProgressRange& theRange) {
return Retrieve(aMetaData, UseStorageConfiguration, Standard_True, theRange); return Retrieve(aMetaData, UseStorageConfiguration, Standard_True, theFilter, theRange);
} }
//======================================================================= //=======================================================================
@ -238,33 +254,39 @@ Handle(CDM_Document) CDF_Application::Retrieve(const Handle(CDM_MetaData)& aMeta
Handle(CDM_Document) CDF_Application::Retrieve (const Handle(CDM_MetaData)& aMetaData, Handle(CDM_Document) CDF_Application::Retrieve (const Handle(CDM_MetaData)& aMetaData,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Standard_Boolean IsComponent, const Standard_Boolean IsComponent,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) { const Message_ProgressRange& theRange) {
Handle(CDM_Document) theDocumentToReturn; Handle(CDM_Document) theDocumentToReturn;
myRetrievableStatus = PCDM_RS_DriverFailure; myRetrievableStatus = PCDM_RS_DriverFailure;
if(IsComponent) { Standard_Boolean isAppendMode = !theFilter.IsNull() && theFilter->IsAppendMode();
if (IsComponent) {
Standard_SStream aMsg; Standard_SStream aMsg;
switch (CanRetrieve(aMetaData)) { myRetrievableStatus = CanRetrieve(aMetaData, isAppendMode);
switch (myRetrievableStatus) {
case PCDM_RS_UnknownDocument: case PCDM_RS_UnknownDocument:
aMsg << "could not find the referenced document: " << aMetaData->Path() << "; not found." <<(char)0 << std::endl; aMsg << "could not find the referenced document: " << aMetaData->Path() << "; not found." <<(char)0 << std::endl;
myRetrievableStatus = PCDM_RS_UnknownDocument;
throw Standard_Failure(aMsg.str().c_str());
break; break;
case PCDM_RS_PermissionDenied: case PCDM_RS_PermissionDenied:
aMsg << "Could not find the referenced document: " << aMetaData->Path() << "; permission denied. " <<(char)0 << std::endl; aMsg << "Could not find the referenced document: " << aMetaData->Path() << "; permission denied. " <<(char)0 << std::endl;
myRetrievableStatus = PCDM_RS_PermissionDenied; break;
throw Standard_Failure(aMsg.str().c_str()); case PCDM_RS_NoDocument:
aMsg << "Document for appending is not defined." << (char)0 << std::endl;
break; break;
default: default:
break; myRetrievableStatus = PCDM_RS_OK;
} }
if (myRetrievableStatus != PCDM_RS_OK)
throw Standard_Failure(aMsg.str().c_str());
myRetrievableStatus = PCDM_RS_DriverFailure;
} }
Standard_Boolean AlreadyRetrieved=aMetaData->IsRetrieved(); Standard_Boolean AlreadyRetrieved = aMetaData->IsRetrieved();
if(AlreadyRetrieved) myRetrievableStatus = PCDM_RS_AlreadyRetrieved; if (AlreadyRetrieved)
Standard_Boolean Modified=AlreadyRetrieved && aMetaData->Document()->IsModified(); myRetrievableStatus = PCDM_RS_AlreadyRetrieved;
if(Modified) myRetrievableStatus = PCDM_RS_AlreadyRetrievedAndModified; Standard_Boolean Modified = AlreadyRetrieved && aMetaData->Document()->IsModified();
if(!AlreadyRetrieved || Modified) if (Modified)
myRetrievableStatus = PCDM_RS_AlreadyRetrievedAndModified;
if (!AlreadyRetrieved || Modified || isAppendMode)
{ {
TCollection_ExtendedString aFormat; TCollection_ExtendedString aFormat;
if (!Format(aMetaData->FileName(), aFormat)) if (!Format(aMetaData->FileName(), aFormat))
@ -273,42 +295,46 @@ Handle(CDM_Document) CDF_Application::Retrieve (const Handle(CDM_MetaData)& aMet
aMsg << "Could not determine format for the file " << aMetaData->FileName() << (char)0; aMsg << "Could not determine format for the file " << aMetaData->FileName() << (char)0;
throw Standard_NoSuchObject(aMsg.str().c_str()); throw Standard_NoSuchObject(aMsg.str().c_str());
} }
Handle(PCDM_Reader) theReader = ReaderFromFormat (aFormat); Handle(PCDM_Reader) theReader = ReaderFromFormat(aFormat);
Handle(CDM_Document) theDocument; Handle(CDM_Document) aDocument;
if(Modified) { if (Modified || isAppendMode) {
theDocument=aMetaData->Document(); aDocument = aMetaData->Document();
theDocument->RemoveAllReferences(); if (!isAppendMode)
aDocument->RemoveAllReferences();
} }
else else
NewDocument(aFormat, theDocument); {
NewDocument(aFormat, aDocument);
SetReferenceCounter(theDocument,PCDM_RetrievalDriver::ReferenceCounter(aMetaData->FileName(), MessageDriver())); SetReferenceCounter(aDocument, PCDM_RetrievalDriver::ReferenceCounter(aMetaData->FileName(), MessageDriver()));
SetDocumentVersion(aDocument, aMetaData);
SetDocumentVersion(theDocument,aMetaData); myMetaDataDriver->ReferenceIterator(MessageDriver())->LoadReferences(aDocument, aMetaData, this, UseStorageConfiguration);
myMetaDataDriver->ReferenceIterator(MessageDriver())->LoadReferences(theDocument,aMetaData,this,UseStorageConfiguration); }
try { try {
OCC_CATCH_SIGNALS OCC_CATCH_SIGNALS
theReader->Read (aMetaData->FileName(), theDocument, this, theRange); theReader->Read(aMetaData->FileName(), aDocument, this, theFilter, theRange);
} }
catch (Standard_Failure const& anException) { catch (Standard_Failure const& anException) {
myRetrievableStatus = theReader->GetStatus(); myRetrievableStatus = theReader->GetStatus();
if(myRetrievableStatus > PCDM_RS_AlreadyRetrieved){ if (myRetrievableStatus > PCDM_RS_AlreadyRetrieved) {
Standard_SStream aMsg; Standard_SStream aMsg;
aMsg << anException << std::endl; aMsg << anException << std::endl;
throw Standard_Failure(aMsg.str().c_str()); throw Standard_Failure(aMsg.str().c_str());
} }
} }
myRetrievableStatus = theReader->GetStatus(); myRetrievableStatus = theReader->GetStatus();
theDocument->Open (this); // must be done before SetMetaData if (!isAppendMode)
theDocument->SetMetaData(aMetaData); {
aDocument->Open(this); // must be done before SetMetaData
aDocument->SetMetaData(aMetaData);
}
theDocumentToReturn=theDocument; theDocumentToReturn = aDocument;
} }
else else
theDocumentToReturn=aMetaData->Document(); theDocumentToReturn = aMetaData->Document();
return theDocumentToReturn; return theDocumentToReturn;
} }
@ -347,10 +373,11 @@ CDF_TypeOfActivation CDF_Application::TypeOfActivation(const Handle(CDM_MetaData
//function : Read //function : Read
//purpose : //purpose :
//======================================================================= //=======================================================================
Handle(CDM_Document) CDF_Application::Read (Standard_IStream& theIStream, void CDF_Application::Read (Standard_IStream& theIStream,
Handle(CDM_Document)& theDocument,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
Handle(CDM_Document) aDoc;
Handle(Storage_Data) dData; Handle(Storage_Data) dData;
TCollection_ExtendedString aFormat; TCollection_ExtendedString aFormat;
@ -373,20 +400,37 @@ Handle(CDM_Document) CDF_Application::Read (Standard_IStream& theIStream,
if (aFormat.IsEmpty()) if (aFormat.IsEmpty())
{ {
myRetrievableStatus = PCDM_RS_FormatFailure; myRetrievableStatus = PCDM_RS_FormatFailure;
return aDoc; return;
} }
// 1. use a format name to detect plugin corresponding to the format to continue reading // use a format name to detect plugin corresponding to the format to continue reading
Handle(PCDM_Reader) aReader = ReaderFromFormat (aFormat); Handle(PCDM_Reader) aReader = ReaderFromFormat (aFormat);
// 2. create document with the detected reader if (theFilter.IsNull() || !theFilter->IsAppendMode())
NewDocument(aFormat, aDoc); {
NewDocument(aFormat, theDocument);
}
else
{
// check the document is ready to append
if (theDocument.IsNull())
{
myRetrievableStatus = PCDM_RS_NoDocument;
return;
}
//check document format equals to the format of the stream
if (theDocument->StorageFormat() != aFormat)
{
myRetrievableStatus = PCDM_RS_FormatFailure;
return;
}
}
// 3. read the content of theIStream to aDoc // read the content of theIStream to aDoc
try try
{ {
OCC_CATCH_SIGNALS OCC_CATCH_SIGNALS
aReader->Read (theIStream, dData, aDoc, this, theRange); aReader->Read (theIStream, dData, theDocument, this, theFilter, theRange);
} }
catch (Standard_Failure const& anException) catch (Standard_Failure const& anException)
{ {
@ -400,8 +444,6 @@ Handle(CDM_Document) CDF_Application::Read (Standard_IStream& theIStream,
} }
myRetrievableStatus = aReader->GetStatus(); myRetrievableStatus = aReader->GetStatus();
return aDoc;
} }
//======================================================================= //=======================================================================
@ -541,11 +583,11 @@ Standard_Boolean CDF_Application::Format(const TCollection_ExtendedString& aFile
//function : CanRetrieve //function : CanRetrieve
//purpose : //purpose :
//======================================================================= //=======================================================================
PCDM_ReaderStatus CDF_Application::CanRetrieve(const Handle(CDM_MetaData)& aMetaData) { PCDM_ReaderStatus CDF_Application::CanRetrieve(const Handle(CDM_MetaData)& aMetaData, const bool theAppendMode) {
if(aMetaData->HasVersion()) if(aMetaData->HasVersion())
return CanRetrieve(aMetaData->Folder(),aMetaData->Name(),aMetaData->Version()); return CanRetrieve(aMetaData->Folder(),aMetaData->Name(),aMetaData->Version(), theAppendMode);
else else
return CanRetrieve(aMetaData->Folder(),aMetaData->Name()); return CanRetrieve(aMetaData->Folder(),aMetaData->Name(), theAppendMode);
} }
//======================================================================= //=======================================================================

View File

@ -103,6 +103,7 @@ public:
(const TCollection_ExtendedString& aFolder, (const TCollection_ExtendedString& aFolder,
const TCollection_ExtendedString& aName, const TCollection_ExtendedString& aName,
const Standard_Boolean UseStorageConfiguration = Standard_True, const Standard_Boolean UseStorageConfiguration = Standard_True,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! This method retrieves a document from the database. //! This method retrieves a document from the database.
@ -124,22 +125,27 @@ public:
const TCollection_ExtendedString& aName, const TCollection_ExtendedString& aName,
const TCollection_ExtendedString& aVersion, const TCollection_ExtendedString& aVersion,
const Standard_Boolean UseStorageConfiguration = Standard_True, const Standard_Boolean UseStorageConfiguration = Standard_True,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
Standard_EXPORT PCDM_ReaderStatus CanRetrieve (const TCollection_ExtendedString& aFolder, Standard_EXPORT PCDM_ReaderStatus CanRetrieve (const TCollection_ExtendedString& theFolder,
const TCollection_ExtendedString& aName); const TCollection_ExtendedString& theName,
const bool theAppendMode);
Standard_EXPORT PCDM_ReaderStatus CanRetrieve (const TCollection_ExtendedString& aFolder, Standard_EXPORT PCDM_ReaderStatus CanRetrieve (const TCollection_ExtendedString& theFolder,
const TCollection_ExtendedString& aName, const TCollection_ExtendedString& theName,
const TCollection_ExtendedString& aVersion); const TCollection_ExtendedString& theVersion,
const bool theAppendMode);
//! Checks status after Retrieve //! Checks status after Retrieve
PCDM_ReaderStatus GetRetrieveStatus() const { return myRetrievableStatus; } PCDM_ReaderStatus GetRetrieveStatus() const { return myRetrievableStatus; }
//! Reads aDoc from standard SEEKABLE stream theIStream, //! Reads theDocument from standard SEEKABLE stream theIStream,
//! the stream should support SEEK functionality //! the stream should support SEEK functionality
Standard_EXPORT Handle(CDM_Document) Read Standard_EXPORT void Read
(Standard_IStream& theIStream, (Standard_IStream& theIStream,
Handle(CDM_Document)& theDocument,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Returns instance of read driver for specified format. //! Returns instance of read driver for specified format.
@ -209,19 +215,21 @@ private:
Standard_EXPORT Handle(CDM_Document) Retrieve Standard_EXPORT Handle(CDM_Document) Retrieve
(const Handle(CDM_MetaData)& aMetaData, (const Handle(CDM_MetaData)& aMetaData,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE;
Standard_EXPORT Handle(CDM_Document) Retrieve Standard_EXPORT Handle(CDM_Document) Retrieve
(const Handle(CDM_MetaData)& aMetaData, (const Handle(CDM_MetaData)& aMetaData,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Standard_Boolean IsComponent, const Standard_Boolean IsComponent,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
Standard_EXPORT Standard_Integer DocumentVersion (const Handle(CDM_MetaData)& theMetaData) Standard_OVERRIDE; Standard_EXPORT Standard_Integer DocumentVersion (const Handle(CDM_MetaData)& theMetaData) Standard_OVERRIDE;
Standard_EXPORT CDF_TypeOfActivation TypeOfActivation (const Handle(CDM_MetaData)& aMetaData); Standard_EXPORT CDF_TypeOfActivation TypeOfActivation (const Handle(CDM_MetaData)& aMetaData);
Standard_EXPORT PCDM_ReaderStatus CanRetrieve (const Handle(CDM_MetaData)& aMetaData); Standard_EXPORT PCDM_ReaderStatus CanRetrieve (const Handle(CDM_MetaData)& aMetaData, const bool theAppendMode);
protected: protected:

View File

@ -34,6 +34,7 @@ class CDM_MetaData;
class CDM_Document; class CDM_Document;
class Resource_Manager; class Resource_Manager;
class Message_Messenger; class Message_Messenger;
class PCDM_ReaderFilter;
class CDM_Application; class CDM_Application;
DEFINE_STANDARD_HANDLE(CDM_Application, Standard_Transient) DEFINE_STANDARD_HANDLE(CDM_Application, Standard_Transient)
@ -95,6 +96,7 @@ private:
Standard_EXPORT virtual Handle(CDM_Document) Retrieve Standard_EXPORT virtual Handle(CDM_Document) Retrieve
(const Handle(CDM_MetaData)& aMetaData, (const Handle(CDM_MetaData)& aMetaData,
const Standard_Boolean UseStorageConfiguration, const Standard_Boolean UseStorageConfiguration,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()) = 0; const Message_ProgressRange& theRange = Message_ProgressRange()) = 0;
//! returns -1 if the metadata has no modification counter. //! returns -1 if the metadata has no modification counter.

View File

@ -31,6 +31,7 @@
#include <TDF_Data.hxx> #include <TDF_Data.hxx>
#include <TDF_ChildIterator.hxx> #include <TDF_ChildIterator.hxx>
#include <TDF_Tool.hxx> #include <TDF_Tool.hxx>
#include <PCDM_ReaderFilter.hxx>
#include <OSD_Path.hxx> #include <OSD_Path.hxx>
#include <OSD_OpenFile.hxx> #include <OSD_OpenFile.hxx>
@ -128,43 +129,73 @@ static Standard_Integer DDocStd_Open (Draw_Interpretor& di,
{ {
if (nb >= 3) { if (nb >= 3) {
TCollection_ExtendedString path (a[1], Standard_True); TCollection_ExtendedString path (a[1], Standard_True);
Standard_CString DocName = a[2];
Handle(TDocStd_Application) A = DDocStd::GetApplication(); Handle(TDocStd_Application) A = DDocStd::GetApplication();
Handle(TDocStd_Document) D; Handle(TDocStd_Document) D;
Standard_Integer insession = A->IsInSession(path);
if (insession > 0) {
di <<"document " << insession << " is already in session\n";
return 0;
}
PCDM_ReaderStatus theStatus; PCDM_ReaderStatus theStatus;
Standard_Boolean anUseStream = Standard_False; Standard_Boolean anUseStream = Standard_False;
Handle(PCDM_ReaderFilter) aFilter = new PCDM_ReaderFilter;
for ( Standard_Integer i = 3; i < nb; i++ ) for ( Standard_Integer i = 3; i < nb; i++ )
{ {
if (!strcmp (a[i], "-stream")) TCollection_AsciiString anArg(a[i]);
if (anArg == "-append")
{
aFilter->Mode() = PCDM_ReaderFilter::AppendMode_Protect;
}
else if (anArg == "-overwrite")
{
aFilter->Mode() = PCDM_ReaderFilter::AppendMode_Overwrite;
}
else if (anArg == "-stream")
{ {
di << "standard SEEKABLE stream is used\n"; di << "standard SEEKABLE stream is used\n";
anUseStream = Standard_True; anUseStream = Standard_True;
break; }
else if (anArg.StartsWith("-skip"))
{
TCollection_AsciiString anAttrType = anArg.SubString(6, anArg.Length());
aFilter->AddSkipped(anAttrType);
}
else if (anArg.StartsWith("-read"))
{
TCollection_AsciiString aValue = anArg.SubString(6, anArg.Length());
if (aValue.Value(1) == '0') // path
{
aFilter->AddPath(aValue);
}
else // attribute to read
{
aFilter->AddRead(aValue);
}
} }
} }
if (aFilter->IsAppendMode() && !DDocStd::GetDocument(DocName, D, Standard_False))
{
di << "for append mode document " << DocName << " must be already created\n";
return 1;
}
Handle(Draw_ProgressIndicator) aProgress = new Draw_ProgressIndicator(di, 1); Handle(Draw_ProgressIndicator) aProgress = new Draw_ProgressIndicator(di, 1);
if (anUseStream) if (anUseStream)
{ {
std::ifstream aFileStream; std::ifstream aFileStream;
OSD_OpenStream (aFileStream, path, std::ios::in | std::ios::binary); OSD_OpenStream (aFileStream, path, std::ios::in | std::ios::binary);
theStatus = A->Open (aFileStream, D, aProgress->Start()); theStatus = A->Open (aFileStream, D, aFilter, aProgress->Start());
} }
else else
{ {
theStatus = A->Open (path, D, aProgress->Start()); theStatus = A->Open (path, D, aFilter , aProgress->Start());
} }
if (theStatus == PCDM_RS_OK && !D.IsNull()) if (theStatus == PCDM_RS_OK && !D.IsNull())
{ {
Handle(DDocStd_DrawDocument) DD = new DDocStd_DrawDocument(D); if (!aFilter->IsAppendMode())
TDataStd_Name::Set(D->GetData()->Root(),a[2]); {
Draw::Set(a[2],DD); Handle(DDocStd_DrawDocument) DD = new DDocStd_DrawDocument (D);
TDataStd_Name::Set (D->GetData()->Root(), DocName);
Draw::Set (DocName, DD);
}
return 0; return 0;
} }
else else
@ -579,7 +610,13 @@ void DDocStd::ApplicationCommands(Draw_Interpretor& theCommands)
__FILE__, DDocStd_NewDocument, g); __FILE__, DDocStd_NewDocument, g);
theCommands.Add("Open", theCommands.Add("Open",
"Open path docname [-stream]", "Open path docname [-stream] [-skipAttribute] [-readAttribute] [-readPath] [-append|-overwrite]"
"\n\t\t The options are:"
"\n\t\t -stream : opens path as a stream"
"\n\t\t -skipAttribute : class name of the attribute to skip during open, for example -skipTDF_Reference"
"\n\t\t -readAttribute : class name of the attribute to read only during open, for example -readTDataStd_Name loads only such attributes"
"\n\t\t -append : to read file into already existing document once again, append new attributes and don't touch existing"
"\n\t\t -overwrite : to read file into already existing document once again, overwriting existing attributes",
__FILE__, DDocStd_Open, g); __FILE__, DDocStd_Open, g);
theCommands.Add("SaveAs", theCommands.Add("SaveAs",

View File

@ -9,6 +9,8 @@ PCDM_DriverError.hxx
PCDM_Reader.cxx PCDM_Reader.cxx
PCDM_Reader.hxx PCDM_Reader.hxx
PCDM_Reader.lxx PCDM_Reader.lxx
PCDM_ReaderFilter.cxx
PCDM_ReaderFilter.hxx
PCDM_ReaderStatus.hxx PCDM_ReaderStatus.hxx
PCDM_ReadWriter.cxx PCDM_ReadWriter.cxx
PCDM_ReadWriter.hxx PCDM_ReadWriter.hxx

View File

@ -69,10 +69,7 @@ void PCDM_ReadWriter::Open (const Handle(Storage_BaseDriver)& aDriver,
//purpose : //purpose :
//======================================================================= //=======================================================================
//Handle(PCDM_ReadWriter) PCDM_ReadWriter::Reader(const TCollection_ExtendedString& aFileName) { Handle(PCDM_ReadWriter) PCDM_ReadWriter::Reader (const TCollection_ExtendedString&)
Handle(PCDM_ReadWriter) PCDM_ReadWriter::Reader
(const TCollection_ExtendedString&)
{ {
return (new PCDM_ReadWriter_1); return (new PCDM_ReadWriter_1);
} }
@ -82,7 +79,7 @@ Handle(PCDM_ReadWriter) PCDM_ReadWriter::Reader
//purpose : //purpose :
//======================================================================= //=======================================================================
Handle(PCDM_ReadWriter) PCDM_ReadWriter::Writer () Handle(PCDM_ReadWriter) PCDM_ReadWriter::Writer()
{ {
return (new PCDM_ReadWriter_1); return (new PCDM_ReadWriter_1);
} }

View File

@ -30,7 +30,7 @@ class PCDM_DriverError;
class CDM_Document; class CDM_Document;
class TCollection_ExtendedString; class TCollection_ExtendedString;
class CDM_Application; class CDM_Application;
class PCDM_ReaderFilter;
class PCDM_Reader; class PCDM_Reader;
DEFINE_STANDARD_HANDLE(PCDM_Reader, Standard_Transient) DEFINE_STANDARD_HANDLE(PCDM_Reader, Standard_Transient)
@ -45,12 +45,14 @@ public:
Standard_EXPORT virtual void Read (const TCollection_ExtendedString& aFileName, Standard_EXPORT virtual void Read (const TCollection_ExtendedString& aFileName,
const Handle(CDM_Document)& aNewDocument, const Handle(CDM_Document)& aNewDocument,
const Handle(CDM_Application)& anApplication, const Handle(CDM_Application)& anApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theProgress = Message_ProgressRange()) = 0; const Message_ProgressRange& theProgress = Message_ProgressRange()) = 0;
Standard_EXPORT virtual void Read (Standard_IStream& theIStream, Standard_EXPORT virtual void Read (Standard_IStream& theIStream,
const Handle(Storage_Data)& theStorageData, const Handle(Storage_Data)& theStorageData,
const Handle(CDM_Document)& theDoc, const Handle(CDM_Document)& theDoc,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theProgress = Message_ProgressRange()) = 0; const Message_ProgressRange& theProgress = Message_ProgressRange()) = 0;
PCDM_ReaderStatus GetStatus() const; PCDM_ReaderStatus GetStatus() const;

View File

@ -0,0 +1,175 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <PCDM_ReaderFilter.hxx>
IMPLEMENT_STANDARD_RTTIEXT(PCDM_ReaderFilter,Standard_Transient)
PCDM_ReaderFilter::PCDM_ReaderFilter (const Handle(Standard_Type)& theSkipped) : myAppend (AppendMode_Forbid)
{
mySkip.Add(theSkipped->Name());
}
PCDM_ReaderFilter::PCDM_ReaderFilter (const TCollection_AsciiString& theEntryToRead) : myAppend (AppendMode_Forbid)
{
mySubTrees.Append(theEntryToRead);
}
PCDM_ReaderFilter::PCDM_ReaderFilter (const AppendMode theAppend) : myAppend (theAppend)
{}
void PCDM_ReaderFilter::Clear()
{
mySkip.Clear();
myRead.Clear();
mySubTrees.Clear();
}
PCDM_ReaderFilter::~PCDM_ReaderFilter()
{
ClearTree();
}
Standard_Boolean PCDM_ReaderFilter::IsPassed (const Handle(Standard_Type)& theAttributeID) const
{
return IsPassedAttr(theAttributeID->Name());
}
Standard_Boolean PCDM_ReaderFilter::IsPassedAttr (const TCollection_AsciiString& theAttributeType) const
{
return myRead.IsEmpty() ? !mySkip.Contains (theAttributeType) :
myRead.Contains (theAttributeType);
}
Standard_Boolean PCDM_ReaderFilter::IsPassed (const TCollection_AsciiString& theEntry) const
{
if (mySubTrees.IsEmpty())
return true;
for (NCollection_List<TCollection_AsciiString>::Iterator anEntry (mySubTrees); anEntry.More(); anEntry.Next())
{
if (theEntry.StartsWith (anEntry.Value()))
{
if (theEntry.Length() > anEntry.Value().Length() &&
theEntry.Value (anEntry.Value().Length() + 1) != ':') // case when theEntry="0:10" should not match "0:1"
continue;
return true;
}
}
return false;
}
Standard_Boolean PCDM_ReaderFilter::IsSubPassed (const TCollection_AsciiString& theEntry) const
{
if (mySubTrees.IsEmpty() || theEntry.Length() == 2) // root is always passed if any sub is defined
return true;
for (NCollection_List<TCollection_AsciiString>::Iterator anEntry (mySubTrees); anEntry.More(); anEntry.Next())
{
if (theEntry.Length() < anEntry.Value().Length() &&
anEntry.Value().Value (theEntry.Length() + 1) == ':' && // case when theEntry="0:1" should not match "0:10"
anEntry.Value().StartsWith (theEntry))
return true;
}
return false;
}
Standard_Boolean PCDM_ReaderFilter::IsPartTree()
{
return !(mySubTrees.IsEmpty() || (mySubTrees.Size() == 1 && mySubTrees.First().Length() < 3));
}
void PCDM_ReaderFilter::StartIteration()
{
myCurrent = &myTree;
myCurrentDepth = 0;
ClearTree();
myTree.Bind(-1, NULL);
if (mySubTrees.IsEmpty())
return;
// create an iteration-tree by the mySubTrees entries
for (NCollection_List<TCollection_AsciiString>::Iterator aTreeIter (mySubTrees); aTreeIter.More(); aTreeIter.Next())
{
TagTree* aMap = &myTree;
TCollection_AsciiString aTagStr, anEntry = aTreeIter.Value();
for (Standard_Integer aTagIndex = 2; !anEntry.IsEmpty(); ++aTagIndex) // skip the root tag
{
aTagStr = anEntry.Token(":", aTagIndex);
if (aTagStr.IsEmpty())
break;
Standard_Integer aTag = aTagStr.IntegerValue();
if (aMap->IsBound (aTag))
{
aMap = (TagTree*)aMap->Find (aTag);
}
else
{
TagTree* aNewMap = new TagTree;
aNewMap->Bind (-1, aMap); // to be able to iterate up, keep father map in the child
aMap->Bind (aTag, aNewMap);
aMap = aNewMap;
}
}
aMap->Bind (-2, NULL); // identifier that this node is in subtrees definition
}
}
void PCDM_ReaderFilter::Up()
{
if (myCurrentDepth == 0)
myCurrent = (TagTree*)myCurrent->Find(-1);
else
myCurrentDepth--;
}
void PCDM_ReaderFilter::Down (const int& theTag)
{
if (myCurrentDepth== 0)
{
if (myCurrent->IsBound (theTag))
myCurrent= (TagTree*)myCurrent->Find (theTag);
else
++myCurrentDepth;
}
else
++myCurrentDepth;
}
Standard_Boolean PCDM_ReaderFilter::IsPassed() const
{
return myCurrent->IsBound(-2);
}
Standard_Boolean PCDM_ReaderFilter::IsSubPassed() const
{
return myCurrentDepth == 0;
}
void PCDM_ReaderFilter::ClearSubTree (const Standard_Address theMap)
{
if (theMap)
{
TagTree* aMap = (TagTree*)theMap;
for (TagTree::Iterator aTagIter (*aMap); aTagIter.More(); aTagIter.Next())
if (aTagIter.Key() != -1)
ClearSubTree (aTagIter.Value());
delete aMap;
}
}
void PCDM_ReaderFilter::ClearTree()
{
for (TagTree::Iterator aTagIter (myTree); aTagIter.More(); aTagIter.Next())
if (aTagIter.Key() != -1)
ClearSubTree (aTagIter.Value());
myTree.Clear();
}

View File

@ -0,0 +1,136 @@
// Copyright (c) 2021 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#ifndef _PCDM_ReaderFilter_HeaderFile
#define _PCDM_ReaderFilter_HeaderFile
#include <Standard_Type.hxx>
#include <Standard_Transient.hxx>
#include <TCollection_AsciiString.hxx>
#include <NCollection_Map.hxx>
#include <NCollection_List.hxx>
class PCDM_ReaderFilter;
DEFINE_STANDARD_HANDLE (PCDM_ReaderFilter, Standard_Transient)
//! Class represents a document reading filter.
//!
//! It allows to set attributes (by class names) that must be skipped during the document reading
//! or attributes that must be retrieved only.
//! In addition it is possible to define one or several subtrees (by entry) which must be
//! retrieved during the reading. Other labels are created, but no one attribute on them.
class PCDM_ReaderFilter : public Standard_Transient
{
public:
//! Supported modes of appending the file content into existing document
enum AppendMode
{
AppendMode_Forbid = 0, //!< do not allow append, default mode
AppendMode_Protect = 1, //!< keeps existing attributes, reads only new ones
AppendMode_Overwrite = 2, //!< overwrites the existing attributes by the loaded ones
};
//! Creates an empty filter, so, all will be retrieved if nothing else is defined.
inline PCDM_ReaderFilter() : myAppend(AppendMode_Forbid) {}
//! Creates a filter to skip only one type of attributes.
Standard_EXPORT PCDM_ReaderFilter (const Handle(Standard_Type)& theSkipped);
//! Creates a filter to read only sub-labels of a label-path.
//! Like, for "0:2" it will read all attributes for labels "0:2", "0:2:1", etc.
Standard_EXPORT PCDM_ReaderFilter (const TCollection_AsciiString& theEntryToRead);
//! Creates a filter to append the content of file to open to existing document.
Standard_EXPORT PCDM_ReaderFilter (const AppendMode theAppend);
//! Destructor for the filter content
Standard_EXPORT ~PCDM_ReaderFilter();
//! Adds skipped attribute by type.
Standard_EXPORT void AddSkipped (const Handle(Standard_Type)& theSkipped) { mySkip.Add(theSkipped->Name()); }
//! Adds skipped attribute by type name.
Standard_EXPORT void AddSkipped (const TCollection_AsciiString& theSkipped) { mySkip.Add (theSkipped); }
//! Adds attribute to read by type. Disables the skipped attributes added.
Standard_EXPORT void AddRead (const Handle(Standard_Type)& theRead) { myRead.Add(theRead->Name()); }
//! Adds attribute to read by type name. Disables the skipped attributes added.
Standard_EXPORT void AddRead (const TCollection_AsciiString& theRead) { myRead.Add (theRead); }
//! Adds sub-tree path (like "0:2").
Standard_EXPORT void AddPath (const TCollection_AsciiString& theEntryToRead) { mySubTrees.Append (theEntryToRead); }
//! Makes filter pass all data.
Standard_EXPORT void Clear();
//! Returns true if attribute must be read.
Standard_EXPORT virtual Standard_Boolean IsPassed (const Handle(Standard_Type)& theAttributeID) const;
//! Returns true if attribute must be read.
Standard_EXPORT virtual Standard_Boolean IsPassedAttr (const TCollection_AsciiString& theAttributeType) const;
//! Returns true if content of the label must be read.
Standard_EXPORT virtual Standard_Boolean IsPassed (const TCollection_AsciiString& theEntry) const;
//! Returns true if some sub-label of the given label is passed.
Standard_EXPORT virtual Standard_Boolean IsSubPassed (const TCollection_AsciiString& theEntry) const;
//! Returns true if only part of the document tree will be retrieved.
Standard_EXPORT virtual Standard_Boolean IsPartTree();
//! Returns the append mode.
Standard_EXPORT AppendMode& Mode() { return myAppend; }
//! Returns true if appending to the document is performed.
Standard_EXPORT Standard_Boolean IsAppendMode() { return myAppend != PCDM_ReaderFilter::AppendMode_Forbid; }
//! Starts the tree iterator. It is used for fast searching of passed labels if the whole tree of labels
//! is parsed. So, on each iteration step the methods Up and Down must be called after the iteration start.
Standard_EXPORT virtual void StartIteration();
//! Iteration to the child label.
Standard_EXPORT virtual void Up();
//! Iteration to the child with defined tag.
Standard_EXPORT virtual void Down (const int& theTag);
//! Returns true if content of the currently iterated label must be read.
Standard_EXPORT virtual Standard_Boolean IsPassed() const;
//! Returns true if some sub-label of the currently iterated label is passed.
Standard_EXPORT virtual Standard_Boolean IsSubPassed() const;
DEFINE_STANDARD_RTTIEXT (PCDM_ReaderFilter, Standard_Transient)
private:
//! Clears the iteration tree
Standard_EXPORT void ClearTree();
//! Clears the iteration sub-tree
Standard_EXPORT static void ClearSubTree (const Standard_Address theMap);
protected:
//! Append mode for reading files into existing document
AppendMode myAppend;
//! Class names of attributes that must be skipped during the read
NCollection_Map<TCollection_AsciiString> mySkip;
//! Class names of only attributes to read (if it is not empty, mySkip is unused)
NCollection_Map<TCollection_AsciiString> myRead;
//! Paths to the labels that must be read. If it is empty, read all.
NCollection_List<TCollection_AsciiString> mySubTrees;
//! Map from tag of a label to sub-tree of this tag. Used for fast browsing the tree
//! and compare with entities that must be read.
typedef NCollection_DataMap<Standard_Integer, Standard_Address> TagTree;
//! Whole tree that correspond to retrieved document.
TagTree myTree;
//! Pointer to the current node of the iterator.
TagTree* myCurrent;
//! If a node does not described in the read-entries, the iterator goes inside of this subtree just by
//! keeping the depth of iteration.
Standard_Integer myCurrentDepth;
};
#endif // _PCDM_ReaderFilter_HeaderFile

View File

@ -45,6 +45,7 @@ IMPLEMENT_STANDARD_RTTIEXT (StdLDrivers_DocumentRetrievalDriver, PCDM_RetrievalD
void StdLDrivers_DocumentRetrievalDriver::Read (const TCollection_ExtendedString& theFileName, void StdLDrivers_DocumentRetrievalDriver::Read (const TCollection_ExtendedString& theFileName,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& , const Handle(CDM_Application)& ,
const Handle(PCDM_ReaderFilter)& ,
const Message_ProgressRange& /*theRange*/) const Message_ProgressRange& /*theRange*/)
{ {
// Read header data and persistent document // Read header data and persistent document
@ -229,6 +230,7 @@ void StdLDrivers_DocumentRetrievalDriver::Read (Standard_IStream&
const Handle(Storage_Data)& /*theStorageData*/, const Handle(Storage_Data)& /*theStorageData*/,
const Handle(CDM_Document)& /*theDoc*/, const Handle(CDM_Document)& /*theDoc*/,
const Handle(CDM_Application)& /*theApplication*/, const Handle(CDM_Application)& /*theApplication*/,
const Handle(PCDM_ReaderFilter)&/*theFilter*/,
const Message_ProgressRange& /*theRange*/) const Message_ProgressRange& /*theRange*/)
{ {
throw Standard_NotImplemented("Reading from stream is not supported by StdLDrivers_DocumentRetrievalDriver"); throw Standard_NotImplemented("Reading from stream is not supported by StdLDrivers_DocumentRetrievalDriver");

View File

@ -29,6 +29,7 @@ public:
Standard_EXPORT virtual void Read (const TCollection_ExtendedString& theFileName, Standard_EXPORT virtual void Read (const TCollection_ExtendedString& theFileName,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE;
//! Override pure virtual method (raises exception Standard_NotImplemented) //! Override pure virtual method (raises exception Standard_NotImplemented)
@ -36,6 +37,7 @@ public:
const Handle(Storage_Data)& theStorageData, const Handle(Storage_Data)& theStorageData,
const Handle(CDM_Document)& theDoc, const Handle(CDM_Document)& theDoc,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE;
DEFINE_STANDARD_RTTIEXT (StdLDrivers_DocumentRetrievalDriver, PCDM_RetrievalDriver) DEFINE_STANDARD_RTTIEXT (StdLDrivers_DocumentRetrievalDriver, PCDM_RetrievalDriver)

View File

@ -21,6 +21,7 @@
#include <CDF_Store.hxx> #include <CDF_Store.hxx>
#include <PCDM_RetrievalDriver.hxx> #include <PCDM_RetrievalDriver.hxx>
#include <PCDM_StorageDriver.hxx> #include <PCDM_StorageDriver.hxx>
#include <PCDM_ReaderFilter.hxx>
#include <Plugin.hxx> #include <Plugin.hxx>
#include <Plugin_Failure.hxx> #include <Plugin_Failure.hxx>
#include <Resource_Manager.hxx> #include <Resource_Manager.hxx>
@ -161,7 +162,7 @@ Standard_Integer TDocStd_Application::NbDocuments() const
//purpose : //purpose :
//======================================================================= //=======================================================================
void TDocStd_Application::GetDocument(const Standard_Integer index,Handle(TDocStd_Document)& aDoc) const void TDocStd_Application::GetDocument(const Standard_Integer index,Handle(TDocStd_Document)& theDoc) const
{ {
CDF_DirectoryIterator it (myDirectory); CDF_DirectoryIterator it (myDirectory);
Standard_Integer current = 0; Standard_Integer current = 0;
@ -170,7 +171,7 @@ void TDocStd_Application::GetDocument(const Standard_Integer index,Handle(TDocSt
if (index == current) { if (index == current) {
Handle(TDocStd_Document) D = Handle(TDocStd_Document) D =
Handle(TDocStd_Document)::DownCast(it.Document()); Handle(TDocStd_Document)::DownCast(it.Document());
aDoc = D; theDoc = D;
return; return;
} }
} }
@ -181,12 +182,12 @@ void TDocStd_Application::GetDocument(const Standard_Integer index,Handle(TDocSt
//purpose : //purpose :
//======================================================================= //=======================================================================
void TDocStd_Application::NewDocument(const TCollection_ExtendedString& format, Handle(CDM_Document)& aDoc) void TDocStd_Application::NewDocument(const TCollection_ExtendedString& format, Handle(CDM_Document)& theDoc)
{ {
Handle(TDocStd_Document) D = new TDocStd_Document(format); Handle(TDocStd_Document) D = new TDocStd_Document(format);
InitDocument (D); InitDocument (D);
CDF_Application::Open(D); // add the document in the session CDF_Application::Open(D); // add the document in the session
aDoc = D; theDoc = D;
} }
//======================================================================= //=======================================================================
@ -195,11 +196,11 @@ void TDocStd_Application::NewDocument(const TCollection_ExtendedString& format,
// : Internally it calls a virtual method NewDocument() with CDM_Document object. // : Internally it calls a virtual method NewDocument() with CDM_Document object.
//======================================================================= //=======================================================================
void TDocStd_Application::NewDocument (const TCollection_ExtendedString& format, Handle(TDocStd_Document)& aDoc) void TDocStd_Application::NewDocument (const TCollection_ExtendedString& format, Handle(TDocStd_Document)& theDoc)
{ {
Handle(CDM_Document) aCDMDoc; Handle(CDM_Document) aCDMDoc;
NewDocument (format, aCDMDoc); NewDocument (format, aCDMDoc);
aDoc = Handle(TDocStd_Document)::DownCast (aCDMDoc); theDoc = Handle(TDocStd_Document)::DownCast (aCDMDoc);
} }
//======================================================================= //=======================================================================
@ -216,20 +217,20 @@ void TDocStd_Application::InitDocument(const Handle(CDM_Document)& /*aDoc*/) con
//purpose : //purpose :
//======================================================================= //=======================================================================
void TDocStd_Application::Close(const Handle(TDocStd_Document)& aDoc) void TDocStd_Application::Close(const Handle(TDocStd_Document)& theDoc)
{ {
if (aDoc.IsNull()) if (theDoc.IsNull())
{ {
return; return;
} }
Handle(TDocStd_Owner) Owner; Handle(TDocStd_Owner) Owner;
if (aDoc->Main().Root().FindAttribute(TDocStd_Owner::GetID(),Owner)) { if (theDoc->Main().Root().FindAttribute(TDocStd_Owner::GetID(),Owner)) {
Handle(TDocStd_Document) emptyDoc; Handle(TDocStd_Document) emptyDoc;
Owner->SetDocument(emptyDoc); Owner->SetDocument(emptyDoc);
} }
aDoc->BeforeClose(); theDoc->BeforeClose();
CDF_Application::Close(aDoc); CDF_Application::Close(theDoc);
} }
//======================================================================= //=======================================================================
@ -267,7 +268,8 @@ Standard_Integer TDocStd_Application::IsInSession (const TCollection_ExtendedStr
//======================================================================= //=======================================================================
PCDM_ReaderStatus TDocStd_Application::Open (const TCollection_ExtendedString& path, PCDM_ReaderStatus TDocStd_Application::Open (const TCollection_ExtendedString& path,
Handle(TDocStd_Document)& aDoc, Handle(TDocStd_Document)& theDoc,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
PCDM_ReaderStatus status = PCDM_RS_DriverFailure; PCDM_ReaderStatus status = PCDM_RS_DriverFailure;
@ -276,7 +278,7 @@ PCDM_ReaderStatus TDocStd_Application::Open (const TCollection_ExtendedString& p
TCollection_ExtendedString file = tool.Name(); TCollection_ExtendedString file = tool.Name();
file += "."; file += ".";
file += tool.Extension(); file += tool.Extension();
status = CanRetrieve(directory, file); status = CanRetrieve(directory, file, !theFilter.IsNull() && theFilter->IsAppendMode());
if (status != PCDM_RS_OK) if (status != PCDM_RS_OK)
{ {
@ -287,9 +289,10 @@ PCDM_ReaderStatus TDocStd_Application::Open (const TCollection_ExtendedString& p
{ {
OCC_CATCH_SIGNALS OCC_CATCH_SIGNALS
Handle(TDocStd_Document) D = Handle(TDocStd_Document) D =
Handle(TDocStd_Document)::DownCast(Retrieve(directory, file, Standard_True, theRange)); Handle(TDocStd_Document)::DownCast(Retrieve(directory, file, Standard_True, theFilter, theRange));
if (theFilter.IsNull() || !theFilter->IsAppendMode())
CDF_Application::Open(D); CDF_Application::Open(D);
aDoc = D; theDoc = D;
} }
catch (Standard_Failure const& anException) catch (Standard_Failure const& anException)
{ {
@ -316,17 +319,20 @@ PCDM_ReaderStatus TDocStd_Application::Open (const TCollection_ExtendedString& p
//======================================================================= //=======================================================================
PCDM_ReaderStatus TDocStd_Application::Open (Standard_IStream& theIStream, PCDM_ReaderStatus TDocStd_Application::Open (Standard_IStream& theIStream,
Handle(TDocStd_Document)& theDoc, Handle(TDocStd_Document)& theDoc,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
try try
{ {
OCC_CATCH_SIGNALS OCC_CATCH_SIGNALS
Handle(TDocStd_Document) D = Handle(TDocStd_Document)::DownCast(Read(theIStream, theRange)); Handle(CDM_Document) aCDMDoc = theDoc;
Read(theIStream, aCDMDoc, theFilter, theRange);
// Read calls NewDocument of TDocStd_Application, so, it should the TDocStd_Document in the result anyway
theDoc = Handle(TDocStd_Document)::DownCast(aCDMDoc);
if (!D.IsNull()) if (!theDoc.IsNull() && (theFilter.IsNull() || !theFilter->IsAppendMode()))
{ {
CDF_Application::Open(D); CDF_Application::Open(theDoc);
theDoc = D;
} }
} }
@ -346,7 +352,7 @@ PCDM_ReaderStatus TDocStd_Application::Open (Standard_IStream& theIStream,
//purpose : //purpose :
//======================================================================= //=======================================================================
PCDM_StoreStatus TDocStd_Application::SaveAs (const Handle(TDocStd_Document)& D, PCDM_StoreStatus TDocStd_Application::SaveAs (const Handle(TDocStd_Document)& theDoc,
const TCollection_ExtendedString& path, const TCollection_ExtendedString& path,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
@ -355,8 +361,8 @@ PCDM_StoreStatus TDocStd_Application::SaveAs (const Handle(TDocStd_Document)& D,
TCollection_ExtendedString file = tool.Name(); TCollection_ExtendedString file = tool.Name();
file+="."; file+=".";
file+=tool.Extension(); file+=tool.Extension();
D->Open(this); theDoc->Open(this);
CDF_Store storer (D); CDF_Store storer (theDoc);
if (!storer.SetFolder(directory)) if (!storer.SetFolder(directory))
{ {
TCollection_ExtendedString aMsg ("TDocStd_Application::SaveAs() - folder "); TCollection_ExtendedString aMsg ("TDocStd_Application::SaveAs() - folder ");
@ -378,7 +384,7 @@ PCDM_StoreStatus TDocStd_Application::SaveAs (const Handle(TDocStd_Document)& D,
} }
} }
if(storer.StoreStatus() == PCDM_SS_OK) if(storer.StoreStatus() == PCDM_SS_OK)
D->SetSaved(); theDoc->SetSaved();
#ifdef OCCT_DEBUG #ifdef OCCT_DEBUG
std::cout<<"TDocStd_Application::SaveAs(): The status = "<<storer.StoreStatus()<<std::endl; std::cout<<"TDocStd_Application::SaveAs(): The status = "<<storer.StoreStatus()<<std::endl;
#endif #endif

View File

@ -227,19 +227,25 @@ public:
//! In order not to override a version of aDoc which //! In order not to override a version of aDoc which
//! is already in memory, this method can be made //! is already in memory, this method can be made
//! to depend on the value returned by IsInSession. //! to depend on the value returned by IsInSession.
//! It is possible to filter out some attributes or
//! parts of the retrieved tree by theFilter.
Standard_EXPORT PCDM_ReaderStatus Open (const TCollection_ExtendedString& path, Standard_EXPORT PCDM_ReaderStatus Open (const TCollection_ExtendedString& path,
Handle(TDocStd_Document)& aDoc, Handle(TDocStd_Document)& theDoc,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Retrieves aDoc from standard SEEKABLE stream theIStream. //! Retrieves aDoc from standard SEEKABLE stream theIStream.
//! the stream should support SEEK functionality //! the stream should support SEEK functionality
//! It is possible to filter out some attributes or
//! parts of the retrieved tree by theFilter.
Standard_EXPORT PCDM_ReaderStatus Open (Standard_IStream& theIStream, Handle(TDocStd_Document)& theDoc, Standard_EXPORT PCDM_ReaderStatus Open (Standard_IStream& theIStream, Handle(TDocStd_Document)& theDoc,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Save the active document in the file <name> in the //! Save the active document in the file <name> in the
//! path <path> ; o verwrites the file if it already exists. //! path <path> ; o verwrites the file if it already exists.
Standard_EXPORT PCDM_StoreStatus SaveAs (const Handle(TDocStd_Document)& aDoc, Standard_EXPORT PCDM_StoreStatus SaveAs (const Handle(TDocStd_Document)& theDoc,
const TCollection_ExtendedString& path, const TCollection_ExtendedString& path,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
@ -253,13 +259,13 @@ public:
//! Exceptions: //! Exceptions:
//! Standard_NotImplemented if the document //! Standard_NotImplemented if the document
//! was not retrieved in the applicative session by using Open. //! was not retrieved in the applicative session by using Open.
Standard_EXPORT PCDM_StoreStatus Save (const Handle(TDocStd_Document)& aDoc, Standard_EXPORT PCDM_StoreStatus Save (const Handle(TDocStd_Document)& theDoc,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Save the active document in the file <name> in the //! Save the active document in the file <name> in the
//! path <path> . overwrite the file if it //! path <path> . overwrite the file if it
//! already exist. //! already exist.
Standard_EXPORT PCDM_StoreStatus SaveAs (const Handle(TDocStd_Document)& aDoc, Standard_EXPORT PCDM_StoreStatus SaveAs (const Handle(TDocStd_Document)& theDoc,
const TCollection_ExtendedString& path, const TCollection_ExtendedString& path,
TCollection_ExtendedString& theStatusMessage, TCollection_ExtendedString& theStatusMessage,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
@ -272,7 +278,7 @@ public:
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());
//! Save the document overwriting the previous file //! Save the document overwriting the previous file
Standard_EXPORT PCDM_StoreStatus Save (const Handle(TDocStd_Document)& aDoc, Standard_EXPORT PCDM_StoreStatus Save (const Handle(TDocStd_Document)& theDoc,
TCollection_ExtendedString& theStatusMessage, TCollection_ExtendedString& theStatusMessage,
const Message_ProgressRange& theRange = Message_ProgressRange()); const Message_ProgressRange& theRange = Message_ProgressRange());

View File

@ -549,7 +549,7 @@ void TDocStd_Document::ClearRedos()
//======================================================================= //=======================================================================
//function : Undo //function : Undo
//purpose : //purpose :
// Some importante notice: // Some important notice:
// 1) The most recent undo delta is at the end of the list. // 1) The most recent undo delta is at the end of the list.
// 2) Removing the LAST item of a list is tedious, but it is done only on // 2) Removing the LAST item of a list is tedious, but it is done only on
// Undo. Remove first is done at each command if the limit is reached! // Undo. Remove first is done at each command if the limit is reached!
@ -623,7 +623,6 @@ Standard_Boolean TDocStd_Document::Redo()
{ {
Standard_Boolean isOpened = myUndoTransaction.IsOpen(); Standard_Boolean isOpened = myUndoTransaction.IsOpen();
Standard_Boolean undoDone = Standard_False; Standard_Boolean undoDone = Standard_False;
// TDF_Label currentObjectLabel = CurrentLabel();//Sauve pour usage ulterieur.
if (!myRedos.IsEmpty()) { if (!myRedos.IsEmpty()) {
// should test the applicability before. // should test the applicability before.
// Reset the transaction // Reset the transaction

View File

@ -67,13 +67,16 @@ enum TDocStd_FormatVersion
//!< * BIN, XML: TopTools_FormatVersion_CURRENT changed to 3 and //!< * BIN, XML: TopTools_FormatVersion_CURRENT changed to 3 and
//!< BinTools_FormatVersion_CURRENT changed to 4 to preserve per-vertex normal //!< BinTools_FormatVersion_CURRENT changed to 4 to preserve per-vertex normal
//!< information in case of triangulation-only Faces [#0031136] //!< information in case of triangulation-only Faces [#0031136]
TDocStd_FormatVersion_CURRENT = TDocStd_FormatVersion_VERSION_11 //!< Current version TDocStd_FormatVersion_VERSION_12, //!< OCCT 7.6.0
//!< * BIN: New binary format for fast reading of part of OCAF document [#0031918]
TDocStd_FormatVersion_CURRENT = TDocStd_FormatVersion_VERSION_12 //!< Current version
}; };
enum enum
{ {
TDocStd_FormatVersion_LOWER = TDocStd_FormatVersion_VERSION_2, TDocStd_FormatVersion_LOWER = TDocStd_FormatVersion_VERSION_2,
TDocStd_FormatVersion_UPPER = TDocStd_FormatVersion_VERSION_11 TDocStd_FormatVersion_UPPER = TDocStd_FormatVersion_VERSION_12
}; };

View File

@ -55,6 +55,7 @@
#include <TDocStd_Application.hxx> #include <TDocStd_Application.hxx>
#include <TDocStd_Document.hxx> #include <TDocStd_Document.hxx>
#include <TDocStd_Owner.hxx> #include <TDocStd_Owner.hxx>
#include <PCDM_ReaderFilter.hxx>
#include <TNaming_NamedShape.hxx> #include <TNaming_NamedShape.hxx>
#include <TopoDS_Shape.hxx> #include <TopoDS_Shape.hxx>
#include <TPrsStd_AISPresentation.hxx> #include <TPrsStd_AISPresentation.hxx>
@ -206,31 +207,65 @@ static Standard_Integer openDoc (Draw_Interpretor& di, Standard_Integer argc, co
Handle(DDocStd_DrawDocument) DD; Handle(DDocStd_DrawDocument) DD;
Handle(TDocStd_Application) A = DDocStd::GetApplication(); Handle(TDocStd_Application) A = DDocStd::GetApplication();
if ( argc != 3 ) if ( argc < 3 )
{ {
di << "invalid number of arguments. Usage:\t XOpen filename docname\n"; di << "invalid number of arguments. Usage:\t XOpen filename docname [-skipAttribute] [-readAttribute] [-readPath] [-append|-overwrite]\n";
return 1; return 1;
} }
TCollection_AsciiString Filename = argv[1]; TCollection_AsciiString Filename = argv[1];
Standard_CString DocName = argv[2]; Standard_CString DocName = argv[2];
if ( DDocStd::GetDocument(DocName, D, Standard_False) ) Handle(PCDM_ReaderFilter) aFilter = new PCDM_ReaderFilter;
for (Standard_Integer i = 3; i < argc; i++)
{ {
di << "document with name " << DocName << " already exists\n"; TCollection_AsciiString anArg(argv[i]);
if (anArg == "-append")
{
aFilter->Mode() = PCDM_ReaderFilter::AppendMode_Protect;
}
else if (anArg == "-overwrite")
{
aFilter->Mode() = PCDM_ReaderFilter::AppendMode_Overwrite;
}
else if (anArg.StartsWith("-skip"))
{
TCollection_AsciiString anAttrType = anArg.SubString(6, anArg.Length());
aFilter->AddSkipped(anAttrType);
}
else if (anArg.StartsWith("-read"))
{
TCollection_AsciiString aValue = anArg.SubString(6, anArg.Length());
if (aValue.Value(1) == '0') // path
{
aFilter->AddPath(aValue);
}
else // attribute to read
{
aFilter->AddRead(aValue);
}
}
}
if (aFilter->IsAppendMode() && !DDocStd::GetDocument (DocName, D, Standard_False))
{
di << "for append mode document " << DocName << " must be already created\n";
return 1; return 1;
} }
Handle(Draw_ProgressIndicator) aProgress = new Draw_ProgressIndicator (di); Handle(Draw_ProgressIndicator) aProgress = new Draw_ProgressIndicator (di);
if ( A->Open(Filename, D, aProgress->Start()) != PCDM_RS_OK ) if ( A->Open (Filename, D, aFilter, aProgress->Start()) != PCDM_RS_OK )
{ {
di << "cannot open XDE document\n"; di << "cannot open XDE document\n";
return 1; return 1;
} }
DD = new DDocStd_DrawDocument(D); if (!aFilter->IsAppendMode())
TDataStd_Name::Set(D->GetData()->Root(), DocName); {
Draw::Set(DocName, DD); DD = new DDocStd_DrawDocument (D);
TDataStd_Name::Set (D->GetData()->Root(), DocName);
Draw::Set (DocName, DD);
}
di << "document " << DocName << " opened\n"; di << "document " << DocName << " opened\n";
@ -1245,7 +1280,12 @@ void XDEDRAW::Init(Draw_Interpretor& di)
di.Add ("XSave","[Doc Path] \t: Save Doc or first document in session", di.Add ("XSave","[Doc Path] \t: Save Doc or first document in session",
__FILE__, saveDoc, g); __FILE__, saveDoc, g);
di.Add ("XOpen","Path Doc \t: Open XDE Document with name Doc from Path", di.Add ("XOpen","Path Doc [-skipAttribute] [-readAttribute] [-readPath] [-append|-overwrite]\t: Open XDE Document with name Doc from Path"
"\n\t\t The options are:"
"\n\t\t -skipAttribute : class name of the attribute to skip during open, for example -skipTDF_Reference"
"\n\t\t -readAttribute : class name of the attribute to read only during open, for example -readTDataStd_Name loads only such attributes"
"\n\t\t -append : to read file into already existing document once again, append new attributes and don't touch existing"
"\n\t\t -overwrite : to read file into already existing document once again, overwriting existing attributes",
__FILE__, openDoc, g); __FILE__, openDoc, g);
di.Add ("Xdump","Doc [int deep (0/1)] \t: Print information about tree's structure", di.Add ("Xdump","Doc [int deep (0/1)] \t: Print information about tree's structure",

View File

@ -169,6 +169,7 @@ void XmlLDrivers_DocumentRetrievalDriver::Read
(const TCollection_ExtendedString& theFileName, (const TCollection_ExtendedString& theFileName,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
myReaderStatus = PCDM_RS_DriverFailure; myReaderStatus = PCDM_RS_DriverFailure;
@ -179,7 +180,7 @@ void XmlLDrivers_DocumentRetrievalDriver::Read
if (aFileStream.is_open() && aFileStream.good()) if (aFileStream.is_open() && aFileStream.good())
{ {
Read (aFileStream, NULL, theNewDocument, theApplication, theRange); Read (aFileStream, NULL, theNewDocument, theApplication, theFilter, theRange);
} }
else else
{ {
@ -201,6 +202,7 @@ void XmlLDrivers_DocumentRetrievalDriver::Read (Standard_IStream& t
const Handle(Storage_Data)& /*theStorageData*/, const Handle(Storage_Data)& /*theStorageData*/,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& /*theFilter*/,
const Message_ProgressRange& theRange) const Message_ProgressRange& theRange)
{ {
Handle(Message_Messenger) aMessageDriver = theApplication -> MessageDriver(); Handle(Message_Messenger) aMessageDriver = theApplication -> MessageDriver();

View File

@ -50,12 +50,14 @@ public:
Standard_EXPORT virtual void Read (const TCollection_ExtendedString& theFileName, Standard_EXPORT virtual void Read (const TCollection_ExtendedString& theFileName,
const Handle(CDM_Document)& theNewDocument, const Handle(CDM_Document)& theNewDocument,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theRange = Message_ProgressRange()) Standard_OVERRIDE;
Standard_EXPORT virtual void Read (Standard_IStream& theIStream, Standard_EXPORT virtual void Read (Standard_IStream& theIStream,
const Handle(Storage_Data)& theStorageData, const Handle(Storage_Data)& theStorageData,
const Handle(CDM_Document)& theDoc, const Handle(CDM_Document)& theDoc,
const Handle(CDM_Application)& theApplication, const Handle(CDM_Application)& theApplication,
const Handle(PCDM_ReaderFilter)& theFilter = Handle(PCDM_ReaderFilter)(),
const Message_ProgressRange& theRange= Message_ProgressRange()) Standard_OVERRIDE; const Message_ProgressRange& theRange= Message_ProgressRange()) Standard_OVERRIDE;
Standard_EXPORT virtual Handle(XmlMDF_ADriverTable) AttributeDrivers (const Handle(Message_Messenger)& theMsgDriver); Standard_EXPORT virtual Handle(XmlMDF_ADriverTable) AttributeDrivers (const Handle(Message_Messenger)& theMsgDriver);

141
tests/bugs/caf/bug31839_1 Normal file
View File

@ -0,0 +1,141 @@
puts "==========="
puts "0031839: Application Framework - Add ability to partially load OCAF document"
puts "==========="
# This test checks partial opening of the document with integer and real attributes
# and then partial appending (reading into the same document).
NewDocument D0 BinOcaf
UndoLimit D0 10
# number of labels of objects in the document
set labs 100
# number of sub-labels of each object
set sublabs 10
NewCommand D0
# store at each object-label sub-labels with two attributes at each
set creation_time [lindex [time {
for {set i 1} {$i <= $labs} {incr i} {
set lab [Label D0 0:1:${i}]
SetName D0 ${lab} Object$i
for {set ii 1} {$ii <= $sublabs} {incr ii} {
set sublab [Label D0 ${lab}:$ii]
SetInteger D0 ${sublab} 10
SetReal D0 ${sublab} 12.3
}
}
}] 0]
set commit_time [lindex [time {
CommitCommand D0
}] 0]
puts "Tree creation time $creation_time mcs"
puts "Creation commit time $commit_time mcs"
set docname ${imagedir}/doc_${casename}.cbf
SaveAs D0 ${docname}
Close D0
set open_time [lindex [time {
Open ${docname} D1
}] 0]
puts "Full document open time $open_time mcs"
set attributes [Attributes D1 0:1:1:1]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] < 0} {
puts "Error: full document is opened incorrectly"
}
Close D1
set open_noint_time [lindex [time {
Open ${docname} D2 -skipTDataStd_Integer
}] 0]
puts "Document without integers open time $open_noint_time mcs"
set attributes [Attributes D2 0:1:1:1]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] >= 0} {
puts "Error: document open without integers contains wrong attributes"
}
set open_oneint_time [lindex [time {
Open ${docname} D2 -append -read0:1:1:1
}] 0]
puts "Read of one integer time $open_oneint_time mcs"
set attributes [Attributes D2 0:1:1:1]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] < 0} {
puts "Error: document open with one integer contains wrong attributes"
}
set attributes [Attributes D2 0:1:1:10]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] >= 0} {
puts "Error: document open with one integer contains wrong attributes at label 10"
}
set open_nineint_time [lindex [time {
Open ${docname} D2 -append -read0:1:1
}] 0]
puts "Read of nine integer time $open_nineint_time mcs"
set attributes [Attributes D2 0:1:1:10]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] < 0} {
puts "Error: document open with nine integer contains wrong attributes at label 10"
}
set attributes [Attributes D2 0:1:1:5]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] < 0} {
puts "Error: document open with nine integer contains wrong attributes at label 5"
}
set attributes [Attributes D2 0:1:2:5]
if {[lsearch $attributes TDataStd_Real] < 0 || [lsearch $attributes TDataStd_Integer] >= 0} {
puts "Error: document open with nine integer contains wrong attributes at the second object"
}
SetInteger D2 0:1:1:5 21
SetReal D2 0:1:1:7 32.1
set open_overwrite_time [lindex [time {
Open ${docname} D2 -overwrite -read0:1:1
}] 0]
puts "Overwrite of ten integers time $open_overwrite_time mcs"
set value [GetInteger D2 0:1:1:5]
if {$value != 10} {
puts "Error: integer is overwritten incorrectly"
}
set value [GetReal D2 0:1:1:7]
if {$value != 12.3} {
puts "Error: real is overwritten incorrectly"
}
SetInteger D2 0:1:1:5 21
SetReal D2 0:1:1:7 32.1
set open_append_time [lindex [time {
Open ${docname} D2 -append -read0:1:1
}] 0]
puts "Append of ten integers time $open_overwrite_time mcs"
set value [GetInteger D2 0:1:1:5]
if {$value != 21} {
puts "Error: integer is overwritten by append"
}
set value [GetReal D2 0:1:1:7]
if {$value != 32.1} {
puts "Error: real is overwritten by append"
}
Close D2

55
tests/bugs/caf/bug31839_2 Normal file
View File

@ -0,0 +1,55 @@
puts "==========="
puts "0031839: Application Framework - Add ability to partially load OCAF document"
puts "==========="
# This test checks partial opening of the document shapes, append and overwrite modes
# for them checking that after overwrite the shapes keep shared topology.
NewDocument D0 BinOcaf
UndoLimit D0 10
NewCommand D0
box b 1 2 3
explode b F
SetShape D0 0:1 b
for {set i 1} {$i <= 6} {incr i} {
set lab [Label D0 0:1:${i}]
SetShape D0 ${lab} b_${i}
}
CommitCommand D0
set docname ${imagedir}/doc_${casename}.cbf
SaveAs D0 ${docname}
Close D0
# open document with shapes skipped
Open ${docname} D1 -skipTNaming_NamedShape
if {![catch {GetShape D1 0:1 b1}]} {
puts "Error: found box at the label 0:1, but it should not be there"
}
if {![catch {GetShape D1 0:1:1 f0}]} {
puts "Error: found face at the label 0:1:1, but it should not be there"
}
# append one face
Open ${docname} D1 -append -read0:1:1
if {[catch {GetShape D1 0:1:1 f1}]} {
puts "Error: Can not find face at the label 0:1:1"
}
if {![catch {GetShape D1 0:1:2 f2}]} {
puts "Error: found face at the label 0:1:2, but it should not be there"
}
# append others, rewrite the first face
Open ${docname} D1 -overwrite
GetShape D1 0:1 box
GetShape D1 0:1:1 f11
set same [CheckSame box f11 F]
if {$same == ""} {
puts "Error: shapes loaded in append mode do not share subshapes (so, face at 0:1:1 was not replaced)"
}

89
tests/bugs/caf/bug31918_1 Normal file
View File

@ -0,0 +1,89 @@
puts "==========="
puts "0031918: Application Framework - New binary format for fast reading part of OCAF document"
puts "==========="
set docname ${imagedir}/doc_${casename}.cbfl
NewDocument D0 BinLOcaf
UndoLimit D0 10
NewCommand D0
# set an array 1000 values from 100 to 1099
set values "100 "
for {set i 101} {$i < 1100} {incr i} {set values "$values $i"}
# set 100 arrays to sub-labels of 0:1 0:2 0:3 and 0:4
for {set lab 1} {$lab <= 4} {incr lab} {
for {set sublab 1} {$sublab <= 100} {incr sublab} {
set command "SetIntArray D0 0:$lab:$sublab 0 1 1000 $values"
eval $command
SetReal D0 0:$lab:$sublab 0.1
}
}
CommitCommand D0
SaveAs D0 ${docname}
Close D0
set whole_time [lindex [time {
Open ${docname} D1
Close D1
} 20] 0]
puts "Whole document open time $whole_time mcs"
set quater_time [lindex [time {
Open ${docname} D2 -read0:2
Close D2
} 20] 0]
puts "Quater of document open time $quater_time mcs"
# Check that open of quater of the document is at least twice faster than open of whole.
if { [expr $quater_time * 2] > $whole_time } {
puts "Error : loading of quater of the document content too slow relatively to the whole document load"
}
set four_quaters_time [lindex [time {
Open ${docname} D3 -read0:1 -read0:2 -read0:3 -read0:4
Close D3
} 20] 0]
puts "Four quaters of document open time $four_quaters_time mcs"
# Check that open of four quaters of the document is not too much slower than opening of the whole document.
if { [expr $four_quaters_time * 0.9] > $whole_time } {
puts "Error : loading of four quaters of the document content too slow relatively to the whole document load"
}
set no_arrays_time [lindex [time {
Open ${docname} D4 -skipTDataStd_IntegerArray -read0:2
}] 0]
puts "Quater of document without arrays open time $no_arrays_time mcs"
set attrs [Attributes D4 0:2:13]
if {"${attrs}" != "TDataStd_Real "} {
puts "Error : loading of document skipping arrays contains invalid attributes list '${attrs}'"
}
if {![catch {Attributes D4 0:1:1:13}] || ![catch {Attributes D4 0:1:3:14}] || ![catch {Attributes D4 0:1:4:1}]} {
puts "Error : loading of document skipping arrays and sub-trees contains invalid attributes list"
}
set append_arrays_time [lindex [time {
Open ${docname} D4 -append -readTDataStd_IntegerArray -read0:2 -read0:3
}] 0]
puts "Half of document arrays open time $append_arrays_time mcs"
set attrs [Attributes D4 0:2:13]
if {"${attrs}" != "TDataStd_Real TDataStd_IntegerArray "} {
puts "Error : loading of document reading arrays separately contains invalid attributes list '${attrs}'"
}
set attrs [Attributes D4 0:3:1]
if {"${attrs}" != "TDataStd_IntegerArray "} {
puts "Error : loading of document reading arrays separately contains invalid attributes list on subtree 3 '${attrs}'"
}
if {![catch {Attributes D4 0:1:1:13}] || ![catch {Attributes D4 0:1:4:1}]} {
puts "Error : loading of document reading arrays separately contains invalid attributes list on 1 and 4 subtrees"
}
Close D4

123
tests/bugs/caf/bug31918_2 Normal file
View File

@ -0,0 +1,123 @@
puts "==========="
puts "0031918: Application Framework - New binary format for fast reading part of OCAF document"
puts "==========="
pload XDE
NewDocument D0 BinOcaf
# creates part-shape by the given sizes
proc store_part {nx ny dx dy dz entry} {
global D0
box b1 0 0 0 [expr $nx + .5] [expr $ny + .5] 1
box b2 0.5 0.5 0 [expr $nx - .5] [expr $nx - .5] 0.4
cut base b1 b2
set command "compound"
for {set x 0} {$x < $nx} {incr x} {
for {set y 0} {$y < $ny} {incr y} {
pcylinder c${x}_$y 0.25 1.01
ttranslate c${x}_$y [expr $x+.75] [expr $y+.75] 0.39
set command "$command c${x}_$y"
}
}
eval "$command cc"
bop base cc
bopfuse part
ttranslate part $dx $dy $dz
Label D0 $entry
SetShape D0 $entry part
}
store_part 16 16 0 0 0 0:1:1
for {set n 1} {$n < 5} {incr n} {
store_part 4 4 $n $n $n 0:2:$n
store_part 4 4 [expr 16-4-$n] $n $n 0:2:[expr $n+4]
store_part 4 4 $n [expr 16-4-$n] $n 0:2:[expr $n+8]
store_part 4 4 [expr 16-4-$n] [expr 16-4-$n] $n 0:2:[expr $n+12]
}
store_part 6 6 5 5 5 0:3:1
store_part 4 4 6 6 6 0:3:2
GetShape D0 0:3:2 top2
set docname ${imagedir}/doc_${casename}.cbf
set save_time [lindex [time {
SaveAs D0 ${docname}
}] 0]
puts "Save time $save_time mcs"
Close D0
set whole_time [lindex [time {
Open ${docname} D1
Close D1
} 20] 0]
puts "Whole document open time $whole_time mcs"
set half_time1 [lindex [time {
Open ${docname} D2 -read0:1 -read0:3
Close D2
} 20] 0]
puts "First half of document open time $half_time1 mcs"
set half_time2 [lindex [time {
Open ${docname} D3 -read0:2
Close D3
} 20] 0]
puts "Second half of document open time $half_time2 mcs"
# Check that open of two halfs of the document separately is not too much slower than open of the whole
if { [expr ($half_time1 + $half_time2) * 0.9] > $whole_time } {
puts "Error : loading of half of the document content is too slow relatively to the whole document load"
}
Open ${docname} D4 -read0:3:2
GetShape D4 0:3:2 opened_top2
checkshape opened_top2
# check shapes are the same before open and after
if {[string first [whatis top2] [whatis opened_top2]] != 7} {
puts "Error : saved and opened shapes are different"
}
Open ${docname} D4 -append -read0:1 -read0:2
GetShape D4 0:1:1 s
checkshape s
for {set n 1} {$n < 16} {incr n} {
GetShape D4 0:2:$n s
checkshape s
}
Close D4
set no_shapes_time [lindex [time {
Open ${docname} D5 -skipTNaming_NamedShape
Close D5
} 20] 0]
puts "Document without shapes open time $no_shapes_time mcs"
# Check that open of the document without shapes is much faster than open of the whole
if { [expr $no_shapes_time * 20] > $whole_time } {
puts "Error : loading of the document without shapes is too slow relatively to the whole document load"
}
# check shapes storage with triangulations
set length_wo_tirangulation [string length [dump s]]
vinit
vdisplay top2 -displaymode 1
NewDocument D6 BinOcaf
UndoLimit D6 10
SetShape D6 0:1 top2
StoreTriangulation 1
SaveAs D6 ${docname}
Close D6
Open ${docname} D7
GetShape D7 0:1 top3
Close D7
checkshape top3
set length_with_tirangulation [string length [dump top3]]
if { [expr $length_with_tirangulation / 7] < $length_wo_tirangulation } {
puts "Error : looks like shape stored with triangulation loaded without trianulation"
}

View File

@ -25,9 +25,7 @@ set output [SaveAs Doc ${imagedir}/testA1.cbf]
Close Doc Close Doc
# Test data # Test data
set ctr { "0%" "Writing document" "Writing sub tree" set ctr { "0%" "Writing document" "Writing sub tree" "100%" }
"Writing geometry" "Writing 2D curves" "Writing curves"
"Writing surfases" "Writing shapes" "100%" }
foreach data ${ctr} { foreach data ${ctr} {
if ![regexp $data $output] { if ![regexp $data $output] {

View File

@ -25,8 +25,7 @@ set output [Open ${bDoc} Doc]
Close Doc Close Doc
# Test data # Test data
set ctr {"0%" "Reading data" "Reading geomentry" "Reading curves 2d" set ctr {"0%" "Reading data" "Reading sub tree" "100%" }
"Reading surfaces" "Reading Shapes" "Reading sub tree" "100%" }
foreach data ${ctr} { foreach data ${ctr} {
if ![regexp $data $output] { if ![regexp $data $output] {

View File

@ -31,9 +31,7 @@ set output [Save Doc]
Close Doc Close Doc
# Test data # Test data
set ctr { "0%" "Writing document" "Writing sub tree" set ctr { "0%" "Writing document" "Writing sub tree" "100%" }
"Writing geometry" "Writing 2D curves" "Writing curves"
"Writing surfases" "Writing shapes" "100%" }
foreach data ${ctr} { foreach data ${ctr} {
if ![regexp $data $output] { if ![regexp $data $output] {