0024023: Revamp the OCCT Handle -- general
[occt.git] / src / IGESCAFControl / IGESCAFControl_Writer.cxx
old mode 100755 (executable)
new mode 100644 (file)
index 02c4dde..73447d8
@@ -1,22 +1,17 @@
 // Created on: 2000-08-17
 // Created by: Andrey BETENEV
-// Copyright (c) 2000-2012 OPEN CASCADE SAS
+// Copyright (c) 2000-2014 OPEN CASCADE SAS
 //
-// The content of this file is subject to the Open CASCADE Technology Public
-// License Version 6.5 (the "License"). You may not use the content of this file
-// except in compliance with the License. Please obtain a copy of the License
-// at http://www.opencascade.org and read it completely before using this file.
+// This file is part of Open CASCADE Technology software library.
 //
-// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
-// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
+// 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.
 //
-// The Original Code and all software distributed under the License is
-// distributed on an "AS IS" basis, without warranty of any kind, and the
-// Initial Developer hereby disclaims all such warranties, including without
-// limitation, any warranties of merchantability, fitness for a particular
-// purpose or non-infringement. Please see the License for the specific terms
-// and conditions governing the rights and limitations under the License.
-
+// Alternatively, this file may be used under the terms of Open CASCADE
+// commercial license or contractual agreement.
 
 #include <IGESCAFControl_Writer.ixx>
 #include <XCAFDoc_ShapeTool.hxx>
 #include <TDF_ChildIterator.hxx>
 #include <TDataStd_Name.hxx>
 #include <IGESData_NameEntity.hxx>
+#include <IGESSolid_Face.hxx>
 #include <TopTools_SequenceOfShape.hxx>
 #include <TColStd_HSequenceOfExtendedString.hxx>
+#include <NCollection_DataMap.hxx>
+#include <IGESData_IGESEntity.hxx>
+#include <IGESData_IGESModel.hxx>
+
+namespace
+{
+  typedef NCollection_DataMap<TopoDS_Shape, TCollection_ExtendedString> DataMapOfShapeNames;
+
+  void  CollectShapeNames (const TDF_Label& theLabel,
+                           const TopLoc_Location& theLocation,
+                           const Handle(TDataStd_Name)& thePrevName,
+                           DataMapOfShapeNames& theMapOfShapeNames)
+  {
+    Standard_Boolean hasReferredShape = Standard_False;
+    Standard_Boolean hasComponents    = Standard_False;
+    TDF_Label aReferredLabel;
+
+    Handle(TDataStd_Name) aName;
+    theLabel.FindAttribute (TDataStd_Name::GetID(), aName);
+
+    if ( XCAFDoc_ShapeTool::GetReferredShape ( theLabel, aReferredLabel ) )
+    {
+      TopLoc_Location aSubLocation = theLocation.Multiplied ( XCAFDoc_ShapeTool::GetLocation ( theLabel ) );
+      CollectShapeNames (aReferredLabel, aSubLocation, aName, theMapOfShapeNames);
+      hasReferredShape = Standard_True;
+    }
+
+    TDF_LabelSequence aSeq;
+    if (XCAFDoc_ShapeTool::GetComponents (theLabel, aSeq))
+    {
+      for (Standard_Integer anIter = 1; anIter <= aSeq.Length(); anIter++)
+      {
+        CollectShapeNames (aSeq.Value (anIter), theLocation, aName, theMapOfShapeNames );
+      }
+      hasComponents = Standard_True;
+    }
+
+    aSeq.Clear();
+    if (XCAFDoc_ShapeTool::GetSubShapes (theLabel, aSeq))
+    {
+      for (Standard_Integer anIter = 1; anIter <= aSeq.Length(); anIter++)
+      {
+        TopoDS_Shape aShape;
+        if (!XCAFDoc_ShapeTool::GetShape (aSeq.Value (anIter), aShape)) continue;
+        if (!aSeq.Value (anIter).FindAttribute (TDataStd_Name::GetID(), aName)) continue;
+        theMapOfShapeNames.Bind (aShape, aName->Get());
+      }
+    }
+
+    if (!hasReferredShape && !hasComponents)
+    {
+      TopoDS_Shape aShape;
+      if (!XCAFDoc_ShapeTool::GetShape (theLabel, aShape)) return;
+      aShape.Move (theLocation);
+      theMapOfShapeNames.Bind (aShape, thePrevName->Get());
+    }
+  }
+}
 
 //=======================================================================
 //function : IGESCAFControl_Writer
