]> OCCT Git - occt.git/commitdiff
0026657: Data Exchange - IGES/STEP OCAF writers should keep hierarchy and colors...
authorgka <gka@opencascade.com>
Thu, 10 Sep 2015 07:54:21 +0000 (10:54 +0300)
committerbugmaster <bugmaster@opencascade.com>
Thu, 17 Sep 2015 14:01:02 +0000 (17:01 +0300)
Make modification to save in the file part of the XCAF document starting from specified label.
If specified label is component of the high-level assembly then high-level assembly is saved in document with one specified component.
In other case only part of the document starting from the specified label is saved.

src/STEPCAFControl/STEPCAFControl_Writer.cxx
src/STEPCAFControl/STEPCAFControl_Writer.hxx
src/XDEDRAW/XDEDRAW_Common.cxx
tests/bugs/step/bug26657 [new file with mode: 0644]

index 96843c3d0a9ad8f662d87c7ed303ac79aad11134..538998cc6fe80d830db8177e4b5c02a5a5b1125e 100644 (file)
@@ -445,28 +445,57 @@ Standard_Boolean STEPCAFControl_Writer::Transfer (STEPControl_Writer &writer,
     if ( shape.IsNull() ) continue;
     
     // write shape either as a whole, or as multifile (with extern refs)
-    if ( ! multi /* || ! XCAFDoc_ShapeTool::IsAssembly ( L ) */ ) {
+    if ( ! multi  ) {
       Actor->SetStdMode ( Standard_False );
 
-      // fill sequence of (sub) shapes for which attributes should be written
-      // and set actor to handle assemblies in a proper way
       TDF_LabelSequence comp;
-      XCAFDoc_ShapeTool::GetComponents ( L, comp, Standard_True );
+
+      //for case when only part of assemby structure should be written in the document
+      //if specified label is component of the assembly then
+      //in order to save location of this component in the high-level assembly
+      //and save name of high-level assembly it is necessary to represent structure of high-level assembly 
+      //as assembly with one component specified by current label. 
+      //For that compound containing only specified component is binded to the label of the high-level assembly.
+      //The such way full structure of high-level assembly was replaced on the assembly contaning one component.
+      if ( XCAFDoc_ShapeTool::IsComponent ( L ) )
+      {
+        TopoDS_Compound aComp;
+        BRep_Builder aB;
+        aB.MakeCompound(aComp);
+        aB.Add(aComp, shape);
+        shape = aComp; 
+        comp.Append(L);
+        TDF_Label ref;
+        if ( XCAFDoc_ShapeTool::GetReferredShape ( L, ref ) )
+        {
+          if(XCAFDoc_ShapeTool::IsAssembly ( ref))
+            XCAFDoc_ShapeTool::GetComponents ( ref, comp, Standard_True );
+        }
+        L = L.Father();
+      }
+      else
+      {
+        // fill sequence of (sub) shapes for which attributes should be written
+        // and set actor to handle assemblies in a proper way
+        if(XCAFDoc_ShapeTool::IsAssembly ( L ))
+          XCAFDoc_ShapeTool::GetComponents ( L, comp, Standard_True );
+      }
+      
       for ( Standard_Integer k=1; k <= comp.Length(); k++ ) {
-       TDF_Label ref;
-       if ( ! XCAFDoc_ShapeTool::GetReferredShape ( comp(k), ref ) ) continue;
-       if ( ! myLabels.IsBound ( ref ) ) {
-         TopoDS_Shape refS = XCAFDoc_ShapeTool::GetShape ( ref );
-         myLabels.Bind ( ref, refS );
-         sublabels.Append ( ref );
-         if ( XCAFDoc_ShapeTool::IsAssembly ( ref ) )
-           Actor->RegisterAssembly ( refS );
-       }
+        TDF_Label ref;
+        if ( ! XCAFDoc_ShapeTool::GetReferredShape ( comp(k), ref ) ) continue;
+        if ( ! myLabels.IsBound ( ref ) ) {
+          TopoDS_Shape refS = XCAFDoc_ShapeTool::GetShape ( ref );
+          myLabels.Bind ( ref, refS );
+          sublabels.Append ( ref );
+          if ( XCAFDoc_ShapeTool::IsAssembly ( ref ) )
+            Actor->RegisterAssembly ( refS );
+        }
       }
       myLabels.Bind ( L, shape );
       sublabels.Append ( L );
       if ( XCAFDoc_ShapeTool::IsAssembly ( L ) )
-       Actor->RegisterAssembly ( shape );
+        Actor->RegisterAssembly ( shape );
 
       writer.Transfer(shape,mode,Standard_False);
       Actor->SetStdMode ( Standard_True ); // restore default behaviour
@@ -615,11 +644,10 @@ TopoDS_Shape STEPCAFControl_Writer::TransferExternFiles (const TDF_Label &L,
   TopoDS_Compound C;
   BRep_Builder B;
   B.MakeCompound ( C );
-  labels.Append ( L );
-
+  //labels.Append ( L ); 
   // if not assembly, write to separate file
-  if ( ! XCAFDoc_ShapeTool::IsAssembly ( L ) ) {
-
+  if ( ! XCAFDoc_ShapeTool::IsAssembly ( L ) && !XCAFDoc_ShapeTool::IsComponent ( L )) {
+    labels.Append ( L );
     // prepare for transfer
     Handle(XSControl_WorkSession) newWS = new XSControl_WorkSession;
     newWS->SelectNorm ( "STEP" );
@@ -660,11 +688,21 @@ TopoDS_Shape STEPCAFControl_Writer::TransferExternFiles (const TDF_Label &L,
     myLabels.Bind ( L, C );
     return C;
   }
-
+  TDF_LabelSequence comp;
+  TDF_Label aCurL = L;
+  //if specified shape is component then high-level assembly is considered
+  //to get valid structure with location
+  if ( XCAFDoc_ShapeTool::IsComponent ( L ) )
+  {
+    comp.Append(L);
+    aCurL = L.Father();
+  }
   // else iterate on components add create structure of empty compounds
   // representing the assembly
-  TDF_LabelSequence comp;
-  XCAFDoc_ShapeTool::GetComponents ( L, comp, Standard_False );
+  else if (XCAFDoc_ShapeTool::IsAssembly ( L ))
+    XCAFDoc_ShapeTool::GetComponents ( L, comp, Standard_False );
+
+  labels.Append ( aCurL );
   for ( Standard_Integer k=1; k <= comp.Length(); k++ ) {
     TDF_Label lab = comp(k);
     TDF_Label ref;
@@ -673,7 +711,7 @@ TopoDS_Shape STEPCAFControl_Writer::TransferExternFiles (const TDF_Label &L,
     Scomp.Location ( XCAFDoc_ShapeTool::GetLocation ( lab ) );
     B.Add ( C, Scomp );
   }
-  myLabels.Bind ( L, C );
+  myLabels.Bind ( aCurL, C );
   return C;
 }
 
index 915c38bfef4dc8074101752ca47b00af93459373..250bf213b89e5f6dc93873ab711fe10f797ffe7e 100644 (file)
@@ -50,7 +50,7 @@ class STEPCAFControl_Writer
 public:
 
   DEFINE_STANDARD_ALLOC
-
+  
   
   //! Creates a writer with an empty
   //! STEP model and sets ColorMode, LayerMode, NameMode and
@@ -80,8 +80,9 @@ public:
   //! gives prefix for names of extern files (can be empty string)
   //! Returns True if translation is OK
   Standard_EXPORT Standard_Boolean Transfer (const Handle(TDocStd_Document)& doc, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0);
-  Standard_EXPORT Standard_Boolean Transfer (const TDF_LabelSequence& L, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0);
-  Standard_EXPORT Standard_Boolean Transfer (const TDF_Label& L, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0);
+  
+  //! Method to transfer part of the document specified by label
+  Standard_EXPORT Standard_Boolean Transfer (const TDF_Label& L, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0 );
 
   Standard_EXPORT Standard_Boolean Perform (const Handle(TDocStd_Document)& doc, const TCollection_AsciiString& filename);
   
@@ -146,12 +147,13 @@ public:
 
 
 protected:
-
+  //! Mehod to writing sequence of root assemblies or part of the file specified by use by one label 
+  Standard_EXPORT Standard_Boolean Transfer (const TDF_LabelSequence& L, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0);
   
   //! Transfers labels to a STEP model
   //! Returns True if translation is OK
   //! isExternFile setting from TransferExternFiles method
-  Standard_EXPORT Standard_Boolean Transfer (STEPControl_Writer& wr, const TDF_LabelSequence& labels, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0, const Standard_Boolean isExternFile = Standard_False);
+  Standard_EXPORT Standard_Boolean Transfer (STEPControl_Writer& wr, const TDF_LabelSequence& labels, const STEPControl_StepModelType mode = STEPControl_AsIs, const Standard_CString multi = 0, const Standard_Boolean isExternFile = Standard_False) ;
   
   //! Parses assembly structure of label L, writes all the simple
   //! shapes each to its own file named by name of its label plus
@@ -186,8 +188,7 @@ protected:
   //! Write SHUO assigned to specified component, to STEP model
   Standard_EXPORT Standard_Boolean WriteSHUOs (const Handle(XSControl_WorkSession)& WS, const TDF_LabelSequence& labels);
 
-
-
+  
 
 private:
 
@@ -212,7 +213,4 @@ private:
 
 
 
-
-
-
 #endif // _STEPCAFControl_Writer_HeaderFile
index 5bef93cbdd138b498ed256f8fdface262f05f97b..cff00719edc0f24330b0ad579170f2c89c9a2a51 100644 (file)
@@ -43,6 +43,7 @@
 #include <XSDRAW_Vars.hxx>
 #include <XSDRAWIGES.hxx>
 #include <XSDRAWSTEP.hxx>
+#include <DDF.hxx>
 
 #include <stdio.h>
 //============================================================
@@ -360,10 +361,13 @@ static Standard_Integer ReadStep (Draw_Interpretor& di, Standard_Integer argc, c
 static Standard_Integer WriteStep (Draw_Interpretor& di, Standard_Integer argc, const char** argv)
 {
   if ( argc <3 ) {
-    di << "Use: " << argv[0] << " Doc filename [mode=a [multifile_prefix]]: write document to the STEP file" << "\n";
-    di << "Parameter mode can be:       a or 0 : AsIs (default)" << "\n";
-    di << "f or 1 : FacettedBRep        s or 2 : ShellBasedSurfaceModel" << "\n";
-    di << "m or 3 : ManifoldSolidBrep   w or 4 : GeometricCurveSet/WireFrame" << "\n";
+    di << "Use: " << argv[0] << " Doc filename [mode [multifile_prefix [label]]]: write document to the STEP file" << "\n";
+    di << "mode can be: a or 0 : AsIs (default)" << "\n";
+    di << "             f or 1 : FacettedBRep        s or 2 : ShellBasedSurfaceModel\n";
+    di << "             m or 3 : ManifoldSolidBrep   w or 4 : GeometricCurveSet/WireFrame\n";
+    di << "multifile_prefix: triggers writing assembly components as separate files,\n";
+    di << "                  and defines common prefix for their names\n";
+    di << "label: tag of the sub-assembly label to save only that sub-assembly\n";
     return 0;
   }
   
@@ -373,16 +377,16 @@ static Standard_Integer WriteStep (Draw_Interpretor& di, Standard_Integer argc,
     di << argv[1] << " is not a document" << "\n";
     return 1;
   }
+  Standard_CString multifile = 0;
   
-  Standard_CString multifile = ( argc >4 ? argv[4] : 0 );
-  
+  Standard_Integer k = 3;
   DeclareAndCast(STEPControl_Controller,ctl,XSDRAW::Controller());
   if (ctl.IsNull()) XSDRAW::SetNorm("STEP");
   STEPCAFControl_Writer writer ( XSDRAW::Session(), Standard_True );
-
+   
   STEPControl_StepModelType mode = STEPControl_AsIs;
-  if ( argc >3 ) {
-    switch (argv[3][0]) {
+  if ( argc > k ) {
+    switch (argv[k][0]) {
     case 'a' :
     case '0' : mode = STEPControl_AsIs;                    break;
     case 'f' :
@@ -396,7 +400,7 @@ static Standard_Integer WriteStep (Draw_Interpretor& di, Standard_Integer argc,
     default :  di<<"3st arg = mode, incorrect [give fsmw]"<<"\n"; return 1;
     }
     Standard_Boolean wrmode = Standard_True;
-    for ( Standard_Integer i = 0; argv[3][i] ; i++ ) 
+    for ( Standard_Integer i = 0; argv[k][i] ; i++ ) 
       switch (argv[3][i]) {
       case '-' : wrmode = Standard_False; break;
       case '+' : wrmode = Standard_True; break;
@@ -405,13 +409,44 @@ static Standard_Integer WriteStep (Draw_Interpretor& di, Standard_Integer argc,
       case 'l' : writer.SetLayerMode (wrmode); break;
       case 'v' : writer.SetPropsMode (wrmode); break;
       }
+    k++;
+  }
+
+  TDF_Label label;
+  if( argc > k)
+  {
+    TCollection_AsciiString aStr(argv[k]);
+    if( aStr.Search(":") ==-1)
+      multifile = argv[k++];
     
   }
-  
-  di << "Translating document " << argv[1] << " to STEP" << "\n";
-  if ( ! writer.Transfer ( Doc, mode, multifile ) ) {
-    di << "The document cannot be translated or gives no result" << "\n";
+  if( argc > k)
+  {
+      
+    if( !DDF::FindLabel(Doc->Main().Data(), argv[k], label) || label.IsNull()) {  
+      di << "No label for entry"  << "\n";
+      return 1; 
+      
+    }
   }
+  if( !label.IsNull())
+  {  
+    di << "Translating label "<< argv[k]<<" of document " << argv[1] << " to STEP" << "\n";
+    if(!writer.Transfer ( label, mode, multifile )) 
+    {
+      di << "The label of document cannot be translated or gives no result" << "\n";
+      return 1;
+    }
+
+  }
+  else
+  {
+    di << "Translating document " << argv[1] << " to STEP" << "\n";
+    if ( ! writer.Transfer ( Doc, mode, multifile ) ) {
+      di << "The document cannot be translated or gives no result" << "\n";
+    }
+  }
+  
 
   di << "Writing STEP file " << argv[2] << "\n";
   IFSelect_ReturnStatus stat = writer.Write(argv[2]);
@@ -440,7 +475,7 @@ void XDEDRAW_Common::InitCommands(Draw_Interpretor& di) {
   di.Add("ReadIges" , "Doc filename: Read IGES file to DECAF document" ,__FILE__, ReadIges, g);
   di.Add("WriteIges" , "Doc filename: Write DECAF document to IGES file" ,__FILE__, WriteIges, g);
   di.Add("ReadStep" , "Doc filename: Read STEP file to DECAF document" ,__FILE__, ReadStep, g);
-  di.Add("WriteStep" , "Doc filename: Write DECAF document to STEP file" ,__FILE__, WriteStep, g);  
+  di.Add("WriteStep" , "Doc filename [mode=a [multifile_prefix] [label]]: Write DECAF document to STEP file" ,__FILE__, WriteStep, g);  
   
   di.Add("XFileList","Print list of files that was transfered by the last transfer" ,__FILE__, GetDicWSList , g);
   di.Add("XFileCur", ": returns name of file which is set as current",__FILE__, GetCurWS, g);
diff --git a/tests/bugs/step/bug26657 b/tests/bugs/step/bug26657
new file mode 100644 (file)
index 0000000..380a5f8
--- /dev/null
@@ -0,0 +1,28 @@
+pload DCAF
+pload TOPTEST
+pload XDE
+puts "========"
+puts "OCC26657"
+puts "========"
+puts ""
+##########################################################################
+# STEP OCAF writers should keep hierarchy and colors when saving non-root elements
+##########################################################################
+pload XDEDRAW
+ReadStep D1 [locate_data_file bug26657.stp]
+WriteStep D1 $imagedir/bug26657_temp.stp a 0:1:1:1:2
+if { [catch { Close D11 } catch_result] } {
+    puts "Document D11 is not exist"
+}
+
+ReadStep D11 $imagedir/bug26657_temp.stp
+XGetOneShape result D11
+checkshape result f
+
+Close D1
+checknbshapes result -solid 3
+XShow D11
+vfit
+vsetdispmode 1
+vdump $imagedir/${test_image}.png
+