From 9361e2c00ab6ab333b32af580352ae6e8f654401 Mon Sep 17 00:00:00 2001 From: skv Date: Tue, 16 Feb 2016 17:19:14 +0300 Subject: [PATCH] 0023216: [CEA 1691] Import the compounds with their names from a STEP file --- idl/STEPPlugin.idl | 6 +- src/GEOM_I_Superv/GEOM_Superv_i.cc | 2 +- src/GEOM_SWIG/STEPPluginBuilder.py | 16 +- src/STEPPlugin/CMakeLists.txt | 3 + src/STEPPlugin/STEPPlugin_GUI.cxx | 13 +- src/STEPPlugin/STEPPlugin_IECallBack.cxx | 2 +- src/STEPPlugin/STEPPlugin_IImport.hxx | 11 +- src/STEPPlugin/STEPPlugin_IOperations.cxx | 14 +- src/STEPPlugin/STEPPlugin_IOperations.hxx | 5 +- src/STEPPlugin/STEPPlugin_IOperations_i.cc | 12 +- src/STEPPlugin/STEPPlugin_IOperations_i.hh | 2 +- src/STEPPlugin/STEPPlugin_ImportDlg.cxx | 94 ++++++ src/STEPPlugin/STEPPlugin_ImportDlg.h | 52 ++++ src/STEPPlugin/STEPPlugin_ImportDriver.cxx | 328 ++++++++++++++++++--- src/STEPPlugin/STEPPlugin_msg_en.ts | 7 + 15 files changed, 509 insertions(+), 58 deletions(-) create mode 100644 src/STEPPlugin/STEPPlugin_ImportDlg.cxx create mode 100644 src/STEPPlugin/STEPPlugin_ImportDlg.h diff --git a/idl/STEPPlugin.idl b/idl/STEPPlugin.idl index ba1a74ec8..9caf6f373 100644 --- a/idl/STEPPlugin.idl +++ b/idl/STEPPlugin.idl @@ -64,10 +64,14 @@ module GEOM * \param theIsIgnoreUnits If True, file length units will be ignored (set to 'meter') * and result model will be scaled, if its units are not meters. * If False (default), file length units will be taken into account. + * \param IsCreateAssemblies If True, for each assembly compound is created + * in the result. If False Compounds that contain a + * single shape are eliminated from the result. * \return List of GEOM_Objects, containing the created shape and propagation groups. */ GEOM::ListOfGO ImportSTEP( in string theFileName, - in boolean theIsIgnoreUnits ); + in boolean theIsIgnoreUnits, + in boolean IsCreateAssemblies); /*! * \brief Read a value of parameter from a file, containing a shape. diff --git a/src/GEOM_I_Superv/GEOM_Superv_i.cc b/src/GEOM_I_Superv/GEOM_Superv_i.cc index 662b2c768..a229accac 100644 --- a/src/GEOM_I_Superv/GEOM_Superv_i.cc +++ b/src/GEOM_I_Superv/GEOM_Superv_i.cc @@ -3579,7 +3579,7 @@ GEOM::GEOM_Object_ptr GEOM_Superv_i::ImportSTEP( const char* theFileName, beginService( " GEOM_Superv_i::ImportSTEP" ); MESSAGE("GEOM_Superv_i::ImportSTEP"); getSTEPPluginOp(); - GEOM::ListOfGO* aSeq = mySTEPOp->ImportSTEP(theFileName, theIsIgnoreUnits ); + GEOM::ListOfGO* aSeq = mySTEPOp->ImportSTEP(theFileName, theIsIgnoreUnits, false ); GEOM::GEOM_Object_ptr anObj; if (aSeq->length() > 0) { diff --git a/src/GEOM_SWIG/STEPPluginBuilder.py b/src/GEOM_SWIG/STEPPluginBuilder.py index 1ee4fc6c7..896c0f7d6 100644 --- a/src/GEOM_SWIG/STEPPluginBuilder.py +++ b/src/GEOM_SWIG/STEPPluginBuilder.py @@ -54,6 +54,9 @@ def ExportSTEP(self, theObject, theFileName, theUnit=GEOM.LU_METER): # @param theIsIgnoreUnits If True, file length units will be ignored (set to 'meter') # and result model will be scaled, if its units are not meters. # If False (default), file length units will be taken into account. +# @param IsCreateAssemblies If True, for each assembly compound is created in +# the result. If False Compounds that contain a single shape +# are eliminated from the result. # @param theName Object name; when specified, this parameter is used # for result publication in the study. Otherwise, if automatic # publication is switched on, default value is used for result name. @@ -67,7 +70,8 @@ def ExportSTEP(self, theObject, theFileName, theUnit=GEOM.LU_METER): # # @ref swig_Import_Export "Example" # @ingroup l2_import_export -def ImportSTEP(self, theFileName, theIsIgnoreUnits = False, theName=None): +def ImportSTEP(self, theFileName, theIsIgnoreUnits = False, + IsCreateAssemblies = False, theName=None): """ Import a shape from the STEP file with given name. @@ -76,6 +80,9 @@ def ImportSTEP(self, theFileName, theIsIgnoreUnits = False, theName=None): ignoreUnits If True, file length units will be ignored (set to 'meter') and result model will be scaled, if its units are not meters. If False (default), file length units will be taken into account. + IsCreateAssemblies If True, for each assembly compound is created in + the result. If False Compounds that contain a single shape + are eliminated from the result. theName Object name; when specified, this parameter is used for result publication in the study. Otherwise, if automatic publication is switched on, default value is used for result name. @@ -94,13 +101,18 @@ def ImportSTEP(self, theFileName, theIsIgnoreUnits = False, theName=None): anOp = GetSTEPPluginOperations(self) anIsIgnoreUnits = theIsIgnoreUnits + anIsCreateAssemblies = IsCreateAssemblies; aName = theName if isinstance( theIsIgnoreUnits, basestring ): anIsIgnoreUnits = False aName = theIsIgnoreUnits pass + elif isinstance( IsCreateAssemblies, basestring ): + anIsCreateAssemblies = False + aName = IsCreateAssemblies + pass - aListObj = anOp.ImportSTEP(theFileName,anIsIgnoreUnits) + aListObj = anOp.ImportSTEP(theFileName,anIsIgnoreUnits,anIsCreateAssemblies) RaiseIfFailed("ImportSTEP", anOp) aNbObj = len(aListObj) if aNbObj > 0: diff --git a/src/STEPPlugin/CMakeLists.txt b/src/STEPPlugin/CMakeLists.txt index db71d3b24..efd69970a 100644 --- a/src/STEPPlugin/CMakeLists.txt +++ b/src/STEPPlugin/CMakeLists.txt @@ -94,6 +94,7 @@ SET(STEPPluginEngine_HEADERS STEPPlugin_IExport.hxx STEPPlugin_IImport.hxx STEPPlugin_ImportDriver.hxx + STEPPlugin_ImportDlg.h STEPPlugin_ExportDlg.h STEPPlugin_ExportDriver.hxx STEPPlugin_IECallBack.hxx @@ -104,6 +105,7 @@ IF(SALOME_BUILD_GUI) SET(_moc_HEADERS STEPPlugin_GUI.h STEPPlugin_ExportDlg.h + STEPPlugin_ImportDlg.h ) ENDIF() @@ -116,6 +118,7 @@ IF(SALOME_BUILD_GUI) SET(STEPPluginGUI_SOURCES STEPPlugin_GUI.cxx STEPPlugin_ExportDlg.cxx + STEPPlugin_ImportDlg.cxx ${_moc_SOURCES} ) ENDIF() diff --git a/src/STEPPlugin/STEPPlugin_GUI.cxx b/src/STEPPlugin/STEPPlugin_GUI.cxx index 5543266d7..2986dea4b 100644 --- a/src/STEPPlugin/STEPPlugin_GUI.cxx +++ b/src/STEPPlugin/STEPPlugin_GUI.cxx @@ -38,6 +38,7 @@ #include "GEOM_Displayer.h" #include "GEOM_GenericObjPtr.h" #include "STEPPlugin_ExportDlg.h" +#include "STEPPlugin_ImportDlg.h" #include #include CORBA_SERVER_HEADER(STEPPlugin) @@ -118,10 +119,11 @@ bool STEPPlugin_GUI::importSTEP( SUIT_Desktop* parent ) STEPOpPtr stepOp = GEOM::ISTEPOperations::_narrow( op ); if ( stepOp.isNull() ) return false; - QStringList fileNames = app->getOpenFileNames( SUIT_FileDlg::getLastVisitedPath().isEmpty() ? QDir::currentPath() : QString(""), - tr( "STEP_FILES" ), - tr( "IMPORT_TITLE" ), - parent ); + bool isCreateAssemblies = true; + QStringList fileNames = STEPPlugin_ImportDlg::getOpenFileNames + (SUIT_FileDlg::getLastVisitedPath().isEmpty() ? QDir::currentPath() : QString(""), + tr("STEP_FILES"), tr("IMPORT_TITLE"), parent, isCreateAssemblies); + if ( fileNames.count() > 0 ) { QStringList entryList; @@ -175,7 +177,8 @@ bool STEPPlugin_GUI::importSTEP( SUIT_Desktop* parent ) } } - GEOM::ListOfGO_var result = stepOp->ImportSTEP( fileName.toUtf8().constData(), ignoreUnits ); + GEOM::ListOfGO_var result = stepOp->ImportSTEP + (fileName.toUtf8().constData(), ignoreUnits, isCreateAssemblies); if ( result->length() > 0 && stepOp->IsDone() ) { GEOM::GEOM_Object_var main = result[0]; diff --git a/src/STEPPlugin/STEPPlugin_IECallBack.cxx b/src/STEPPlugin/STEPPlugin_IECallBack.cxx index ac0869716..b745f0d04 100644 --- a/src/STEPPlugin/STEPPlugin_IECallBack.cxx +++ b/src/STEPPlugin/STEPPlugin_IECallBack.cxx @@ -70,7 +70,7 @@ STEPPlugin_IECallBack::Import( int theDocId, { STEPPlugin_IOperations* aPluginOperations = STEPPlugin_OperationsCreator::get( GetEngine(), theDocId ); bool anIsIgnoreUnits = ( theFormatName == "STEP_SCALE" ) ? true : false; - return aPluginOperations->ImportSTEP( theFileName, anIsIgnoreUnits ); + return aPluginOperations->ImportSTEP( theFileName, anIsIgnoreUnits, false ); } //============================================================================= diff --git a/src/STEPPlugin/STEPPlugin_IImport.hxx b/src/STEPPlugin/STEPPlugin_IImport.hxx index 3b63fdfdc..f7630e4eb 100644 --- a/src/STEPPlugin/STEPPlugin_IImport.hxx +++ b/src/STEPPlugin/STEPPlugin_IImport.hxx @@ -22,8 +22,9 @@ #include "GEOM_Function.hxx" -#define IMPORTSTEP_ARG_FILENAME 1 -#define IMPORTSTEP_ARG_IGNORE_UNITS 2 +#define IMPORTSTEP_ARG_FILENAME 1 +#define IMPORTSTEP_ARG_IGNORE_UNITS 2 +#define IMPORTSTEP_ARG_CREATE_ASSEMBLIES 3 class STEPPlugin_IImport { @@ -41,6 +42,12 @@ public: bool GetIsIgnoreUnits() { return bool( _func->GetInteger( IMPORTSTEP_ARG_IGNORE_UNITS ) ); } + void SetIsCreateAssemblies( bool IsCreateAssemblies ) + { _func->SetInteger + ( IMPORTSTEP_ARG_CREATE_ASSEMBLIES, IsCreateAssemblies ? 1 : 0 ); } + bool GetIsCreateAssemblies() + { return ( _func->GetInteger( IMPORTSTEP_ARG_CREATE_ASSEMBLIES ) != 0 ); } + private: Handle(GEOM_Function) _func; }; diff --git a/src/STEPPlugin/STEPPlugin_IOperations.cxx b/src/STEPPlugin/STEPPlugin_IOperations.cxx index 72064e8e3..24f898aeb 100644 --- a/src/STEPPlugin/STEPPlugin_IOperations.cxx +++ b/src/STEPPlugin/STEPPlugin_IOperations.cxx @@ -167,8 +167,9 @@ void STEPPlugin_IOperations::ExportSTEP */ //============================================================================= Handle(TColStd_HSequenceOfTransient) -STEPPlugin_IOperations::ImportSTEP( const TCollection_AsciiString& theFileName, - const bool theIsIgnoreUnits ) +STEPPlugin_IOperations::ImportSTEP(const TCollection_AsciiString& theFileName, + const bool theIsIgnoreUnits, + const bool IsCreateAssemblies) { SetErrorCode(KO); if( theFileName.IsEmpty() ) return NULL; @@ -188,6 +189,7 @@ STEPPlugin_IOperations::ImportSTEP( const TCollection_AsciiString& theFileName, STEPPlugin_IImport aCI( aFunction ); aCI.SetFileName( theFileName ); aCI.SetIsIgnoreUnits( theIsIgnoreUnits ); + aCI.SetIsCreateAssemblies( IsCreateAssemblies ); //Perform the Import Handle(TColStd_HSequenceOfTransient) aSeq = new TColStd_HSequenceOfTransient; @@ -211,10 +213,10 @@ STEPPlugin_IOperations::ImportSTEP( const TCollection_AsciiString& theFileName, //Make a Python command GEOM::TPythonDump pd (aFunction); - if( theIsIgnoreUnits ) - pd << aSeq << " = geompy.ImportSTEP(\"" << theFileName.ToCString() << "\", True)"; - else - pd << aSeq << " = geompy.ImportSTEP(\"" << theFileName.ToCString() << "\")"; + pd << aSeq << " = geompy.ImportSTEP(\"" << theFileName.ToCString() << "\", "; + pd << (theIsIgnoreUnits ? "True" : "False"); + pd << ", " << (IsCreateAssemblies ? "True" : "False"); + pd << ")"; SetErrorCode(OK); return aSeq; diff --git a/src/STEPPlugin/STEPPlugin_IOperations.hxx b/src/STEPPlugin/STEPPlugin_IOperations.hxx index 92b3f160e..90266d34b 100644 --- a/src/STEPPlugin/STEPPlugin_IOperations.hxx +++ b/src/STEPPlugin/STEPPlugin_IOperations.hxx @@ -57,8 +57,9 @@ public: void ExportSTEP( const Handle(GEOM_Object), const TCollection_AsciiString&, const LengthUnit ); - Handle(TColStd_HSequenceOfTransient) ImportSTEP( const TCollection_AsciiString&, - const bool ); + Handle(TColStd_HSequenceOfTransient) ImportSTEP(const TCollection_AsciiString&, + const bool, + const bool); TCollection_AsciiString ReadValue( const TCollection_AsciiString&, const TCollection_AsciiString& ); diff --git a/src/STEPPlugin/STEPPlugin_IOperations_i.cc b/src/STEPPlugin/STEPPlugin_IOperations_i.cc index fba3ce031..fa40dae0e 100644 --- a/src/STEPPlugin/STEPPlugin_IOperations_i.cc +++ b/src/STEPPlugin/STEPPlugin_IOperations_i.cc @@ -119,11 +119,16 @@ void STEPPlugin_IOperations_i::ExportSTEP(GEOM::GEOM_Object_ptr theOriginal, * \param theIsIgnoreUnits If True, file length units will be ignored (set to 'meter') * and result model will be scaled, if its units are not meters. * If False (default), file length units will be taken into account. + * \param IsCreateAssemblies If True, for each assembly compound is created + * in the result. If False Compounds that contain a + * single shape are eliminated from the result. * \return List of GEOM_Objects, containing the created shape and propagation groups. */ //============================================================================= -GEOM::ListOfGO* STEPPlugin_IOperations_i::ImportSTEP( const char* theFileName, - const bool theIsIgnoreUnits = false ) +GEOM::ListOfGO* STEPPlugin_IOperations_i::ImportSTEP + (const char *theFileName, + const bool theIsIgnoreUnits, + const bool IsCreateAssemblies) { GEOM::ListOfGO_var aSeq = new GEOM::ListOfGO; @@ -131,7 +136,8 @@ GEOM::ListOfGO* STEPPlugin_IOperations_i::ImportSTEP( const char* theFileName, GetOperations()->SetNotDone(); //Import the shape from the file - Handle(TColStd_HSequenceOfTransient) aHSeq = GetOperations()->ImportSTEP( theFileName, theIsIgnoreUnits ); + Handle(TColStd_HSequenceOfTransient) aHSeq = GetOperations()->ImportSTEP + (theFileName, theIsIgnoreUnits, IsCreateAssemblies); if( !GetOperations()->IsDone() || aHSeq.IsNull() ) return aSeq._retn(); diff --git a/src/STEPPlugin/STEPPlugin_IOperations_i.hh b/src/STEPPlugin/STEPPlugin_IOperations_i.hh index 16e000909..4faa4128c 100644 --- a/src/STEPPlugin/STEPPlugin_IOperations_i.hh +++ b/src/STEPPlugin/STEPPlugin_IOperations_i.hh @@ -45,7 +45,7 @@ public: void ExportSTEP( GEOM::GEOM_Object_ptr, const char*, GEOM::length_unit ); - GEOM::ListOfGO* ImportSTEP( const char*, const bool ); + GEOM::ListOfGO* ImportSTEP( const char*, const bool, const bool ); char* ReadValue( const char*, const char* ); STEPPlugin_IOperations* GetOperations(); diff --git a/src/STEPPlugin/STEPPlugin_ImportDlg.cxx b/src/STEPPlugin/STEPPlugin_ImportDlg.cxx new file mode 100644 index 000000000..de6cb2169 --- /dev/null +++ b/src/STEPPlugin/STEPPlugin_ImportDlg.cxx @@ -0,0 +1,94 @@ +// Copyright (C) 2014-2015 CEA/DEN, EDF R&D, OPEN CASCADE +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#include "STEPPlugin_ImportDlg.h" + +#include +#include +#include + +//============================================================================= +// Constructor +//============================================================================= +STEPPlugin_ImportDlg::STEPPlugin_ImportDlg(QWidget *parent) + : SUIT_FileDlg (parent, true, true, true), + myCheckBox (0) +{ + myCheckBox = new QCheckBox(tr("STEP_CREATE_ASSEMBLIES"), this); + + myCheckBox->setChecked(true); + + layout()->addWidget(myCheckBox); +} + +//============================================================================= +// Destructor +//============================================================================= +STEPPlugin_ImportDlg::~STEPPlugin_ImportDlg() +{ +} + +//============================================================================= +// IsCreateAssemblies +//============================================================================= +bool STEPPlugin_ImportDlg::IsCreateAssemblies() const +{ + return myCheckBox->isChecked(); +} + +//============================================================================= +// getOpenFileNames +//============================================================================= +QStringList STEPPlugin_ImportDlg::getOpenFileNames + (const QString &theInitial, + const QString &theFilters, + const QString &theCaption, + QWidget *theParent, + bool &IsCreateAssemblies) +{ + STEPPlugin_ImportDlg anImpDlg(theParent); + QStringList aFilters = theFilters.split(";;", QString::SkipEmptyParts); + + anImpDlg.setFileMode(ExistingFiles); + + if (aFilters.isEmpty()) { + anImpDlg.setFilter(tr("ALL_FILES_FILTER")); // All files (*) + } else { + anImpDlg.setFilters(aFilters); + } + + if (!theCaption.isEmpty()) { + anImpDlg.setWindowTitle(theCaption); + } + + if (!theInitial.isEmpty()) { + anImpDlg.processPath(theInitial); + } + + QStringList aFileNames; + + if (anImpDlg.exec() == QDialog::Accepted) { + aFileNames = anImpDlg.selectedFiles(); + IsCreateAssemblies = anImpDlg.IsCreateAssemblies(); + } + + QApplication::processEvents(); + + return aFileNames; +} diff --git a/src/STEPPlugin/STEPPlugin_ImportDlg.h b/src/STEPPlugin/STEPPlugin_ImportDlg.h new file mode 100644 index 000000000..32f75d3e5 --- /dev/null +++ b/src/STEPPlugin/STEPPlugin_ImportDlg.h @@ -0,0 +1,52 @@ +// Copyright (C) 2014-2015 CEA/DEN, EDF R&D, OPEN CASCADE +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#ifndef STEPPlugin_ImportDlg_H +#define STEPPlugin_ImportDlg_H + +#include +#include +#include CORBA_CLIENT_HEADER(STEPPlugin) + +class QCheckBox; + +class STEPPlugin_ImportDlg: public SUIT_FileDlg +{ + Q_OBJECT + +public: + + STEPPlugin_ImportDlg(QWidget *parent); + ~STEPPlugin_ImportDlg(); + + bool IsCreateAssemblies() const; + + static QStringList getOpenFileNames (const QString &theInitial, + const QString &theFilters, + const QString &theCaption, + QWidget *theParent, + bool &IsCreateAssemblies); + +private: + + QCheckBox *myCheckBox; + +}; + +#endif // STEPPlugin_ImportDlg_H diff --git a/src/STEPPlugin/STEPPlugin_ImportDriver.cxx b/src/STEPPlugin/STEPPlugin_ImportDriver.cxx index 961dd77be..1cf37959d 100644 --- a/src/STEPPlugin/STEPPlugin_ImportDriver.cxx +++ b/src/STEPPlugin/STEPPlugin_ImportDriver.cxx @@ -47,6 +47,7 @@ #include #include #include +#include #include #include #include @@ -57,7 +58,11 @@ #include #include #include +#include #include +#include +#include +#include #include #include #include @@ -139,22 +144,227 @@ namespace return aResult; } + //============================================================================= + /*! + * GetAllParents() + */ + //============================================================================= + + Standard_Boolean GetAllParents(const TopoDS_Shape &theShape, + const TopoDS_Shape &theSubShape, + TopTools_ListOfShape &theParents) + { + const TopAbs_ShapeEnum aSubShType = theSubShape.ShapeType(); + Standard_Boolean aResult = Standard_False; + + if (theShape.ShapeType() >= aSubShType) { + return aResult; // NULL shape + } + + TopoDS_Iterator anIt(theShape); + TopTools_MapOfShape aMapFence; + + for (; anIt.More(); anIt.Next()) { + const TopoDS_Shape &aSubShape = anIt.Value(); + + if (aMapFence.Add(aSubShape)) { + if (theSubShape.IsSame(aSubShape)) { + // The sub-shape is found. theShape is its parent. + theParents.Append(theShape); + aResult = Standard_True; + break; + } + + if (aSubShape.ShapeType() < aSubShType) { + if (GetAllParents(aSubShape, theSubShape, theParents)) { + // The sub-shape is found. + theParents.Append(theShape); + aResult = Standard_True; + break; + } + } + } + } + + return aResult; + } + + //============================================================================= + /*! + * BuildModifiedShape() + */ + //============================================================================= + + TopoDS_Shape BuildModifiedShape + (const TopoDS_Shape &theShape, + TopTools_DataMapOfShapeShape &theMapModified) + { + // Check if the shape is modified. + TopoDS_Shape aFwdShape = theShape.Oriented(TopAbs_FORWARD); + TopoDS_Iterator anIt(aFwdShape); + Standard_Boolean isModified = Standard_False; + + for (; anIt.More(); anIt.Next()) { + if (theMapModified.IsBound(anIt.Value())) { + isModified = Standard_True; + break; + } + } + + TopoDS_Shape aResult; + + if (isModified) { + BRep_Builder aBuilder; + + aResult = aFwdShape.EmptyCopied(); + + for (anIt.Initialize(aFwdShape); anIt.More(); anIt.Next()) { + const TopoDS_Shape &aSubShape = anIt.Value(); + + if (theMapModified.IsBound(aSubShape)) { + TopoDS_Shape aModifSubShape = theMapModified.Find(aSubShape); + + if (aModifSubShape.IsNull()) { + // Recursively compute the sub-shape. + aModifSubShape = BuildModifiedShape(aSubShape, theMapModified); + } + + aBuilder.Add(aResult, aModifSubShape); + } else { + aBuilder.Add(aResult, aSubShape); + } + } + + // Set the result shape orienation. + aResult.Orientation(theShape.Orientation()); + theMapModified.Bind(theShape, aResult); + } else { + aResult = theShape; + } + + return aResult; + } + + //============================================================================= + /*! + * CreateAssemblies() + */ + //============================================================================= + + TopoDS_Shape CreateAssemblies + (const STEPControl_Reader &theReader, + const TopoDS_Shape &theShape, + TopTools_DataMapOfShapeShape &theMapShapeAssembly) + { + TopoDS_Shape aResult = theShape; + Handle(XSControl_TransferReader) aTR = theReader.WS()->TransferReader(); + TopTools_ListOfShape aListAssemblies; + + if (!aTR.IsNull()) { + Handle(Interface_InterfaceModel) aModel = theReader.WS()->Model(); + Handle(Transfer_TransientProcess) aTP = aTR->TransientProcess(); + Standard_Integer aNbEntities = aModel->NbEntities(); + Standard_Integer i; + Handle(Standard_Type) aNAUOType = + STANDARD_TYPE(StepRepr_NextAssemblyUsageOccurrence); + + for (i = 1; i <= aNbEntities; i++) { + Handle(Standard_Transient) anEnti = aModel->Value(i); + + if (anEnti->IsKind(aNAUOType)) { + // This is an assembly. Find target shape + TopoDS_Shape aShape = GetShape(anEnti, aTP); + + if (aShape.IsNull()) { + continue; + } + + if (aShape.ShapeType() != TopAbs_COMPOUND) { + aListAssemblies.Append(aShape); + } + } + } + } + + // Create assemblies. + if (!aListAssemblies.IsEmpty()) { + TopTools_ListIteratorOfListOfShape anIter(aListAssemblies); + BRep_Builder aBuilder; + + for (; anIter.More(); anIter.Next()) { + const TopoDS_Shape &aShape = anIter.Value(); + TopTools_ListOfShape aParents; + + if (GetAllParents(theShape, aShape, aParents) && + aParents.First().ShapeType() == TopAbs_COMPOUND) { + TopoDS_Compound aComp; + TopTools_ListIteratorOfListOfShape aParentIter(aParents); + + // Fill theMapShapeAssembly. + for (; aParentIter.More(); aParentIter.Next()) { + theMapShapeAssembly.Bind(aParentIter.Value(), TopoDS_Shape()); + } + + aBuilder.MakeCompound(aComp); + aBuilder.Add(aComp, aShape); + theMapShapeAssembly.Bind(aShape, aComp); + } + } + + // Build a new shape. + aResult = BuildModifiedShape(theShape, theMapShapeAssembly); + } + + return aResult; + } + //============================================================================= /*! * StoreName() */ //============================================================================= - void StoreName( const Handle(Standard_Transient) &theEnti, - const TopTools_IndexedMapOfShape &theIndices, - const Handle(Transfer_TransientProcess) &theTP, - const TDF_Label &theShapeLabel) + void StoreName(const Handle(Standard_Transient) &theEnti, + const TopTools_IndexedMapOfShape &theIndices, + const Handle(XSControl_WorkSession) &theWS, + const Handle(Transfer_TransientProcess) &theTP, + const TDF_Label &theShapeLabel, + TopTools_DataMapOfShapeShape &theMapShapeAssembly) { Handle(TCollection_HAsciiString) aName; if (theEnti->IsKind(STANDARD_TYPE(StepShape_TopologicalRepresentationItem)) || theEnti->IsKind(STANDARD_TYPE(StepGeom_GeometricRepresentationItem))) { aName = Handle(StepRepr_RepresentationItem)::DownCast(theEnti)->Name(); + } else if (theEnti->IsKind(STANDARD_TYPE(StepRepr_NextAssemblyUsageOccurrence))) { + Handle(StepRepr_NextAssemblyUsageOccurrence) aNAUO = + Handle(StepRepr_NextAssemblyUsageOccurrence)::DownCast(theEnti); + + Interface_EntityIterator aSubs = theWS->Graph().Sharings(aNAUO); + + for (aSubs.Start(); aSubs.More(); aSubs.Next()) { + Handle(StepRepr_ProductDefinitionShape) aPDS = + Handle(StepRepr_ProductDefinitionShape)::DownCast(aSubs.Value()); + + if(aPDS.IsNull()) { + continue; + } + + Handle(StepBasic_ProductDefinitionRelationship) aPDR = + aPDS->Definition().ProductDefinitionRelationship(); + + if (aPDR.IsNull()) { + continue; + } + + if (aPDR->HasDescription() && aPDR->Description()->Length() >0) { + aName = aPDR->Description(); + } else if (!aPDR->Name().IsNull() && aPDR->Name()->Length() >0 ) { + aName = aPDR->Name(); + } else if (!aPDR->Id().IsNull()) { + aName = aPDR->Id(); + } + } } else { Handle(StepBasic_ProductDefinition) PD = Handle(StepBasic_ProductDefinition)::DownCast(theEnti); @@ -198,6 +408,10 @@ namespace // find target shape TopoDS_Shape S = GetShape(theEnti, theTP); + if (theMapShapeAssembly.IsBound(S)) { + S = theMapShapeAssembly.Find(S); + } + if (S.IsNull()) { return; } @@ -392,6 +606,7 @@ Standard_Integer STEPPlugin_ImportDriver::Execute( TFunction_Logbook& log ) cons TCollection_AsciiString aFileName = aData.GetFileName().ToCString(); bool anIsIgnoreUnits = aData.GetIsIgnoreUnits(); + bool isCreateAssemblies = aData.GetIsCreateAssemblies(); TDF_Label aShapeLabel = aFunction->GetNamingEntry(); MESSAGE("Import STEP from file " << aFileName.ToCString() ); @@ -439,48 +654,91 @@ Standard_Integer STEPPlugin_ImportDriver::Execute( TFunction_Logbook& log ) cons aReader.PrintCheckLoad(failsonly, IFSelect_ItemsByEntity); // Root transfers - Standard_Integer nbr = aReader.NbRootsForTransfer(); + Standard_Integer aNbRoots = aReader.NbRootsForTransfer(); + Standard_Integer i; + aReader.PrintCheckTransfer(failsonly, IFSelect_ItemsByEntity); - for (Standard_Integer n = 1; n <= nbr; n++) { - Standard_Boolean ok = aReader.TransferRoot(n); - // Collecting resulting entities - Standard_Integer nbs = aReader.NbShapes(); - if (!ok || nbs == 0) - continue; // skip empty root - - // For a single entity - else if (nbr == 1 && nbs == 1) { - aResShape = aReader.Shape(1); - if (aResShape.ShapeType() == TopAbs_COMPOUND) { - int nbSub1 = 0; - TopoDS_Shape currShape; - TopoDS_Iterator It (aResShape, Standard_True, Standard_True); - for (; It.More(); It.Next()) { - nbSub1++; - currShape = It.Value(); - } - if (nbSub1 == 1) - aResShape = currShape; + for (i = 1; i <= aNbRoots; i++) { + aReader.TransferRoot(i); + } + + // Create result shape + const Standard_Integer aNbShapes = aReader.NbShapes(); + TopTools_ListOfShape aListResShapes; + + if (isCreateAssemblies) { + for (i = 1; i <= aNbShapes; i++) { + TopoDS_Shape aShape = aReader.Shape(i); + + if (aShape.IsNull()) { + continue; } - break; - } - for (Standard_Integer i = 1; i <= nbs; i++) { + aListResShapes.Append(aShape); + } + } else { + for (i = 1; i <= aNbShapes; i++) { TopoDS_Shape aShape = aReader.Shape(i); - if (aShape.IsNull()) + + if (aShape.IsNull()) { continue; - else - B.Add(compound, aShape); + } + + if (aShape.ShapeType() == TopAbs_COMPOUND) { + int aNbSub = 0; + TopoDS_Shape aSubShape; + TopoDS_Iterator anIt (aShape, Standard_True, Standard_True); + + for (; anIt.More(); anIt.Next()) { + aNbSub++; + aSubShape = anIt.Value(); + } + + if (aNbSub == 1) { + // Use the single sub-shape + aListResShapes.Append(aSubShape); + } else if (aNbSub > 1) { + // Use the shape + aListResShapes.Append(aShape); + } + } + } + } + + // Construct result shape. + if (!aListResShapes.IsEmpty()) { + if (aListResShapes.Extent() == 1) { + // Use the single shape. + aResShape = aListResShapes.First(); + } else { + // Make a compound of result shapes. + TopTools_ListIteratorOfListOfShape anIt(aListResShapes); + + for (; anIt.More(); anIt.Next()) { + B.Add(compound, anIt.Value()); + } + + aResShape = compound; } } - if( aResShape.IsNull() ) - aResShape = compound; + + if( aResShape.IsNull() ) { + StdFail_NotDone::Raise("Null result shape"); + return 0; + } // Check if any BRep entity has been read, there must be at least a vertex if ( !TopExp_Explorer( aResShape, TopAbs_VERTEX ).More() ) StdFail_NotDone::Raise( "No geometrical data in the imported file." ); + // Create assemblies in the shape, if they are not created yet. + TopTools_DataMapOfShapeShape aMapShapeAssembly; + + if (isCreateAssemblies) { + aResShape = CreateAssemblies(aReader, aResShape, aMapShapeAssembly); + } + // BEGIN: Store names and materials of sub-shapes from file TopTools_IndexedMapOfShape anIndices; TopExp::MapShapes(aResShape, anIndices); @@ -496,7 +754,8 @@ Standard_Integer STEPPlugin_ImportDriver::Execute( TFunction_Logbook& log ) cons Handle(Standard_Transient) enti = Model->Value(ie); // Store names. - StoreName(enti, anIndices, TP, aShapeLabel); + StoreName(enti, anIndices, aReader.WS(), + TP, aShapeLabel, aMapShapeAssembly); // Store materials. StoreMaterial(enti, anIndices, TP, aShapeLabel); @@ -575,6 +834,7 @@ GetCreationInformation( std::string& theOperationName, AddParam( theParams, "File name", aCI.GetFileName() ); if( aCI.GetIsIgnoreUnits() ) AddParam( theParams, "Format", "STEP_SCALE" ); + AddParam( theParams, "Create Assemblies", aCI.GetIsCreateAssemblies() ); break; default: return false; diff --git a/src/STEPPlugin/STEPPlugin_msg_en.ts b/src/STEPPlugin/STEPPlugin_msg_en.ts index 47d15c8f8..606569a0d 100644 --- a/src/STEPPlugin/STEPPlugin_msg_en.ts +++ b/src/STEPPlugin/STEPPlugin_msg_en.ts @@ -95,4 +95,11 @@ Ignoring units will cause model scaling (as dimensions are supposed to be specif microinch + + STEPPlugin_ImportDlg + + STEP_CREATE_ASSEMBLIES + Create assemblies + + -- 2.39.2