@@ -88,35 +142,13 @@ Standard_Boolean IGESCAFControl_Writer::Transfer (const Handle(TDocStd_Document)
 {  
   // translate free top-level shapes of the DECAF document
   Handle(XCAFDoc_ShapeTool) STool = XCAFDoc_DocumentTool::ShapeTool( doc->Main() );
-  TDF_LabelSequence shapes;
-  STool->GetFreeShapes ( shapes );
-  if ( shapes.Length() <=0 ) return Standard_False;
-  for ( Standard_Integer i=1; i <= shapes.Length(); i++ ) {
-    TopoDS_Shape shape = STool->GetShape ( shapes.Value(i) );
-    if ( ! shape.IsNull() ) 
-      AddShape ( shape );
-//      IGESControl_Writer::Transfer ( shape );
-  }
-  
-  // write colors
-  if ( GetColorMode() )
-    WriteAttributes ( doc );
+  if ( STool.IsNull() ) return Standard_False;
 
-  // write layers
-  if ( GetLayerMode() )
-    WriteLayers ( doc );
-  
-  // write names
-  if ( GetNameMode() )
-    WriteNames( doc );
-  
-  // refresh graph
-//  WS()->ComputeGraph ( Standard_True );
-  ComputeModel();
+  TDF_LabelSequence labels;
+  STool->GetFreeShapes ( labels );
+  return Transfer (labels);
+}  
   
-  return Standard_True;
-}
-
 //=======================================================================
 //function : Perform
 //purpose  : 
@@ -141,18 +173,48 @@ Standard_Boolean IGESCAFControl_Writer::Perform (const Handle(TDocStd_Document)
   return Write ( filename.ToCString() ) == IFSelect_RetDone;
 }
   
+//=======================================================================
+//function : Transfer
+//purpose  : 
+//=======================================================================
+
+Standard_Boolean IGESCAFControl_Writer::Transfer (const TDF_LabelSequence& labels)
+{  
+  if ( labels.Length() <=0 ) return Standard_False;
+  for ( Standard_Integer i=1; i <= labels.Length(); i++ ) {
+    TopoDS_Shape shape = XCAFDoc_ShapeTool::GetShape ( labels.Value(i) );
+    if ( ! shape.IsNull() ) 
+      AddShape ( shape );
+//      IGESControl_Writer::Transfer ( shape );
+  }
+  
+  // write colors
+  if ( GetColorMode() )
+    WriteAttributes ( labels );
+
+  // write layers
+  if ( GetLayerMode() )
+    WriteLayers ( labels );
+  
+  // write names
+  if ( GetNameMode() )
+    WriteNames( labels );
+  
+  // refresh graph
+//  WS()->ComputeGraph ( Standard_True );
+  ComputeModel();
+  
+  return Standard_True;
+}
+
 //=======================================================================
 //function : WriteAttributes
 //purpose  : 
 //=======================================================================
 
