X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;f=src%2FSalomeApp%2FSalomeApp_Study.cxx;h=98b68ca27ec5402ab1345da10456d6f1ef336fb4;hb=1292b3367a82e807454410dea4b7853de69929c5;hp=d01cdd9f8c6421863209f96e634d0b354e7fd606;hpb=c290de4a12ee8b844a0b82288884f45044659e6e;p=modules%2Fgui.git diff --git a/src/SalomeApp/SalomeApp_Study.cxx b/src/SalomeApp/SalomeApp_Study.cxx index d01cdd9f8..98b68ca27 100644 --- a/src/SalomeApp/SalomeApp_Study.cxx +++ b/src/SalomeApp/SalomeApp_Study.cxx @@ -2,21 +2,32 @@ #include "SalomeApp_Module.h" #include "SalomeApp_DataModel.h" -#include "SalomeApp_RootObject.h" #include "SalomeApp_DataObject.h" #include "SalomeApp_Application.h" +#include "SalomeApp_Engine_i.hxx" + +#include "LightApp_RootObject.h" #include #include +#include + #include "utilities.h" +#include "string.h" +#include "vector.h" + +#include "SALOMEDS_Tool.hxx" + +#include +#include CORBA_SERVER_HEADER(SALOME_Exception) /*! Constructor. */ SalomeApp_Study::SalomeApp_Study( SUIT_Application* app ) -: CAM_Study( app ) +: LightApp_Study( app ) { } @@ -63,10 +74,9 @@ void SalomeApp_Study::createDocument() setStudyName( aName ); // create myRoot - setRoot( new SalomeApp_RootObject( this ) ); + setRoot( new LightApp_RootObject( this ) ); CAM_Study::createDocument(); - emit created( this ); } @@ -85,7 +95,7 @@ bool SalomeApp_Study::openDocument( const QString& theFileName ) setStudyDS( study ); - setRoot( new SalomeApp_RootObject( this ) ); // create myRoot + setRoot( new LightApp_RootObject( this ) ); // create myRoot // update loaded data models: call open() and update() on them. ModelList dm_s; @@ -99,8 +109,9 @@ bool SalomeApp_Study::openDocument( const QString& theFileName ) ((SalomeApp_Application*)application())->updateObjectBrowser( false ); bool res = CAM_Study::openDocument( theFileName ); + emit opened( this ); - + study->IsSaved(true); return res; } @@ -119,13 +130,14 @@ bool SalomeApp_Study::loadDocument( const QString& theStudyName ) setStudyDS( study ); - setRoot( new SalomeApp_RootObject( this ) ); // create myRoot + setRoot( new LightApp_RootObject( this ) ); // create myRoot //SRN: BugID IPAL9021, put there the same code as in a method openDocument // update loaded data models: call open() and update() on them. ModelList dm_s; dataModels( dm_s ); + for ( ModelListIterator it( dm_s ); it.current(); ++it ) openDataModel( studyName(), it.current() ); @@ -144,15 +156,20 @@ bool SalomeApp_Study::loadDocument( const QString& theStudyName ) //======================================================================= // name : saveDocumentAs -/*! Purpose : Save document */ +/*! Purpose : Save document*/ //======================================================================= bool SalomeApp_Study::saveDocumentAs( const QString& theFileName ) { ModelList list; dataModels( list ); SalomeApp_DataModel* aModel = (SalomeApp_DataModel*)list.first(); - for ( ; aModel; aModel = (SalomeApp_DataModel*)list.next() ) - aModel->saveAs( theFileName, this ); + QStringList listOfFiles; + for ( ; aModel; aModel = (SalomeApp_DataModel*)list.next() ) { + listOfFiles.clear(); + aModel->saveAs( theFileName, this, listOfFiles ); + if ( !listOfFiles.isEmpty() ) + saveModuleData(aModel->module()->name(), listOfFiles); + } // save SALOMEDS document SUIT_ResourceMgr* resMgr = application()->resourceMgr(); @@ -165,7 +182,7 @@ bool SalomeApp_Study::saveDocumentAs( const QString& theFileName ) SalomeApp_Application::studyMgr()->SaveAs ( theFileName.latin1(), studyDS(), isMultiFile ); bool res = CAM_Study::saveDocumentAs( theFileName ); //SRN: BugID IPAL9377, removed usage of uninitialized variable - + res = res && saveStudyData(theFileName); if ( res ) emit saved( this ); @@ -174,40 +191,47 @@ bool SalomeApp_Study::saveDocumentAs( const QString& theFileName ) //======================================================================= // name : saveDocument -/*! Purpose : Save document */ +/*! Purpose : Save document*/ //======================================================================= -void SalomeApp_Study::saveDocument() +bool SalomeApp_Study::saveDocument() { ModelList list; dataModels( list ); SalomeApp_DataModel* aModel = (SalomeApp_DataModel*)list.first(); - for ( ; aModel; aModel = (SalomeApp_DataModel*)list.next() ) - aModel->save(); - - CAM_Study::saveDocument(); + QStringList listOfFiles; + for ( ; aModel; aModel = (SalomeApp_DataModel*)list.next() ) { + listOfFiles.clear(); + aModel->save(listOfFiles); + if ( !listOfFiles.isEmpty() ) + saveModuleData(aModel->module()->name(), listOfFiles); + } // save SALOMEDS document SUIT_ResourceMgr* resMgr = application()->resourceMgr(); if( !resMgr ) - return; - + return false; + bool isMultiFile = resMgr->booleanValue( "Study", "multi_file", false ), isAscii = resMgr->booleanValue( "Study", "ascii_file", true ); isAscii ? SalomeApp_Application::studyMgr()->SaveASCII( studyDS(), isMultiFile ) : SalomeApp_Application::studyMgr()->Save ( studyDS(), isMultiFile ); - emit saved( this ); + bool res = CAM_Study::saveDocument(); + + res = res && saveStudyData(studyName()); + if ( res ) + emit saved( this ); + + return res; } //================================================================ // Function : closeDocument -/*! Purpose : Close document */ +/*! Purpose : Close document*/ //================================================================ void SalomeApp_Study::closeDocument(bool permanently) { - // Inform everybody that this study is going to close when it's most safe to, - // i.e. in the very beginning - emit closed( this ); + LightApp_Study::closeDocument(permanently); // close SALOMEDS document _PTR(Study) studyPtr = studyDS(); @@ -217,25 +241,18 @@ void SalomeApp_Study::closeDocument(bool permanently) SALOMEDSClient_Study* aStudy = 0; setStudyDS( _PTR(Study)(aStudy) ); } - - CAM_Study::closeDocument(permanently); } //================================================================ // Function : isModified -/*! Purpose : Check data model on modifications.*/ +// Purpose : //================================================================ bool SalomeApp_Study::isModified() const { bool isAnyChanged = studyDS() && studyDS()->IsModified(); - ModelList list; dataModels( list ); + if (!isAnyChanged) + isAnyChanged = LightApp_Study::isModified(); - SalomeApp_DataModel* aModel = 0; - for ( QPtrListIterator it( list ); it.current() && !isAnyChanged; ++it ){ - aModel = dynamic_cast( it.current() ); - if ( aModel ) - isAnyChanged = aModel->isModified(); - } return isAnyChanged; } @@ -246,17 +263,75 @@ bool SalomeApp_Study::isModified() const bool SalomeApp_Study::isSaved() const { bool isAllSaved = studyDS() && studyDS()->GetPersistentReference().size(); - ModelList list; dataModels( list ); + if (!isAllSaved) + isAllSaved = LightApp_Study::isModified(); - SalomeApp_DataModel* aModel = 0; - for ( QPtrListIterator it( list ); it.current() && isAllSaved; ++it ){ - aModel = dynamic_cast( it.current() ); - if ( aModel ) - isAllSaved = aModel->isSaved(); - } return isAllSaved; } +//======================================================================= +// name : saveModuleData +/*! Purpose : save list file for module 'theModuleName' */ +//======================================================================= +void SalomeApp_Study::saveModuleData( QString theModuleName, QStringList theListOfFiles ) +{ + int aNb = theListOfFiles.count(); + if ( aNb == 0 ) + return; + + std::vector aListOfFiles ( aNb ); + int anIndex = 0; + for ( QStringList::Iterator it = theListOfFiles.begin(); it != theListOfFiles.end(); ++it ) { + if ( (*it).isEmpty() ) + continue; + aListOfFiles[anIndex] = (*it).latin1(); + anIndex++; + } + SetListOfFiles(theModuleName, aListOfFiles); +} + +//======================================================================= +// name : openModuleData +/*! Purpose : gets list of file for module 'theModuleNam' */ +//======================================================================= +void SalomeApp_Study::openModuleData( QString theModuleName, QStringList& theListOfFiles ) +{ + std::vector aListOfFiles = GetListOfFiles( theModuleName ); + + int i, aLength = aListOfFiles.size() - 1; + if ( aLength < 0 ) + return; + + //Get a temporary directory for saved a file + theListOfFiles.append(aListOfFiles[0].c_str()); + + for(i = 0; i < aLength; i++) + theListOfFiles.append(aListOfFiles[i+1].c_str()); +} + +//======================================================================= +// name : saveStudyData +/*! Purpose : save data from study */ +//======================================================================= +bool SalomeApp_Study::saveStudyData( const QString& theFileName ) +{ + ModelList list; dataModels( list ); + SalomeApp_DataModel* aModel = (SalomeApp_DataModel*)list.first(); + std::vector listOfFiles(0); + for ( ; aModel; aModel = (SalomeApp_DataModel*)list.next() ) + SetListOfFiles(aModel->module()->name(), listOfFiles); + return true; +} + +//======================================================================= +// name : openStudyData +/*! Purpose : open data for study */ +//======================================================================= +bool SalomeApp_Study::openStudyData( const QString& theFileName ) +{ + return true; +} + /*! Set studyDS. */ @@ -274,21 +349,36 @@ void SalomeApp_Study::dataModelInserted (const CAM_DataModel* dm) CAM_Study::dataModelInserted(dm); - // Create SComponent for module, using default engine (CORBAless) - SalomeApp_Module* aModule = (SalomeApp_Module*)(dm->module()); - if (aModule) { - QString anEngineIOR = aModule->engineIOR(); - if (anEngineIOR.isEmpty()) { // CORBAless module - // Check SComponent existance - _PTR(SComponent) aComp = studyDS()->FindComponent(dm->module()->name()); - if (!aComp) { - // Create SComponent - _PTR(StudyBuilder) aBuilder = studyDS()->NewBuilder(); - aComp = aBuilder->NewComponent(dm->module()->name()); - - // Set default engine IOR - aBuilder->DefineComponentInstance(aComp, SalomeApp_Application::defaultEngineIOR().latin1()); + // addComponent(dm); +} + +/*! + Create SComponent for module, using default engine (CORBAless) +*/ +void SalomeApp_Study::addComponent(const CAM_DataModel* dm) +{ + SalomeApp_Module* aModule = dynamic_cast( dm->module() ); + // 1. aModule == 0 means that this is a light module (no CORBA enigine) + if (!aModule) { + // Check SComponent existance + _PTR(Study) aStudy = studyDS(); + if (!aStudy) + return; + _PTR(SComponent) aComp = aStudy->FindComponent(dm->module()->name()); + if (!aComp) { + // Create SComponent + _PTR(StudyBuilder) aBuilder = aStudy->NewBuilder(); + aComp = aBuilder->NewComponent(dm->module()->name()); + aBuilder->SetName(aComp, dm->module()->moduleName().latin1()); + QString anIconName = dm->module()->iconName(); + if (!anIconName.isEmpty()) { + _PTR(AttributePixMap) anAttr = aBuilder->FindOrCreateAttribute(aComp, "AttributePixMap"); + if (anAttr) + anAttr->SetPixMap(anIconName.latin1()); } + // Set default engine IOR + aBuilder->DefineComponentInstance(aComp, SalomeApp_Application::defaultEngineIOR().latin1()); + SalomeApp_DataModel::BuildTree( aComp, root(), this, /*skipExisitng=*/true ); } } } @@ -301,13 +391,60 @@ bool SalomeApp_Study::openDataModel( const QString& studyName, CAM_DataModel* dm if (!dm) return false; - SalomeApp_DataModel* aDM = (SalomeApp_DataModel*)(dm); - if (aDM && aDM->open(studyName, this)) { + // SalomeApp_DataModel* aDM = (SalomeApp_DataModel*)(dm); + SalomeApp_Module* aModule = dynamic_cast( dm->module() ); + _PTR(Study) aStudy = studyDS(); // shared_ptr cannot be used here + _PTR(SComponent) aSComp; + QString anEngine; + // 1. aModule == 0 means that this is a light module (no CORBA enigine) + if (!aModule) { + anEngine = SalomeApp_Application::defaultEngineIOR(); + aSComp = aStudy->FindComponent(dm->module()->name()); + } + else { + SalomeApp_DataModel* aDM = dynamic_cast( dm ); + if ( aDM ) { + QString anId = aDM->getRootEntry( this ); + if ( anId.isEmpty() ) + return true; // Probably nothing to load + anEngine = aDM->getModule()->engineIOR(); + if ( anEngine.isEmpty() ) + return false; + aSComp = aStudy->FindComponentID( std::string( anId.latin1() ) ); + } + } + if ( aSComp ) { + _PTR(StudyBuilder) aBuilder( aStudy->NewBuilder() ); + if ( aBuilder ) { + try { + aBuilder->LoadWith( aSComp, std::string( anEngine.latin1() ) ); + } + catch( const SALOME::SALOME_Exception& ) { + // Oops, something went wrong while loading -> return an error + return false; + } + // Something has been read -> create data model tree + //SalomeApp_DataModel* aDM = dynamic_cast( dm ); + // aDM->buildTree( aSComp, 0, this ); + } + } else { + // Don't return false here, for there might be no data + // for a given component in the study yet + } + QStringList listOfFiles; + openModuleData(dm->module()->name(), listOfFiles); + if (dm && dm->open(studyName, this, listOfFiles)) { + // Remove the files and temporary directory, created + // for this module by LightApp_Engine_i::Load() + bool isMultiFile = false; // TODO: decide, how to access this parameter + RemoveTemporaryFiles( dm->module()->name(), isMultiFile ); + // Something has been read -> create data model tree - aDM->update(NULL, this); + LightApp_DataModel* aDM = dynamic_cast( dm ); + if ( aDM ) + aDM->update(NULL, this); return true; } - return false; } @@ -332,3 +469,144 @@ QString SalomeApp_Study::newStudyName() const } return newName; } + +//================================================================ +// Function : GetListOfFiles +/*! Purpose : to be used by CORBAless modules*/ +//================================================================ +std::vector SalomeApp_Study::GetListOfFiles( const char* theModuleName ) const +{ + SalomeApp_Engine_i* aDefaultEngine = SalomeApp_Engine_i::GetInstance(); + if (aDefaultEngine) + return aDefaultEngine->GetListOfFiles(id(), theModuleName); + + std::vector aListOfFiles; + return aListOfFiles; +} + +//================================================================ +// Function : SetListOfFiles +/*! Purpose : to be used by CORBAless modules*/ +//================================================================ +void SalomeApp_Study::SetListOfFiles ( const char* theModuleName, + const std::vector theListOfFiles ) +{ + SalomeApp_Engine_i* aDefaultEngine = SalomeApp_Engine_i::GetInstance(); + if (aDefaultEngine) + aDefaultEngine->SetListOfFiles(theListOfFiles, id(), theModuleName); +} + +//================================================================ +// Function : GetTmpDir +/*! Purpose : to be used by CORBAless modules*/ +//================================================================ +std::string SalomeApp_Study::GetTmpDir ( const char* theURL, const bool isMultiFile ) +{ + std::string anURLDir = SALOMEDS_Tool::GetDirFromPath(theURL); + std::string aTmpDir = isMultiFile ? anURLDir : SALOMEDS_Tool::GetTmpDir(); + return aTmpDir; +} + +//================================================================ +// Function : RemoveTemporaryFiles +/*! Purpose : to be used by CORBAless modules*/ +//================================================================ +void SalomeApp_Study::RemoveTemporaryFiles ( const char* theModuleName, const bool isMultiFile ) const +{ + if (isMultiFile) + return; + + std::vector aListOfFiles = GetListOfFiles( theModuleName ); + if (aListOfFiles.size() > 0) { + std::string aTmpDir = aListOfFiles[0]; + + const int n = aListOfFiles.size() - 1; + SALOMEDS::ListOfFileNames_var aSeq = new SALOMEDS::ListOfFileNames; + aSeq->length(n); + for (int i = 0; i < n; i++) + aSeq[i] = CORBA::string_dup(aListOfFiles[i + 1].c_str()); + + SALOMEDS_Tool::RemoveTemporaryFiles(aTmpDir.c_str(), aSeq.in(), true); + } +} + +// END: methods to be used by CORBAless modules + +void SalomeApp_Study::deleteReferencesTo( _PTR( SObject ) obj ) +{ + _PTR(StudyBuilder) sb = studyDS()->NewBuilder(); + std::vector<_PTR(SObject)> aRefs = studyDS()->FindDependances( obj ); + for( int i=0, n=aRefs.size(); iGetFatherComponent()->ComponentDataType()==obj->GetFatherComponent()->ComponentDataType() ) + { + sb->RemoveReference( o ); + sb->RemoveObjectWithChildren( o ); + } + } +} + +//================================================================ +// Function : referencedToEntry +/*! Purpose : Return referenced entry from entry*/ +//================================================================ +QString SalomeApp_Study::referencedToEntry( const QString& entry ) const +{ + _PTR(SObject) obj = studyDS()->FindObjectID( entry.latin1() ); + _PTR(SObject) refobj; + + if( obj && obj->ReferencedObject( refobj ) ) + return refobj->GetID().c_str(); + return LightApp_Study::referencedToEntry( entry ); +} + +//================================================================ +// Function : componentDataType +/*! Purpose : Return component data type from entry*/ +//================================================================ +QString SalomeApp_Study::componentDataType( const QString& entry ) const +{ + _PTR(SObject) obj( studyDS()->FindObjectID( entry.latin1() ) ); + if ( !obj ) + return LightApp_Study::componentDataType( entry ); + return obj->GetFatherComponent()->ComponentDataType().c_str(); +} + +//================================================================ +// Function : componentDataType +/*! Purpose : Return component data type from entry*/ +//================================================================ +bool SalomeApp_Study::isComponent( const QString& entry ) const +{ + _PTR(SObject) obj( studyDS()->FindObjectID( entry.latin1() ) ); + return obj && QString( obj->GetID().c_str() ) == obj->GetFatherComponent()->GetID().c_str(); +} + +//================================================================ +// Function : children +/*! Purpose : Return entries of children of object*/ +//================================================================ +void SalomeApp_Study::children( const QString& entry, QStringList& child_entries ) const +{ + _PTR(SObject) SO = studyDS()->FindObjectID( entry.latin1() ); + _PTR(ChildIterator) anIter ( studyDS()->NewChildIterator( SO ) ); + anIter->InitEx( true ); + while( anIter->More() ) + { + _PTR(SObject) val( anIter->Value() ); + child_entries.append( val->GetID() ); + anIter->Next(); + } +} + +void SalomeApp_Study::components( QStringList& comps ) const +{ + for( _PTR(SComponentIterator) it ( studyDS()->NewComponentIterator() ); it->More(); it->Next() ) + { + _PTR(SComponent) aComponent ( it->Value() ); + if( aComponent && aComponent->ComponentDataType() == "Interface Applicative" ) + continue; // skip the magic "Interface Applicative" component + comps.append( aComponent->ComponentDataType() ); + } +}