Salome HOME
Fixes for bugs PAL7846, PAL7987. "Add dataflow in Study", "Put out-port value to...
[modules/superv.git] / src / SUPERVGUI / SUPERVGUI.cxx
1 //  SUPERV SUPERVGUI : GUI for Supervisor component
2 //
3 //  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
5 // 
6 //  This library is free software; you can redistribute it and/or 
7 //  modify it under the terms of the GNU Lesser General Public 
8 //  License as published by the Free Software Foundation; either 
9 //  version 2.1 of the License. 
10 // 
11 //  This library is distributed in the hope that it will be useful, 
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of 
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
14 //  Lesser General Public License for more details. 
15 // 
16 //  You should have received a copy of the GNU Lesser General Public 
17 //  License along with this library; if not, write to the Free Software 
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
19 // 
20 //  See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org 
21 //
22 //
23 //
24 //  File   : SUPERVGUI.cxx
25 //  Author : Francis KLOSS
26 //  Module : SUPERV
27
28 using namespace std;
29 #include "SUPERVGUI.h"
30
31 #include "QAD_Resource.h"
32 #include "QAD_FileDlg.h"
33 #include "QAD_Application.h"
34 #include "QAD_StudyFrame.h"
35 #include "QAD_RightFrame.h"
36 #include "QAD_LeftFrame.h"
37 #include "QAD_ViewFrame.h"
38 #include "QAD_ObjectBrowser.h"
39 #include "QAD_ObjectBrowserItem.h"
40 #include "QAD_MessageBox.h"
41
42 #include "SALOME_Selection.h"
43 #include "SALOME_ListIteratorOfListIO.hxx"
44 #include "SALOME_InteractiveObject.hxx"
45 #include "SALOMEGUI_ImportOperation.h"
46 #include "SALOMEGUI_NameDlg.h"            
47 #include "Utils_ORB_INIT.hxx"
48
49 #include CORBA_SERVER_HEADER(SALOMEDS_Attributes)
50
51
52 int SUPERVGUI::factory = 0;
53 SUPERVGUI Supervision("");
54
55
56 SUPERVGUI::SUPERVGUI(const QString& theName, QObject* theParent)
57      : SALOMEGUI( theName, theParent ),
58        desktop(0),
59        study(0),
60        browser(0)
61   //info(0)
62 {
63     Trace("SUPERVGUI::SUPERVGUI")
64     if (factory==0) {
65         factory = 1;
66         MESSAGE("SUPERVGUI Info : factory build");
67     } else {
68         MESSAGE("SUPERVGUI Error : another call to factory constructor");
69     };
70 }
71
72 SUPERVGUI::~SUPERVGUI() {
73     Trace("SUPERVGUI::~SUPERVGUI")
74     if (factory==1) {
75         factory = 0;
76         //if (!engine->_is_nil()) CORBA::release(engine);         
77         //info->close();
78         if (browser) {
79           if (browser->isVisible())
80             browser->close();
81           delete browser;
82         }
83         MESSAGE("SUPERVGUI Info : factory destroy");
84     } else {
85         MESSAGE("SUPERVGUI Error : another call to factory destructor");
86     };
87 }
88
89 void SUPERVGUI::init(QAD_Desktop* parent) {
90     Trace("SUPERVGUI::init")
91     if (desktop==0) {
92         desktop = parent;
93         study = desktop->getActiveStudy();
94         SALOME_NamingService* namingService = desktop->getNameService();
95         loadEngine(namingService);
96         browser = new SUPERVGUI_Service(namingService);
97         //info    = new SUPERVGUI_Information();
98         cursor  = desktop->cursor();
99         connect(desktop->getMainFrame(), SIGNAL(windowActivated(QWidget*)), this, SLOT(setMain(QWidget*)));
100
101         int anId = 300;
102         parent->menuBar()->changeItem(anId,parent->getComponentUserName("SUPERV"));
103         
104     };
105 }
106
107
108 QAD_StudyFrame* SUPERVGUI::createGraph() {
109   QAD_StudyFrame* aStudyFrame = study->newWindow3d(study->getNextStudyFrameName(),
110                                                    VIEW_GRAPHSUPERV, false);
111   if (aStudyFrame) {
112     connect(study, 
113             SIGNAL(supervStudyFrameClosing(QAD_ViewFrame*)), 
114             &Supervision, 
115             SLOT(onGraphClosed(QAD_ViewFrame*)));
116   }
117   return aStudyFrame;
118 }
119
120
121
122 void SUPERVGUI::loadEngine(SALOME_NamingService* namingService) {
123     Trace("SUPERVGUI::loadEngine")
124     SALOME_LifeCycleCORBA LCC(namingService);
125     Engines::Component_var objComponent = LCC.FindOrLoad_Component("SuperVisionContainer", "SUPERV");
126     if (CORBA::is_nil(objComponent)) {
127         QMessageBox::warning(QAD_Application::getDesktop(), tr("ERROR"), tr("MSG_CANT_LOAD_SUPERV"));
128         return;
129     };
130
131     SUPERV::SuperG_var aSuperVisionComponent;
132     aSuperVisionComponent = SUPERV::SuperG::_narrow(objComponent);
133     if (CORBA::is_nil(aSuperVisionComponent)) {
134         QMessageBox::warning(QAD_Application::getDesktop(), tr("ERROR"), tr("MSG_CANT_NARROW_SUPERV"));
135         return;
136     };
137
138     //    engine  = new SUPERV::SuperG_var;
139     engine = aSuperVisionComponent;
140 }
141 /*
142 bool SUPERVGUI::information(SUPERV_CNode node, bool isReadOnly) {
143     Trace("SUPERVGUI::information")
144     return(info->run(node, isReadOnly));
145 }
146 */
147 void SUPERVGUI::putInfo(const char* mess) {
148     Trace("SUPERVGUI::putInfo")
149     desktop->putInfo(mess);
150 }
151
152 QAD_Desktop* SUPERVGUI::getDesktop() {
153     Trace("SUPERVGUI::getDesktop")
154     return(desktop);
155 }
156
157 SUPERV_Engine SUPERVGUI::getEngine() {
158     Trace("SUPERVGUI::getEngine")
159     return(engine);
160 }
161
162 SUPERVGUI_Service* SUPERVGUI::getBrowser() {
163     Trace("SUPERVGUI::getBrowser")
164     return(browser);
165 }
166
167 QCursor SUPERVGUI::getCursor() {
168     Trace("SUPERVGUI::getCursor")
169     return(cursor);
170 }
171
172 SUPERVGUI_Main* SUPERVGUI::getMain() {
173     Trace("SUPERVGUI::getMain")
174     return main;
175 }
176
177
178 void SUPERVGUI::registerGraph(QString theName, SUPERVGUI_Main* theGraph){
179   theGraph->setHashCode(theName);
180   myGraphList.append(theGraph);
181 }
182
183
184 void SUPERVGUI::unregisterGraph(SUPERVGUI_Main* theGraph) {
185   SUPERVGUI_Main* aMain;
186   for (aMain = myGraphList.first(); aMain; aMain = myGraphList.next()) {
187     if (aMain == theGraph)
188       myGraphList.remove(aMain);
189   }
190 }
191
192
193 bool SUPERVGUI::isContains(QAD_Study* theStudy, const QString theKey) {
194   SUPERVGUI_Main* aMain;
195   for (aMain = myGraphList.first(); aMain; aMain = myGraphList.next()) {
196     if ((aMain->getStudy() == theStudy) && (aMain->getHashCode() == theKey))
197       return true;
198   }
199   return false;
200 }
201
202
203 void SUPERVGUI::onGraphClosed(QAD_ViewFrame* theViewFrame) {
204   if(SUPERVGraph_ViewFrame* supervFrame = dynamic_cast<SUPERVGraph_ViewFrame*>(theViewFrame)){
205     disconnect(study, 0 , this, 0);
206     SUPERVGraph_View* view = supervFrame->getViewWidget();
207     SUPERVGUI_Main* aGraph = dynamic_cast<SUPERVGUI_Main*>(view);
208     if (aGraph) {
209       unregisterGraph(aGraph);
210       SUPERV_Graph aDataFlow = aGraph->getDataflow();
211       if ( !SUPERV_isNull( aDataFlow ) ) {
212         if ( aDataFlow->IsExecuting() ) {
213           const int aMsgResult = QMessageBox::warning(QAD_Application::getDesktop(),
214                                                       tr("WARNING"), 
215                                                       tr("MSG_DF_RUNNING"), 
216                                                       tr("MSG_DF_EXECUTION"), 
217                                                       tr("MSG_DF_KILL"));
218           if ( aMsgResult == 1 ) {
219             // KILL EXECUTION
220             if ( aDataFlow->Kill() ) {
221               // Kill() sends KillEvent and KillState to SUPERVGUI_Thread
222               // while sets myIsActive flag to false when it receives such event/state
223               // after myIsActive is false it calls QThread::exit() to terminate.
224
225               // why while() { qApp->processEvents() } ?
226               // because: SUPERVGUI_Thread::run() receives events, and calls myMain->execute()
227               // method using SALOME_Event paradigm, ProcessVoidEvent() function - 
228               // it puts this event to the main application event loop, in which we are being now.
229               // So if we block main GUI application thread (by calling aGraph->getMyThread()->wait() here)
230               // then we will have a deadlock of 2 threads waiting for one another 
231               while (aGraph->getMyThread()->running()) 
232                 qApp->processEvents();
233             }
234           }
235           else { // BACKGROUND EXECUTION
236             emit KillMainThread(true); // set SUPERVGUI_Thread::myIsActive to false
237             while ( aGraph->getMyThread()->running() )
238               qApp->processEvents();
239           }
240         }
241         else { // EXECUTION IS FINISHED, JUST DESTROY THE SUPERVGUI_Thread object and return.
242           emit KillMainThread(true);
243           while ( aGraph->getMyThread()->running() ) 
244             qApp->processEvents();
245         }
246       }
247     }
248   }
249 }
250
251 void SUPERVGUI::setMain(QWidget* w) {
252   main = 0;
253   QAD_StudyFrame* aStudyFrame = dynamic_cast<QAD_StudyFrame*>(w);
254   if (!aStudyFrame) return;
255
256   study = aStudyFrame->getStudy();
257   if (!study) return;
258
259   QAD_ViewFrame* viewFrame = aStudyFrame->getRightFrame()->getViewFrame();
260   if(SUPERVGraph_ViewFrame* supervFrame = dynamic_cast<SUPERVGraph_ViewFrame*>(viewFrame)){
261     SUPERVGraph_View* view = supervFrame->getViewWidget();
262     if (view) {
263       main = dynamic_cast<SUPERVGUI_Main*>(view);
264       connect(&Supervision, SIGNAL(KillMainThread(bool)), main->getMyThread(), SLOT(KillThread(bool)));
265     }
266   }
267   Trace("SUPERVGUI::setMain - main: "<<main);
268 }
269
270 void SUPERVGUI::displayDataflow() {
271     Trace("SUPERVGUI::displayDataflow");
272     QAD_ObjectBrowser* aBrowser = ((QAD_StudyFrame*)(desktop->getMainFrame()->activeWindow()))->getLeftFrame()->getObjectBrowser();
273     SUPERV_Graph aDataFlow;
274     QString aIORName;
275
276     QAD_ObjectBrowserItem* item = (QAD_ObjectBrowserItem*)(aBrowser->getListView()->currentItem());
277     SALOMEDS::SObject_var aObj = desktop->getActiveStudy()->getStudyDocument()->FindObjectID(item->getEntry().latin1());
278     SALOMEDS::GenericAttribute_var anAttr;
279     if (aObj->FindAttribute(anAttr, "AttributeIOR")) {
280       SALOMEDS::AttributeIOR_var anIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
281       Standard_CString ior = anIOR->Value();
282       aIORName = ior;
283       if (isContains(study, aIORName)) {
284         if (QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), 
285                                  tr("MSG_GRAPH_DISPLAYED").arg(""), 
286                                  QMessageBox::Yes, QMessageBox::No) == QMessageBox::No)
287           return;
288       }
289       //aDataFlow = engine->getStreamGraph(ior);
290       aDataFlow = engine->getGraph(ior);
291       if (SUPERV_isNull(aDataFlow)) {
292         QMessageBox::warning(0, tr("ERROR"), tr("MSG_ACCESS_BAD_IOR"));
293         return;
294       }
295       /* ASV: 20.10.04: fix for 6896
296       if (aDataFlow->IsStreamGraph()) {
297         SUPERV_StreamGraph aDataFlowStream = aDataFlow->ToStreamGraph();
298         if (SUPERV_isNull(aDataFlowStream)) {
299           QMessageBox::warning(0, tr("ERROR"), tr("MSG_ACCESS_BAD_IOR"));
300           return;
301         }
302         aDataFlow = aDataFlowStream;
303       }
304       */
305     }
306     QAD_StudyFrame* aStudyFrame = createGraph();
307     SUPERVGraph_ViewFrame* aViewFrame = dynamic_cast<SUPERVGraph_ViewFrame*>
308       (aStudyFrame->getRightFrame()->getViewFrame());
309     if(aViewFrame) {
310       main = new SUPERVGUI_Main(aViewFrame, desktop, aDataFlow);
311       registerGraph(aIORName, main);
312       study->showFrame(aStudyFrame);
313     }
314 }
315
316
317 void SUPERVGUI::renameDataflow() {
318   SALOME_Selection* Sel = SALOME_Selection::Selection( study->getSelection() );
319   SALOME_ListIteratorOfListIO It( Sel->StoredIObjects() );
320   for ( ; It.More(); It.Next() ) {
321     Handle(SALOME_InteractiveObject) IObject = It.Value();
322     
323     SALOMEDS::Study_var aStudy = study->getStudyDocument();
324     SALOMEDS::SObject_var obj = aStudy->FindObjectID( IObject->getEntry() );
325     SALOMEDS::GenericAttribute_var anAttr;
326     SALOMEDS::AttributeName_var    aName;
327     if ( !obj->_is_nil() ) {
328       if (obj->FindAttribute(anAttr, "AttributeName")) {
329         aName = SALOMEDS::AttributeName::_narrow(anAttr);
330         QString nm = QString( aName->Value() );
331         nm = SALOMEGUI_NameDlg::getName( QAD_Application::getDesktop(), nm );
332         if ( !nm.isEmpty() ) {
333           // sak : 24.11.04 : fix for PAL6898 : if rename fails (study locked), 
334           // a message box is displayed, and cursor is "wait cursor".  We think that "wait cursor"
335           // is not neccessary here, because the rename operation is fast.
336           //QApplication::setOverrideCursor( Qt::waitCursor );
337           study->renameIObject( IObject, nm );
338           //QApplication::restoreOverrideCursor();
339         }
340       }
341     }
342   }
343 }
344
345 void SUPERVGUI::exportDataflow() {
346     Trace("SUPERVGUI::exportDataflow")
347     if ( main==0 ) {
348       QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_EXPORT"));
349     } 
350     else if ( SUPERV_isNull( main->getDataflow() ) ) { // should not normally happen..
351       QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_EXPORT"));
352     } 
353     else {
354       QString f = QAD_FileDlg::getFileName(QAD_Application::getDesktop(),
355                                            "",
356                                            "*.xml",
357                                            tr("TTL_EXPORT_DATAFLOW"),
358                                            false);
359       if ( !f.isEmpty() ) {
360         
361         // asv : bug [VSR Bugs and Improvements in Supervisor] 1.8 : when exporting a file, 
362         // a backup copy of an existing file must be created (in case Export fails..)
363         QString aBackupFile = SUPERVGUI::createBackupFile( f );
364
365         if ( main->getDataflow()->Export(f.latin1()) ) {
366           unregisterGraph(main);
367           registerGraph(f, main);
368
369           // remove a backup file if export was successfull
370           if ( !aBackupFile.isNull() && !aBackupFile.isEmpty() )
371             QFile::remove( aBackupFile );
372         }
373         else {
374           QMessageBox::warning(QAD_Application::getDesktop(), tr("ERROR"), tr("MSG_BAD_WRITING").arg(aBackupFile));
375         }
376       }
377     }
378 }
379
380 /** 
381  *If a file with theOriginalFileName exists, then the function tries to create 
382  * its backup copy of it (the_name + ".bakX", X = 0,1,2,..,99).  Returns backup file's name
383  * If a file with theOriginalFileName does not exist, or creation fails - Return empty string.
384  */
385 QString SUPERVGUI::createBackupFile( const QString& theOriginalFileName ) {
386   QString theBackupFileName("");
387   if ( QFile::exists( theOriginalFileName ) ) {
388     // 1. construct a backup file name
389     int i = 0;
390     do {
391       theBackupFileName = theOriginalFileName;
392       theBackupFileName += ".bak";
393       theBackupFileName += QString::number(i++);
394     } 
395     while ( QFile::exists( theBackupFileName ) && i < 100 ); // max 99 backup files
396     // if *.bak99 exists -- it will be overwritten 
397     
398     // 2. copy the original file to theBackupFileName
399     QString cmd( "cp \"");
400     cmd += theOriginalFileName;
401     cmd += "\" \"";
402     cmd += theBackupFileName;
403     cmd += "\"";
404     bool res = system( cmd.latin1() );
405     if ( res ) 
406       theBackupFileName = QString("");
407   }
408   return theBackupFileName;
409 }
410
411 void SUPERVGUI::newDataflow() {
412   createDataflow( New );
413 }
414
415 void SUPERVGUI::importDataflow() {
416   createDataflow( Import );
417 }
418
419 void SUPERVGUI::modifyDataflow() {
420   createDataflow( Modify );
421 }
422
423 bool SUPERVGUI::createDataflow( const NEW_DF_MODE mode ) {
424   Trace("SUPERVGUI::createDataflow, mode = " << mode );
425
426   // asv : 27.01.05 : fix for PAL7823 : if the study is locked - warn the user and return.
427   SALOMEDS::Study_var aStudy = study->getStudyDocument();
428   if ( aStudy->GetProperties()->IsLocked() ) {
429     QMessageBox::warning(QAD_Application::getDesktop(), tr("WRN_WARNING"), tr("WRN_STUDY_LOCKED"));
430     return false;
431   }
432
433   SUPERV::Graph_var aGraph;
434
435   QString f; // file name.  declared here because may be used below in error msg construction..
436   if ( mode == Import || mode == Modify ) { // 0. import or modify existing dataflow - select XML file
437     QString title = QString( "TLT_CREATE_DF_%1" ).arg( mode );
438     f = QAD_FileDlg::getFileName( QAD_Application::getDesktop(), "", "*.xml", tr( title ), true );
439     if ( f.isEmpty() ) // pressed Cancel in file select dialog
440       return false;
441     
442     // check if study already contains a graph imported from the same file
443     if ( isContains( study, f ) ) {
444       if ( QMessageBox::warning( QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_GRAPH_DISPLAYED").arg(f), 
445                                  QMessageBox::Yes, QMessageBox::No) == QMessageBox::No )
446         return false;
447     }
448     
449     // 1. create a graph
450     aGraph = ( mode == Import ) ? engine->StreamGraphE( f ) : engine->StreamGraph( f );        
451   }
452   else
453     aGraph = engine->StreamGraph( MAIN_NEW );
454
455   if ( CORBA::is_nil( aGraph ) ) {
456     QString msg( mode == New ? tr("MSG_CANT_CREATE_DF") : tr("MSG_BAD_FILE").arg(f) );
457     QAD_MessageBox::warn1( QAD_Application::getDesktop(), tr("ERROR"), tr(msg), tr("BUT_OK") );
458     return false;
459   }
460
461   // 2. create a ViewFrame object
462   QAD_StudyFrame* aStudyFrame = createGraph();
463   SUPERVGraph_ViewFrame* aViewFrame = dynamic_cast<SUPERVGraph_ViewFrame*>
464     (aStudyFrame->getRightFrame()->getViewFrame());
465   if ( aViewFrame ) {
466
467     // 3. bind Graph and ViewFrame == create SUPERVGUI_Main object
468     main = new SUPERVGUI_Main(aViewFrame, desktop, aGraph);
469     if ( mode == New )
470       main->addNode();
471     else
472       registerGraph( f, main );
473     study->showFrame(aStudyFrame);
474   }
475
476   return true;
477 }
478
479 void SUPERVGUI::reloadDataflow() {
480   Trace("SUPERVGUI::reloadDataflow");
481   if ( main )  
482     main->sync();
483   else 
484     QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_RELOAD"));
485 }
486
487 void SUPERVGUI::runDataflow() {
488   Trace("SUPERVGUI::runDataflow");
489   if ( main )
490     main->run( /*andSuspend=*/false );
491   else
492     QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_RUN"));
493 }
494
495 void SUPERVGUI::stepByStep() {
496   Trace("SUPERVGUI::stepByStep");
497   if ( main )
498     main->run( /*andSuspend=*/true );
499   else
500     QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_RUN"));
501 }
502
503 void SUPERVGUI::killDataflow() {
504   Trace("SUPERVGUI::killDataflow");
505   if ( main )
506     main->kill();
507   else
508     QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_KILL"));
509 }
510
511 void SUPERVGUI::suspendResumeDataflow() {
512   Trace("SUPERVGUI::suspendResumeDataflow");
513   if ( main )
514     main->suspendResume();
515   else
516     QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_SUSPEND"));
517 }
518
519 void SUPERVGUI::showComponents() {
520   Trace("SUPERVGUI::showComponents");
521   if ( main ) {
522     if ( main->isEditable() )
523       main->addNode();
524     else
525       QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOTEDITABLE"));
526   }
527   else
528     QMessageBox::warning(QAD_Application::getDesktop(), tr("WARNING"), tr("MSG_NOWINDOW_TO_ADD"));
529
530 }
531
532
533 bool SUPERVGUI::CustomPopup(QAD_Desktop* parent, QPopupMenu* popup, const QString& theContext, const QString& theParent, const QString& theObject) {
534   Trace("SUPERVGUI::customPopup");
535   Supervision.init(parent);
536   if(popup->count() > 3) {
537     // Temporary code: is to be deleted soon
538     popup->removeItem(QAD_Display_Popup_ID);
539     popup->removeItem(QAD_DisplayOnly_Popup_ID);
540     popup->removeItem(QAD_Erase_Popup_ID);
541     int id = popup->idAt(popup->count() - 1);
542     if (id < 0 && id != -1) popup->removeItem(id); // separator
543     // Temporary code end
544   }
545     SALOME_Selection* Sel = SALOME_Selection::Selection(study->getSelection() );
546     if ((Sel==NULL) || (Sel->IObjectCount() == 0)) return false;
547
548     if (Sel->IObjectCount() == 1) {
549       Handle(SALOME_InteractiveObject) anIObj = Sel->firstIObject();
550
551       // insert SUPERV-specific popup items here
552
553       bool isDataflow, ownObj;
554       whatIsSelected(anIObj, ownObj, isDataflow);
555       
556       if (isDataflow) {
557         popup->insertItem(tr( "MSG_RENAME" ), this, SLOT(renameDataflow()));
558         popup->insertItem("Display", this, SLOT(displayDataflow()));
559         popup->insertSeparator();
560       }
561       if (ownObj)
562         popup->insertItem(tr("MSG_DELETE"), this, SLOT(deleteObject()));
563     }
564     if (Sel->IObjectCount() > 1) {
565       int aIObjCount = 0;
566       SALOME_ListIteratorOfListIO It_forCheckOwner(Sel->StoredIObjects());
567       for(;It_forCheckOwner.More();It_forCheckOwner.Next()) {
568         Handle(SALOME_InteractiveObject) anIObj = It_forCheckOwner.Value();
569         bool aIsOwner, aIsDataflow;
570         whatIsSelected(anIObj, aIsOwner, aIsDataflow);
571         
572         if (aIsOwner) aIObjCount++;
573       }
574       if (aIObjCount == Sel->IObjectCount())  //all selected objects belong to Supervision
575         popup->insertItem(tr("MSG_DELETE"), this, SLOT(deleteObject()));
576     }
577   return(true);
578 }
579
580  
581
582 /** Returns:
583     theIsOwner = true if Selected object belongs to Suipervision.
584     theIsDataflow = true if Selected object is Dataflow
585 */
586 void SUPERVGUI::whatIsSelected(const Handle(SALOME_InteractiveObject)& theObj, bool& theIsOwner, bool& theIsDataflow) {
587   theIsOwner = false;
588   theIsDataflow = false;
589
590   if (theObj.IsNull()) return;
591   
592   SALOMEDS::Study_var aStudy = study->getStudyDocument();
593   SALOMEDS::SObject_var  obj = aStudy->FindObjectID( theObj->getEntry() );
594
595   if ( !obj->_is_nil() ) {
596     SALOMEDS::SComponent_var comp = obj->GetFatherComponent();
597     if ( !comp->_is_nil() ) {
598       SALOMEDS::GenericAttribute_var anAttr;
599       SALOMEDS::AttributeName_var    aName;
600       if (comp->FindAttribute(anAttr, "AttributeName")) {
601         aName = SALOMEDS::AttributeName::_narrow(anAttr);
602         QString compName(aName->Value());
603         //if (compName.compare(STUDY_SUPERVISION) == 0) {
604         if (compName.compare(QAD_Application::getDesktop()->getComponentUserName("SUPERV")) == 0) {
605           SALOMEDS::GenericAttribute_var anAttr;
606           if (obj->FindAttribute(anAttr, "AttributeIOR")) {
607             SALOMEDS::AttributeIOR_var anIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
608             //SUPERV_Graph aDataFlow = engine->getStreamGraph(anIOR->Value());
609             SUPERV_Graph aDataFlow = engine->getGraph(anIOR->Value());
610             if (!SUPERV_isNull(aDataFlow)) {
611               if (aDataFlow->IsStreamGraph()) {
612                 if (!SUPERV_isNull(aDataFlow->ToStreamGraph()))
613                   theIsDataflow = true;
614               }
615               else
616                 theIsDataflow = true;
617             }
618           }
619           CORBA::String_var anObjectID = obj->GetID();
620           CORBA::String_var aComponentID = comp->GetID();
621           if (strcmp(anObjectID, aComponentID)) theIsOwner = true;          
622         }
623       }
624     }
625   }
626 }
627
628 void SUPERVGUI::deleteObject() {
629   SALOME_Selection* Sel = SALOME_Selection::Selection(study->getSelection() );
630   if ((Sel==NULL) || (Sel->IObjectCount() == 0)) return;
631    
632   // sak : 24.11.04 : fix for PAL6899 : if the study is locked - warn the user and return.
633   SALOMEDS::Study_var aStudy = study->getStudyDocument();
634   if ( aStudy->GetProperties()->IsLocked() ) {
635     QMessageBox::warning(QAD_Application::getDesktop(), tr("WRN_WARNING"), tr("WRN_STUDY_LOCKED"));
636     return;
637   }
638
639   // sak : 24.11.04 : fix for PAL6901 : Incorrect deletion of the objects : pressing ESC button
640   // emitted "YES" button click, now it is corrected, and treated as "NO" button click.
641   if (QMessageBox::warning(QAD_Application::getDesktop(),
642                            tr("WARNING"),
643                            tr("MSG_ASK_DELETE"),
644                            QMessageBox::No, QMessageBox::Yes) != QMessageBox::Yes)
645     return;
646    
647   SALOME_ListIteratorOfListIO It(Sel->StoredIObjects());
648   for(;It.More();It.Next()) {
649     Handle(SALOME_InteractiveObject) anIObj = It.Value();
650     bool aIsOwner, aIsDataflow;
651     whatIsSelected(anIObj, aIsOwner, aIsDataflow);
652     
653     SALOMEDS::SObject_var  aObj = aStudy->FindObjectID( anIObj->getEntry() );
654     if (!aObj->_is_nil()) {
655       QAD_Operation* op = new SALOMEGUI_ImportOperation( study );
656       SALOMEDS::StudyBuilder_var aBuilder = aStudy->NewBuilder();
657       op->start();
658       aBuilder->RemoveObjectWithChildren(aObj);
659       op->finish();
660     }
661   }
662   Sel->ClearIObjects() ; 
663 }
664
665 bool SUPERVGUI::OnGUIEvent(int command, QAD_Desktop* parent) {
666   Supervision.init(parent);
667   switch (command) {
668   case 301: 
669     Supervision.importDataflow();
670     return(false);
671     
672   case 302: 
673     Supervision.exportDataflow();
674     return(false);
675     
676   case 303: 
677     Supervision.newDataflow();
678     return(false);
679     
680   case 304: 
681     Supervision.modifyDataflow();
682     return(false);
683     
684   case 305:
685     Supervision.reloadDataflow();
686     return(false);
687     
688   case 306:
689     Supervision.runDataflow();
690     return(false);
691     
692   case 307: 
693     Supervision.killDataflow();
694     return(false);
695     
696   case 308:
697     Supervision.suspendResumeDataflow();
698     return(false);
699     
700   case 309: 
701     Supervision.showComponents();
702     return(false);
703     
704   case 310: 
705     Supervision.stepByStep();
706     return(false);
707     
708   default: 
709     QMessageBox::warning(QAD_Application::getDesktop(), "Supervision Error", "Unknown Command From Salome");
710     return(false);
711   }
712 }
713
714 bool SUPERVGUI::SetSettings(QAD_Desktop* parent) {
715   Trace("SUPERVGUI::SetSettings");
716   Supervision.init(parent);
717   return(true);
718 }
719
720 void SUPERVGUI::DefinePopup(QString& theContext, QString& theParent, QString& theObject) {
721   theObject  = "";
722   theContext = "";
723 }
724
725 bool SUPERVGUI::ActiveStudyChanged(QAD_Desktop* parent) {
726   Trace("SUPERVGUI::activeStudyChanged");
727   study = desktop->getActiveStudy();
728   return true;
729 }
730
731 void SUPERVGUI::SupportedViewType (int* buffer, int bufferSize)
732 {
733   if (!buffer || !bufferSize) return;
734   buffer[0] = (int)VIEW_GRAPHSUPERV;
735 }
736
737 extern "C"
738 {
739   Standard_EXPORT SALOMEGUI* GetComponentGUI() {
740     return &Supervision;
741   }
742 }