-Standard_Boolean IGESCAFControl_Writer::WriteAttributes (const Handle(TDocStd_Document)& Doc
+Standard_Boolean IGESCAFControl_Writer::WriteAttributes (const TDF_LabelSequence& labels
 {
-  // Iterate on shapes in the document
-  Handle(XCAFDoc_ShapeTool) STool = XCAFDoc_DocumentTool::ShapeTool( Doc->Main() );
-
-  TDF_LabelSequence labels;
-  STool->GetFreeShapes ( labels );
+  // Iterate on labels
   if ( labels.Length() <=0 ) return Standard_False;
   for ( Standard_Integer i=1; i <= labels.Length(); i++ ) {
     TDF_Label L = labels.Value(i);
@@ -166,7 +228,7 @@ Standard_Boolean IGESCAFControl_Writer::WriteAttributes (const Handle(TDocStd_Do
     // get a target shape and try to find corresponding context
     // (all the colors set under that label will be put into that context)
     TopoDS_Shape S;
-    if ( ! STool->GetShape ( L, S ) ) continue;
+    if ( ! XCAFDoc_ShapeTool::GetShape ( L, S ) ) continue;
         
     // iterate on subshapes and create IGES styles 
     XCAFPrs_DataMapOfStyleTransient colors;
@@ -203,7 +265,7 @@ void IGESCAFControl_Writer::MakeColors (const TopoDS_Shape &S,
   // analyze whether current entity should get a color 
   Standard_Boolean hasColor = Standard_False;
   Quantity_Color col;
-  if ( S.ShapeType() == TopAbs_FACE ) {
+  if ( S.ShapeType() == TopAbs_FACE  || S.ShapeType() == TopAbs_SOLID) {
     if ( style.IsSetColorSurf() ) {
       hasColor = Standard_True;
       col = style.GetColorSurf();
@@ -240,6 +302,12 @@ void IGESCAFControl_Writer::MakeColors (const TopoDS_Shape &S,
     Handle(TransferBRep_ShapeMapper) mapper = TransferBRep::ShapeMapper ( FP, S );
     if ( FP->FindTypedTransient ( mapper, STANDARD_TYPE(IGESData_IGESEntity), ent ) ) {
       ent->InitColor ( colent, rank );
+      Handle(IGESSolid_Face) ent_f = Handle(IGESSolid_Face)::DownCast(ent);
+      if (!ent_f.IsNull())
+      {
+        if (!ent_f->Surface().IsNull())
+          ent_f->Surface()->InitColor ( colent, rank );
+      }
     }
     else {
       // may be S was splited during shape process
@@ -254,7 +322,16 @@ void IGESCAFControl_Writer::MakeColors (const TopoDS_Shape &S,
          for (i=1; i<=nb; i++) {
            Handle(Standard_Transient) t = TransientListBinder->Transient(i);
            ent = Handle(IGESData_IGESEntity)::DownCast(t);
-           if (!ent.IsNull()) ent->InitColor ( colent, rank );
+           if (!ent.IsNull())
+      {
+        ent->InitColor ( colent, rank );
+        Handle(IGESSolid_Face) ent_f = Handle(IGESSolid_Face)::DownCast(ent);
+        if (!ent_f.IsNull())
+        {
+          if (!ent_f->Surface().IsNull())
+            ent_f->Surface()->InitColor ( colent, rank );
+        }
+      }
          }
        }
        /* // alternative: consider recursive mapping S -> compound -> entities
@@ -309,11 +386,8 @@ static void AttachLayer (const Handle(Transfer_FinderProcess) &FP,
     Handle(TransferBRep_ShapeMapper) mapper = TransferBRep::ShapeMapper ( FP, localShape );
     if ( FP->FindTypedTransient ( mapper, STANDARD_TYPE(IGESData_IGESEntity), Igesent ) ) {
       Igesent->InitLevel( 0, localIntName );
-// #ifdef DEB
-//       cout << "Init layer " << localIntName << " for "<< localShape.TShape()->DynamicType()->Name() << endl;
-// #endif
     }
-#ifdef DEB
+#ifdef OCCT_DEBUG
     else cout << "Warning: Can't find entity for shape in mapper" << endl;
 #endif
   }
@@ -341,11 +415,12 @@ static void MakeLayers (const Handle(Transfer_FinderProcess) &FP,
 //purpose  : 
 //=======================================================================
 
-Standard_Boolean IGESCAFControl_Writer::WriteLayers (const Handle(TDocStd_Document)& Doc
+Standard_Boolean IGESCAFControl_Writer::WriteLayers (const TDF_LabelSequence& labels
 {
-  Handle(XCAFDoc_ShapeTool) STool = XCAFDoc_DocumentTool::ShapeTool( Doc->Main() );
+  if ( labels.Length() <=0 ) return Standard_False;
+  Handle(XCAFDoc_ShapeTool) STool = XCAFDoc_DocumentTool::ShapeTool( labels(1) );
   if ( STool.IsNull() ) return Standard_False;
-  Handle(XCAFDoc_LayerTool) LTool = XCAFDoc_DocumentTool::LayerTool( Doc->Main() );
+  Handle(XCAFDoc_LayerTool) LTool = XCAFDoc_DocumentTool::LayerTool( labels(1) );
   if ( LTool.IsNull() ) return Standard_False;
   
   Standard_Integer globalIntName = 0;
@@ -395,37 +470,54 @@ Standard_Boolean IGESCAFControl_Writer::WriteLayers (const Handle(TDocStd_Docume
 //purpose  : 
 //=======================================================================
 
-Standard_Boolean IGESCAFControl_Writer::WriteNames (const Handle(TDocStd_Document)& Doc) 
+Standard_Boolean IGESCAFControl_Writer::WriteNames (const TDF_LabelSequence& theLabels)
 {
-  Handle(XCAFDoc_ShapeTool) STool = XCAFDoc_DocumentTool::ShapeTool( Doc->Main() );
-  if ( STool.IsNull() ) return Standard_False;
-  TDF_ChildIterator labelShIt(STool->BaseLabel() , Standard_True);
-  for (; labelShIt.More(); labelShIt.Next() ) {
-    TDF_Label shLabel = labelShIt.Value();
+  if (theLabels.Length() <= 0) return Standard_False;
+
+  DataMapOfShapeNames aMapOfShapeNames;
+
+  for (Standard_Integer anIter = 1; anIter <= theLabels.Length(); anIter++ )
+  {
+    TDF_Label aLabel = theLabels.Value (anIter);
+
+    TopoDS_Shape aShape;
     Handle(TDataStd_Name) aName;
-    if ( !shLabel.FindAttribute( TDataStd_Name::GetID(), aName) ) continue;
-    TCollection_ExtendedString shName = aName->Get();
-    TopoDS_Shape Sh;
-    if ( !STool->GetShape(shLabel, Sh) ) continue;
-    Handle(Transfer_FinderProcess) FP = TransferProcess();
-    Handle(IGESData_IGESEntity) Igesent;
-    Handle(TransferBRep_ShapeMapper) mapper = TransferBRep::ShapeMapper ( FP, Sh );
-    if ( FP->FindTypedTransient ( mapper, STANDARD_TYPE(IGESData_IGESEntity), Igesent ) ) {
-      Handle(TCollection_HAsciiString) HAname = new TCollection_HAsciiString ( "        " );
-      Standard_Integer len = 8 - shName.Length();
-      if ( len <0 ) len = 0;
-      for ( Standard_Integer k=1; len <8; k++, len++ ) {
-       HAname->SetValue ( len+1, IsAnAscii(shName.Value(k)) ? (Standard_Character)shName.Value(k) : '?' );
+    if (!XCAFDoc_ShapeTool::GetShape (aLabel, aShape)) continue;
+    if (!aLabel.FindAttribute (TDataStd_Name::GetID(), aName)) continue;
+
+    aMapOfShapeNames.Bind (aShape, aName->Get());
+
+    // Collect names for subshapes
+    TopLoc_Location aLocation;
+    CollectShapeNames (aLabel, aLocation, aName, aMapOfShapeNames);
+  }
+
+  for (DataMapOfShapeNames::Iterator anIter (aMapOfShapeNames);
+       anIter.More(); anIter.Next())
+  {
+    const TopoDS_Shape& aShape = anIter.Key();
+    const TCollection_ExtendedString& aName = anIter.Value();
+
+    Handle(Transfer_FinderProcess) aFinderProcess = TransferProcess();
+    Handle(IGESData_IGESEntity) anIGESEntity;
+    Handle(TransferBRep_ShapeMapper) aShapeMapper = TransferBRep::ShapeMapper (aFinderProcess, aShape);
+
+    if (aFinderProcess->FindTypedTransient (aShapeMapper, STANDARD_TYPE(IGESData_IGESEntity), anIGESEntity))
+    {
+      Handle(TCollection_HAsciiString) anAsciiName = new TCollection_HAsciiString ("        ");
+      Standard_Integer aNameLength = 8 - aName.Length();
+      if (aNameLength < 0) aNameLength = 0;
+      for (Standard_Integer aCharPos = 1; aNameLength < 8; aCharPos++, aNameLength++)
+      {
+        anAsciiName->SetValue (aNameLength+1, IsAnAscii (aName.Value (aCharPos)) ? (Standard_Character )aName.Value (aCharPos) : '?');
       }
-      Igesent->SetLabel( HAname );
-//       Handle(IGESData_NameEntity) aNameent = new IGESData_NameEntity;
-//       Igesent->AddProperty(aNameent);
-   }
+      anIGESEntity->SetLabel (anAsciiName);
+    }
   }
+
   return Standard_True;
 }
 
-
 //=======================================================================
 //function : SetColorMode
 //purpose  :