Salome HOME
df3f7b7d7f27730d9d718e2df7e6e731179644f6
[modules/paravis.git] / src / PVGUI / PVGUI_Module.cxx
1 // PARAVIS : ParaView wrapper SALOME module
2 //
3 // Copyright (C) 2010-2012  CEA/DEN, EDF R&D
4 //
5 // This library is free software; you can redistribute it and/or
6 // modify it under the terms of the GNU Lesser General Public
7 // License as published by the Free Software Foundation; either
8 // version 2.1 of the License.
9 //
10 // This library is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13 // Lesser General Public License for more details.
14 //
15 // You should have received a copy of the GNU Lesser General Public
16 // License along with this library; if not, write to the Free Software
17 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
18 //
19 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
20 //
21 // File   : PVGUI_Module.cxx
22 // Author : Julia DOROVSKIKH
23
24 #include <Standard_math.hxx>  // E.A. must be included before Python.h to fix compilation on windows
25 #ifdef HAVE_FINITE
26 #undef HAVE_FINITE            // VSR: avoid compilation warning on Linux : "HAVE_FINITE" redefined
27 #endif
28 #include <vtkPython.h> // Python first
29 #include "PVGUI_Module.h"
30
31 #include "SALOMEconfig.h"
32 #ifdef WITH_VISU
33 #include CORBA_CLIENT_HEADER(VISU_Gen)
34 #endif
35 #include CORBA_SERVER_HEADER(SALOMEDS)
36
37
38 #include "PARAVIS_Gen_i.hh"
39
40 #include "PV_Tools.h"
41
42 #include "PVGUI_ViewModel.h"
43 #include "PVGUI_ViewManager.h"
44 #include "PVGUI_ViewWindow.h"
45 #include "PVGUI_Tools.h"
46 #include "PVGUI_ParaViewSettingsPane.h"
47 #include "PVGUI_OutputWindowAdapter.h"
48
49 #include <SUIT_DataBrowser.h>
50 #include <SUIT_Desktop.h>
51 #include <SUIT_MessageBox.h>
52 #include <SUIT_ResourceMgr.h>
53 #include <SUIT_Session.h>
54 #include <SUIT_OverrideCursor.h>
55 #include <SUIT_ExceptionHandler.h>
56
57 // SALOME Includes
58 #include "SALOME_LifeCycleCORBA.hxx"
59 #include "SALOMEDS_SObject.hxx"
60
61 #include "LightApp_SelectionMgr.h"
62 #include "LightApp_NameDlg.h"
63
64 #include <SalomeApp_Application.h>
65 #include <SalomeApp_Study.h>
66 #include <SALOME_ListIO.hxx>
67 #include <SALOMEDS_Tool.hxx>
68 #include <PyInterp_Dispatcher.h>
69
70 #include <QtxActionMenuMgr.h>
71 #include <QtxActionToolMgr.h>
72
73 #include <QAction>
74 #include <QApplication>
75 #include <QCursor>
76 #include <QDir>
77 #include <QFile>
78 #include <QFileInfo>
79 #include <QIcon>
80 #include <QInputDialog>
81 #include <QMenu>
82 #include <QStatusBar>
83 #include <QString>
84 #include <QStringList>
85 #include <QTimer>
86 #include <QToolBar>
87 #include <QTextStream>
88 #include <QShortcut>
89 #include <QDockWidget>
90 #include <QHelpEngine>
91
92 #include <pqApplicationCore.h>
93 #include <pqPVApplicationCore.h>
94 #include <pqActiveView.h>
95 #include <pqObjectBuilder.h>
96 #include <pqOptions.h>
97 #include <pqRenderView.h>
98 #include <pqServer.h>
99 #include <pqUndoStack.h>
100 #include <pqVCRController.h>
101 #include <pqTabbedMultiViewWidget.h>
102 #include <pqPipelineSource.h>
103 #include <pqActiveObjects.h>
104 #include <vtkProcessModule.h>
105 #include <vtkSMSession.h>
106 #include <vtkPVSession.h>
107 #include <vtkPVProgressHandler.h>
108 #include <pqParaViewBehaviors.h>
109 #include <pqHelpReaction.h>
110 #include <vtkOutputWindow.h>
111 #include <pqPluginManager.h>
112 //#include <vtkPVPluginInformation.h>
113 #include "pqInterfaceTracker.h"
114 #include <pqSettings.h>
115 #include <pqPythonDialog.h>
116 #include <pqPythonManager.h>
117 #include <pqPythonShell.h>
118 //#include <pqBrandPluginsLoader.h>
119 #include <pqLoadDataReaction.h>
120 #include <vtkEventQtSlotConnect.h>
121 #include <pqPythonScriptEditor.h>
122 #include <pqStandardSummaryPanelImplementation.h>
123 #include <pqCollaborationBehavior.h>
124 #include <pqDataRepresentation.h>
125 #include <pqPipelineRepresentation.h>
126 #include <pqLookupTableManager.h>
127 #include <pqDisplayColorWidget.h>
128 #include <pqColorToolbar.h>
129 #include <pqScalarBarVisibilityReaction.h>
130 #include <pqStandardPropertyWidgetInterface.h>
131 #include <pqMultiServerBehavior.h>
132 #include <pqViewStreamingBehavior.h>
133
134 #include <PARAVIS_version.h>
135
136 #include <vtkPVConfig.h>
137
138 #include <PVGUI_MatplotlibMathTextUtilities.h>
139
140 #include CORBA_SERVER_HEADER(SALOME_ModuleCatalog)
141
142 /*
143  * Make sure all the kits register their classes with vtkInstantiator.
144  * Since ParaView uses Tcl wrapping, all of VTK is already compiled in
145  * anyway.  The instantiators will add no more code for the linker to
146  * collect.
147  */
148
149 //#include <vtkCommonInstantiator.h>
150 //#include <vtkFilteringInstantiator.h>
151 //#include <vtkGenericFilteringInstantiator.h>
152 //#include <vtkIOInstantiator.h>
153 //#include <vtkImagingInstantiator.h>
154 //#include <vtkInfovisInstantiator.h>
155 //#include <vtkGraphicsInstantiator.h>
156
157 //#include <vtkRenderingInstantiator.h>
158 //#include <vtkVolumeRenderingInstantiator.h>
159 //#include <vtkHybridInstantiator.h>
160 //#include <vtkParallelInstantiator.h>
161
162 #include <pqAlwaysConnectedBehavior.h>
163 #include <pqApplicationCore.h>
164 #include <pqAutoLoadPluginXMLBehavior.h>
165 #include <pqCommandLineOptionsBehavior.h>
166 #include <pqCrashRecoveryBehavior.h>
167 #include <pqDataTimeStepBehavior.h>
168 #include <pqDefaultViewBehavior.h>
169 #include <pqDeleteBehavior.h>
170 #include <pqObjectPickingBehavior.h>
171 #include <pqPersistentMainWindowStateBehavior.h>
172 #include <pqPipelineContextMenuBehavior.h>
173 #include <pqPluginActionGroupBehavior.h>
174 #include <pqPluginDockWidgetsBehavior.h>
175 #include <pqPluginManager.h>
176 #include <pqPVNewSourceBehavior.h>
177 #include <pqSpreadSheetVisibilityBehavior.h>
178 #include <pqStandardViewModules.h>
179 #include <pqUndoRedoBehavior.h>
180 #include <pqViewFrameActionsBehavior.h>
181 #include <pqServerManagerObserver.h>
182
183 #include <vtkClientServerInterpreterInitializer.h>
184
185
186 //----------------------------------------------------------------------------
187 pqPVApplicationCore* PVGUI_Module::MyCoreApp = 0;
188 //PVGUI_OutputWindowAdapter* PVGUI_Module::pqImplementation::OutputWindowAdapter = 0;
189 //QPointer<pqHelpWindow> PVGUI_Module::pqImplementation::helpWindow = 0;
190
191 PVGUI_Module* ParavisModule = 0;
192
193 /*!
194   \mainpage
195
196   <h2>Building and installing PARAVIS</h2>
197   As any other SALOME module, PARAVIS requires PARAVIS_ROOT_DIR environment variable to be set to PARAVIS
198   installation directory.
199   Other variables needed for correct detection of ParaView location:
200   \li PVHOME - points at the ParaView installation directory tree
201   \li PVVERSION - number of ParaView version
202
203   It also requires common SALOME environment including GUI_ROOT_DIR and other prerequsites.
204
205
206   PARAVIS module can be launched using the following commands:
207   \li Full SALOME configuration
208   \code
209   runSalome --modules="PARAVIS"
210   \endcode
211
212   <h2>ParaView GUI integration</h2>
213   <h3>ParaView GUI integration overview</h3>
214
215   The main idea is to reuse ParaView GUI internal logic as much as possible, providing a layer 
216   between it and SALOME GUI that hides the following SALOME GUI implementation details from ParaView:
217
218   \li SALOME GUI executable and Qt event loop
219   \li SALOME GUI desktop
220   \li Dock windows areas
221   \li SALOME menu and toolbar managers
222
223   Major part of the integration is implemented in PVGUI_Module class.
224
225   <h3>ParaView client initalization</h3>
226
227   ParaView client initalization is performed when an instance of PVGUI_Module class has been created 
228   and \link PVGUI_Module::initialize() PVGUI_Module::initialize()\endlink method is called by SALOME GUI.
229   The actual client start-up is done in \link PVGUI_Module::pvInit() PVGUI_Module::pvInit()\endlink method. 
230   
231
232   <h3>Multi-view manager</h3>
233
234   SALOME GUI requires that each kind of view be implemnted with help of (at least) three classes. For ParaView multi-view manager 
235   these are:
236
237   \li PVGUI_ViewManager - view manager class
238   \li PVGUI_Viewer      - view model class
239   \li PVGUI_ViewWindow  - view window class that acts as a parent for %pqViewManager
240
241   Single instances of PVGUI_ViewManager and PVGUI_ViewWindow classes are created by \link PVGUI_Module::showView() 
242   PVGUI_Module::showView()\endlink method upon the first PARAVIS module activation. The same method hides the multi-view manager 
243   when the module is deactivated (the user switches to another module or a study is closed). 
244   A special trick is used to make PVGUI_ViewWindow the parent of %pqViewManager widget. It is created initally by %pqMainWindowCore
245   with the desktop as a parent, so when it is shown PVGUI_ViewWindow instance is passed to its setParent() method. In  
246   \link PVGUI_ViewWindow::~PVGUI_ViewWindow() PVGUI_ViewWindow::~PVGUI_ViewWindow()\endlink the parent is nullified to avoid deletion
247   of %pqViewManager widget that would break %pqMainWindowCore class.
248
249   <h3>ParaView plugins</h3>
250   ParaView server and client plugins are managed by %pqMainWindowCore slots that has full access to PARAVIS menus and toolbars. 
251   As a result they appears automatically in PARAVIS menus and toolbars if loaded successfully.
252 */
253
254 /*!
255   \class PVGUI_Module
256   \brief Implementation 
257          SALOME module wrapping ParaView GUI.
258 */
259
260
261 /*
262   Fix for the issue 21730: [CEA 596] Slice of polyhedron in PARAVIS returns no cell.
263   Wrap vtkEDFCutter filter.
264 */
265
266 extern "C" void vtkEDFCutterCS_Initialize(vtkClientServerInterpreter*);
267 static void vtkEDFHelperInit();
268
269 void vtkEDFHelperInit(vtkClientServerInterpreter* interp){
270     vtkEDFCutterCS_Initialize(interp);
271 }
272
273 void vtkEDFHelperInit() {
274     vtkClientServerInterpreterInitializer::GetInitializer()->
275         RegisterCallback(&vtkEDFHelperInit);
276 }
277
278
279   _PTR(SComponent)
280   ClientFindOrCreateParavisComponent(_PTR(Study) theStudyDocument)
281   {
282     _PTR(SComponent) aSComponent = theStudyDocument->FindComponent("PARAVIS");
283     if (!aSComponent) {
284       _PTR(StudyBuilder) aStudyBuilder = theStudyDocument->NewBuilder();
285       aStudyBuilder->NewCommand();
286       int aLocked = theStudyDocument->GetProperties()->IsLocked();
287       if (aLocked) theStudyDocument->GetProperties()->SetLocked(false);
288       aSComponent = aStudyBuilder->NewComponent("PARAVIS");
289       _PTR(GenericAttribute) anAttr =
290         aStudyBuilder->FindOrCreateAttribute(aSComponent, "AttributeName");
291       _PTR(AttributeName) aName (anAttr);
292
293       CORBA::ORB_var anORB = PARAVIS::PARAVIS_Gen_i::GetORB();
294       SALOME_NamingService *NamingService = new SALOME_NamingService( anORB );
295       CORBA::Object_var objVarN = NamingService->Resolve("/Kernel/ModulCatalog");
296       SALOME_ModuleCatalog::ModuleCatalog_var Catalogue =
297         SALOME_ModuleCatalog::ModuleCatalog::_narrow(objVarN);
298       SALOME_ModuleCatalog::Acomponent_var Comp = Catalogue->GetComponent( "PARAVIS" );
299       if (!Comp->_is_nil()) {
300         aName->SetValue(Comp->componentusername());
301       }
302
303       anAttr = aStudyBuilder->FindOrCreateAttribute(aSComponent, "AttributePixMap");
304       _PTR(AttributePixMap) aPixmap (anAttr);
305       aPixmap->SetPixMap( "pqAppIcon16.png" );
306
307       // Create Attribute parameters for future using
308       anAttr = aStudyBuilder->FindOrCreateAttribute(aSComponent, "AttributeParameter");
309
310
311       PARAVIS::PARAVIS_Gen_var aPARAVIS = PARAVIS::PARAVIS_Gen_i::GetParavisGenImpl()->_this();
312
313       aStudyBuilder->DefineComponentInstance(aSComponent, aPARAVIS->GetIOR());
314       if (aLocked) theStudyDocument->GetProperties()->SetLocked(true);
315       aStudyBuilder->CommitCommand();
316     }
317     return aSComponent;
318   }
319
320 /*!
321   Clean up function; used to stop ParaView progress events when
322   exception is caught by global exception handler.
323 */
324 void paravisCleanUp()
325 {
326   if ( pqApplicationCore::instance() ) {
327     pqServer* s = pqApplicationCore::instance()->getActiveServer();
328     if ( s ) s->session()->GetProgressHandler()->CleanupPendingProgress();
329   }
330 }
331
332 /*!
333   \brief Constructor. Sets the default name for the module.
334 */
335 PVGUI_Module::PVGUI_Module()
336   : SalomeApp_Module( "PARAVIS" ),
337     //    Implementation( 0 ),
338     mySelectionControlsTb( -1 ),
339     mySourcesMenuId( -1 ),
340     myFiltersMenuId( -1 ),
341     myMacrosMenuId(-1),
342     myToolbarsMenuId(-1),
343     myRecentMenuId(-1),
344     myOldMsgHandler(0),
345     myTraceWindow(0),
346     myStateCounter(0)
347 {
348 #ifdef HAS_PV_DOC
349   Q_INIT_RESOURCE( PVGUI );
350 #endif
351   ParavisModule = this;
352
353   // Clear old macros
354   QString aDestPath = QString( "%1/.config/%2/Macros" ).arg( QDir::homePath() ).arg( QApplication::applicationName() );
355   QStringList aFilter;
356   aFilter << "*.py";
357
358   QDir aDestDir(aDestPath);
359   QStringList aDestFiles = aDestDir.entryList(aFilter, QDir::Files);
360   foreach (QString aStr, aDestFiles) {
361     aDestDir.remove(aStr);
362   }
363 }
364
365 /*!
366   \brief Destructor.
367 */
368 PVGUI_Module::~PVGUI_Module()
369 {
370 }
371
372
373
374 /*!
375   \brief Initialize module. Creates menus, prepares context menu, etc.
376   \param app SALOME GUI application instance
377 */
378 void PVGUI_Module::initialize( CAM_Application* app )
379 {
380   //VTN: Disable conflict with python initialization for MatPlot.
381   PVGUI_MatplotlibMathTextUtilities::Disable();
382
383   SalomeApp_Module::initialize( app );
384
385   // Create ParaViS actions
386   createActions();
387   // Create ParaViS menus
388   createMenus();
389
390   // Uncomment to debug ParaView initialization
391   // "aa" used instead of "i" as GDB doesn't like "i" variables :)
392   /*
393   int aa = 1;
394   while( aa ){
395     aa = aa;
396   }
397   */
398   
399   // Initialize ParaView client
400   pvInit();
401
402   // Create GUI elements (menus, toolbars, dock widgets)
403   //if ( !Implementation ){
404     SalomeApp_Application* anApp = getApp();
405     SUIT_Desktop* aDesktop = anApp->desktop();
406
407     // connect(aDesktop, SIGNAL()
408
409     // Remember current state of desktop toolbars
410     QList<QToolBar*> foreignToolbars = aDesktop->findChildren<QToolBar*>();
411
412     // Simulate ParaView client main window
413     //Implementation = new pqImplementation( aDesktop );
414
415     setupDockWidgets();
416     
417     pvCreateActions();
418     pvCreateToolBars();
419     pvCreateMenus();
420
421     QList<QDockWidget*> activeDocks = aDesktop->findChildren<QDockWidget*>();
422     QList<QMenu*> activeMenus = aDesktop->findChildren<QMenu*>();
423
424     // new pqParaViewBehaviors(anApp->desktop(), this);
425     // Has to be replaced in order to exclude using of pqQtMessageHandlerBehaviour
426     //  Start pqParaViewBehaviors
427     // Register ParaView interfaces.
428     //pqPluginManager* pgm = pqApplicationCore::instance()->getPluginManager();
429     pqInterfaceTracker* pgm = pqApplicationCore::instance()->interfaceTracker();
430
431     // * adds support for standard paraview views.
432     pgm->addInterface(new pqStandardViewModules(pgm));
433     pgm->addInterface(new pqStandardSummaryPanelImplementation(pgm));
434     pgm->addInterface(new pqStandardPropertyWidgetInterface(pgm));
435
436     // Load plugins distributed with application.
437     pqApplicationCore::instance()->loadDistributedPlugins();
438
439     // Define application behaviors.
440     //new pqQtMessageHandlerBehavior(this);
441     new pqDataTimeStepBehavior(this);
442     new pqViewFrameActionsBehavior(this);
443     new pqSpreadSheetVisibilityBehavior(this);
444     new pqPipelineContextMenuBehavior(this);
445     new pqDefaultViewBehavior(this);
446     new pqAlwaysConnectedBehavior(this);
447     new pqPVNewSourceBehavior(this);
448     new pqDeleteBehavior(this);
449     new pqUndoRedoBehavior(this);
450     new pqCrashRecoveryBehavior(this);
451     new pqAutoLoadPluginXMLBehavior(this);
452     new pqPluginDockWidgetsBehavior(aDesktop);
453     //new pqVerifyRequiredPluginBehavior(this);
454     new pqPluginActionGroupBehavior(aDesktop);
455     //new pqFixPathsInStateFilesBehavior(this);
456     new pqCommandLineOptionsBehavior(this);
457     new pqPersistentMainWindowStateBehavior(aDesktop);
458     new pqObjectPickingBehavior(aDesktop);
459     new pqCollaborationBehavior(this);
460     new pqMultiServerBehavior(this);
461     new pqViewStreamingBehavior(this);
462
463     // Setup quick-launch shortcuts.
464     QShortcut *ctrlSpace = new QShortcut(Qt::CTRL + Qt::Key_Space, aDesktop);
465     QObject::connect(ctrlSpace, SIGNAL(activated()),
466       pqApplicationCore::instance(), SLOT(quickLaunch()));
467     QShortcut *altSpace = new QShortcut(Qt::ALT + Qt::Key_Space, aDesktop);
468     QObject::connect(altSpace, SIGNAL(activated()),
469       pqApplicationCore::instance(), SLOT(quickLaunch()));
470     //  End pqParaViewBehaviors
471
472     // Find Plugin Dock Widgets
473     QList<QDockWidget*> currentDocks = aDesktop->findChildren<QDockWidget*>();
474     QList<QDockWidget*>::iterator i;
475     for (i = currentDocks.begin(); i != currentDocks.end(); ++i) {
476       if(!activeDocks.contains(*i)) {
477         myDockWidgets[*i] = false; // hidden by default
478         (*i)->hide();
479       }
480     }
481
482     // Find Plugin Menus
483     QList<QMenu*> currentMenus = aDesktop->findChildren<QMenu*>();
484     QList<QMenu*>::iterator im;
485     for (im = currentMenus.begin(); im != currentMenus.end(); ++im) {
486       if(!activeMenus.contains(*im)) {
487         myMenus.append(*im);
488       }
489     }
490
491     SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
492     QString aPath = resMgr->stringValue("resources", "PARAVIS", QString());
493     if (!aPath.isNull()) {
494       MyCoreApp->loadConfiguration(aPath + QDir::separator() + "ParaViewFilters.xml");
495       MyCoreApp->loadConfiguration(aPath + QDir::separator() + "ParaViewReaders.xml");
496       MyCoreApp->loadConfiguration(aPath + QDir::separator() + "ParaViewSources.xml");
497       MyCoreApp->loadConfiguration(aPath + QDir::separator() + "ParaViewWriters.xml");
498     }
499      
500     // Force creation of engine
501     PARAVIS::GetParavisGen(this);
502     updateObjBrowser();
503
504     // Find created toolbars
505     QCoreApplication::processEvents();
506
507     QList<QToolBar*> allToolbars = aDesktop->findChildren<QToolBar*>();
508     foreach(QToolBar* aBar, allToolbars) {
509       if (!foreignToolbars.contains(aBar)) {
510         myToolbars[aBar] = true;
511         myToolbarBreaks[aBar] = false;
512         aBar->setVisible(false);
513         aBar->toggleViewAction()->setVisible(false);
514       }
515     }
516     //}
517
518   updateMacros();
519  
520   // we need to start trace after connection is done
521   connect(pqApplicationCore::instance()->getObjectBuilder(), SIGNAL(finishedAddingServer(pqServer*)), 
522           this, SLOT(onFinishedAddingServer(pqServer*)));
523
524   connect(pqApplicationCore::instance()->getObjectBuilder(), SIGNAL(dataRepresentationCreated(pqDataRepresentation*)), 
525           this, SLOT(onDataRepresentationCreated(pqDataRepresentation*)));
526
527
528   SUIT_ResourceMgr* aResourceMgr = SUIT_Session::session()->resourceMgr();
529   bool isStop = aResourceMgr->booleanValue( "PARAVIS", "stop_trace", false );
530   // start timer to activate trace in a proper moment
531   if(!isStop) 
532     startTimer( 50 );
533
534   this->VTKConnect = vtkEventQtSlotConnect::New();
535   
536   vtkProcessModule* pm = vtkProcessModule::GetProcessModule();
537   if(pm) {
538     vtkPVSession* pvs = dynamic_cast<vtkPVSession*>(pm->GetSession());
539     if(pvs) {
540       vtkPVProgressHandler* ph = pvs->GetProgressHandler();
541       if(ph) {
542         this->VTKConnect->Connect(ph, vtkCommand::StartEvent,
543                                   this, SLOT(onStartProgress()));
544         this->VTKConnect->Connect(ph, vtkCommand::EndEvent,
545                                   this, SLOT(onEndProgress()));
546       }
547     }
548   }
549   
550   connect(&pqActiveObjects::instance(),
551           SIGNAL(representationChanged(pqRepresentation*)),
552           this, SLOT(onRepresentationChanged(pqRepresentation*)));
553 }
554
555 void PVGUI_Module::onStartProgress()
556 {
557   QApplication::setOverrideCursor(Qt::WaitCursor);
558 }
559
560 void PVGUI_Module::onEndProgress()
561 {
562   QApplication::restoreOverrideCursor();
563 }
564
565 void PVGUI_Module::onFinishedAddingServer(pqServer* /*server*/)
566 {
567   SUIT_ResourceMgr* aResourceMgr = SUIT_Session::session()->resourceMgr();
568   bool isStop = aResourceMgr->booleanValue( "PARAVIS", "stop_trace", false );
569   if(!isStop) 
570     startTimer( 50 );
571 }
572
573 void PVGUI_Module::onDataRepresentationCreated(pqDataRepresentation* data) {
574   if(!data)
575     return;
576   
577   if(!data->getLookupTable())
578     return;
579   
580   SUIT_ResourceMgr* aResourceMgr = SUIT_Session::session()->resourceMgr();
581   if(!aResourceMgr)
582     return;
583
584   bool visible = aResourceMgr->booleanValue( "PARAVIS", "show_color_legend", false );
585   pqLookupTableManager* lut_mgr = pqApplicationCore::instance()->getLookupTableManager();
586   
587   if(lut_mgr) {
588     lut_mgr->setScalarBarVisibility(data,visible);
589   }
590
591   connect(data, SIGNAL(dataUpdated()), this, SLOT(onDataRepresentationUpdated()));
592 }
593
594 void PVGUI_Module::onDataRepresentationUpdated() {
595   SalomeApp_Study* activeStudy = dynamic_cast<SalomeApp_Study*>(application()->activeStudy());
596   if(!activeStudy) return;
597   
598   activeStudy->Modified();
599 }
600
601 void PVGUI_Module::onVariableChanged(pqVariableType t, const QString) {
602   
603   pqDisplayColorWidget* colorWidget = qobject_cast<pqDisplayColorWidget*>(sender());
604   if( !colorWidget )
605     return;
606
607   if( t == VARIABLE_TYPE_NONE )
608     return;
609
610   SUIT_ResourceMgr* aResourceMgr = SUIT_Session::session()->resourceMgr();
611   
612   if(!aResourceMgr)
613     return;
614
615   bool visible = aResourceMgr->booleanValue( "PARAVIS", "show_color_legend", false );
616   
617   if(!visible)
618     return;
619   
620   /*//VTN: getRepresentation is protected
621   pqDataRepresentation* data  = colorWidget->getRepresentation();
622
623   if( !data->getLookupTable() )
624     return;
625
626   pqLookupTableManager* lut_mgr = pqApplicationCore::instance()->getLookupTableManager();
627
628   if(lut_mgr) {
629     lut_mgr->setScalarBarVisibility(data,visible);
630   }
631   */
632   pqColorToolbar* colorTooBar = qobject_cast<pqColorToolbar*>(colorWidget->parent());
633   if( !colorTooBar )
634     return;
635
636   pqScalarBarVisibilityReaction* scalarBarVisibility = colorTooBar->findChild<pqScalarBarVisibilityReaction *>();
637   if(scalarBarVisibility) {
638     scalarBarVisibility->setScalarBarVisibility(visible);
639   }
640 }
641
642
643 /*!
644   \brief Launches a tracing of current server
645 */
646 void PVGUI_Module::timerEvent(QTimerEvent* te )
647 {
648 #ifndef WNT
649   PyInterp_Dispatcher* aDispatcher = PyInterp_Dispatcher::Get();
650   if ( !aDispatcher->IsBusy() ) {
651     pqPythonManager* manager = qobject_cast<pqPythonManager*>
652       ( pqApplicationCore::instance()->manager( "PYTHON_MANAGER" ) );
653     if ( manager )  {
654       pqPythonDialog* pyDiag = manager->pythonShellDialog();
655       if ( pyDiag ) {
656         pqPythonShell* shell = pyDiag->shell();
657         if ( shell ) {
658           QString script = "from paraview import smtrace\nsmtrace.start_trace()\n";
659           shell->executeScript(script);
660           killTimer( te->timerId() );
661         }
662       }
663     }
664   }
665 #endif
666 }
667   
668 void PVGUI_Module::updateMacros()
669 {
670   pqPythonManager* aPythonManager = pqPVApplicationCore::instance()->pythonManager();
671   if(!aPythonManager)  {
672     return;
673   }
674   
675   QString aRootDir = getenv("PARAVIS_ROOT_DIR");
676
677   QString aSourcePath = aRootDir + "/bin/salome/Macro";
678
679   QStringList aFilter;
680   aFilter << "*.py";
681
682   QDir aSourceDir(aSourcePath);
683   QStringList aSourceFiles = aSourceDir.entryList(aFilter, QDir::Files);
684   foreach (QString aStr, aSourceFiles) {
685     aPythonManager->addMacro(aSourcePath + "/" + aStr);
686   }
687 }
688
689
690 /*!
691   \brief Get list of compliant dockable GUI elements
692   \param m map to be filled in ("type":"default_position")
693 */
694 void PVGUI_Module::windows( QMap<int, int>& m ) const
695 {
696   m.insert( LightApp_Application::WT_ObjectBrowser, Qt::LeftDockWidgetArea );
697   m.insert( LightApp_Application::WT_PyConsole, Qt::BottomDockWidgetArea );
698   // ParaView diagnostic output redirected here
699   m.insert( LightApp_Application::WT_LogWindow, Qt::BottomDockWidgetArea );
700 }
701
702 /*!
703   \brief Static method, performs initialization of ParaView session.
704   \return \c true if ParaView has been initialized successfully, otherwise false
705 */
706 bool PVGUI_Module::pvInit()
707 {
708   //  if ( !pqImplementation::Core ){
709   if ( ! MyCoreApp) {
710     // Obtain command-line arguments
711     int argc = 0;
712     char** argv = 0;
713     QString aOptions = getenv("PARAVIS_OPTIONS");
714     QStringList aOptList = aOptions.split(":", QString::SkipEmptyParts);
715     argv = new char*[aOptList.size() + 1];
716     QStringList args = QApplication::arguments();
717     argv[0] = (args.size() > 0)? strdup(args[0].toLatin1().constData()) : strdup("paravis");
718     argc++;
719
720     foreach (QString aStr, aOptList) {
721       argv[argc] = strdup( aStr.toLatin1().constData() );
722       argc++;
723     }
724     MyCoreApp = new pqPVApplicationCore (argc, argv);
725     if (MyCoreApp->getOptions()->GetHelpSelected() ||
726         MyCoreApp->getOptions()->GetUnknownArgument() ||
727         MyCoreApp->getOptions()->GetErrorMessage() ||
728         MyCoreApp->getOptions()->GetTellVersion()) {
729       return false;
730       }
731
732     /* VTN: Looks like trash. For porting see branded_paraview_initializer.cxx.in
733     // Not sure why this is needed. Andy added this ages ago with comment saying
734     // needed for Mac apps. Need to check that it's indeed still required.
735     QDir dir(QApplication::applicationDirPath());
736     dir.cdUp();
737     dir.cd("Plugins");
738     QApplication::addLibraryPath(dir.absolutePath());
739     // Load required application plugins.
740     QString plugin_string = "";
741     QStringList plugin_list = plugin_string.split(';',QString::SkipEmptyParts);
742     pqBrandPluginsLoader loader;
743     if (loader.loadPlugins(plugin_list) == false) {
744       printf("Failed to load required plugins for this application\n");
745       return false;
746     }
747
748     // Load optional plugins.
749     plugin_string = "";
750     plugin_list = plugin_string.split(';',QString::SkipEmptyParts);
751     loader.loadPlugins(plugin_list, true); //quietly skip not-found plugins.
752     */
753     // End of Initializer code
754
755     vtkOutputWindow::SetInstance(PVGUI_OutputWindowAdapter::New());
756     
757     new pqTabbedMultiViewWidget(); // it registers as "MULTIVIEW_WIDGET on creation
758     
759     for (int i = 0; i < argc; i++)
760       free(argv[i]);
761     delete[] argv;
762   }
763   
764   return true;
765 }
766  
767 /*!
768   \brief Shows (toShow = true) or hides ParaView view window
769 */
770 void PVGUI_Module::showView( bool toShow )
771 {
772   SalomeApp_Application* anApp = getApp();
773   PVGUI_ViewManager* viewMgr =
774     dynamic_cast<PVGUI_ViewManager*>( anApp->getViewManager( PVGUI_Viewer::Type(), false ) );
775   if ( !viewMgr ) {
776     viewMgr = new PVGUI_ViewManager( anApp->activeStudy(), anApp->desktop() );
777     anApp->addViewManager( viewMgr );
778     connect( viewMgr, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
779              anApp, SLOT( onCloseView( SUIT_ViewManager* ) ) );
780   }
781
782   PVGUI_ViewWindow* pvWnd = dynamic_cast<PVGUI_ViewWindow*>( viewMgr->getActiveView() );
783   if ( !pvWnd ) {
784     pvWnd = dynamic_cast<PVGUI_ViewWindow*>( viewMgr->createViewWindow() );
785   }
786
787   pvWnd->setShown( toShow );
788   if ( toShow ) pvWnd->setFocus();
789 }
790
791 /*!
792   \brief Slot to show help for proxy.
793 */
794 void PVGUI_Module::showHelpForProxy( const QString& groupname, const QString& proxyname )
795 {
796   pqHelpReaction::showProxyHelp(groupname, proxyname);
797 }
798
799
800 /*!
801   \brief Slot to show the waiting state.
802 */
803 void PVGUI_Module::onPreAccept()
804 {
805   getApp()->desktop()->statusBar()->showMessage(tr("STB_PREACCEPT"));
806   QApplication::setOverrideCursor(QCursor(Qt::WaitCursor));
807 }
808
809 /*!
810   \brief Slot to show the ready state.
811 */
812 void PVGUI_Module::onPostAccept()
813 {
814   getApp()->desktop()->statusBar()->showMessage(tr("STB_POSTACCEPT"), 2000);
815   QTimer::singleShot(0, this, SLOT(endWaitCursor()));
816 }
817
818 /*!
819   \brief Slot to switch off wait cursor.
820 */
821 void PVGUI_Module::endWaitCursor()
822 {
823   QApplication::restoreOverrideCursor();
824 }
825
826 /*!
827   \brief Returns the ParaView multi-view manager.
828 */
829 pqTabbedMultiViewWidget* PVGUI_Module::getMultiViewManager() const
830 {
831   return qobject_cast<pqTabbedMultiViewWidget*>(pqApplicationCore::instance()->manager("MULTIVIEW_WIDGET"));
832 }
833
834
835 static void ParavisMessageOutput(QtMsgType type, const char *msg)
836 {
837   switch(type)
838     {
839   case QtDebugMsg:
840     vtkOutputWindow::GetInstance()->DisplayText(msg);
841     break;
842   case QtWarningMsg:
843     vtkOutputWindow::GetInstance()->DisplayErrorText(msg);
844     break;
845   case QtCriticalMsg:
846     vtkOutputWindow::GetInstance()->DisplayErrorText(msg);
847     break;
848   case QtFatalMsg:
849     vtkOutputWindow::GetInstance()->DisplayErrorText(msg);
850     break;
851     }
852 }
853
854
855
856 /*!
857   \brief Activate module.
858   \param study current study
859   \return \c true if activaion is done successfully or 0 to prevent
860   activation on error
861 */
862 bool PVGUI_Module::activateModule( SUIT_Study* study )
863 {
864   myOldMsgHandler = qInstallMsgHandler(ParavisMessageOutput);
865   
866   SUIT_ExceptionHandler::addCleanUpRoutine( paravisCleanUp );
867
868   bool isDone = SalomeApp_Module::activateModule( study );
869   if ( !isDone ) return false;
870
871   showView( true );
872   if ( mySourcesMenuId != -1 ) menuMgr()->show(mySourcesMenuId);
873   if ( myFiltersMenuId != -1 ) menuMgr()->show(myFiltersMenuId);
874   if ( myFiltersMenuId != -1 ) menuMgr()->show(myMacrosMenuId);
875   if ( myFiltersMenuId != -1 ) menuMgr()->show(myToolbarsMenuId);
876   setMenuShown( true );
877   setToolShown( true );
878
879   restoreDockWidgetsState();
880
881   QMenu* aMenu = menuMgr()->findMenu( myRecentMenuId );
882   if(aMenu) {
883     QList<QAction*> anActns = aMenu->actions();
884     for (int i = 0; i < anActns.size(); ++i) {
885       QAction* a = anActns.at(i);
886       if(a)
887         a->setVisible(true);
888     }
889   }
890
891   QList<QMenu*>::iterator it;
892   for (it = myMenus.begin(); it != myMenus.end(); ++it) {
893     QAction* a = (*it)->menuAction();
894     if(a)
895       a->setVisible(true);
896   }
897
898   if ( myRecentMenuId != -1 ) menuMgr()->show(myRecentMenuId);
899
900   ClientFindOrCreateParavisComponent(PARAVIS::GetCStudy(this));
901
902   return isDone;
903 }
904
905
906 /*!
907   \brief Deactivate module.
908   \param study current study
909   \return \c true if deactivaion is done successfully or 0 to prevent
910   deactivation on error
911 */
912 bool PVGUI_Module::deactivateModule( SUIT_Study* study )
913 {
914   QMenu* aMenu = menuMgr()->findMenu( myRecentMenuId );
915   if(aMenu) {
916     QList<QAction*> anActns = aMenu->actions();
917     for (int i = 0; i < anActns.size(); ++i) {
918       QAction* a = anActns.at(i);
919       if(a)
920         a->setVisible(false);
921     }
922   }
923
924   QList<QMenu*>::iterator it;
925   for (it = myMenus.begin(); it != myMenus.end(); ++it) {
926     QAction* a = (*it)->menuAction();
927     if(a)
928       a->setVisible(false);
929   }
930
931   QList<QDockWidget*> aStreamingViews = application()->desktop()->findChildren<QDockWidget*>("pqStreamingControls");
932   foreach(QDockWidget* aView, aStreamingViews) {
933     if (!myDockWidgets.contains(aView))
934       myDockWidgets[aView] = aView->isVisible();
935   }
936
937   /*if (pqImplementation::helpWindow) {
938     pqImplementation::helpWindow->hide();
939     }*/
940   showView( false );
941   // hide menus
942   menuMgr()->hide(myRecentMenuId);
943   menuMgr()->hide(mySourcesMenuId);
944   menuMgr()->hide(myFiltersMenuId);
945   menuMgr()->hide(myMacrosMenuId);
946   menuMgr()->hide(myToolbarsMenuId);
947   setMenuShown( false );
948   setToolShown( false );
949
950
951   saveDockWidgetsState();
952
953   SUIT_ExceptionHandler::removeCleanUpRoutine( paravisCleanUp );
954
955   if (myOldMsgHandler)
956     qInstallMsgHandler(myOldMsgHandler);
957
958   return SalomeApp_Module::deactivateModule( study );
959 }
960
961
962 /*!
963   \brief Called when application is closed.
964
965   Process finalize application functionality from ParaView in order to save server settings
966   and nullify application pointer if the application is being closed.
967
968   \param theApp application
969 */
970 void PVGUI_Module::onApplicationClosed( SUIT_Application* theApp )
971 {
972   pqApplicationCore::instance()->settings()->sync();
973   int aAppsNb = SUIT_Session::session()->applications().size();
974   if (aAppsNb == 1) {
975     deleteTemporaryFiles();
976     MyCoreApp->deleteLater();
977   }
978   CAM_Module::onApplicationClosed(theApp);
979 }
980
981
982 /*!
983   \brief Called when study is closed.
984
985   Removes data model from the \a study.
986
987   \param study study being closed
988 */
989 void PVGUI_Module::studyClosed(SUIT_Study* study)
990 {
991   clearParaviewState();
992
993   SalomeApp_Module::studyClosed(study);
994 }
995
996 /*!
997   \brief Called when study is opened.
998 */
999 void PVGUI_Module::onModelOpened()
1000 {
1001   _PTR(Study) studyDS = PARAVIS::GetCStudy(this);
1002   if(!studyDS) {
1003     return;
1004   }
1005   
1006   _PTR(SComponent) paravisComp = 
1007     studyDS->FindComponent(PARAVIS::GetParavisGen(this)->ComponentDataType());
1008   if(!paravisComp) {
1009     return;
1010   }
1011
1012   _PTR(ChildIterator) anIter(studyDS->NewChildIterator(paravisComp));
1013   for (; anIter->More(); anIter->Next()) {
1014     _PTR(SObject) aSObj = anIter->Value();
1015     _PTR(GenericAttribute) anAttr;
1016     if (!aSObj->FindAttribute(anAttr, "AttributeLocalID")) {
1017       continue;
1018     }
1019     _PTR(AttributeLocalID) anID(anAttr);
1020     if (anID->Value() == PVSTATEID) {
1021       myStateCounter++;
1022     }
1023   }
1024 }
1025
1026 /*!
1027   \brief Returns IOR of current engine
1028 */
1029 QString PVGUI_Module::engineIOR() const
1030 {
1031   CORBA::String_var anIOR = PARAVIS::GetParavisGen(this)->GetIOR();
1032   return QString(anIOR.in());
1033 }
1034
1035
1036 /*!
1037   \brief Open file of format supported by ParaView
1038 */
1039 void PVGUI_Module::openFile(const char* theName)
1040 {
1041   QStringList aFiles;
1042   aFiles<<theName;
1043   pqLoadDataReaction::loadData(aFiles);
1044 }
1045
1046 void PVGUI_Module::executeScript(const char *script)
1047 {
1048 #ifndef WNT
1049   pqPythonManager* manager = qobject_cast<pqPythonManager*>(
1050                              pqApplicationCore::instance()->manager("PYTHON_MANAGER"));
1051   if (manager)  {
1052     pqPythonDialog* pyDiag = manager->pythonShellDialog();
1053     if (pyDiag) {
1054       pyDiag->runString(script);  
1055       }
1056     }
1057 #endif
1058 }
1059
1060 /*!
1061   \brief Returns trace string
1062 */
1063 static const QString MYReplaceStr("paraview.simple");
1064 static const QString MYReplaceImportStr("except: from pvsimple import *");
1065 QString PVGUI_Module::getTraceString()
1066 {
1067   QString traceString;
1068 #ifndef WNT
1069   pqPythonManager* manager = qobject_cast<pqPythonManager*>(
1070                              pqApplicationCore::instance()->manager("PYTHON_MANAGER"));
1071   if (manager)  {
1072     pqPythonDialog* pyDiag = manager->pythonShellDialog();
1073     if (pyDiag) {
1074       pyDiag->runString("from paraview import smtrace\n"
1075                         "__smtraceString = smtrace.get_trace_string()\n");
1076       pyDiag->shell()->makeCurrent();
1077       PyObject* main_module = PyImport_AddModule((char*)"__main__");
1078       PyObject* global_dict = PyModule_GetDict(main_module);
1079       PyObject* string_object = PyDict_GetItemString(global_dict, "__smtraceString");
1080       char* string_ptr = string_object ? PyString_AsString(string_object) : 0;
1081       if (string_ptr)  {
1082         traceString = string_ptr;
1083       }
1084       pyDiag->shell()->releaseControl();
1085     }
1086   }
1087   if ((!traceString.isNull()) && traceString.length() != 0) {
1088     int aPos = traceString.indexOf(MYReplaceStr);
1089     while (aPos != -1) {
1090       traceString = traceString.replace(aPos, MYReplaceStr.length(), "pvsimple");
1091       aPos = traceString.indexOf(MYReplaceStr, aPos);
1092     }
1093     int aImportPos = traceString.indexOf(MYReplaceImportStr);
1094     if(aImportPos != -1)
1095       {
1096       traceString = traceString.replace(aImportPos, MYReplaceImportStr.length(), "except:\n  import pvsimple\n  from pvsimple import *");
1097       }
1098   }
1099 #endif
1100   return traceString;
1101 }
1102
1103 /*!
1104   \brief Saves trace string to disk file
1105 */
1106 void PVGUI_Module::saveTrace(const char* theName)
1107 {
1108   QFile file(theName);
1109   if (!file.open(QIODevice::WriteOnly | QIODevice::Text)) {
1110     MESSAGE( "Could not open file:" << theName );
1111     return;
1112   }
1113   QTextStream out(&file);
1114   out << getTraceString();
1115   file.close();
1116 }
1117
1118 /*!
1119   \brief Saves ParaView state to a disk file
1120 */
1121 void PVGUI_Module::saveParaviewState(const char* theFileName)
1122 {
1123   pqApplicationCore::instance()->saveState(theFileName);
1124 }
1125
1126 /*!
1127   \brief Delete all objects for Paraview Pipeline Browser
1128 */
1129 void PVGUI_Module::clearParaviewState()
1130 {
1131   QAction* deleteAllAction = action(DeleteAllId);
1132   if (deleteAllAction) {
1133     deleteAllAction->activate(QAction::Trigger);
1134   }
1135 }
1136
1137 /*!
1138   \brief Restores ParaView state from a disk file
1139
1140   If toClear == true, the current ojects will be deleted
1141 */
1142 void PVGUI_Module::loadParaviewState(const char* theFileName)
1143 {
1144   pqApplicationCore::instance()->loadState(theFileName, getActiveServer());
1145 }
1146
1147 /*!
1148   \brief Imports MED data from VISU module by data entry
1149 */
1150 void PVGUI_Module::onImportFromVisu(QString theEntry)
1151 {
1152 #ifdef WITH_VISU
1153   SUIT_OverrideCursor aWaitCursor;
1154
1155   // get active study
1156   SalomeApp_Study* activeStudy = dynamic_cast<SalomeApp_Study*>(application()->activeStudy());
1157   if(!activeStudy) return;
1158
1159   // get SALOMEDS client study 
1160   _PTR(Study) aStudy = activeStudy->studyDS();
1161   if(!aStudy) return;
1162
1163   // find VISU component in a study
1164   _PTR(SComponent) aVisuComp = aStudy->FindComponent( "VISU" );
1165   if(!aVisuComp) return;
1166
1167   // get SObject client by entry
1168   _PTR(SObject) aSObj = aStudy->FindObjectID(qPrintable(theEntry));
1169   if (!aSObj) return;
1170
1171   // get CORBA SObject
1172   SALOMEDS_SObject* aSObject = _CAST(SObject, aSObj);
1173   if ( !aSObject ) return;
1174
1175   // load VISU engine
1176   SALOME_NamingService* aNamingService = SalomeApp_Application::namingService();
1177   SALOME_LifeCycleCORBA aLCC(aNamingService);
1178
1179   Engines::EngineComponent_var aComponent = aLCC.FindOrLoad_Component("FactoryServer","VISU");
1180   VISU::VISU_Gen_var aVISU = VISU::VISU_Gen::_narrow(aComponent);
1181   if(CORBA::is_nil(aVISU)) return;
1182
1183   _PTR(StudyBuilder) aStudyBuilder = aStudy->NewBuilder();
1184   aStudyBuilder->LoadWith( aVisuComp, SalomeApp_Application::orb()->object_to_string(aVISU) );
1185
1186   // get VISU result object
1187   CORBA::Object_var aResultObject = aSObject->GetObject();
1188   if (CORBA::is_nil(aResultObject)) return;
1189   VISU::Result_var aResult = VISU::Result::_narrow( aResultObject );
1190   if (CORBA::is_nil(aResult)) return;
1191
1192   // export VISU result to the MED file
1193   std::string aTmpDir = SALOMEDS_Tool::GetTmpDir();
1194   std::string aFileName = aSObject->GetName();
1195   std::string aFilePath = aTmpDir + aFileName;
1196
1197   if (aResult->ExportMED(aFilePath.c_str())) {
1198     openFile(aFilePath.c_str());
1199     myTemporaryFiles.append(QString(aFilePath.c_str()));
1200   }
1201 #else
1202   MESSAGE("Visu module is not found.");
1203 #endif
1204 }
1205
1206 /*!
1207   \brief Deletes temporary files created during import operation from VISU
1208 */
1209 void PVGUI_Module::deleteTemporaryFiles()
1210 {
1211   foreach(QString aFile, myTemporaryFiles) {
1212     if (QFile::exists(aFile)) {
1213       QFile::remove(aFile);
1214     }
1215   }
1216 }
1217
1218
1219 /*!
1220   \brief Returns current active ParaView server
1221 */
1222 pqServer* PVGUI_Module::getActiveServer()
1223 {
1224   return pqApplicationCore::instance()->getActiveServer();
1225 }
1226
1227
1228 /*!
1229   \brief Creates PARAVIS preference pane 
1230 */
1231 void PVGUI_Module::createPreferences()
1232 {
1233   // Paraview settings tab
1234   int aParaViewSettingsTab = addPreference( tr( "TIT_PVIEWSETTINGS" ) );
1235   int aPanel = addPreference(QString(), aParaViewSettingsTab, LightApp_Preferences::UserDefined, "PARAVIS", "");
1236   setPreferenceProperty(aPanel, "content", (qint64)(new PVGUI_ParaViewSettingsPane()));
1237
1238   // Paravis settings tab
1239   int aParaVisSettingsTab = addPreference( tr( "TIT_PVISSETTINGS" ) );
1240   addPreference( tr( "PREF_STOP_TRACE" ), aParaVisSettingsTab, LightApp_Preferences::Bool, "PARAVIS", "stop_trace");
1241
1242   int aSaveType = addPreference(tr( "PREF_SAVE_TYPE_LBL" ), aParaVisSettingsTab,
1243                                 LightApp_Preferences::Selector,
1244                                 "PARAVIS", "savestate_type");
1245   QList<QVariant> aIndices;
1246   QStringList aStrings;
1247   aIndices<<0<<1<<2;
1248   aStrings<<tr("PREF_SAVE_TYPE_0");
1249   aStrings<<tr("PREF_SAVE_TYPE_1");
1250   aStrings<<tr("PREF_SAVE_TYPE_2");
1251   setPreferenceProperty(aSaveType, "strings", aStrings);
1252   setPreferenceProperty(aSaveType, "indexes", aIndices);
1253
1254   //rnv: imp 21712: [CEA 581] Preference to display legend by default 
1255   int aDispColoreLegend = addPreference( tr( "PREF_SHOW_COLOR_LEGEND" ), aParaVisSettingsTab,
1256                                          LightApp_Preferences::Bool, "PARAVIS", "show_color_legend");
1257 }
1258
1259 /*!
1260   \brief Creates ParaViS context menu popup
1261 */
1262 void PVGUI_Module::contextMenuPopup(const QString& theClient, QMenu* theMenu, QString& theTitle)
1263 {
1264   SalomeApp_Module::contextMenuPopup(theClient, theMenu, theTitle);
1265   
1266   // Check if we are in Object Browser
1267   SUIT_DataBrowser* ob = getApp()->objectBrowser();
1268   bool isOBClient = (ob && theClient == ob->popupClientType());
1269   if (!isOBClient) {
1270     return;
1271   }
1272
1273   // Get list of selected objects
1274   LightApp_SelectionMgr* aSelectionMgr = getApp()->selectionMgr();
1275   SALOME_ListIO aListIO;
1276   aSelectionMgr->selectedObjects(aListIO);
1277   if (aListIO.Extent() == 1 && aListIO.First()->hasEntry()) {
1278     QString entry = QString(aListIO.First()->getEntry());
1279     
1280     // Get active study
1281     SalomeApp_Study* activeStudy = 
1282       dynamic_cast<SalomeApp_Study*>(getApp()->activeStudy());
1283     if(!activeStudy) {
1284       return;
1285     }
1286
1287     // Get SALOMEDS client study 
1288     _PTR(Study) studyDS = activeStudy->studyDS();
1289     if(!studyDS) {
1290       return;
1291     }
1292
1293     QString paravisDataType(PARAVIS::GetParavisGen(this)->ComponentDataType());
1294     if(activeStudy && activeStudy->isComponent(entry) && 
1295        activeStudy->componentDataType(entry) == paravisDataType) {
1296       // ParaViS module object
1297       theMenu->addSeparator();
1298       theMenu->addAction(action(SaveStatePopupId));
1299     }
1300     else {
1301       // Try to get state object
1302       _PTR(SObject) stateSObj = 
1303         studyDS->FindObjectID(entry.toLatin1().constData());
1304       if (!stateSObj) {
1305         return;
1306       }
1307       
1308       // Check local id
1309       _PTR(GenericAttribute) anAttr;
1310       if (!stateSObj->FindAttribute(anAttr, "AttributeLocalID")) {
1311         return;
1312       }
1313
1314       _PTR(AttributeLocalID) anID(anAttr);
1315       
1316       if (anID->Value() == PVSTATEID) {
1317         // Paraview state object
1318         theMenu->addSeparator();
1319         theMenu->addAction(action(AddStatePopupId));
1320         theMenu->addAction(action(CleanAndAddStatePopupId));
1321         theMenu->addSeparator();
1322         theMenu->addAction(action(ParaVisRenameId));
1323         theMenu->addAction(action(ParaVisDeleteId));
1324       }
1325     }
1326   }
1327 }
1328
1329 void PVGUI_Module::onShowTrace()
1330 {
1331   if (!myTraceWindow) {
1332     myTraceWindow = new pqPythonScriptEditor(getApp()->desktop());
1333   }
1334   myTraceWindow->setText(getTraceString());
1335   myTraceWindow->show();
1336   myTraceWindow->raise();
1337   myTraceWindow->activateWindow();
1338 }
1339
1340 /*!
1341   \brief Show ParaView view.
1342 */
1343 void PVGUI_Module::onNewParaViewWindow()
1344 {
1345   showView(true);
1346 }
1347
1348 /*!
1349   \brief Save state under the module root object.
1350 */
1351 void PVGUI_Module::onSaveMultiState()
1352 {
1353   // Create state study object
1354   
1355   // Get SALOMEDS client study
1356   _PTR(Study) studyDS = PARAVIS::GetCStudy(this);
1357   if(!studyDS) {
1358     return;
1359   }
1360   
1361   _PTR(SComponent) paravisComp = 
1362     studyDS->FindComponent(PARAVIS::GetParavisGen(this)->ComponentDataType());
1363   if(!paravisComp) {
1364     return;
1365   }
1366
1367   // Unlock the study if it is locked
1368   bool isLocked = studyDS->GetProperties()->IsLocked();
1369   if (isLocked) {
1370     studyDS->GetProperties()->SetLocked(false);
1371   }
1372   
1373   QString stateName = tr("SAVED_PARAVIEW_STATE_NAME") + 
1374     QString::number(myStateCounter + 1);
1375
1376   _PTR(StudyBuilder) studyBuilder = studyDS->NewBuilder();
1377   _PTR(SObject) newSObj = studyBuilder->NewObject(paravisComp);
1378
1379   // Set name
1380   _PTR(GenericAttribute) anAttr;
1381   anAttr = studyBuilder->FindOrCreateAttribute(newSObj, "AttributeName");
1382   _PTR(AttributeName) nameAttr(anAttr);
1383   
1384   nameAttr->SetValue(stateName.toLatin1().constData());
1385
1386   // Set local id
1387   anAttr = studyBuilder->FindOrCreateAttribute(newSObj, "AttributeLocalID");
1388   _PTR(AttributeLocalID) localIdAttr(anAttr);
1389   
1390   localIdAttr->SetValue(PVSTATEID);
1391
1392   // Set file name
1393   QString stateEntry = QString::fromStdString(newSObj->GetID());
1394  
1395   // File name for state saving
1396   QString tmpDir = QString::fromStdString(SALOMEDS_Tool::GetTmpDir());
1397   QString fileName = QString("%1_paravisstate:%2").arg(tmpDir, 
1398                                                        stateEntry);
1399
1400   anAttr = studyBuilder->FindOrCreateAttribute(newSObj, "AttributeString");
1401   _PTR(AttributeString) stringAttr(anAttr);
1402   
1403   stringAttr->SetValue(fileName.toLatin1().constData());
1404
1405   // Lock the study back if necessary
1406   if (isLocked) {
1407     studyDS->GetProperties()->SetLocked(true);
1408   }
1409   
1410   // Save state
1411   saveParaviewState(fileName.toLatin1().constData());
1412   myTemporaryFiles.append(fileName);
1413   
1414   // Increment the counter
1415   myStateCounter++;
1416
1417   updateObjBrowser();
1418 }
1419
1420 /*!
1421   \brief Restore the selected state by merging with the current one.
1422 */
1423 void PVGUI_Module::onAddState()
1424 {
1425   loadSelectedState(false);
1426 }
1427
1428 /*!
1429   \brief Clean the current state and restore the selected one.
1430 */
1431 void PVGUI_Module::onCleanAddState()
1432 {
1433   loadSelectedState(true);
1434 }
1435
1436 /*!
1437   \brief Rename the selected object.
1438 */
1439 void PVGUI_Module::onRename()
1440 {
1441   LightApp_SelectionMgr* aSelectionMgr = getApp()->selectionMgr();
1442   SALOME_ListIO aListIO;
1443   aSelectionMgr->selectedObjects(aListIO);
1444   
1445   if (aListIO.Extent() == 1 && aListIO.First()->hasEntry()) {
1446     std::string entry = aListIO.First()->getEntry();
1447     
1448     // Get SALOMEDS client study 
1449     _PTR(Study) studyDS = PARAVIS::GetCStudy(this);
1450     if(!studyDS) {
1451       return;
1452     }
1453     
1454     // Unlock the study if it is locked
1455     bool isLocked = studyDS->GetProperties()->IsLocked();
1456     if (isLocked) {
1457       studyDS->GetProperties()->SetLocked(false);
1458     }
1459     
1460     // Rename the selected state object
1461     _PTR(SObject) stateSObj = studyDS->FindObjectID(entry);
1462     if (!stateSObj) {
1463       return;
1464     }
1465     
1466     _PTR(GenericAttribute) anAttr;
1467     if (stateSObj->FindAttribute(anAttr, "AttributeName")) {
1468       _PTR(AttributeName) nameAttr (anAttr);
1469       QString newName = 
1470         LightApp_NameDlg::getName(getApp()->desktop(), nameAttr->Value().c_str());
1471       if (!newName.isEmpty()) {
1472         nameAttr->SetValue(newName.toLatin1().constData());
1473         aListIO.First()->setName(newName.toLatin1().constData());
1474       }
1475     }
1476     
1477     // Lock the study back if necessary
1478     if (isLocked) {
1479       studyDS->GetProperties()->SetLocked(true);
1480     }
1481     
1482     // Update object browser
1483     updateObjBrowser();
1484     
1485   }
1486 }
1487
1488 /*!
1489   \brief Delete the selected objects.
1490 */
1491 void PVGUI_Module::onDelete()
1492 {
1493   LightApp_SelectionMgr* aSelectionMgr = getApp()->selectionMgr();
1494   SALOME_ListIO aListIO;
1495   aSelectionMgr->selectedObjects(aListIO);
1496   
1497   if (aListIO.Extent() == 1 && aListIO.First()->hasEntry()) {
1498     std::string entry = aListIO.First()->getEntry();
1499     
1500     // Get SALOMEDS client study 
1501     _PTR(Study) studyDS = PARAVIS::GetCStudy(this);
1502     if(!studyDS) {
1503       return;
1504     }
1505     
1506     // Unlock the study if it is locked
1507     bool isLocked = studyDS->GetProperties()->IsLocked();
1508     if (isLocked) {
1509       studyDS->GetProperties()->SetLocked(false);
1510     }
1511     
1512     // Remove the selected state from the study
1513     _PTR(StudyBuilder) studyBuilder = studyDS->NewBuilder();
1514     _PTR(SObject) stateSObj = studyDS->FindObjectID(entry);
1515     studyBuilder->RemoveObject(stateSObj);
1516     
1517     // Lock the study back if necessary
1518     if (isLocked) {
1519       studyDS->GetProperties()->SetLocked(true);
1520     }
1521     
1522     // Update object browser
1523     updateObjBrowser();
1524   }
1525 }
1526
1527 /*!
1528   \brief Discover help project files from the resources.
1529   \return name of the help file. 
1530 */
1531 QString PVGUI_Module::getHelpFileName() {
1532   QString aPVHome(getenv("PVHOME"));
1533   if (aPVHome.isNull()) {
1534     qWarning("Wariable PVHOME is not defined");
1535     return QString();
1536   }
1537   QChar aSep = QDir::separator();
1538   //PARAVIEW_VERSION from the vtkPVConfig.h file
1539   QString aFileName =  aPVHome + aSep + "share" + aSep + "doc" + aSep + "paraview-"+ PARAVIEW_VERSION + aSep + "paraview.qch";
1540   return aFileName;
1541 }
1542
1543
1544 /*!
1545   \brief Load selected paraview state
1546
1547   If toClear == true, the current state will be cleared
1548 */
1549 void PVGUI_Module::loadSelectedState(bool toClear)
1550 {
1551   QString fileName;
1552
1553   LightApp_SelectionMgr* aSelectionMgr = getApp()->selectionMgr();
1554   SALOME_ListIO aListIO;
1555   aSelectionMgr->selectedObjects(aListIO);
1556   
1557   if (aListIO.Extent() == 1 && aListIO.First()->hasEntry()) {
1558     std::string entry = aListIO.First()->getEntry();
1559     
1560     // Get SALOMEDS client study 
1561     _PTR(Study) studyDS = PARAVIS::GetCStudy(this);
1562     if(!studyDS) {
1563       return;
1564     }
1565
1566     // Check local id
1567     _PTR(SObject) stateSObj = studyDS->FindObjectID(entry);
1568     _PTR(GenericAttribute) anAttr;
1569     if (!stateSObj->FindAttribute(anAttr, "AttributeLocalID")) {
1570       return;
1571     }
1572     _PTR(AttributeLocalID) anID(anAttr);
1573     if (!anID->Value() == PVSTATEID) {
1574       return;
1575     }
1576
1577     // Get state file name
1578     if (stateSObj->FindAttribute(anAttr, "AttributeString")) {
1579       _PTR(AttributeString) aStringAttr(anAttr);
1580       QString stringValue(aStringAttr->Value().c_str());
1581
1582       if (QFile::exists(stringValue)) {
1583         fileName = stringValue;
1584       }
1585     }
1586   }
1587   
1588   if (!fileName.isEmpty()) {
1589     if (toClear) {
1590       clearParaviewState();
1591     }
1592
1593     loadParaviewState(fileName.toLatin1().constData());
1594   } 
1595   else {
1596     SUIT_MessageBox::critical(getApp()->desktop(),
1597                               tr("ERR_ERROR"),
1598                               tr("ERR_STATE_CANNOT_BE_RESTORED"));
1599   }
1600 }
1601
1602 void PVGUI_Module::onRepresentationChanged(pqRepresentation*) {
1603
1604
1605   //rnv: to fix the issue "21712: [CEA 581] Preference to display legend by default"
1606   //     find the pqDisplayColorWidget instances and connect the variableChanged SIGNAL on the 
1607   //     onVariableChanged slot of this class. This connection needs to change visibility 
1608   //     of the "Colored Legend" after change the "Color By" array.
1609   QList<pqDisplayColorWidget*> aWidget = getApp()->desktop()->findChildren<pqDisplayColorWidget*>();
1610   
1611   for (int i = 0; i < aWidget.size() ; i++ ) {
1612     if( aWidget[i] ) {
1613       connect( aWidget[i], SIGNAL ( variableChanged ( pqVariableType, const QString ) ), 
1614                this, SLOT(onVariableChanged( pqVariableType, const QString) ), Qt::UniqueConnection );
1615     }    
1616   }
1617 }
1618
1619
1620 /*!
1621   \fn CAM_Module* createModule();
1622   \brief Export module instance (factory function).
1623   \return new created instance of the module
1624 */
1625
1626 #ifdef WNT
1627 #define PVGUI_EXPORT __declspec(dllexport)
1628 #else   // WNT
1629 #define PVGUI_EXPORT
1630 #endif  // WNT
1631
1632 extern "C" {
1633
1634   bool flag = false;
1635   PVGUI_EXPORT CAM_Module* createModule() {
1636     if(!flag) {
1637         vtkEDFHelperInit();
1638         flag = true;
1639     }      
1640     return new PVGUI_Module();
1641   }
1642   
1643   PVGUI_EXPORT char* getModuleVersion() {
1644     return (char*)PARAVIS_VERSION_STR;
1645   }
1646           
1647 }