Salome HOME
Fix misprint in the translation file
[modules/gui.git] / src / LightApp / LightApp_Application.cxx
1 // Copyright (C) 2007-2014  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007  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, or (at your option) any later version.
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.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22
23 // File:      LightApp_Application.cxx
24 // Created:   6/20/2005 18:39:45 PM
25 // Author:    Natalia Donis
26
27 #ifdef WIN32
28 // E.A. : On windows with python 2.6, there is a conflict
29 // E.A. : between pymath.h and Standard_math.h which define
30 // E.A. : some same symbols : acosh, asinh, ...
31   #include <Standard_math.hxx>
32   #ifndef DISABLE_PYCONSOLE
33     #include <pymath.h>
34   #endif
35 #endif
36
37 #ifndef DISABLE_PYCONSOLE
38   #include "LightApp_PyInterp.h" // WARNING! This include must be the first!
39   #include <PyConsole_Console.h>
40 #endif
41
42 #include "LightApp_Application.h"
43 #include "LightApp_Module.h"
44 #include "LightApp_DataModel.h"
45 #include "LightApp_DataOwner.h"
46 #include "LightApp_Displayer.h"
47 #include "LightApp_Study.h"
48 #include "LightApp_Preferences.h"
49 #include "LightApp_PreferencesDlg.h"
50 #include "LightApp_ModuleDlg.h"
51 #include "LightApp_AboutDlg.h"
52 #include "LightApp_ModuleAction.h"
53 // temporary commented
54 #include "LightApp_EventFilter.h"
55 #include "LightApp_OBSelector.h"
56 #include "LightApp_SelectionMgr.h"
57 #include "LightApp_DataObject.h"
58 #include "LightApp_WgViewModel.h"
59 #include "LightApp_FullScreenHelper.h"
60
61 #include <GUI_version.h>
62
63 #include <SALOME_Event.h>
64
65 #include <Style_Salome.h>
66 #include <Style_PrefDlg.h>
67
68 #include <CAM_Module.h>
69 #include <CAM_DataModel.h>
70 #include <CAM_Study.h>
71 #include <STD_TabDesktop.h>
72
73 #include <SUIT_DataBrowser.h>
74 #include <SUIT_Session.h>
75 #include <SUIT_Study.h>
76 #include <SUIT_FileDlg.h>
77 #include <SUIT_ResourceMgr.h>
78 #include <SUIT_ShortcutMgr.h>
79 #include <SUIT_Tools.h>
80 #include <SUIT_Accel.h>
81 #include <SUIT_MessageBox.h>
82 #include <SUIT_ViewWindow.h>
83
84 #include <Qtx.h>
85 #include <QtxToolBar.h>
86 #include <QtxTreeView.h>
87 #include <QtxMRUAction.h>
88 #include <QtxDockAction.h>
89 #include <QtxDockWidget.h>
90 #include <QtxActionToolMgr.h>
91 #include <QtxSearchTool.h>
92 #include <QtxWorkstack.h>
93 #include <QtxMap.h>
94
95 #include <LogWindow.h>
96
97 #ifndef DISABLE_GLVIEWER
98   #include <GLViewer_Viewer.h>
99   #include <GLViewer_ViewManager.h>
100   #include "LightApp_GLSelector.h"
101 #endif
102
103 #ifndef DISABLE_PLOT2DVIEWER
104   #include <Plot2d_ViewManager.h>
105   #include <Plot2d_ViewModel.h>
106   #include <Plot2d_ViewWindow.h>
107   #include <Plot2d_ViewFrame.h>
108   #include "LightApp_Plot2dSelector.h"
109 #ifndef DISABLE_SALOMEOBJECT
110   #include <SPlot2d_ViewModel.h>
111 #else
112   #include <Plot2d_ViewModel.h>
113 #endif
114 #endif
115
116 #ifndef DISABLE_OCCVIEWER
117   #include <OCCViewer_ViewManager.h>
118   #include <OCCViewer_ViewFrame.h>
119 #ifndef DISABLE_SALOMEOBJECT
120   #include <SOCC_ViewModel.h>
121 #else
122   #include <OCCViewer_ViewModel.h>
123 #endif
124   #include "LightApp_OCCSelector.h"
125 #endif
126
127 #ifndef DISABLE_VTKVIEWER
128 #ifndef DISABLE_SALOMEOBJECT
129   #include <SVTK_ViewModel.h>
130   #include <SVTK_ViewManager.h>
131   #include "LightApp_VTKSelector.h"
132 #else
133   #include <VTKViewer_ViewModel.h>
134   #include <VTKViewer_ViewManager.h>
135 #endif
136   #include <VTKViewer_ViewModel.h>
137 #endif
138
139 #ifndef DISABLE_QXGRAPHVIEWER
140   #include <QxScene_ViewManager.h>
141   #include <QxScene_ViewModel.h>
142   #include <QxScene_ViewWindow.h>
143 #endif
144
145 #ifndef DISABLE_GRAPHICSVIEW
146   #include "GraphicsView_Viewer.h"
147   #include "GraphicsView_ViewManager.h"
148   #include "LightApp_GVSelector.h"
149 #endif
150
151 #ifndef DISABLE_PVVIEWER
152   #include "PVViewer_ViewManager.h"
153   #include "PVViewer_ViewWindow.h"
154   #include "PVViewer_ViewModel.h"
155 #endif
156
157
158 #define VISIBILITY_COLUMN_WIDTH 25
159
160 #include <QDir>
161 #include <QImage>
162 #include <QString>
163 #include <QWidget>
164 #include <QStringList>
165 #include <QFile>
166 #include <QApplication>
167 #include <QMap>
168 #include <QStatusBar>
169 #include <QThread>
170 #include <QObjectList>
171 #include <QComboBox>
172 #include <QInputDialog>
173 #include <QFontDatabase>
174 #include <QIcon>
175 #include <QByteArray>
176 #include <QMenu>
177 #include <QProcess>
178 #include <QTimer>
179 #include <QHeaderView>
180 #include <QTreeView>
181 #include <QMimeData>
182 #include <QShortcut>
183
184 #include <utilities.h>
185
186 #define FIRST_HELP_ID 1000000
187
188 #ifndef DISABLE_SALOMEOBJECT
189   #include <SALOME_InteractiveObject.hxx>
190   #include <SALOME_ListIO.hxx>
191 #endif
192
193 #include <Standard_Version.hxx>
194
195 #define ToolBarMarker    0
196 #define DockWidgetMarker 1
197
198 static const char* imageEmptyIcon[] = {
199 "20 20 1 1",
200 ".      c None",
201 "....................",
202 "....................",
203 "....................",
204 "....................",
205 "....................",
206 "....................",
207 "....................",
208 "....................",
209 "....................",
210 "....................",
211 "....................",
212 "....................",
213 "....................",
214 "....................",
215 "....................",
216 "....................",
217 "....................",
218 "....................",
219 "....................",
220 "...................."};
221
222 int LightApp_Application::lastStudyId = 0;
223
224 // Markers used to parse array with dockable windows and toolbars state.
225 // For more details please see the qdockarealayout.cpp && qtoolbararealayout.cpp
226 // in the Qt source code.
227
228 #define QDockWidgetMarker 0xfd // = DockWidgetStateMarker
229 #define QToolBarMarker 0xfc    // = ToolBarStateMarkerEx
230
231 // Format of the Byte array with the windows and toolbar state is:
232 // VersionMarker|version|DockWidgetStateMarker|nbDockWidgetLines|...DocWidgetData...|ToolBarStateMarkerEx|nbToolBarLines|...ToolBarData...
233
234 //Find toolbar marker position in the array in the following way:
235 //since the 'toolbar marker' is not unique, find index of first occurrence of the
236 //'toolbar marker' in the array and check that next string is name of the toolbar
237
238 int getToolbarMarkerIndex(QByteArray input, const QStringList& aFlags) {
239   int aResult = -1,tmp = 0;
240   int inputLen = input.length();
241   QDataStream anInputData(&input, QIODevice::ReadOnly);
242   while(tmp < inputLen) {
243       tmp = input.indexOf(QToolBarMarker, tmp + 1);
244       if(tmp < 0 )
245         break;
246       anInputData.device()->seek(tmp);
247       uchar mark;
248       anInputData>>mark;
249       int lines;
250       anInputData >> lines;
251
252       if(lines == 0 && anInputData.atEnd()){
253         //Case then array doesn't contain information about toolbars,
254         aResult = tmp;
255         break;
256       }
257
258       int pos;
259       anInputData >> pos;
260       int cnt;
261       anInputData >> cnt;
262       QString str;
263       anInputData>>str;
264       if(aFlags.contains(str)) {
265         aResult = tmp;
266         break;
267       }
268     }        
269   return aResult;
270 }
271
272 /*!
273   \return last global id of study
274 */
275 int LightApp_Application::studyId()
276 {
277   return LightApp_Application::lastStudyId;
278 }
279
280 /*!Create new instance of LightApp_Application.*/
281 extern "C" LIGHTAPP_EXPORT SUIT_Application* createApplication()
282 {
283   return new LightApp_Application();
284 }
285
286 /*! \var global preferences of LightApp */
287 LightApp_Preferences* LightApp_Application::_prefs_ = 0;
288
289
290 /*!
291   \class LightApp_Application
292   Application containing LightApp module
293 */
294
295 /*!Constructor.*/
296 LightApp_Application::LightApp_Application()
297 : CAM_Application( false ),
298   myPrefs( 0 ),
299   myScreenHelper(new LightApp_FullScreenHelper())
300 {
301   Q_INIT_RESOURCE( LightApp );
302
303   STD_TabDesktop* desk = new STD_TabDesktop();
304   desk->setFullScreenAllowed(false);
305   desk->setMinimizeAllowed(false);
306
307   setDesktop( desk );
308
309   // initialize auto save timer
310   myAutoSaveTimer = new QTimer( this );
311   myAutoSaveTimer->setSingleShot( true );
312   connect( myAutoSaveTimer, SIGNAL( timeout() ), this, SLOT( onSaveDoc() ) );
313
314   SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
315   QPixmap aLogo = aResMgr->loadPixmap( "LightApp", tr( "APP_DEFAULT_ICO" ), false );
316
317   desktop()->setWindowIcon( aLogo );
318   desktop()->setDockableMenuBar( false );
319   desktop()->setDockableStatusBar( false );
320
321   // base logo (salome itself)
322   desktop()->logoInsert( "_app_base",  aResMgr->loadPixmap( "LightApp", tr( "APP_BASE_LOGO" ), false ) );
323   // extra logo (salome-based application)
324   desktop()->logoInsert( "_app_extra", aResMgr->loadPixmap( "LightApp", tr( "APP_EXTRA_LOGO" ), false ) );
325
326   clearViewManagers();
327
328   mySelMgr = new LightApp_SelectionMgr( this );
329
330   myAccel = SUIT_Accel::getAccel();
331
332 #ifndef DISABLE_OCCVIEWER
333   myAccel->setActionKey( SUIT_Accel::PanLeft,     Qt::CTRL+Qt::Key_Left,     OCCViewer_Viewer::Type() );
334   myAccel->setActionKey( SUIT_Accel::PanRight,    Qt::CTRL+Qt::Key_Right,    OCCViewer_Viewer::Type() );
335   myAccel->setActionKey( SUIT_Accel::PanUp,       Qt::CTRL+Qt::Key_Up,       OCCViewer_Viewer::Type() );
336   myAccel->setActionKey( SUIT_Accel::PanDown,     Qt::CTRL+Qt::Key_Down,     OCCViewer_Viewer::Type() );
337   myAccel->setActionKey( SUIT_Accel::ZoomIn,      Qt::CTRL+Qt::Key_Plus,     OCCViewer_Viewer::Type() );
338   myAccel->setActionKey( SUIT_Accel::ZoomOut,     Qt::CTRL+Qt::Key_Minus,    OCCViewer_Viewer::Type() );
339   myAccel->setActionKey( SUIT_Accel::ZoomFit,     Qt::CTRL+Qt::Key_Asterisk, OCCViewer_Viewer::Type() );
340   myAccel->setActionKey( SUIT_Accel::ZoomFit,     Qt::Key_Space,             OCCViewer_Viewer::Type() );
341   myAccel->setActionKey( SUIT_Accel::RotateLeft,  Qt::ALT+Qt::Key_Left,      OCCViewer_Viewer::Type() );
342   myAccel->setActionKey( SUIT_Accel::RotateRight, Qt::ALT+Qt::Key_Right,     OCCViewer_Viewer::Type() );
343   myAccel->setActionKey( SUIT_Accel::RotateUp,    Qt::ALT+Qt::Key_Up,        OCCViewer_Viewer::Type() );
344   myAccel->setActionKey( SUIT_Accel::RotateDown,  Qt::ALT+Qt::Key_Down,      OCCViewer_Viewer::Type() );
345 #endif
346 #ifndef DISABLE_VTKVIEWER
347   myAccel->setActionKey( SUIT_Accel::PanLeft,     Qt::CTRL+Qt::Key_Left,     VTKViewer_Viewer::Type() );
348   myAccel->setActionKey( SUIT_Accel::PanRight,    Qt::CTRL+Qt::Key_Right,    VTKViewer_Viewer::Type() );
349   myAccel->setActionKey( SUIT_Accel::PanUp,       Qt::CTRL+Qt::Key_Up,       VTKViewer_Viewer::Type() );
350   myAccel->setActionKey( SUIT_Accel::PanDown,     Qt::CTRL+Qt::Key_Down,     VTKViewer_Viewer::Type() );
351   myAccel->setActionKey( SUIT_Accel::ZoomIn,      Qt::CTRL+Qt::Key_Plus,     VTKViewer_Viewer::Type() );
352   myAccel->setActionKey( SUIT_Accel::ZoomOut,     Qt::CTRL+Qt::Key_Minus,    VTKViewer_Viewer::Type() );
353   myAccel->setActionKey( SUIT_Accel::ZoomFit,     Qt::CTRL+Qt::Key_Asterisk, VTKViewer_Viewer::Type() );
354   myAccel->setActionKey( SUIT_Accel::ZoomFit,     Qt::Key_Space,             VTKViewer_Viewer::Type() );
355   myAccel->setActionKey( SUIT_Accel::RotateLeft,  Qt::ALT+Qt::Key_Left,      VTKViewer_Viewer::Type() );
356   myAccel->setActionKey( SUIT_Accel::RotateRight, Qt::ALT+Qt::Key_Right,     VTKViewer_Viewer::Type() );
357   myAccel->setActionKey( SUIT_Accel::RotateUp,    Qt::ALT+Qt::Key_Up,        VTKViewer_Viewer::Type() );
358   myAccel->setActionKey( SUIT_Accel::RotateDown,  Qt::ALT+Qt::Key_Down,      VTKViewer_Viewer::Type() );
359 #endif
360 #ifndef DISABLE_PLOT2DVIEWER
361   myAccel->setActionKey( SUIT_Accel::PanLeft,     Qt::CTRL+Qt::Key_Left,     Plot2d_Viewer::Type() );
362   myAccel->setActionKey( SUIT_Accel::PanRight,    Qt::CTRL+Qt::Key_Right,    Plot2d_Viewer::Type() );
363   myAccel->setActionKey( SUIT_Accel::PanUp,       Qt::CTRL+Qt::Key_Up,       Plot2d_Viewer::Type() );
364   myAccel->setActionKey( SUIT_Accel::PanDown,     Qt::CTRL+Qt::Key_Down,     Plot2d_Viewer::Type() );
365   myAccel->setActionKey( SUIT_Accel::ZoomIn,      Qt::CTRL+Qt::Key_Plus,     Plot2d_Viewer::Type() );
366   myAccel->setActionKey( SUIT_Accel::ZoomOut,     Qt::CTRL+Qt::Key_Minus,    Plot2d_Viewer::Type() );
367   myAccel->setActionKey( SUIT_Accel::ZoomFit,     Qt::CTRL+Qt::Key_Asterisk, Plot2d_Viewer::Type() );
368   myAccel->setActionKey( SUIT_Accel::ZoomFit,     Qt::Key_Space,             Plot2d_Viewer::Type() );
369 #endif
370
371   connect( mySelMgr, SIGNAL( selectionChanged() ), this, SLOT( onSelection() ) );
372   connect( desktop(), SIGNAL( windowActivated( SUIT_ViewWindow* ) ),
373            this,      SLOT( onWindowActivated( SUIT_ViewWindow* ) ), Qt::UniqueConnection );
374   connect( this, SIGNAL( viewManagerRemoved( SUIT_ViewManager* ) ),
375            this, SLOT( onViewManagerRemoved( SUIT_ViewManager* ) ), Qt::UniqueConnection );
376
377
378   // Set existing font for the python console in resources
379   if( !aResMgr->hasValue( "PyConsole", "font" ) )
380     return;
381
382   QFont f = aResMgr->fontValue( "PyConsole", "font" );
383   QFontDatabase fdb;
384   QStringList famdb = fdb.families();
385
386   if ( famdb.contains(f.family()) || !aResMgr->hasValue( "PyConsole", "additional_families" ) )
387     return;
388
389   QStringList anAddFamilies = aResMgr->stringValue( "PyConsole", "additional_families" ).split( ";", QString::SkipEmptyParts );
390   QString aFamily;
391   for ( QStringList::Iterator it = anAddFamilies.begin(); it != anAddFamilies.end(); ++it )
392   {
393     aFamily = *it;
394     if ( famdb.contains(aFamily) )
395     {
396       f.setFamily( aFamily );
397       aResMgr->setValue( "PyConsole", "font", f );
398       break;
399     }
400   }
401 }
402
403 /*!Destructor.
404  *\li Save window geometry.
405  *\li Save desktop geometry.
406  *\li Save resource maneger.
407  *\li Delete selection manager.
408  */
409 LightApp_Application::~LightApp_Application()
410 {
411   delete mySelMgr;
412   delete myScreenHelper;
413 }
414
415 /*!Start application.*/
416 void LightApp_Application::start()
417 {
418   CAM_Application::start();
419
420   updateWindows();
421   updateViewManagers();
422   updateCommandsStatus();
423
424   putInfo( "" );
425   desktop()->statusBar()->showMessage( "" );
426
427   LightApp_EventFilter::Init();
428 }
429
430 /*!Gets application name.*/
431 QString LightApp_Application::applicationName() const
432 {
433   static QString _app_name;
434   if ( _app_name.isEmpty() )
435     _app_name = tr( "APP_NAME" );
436   return _app_name;
437 }
438
439 /*!Gets application version.*/
440 QString LightApp_Application::applicationVersion() const
441 {
442   static QString _app_version;
443
444   if ( _app_version.isEmpty() )
445   {
446     QString resVersion = tr( "APP_VERSION" );
447     if ( resVersion != "APP_VERSION" )
448     {
449       _app_version = resVersion;
450     }
451     else
452     {
453       _app_version = GUI_VERSION_STR;
454     }
455   }
456   return _app_version;
457 }
458
459 /*!Load module by \a name.*/
460 CAM_Module* LightApp_Application::loadModule( const QString& name, const bool showMsg )
461 {
462   CAM_Module* mod = CAM_Application::loadModule( name, showMsg );
463   if ( mod )
464   {
465     connect( this, SIGNAL( studyOpened() ), mod, SLOT( onModelOpened() ) );
466     connect( this, SIGNAL( studySaved() ),  mod, SLOT( onModelSaved() ) );
467     connect( this, SIGNAL( studyClosed() ), mod, SLOT( onModelClosed() ) );
468   }
469   return mod;
470 }
471
472 /*!Activate module by \a modName*/
473 bool LightApp_Application::activateModule( const QString& modName )
474 {
475   QString actName;
476   CAM_Module* prevMod = activeModule();
477
478   if ( prevMod )
479     actName = prevMod->moduleName();
480
481   if ( actName == modName )
482     return true;
483
484   putInfo( tr( "ACTIVATING_MODULE" ).arg( modName ) );
485
486   saveDockWindowsState();
487
488   bool status = CAM_Application::activateModule( modName );
489
490   updateModuleActions();
491
492   putInfo( "" );
493
494   if ( !status )
495     return false;
496
497   updateWindows();
498   updateViewManagers();
499
500   return true;
501 }
502
503 /*!Gets selection manager.*/
504 LightApp_SelectionMgr* LightApp_Application::selectionMgr() const
505 {
506   return mySelMgr;
507 }
508
509 /*!Creat action "New window" for certain type of viewer:*/
510 void LightApp_Application::createActionForViewer( const int id,
511                                                   const int parentId,
512                                                   const QString& suffix,
513                                                   const int accel )
514 {
515   QString vtlt = tr( QString( "NEW_WINDOW_%1" ).arg( suffix ).toLatin1().constData() );
516   QString tip = tr( "CREATING_NEW_WINDOW" ).arg( vtlt.remove( "&" ) );
517   QAction* a = createAction( id,                      // menu action id
518                              tip,                     // status tip
519                              QIcon(),                 // icon
520                              vtlt,                    // menu text
521                              tip,                     // tooltip
522                              accel,                   // shortcut
523                              desktop(),               // parent
524                              false,                   // toggle flag
525                              this,                    // receiver
526                              SLOT( onNewWindow() ) ); // slot
527   createMenu( a, parentId, -1 );
528 }
529
530 /*!Create actions:*/
531
532 void LightApp_Application::createActions()
533 {
534   CAM_Application::createActions();
535
536   SUIT_Desktop* desk = desktop();
537   SUIT_ResourceMgr* resMgr = resourceMgr();
538
539   // Preferences
540   createAction( PreferencesId, tr( "TOT_DESK_PREFERENCES" ), QIcon(),
541                 tr( "MEN_DESK_PREFERENCES" ), tr( "PRP_DESK_PREFERENCES" ),
542                 Qt::CTRL+Qt::Key_R, desk, false, this, SLOT( onPreferences() ) );
543
544   // Help menu:
545
546   // - Help for modules
547
548   int helpMenu = createMenu( tr( "MEN_DESK_HELP" ), -1, -1, 1000 );
549   createMenu( separator(), helpMenu, -1, 10 );
550   QStringList aModuleList;
551   modules( aModuleList, false );
552   aModuleList.prepend( "GUI" );
553   aModuleList.prepend( "KERNEL" );
554
555   int id = LightApp_Application::UserID + FIRST_HELP_ID;
556
557   QString aModule;
558   foreach( aModule, aModuleList ) {
559     if ( aModule.isEmpty() )                                         // module title (user name)
560       continue;
561     IMap <QString, QString> helpData;                                // list of help files for the module
562     QString helpSubMenu;                                             // help submenu name (empty if not needed)
563     QString modName = moduleName( aModule );                         // module name
564     if ( modName.isEmpty() ) modName = aModule;                      // for KERNEL and GUI
565     QString rootDir = QString( "%1_ROOT_DIR" ).arg( modName );       // module root dir variable
566     QString modDir  = getenv( rootDir.toLatin1().constData() );      // module root dir
567     QString docSection;
568     if (resMgr->hasValue( modName, "documentation" ) )
569       docSection = resMgr->stringValue(modName, "documentation");
570     else if ( resMgr->hasSection( modName + "_documentation" ) )
571       docSection = modName + "_documentation";
572     if ( !docSection.isEmpty() ) {
573       helpSubMenu = resMgr->stringValue( docSection, "sub_menu", "" ).arg( aModule );
574       QStringList listOfParam = resMgr->parameters( docSection );
575       foreach( QString paramName, listOfParam ) {
576         QString valueStr = resMgr->stringValue( docSection, paramName );
577         if ( !valueStr.isEmpty() ) {
578           QFileInfo fi( valueStr );
579           if ( fi.isRelative() && !modDir.isEmpty() )
580             valueStr = Qtx::addSlash( modDir ) + valueStr;
581           if ( QFile::exists( valueStr ) )
582             helpData.insert( paramName.arg( aModule ), valueStr );
583         }
584       }
585     }
586
587     if ( helpData.isEmpty() && !modDir.isEmpty() ) {
588       QStringList idxLst = QStringList() << modDir << "share" << "doc" << "salome" << "gui" << modName << "index.html";
589       QString indexFile = idxLst.join( QDir::separator() );          // index file
590       if ( QFile::exists( indexFile ) )
591         helpData.insert( tr( "%1 module Users's Guide" ).arg( aModule ), indexFile );
592     }
593
594     IMapConstIterator<QString, QString > fileIt;
595     for ( fileIt = helpData.begin(); fileIt != helpData.end(); fileIt++ ) {
596       QString helpFileName = fileIt.key();
597       // remove all '//' occurances 
598       while ( helpFileName.contains( "//" ) )
599         helpFileName.replace( "//", "" );
600       // obtain submenus hierarchy if given
601       QStringList smenus = helpFileName.split( "/" );
602       helpFileName = smenus.last();
603       smenus.removeLast();
604       QAction* a = createAction( id, helpFileName,
605                                  resMgr->loadPixmap( "STD", tr( "ICON_HELP" ), false ),
606                                  helpFileName, helpFileName,
607                                  0, desk, false, this, SLOT( onHelpContentsModule() ) );
608       a->setData( fileIt.value() );
609       if ( !helpSubMenu.isEmpty() ) {
610         smenus.prepend( helpSubMenu );
611       }
612       // create sub-menus hierarchy
613       int menuId = helpMenu;
614       foreach ( QString subMenu, smenus ) {
615         menuId = createMenu( subMenu, menuId, -1, 0 );
616       }
617       createMenu( a, menuId, -1, 0 );
618       id++;
619     }
620   }
621
622   // - Additional help items
623
624   createMenu( separator(), helpMenu, -1, 5 );
625
626   QStringList addHelpItems = resMgr->parameters( "add_help" );
627   foreach ( QString addHelpItem, addHelpItems ) {
628     QString valueStr = resMgr->stringValue( "add_help", addHelpItem );
629     if ( !valueStr.isEmpty() && QFile::exists( valueStr ) ) {
630       QAction* a = createAction( id, addHelpItem,
631                                  resMgr->loadPixmap( "STD", tr( "ICON_HELP" ), false ),
632                                  addHelpItem, addHelpItem,
633                                  0, desk, false, this, SLOT( onHelpContentsModule() ) );
634       a->setData( valueStr );
635       createMenu( a, helpMenu, -1, 5 );
636       id++;
637     }
638   }
639
640   //! MRU
641   static QtxMRUAction* mru = new QtxMRUAction( tr( "TOT_DESK_MRU" ), tr( "MEN_DESK_MRU" ), 0 );
642   connect( mru, SIGNAL( activated( const QString& ) ), this, SLOT( onMRUActivated( const QString& ) ) );
643   registerAction( MRUId, mru );
644
645   // default icon for neutral point ('SALOME' module)
646   QPixmap defIcon = resMgr->loadPixmap( "LightApp", tr( "APP_DEFAULT_ICO" ), false );
647   if ( defIcon.isNull() )
648     defIcon = QPixmap( imageEmptyIcon );
649
650   //! default icon for any module
651   QPixmap modIcon = resMgr->loadPixmap( "LightApp", tr( "APP_MODULE_ICO" ), false );
652   if ( modIcon.isNull() )
653     modIcon = QPixmap( imageEmptyIcon );
654
655   QStringList modList;
656   modules( modList, false );
657
658   if ( modList.count() > 1 )
659   {
660     LightApp_ModuleAction* moduleAction =
661       new LightApp_ModuleAction( tr( "APP_NAME" ), defIcon, desk );
662
663     QMap<QString, QString> iconMap;
664     moduleIconNames( iconMap );
665
666     const int iconSize = 20;
667
668     QStringList::Iterator it;
669     for ( it = modList.begin(); it != modList.end(); ++it )
670     {
671       if ( !isLibExists( *it ) )
672         continue;
673
674       QString modName = moduleName( *it );
675
676       if ( !isModuleAccessible( *it ) )
677         continue;
678
679       QString iconName;
680       if ( iconMap.contains( *it ) )
681         iconName = iconMap[*it];
682
683       QPixmap icon = resMgr->loadPixmap( modName, iconName, false );
684       if ( icon.isNull() )
685       {
686         icon = modIcon;
687         INFOS ( "\n****************************************************************" << std::endl
688                 <<  "*    Icon for " << (*it).toLatin1().constData()
689                 << " not found. Using the default one." << std::endl
690                 << "****************************************************************" << std::endl );
691       }
692
693       icon = Qtx::scaleIcon( icon, iconSize );
694
695       moduleAction->insertModule( *it, icon );
696     }
697
698     connect( moduleAction, SIGNAL( moduleActivated( const QString& ) ),
699              this, SLOT( onModuleActivation( const QString& ) ) );
700     registerAction( ModulesListId, moduleAction );
701   }
702
703   // New window
704   int windowMenu = createMenu( tr( "MEN_DESK_WINDOW" ), -1, MenuWindowId, 100 );
705   int newWinMenu = createMenu( tr( "MEN_DESK_NEWWINDOW" ), windowMenu, -1, 0 );
706
707   createAction( CloseId, tr( "TOT_CLOSE" ), QIcon(), tr( "MEN_DESK_CLOSE" ), tr( "PRP_CLOSE" ),
708                 Qt::CTRL+Qt::Key_F4, desk, false, this, SLOT( onCloseWindow() ) );
709   createAction( CloseAllId, tr( "TOT_CLOSE_ALL" ), QIcon(), tr( "MEN_DESK_CLOSE_ALL" ), tr( "PRP_CLOSE_ALL" ),
710                 0, desk, false, this, SLOT( onCloseAllWindow() ) );
711   createAction( GroupAllId, tr( "TOT_GROUP_ALL" ), QIcon(), tr( "MEN_DESK_GROUP_ALL" ), tr( "PRP_GROUP_ALL" ),
712                 0, desk, false, this, SLOT( onGroupAllWindow() ) );
713
714   createMenu( CloseId,     windowMenu, 0, -1 );
715   createMenu( CloseAllId,  windowMenu, 0, -1 );
716   createMenu( GroupAllId,  windowMenu, 0, -1 );
717   createMenu( separator(), windowMenu, -1, 0 );
718
719 #ifndef DISABLE_GLVIEWER
720   createActionForViewer( NewGLViewId, newWinMenu, QString::number( 0 ), Qt::ALT+Qt::Key_G );
721 #endif
722 #ifndef DISABLE_PLOT2DVIEWER
723   createActionForViewer( NewPlot2dId, newWinMenu, QString::number( 1 ), Qt::ALT+Qt::Key_P );
724 #endif
725 #ifndef DISABLE_OCCVIEWER
726   createActionForViewer( NewOCCViewId, newWinMenu, QString::number( 2 ), Qt::ALT+Qt::Key_O );
727 #endif
728 #ifndef DISABLE_VTKVIEWER
729   createActionForViewer( NewVTKViewId, newWinMenu, QString::number( 3 ), Qt::ALT+Qt::Key_K );
730 #endif
731 #ifndef DISABLE_QXGRAPHVIEWER
732   createActionForViewer( NewQxSceneViewId, newWinMenu, QString::number( 4 ), Qt::ALT+Qt::Key_S );
733 #endif
734 #ifndef DISABLE_GRAPHICSVIEW
735   createActionForViewer( NewGraphicsViewId, newWinMenu, QString::number( 5 ), Qt::ALT+Qt::Key_R );
736 #endif
737 #ifndef DISABLE_PVVIEWER
738   createActionForViewer( NewPVViewId, newWinMenu, QString::number( 6 ), Qt::ALT+Qt::Key_W );
739 #endif
740
741   createAction( RenameId, tr( "TOT_RENAME" ), QIcon(), tr( "MEN_DESK_RENAME" ), tr( "PRP_RENAME" ),
742                 Qt::ALT+Qt::SHIFT+Qt::Key_R, desk, false, this, SLOT( onRenameWindow() ) );
743   createMenu( RenameId, windowMenu, -1 );
744
745   int fileMenu = createMenu( tr( "MEN_DESK_FILE" ), -1 );
746   createMenu( PreferencesId, fileMenu, 50, -1 );
747   createMenu( separator(), fileMenu, -1, 50, -1 );
748
749   createMenu( separator(), fileMenu, -1, 100, -1 );
750   createMenu( MRUId, fileMenu, 100, -1 );
751   createMenu( separator(), fileMenu, -1, 100, -1 );
752
753   createAction( StyleId, tr( "TOT_THEME" ), QIcon(), tr( "MEN_DESK_THEME" ), tr( "PRP_THEME" ),
754                 0, desk, false, this, SLOT( onStylePreferences() ) );
755
756   createAction( FullScreenId, tr( "TOT_FULLSCREEN" ), QIcon(), tr( "MEN_DESK_FULLSCREEN" ), tr( "PRP_FULLSCREEN" ),
757                 Qt::Key_F11, desk, false, this, SLOT( onFullScreen() ) );
758
759
760   int viewMenu = createMenu( tr( "MEN_DESK_VIEW" ), -1 );
761   createMenu( separator(), viewMenu, -1, 20, -1 );
762   createMenu( StyleId, viewMenu, 20, -1 );
763   createMenu( FullScreenId, viewMenu, 20, -1 );
764
765   int modTBar = createTool( tr( "INF_TOOLBAR_MODULES" ),    // title (language-dependant)
766                             QString( "SalomeModules" ) );   // name (language-independant)
767   createTool( ModulesListId, modTBar );
768 }
769
770 /*!On module activation action.*/
771 void LightApp_Application::onModuleActivation( const QString& modName )
772 {
773   // Force user to create/open a study before module activation
774   QMap<QString, QString> iconMap;
775   moduleIconNames( iconMap );
776   QPixmap icon = resourceMgr()->loadPixmap( moduleName( modName ), iconMap[ modName ], false );
777   if ( icon.isNull() )
778     icon = resourceMgr()->loadPixmap( "LightApp", tr( "APP_MODULE_BIG_ICO" ), false ); // default icon for any module
779
780   bool cancelled = false;
781
782   while ( !modName.isEmpty() && !activeStudy() && !cancelled ){
783     LightApp_ModuleDlg aDlg( desktop(), modName, icon );
784     QMap<int, QString> opmap = activateModuleActions();
785     for ( QMap<int, QString>::ConstIterator it = opmap.begin(); it != opmap.end(); ++it )
786       aDlg.addButton( it.value(), it.key() );
787
788     int res = aDlg.exec();
789     if ( res ) {
790       // some operation is selected
791       moduleActionSelected( res );
792     }
793     else {
794       // cancelled
795       putInfo( tr("INF_CANCELLED") );
796
797       LightApp_ModuleAction* moduleAction =
798         qobject_cast<LightApp_ModuleAction*>( action( ModulesListId ) );
799       if ( moduleAction )
800         moduleAction->setActiveModule( QString() );
801       cancelled = true;
802     }
803   }
804
805   if ( !cancelled )
806     activateModule( modName );
807 }
808
809 /*!Default module activation.*/
810 QString LightApp_Application::defaultModule() const
811 {
812   QStringList aModuleNames;
813   modules( aModuleNames, false ); // obtain a complete list of module names for the current configuration
814   //! If there's the one and only module --> activate it automatically
815   //! TODO: Possible improvement - default module can be taken from preferences
816   return aModuleNames.count() > 1 ? "" : ( aModuleNames.count() ? aModuleNames.first() : "" );
817 }
818
819 /*!On new window slot.*/
820 void LightApp_Application::onNewWindow()
821 {
822   const QObject* obj = sender();
823   if ( !obj || !obj->inherits( "QAction" ) )
824     return;
825
826   QString type;
827   int id = actionId( (QAction*)obj );
828   switch ( id )
829   {
830 #ifndef DISABLE_GLVIEWER
831   case NewGLViewId:
832     type = GLViewer_Viewer::Type();
833     break;
834 #endif
835 #ifndef DISABLE_PLOT2DVIEWER
836   case NewPlot2dId:
837     type = Plot2d_Viewer::Type();
838     break;
839 #endif
840 #ifndef DISABLE_OCCVIEWER
841   case NewOCCViewId:
842     type = OCCViewer_Viewer::Type();
843     break;
844 #endif
845 #ifndef DISABLE_VTKVIEWER
846   case NewVTKViewId:
847     type = VTKViewer_Viewer::Type();
848     break;
849 #endif
850 #ifndef DISABLE_QXGRAPHVIEWER
851   case NewQxSceneViewId:
852     type = QxScene_Viewer::Type();
853     break;
854 #endif
855 #ifndef DISABLE_GRAPHICSVIEW
856   case NewGraphicsViewId:
857     type = GraphicsView_Viewer::Type();
858     break;
859 #endif
860 #ifndef DISABLE_PVVIEWER
861   case NewPVViewId:
862     type = PVViewer_Viewer::Type();
863     break;
864 #endif
865   }
866
867   if ( !type.isEmpty() )
868     createViewManager( type );
869 }
870
871 /*!
872   SLOT: Creates new document
873 */
874 void LightApp_Application::onNewDoc()
875 {
876 #ifdef SINGLE_DESKTOP
877   if ( !checkExistingDoc() )
878     return;
879 #endif
880
881   //asl: fix for 0020515
882   saveDockWindowsState();
883   
884   CAM_Application::onNewDoc();
885 }
886
887 /*!
888   SLOT: Opens new document
889 */
890 void LightApp_Application::onOpenDoc()
891 {
892   SUIT_Study* study = activeStudy();
893   
894 #ifdef SINGLE_DESKTOP
895   if ( !checkExistingDoc() )
896     return;
897 #endif
898   
899   CAM_Application::onOpenDoc();
900   
901   if ( !study ) // new study will be create in THIS application
902   {
903     updateWindows();
904     updateViewManagers();
905   }
906 }
907
908 /*!
909   SLOT: Opens new document.
910   \param aName - name of file
911 */
912 bool LightApp_Application::onOpenDoc( const QString& aName )
913 {
914 #ifdef SINGLE_DESKTOP
915   if ( !checkExistingDoc() )
916     return false;
917 #endif
918
919   saveDockWindowsState();
920
921   // We should take mru action first because this application instance can be deleted later.
922   QtxMRUAction* mru = ::qobject_cast<QtxMRUAction*>( action( MRUId ) );
923   
924   bool res = CAM_Application::onOpenDoc( aName );
925
926   if ( mru )
927   {
928     if ( res )
929       mru->insert( aName );
930     else
931       mru->remove( aName );
932   }
933   return res;
934 }
935
936 /*!
937   SLOT: Displays "About" message box
938 */
939 void LightApp_Application::onHelpAbout()
940 {
941   LightApp_AboutDlg dlg( applicationName(), applicationVersion(), desktop() );
942   dlg.exec();
943 }
944
945 /*!
946   Private SLOT: Called on selection is changed
947   Dispatchs active module that selection is changed
948 */
949 void LightApp_Application::onSelection()
950 {
951   onSelectionChanged();
952
953   if ( activeModule() && activeModule()->inherits( "LightApp_Module" ) )
954     ((LightApp_Module*)activeModule())->selectionChanged();
955 }
956
957 /*!
958   Sets active study.
959  \param study - SUIT_Study.
960 */
961 void LightApp_Application::setActiveStudy( SUIT_Study* study )
962 {
963   CAM_Application::setActiveStudy( study );
964 }
965
966 /*!
967   Enables/Disables menu items and toolbar buttons. Rebuild menu
968 */
969 void LightApp_Application::updateCommandsStatus()
970 {
971   CAM_Application::updateCommandsStatus();
972   QAction* a = 0;
973
974 #ifndef DISABLE_GLVIEWER
975   a = action( NewGLViewId );
976   if( a )
977     a->setEnabled( activeStudy() );
978 #endif
979
980 #ifndef DISABLE_PLOT2DVIEWER
981   a = action( NewPlot2dId );
982   if( a )
983     a->setEnabled( activeStudy() );
984 #endif
985
986 #ifndef DISABLE_OCCVIEWER
987   a = action( NewOCCViewId );
988   if( a )
989     a->setEnabled( activeStudy() );
990 #endif
991
992 #ifndef DISABLE_VTKVIEWER
993   a = action( NewVTKViewId );
994   if( a )
995     a->setEnabled( activeStudy() );
996 #endif
997
998 #ifndef DISABLE_QXGRAPHVIEWER
999   a = action( NewQxSceneViewId );
1000   if( a )
1001     a->setEnabled( activeStudy() );
1002 #endif
1003
1004 #ifndef DISABLE_GRAPHICSVIEW
1005   a = action( NewGraphicsViewId );
1006   if( a )
1007     a->setEnabled( activeStudy() );
1008 #endif
1009
1010 #ifndef DISABLE_PVVIEWER
1011   a = action( NewPVViewId );
1012   if( a )
1013     a->setEnabled( activeStudy() );
1014 #endif
1015 }
1016
1017 /*!
1018   \class RunBrowser
1019   Runs system command in separate thread
1020 */
1021 class RunBrowser: public QThread
1022 {
1023 public:
1024   RunBrowser( LightApp_Application* app,
1025               const QString&        theApp,
1026               const QString&        theParams,
1027               const QString&        theHelpFile,
1028               const QString&        theContext = QString() )
1029     : myApp( theApp ),
1030       myParams( theParams ),
1031       myContext( theContext ),
1032       myStatus(0),
1033       myLApp( app )
1034   {
1035     //For the external browser always specify 'file://' protocol,
1036     //because some WEB browsers (for example Mozilla Firefox) can't open local file without protocol.
1037     myHelpFile = QString("file://%1").arg( QFileInfo( theHelpFile ).canonicalFilePath() );
1038   }
1039
1040   virtual void run()
1041   {
1042     if ( !myApp.isEmpty() && !myHelpFile.isEmpty()) {
1043       QString aCommand = QString( "%1 %2 \"%3%4\"" ).arg( myApp, myParams, myHelpFile, myContext.isEmpty() ? QString("") : QString( "#%1" ).arg( myContext ) );
1044
1045       QProcess* proc = new QProcess();
1046
1047       proc->start( aCommand );
1048       if ( !proc->waitForStarted() ) {
1049         SALOME_CustomEvent* ce2000 = new SALOME_CustomEvent( 2000 );
1050         QString* msg = new QString( QObject::tr( "EXTERNAL_BROWSER_CANNOT_SHOW_PAGE" ).arg( myApp, myHelpFile ) );
1051         ce2000->setData( msg );
1052         QApplication::postEvent( myLApp, ce2000 );
1053       }
1054     }
1055   }
1056
1057 private:
1058   QString               myApp;
1059   QString               myParams;
1060   QString               myHelpFile;
1061   QString               myContext;
1062   int                   myStatus;
1063   LightApp_Application* myLApp;
1064 };
1065
1066 /*!
1067   SLOT: Displays help contents for choosen module
1068 */
1069 void LightApp_Application::onHelpContentsModule()
1070 {
1071   const QAction* a = (QAction*) sender();
1072   QString helpFile = a->data().toString();
1073   if ( helpFile.isEmpty() ) return;
1074
1075   SUIT_ResourceMgr* resMgr = resourceMgr();
1076   QString platform;
1077 #ifdef WIN32
1078   platform = "winapplication";
1079 #else
1080   platform = "application";
1081 #endif
1082   QString anApp = resMgr->stringValue("ExternalBrowser", platform);
1083 #ifdef WIN32
1084   QString quote("\"");
1085   anApp.prepend( quote );
1086   anApp.append( quote );
1087 #endif
1088   QString aParams = resMgr->stringValue("ExternalBrowser", "parameters");
1089   bool useExtBrowser = resMgr->booleanValue("ExternalBrowser", "use_external_browser", false );
1090
1091   if( useExtBrowser ) {
1092     if ( !anApp.isEmpty() ) {
1093       RunBrowser* rs = new RunBrowser( this, anApp, aParams, helpFile );
1094       rs->start();
1095     }
1096     else {
1097       if ( SUIT_MessageBox::question( desktop(), tr( "WRN_WARNING" ), tr( "DEFINE_EXTERNAL_BROWSER" ),
1098                                       SUIT_MessageBox::Yes | SUIT_MessageBox::No,
1099                                       SUIT_MessageBox::Yes ) == SUIT_MessageBox::Yes )
1100
1101         showPreferences( tr( "PREF_APP" ) );
1102     }
1103   }
1104   else {
1105     QStringList parameters;
1106     parameters << QString( "--language=%1" ).arg( resMgr->stringValue( "language", "language" ) );
1107     parameters << helpFile;
1108     QProcess::startDetached( "HelpBrowser", parameters );
1109   }
1110 }
1111
1112 /*!
1113   SLOT: Displays help contents for choosen dialog
1114 */
1115 void LightApp_Application::onHelpContextModule( const QString& theComponentName,
1116                                                 const QString& theFileName,
1117                                                 const QString& theContext )
1118 {
1119   QString fileName = theFileName;
1120   QString context  = theContext;
1121   if ( !QFile::exists( fileName ) && theContext.isEmpty() ) {
1122     // context might be passed within theFileName argument
1123     QStringList comps = fileName.split("#");
1124     if ( comps.count() > 1 ) {
1125       context = comps.last();
1126       comps.removeLast();
1127       fileName = comps.join("#");
1128     }
1129   }
1130
1131   QString homeDir = "";
1132   if ( !theComponentName.isEmpty() ) {
1133     QString dir = getenv( ( theComponentName + "_ROOT_DIR" ).toLatin1().constData() );
1134     if ( !dir.isEmpty() )
1135       homeDir = Qtx::addSlash( Qtx::addSlash( dir )      +
1136                                Qtx::addSlash( "share" )  +
1137                                Qtx::addSlash( "doc" )    +
1138                                Qtx::addSlash( "salome" ) +
1139                                Qtx::addSlash( "gui" )    +
1140                                Qtx::addSlash( theComponentName ) );
1141   }
1142
1143   QString helpFile = QFileInfo( homeDir + fileName ).absoluteFilePath();
1144   SUIT_ResourceMgr* resMgr = resourceMgr();
1145         QString platform;
1146 #ifdef WIN32
1147         platform = "winapplication";
1148 #else
1149         platform = "application";
1150 #endif
1151         QString anApp = resMgr->stringValue("ExternalBrowser", platform);
1152 #ifdef WIN32
1153         QString quote("\"");
1154         anApp.prepend( quote );
1155         anApp.append( quote );
1156 #endif
1157
1158   bool useExtBrowser = resMgr->booleanValue("ExternalBrowser", "use_external_browser", false );
1159
1160   if(useExtBrowser) {
1161     QString aParams = resMgr->stringValue("ExternalBrowser", "parameters");
1162
1163     if ( !anApp.isEmpty() ) {
1164       RunBrowser* rs = new RunBrowser( this, anApp, aParams, helpFile, context );
1165       rs->start();
1166     }
1167     else {
1168       if ( SUIT_MessageBox::question( desktop(), tr( "WRN_WARNING" ), tr( "DEFINE_EXTERNAL_BROWSER" ),
1169                                       SUIT_MessageBox::Yes | SUIT_MessageBox::No,
1170                                       SUIT_MessageBox::Yes ) == SUIT_MessageBox::Yes )
1171         showPreferences( tr( "PREF_APP" ) );
1172     }
1173   }
1174   else {
1175     QStringList parameters;
1176     parameters << QString( "--language=%1" ).arg( resMgr->stringValue( "language", "language" ) );
1177     parameters << QString( "%1#%2" ).arg( helpFile ).arg( context );
1178     QProcess::startDetached( "HelpBrowser", parameters );
1179   }
1180 }
1181
1182 /*!
1183   Sets enable or disable some actions on selection changed.
1184 */
1185 void LightApp_Application::onSelectionChanged()
1186 {
1187   LightApp_Module* m = dynamic_cast<LightApp_Module*>( activeModule() );
1188   bool canCopy  = m ? m->canCopy() : false;
1189   bool canPaste = m ? m->canPaste() : false;
1190
1191   action( EditCopyId )->setEnabled(canCopy);
1192   action( EditPasteId )->setEnabled(canPaste);
1193 }
1194
1195 QWidget* LightApp_Application::dockWindow( const int id ) const
1196 {
1197   QWidget* wid = 0;
1198   if ( myWin.contains( id ) )
1199     wid = myWin[id];
1200   return wid;
1201 }
1202
1203 QDockWidget* LightApp_Application::windowDock( QWidget* wid ) const
1204 {
1205   if ( !wid )
1206     return 0;
1207
1208   QDockWidget* dock = 0;
1209   QWidget* w = wid->parentWidget();
1210   while ( w && !dock )
1211   {
1212     dock = ::qobject_cast<QDockWidget*>( w );
1213     w = w->parentWidget();
1214   }
1215   return dock;
1216 }
1217
1218 void LightApp_Application::insertDockWindow( const int id, QWidget* wid )
1219 {
1220   if ( !wid )
1221     return;
1222
1223   if ( wid != dockWindow( id ) )
1224     removeDockWindow( id );
1225
1226   myWin.insert( id, wid );
1227
1228   QtxDockWidget* dock = new QtxDockWidget( true, desktop() );
1229   connect( dock, SIGNAL(  destroyed( QObject* ) ), this, SLOT( onWCDestroyed( QObject* ) ) );
1230
1231   dock->setFeatures( QDockWidget::AllDockWidgetFeatures );
1232   dock->setObjectName( wid->objectName().isEmpty() ? QString( "window_%1" ).arg( id ) : 
1233                        QString( "%1Dock" ).arg( wid->objectName() ) );
1234   dock->setWidget( wid );
1235
1236   QKeySequence accel = wid->property( "shortcut" ).value<QKeySequence>();
1237   if ( !accel.isEmpty() )
1238     dock->toggleViewAction()->setShortcut( accel );
1239
1240   dock->show();
1241 }
1242
1243 void LightApp_Application::removeDockWindow( const int id )
1244 {
1245   QWidget* wid = dockWindow( id );
1246   if ( !wid )
1247     return;
1248
1249   myWin.remove( id );
1250
1251   QDockWidget* dock = windowDock( wid );
1252   if ( !dock )
1253     return;
1254
1255   dock->setWidget( 0 );
1256   wid->setParent( 0 );
1257   wid->setVisible( false );
1258   delete dock;
1259 }
1260
1261 void LightApp_Application::placeDockWindow( const int id, Qt::DockWidgetArea place )
1262 {
1263   QDockWidget* dock = windowDock( dockWindow( id ) );
1264   if ( dock && desktop() ) {
1265     desktop()->addDockWidget( place, dock );
1266     QtxDockAction* a = qobject_cast<QtxDockAction*>( action( ViewWindowsId ) );
1267     if ( a ) a->update();
1268   }
1269 }
1270
1271 /*!
1272   Gets window.
1273   \param flag - key for window
1274   \param studyId - study id
1275   Flag used how identificator of window in windows list.
1276 */
1277 QWidget* LightApp_Application::getWindow( const int flag, const int )
1278 {
1279   QWidget* wid = dockWindow( flag );
1280   if ( !wid )
1281     insertDockWindow( flag, wid = createWindow( flag ) );
1282
1283   QMap<int, int> winMap;
1284   currentWindows( winMap );
1285   if ( winMap.contains( flag ) )
1286     placeDockWindow( flag, (Qt::DockWidgetArea)winMap[flag] );
1287
1288   return wid;
1289 }
1290
1291 /*!
1292   \return Object Browser
1293 */
1294 SUIT_DataBrowser* LightApp_Application::objectBrowser()
1295 {
1296   return qobject_cast<SUIT_DataBrowser*>( dockWindow( WT_ObjectBrowser ) );
1297 }
1298
1299 /*!
1300   \return Log Window
1301 */
1302 LogWindow* LightApp_Application::logWindow()
1303 {
1304   return qobject_cast<LogWindow*>( dockWindow( WT_LogWindow ) );
1305 }
1306
1307 #ifndef DISABLE_PYCONSOLE
1308 /*!
1309   This returns the python console integrated to the GUI. Depending
1310   when you request the python console, this function could return
1311   null. Then the optional parameter force (default to false) can be
1312   set to force the creation of the python console if it is not done
1313   already. 
1314   \param force - if true, the pythonConsole is created if it does not exist yet
1315   \return Python Console
1316 */
1317 PyConsole_Console* LightApp_Application::pythonConsole(const bool force)
1318 {
1319   QWidget* wid = dockWindow( WT_PyConsole );
1320   if ( !wid && force==true) {
1321     wid = getWindow(WT_PyConsole);
1322   }
1323   return qobject_cast<PyConsole_Console*>( wid );
1324 }
1325 #endif
1326
1327 /*!
1328   Updates object browser and maybe data models
1329   \param updateModels - if it is true, then data models are updated
1330 */
1331 void LightApp_Application::updateObjectBrowser( const bool updateModels )
1332 {
1333   // update existing data models
1334   if ( updateModels )
1335   {
1336     const bool isAutoUpdate = objectBrowser() ? objectBrowser()->autoUpdate() : true;
1337     if ( objectBrowser() )
1338       objectBrowser()->setAutoUpdate( false );
1339
1340     LightApp_Study* study = dynamic_cast<LightApp_Study*>(activeStudy());
1341     if ( study ) {
1342       CAM_Study::ModelList dm_list;
1343       study->dataModels( dm_list );
1344       QListIterator<CAM_DataModel*> it( dm_list );
1345       while ( it.hasNext() ) {
1346         CAM_DataModel* camDM = it.next();
1347         if ( camDM && camDM->inherits( "LightApp_DataModel" ) )
1348           ((LightApp_DataModel*)camDM)->update();
1349       }
1350     }
1351
1352     if( objectBrowser() )
1353       objectBrowser()->setAutoUpdate( isAutoUpdate );
1354   }
1355
1356   if ( objectBrowser() ) {
1357     objectBrowser()->updateGeometry();
1358     objectBrowser()->updateTree( 0, false );
1359   }
1360 }
1361
1362 /*!
1363   \return preferences
1364 */
1365 LightApp_Preferences* LightApp_Application::preferences() const
1366 {
1367   return preferences( false );
1368 }
1369
1370 /*!
1371   \return first view manager of some type
1372   \param vmType - type of view manager
1373   \param create - is it necessary to create view manager in case, when there is no manager of such type
1374 */
1375 SUIT_ViewManager* LightApp_Application::getViewManager( const QString& vmType, const bool create )
1376 {
1377   SUIT_ViewManager* aVM = viewManager( vmType );
1378   SUIT_ViewManager* anActiveVM = CAM_Application::activeViewManager();
1379
1380   if ( anActiveVM && anActiveVM->getType() == vmType )
1381     aVM = anActiveVM;
1382
1383   if ( aVM && create )
1384   {
1385     if ( !aVM->getActiveView() )
1386       aVM->createView();
1387     else
1388       aVM->getActiveView()->setFocus();
1389   }
1390   else if ( create )
1391     aVM = createViewManager( vmType );
1392
1393   return aVM;
1394 }
1395
1396 /*!
1397   Creates view manager of some type
1398   \param vmType - type of view manager
1399 */
1400 SUIT_ViewManager* LightApp_Application::createViewManager( const QString& vmType )
1401 {
1402   SUIT_ResourceMgr* resMgr = resourceMgr();
1403
1404   SUIT_ViewManager* viewMgr = 0;
1405 #ifndef DISABLE_GLVIEWER
1406   if( vmType == GLViewer_Viewer::Type() )
1407   {
1408     viewMgr = new GLViewer_ViewManager( activeStudy(), desktop() );
1409     new LightApp_GLSelector( (GLViewer_Viewer2d*)viewMgr->getViewModel(), mySelMgr );
1410   }
1411 #endif
1412 #ifndef DISABLE_PLOT2DVIEWER
1413   if( vmType == Plot2d_Viewer::Type() )
1414   {
1415     viewMgr = new Plot2d_ViewManager( activeStudy(), desktop() );
1416     Plot2d_Viewer* vm;
1417 #ifndef DISABLE_SALOMEOBJECT
1418     SPlot2d_Viewer* v = new SPlot2d_Viewer();
1419     vm = v;
1420     new LightApp_Plot2dSelector( v, mySelMgr );
1421 #else
1422     vm = new Plot2d_Viewer();
1423 #endif
1424     viewMgr->setViewModel( vm  );// custom view model, which extends SALOME_View interface
1425     Plot2d_ViewWindow* wnd = dynamic_cast<Plot2d_ViewWindow*>( viewMgr->getActiveView() );
1426     if( wnd )
1427     {
1428       Plot2d_ViewFrame* frame = wnd->getViewFrame();
1429       frame->setBackgroundColor( resMgr->colorValue( "Plot2d", "Background", frame->backgroundColor() ) );
1430     }
1431   }
1432 #endif
1433 #ifndef DISABLE_QXGRAPHVIEWER
1434   if( vmType == QxScene_Viewer::Type() )
1435   {
1436     viewMgr = new QxScene_ViewManager( activeStudy(), desktop() );
1437     QxScene_Viewer* vm = new QxScene_Viewer();
1438     viewMgr->setViewModel( vm  );
1439     //QxScene_ViewWindow* wnd = dynamic_cast<QxScene_ViewWindow*>( viewMgr->getActiveView() );
1440   }
1441 #endif
1442 #ifndef DISABLE_GRAPHICSVIEW
1443   if( vmType == GraphicsView_Viewer::Type() )
1444   {
1445     viewMgr = new GraphicsView_ViewManager( activeStudy(), desktop() );
1446     new LightApp_GVSelector( (GraphicsView_Viewer*)viewMgr->getViewModel(), mySelMgr );
1447   }
1448 #endif
1449 #ifndef DISABLE_PVVIEWER
1450   if( vmType == PVViewer_Viewer::Type() )
1451   {
1452     viewMgr = new PVViewer_ViewManager( activeStudy(), desktop(), logWindow() );
1453   }
1454 #endif
1455 #ifndef DISABLE_OCCVIEWER
1456   if( vmType == OCCViewer_Viewer::Type() )
1457   {
1458     viewMgr = new OCCViewer_ViewManager( activeStudy(), desktop() );
1459     OCCViewer_Viewer* vm;
1460 #ifndef DISABLE_SALOMEOBJECT
1461     vm = new SOCC_Viewer();
1462 #else
1463     vm = new OCCViewer_Viewer( true );
1464 #endif
1465     vm->setBackground( OCCViewer_ViewFrame::TOP_LEFT,
1466                        resMgr->backgroundValue( "OCCViewer", "xz_background", vm->background(OCCViewer_ViewFrame::TOP_LEFT) ) );
1467     vm->setBackground( OCCViewer_ViewFrame::TOP_RIGHT,
1468                        resMgr->backgroundValue( "OCCViewer", "yz_background", vm->background(OCCViewer_ViewFrame::TOP_RIGHT) ) );
1469     vm->setBackground( OCCViewer_ViewFrame::BOTTOM_LEFT,
1470                        resMgr->backgroundValue( "OCCViewer", "xy_background", vm->background(OCCViewer_ViewFrame::BOTTOM_LEFT) ) );
1471     vm->setBackground( OCCViewer_ViewFrame::BOTTOM_RIGHT,
1472                        resMgr->backgroundValue( "OCCViewer", "background", vm->background(OCCViewer_ViewFrame::MAIN_VIEW) ) );
1473
1474     vm->setTrihedronSize(  resMgr->doubleValue( "3DViewer", "trihedron_size", vm->trihedronSize() ),
1475                            resMgr->booleanValue( "3DViewer", "relative_size", vm->trihedronRelative() ));
1476     vm->setInteractionStyle( resMgr->integerValue( "3DViewer", "navigation_mode", vm->interactionStyle() ) );
1477     vm->setZoomingStyle( resMgr->integerValue( "3DViewer", "zooming_mode", vm->zoomingStyle() ) );
1478     vm->enablePreselection( resMgr->booleanValue( "OCCViewer", "enable_preselection", vm->isPreselectionEnabled() ) );
1479     vm->enableSelection(    resMgr->booleanValue( "OCCViewer", "enable_selection",    vm->isSelectionEnabled() ) );
1480
1481     viewMgr->setViewModel( vm );// custom view model, which extends SALOME_View interface
1482     new LightApp_OCCSelector( (OCCViewer_Viewer*)viewMgr->getViewModel(), mySelMgr );
1483   }
1484 #endif
1485 #ifndef DISABLE_VTKVIEWER
1486 #ifndef DISABLE_SALOMEOBJECT
1487   if ( vmType == SVTK_Viewer::Type() )
1488 #else
1489   if ( vmType == VTKViewer_Viewer::Type() )
1490 #endif
1491   {
1492 #ifndef DISABLE_SALOMEOBJECT
1493     viewMgr = new SVTK_ViewManager( activeStudy(), desktop() );
1494     SVTK_Viewer* vm = dynamic_cast<SVTK_Viewer*>( viewMgr->getViewModel() );
1495     if( vm )
1496     {
1497       vm->setProjectionMode( resMgr->integerValue( "VTKViewer", "projection_mode", vm->projectionMode() ) );
1498       vm->setBackground( resMgr->backgroundValue( "VTKViewer", "background", vm->background() ) );
1499       vm->setTrihedronSize( resMgr->doubleValue( "3DViewer", "trihedron_size", vm->trihedronSize() ),
1500                             resMgr->booleanValue( "3DViewer", "relative_size", vm->trihedronRelative() ) );
1501       vm->setStaticTrihedronVisible( resMgr->booleanValue( "3DViewer", "show_static_trihedron", vm->isStaticTrihedronVisible() ) );
1502       vm->setInteractionStyle( resMgr->integerValue( "3DViewer", "navigation_mode", vm->interactionStyle() ) );
1503       vm->setZoomingStyle( resMgr->integerValue( "3DViewer", "zooming_mode", vm->zoomingStyle() ) );
1504       vm->setPreSelectionMode(resMgr->integerValue( "VTKViewer", "preselection", vm->preSelectionMode() ) );
1505       vm->enableSelection( resMgr->booleanValue( "VTKViewer", "enable_selection", vm->isSelectionEnabled() ) );
1506       vm->setIncrementalSpeed( resMgr->integerValue( "VTKViewer", "speed_value", vm->incrementalSpeed() ),
1507                                resMgr->integerValue( "VTKViewer", "speed_mode", vm->incrementalSpeedMode() ) );
1508       vm->setSpacemouseButtons( resMgr->integerValue( "VTKViewer", "spacemouse_func1_btn", vm->spacemouseBtn(1) ),
1509                                 resMgr->integerValue( "VTKViewer", "spacemouse_func2_btn", vm->spacemouseBtn(2) ),
1510                                 resMgr->integerValue( "VTKViewer", "spacemouse_func5_btn", vm->spacemouseBtn(3) ) );
1511       new LightApp_VTKSelector( vm, mySelMgr );
1512     }
1513 #else
1514     viewMgr = new VTKViewer_ViewManager( activeStudy(), desktop() );
1515     VTKViewer_Viewer* vm = dynamic_cast<VTKViewer_Viewer*>( viewMgr->getViewModel() );
1516     if ( vm )
1517       vm->setBackground( resMgr->backgroundValue( "VTKViewer", "background", vm->background() ) );
1518 #endif
1519   }
1520 #endif
1521
1522   if ( !viewMgr )
1523     return 0;
1524
1525   addViewManager( viewMgr );
1526   SUIT_ViewWindow* viewWin = viewMgr->createViewWindow();
1527
1528   if ( viewWin && desktop() ) {
1529     viewWin->resize( (int)( desktop()->width() * 0.6 ), (int)( desktop()->height() * 0.6 ) );
1530     viewWin->setDropDownButtons( resMgr->booleanValue( "viewers", "drop_down_buttons", true ) );
1531   }
1532
1533   return viewMgr;
1534 }
1535
1536 SUIT_ViewManager* LightApp_Application::createViewManager( const QString& vmType, QWidget* w )
1537 {
1538   SUIT_ResourceMgr* resMgr = resourceMgr();
1539
1540   SUIT_ViewManager* vm = new SUIT_ViewManager( activeStudy(),
1541                                                desktop(),
1542                                                new LightApp_WgViewModel( vmType, w ) );
1543   vm->setTitle( QString( "%1: %M - viewer %V" ).arg( vmType ) );
1544
1545   addViewManager( vm );
1546   SUIT_ViewWindow* vw = vm->createViewWindow();
1547   if ( vw && desktop() ) {
1548     vw->resize( (int)( desktop()->width() * 0.6 ), (int)( desktop()->height() * 0.6 ) );
1549     vw->setDropDownButtons( resMgr->booleanValue( "viewers", "drop_down_buttons", true ) );
1550   }
1551
1552   if ( !vmType.isEmpty() && !myUserWmTypes.contains( vmType ) )
1553     myUserWmTypes << vmType;
1554
1555   return vm;
1556 }
1557
1558 SUIT_ViewManager* LightApp_Application::createViewManager( SUIT_ViewModel* theModel )
1559 {
1560   SUIT_ResourceMgr* resMgr = resourceMgr();
1561
1562   SUIT_ViewManager* vm = new SUIT_ViewManager( activeStudy(),
1563                                                desktop(),
1564                                                theModel );
1565
1566   QString vmType = vm->getType();
1567
1568   vm->setTitle( QString( "%1: %M - viewer %V" ).arg( vmType ) );
1569
1570   addViewManager( vm );
1571   SUIT_ViewWindow* vw = vm->createViewWindow();
1572   if ( vw && desktop() ) {
1573     vw->resize( (int)( desktop()->width() * 0.6 ), (int)( desktop()->height() * 0.6 ) );
1574     vw->setDropDownButtons( resMgr->booleanValue( "viewers", "drop_down_buttons", true ) );
1575   }
1576
1577   if ( !vmType.isEmpty() && !myUserWmTypes.contains( vmType ) )
1578     myUserWmTypes << vmType;
1579
1580   return vm;
1581 }
1582
1583 /*!
1584   SLOT: Removes view manager from application
1585 */
1586 void LightApp_Application::onCloseView( SUIT_ViewManager* theVM )
1587 {
1588   removeViewManager( theVM );
1589 }
1590
1591 /*!
1592   Protected SLOT: On study created.
1593   \param theStudy - just created study
1594 */
1595 void LightApp_Application::onStudyCreated( SUIT_Study* theStudy )
1596 {
1597   SUIT_DataObject* aRoot = 0;
1598   if ( theStudy && theStudy->root() )
1599   {
1600     aRoot = theStudy->root();
1601     //aRoot->setName( tr( "DATA_MODELS" ) );
1602   }
1603
1604   getWindow( WT_ObjectBrowser );
1605
1606   loadDockWindowsState();
1607
1608   if ( objectBrowser() )
1609     objectBrowser()->setRoot( aRoot );
1610
1611   activateModule( defaultModule() );
1612
1613   if ( objectBrowser() )
1614     objectBrowser()->openLevels();
1615
1616 #ifndef DISABLE_PYCONSOLE
1617   if( pythonConsole() )
1618     getPyInterp()->initStudy();
1619 #endif
1620 }
1621
1622 /*!
1623   Protected SLOT: On study opened.
1624   \param theStudy - just opened  study
1625 */
1626 void LightApp_Application::onStudyOpened( SUIT_Study* theStudy )
1627 {
1628   SUIT_DataObject* aRoot = 0;
1629   if ( theStudy && theStudy->root() )
1630   {
1631     aRoot = theStudy->root();
1632     //aRoot->dump();
1633   }
1634
1635   getWindow( WT_ObjectBrowser );
1636
1637   loadDockWindowsState();
1638
1639   if ( objectBrowser() )
1640     objectBrowser()->setRoot( aRoot );
1641
1642   activateModule( defaultModule() );
1643
1644   if ( objectBrowser() )
1645     objectBrowser()->openLevels();
1646
1647 #ifndef DISABLE_PYCONSOLE
1648   if( pythonConsole() )
1649     getPyInterp()->initStudy();
1650 #endif
1651
1652   emit studyOpened();
1653 }
1654
1655 /*!Protected SLOT. On study saved.*/
1656 void LightApp_Application::onStudySaved( SUIT_Study* s )
1657 {
1658   QtxMRUAction* mru = ::qobject_cast<QtxMRUAction*>( action( MRUId ) );
1659   if ( mru && s )
1660       mru->insert( s->studyName() );
1661
1662   emit studySaved();
1663 }
1664
1665 /*!Protected SLOT. On study closed.*/
1666 void LightApp_Application::onStudyClosed( SUIT_Study* s )
1667 {
1668   /*
1669   disconnect( this, SIGNAL( viewManagerRemoved( SUIT_ViewManager* ) ),
1670               this, SLOT( onViewManagerRemoved( SUIT_ViewManager* ) ) );
1671   */
1672
1673   // stop auto-save timer
1674   myAutoSaveTimer->stop();
1675
1676   // Bug 10396: clear selection
1677   mySelMgr->clearSelected();
1678
1679   // Bug 12944: emit signal only after clear selection
1680   emit studyClosed();
1681
1682   activateModule( "" );
1683 }
1684
1685 /*!Protected SLOT.On desktop activated.*/
1686 void LightApp_Application::onDesktopActivated()
1687 {
1688   CAM_Application::onDesktopActivated();
1689   LightApp_Module* aModule = dynamic_cast<LightApp_Module*>(activeModule());
1690   if(aModule)
1691     aModule->studyActivated();
1692 }
1693
1694 void LightApp_Application::studyOpened( SUIT_Study* s )
1695 {
1696   CAM_Application::studyOpened( s );
1697
1698   updateWindows();
1699   updateViewManagers();
1700 }
1701
1702 void LightApp_Application::studySaved( SUIT_Study* s )
1703 {
1704   CAM_Application::studyOpened( s );
1705   SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
1706   if ( aResMgr && activeStudy() ) {
1707     int autoSaveInterval = aResMgr->integerValue( "Study", "auto_save_interval", 0 );
1708     if ( autoSaveInterval > 0 ) myAutoSaveTimer->start( autoSaveInterval*60000 );
1709   }
1710 }
1711
1712 void LightApp_Application::studyCreated( SUIT_Study* s )
1713 {
1714   CAM_Application::studyCreated( s );
1715
1716   updateWindows();
1717   updateViewManagers();
1718 }
1719
1720 /*!Gets file filter.
1721  *\retval QString "(*.bin)"
1722  */
1723 QString LightApp_Application::getFileFilter() const
1724 {
1725   //return "(*.bin)";
1726   // HDF persistence
1727   return "(*.hdf)";
1728 }
1729
1730 /*!
1731   Shows file dialog and return user selected file name
1732 */
1733 QString LightApp_Application::getFileName( bool open, const QString& initial, const QString& filters,
1734                                            const QString& caption, QWidget* parent )
1735 {
1736   if ( !parent )
1737     parent = desktop();
1738   QStringList fls = filters.split( ";;", QString::SkipEmptyParts );
1739   return SUIT_FileDlg::getFileName( parent, initial, fls, caption, open, true );
1740 }
1741
1742 /*! Gets directory*/
1743 QString LightApp_Application::getDirectory( const QString& initial, const QString& caption, QWidget* parent )
1744 {
1745   if ( !parent )
1746     parent = desktop();
1747   return SUIT_FileDlg::getExistingDirectory( parent, initial, caption, true );
1748 }
1749
1750 /*! Get open file names*/
1751 QStringList LightApp_Application::getOpenFileNames( const QString& initial, const QString& filters,
1752                                                     const QString& caption, QWidget* parent )
1753 {
1754   if ( !parent )
1755     parent = desktop();
1756   QStringList fls = filters.split( ";;", QString::SkipEmptyParts );
1757   return SUIT_FileDlg::getOpenFileNames( parent, initial, fls, caption, true );
1758 }
1759
1760 /*!Private SLOT. Update object browser.*/
1761 void LightApp_Application::onRefresh()
1762 {
1763   updateObjectBrowser( true );
1764 }
1765
1766 /*!Private SLOT. Support drag-and-drop operation.*/
1767 void LightApp_Application::onDropped( const QList<SUIT_DataObject*>& objects, SUIT_DataObject* parent, int row, Qt::DropAction action )
1768 {
1769   LightApp_DataObject* parentObj = dynamic_cast<LightApp_DataObject*>( parent );
1770   if ( !parentObj )
1771     return;
1772
1773   LightApp_Module* aModule = dynamic_cast<LightApp_Module*>( parentObj->module() );
1774   if ( aModule )
1775     aModule->dropObjects( objects, parentObj, row, action );
1776 }
1777
1778 /*!Private SLOT. On preferences.*/
1779 void LightApp_Application::onPreferences()
1780 {
1781   showPreferences( activeModule() ? activeModule()->moduleName() : tr( "PREF_CATEGORY_SALOME" ) );
1782 }
1783
1784 /*!Private SLOT. On preferences.*/
1785 void LightApp_Application::showPreferences( const QString& itemText )
1786 {
1787   QApplication::setOverrideCursor( Qt::WaitCursor );
1788
1789   LightApp_PreferencesDlg* prefDlg = new LightApp_PreferencesDlg( preferences( true ), desktop());
1790
1791   QApplication::restoreOverrideCursor();
1792
1793   if ( !prefDlg )
1794     return;
1795
1796   preferences()->activateItem( itemText );
1797
1798   if ( ( prefDlg->exec() == QDialog::Accepted || prefDlg->isSaved() ) &&  resourceMgr() )
1799   {
1800     if ( desktop() )
1801       resourceMgr()->setValue( "desktop", "geometry", desktop()->storeGeometry() );
1802     resourceMgr()->save();
1803
1804     // Update shortcuts
1805     shortcutMgr()->updateShortcuts();
1806   }
1807
1808   delete prefDlg;
1809 }
1810
1811 /*!Protected SLOT. On preferences changed.*/
1812 void LightApp_Application::onPreferenceChanged( QString& modName, QString& section, QString& param )
1813 {
1814   LightApp_Module* sMod = 0;
1815   CAM_Module* mod = module( modName );
1816   if ( mod && mod->inherits( "LightApp_Module" ) )
1817     sMod = (LightApp_Module*)mod;
1818
1819   if ( sMod )
1820     sMod->preferencesChanged( section, param );
1821   else
1822     preferencesChanged( section, param );
1823   // emit signal to allow additional preferences changing processing
1824   emit preferenceChanged( modName, section, param );
1825 }
1826
1827 /*!Remove all windows from study.*/
1828 void LightApp_Application::beforeCloseDoc( SUIT_Study* s )
1829 {
1830   saveDockWindowsState();
1831
1832   if ( SUIT_DataBrowser* ob = objectBrowser() )
1833     ob->setModel(0);
1834
1835   CAM_Application::beforeCloseDoc( s );
1836 }
1837
1838 /*!Update actions.*/
1839 void LightApp_Application::updateActions()
1840 {
1841   updateCommandsStatus();
1842 }
1843
1844 /*!
1845   Creates new study
1846 */
1847 SUIT_Study* LightApp_Application::createNewStudy()
1848 {
1849   LightApp_Application::lastStudyId++;
1850
1851   LightApp_Study* aStudy = new LightApp_Study( this );
1852
1853   // Set up processing of major study-related events
1854   connect( aStudy, SIGNAL( created( SUIT_Study* ) ), this, SLOT( onStudyCreated( SUIT_Study* ) ) );
1855   connect( aStudy, SIGNAL( opened ( SUIT_Study* ) ), this, SLOT( onStudyOpened ( SUIT_Study* ) ) );
1856   connect( aStudy, SIGNAL( saved  ( SUIT_Study* ) ), this, SLOT( onStudySaved  ( SUIT_Study* ) ) );
1857   connect( aStudy, SIGNAL( closed ( SUIT_Study* ) ), this, SLOT( onStudyClosed ( SUIT_Study* ) ) );
1858
1859   return aStudy;
1860 }
1861
1862 /*!
1863   Creates window by flag.
1864   \param flag - identificator of window type
1865 */
1866 QWidget* LightApp_Application::createWindow( const int flag )
1867 {
1868   QWidget* wid = 0;
1869
1870   SUIT_ResourceMgr* resMgr = resourceMgr();
1871
1872   if ( flag == WT_ObjectBrowser )
1873   {
1874     SUIT_DataBrowser* ob = new SUIT_DataBrowser( new LightApp_DataObject(), desktop() );
1875     ob->setObjectName( "objectBrowser" );
1876     ob->setSortMenuEnabled( true );
1877     ob->setAutoUpdate( true );
1878     if ( resMgr->hasValue( "ObjectBrowser", "auto_hide_search_tool" ) )
1879       ob->searchTool()->enableAutoHide( resMgr->booleanValue( "ObjectBrowser", "auto_hide_search_tool" ) );
1880
1881     //ob->setAutoOpenLevel( 1 ); // commented by ASV as a fix to bug IPAL10107
1882     ob->setWindowTitle( tr( "OBJECT_BROWSER" ) );
1883     connect( ob, SIGNAL( requestUpdate() ), this, SLOT( onRefresh() ) );
1884
1885     QString EntryCol = QObject::tr( "ENTRY_COLUMN" );
1886     SUIT_AbstractModel* treeModel = dynamic_cast<SUIT_AbstractModel*>( ob->model() );
1887     treeModel->setSearcher( this );
1888     treeModel->registerColumn( 0, EntryCol, LightApp_DataObject::EntryId );
1889     treeModel->setAppropriate( EntryCol, Qtx::Toggled );
1890
1891     // Mantis issue 0020136: Drag&Drop in OB
1892     SUIT_ProxyModel* proxyModel = dynamic_cast<SUIT_ProxyModel*>(treeModel);
1893     if ( proxyModel ) {
1894       connect( proxyModel, SIGNAL( dropped( const QList<SUIT_DataObject*>&, SUIT_DataObject*, int, Qt::DropAction ) ),
1895                this,       SLOT( onDropped( const QList<SUIT_DataObject*>&, SUIT_DataObject*, int, Qt::DropAction ) ) );
1896     }
1897
1898     // temporary commented
1899     /*
1900     OB_ListView* ob_list = dynamic_cast<OB_ListView*>( const_cast<QListView*>( ob->listView() ) );
1901     if( ob_list )
1902       ob_list->setColumnMaxWidth( 0, desktop()->width()/4 );
1903     */
1904
1905     // Create OBSelector
1906     new LightApp_OBSelector( ob, mySelMgr );
1907
1908     ob->treeView()->header()->setResizeMode(SUIT_DataObject::VisibilityId, QHeaderView::Fixed);
1909     ob->treeView()->header()->moveSection(SUIT_DataObject::NameId,SUIT_DataObject::VisibilityId);
1910     ob->treeView()->setColumnWidth(SUIT_DataObject::VisibilityId, VISIBILITY_COLUMN_WIDTH);
1911     ob->setProperty( "shortcut", QKeySequence( "Alt+Shift+O" ) );
1912     wid = ob;
1913     ob->connectPopupRequest( this, SLOT( onConnectPopupRequest( SUIT_PopupClient*, QContextMenuEvent* ) ) );
1914   }
1915 #ifndef DISABLE_PYCONSOLE
1916   else  if ( flag == WT_PyConsole )
1917   {
1918     PyConsole_Console* pyCons = new PyConsole_EnhConsole( desktop(), getPyInterp() );
1919     pyCons->setObjectName( "pythonConsole" );
1920     pyCons->setWindowTitle( tr( "PYTHON_CONSOLE" ) );
1921     pyCons->setFont(resourceMgr()->fontValue( "PyConsole", "font" ));
1922     pyCons->setIsShowBanner(resourceMgr()->booleanValue( "PyConsole", "show_banner", true ));
1923     pyCons->setProperty( "shortcut", QKeySequence( "Alt+Shift+P" ) );
1924
1925     wid = pyCons;
1926     pyCons->connectPopupRequest( this, SLOT( onConnectPopupRequest( SUIT_PopupClient*, QContextMenuEvent* ) ) );
1927   }
1928 #endif
1929   else if ( flag == WT_LogWindow )
1930   {
1931     LogWindow* logWin = new LogWindow( desktop() );
1932     logWin->setObjectName( "logWindow" );
1933     logWin->setWindowTitle( tr( "LOG_WINDOW" ) );
1934     logWin->setProperty( "shortcut", QKeySequence( "Alt+Shift+L" ) );
1935     wid = logWin;
1936     logWin->connectPopupRequest( this, SLOT( onConnectPopupRequest( SUIT_PopupClient*, QContextMenuEvent* ) ) );
1937   }
1938   return wid;
1939 }
1940
1941 /*!
1942   \return default windows( Object Browser, Python Console )
1943   Adds to map \a aMap.
1944  */
1945 void LightApp_Application::defaultWindows( QMap<int, int>& aMap ) const
1946 {
1947 #ifndef DISABLE_PYCONSOLE
1948   aMap.insert( WT_PyConsole, Qt::BottomDockWidgetArea );
1949 #endif
1950   if ( activeStudy() ) {
1951     aMap.insert( WT_ObjectBrowser, Qt::LeftDockWidgetArea );
1952     //  aMap.insert( WT_LogWindow, Qt::DockBottom );
1953   }
1954 }
1955
1956 /*!Default view managers*/
1957 void LightApp_Application::defaultViewManagers( QStringList& ) const
1958 {
1959   /*!Do nothing.*/
1960 }
1961
1962 /*!
1963   \return preferences.
1964   Create preferences, if \a crt = true.
1965 */
1966 LightApp_Preferences* LightApp_Application::preferences( const bool crt ) const
1967 {
1968   if ( myPrefs )
1969     return myPrefs;
1970
1971   LightApp_Application* that = (LightApp_Application*)this;
1972
1973   bool toCreate = !_prefs_ && crt;
1974   if ( toCreate )
1975   {
1976     _prefs_ = new LightApp_Preferences( resourceMgr() );
1977     that->createPreferences( _prefs_ );
1978   }
1979
1980   that->myPrefs = _prefs_;
1981
1982   connect( myPrefs, SIGNAL( preferenceChanged( QString&, QString&, QString& ) ),
1983            this, SLOT( onPreferenceChanged( QString&, QString&, QString& ) ), Qt::UniqueConnection );
1984   connect( myPrefs, SIGNAL( resetToDefaults() ),
1985            this, SIGNAL( preferenceResetToDefaults() ), Qt::UniqueConnection );
1986
1987   if ( !crt )
1988     return myPrefs;
1989
1990   SUIT_ResourceMgr* resMgr = resourceMgr();
1991
1992   QList<SUIT_Application*> appList = SUIT_Session::session()->applications();
1993   for ( QList<SUIT_Application*>::iterator appIt = appList.begin(); appIt != appList.end(); ++appIt )
1994   {
1995     LightApp_Application* app = ::qobject_cast<LightApp_Application*>( *appIt );
1996     if ( !app )
1997       continue;
1998
1999     QStringList modNameList;
2000     app->modules( modNameList, false );
2001
2002     QMap<QString, QString> iconMap;
2003     app->moduleIconNames( iconMap );
2004
2005     for ( QStringList::const_iterator it = modNameList.begin(); it != modNameList.end(); ++it )
2006     {
2007       if ( !app->isLibExists( *it ) || _prefs_->hasModule( *it ) )
2008         continue;
2009
2010       int modId = _prefs_->addPreference( *it );
2011       if ( iconMap.contains( *it ) )
2012         _prefs_->setItemIcon( modId, Qtx::scaleIcon( resMgr->loadPixmap( moduleName( *it ), iconMap[*it], false ), 20 ) );
2013     }
2014
2015     ModuleList modList;
2016     app->modules( modList );
2017     QListIterator<CAM_Module*> itr( modList );
2018     while ( itr.hasNext() )
2019     {
2020       LightApp_Module* mod = 0;
2021
2022       CAM_Module* anItem = itr.next();
2023       if ( anItem->inherits( "LightApp_Module" ) )
2024         mod = (LightApp_Module*)anItem;
2025
2026       if ( mod && !_prefs_->hasModule( mod->moduleName() ) )
2027       {
2028         _prefs_->addPreference( mod->moduleName() );
2029         mod->createPreferences();
2030         that->emptyPreferences( mod->moduleName() );
2031       }
2032     }
2033   }
2034   _prefs_->setItemProperty( "info", tr( "PREFERENCES_NOT_LOADED" ) );
2035
2036   return myPrefs;
2037 }
2038
2039 /*!
2040   Adds new module to application
2041 */
2042 void LightApp_Application::moduleAdded( CAM_Module* mod )
2043 {
2044   CAM_Application::moduleAdded( mod );
2045
2046   LightApp_Module* lightMod = 0;
2047   if ( mod && mod->inherits( "LightApp_Module" ) )
2048     lightMod = (LightApp_Module*)mod;
2049
2050   if ( myPrefs && lightMod && !myPrefs->hasModule( lightMod->moduleName() ))
2051   {
2052     myPrefs->addPreference( mod->moduleName() );
2053     lightMod->createPreferences();
2054     emptyPreferences( mod->moduleName() );
2055   }
2056 }
2057
2058 void LightApp_Application::emptyPreferences( const QString& modName )
2059 {
2060   QtxPreferenceItem* item = myPrefs->findItem( modName, true );
2061   if ( !item || !item->isEmpty() )
2062     return;
2063
2064   //  printf( "---------------------> Modify for empty module.\n" );
2065
2066   QtxPagePrefFrameItem* frm = new QtxPagePrefFrameItem( item->title(), item->parentItem() );
2067   frm->setIcon( item->icon() );
2068   frm->setStretch( false );
2069   item->parentItem()->insertItem( frm, item );
2070   new QtxPagePrefLabelItem( Qt::AlignCenter, tr( "PREFERENCES_NOT_SUPPORTED" ).arg( modName ), frm );
2071   delete item;
2072 }
2073
2074 /*!
2075   Create preferences
2076 */
2077 void LightApp_Application::createPreferences( LightApp_Preferences* pref )
2078 {
2079   if ( !pref )
2080     return;
2081
2082   QStringList     aValuesList;
2083   QList<QVariant> anIndicesList;
2084   QIntList        idList;
2085   QIntList        txtList;
2086
2087   // . Top-level "SALOME" preferences group <<start>>
2088   int salomeCat = pref->addPreference( tr( "PREF_CATEGORY_SALOME" ) );
2089   pref->setItemIcon( salomeCat, Qtx::scaleIcon( resourceMgr()->loadPixmap( "LightApp", tr( "APP_DEFAULT_ICO" ), false ), 20 ) );
2090
2091   // .. "General" preferences tab <<start>>
2092   int genTab = pref->addPreference( tr( "PREF_TAB_GENERAL" ), salomeCat );
2093
2094   // ... "Language" group <<start>>
2095   int langGroup = pref->addPreference( tr( "PREF_GROUP_LANGUAGE" ), genTab );
2096   pref->setItemProperty( "columns", 2, langGroup );
2097   // .... -> application language
2098   int curLang = pref->addPreference( tr( "PREF_CURRENT_LANGUAGE" ), langGroup,
2099                                           LightApp_Preferences::Selector, "language", "language" );
2100   QStringList aLangs = SUIT_Session::session()->resourceMgr()->stringValue( "language", "languages", "en" ).split( "," );
2101   QList<QVariant> aIcons;
2102   foreach ( QString aLang, aLangs ) {
2103     aIcons << QPixmap( QString( ":/images/%1" ).arg( aLang ) );
2104   }
2105   pref->setItemProperty( "strings", aLangs, curLang );
2106   pref->setItemProperty( "icons",   aIcons, curLang );
2107
2108   int curLocale = pref->addPreference( tr( "PREF_CURRENT_LOCALE" ), langGroup,
2109                                           LightApp_Preferences::Bool, "language", "locale" );
2110   // ... "Language" group <<end>>
2111
2112   // ... "Look and feel" group <<start>>
2113   int lookGroup = pref->addPreference( tr( "PREF_GROUP_LOOK_AND_FEEL" ), genTab );
2114   pref->setItemProperty( "columns", 2, lookGroup );
2115   // .... -> show splash-screen
2116   pref->addPreference( tr( "PREF_SHOW_SPLASH" ), lookGroup, LightApp_Preferences::Bool, "launch", "splash" );
2117   // .... -> opaque resize
2118   pref->addPreference( tr( "PREF_OPAQUE_RESIZE" ), lookGroup, LightApp_Preferences::Bool, "desktop", "opaque_resize" );
2119   // .... -> drop-down buttons 
2120   pref->addPreference( tr( "PREF_DROP_DOWN_BUTTONS" ), lookGroup, LightApp_Preferences::Bool, "viewers", "drop_down_buttons" );
2121   // ... "Look and feel" group <<end>>
2122
2123   // ... "Study properties" group <<start>>
2124   int studyGroup = pref->addPreference( tr( "PREF_GROUP_STUDY" ), genTab );
2125   pref->setItemProperty( "columns", 2, studyGroup );
2126   // .... -> multi-file save
2127   pref->addPreference( tr( "PREF_MULTI_FILE" ), studyGroup, LightApp_Preferences::Bool, "Study", "multi_file" );
2128   // .... -> ascii save mode
2129   pref->addPreference( tr( "PREF_ASCII_FILE" ), studyGroup, LightApp_Preferences::Bool, "Study", "ascii_file" );
2130   // .... -> store windows geometry
2131   pref->addPreference( tr( "PREF_STORE_POS" ),  studyGroup, LightApp_Preferences::Bool, "Study", "store_positions" );
2132   pref->addPreference( "", studyGroup, LightApp_Preferences::Space );
2133   pref->addPreference( tr( "PREF_STORE_TOOL_POS" ),  studyGroup, LightApp_Preferences::Bool, "Study", "store_tool_positions" );
2134   // .... -> auto-save
2135   int autoSaveInterval = pref->addPreference( tr( "PREF_AUTO_SAVE" ),  studyGroup,
2136                                               LightApp_Preferences::IntSpin, "Study", "auto_save_interval" );
2137   pref->setItemProperty( "min",        0, autoSaveInterval );
2138   pref->setItemProperty( "max",     1440, autoSaveInterval );
2139   pref->setItemProperty( "special", tr( "PREF_AUTO_SAVE_DISABLED" ), autoSaveInterval );
2140   // ... "Study properties" group <<end>>
2141
2142   // ... "Help browser" group <<start>>
2143   int extgroup = pref->addPreference( tr( "PREF_GROUP_EXT_BROWSER" ), genTab, LightApp_Preferences::Auto, "ExternalBrowser", "use_external_browser");
2144 #ifdef WIN32
2145   QString platform = "winapplication";
2146 #else
2147   QString platform = "application";
2148 #endif
2149   // .... -> browser application
2150   int apppref = pref->addPreference( tr( "PREF_APP" ), extgroup, LightApp_Preferences::File, "ExternalBrowser", platform );
2151   pref->setItemProperty( "mode", Qtx::PT_OpenFile, apppref );
2152   // .... -> browser parameters
2153   pref->addPreference( tr( "PREF_PARAM" ), extgroup, LightApp_Preferences::String, "ExternalBrowser", "parameters" );
2154   // ... "Help browser" group <<end>>
2155
2156   // ... "Python console properties" group <<start>>
2157   int pythonConsoleGroup = pref->addPreference( tr( "PREF_GROUP_PY_CONSOLE" ), genTab );
2158   // .... -> font
2159   pref->addPreference( tr( "PREF_FONT" ), pythonConsoleGroup, LightApp_Preferences::Font, "PyConsole", "font" );
2160   // .... -> show banner
2161   pref->addPreference( tr( "PREF_SHOW_BANNER" ), pythonConsoleGroup, LightApp_Preferences::Bool, "PyConsole", "show_banner" );
2162   // ... "Python console properties" group <<end>>
2163
2164   // ... "MRU" preferences group <<start>>
2165   int mruGroup = pref->addPreference( tr( "PREF_GROUP_MRU" ), genTab, LightApp_Preferences::Auto, "MRU", "show_mru" );
2166   pref->setItemProperty( "columns", 4, mruGroup );
2167   // number of MRU items
2168   int mruVisCount = pref->addPreference( tr( "PREF_MRU_VISIBLE_COUNT" ), mruGroup, LightApp_Preferences::IntSpin,
2169                                          "MRU", "visible_count" );
2170   pref->setItemProperty( "min", 0,   mruVisCount );
2171   pref->setItemProperty( "max", 100, mruVisCount );
2172   // MRU links type
2173   int mruLinkType = pref->addPreference( tr( "PREF_MRU_LINK_TYPE" ), mruGroup, LightApp_Preferences::Selector,
2174                                          "MRU", "link_type" );
2175   aValuesList.clear();
2176   anIndicesList.clear();
2177   aValuesList   << tr("PREF_MRU_LINK_AUTO") << tr("PREF_MRU_LINK_SHORT") << tr("PREF_MRU_LINK_FULL");
2178   anIndicesList << 0                        << 1                         << 2                       ;
2179   pref->setItemProperty( "strings", aValuesList,   mruLinkType );
2180   pref->setItemProperty( "indexes", anIndicesList, mruLinkType );
2181   // ... "MRU" preferences group <<end>>
2182   // .. "General" preferences tab <<end>>
2183
2184   // .. "3D viewer" group <<start>>
2185   int Viewer3DGroup = pref->addPreference( tr( "PREF_GROUP_3DVIEWER" ), salomeCat );
2186   // ... -> navigation mode
2187   int vtkStyleMode = pref->addPreference( tr( "PREF_NAVIGATION" ), Viewer3DGroup,
2188                                           LightApp_Preferences::Selector, "3DViewer", "navigation_mode" );
2189   aValuesList.clear();
2190   anIndicesList.clear();
2191   aValuesList   << tr("PREF_STANDARD_STYLE") << tr("PREF_KEYFREE_STYLE");
2192   anIndicesList << 0                         << 1;
2193   pref->setItemProperty( "strings", aValuesList,   vtkStyleMode );
2194   pref->setItemProperty( "indexes", anIndicesList, vtkStyleMode );
2195   // ... -> zooming mode
2196   int occZoomingStyleMode = pref->addPreference( tr( "PREF_ZOOMING" ), Viewer3DGroup,
2197                                                  LightApp_Preferences::Selector, "3DViewer", "zooming_mode" );
2198   aValuesList.clear();
2199   anIndicesList.clear();
2200   aValuesList   << tr("PREF_ZOOMING_AT_CENTER") << tr("PREF_ZOOMING_AT_CURSOR");
2201   anIndicesList << 0                            << 1;
2202   pref->setItemProperty( "strings", aValuesList,   occZoomingStyleMode );
2203   pref->setItemProperty( "indexes", anIndicesList, occZoomingStyleMode );
2204   // ... "Trihedron" group <<start>>
2205   int occTriGroup = pref->addPreference( tr( "PREF_TRIHEDRON" ), Viewer3DGroup );
2206   pref->setItemProperty( "columns", 2, occTriGroup );
2207   // .... -> trihedron size
2208   int occTS = pref->addPreference( tr( "PREF_TRIHEDRON_SIZE" ), occTriGroup,
2209                                    LightApp_Preferences::DblSpin, "3DViewer", "trihedron_size" );
2210   pref->setItemProperty( "min", 1.0E-06, occTS );
2211   pref->setItemProperty( "max", 1000, occTS );
2212   // .... -> relative size of trihedron
2213   pref->addPreference( tr( "PREF_RELATIVE_SIZE" ), occTriGroup, LightApp_Preferences::Bool, "3DViewer", "relative_size" );
2214   // .... -> show static trihedron
2215   pref->addPreference( tr( "PREF_SHOW_STATIC_TRIHEDRON" ), occTriGroup, LightApp_Preferences::Bool, "3DViewer", "show_static_trihedron" );
2216   // ... "Trihedron" group <<end>>
2217   // .. "3D viewer" group <<end>>
2218
2219   QString formats;
2220   int bgId;
2221 #ifndef DISABLE_OCCVIEWER
2222   // .. "OCC viewer" group <<start>>
2223   int occGroup = pref->addPreference( tr( "PREF_GROUP_OCCVIEWER" ), salomeCat );
2224
2225   // ... "Background" group <<start>>
2226   int bgGroup = pref->addPreference( tr( "PREF_VIEWER_BACKGROUND" ), occGroup );
2227   //  pref->setItemProperty( "columns", 2, bgGroup );
2228   aValuesList.clear();
2229   anIndicesList.clear();
2230   txtList.clear();
2231   formats = OCCViewer_Viewer::backgroundData( aValuesList, idList, txtList );
2232   foreach( int gid, idList ) anIndicesList << gid;
2233   // .... -> 3D viewer background
2234   bgId = pref->addPreference( tr( "PREF_3DVIEWER_BACKGROUND" ), bgGroup,
2235                                   LightApp_Preferences::Background, "OCCViewer", "background" );
2236   pref->setItemProperty( "gradient_names", aValuesList, bgId );
2237   pref->setItemProperty( "gradient_ids", anIndicesList, bgId );
2238   pref->setItemProperty( "texture_enabled", !txtList.isEmpty(), bgId );
2239   pref->setItemProperty( "texture_center_enabled", (bool)txtList.contains( Qtx::CenterTexture ), bgId );
2240   pref->setItemProperty( "texture_tile_enabled", (bool)txtList.contains( Qtx::TileTexture ), bgId );
2241   pref->setItemProperty( "texture_stretch_enabled", (bool)txtList.contains( Qtx::StretchTexture ), bgId );
2242   pref->setItemProperty( "custom_enabled", false, bgId );
2243   pref->setItemProperty( "image_formats", formats, bgId );
2244   // .... -> XZ viewer background
2245   bgId = pref->addPreference( tr( "PREF_XZVIEWER_BACKGROUND" ), bgGroup,
2246                               LightApp_Preferences::Background, "OCCViewer", "xz_background" );
2247   pref->setItemProperty( "gradient_names", aValuesList, bgId );
2248   pref->setItemProperty( "gradient_ids", anIndicesList, bgId );
2249   pref->setItemProperty( "texture_enabled", !txtList.isEmpty(), bgId );
2250   pref->setItemProperty( "texture_center_enabled", (bool)txtList.contains( Qtx::CenterTexture ), bgId );
2251   pref->setItemProperty( "texture_tile_enabled", (bool)txtList.contains( Qtx::TileTexture ), bgId );
2252   pref->setItemProperty( "texture_stretch_enabled", (bool)txtList.contains( Qtx::StretchTexture ), bgId );
2253   pref->setItemProperty( "custom_enabled", false, bgId );
2254   pref->setItemProperty( "image_formats", formats, bgId );
2255   // .... -> YZ viewer background
2256   bgId = pref->addPreference( tr( "PREF_YZVIEWER_BACKGROUND" ), bgGroup,
2257                               LightApp_Preferences::Background, "OCCViewer", "yz_background" );
2258   pref->setItemProperty( "gradient_names", aValuesList, bgId );
2259   pref->setItemProperty( "gradient_ids", anIndicesList, bgId );
2260   pref->setItemProperty( "texture_enabled", !txtList.isEmpty(), bgId );
2261   pref->setItemProperty( "texture_center_enabled", (bool)txtList.contains( Qtx::CenterTexture ), bgId );
2262   pref->setItemProperty( "texture_tile_enabled", (bool)txtList.contains( Qtx::TileTexture ), bgId );
2263   pref->setItemProperty( "texture_stretch_enabled", (bool)txtList.contains( Qtx::StretchTexture ), bgId );
2264   pref->setItemProperty( "custom_enabled", false, bgId );
2265   pref->setItemProperty( "image_formats", formats, bgId );
2266   // .... -> XY viewer background
2267   bgId = pref->addPreference( tr( "PREF_XYVIEWER_BACKGROUND" ), bgGroup,
2268                               LightApp_Preferences::Background, "OCCViewer", "xy_background" );
2269   pref->setItemProperty( "gradient_names", aValuesList, bgId );
2270   pref->setItemProperty( "gradient_ids", anIndicesList, bgId );
2271   pref->setItemProperty( "texture_enabled", !txtList.isEmpty(), bgId );
2272   pref->setItemProperty( "texture_center_enabled", (bool)txtList.contains( Qtx::CenterTexture ), bgId );
2273   pref->setItemProperty( "texture_tile_enabled", (bool)txtList.contains( Qtx::TileTexture ), bgId );
2274   pref->setItemProperty( "texture_stretch_enabled", (bool)txtList.contains( Qtx::StretchTexture ), bgId );
2275   pref->setItemProperty( "custom_enabled", false, bgId );
2276   pref->setItemProperty( "image_formats", formats, bgId );
2277   // ... "Background" group <<end>>
2278
2279
2280   // ... "Selection" group <<start>>
2281   int occSelectionGroup = pref->addPreference( tr( "PREF_GROUP_SELECTION" ), occGroup );
2282   pref->setItemProperty( "columns", 2, occSelectionGroup );
2283   // .... -> enable preselection
2284   pref->addPreference( tr( "PREF_ENABLE_PRESELECTION" ), occSelectionGroup, 
2285                        LightApp_Preferences::Bool, "OCCViewer", "enable_preselection" );
2286   // .... -> enable selection
2287   pref->addPreference( tr( "PREF_ENABLE_SELECTION" ), occSelectionGroup, 
2288                        LightApp_Preferences::Bool, "OCCViewer", "enable_selection" );
2289   // ... "Selection" group <<end>>
2290
2291   // ... -> empty frame (for layout) <<start>>
2292   int occGen = pref->addPreference( "", occGroup, LightApp_Preferences::Frame );
2293   pref->setItemProperty( "margin",  0, occGen );
2294   pref->setItemProperty( "columns", 2, occGen );
2295   // ... -> empty frame (for layout) <<end>>
2296   // .. "OCC viewer" group <<end>>
2297 #endif
2298
2299 #ifndef DISABLE_VTKVIEWER
2300   // .. "VTK viewer" group <<start>>
2301   int vtkGroup = pref->addPreference( tr( "PREF_GROUP_VTKVIEWER" ), salomeCat ); //viewTab
2302
2303   // ... -> empty frame (for layout) <<start>>
2304   int vtkGen = pref->addPreference( "", vtkGroup, LightApp_Preferences::Frame );
2305   //pref->setItemProperty( "columns", 2, vtkGen );
2306   // .... -> projection mode
2307   int vtkProjMode = pref->addPreference( tr( "PREF_PROJECTION_MODE" ), vtkGen,
2308                                          LightApp_Preferences::Selector, "VTKViewer", "projection_mode" );
2309   aValuesList.clear();
2310   anIndicesList.clear();
2311   aValuesList   << tr("PREF_ORTHOGRAPHIC") << tr("PREF_PERSPECTIVE");
2312   anIndicesList << 0                       << 1;
2313   pref->setItemProperty( "strings", aValuesList,   vtkProjMode );
2314   pref->setItemProperty( "indexes", anIndicesList, vtkProjMode );
2315   // .... -> background
2316   aValuesList.clear();
2317   anIndicesList.clear();
2318   txtList.clear();
2319 #ifndef DISABLE_SALOMEOBJECT
2320   formats = SVTK_Viewer::backgroundData( aValuesList, idList, txtList );
2321 #endif
2322   foreach( int gid, idList ) anIndicesList << gid;
2323   bgId = pref->addPreference( tr( "PREF_VIEWER_BACKGROUND" ), vtkGen,
2324                               LightApp_Preferences::Background, "VTKViewer", "background" );
2325   pref->setItemProperty( "gradient_names", aValuesList, bgId );
2326   pref->setItemProperty( "gradient_ids", anIndicesList, bgId );
2327   pref->setItemProperty( "texture_enabled", !txtList.isEmpty(), bgId );
2328   pref->setItemProperty( "texture_center_enabled", (bool)txtList.contains( Qtx::CenterTexture ), bgId );
2329   pref->setItemProperty( "texture_tile_enabled", (bool)txtList.contains( Qtx::TileTexture ), bgId );
2330   pref->setItemProperty( "texture_stretch_enabled", (bool)txtList.contains( Qtx::StretchTexture ), bgId );
2331   pref->setItemProperty( "custom_enabled", false, bgId );
2332 #ifndef DISABLE_SALOMEOBJECT
2333   pref->setItemProperty( "image_formats", formats, bgId );
2334 #endif
2335   // .... -> speed increment
2336   int vtkSpeed = pref->addPreference( tr( "PREF_INCREMENTAL_SPEED" ), vtkGen,
2337                                       LightApp_Preferences::IntSpin, "VTKViewer", "speed_value" );
2338   pref->setItemProperty( "min", 1, vtkSpeed );
2339   pref->setItemProperty( "max", 1000, vtkSpeed );
2340   // .... -> speed mode
2341   int vtkSpeedMode = pref->addPreference( tr( "PREF_INCREMENTAL_SPEED_MODE" ), vtkGen,
2342                                           LightApp_Preferences::Selector, "VTKViewer", "speed_mode" );
2343   aValuesList.clear();
2344   anIndicesList.clear();
2345   aValuesList   << tr("PREF_ARITHMETIC") << tr("PREF_GEOMETRICAL");
2346   anIndicesList << 0                     << 1;
2347   pref->setItemProperty( "strings", aValuesList,   vtkSpeedMode );
2348   pref->setItemProperty( "indexes", anIndicesList, vtkSpeedMode );
2349
2350   // ... "Selection" group <<start>>
2351   int vtkSelectionGroup = pref->addPreference( tr( "PREF_GROUP_SELECTION" ), vtkGroup );
2352   pref->setItemProperty( "columns", 2, vtkSelectionGroup );
2353   // .... -> preselection
2354   int vtkPreselection = pref->addPreference( tr( "PREF_PRESELECTION" ),  vtkSelectionGroup, 
2355                                              LightApp_Preferences::Selector, "VTKViewer", "preselection" );
2356   aValuesList.clear();
2357   anIndicesList.clear();
2358   aValuesList   << tr("PREF_PRESELECTION_STANDARD") << tr("PREF_PRESELECTION_DYNAMIC") << tr("PREF_PRESELECTION_DISABLED");
2359   anIndicesList << 0 << 1 << 2;
2360   pref->setItemProperty( "strings", aValuesList,   vtkPreselection );
2361   pref->setItemProperty( "indexes", anIndicesList, vtkPreselection );
2362   // .... -> enable selection
2363   pref->addPreference( tr( "PREF_ENABLE_SELECTION" ), vtkSelectionGroup, LightApp_Preferences::Bool, "VTKViewer", "enable_selection" );
2364   // ... "Selection" group <<end>>
2365
2366   // ... -> empty frame (for layout) <<end>>
2367
2368   // ... space mouse sub-group <<start>>
2369   int vtkSM = pref->addPreference( tr( "PREF_FRAME_SPACEMOUSE" ), vtkGroup, LightApp_Preferences::GroupBox );
2370   //pref->setItemProperty( "columns", 2, vtkSM );
2371   // .... -> decrease speed increment
2372   int spacemousePref1 = pref->addPreference( tr( "PREF_SPACEMOUSE_FUNC_1" ), vtkSM,
2373                                              LightApp_Preferences::Selector, "VTKViewer",
2374                                              "spacemouse_func1_btn" );
2375   // .... -> increase speed increment
2376   int spacemousePref2 = pref->addPreference( tr( "PREF_SPACEMOUSE_FUNC_2" ), vtkSM,
2377                                              LightApp_Preferences::Selector, "VTKViewer",
2378                                              "spacemouse_func2_btn" );
2379   // .... -> dominant / combined switch  
2380   int spacemousePref3 = pref->addPreference( tr( "PREF_SPACEMOUSE_FUNC_3" ), vtkSM,
2381                                              LightApp_Preferences::Selector, "VTKViewer",
2382                                              "spacemouse_func5_btn" ); //
2383   aValuesList.clear();
2384   anIndicesList.clear();
2385   aValuesList << tr( "PREF_SPACEMOUSE_BTN_1" )  << tr( "PREF_SPACEMOUSE_BTN_2" ) << tr( "PREF_SPACEMOUSE_BTN_3" );
2386   aValuesList << tr( "PREF_SPACEMOUSE_BTN_4" )  << tr( "PREF_SPACEMOUSE_BTN_5" ) << tr( "PREF_SPACEMOUSE_BTN_6" );
2387   aValuesList << tr( "PREF_SPACEMOUSE_BTN_7" )  << tr( "PREF_SPACEMOUSE_BTN_8" ) << tr( "PREF_SPACEMOUSE_BTN_*" );
2388   aValuesList << tr( "PREF_SPACEMOUSE_BTN_10" ) << tr( "PREF_SPACEMOUSE_BTN_11" );
2389   anIndicesList << 1 << 2 << 3 << 4 << 5 << 6 << 7 << 8 << 9 << 10 << 11;
2390   pref->setItemProperty( "strings", aValuesList,   spacemousePref1 );
2391   pref->setItemProperty( "indexes", anIndicesList, spacemousePref1 );
2392   pref->setItemProperty( "strings", aValuesList,   spacemousePref2 );
2393   pref->setItemProperty( "indexes", anIndicesList, spacemousePref2 );
2394   pref->setItemProperty( "strings", aValuesList,   spacemousePref3 );
2395   pref->setItemProperty( "indexes", anIndicesList, spacemousePref3 );
2396   // ... space mouse sub-group <<end>>
2397
2398   // ... avi recording sub-group <<start>>
2399   int vtkRec = pref->addPreference( tr( "PREF_FRAME_RECORDING" ), vtkGroup, LightApp_Preferences::GroupBox );
2400   pref->setItemProperty( "columns", 2, vtkRec );
2401   // .... -> recording mode
2402   int modePref = pref->addPreference( tr( "PREF_RECORDING_MODE" ), vtkRec,
2403                                       LightApp_Preferences::Selector, "VTKViewer", "recorder_mode" );
2404   aValuesList.clear();
2405   anIndicesList.clear();
2406   aValuesList   << tr( "PREF_SKIPPED_FRAMES" ) << tr( "PREF_ALL_DISLPAYED_FRAMES" );
2407   anIndicesList << 0                           << 1;
2408   pref->setItemProperty( "strings", aValuesList,   modePref );
2409   pref->setItemProperty( "indexes", anIndicesList, modePref );
2410   // .... -> fps
2411   int fpsPref = pref->addPreference( tr( "PREF_FPS" ), vtkRec,
2412                                      LightApp_Preferences::DblSpin, "VTKViewer", "recorder_fps" );
2413   pref->setItemProperty( "min", 0.1, fpsPref );
2414   pref->setItemProperty( "max", 100, fpsPref );
2415   // .... -> quality
2416   int qualityPref = pref->addPreference( tr( "PREF_QUALITY" ), vtkRec,
2417                                          LightApp_Preferences::IntSpin, "VTKViewer", "recorder_quality" );
2418   pref->setItemProperty( "min", 1, qualityPref );
2419   pref->setItemProperty( "max", 100, qualityPref );
2420   // .... -> progressive mode
2421   pref->addPreference( tr( "PREF_PROGRESSIVE" ), vtkRec,
2422                        LightApp_Preferences::Bool, "VTKViewer", "recorder_progressive" );
2423   // ... avi recording sub-group <<end>>
2424
2425   // ... group names sub-group <<start>>
2426   int vtkGN = pref->addPreference( tr( "PREF_FRAME_GROUP_NAMES" ), vtkGroup,
2427                                    LightApp_Preferences::GroupBox, "VTKViewer", "show_group_names" );
2428   pref->setItemProperty( "columns", 2, vtkGN );
2429   // .... -> text color
2430   pref->addPreference( tr(  "PREF_GROUP_NAMES_TEXT_COLOR" ), vtkGN,
2431                        LightApp_Preferences::Color, "VTKViewer", "group_names_text_color" );
2432   // .... -> transparency
2433   int transPref = pref->addPreference( tr( "PREF_GROUP_NAMES_TRANSPARENCY" ), vtkGN,
2434                                        LightApp_Preferences::DblSpin, "VTKViewer", "group_names_transparency" );
2435   pref->setItemProperty( "min", 0.0, transPref );
2436   pref->setItemProperty( "max", 1.0, transPref );
2437   pref->setItemProperty( "step", 0.1, transPref );
2438   // ... -> group names sub-group <<end>>
2439   // .. "VTK viewer" group <<end>>
2440 #endif
2441
2442   // .. "Plot2d viewer" group <<start>>
2443   int plot2dGroup = pref->addPreference( tr( "PREF_GROUP_PLOT2DVIEWER" ), salomeCat ); //viewTab
2444   //pref->setItemProperty( "columns", 2, plot2dGroup );
2445
2446   // ... -> background
2447   pref->addPreference( tr( "PREF_VIEWER_BACKGROUND_COLOR" ), plot2dGroup,
2448                        LightApp_Preferences::Color, "Plot2d", "Background" );
2449   // ... -> selection color
2450   pref->addPreference( tr( "PREF_VIEWER_SELECTION" ), plot2dGroup,
2451                        LightApp_Preferences::Color, "Plot2d", "SelectionColor" );
2452
2453   // ... "Viewer" group <<start>>
2454   int plot2dViewerGroup = pref->addPreference( tr( "PREF_GROUP_VIEWER" ), plot2dGroup );
2455
2456   // .... -> curve type
2457   int curveType = pref->addPreference( tr( "PREF_CURVE_TYPE" ), plot2dViewerGroup,
2458                                        LightApp_Preferences::Selector, "Plot2d", "CurveType" );
2459   aValuesList.clear();
2460   anIndicesList.clear();
2461   aValuesList   << tr("PREF_POINTS") << tr("PREF_LINES") << tr("PREF_SPLINE");
2462   anIndicesList << 0                 << 1                << 2                ;
2463   pref->setItemProperty( "strings", aValuesList,   curveType );
2464   pref->setItemProperty( "indexes", anIndicesList, curveType );
2465   // .... -> marker size
2466   int markerSize = pref->addPreference( tr( "PREF_MARKER_SIZE" ), plot2dViewerGroup,
2467                                         LightApp_Preferences::IntSpin, "Plot2d", "MarkerSize" );
2468   pref->setItemProperty( "min", 0, markerSize );
2469   pref->setItemProperty( "max", 100, markerSize );
2470   // .... -> horizontal scaling mode
2471   int horScale = pref->addPreference( tr( "PREF_HOR_AXIS_SCALE" ), plot2dViewerGroup,
2472                                       LightApp_Preferences::Selector, "Plot2d", "HorScaleMode" );
2473   aValuesList.clear();
2474   anIndicesList.clear();
2475   aValuesList   << tr("PREF_LINEAR") << tr("PREF_LOGARITHMIC");
2476   anIndicesList << 0                 << 1                     ;
2477   pref->setItemProperty( "strings", aValuesList,   horScale );
2478   pref->setItemProperty( "indexes", anIndicesList, horScale );
2479   // .... -> vertical scaling mode
2480   int verScale = pref->addPreference( tr( "PREF_VERT_AXIS_SCALE" ), plot2dViewerGroup,
2481                                       LightApp_Preferences::Selector, "Plot2d", "VerScaleMode" );
2482   pref->setItemProperty( "strings", aValuesList,   verScale );
2483   pref->setItemProperty( "indexes", anIndicesList, verScale );
2484
2485   // .... -> errors/deviation colot
2486   pref->addPreference( tr( "PREF_DEVIATION_COLOR" ), plot2dViewerGroup,
2487                        LightApp_Preferences::Color, "Plot2d", "DeviationMarkerColor" );
2488   // .... -> deviation markers line size
2489   int deviationMarkerLw = pref->addPreference( tr( "PREF_DEVIATION_MARKER_LW" ), plot2dViewerGroup,
2490                                         LightApp_Preferences::IntSpin, "Plot2d", "DeviationMarkerLineWidth" );
2491   pref->setItemProperty( "min", 1, deviationMarkerLw );
2492   pref->setItemProperty( "max", 5, deviationMarkerLw );
2493   // .... -> deviation markers tick mark size
2494   int deviationMarkerTs = pref->addPreference( tr( "PREF_DEVIATION_MARKER_TS" ), plot2dViewerGroup,
2495                                         LightApp_Preferences::IntSpin, "Plot2d", "DeviationMarkerTickSize" );
2496   pref->setItemProperty( "min", 1, deviationMarkerTs );
2497   pref->setItemProperty( "max", 5, deviationMarkerTs );
2498   // .... "Viewer" group <<end>>
2499
2500   // ... "Legend" group <<start>>
2501   int plot2dLegendGroup = pref->addPreference( tr( "PREF_GROUP_LEGEND" ), plot2dGroup );
2502
2503   // .... -> show legend
2504   pref->addPreference( tr( "PREF_SHOW_LEGEND" ), plot2dLegendGroup,
2505                        LightApp_Preferences::Bool, "Plot2d", "ShowLegend" );
2506   // .... -> legend position
2507   int legendPosition = pref->addPreference( tr( "PREF_LEGEND_POSITION" ), plot2dLegendGroup,
2508                                             LightApp_Preferences::Selector, "Plot2d", "LegendPos" );
2509   aValuesList.clear();
2510   anIndicesList.clear();
2511   aValuesList   << tr("PREF_LEFT") << tr("PREF_RIGHT") << tr("PREF_TOP") << tr("PREF_BOTTOM");
2512   anIndicesList << 0               << 1                << 2              << 3                ;
2513   pref->setItemProperty( "strings", aValuesList,   legendPosition );
2514   pref->setItemProperty( "indexes", anIndicesList, legendPosition );
2515   // .... -> Symbol type
2516   int legendSymbolType = pref->addPreference( tr( "PREF_LEGEND_SYMBOL_TYPE" ), plot2dLegendGroup,
2517                                             LightApp_Preferences::Selector, "Plot2d", "LegendSymbolType" );
2518   aValuesList.clear();
2519   anIndicesList.clear();
2520   aValuesList   << tr("PREF_MARKER_ON_LINE") << tr("PREF_MARKER_ABOVE_LINE");
2521   anIndicesList << 0                            << 1                        ;
2522   pref->setItemProperty( "strings", aValuesList,   legendSymbolType );
2523   pref->setItemProperty( "indexes", anIndicesList, legendSymbolType );
2524   // .... -> legend font
2525   pref->addPreference( tr( "PREF_LEGEND_FONT" ), plot2dLegendGroup, LightApp_Preferences::Font, "Plot2d", "LegendFont" );
2526   // ... -> font color
2527   pref->addPreference( tr( "PREF_FONT_COLOR" ), plot2dLegendGroup, LightApp_Preferences::Color, "Plot2d", "LegendFontColor" );
2528   // ... -> selection font color
2529   pref->addPreference( tr( "PREF_SELECTED_FONT_COLOR" ), plot2dLegendGroup, LightApp_Preferences::Color, "Plot2d", "SelectedLegendFontColor" );
2530   // ... "Legend" group <<end>>
2531
2532   // .. "Plot2d viewer" group <<end>>
2533
2534   // .. "Directories" preferences tab <<start>>
2535   int dirTab = pref->addPreference( tr( "PREF_TAB_DIRECTORIES" ), salomeCat );
2536   // ... --> quick directories list
2537   int dirGroup = pref->addPreference( tr( "PREF_GROUP_DIRECTORIES" ), dirTab );
2538   pref->addPreference( tr( "" ), dirGroup,
2539                        LightApp_Preferences::DirList, "FileDlg", "QuickDirList" );
2540   // .. "Directories" preferences tab <<end>>
2541
2542   // .. "Object browser" preferences tab <<start>>
2543   int obTab = pref->addPreference( tr( "PREF_TAB_OBJBROWSER" ), salomeCat );
2544
2545   // ... "Search tool" group <<start>>
2546   int stGroup = pref->addPreference( tr( "PREF_OBJ_BROWSER_SEARCH_TOOL" ), obTab );
2547   // .... --> auto-hide
2548   pref->addPreference( tr( "PREF_AUTO_HIDE_SEARCH_TOOL" ), stGroup, LightApp_Preferences::Bool,
2549                        "ObjectBrowser", "auto_hide_search_tool" );
2550   // ... "Search tool" group <<end>>
2551
2552   // ... "Object browser settings" group <<start>>
2553   int objSetGroup = pref->addPreference( tr( "PREF_GROUP_LOOK_AND_FEEL" ), obTab );
2554   pref->setItemProperty( "columns", 2, objSetGroup );
2555   // .... -> auto size first column
2556   pref->addPreference( tr( "PREF_AUTO_SIZE_FIRST" ), objSetGroup, LightApp_Preferences::Bool,
2557                        "ObjectBrowser", "auto_size_first" );
2558   // .... -> auto size other columns
2559   pref->addPreference( tr( "PREF_AUTO_SIZE" ), objSetGroup, LightApp_Preferences::Bool,
2560                        "ObjectBrowser", "auto_size" );
2561   // .... -> resize columns on expand item
2562   pref->addPreference( tr( "PREF_RESIZE_ON_EXPAND_ITEM" ), objSetGroup, LightApp_Preferences::Bool,
2563                        "ObjectBrowser", "resize_on_expand_item" );
2564   // .... -> browse to published object
2565   int browsePublished = pref->addPreference( tr( "PREF_BROWSE_TO_THE_PUBLISHED_OBJECT" ), objSetGroup, LightApp_Preferences::Selector,
2566                                              "ObjectBrowser", "browse_published_object" );
2567   aValuesList.clear();
2568   anIndicesList.clear();
2569   aValuesList << tr( "PREF_BROWSE_NEVER" ) << tr( "PREF_BROWSE_AFTER_APPLY_AND_CLOSE_ONLY" ) << tr( "PREF_BROWSE_ALWAYS" );
2570   anIndicesList << BP_Never << BP_ApplyAndClose << BP_Always;
2571   pref->setItemProperty( "strings", aValuesList,   browsePublished );
2572   pref->setItemProperty( "indexes", anIndicesList, browsePublished );
2573   // ... "Object browser settings" group <<end>>
2574   // .. "Object browser" preferences tab <<end>>
2575
2576   // .. "Shortcuts" preferences tab <<start>>
2577   int shortcutTab = pref->addPreference( tr( "PREF_TAB_SHORTCUTS" ), salomeCat );
2578   // ... "Shortcuts settings" group <<start>>
2579   int shortcutGroup = pref->addPreference( tr( "PREF_GROUP_SHORTCUTS" ), shortcutTab );
2580   pref->addPreference( tr( "" ), shortcutGroup,
2581                        LightApp_Preferences::ShortcutTree, "shortcuts" );
2582   // ... "Shortcuts settings" group <<end>>
2583   // .. "Shortcuts" preferences tab <<end>>
2584   // . Top-level "SALOME" preferences group <<end>>
2585
2586   pref->retrieve();
2587 }
2588
2589 /*!
2590   Changes appearance of application according to changed preferences
2591   \param sec - section
2592   \param param - name of changed parameter
2593 */
2594 void LightApp_Application::preferencesChanged( const QString& sec, const QString& param )
2595 {
2596   SUIT_ResourceMgr* resMgr = resourceMgr();
2597   if ( !resMgr )
2598     return;
2599
2600   if ( sec == "viewers" && param == "drop_down_buttons" )
2601   {
2602     ViewManagerList vmlist = viewManagers();
2603     foreach( SUIT_ViewManager* vm, vmlist )
2604     {
2605       QVector<SUIT_ViewWindow*> vwlist = vm->getViews();
2606       foreach( SUIT_ViewWindow* vw, vwlist )
2607         if ( vw ) vw->setDropDownButtons( resMgr->booleanValue( "viewers", "drop_down_buttons", true ) );
2608     }
2609   }
2610
2611   if ( sec == QString( "3DViewer" ) && (param == QString( "trihedron_size" ) || param == QString( "relative_size" )))
2612   {
2613     double sz = resMgr->doubleValue( sec, "trihedron_size", -1 );
2614     bool relative = resMgr->booleanValue( sec, "relative_size", true );
2615     QList<SUIT_ViewManager*> lst;
2616 #ifndef DISABLE_OCCVIEWER
2617     viewManagers( OCCViewer_Viewer::Type(), lst );
2618     QListIterator<SUIT_ViewManager*> itOCC( lst );
2619     while ( itOCC.hasNext() && sz >= 0 )
2620     {
2621       SUIT_ViewModel* vm = itOCC.next()->getViewModel();
2622       if ( !vm || !vm->inherits( "OCCViewer_Viewer" ) )
2623         continue;
2624
2625       OCCViewer_Viewer* occVM = (OCCViewer_Viewer*)vm;
2626       occVM->setTrihedronSize( sz, relative );
2627       occVM->getAISContext()->UpdateCurrentViewer();
2628     }
2629 #endif
2630 #ifndef DISABLE_VTKVIEWER
2631 #ifndef DISABLE_SALOMEOBJECT
2632     viewManagers( SVTK_Viewer::Type(), lst );
2633     QListIterator<SUIT_ViewManager*> itVTK( lst );
2634     while ( itVTK.hasNext() && sz >= 0 )
2635     {
2636       SUIT_ViewModel* vm = itVTK.next()->getViewModel();
2637       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2638         continue;
2639
2640       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2641       if( vtkVM )
2642       {
2643         vtkVM->setTrihedronSize( sz, relative );
2644         vtkVM->Repaint();
2645       }
2646     }
2647 #endif
2648 #endif
2649   }
2650
2651   if ( sec == QString( "3DViewer" ) && param == QString( "show_static_trihedron" ) )
2652   {
2653     bool isVisible = resMgr->booleanValue( "3DViewer", "show_static_trihedron", true );
2654     QList<SUIT_ViewManager*> lst;
2655 #ifndef DISABLE_OCCVIEWER
2656     viewManagers( OCCViewer_Viewer::Type(), lst );
2657     QListIterator<SUIT_ViewManager*> itOCC( lst );
2658     while ( itOCC.hasNext() )
2659     {
2660       SUIT_ViewModel* vm = itOCC.next()->getViewModel();
2661       if ( !vm || !vm->inherits( "OCCViewer_Viewer" ) )
2662         continue;
2663
2664       OCCViewer_Viewer* occVM = dynamic_cast<OCCViewer_Viewer*>( vm );
2665       if( occVM )
2666       {
2667         occVM->setStaticTrihedronDisplayed( isVisible );
2668       }
2669     }
2670 #endif
2671 #ifndef DISABLE_VTKVIEWER
2672 #ifndef DISABLE_SALOMEOBJECT
2673     viewManagers( SVTK_Viewer::Type(), lst );
2674     QListIterator<SUIT_ViewManager*> itVTK( lst );
2675     while ( itVTK.hasNext() )
2676     {
2677       SUIT_ViewModel* vm = itVTK.next()->getViewModel();
2678       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2679         continue;
2680
2681       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2682       if( vtkVM )
2683       {
2684         vtkVM->setStaticTrihedronVisible( isVisible );
2685         vtkVM->Repaint();
2686       }
2687     }
2688 #endif
2689 #endif
2690   }
2691
2692   if ( sec == QString( "3DViewer" ) && param == QString( "navigation_mode" ) )
2693   {
2694     int mode = resMgr->integerValue( "3DViewer", "navigation_mode", 0 );
2695     QList<SUIT_ViewManager*> lst;
2696 #ifndef DISABLE_OCCVIEWER
2697     viewManagers( OCCViewer_Viewer::Type(), lst );
2698     QListIterator<SUIT_ViewManager*> itOCC( lst );
2699     while ( itOCC.hasNext() )
2700     {
2701       SUIT_ViewModel* vm = itOCC.next()->getViewModel();
2702       if ( !vm || !vm->inherits( "OCCViewer_Viewer" ) )
2703         continue;
2704
2705       OCCViewer_Viewer* occVM = (OCCViewer_Viewer*)vm;
2706       occVM->setInteractionStyle( mode );
2707     }
2708 #endif
2709 #ifndef DISABLE_VTKVIEWER
2710 #ifndef DISABLE_SALOMEOBJECT
2711     viewManagers( SVTK_Viewer::Type(), lst );
2712     QListIterator<SUIT_ViewManager*> itVTK( lst );
2713     while ( itVTK.hasNext() )
2714     {
2715       SUIT_ViewModel* vm = itVTK.next()->getViewModel();
2716       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2717         continue;
2718
2719       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2720       if( vtkVM ) vtkVM->setInteractionStyle( mode );
2721     }
2722 #endif
2723 #endif
2724   }
2725
2726 #ifndef DISABLE_OCCVIEWER
2727   if ( sec == QString( "OCCViewer" ) && param == QString( "enable_preselection" ) )
2728   {
2729     bool isToEnablePreselection = resMgr->booleanValue( "OCCViewer", "enable_preselection", true );
2730     QList<SUIT_ViewManager*> lst;
2731     viewManagers( OCCViewer_Viewer::Type(), lst );
2732     QListIterator<SUIT_ViewManager*> it( lst );
2733     while ( it.hasNext() )
2734     {
2735       SUIT_ViewModel* vm = it.next()->getViewModel();
2736       if ( !vm || !vm->inherits( "OCCViewer_Viewer" ) )
2737         continue;
2738
2739       OCCViewer_Viewer* occVM = (OCCViewer_Viewer*)vm;
2740       occVM->enablePreselection( isToEnablePreselection );
2741     }
2742   }
2743 #endif
2744
2745 #ifndef DISABLE_OCCVIEWER
2746   if ( sec == QString( "OCCViewer" ) && param == QString( "enable_selection" ) )
2747   {
2748     bool isToEnableSelection = resMgr->booleanValue( "OCCViewer", "enable_selection", true );
2749     QList<SUIT_ViewManager*> lst;
2750     viewManagers( OCCViewer_Viewer::Type(), lst );
2751     QListIterator<SUIT_ViewManager*> it( lst );
2752     while ( it.hasNext() )
2753     {
2754       SUIT_ViewModel* vm = it.next()->getViewModel();
2755       if ( !vm || !vm->inherits( "OCCViewer_Viewer" ) )
2756         continue;
2757
2758       OCCViewer_Viewer* occVM = (OCCViewer_Viewer*)vm;
2759       occVM->enableSelection( isToEnableSelection );
2760     }
2761   }
2762 #endif
2763
2764   if ( sec == QString( "3DViewer" ) && param == QString( "zooming_mode" ) )
2765   {
2766     int mode = resMgr->integerValue( "3DViewer", "zooming_mode", 0 );
2767     QList<SUIT_ViewManager*> lst;
2768 #ifndef DISABLE_OCCVIEWER
2769     viewManagers( OCCViewer_Viewer::Type(), lst );
2770     QListIterator<SUIT_ViewManager*> itOCC( lst );
2771     while ( itOCC.hasNext() )
2772     {
2773       SUIT_ViewModel* vm = itOCC.next()->getViewModel();
2774       if ( !vm || !vm->inherits( "OCCViewer_Viewer" ) )
2775         continue;
2776
2777       OCCViewer_Viewer* occVM = (OCCViewer_Viewer*)vm;
2778       occVM->setZoomingStyle( mode );
2779     }
2780 #endif
2781 #ifndef DISABLE_VTKVIEWER
2782 #ifndef DISABLE_SALOMEOBJECT
2783     viewManagers( SVTK_Viewer::Type(), lst );
2784     QListIterator<SUIT_ViewManager*> itVTK( lst );
2785     while ( itVTK.hasNext() )
2786     {
2787       SUIT_ViewModel* vm = itVTK.next()->getViewModel();
2788       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2789         continue;
2790
2791       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2792       if( vtkVM ) vtkVM->setZoomingStyle( mode );
2793     }
2794 #endif
2795 #endif
2796   }
2797
2798 #ifndef DISABLE_VTKVIEWER
2799   if ( sec == QString( "VTKViewer" ) && (param == QString( "speed_value" ) || param == QString( "speed_mode" )) )
2800   {
2801     int speed = resMgr->integerValue( "VTKViewer", "speed_value", 10 );
2802     int mode = resMgr->integerValue( "VTKViewer", "speed_mode", 0 );
2803     QList<SUIT_ViewManager*> lst;
2804 #ifndef DISABLE_SALOMEOBJECT
2805     viewManagers( SVTK_Viewer::Type(), lst );
2806     QListIterator<SUIT_ViewManager*> it( lst );
2807     while ( it.hasNext() )
2808     {
2809       SUIT_ViewModel* vm = it.next()->getViewModel();
2810       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2811         continue;
2812
2813       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2814       if( vtkVM ) vtkVM->setIncrementalSpeed( speed, mode );
2815     }
2816 #endif
2817   }
2818 #endif
2819
2820 #ifndef DISABLE_VTKVIEWER
2821   if ( sec == QString( "VTKViewer" ) && param == QString( "projection_mode" ) )
2822   {
2823     int mode = resMgr->integerValue( "VTKViewer", "projection_mode", 0 );
2824     QList<SUIT_ViewManager*> lst;
2825 #ifndef DISABLE_SALOMEOBJECT
2826     viewManagers( SVTK_Viewer::Type(), lst );
2827     QListIterator<SUIT_ViewManager*> it( lst );
2828     while ( it.hasNext() )
2829     {
2830       SUIT_ViewModel* vm = it.next()->getViewModel();
2831       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2832         continue;
2833
2834       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2835       if( vtkVM ) vtkVM->setProjectionMode( mode );
2836     }
2837 #endif
2838   }
2839 #endif
2840
2841 #ifndef DISABLE_VTKVIEWER
2842   if ( sec == QString( "VTKViewer" ) && param == QString( "preselection" ) )
2843   {
2844     int mode = resMgr->integerValue( "VTKViewer", "preselection", 0 );
2845     QList<SUIT_ViewManager*> lst;
2846 #ifndef DISABLE_SALOMEOBJECT
2847     viewManagers( SVTK_Viewer::Type(), lst );
2848     QListIterator<SUIT_ViewManager*> it( lst );
2849     while ( it.hasNext() )
2850     {
2851       SUIT_ViewModel* vm = it.next()->getViewModel();
2852       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2853         continue;
2854
2855       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2856       if( vtkVM ) vtkVM->setPreSelectionMode( mode );
2857     }
2858 #endif
2859   }
2860 #endif
2861
2862 #ifndef DISABLE_VTKVIEWER
2863   if ( sec == QString( "VTKViewer" ) && param == QString( "enable_selection" ) )
2864   {
2865     bool isToEnableSelection = resMgr->booleanValue( "VTKViewer", "enable_selection", true );
2866     QList<SUIT_ViewManager*> lst;
2867 #ifndef DISABLE_SALOMEOBJECT
2868     viewManagers( SVTK_Viewer::Type(), lst );
2869     QListIterator<SUIT_ViewManager*> it( lst );
2870     while ( it.hasNext() )
2871     {
2872       SUIT_ViewModel* vm = it.next()->getViewModel();
2873       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2874         continue;
2875
2876       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2877       if( vtkVM ) vtkVM->enableSelection( isToEnableSelection );
2878     }
2879 #endif
2880   }
2881 #endif
2882
2883 #ifndef DISABLE_VTKVIEWER
2884   if ( sec == QString( "VTKViewer" ) && (param == QString( "spacemouse_func1_btn" ) ||
2885                                          param == QString( "spacemouse_func2_btn" ) ||
2886                                          param == QString( "spacemouse_func5_btn" ) ) )
2887   {
2888     int btn1 = resMgr->integerValue( "VTKViewer", "spacemouse_func1_btn", 1 );
2889     int btn2 = resMgr->integerValue( "VTKViewer", "spacemouse_func2_btn", 2 );
2890     int btn3 = resMgr->integerValue( "VTKViewer", "spacemouse_func5_btn", 9 );
2891     QList<SUIT_ViewManager*> lst;
2892 #ifndef DISABLE_SALOMEOBJECT
2893     viewManagers( SVTK_Viewer::Type(), lst );
2894     QListIterator<SUIT_ViewManager*> it( lst );
2895     while ( it.hasNext() )
2896     {
2897       SUIT_ViewModel* vm = it.next()->getViewModel();
2898       if ( !vm || !vm->inherits( "SVTK_Viewer" ) )
2899         continue;
2900
2901       SVTK_Viewer* vtkVM = dynamic_cast<SVTK_Viewer*>( vm );
2902       if( vtkVM ) vtkVM->setSpacemouseButtons( btn1, btn2, btn3 );
2903     }
2904 #endif
2905   }
2906 #endif
2907   if( sec=="ObjectBrowser" )
2908   {
2909     SUIT_DataBrowser* ob = objectBrowser();
2910     if ( !ob )
2911       return;
2912
2913     if ( param=="auto_size_first" )
2914     {
2915       bool autoSizeFirst = resMgr->booleanValue( "ObjectBrowser", "auto_size_first", true );
2916       ob->setAutoSizeFirstColumn( autoSizeFirst );
2917       if ( autoSizeFirst )
2918         ob->adjustFirstColumnWidth();
2919     }
2920     else if ( param=="auto_size" ) {
2921       bool autoSize = resMgr->booleanValue( "ObjectBrowser", "auto_size", false );
2922       ob->setAutoSizeColumns(autoSize);
2923       if ( autoSize )
2924         ob->adjustColumnsWidth();
2925     }
2926     else if ( param=="resize_on_expand_item" ) {
2927       bool resizeOnExpandItem = resMgr->booleanValue( "ObjectBrowser", "resize_on_expand_item", false );
2928       ob->setResizeOnExpandItem(resizeOnExpandItem);
2929     }
2930     else if ( param == "auto_hide_search_tool" ) {
2931       ob->searchTool()->enableAutoHide( resMgr->booleanValue( "ObjectBrowser", "auto_hide_search_tool" ) );
2932     }
2933   }
2934
2935   if( sec=="Study" )
2936   {
2937     if( param=="auto_save_interval" ) {
2938       myAutoSaveTimer->stop();
2939       int autoSaveInterval = resMgr->integerValue( "Study", "auto_save_interval", 0 );
2940       if ( activeStudy() && autoSaveInterval > 0 ) myAutoSaveTimer->start( autoSaveInterval*60000 );
2941     }
2942   }
2943
2944 #ifndef DISABLE_PYCONSOLE
2945   if( sec=="PyConsole" && pythonConsole() )
2946   {
2947     if ( param=="font" ) {
2948       pythonConsole()->setFont( resMgr->fontValue( "PyConsole", "font" ) );
2949     }
2950     else if ( param=="show_banner" ) {
2951       pythonConsole()->setIsShowBanner( resMgr->booleanValue( "PyConsole", "show_banner", true ) );
2952     }
2953   }
2954 #endif
2955
2956   if( sec=="MRU" )
2957   {
2958     QtxMRUAction* mru = ::qobject_cast<QtxMRUAction*>( action( MRUId ) );
2959     if ( mru ) {
2960       if ( param == "visible_count" )
2961         mru->setVisibleCount( resMgr->integerValue( "MRU", "visible_count", 5 ) );    // 5 MRU items by default
2962       else if ( param == "max_count" )
2963         mru->setHistoryCount( resMgr->integerValue( "MRU", "max_count", -1 ) );       // unlimited history by default
2964       else if ( param == "insert_mode" )
2965         mru->setInsertMode( resMgr->integerValue( "MRU", "insert_mode", 0 ) );        // QtxMRUAction::MoveFirst by default
2966       else if ( param == "link_type" )
2967         mru->setLinkType( resMgr->integerValue( "MRU", "link_type", 0 ) );            // QtxMRUAction::LinkAuto by default
2968       else if ( param == "show_clear" )
2969         mru->setClearPossible( resMgr->booleanValue( "MRU", "show_clear", false ) );  // do not show "Clear" item by default
2970       else if ( param == "show_mru" )
2971         mru->setVisible( resMgr->booleanValue( "MRU", "show_mru", false ) );          // do not show MRU menu item by default
2972     }
2973   }
2974   if ( sec == "language" && param == "language" )
2975   {
2976     SUIT_MessageBox::information( desktop(), tr( "WRN_WARNING" ), tr( "LANG_CHANGED" ) );
2977   }
2978   if ( sec == "language" && param == "locale")
2979   {
2980     SUIT_MessageBox::information( desktop(), tr( "WRN_WARNING" ), tr( "LOCALE_CHANGED" ) );
2981   }
2982   if ( sec == "desktop" && param == "opaque_resize" ) {
2983     bool opaqueResize = resMgr->booleanValue( "desktop", "opaque_resize", false );
2984     QMainWindow::DockOptions dopts = desktop()->dockOptions();
2985     if ( opaqueResize ) dopts |= QMainWindow::AnimatedDocks;
2986     else                dopts &= ~QMainWindow::AnimatedDocks;
2987     desktop()->setDockOptions( dopts );
2988     desktop()->setOpaqueResize( opaqueResize );
2989     if ( dynamic_cast<STD_TabDesktop*>( desktop() ) )
2990       dynamic_cast<STD_TabDesktop*>( desktop() )->workstack()->setOpaqueResize( opaqueResize );
2991   }
2992
2993 #ifndef DISABLE_PLOT2DVIEWER
2994   QList<SUIT_ViewManager*> lst;
2995   viewManagers( Plot2d_Viewer::Type(), lst );
2996   QListIterator<SUIT_ViewManager*> itPlot2d( lst );
2997   while ( itPlot2d.hasNext() ) {
2998     SUIT_ViewManager* viewMgr = itPlot2d.next();
2999     SUIT_ViewModel* vm = viewMgr->getViewModel();
3000     if ( !vm || !vm->inherits( "Plot2d_Viewer" ) )
3001       continue;
3002
3003     Plot2d_Viewer* Plot2dVM = dynamic_cast<Plot2d_Viewer*>( vm );
3004
3005     viewMgr->setViewModel( vm  );
3006     Plot2d_ViewWindow* wnd = dynamic_cast<Plot2d_ViewWindow*>( viewMgr->getActiveView() );
3007     if( wnd ) {
3008       Plot2d_ViewFrame* frame = wnd->getViewFrame();
3009       frame->SetPreference();
3010     }
3011   }
3012 #endif
3013 }
3014
3015 /*!
3016   Loads preferences
3017 */
3018 void LightApp_Application::loadPreferences()
3019 {
3020   CAM_Application::loadPreferences();
3021
3022   SUIT_ResourceMgr* aResMgr = resourceMgr();
3023
3024   if ( !aResMgr )
3025     return;
3026
3027   static bool mru_load = true;
3028   if ( mru_load )
3029   {
3030     QtxMRUAction* mru = ::qobject_cast<QtxMRUAction*>( action( MRUId ) );
3031     if ( mru ) {
3032       mru->setVisible( aResMgr->booleanValue( "MRU", "show_mru", false ) );         // do not show MRU menu item by default
3033       mru->setVisibleCount( aResMgr->integerValue( "MRU", "visible_count", 5 ) );   // 5 MRU items by default
3034       mru->setHistoryCount( aResMgr->integerValue( "MRU", "max_count", -1 ) );      // unlimited history by default
3035       mru->setInsertMode( aResMgr->integerValue( "MRU", "insert_mode", 0 ) );       // QtxMRUAction::MoveFirst by default
3036       mru->setLinkType( aResMgr->integerValue( "MRU", "link_type", 0 ) );           // QtxMRUAction::LinkAuto by default
3037       mru->setClearPossible( aResMgr->booleanValue( "MRU", "show_clear", false ) ); // do not show "Clear" item by default
3038       mru->loadLinks( aResMgr, "MRU" );
3039     }
3040     mru_load = false;
3041   }
3042
3043   myWinVis.clear();
3044   QStringList mods = aResMgr->parameters( "windows_visibility" );
3045   for ( QStringList::const_iterator itr = mods.begin(); itr != mods.end(); ++itr )
3046   {
3047     QByteArray arr;
3048     if ( aResMgr->value( "windows_visibility", *itr, arr ) )
3049       myWinVis.insert( *itr, arr );
3050   }
3051
3052   if ( desktop() ) {
3053     desktop()->retrieveGeometry( aResMgr->stringValue( "desktop", "geometry" ) );
3054     bool opaqueResize = aResMgr->booleanValue( "desktop", "opaque_resize", false );
3055     QMainWindow::DockOptions dopts = desktop()->dockOptions();
3056     if ( opaqueResize ) dopts |= QMainWindow::AnimatedDocks;
3057     else                dopts &= ~QMainWindow::AnimatedDocks;
3058     desktop()->setDockOptions( dopts );
3059     desktop()->setOpaqueResize( opaqueResize );
3060     if ( dynamic_cast<STD_TabDesktop*>( desktop() ) )
3061       dynamic_cast<STD_TabDesktop*>( desktop() )->workstack()->setOpaqueResize( opaqueResize );
3062   }
3063 }
3064
3065 /*!
3066   Saves preferences
3067 */
3068 void LightApp_Application::savePreferences()
3069 {
3070   CAM_Application::savePreferences();
3071
3072   saveDockWindowsState();
3073
3074   SUIT_ResourceMgr* aResMgr = resourceMgr();
3075
3076   if ( !aResMgr )
3077     return;
3078
3079   QtxMRUAction* mru = ::qobject_cast<QtxMRUAction*>( action( MRUId ) );
3080   if ( mru )
3081     mru->saveLinks( aResMgr, "MRU" );
3082
3083   for ( WinVis::const_iterator itr = myWinVis.begin(); itr != myWinVis.end(); ++itr )
3084     aResMgr->setValue( "windows_visibility", itr.key(), itr.value() );
3085
3086   if ( desktop() )
3087     aResMgr->setValue( "desktop", "geometry", desktop()->storeGeometry() );
3088
3089 #if GUI_DEVELOPMENT > 0
3090   aResMgr->setValue( "salome", "version", QString(GUI_VERSION_STR)+"dev" );
3091 #else
3092   aResMgr->setValue( "salome", "version", QString(GUI_VERSION_STR) );
3093 #endif
3094
3095   aResMgr->save();
3096 }
3097
3098 /*!
3099   Updates desktop title
3100 */
3101 void LightApp_Application::updateDesktopTitle()
3102 {
3103   QString aTitle = applicationName();
3104   QString aVer = applicationVersion();
3105   if ( !aVer.isEmpty() )
3106     aTitle += QString( " " ) + aVer;
3107
3108   if ( activeStudy() ) {
3109     QString sName = SUIT_Tools::file( activeStudy()->studyName().trimmed(), false );
3110     aTitle += QString( " - [%1]" ).arg( sName );
3111   }
3112
3113   desktop()->setWindowTitle( aTitle );
3114 }
3115
3116 /*!
3117   \brief Get map of the operations which can be performed
3118   on the module activation.
3119
3120   The method should return the map of the kind \c {<id>:<name>}
3121   where \c <id> is an integer identifier of the operation and
3122   \c <name> is a title for the button to be added to the
3123   dialog box. After user selects the required operation by the
3124   clicking the corresponding button in the dialog box, its identifier
3125   is passed to the moduleActionSelected() method to process
3126   the made choice.
3127
3128   \return map of the operations
3129   \sa moduleActionSelected()
3130 */
3131 QMap<int, QString> LightApp_Application::activateModuleActions() const
3132 {
3133   QMap<int, QString> opmap;
3134   opmap.insert( NewStudyId,  tr( "ACTIVATE_MODULE_OP_NEW" ) );
3135   opmap.insert( OpenStudyId, tr( "ACTIVATE_MODULE_OP_OPEN" ) );
3136   return opmap;
3137 }
3138
3139 /*!
3140   \brief Called when the used selectes required operation chosen
3141   from "Activate module" dialog box.
3142
3143   Performs the required operation according to the user choice.
3144
3145   \param id operation identifier
3146   \sa activateModuleActions()
3147 */
3148 void LightApp_Application::moduleActionSelected( const int id )
3149 {
3150   switch ( id ) {
3151   case NewStudyId:
3152     onNewDoc();
3153     break;
3154   case OpenStudyId:
3155     onOpenDoc();
3156     break;
3157   default:
3158     break;
3159   }
3160 }
3161
3162 /*!
3163   Updates windows after close document
3164 */
3165 void LightApp_Application::afterCloseDoc()
3166 {
3167   updateWindows();
3168
3169   CAM_Application::afterCloseDoc();
3170 }
3171
3172 /*!
3173   Updates actions of active module
3174 */
3175 void LightApp_Application::updateModuleActions()
3176 {
3177   QString modName;
3178   if ( activeModule() ) {
3179     modName = activeModule()->moduleName();
3180     if ( !isModuleAccessible( modName ) ) {
3181       QList<SUIT_Application*> apps = SUIT_Session::session()->applications();
3182       foreach( SUIT_Application* app, apps ) {
3183         LightApp_Application* lapp = dynamic_cast<LightApp_Application*>( app );
3184         if ( lapp && lapp != this )
3185           lapp->removeModuleAction( modName );
3186       }
3187     }
3188   }
3189
3190   LightApp_ModuleAction* moduleAction =
3191     qobject_cast<LightApp_ModuleAction*>( action( ModulesListId ) );
3192   if ( moduleAction )
3193     moduleAction->setActiveModule( modName );
3194 }
3195
3196 void LightApp_Application::removeModuleAction( const QString& modName )
3197 {
3198   LightApp_ModuleAction* moduleAction =
3199     qobject_cast<LightApp_ModuleAction*>( action( ModulesListId ) );
3200   if ( moduleAction )
3201     moduleAction->removeModule( modName );
3202 }
3203
3204 /*!
3205   Gets current windows.
3206   \param winMap - output current windows map.
3207 */
3208 void LightApp_Application::currentWindows( QMap<int, int>& winMap ) const
3209 {
3210   winMap.clear();
3211   if ( activeModule() && activeModule()->inherits( "LightApp_Module" ) )
3212     ((LightApp_Module*)activeModule())->windows( winMap );
3213   else
3214     defaultWindows( winMap );
3215 }
3216
3217 /*!
3218   Gets current view managers.
3219   \param lst - output current view managers list.
3220 */
3221 void LightApp_Application::currentViewManagers( QStringList& lst ) const
3222 {
3223   lst.clear();
3224   if ( !activeStudy() )
3225     return;
3226
3227   if ( activeModule() && activeModule()->inherits( "LightApp_Module" ) )
3228     ((LightApp_Module*)activeModule())->viewManagers( lst );
3229   else
3230     defaultViewManagers( lst );
3231 }
3232
3233 /*!
3234   Updates windows
3235 */
3236 void LightApp_Application::updateWindows()
3237 {
3238   QMap<int, int> winMap;
3239   currentWindows( winMap );
3240
3241   for ( QMap<int, int>::ConstIterator it = winMap.begin(); it != winMap.end(); ++it )
3242   {
3243     if ( !dockWindow( it.key() ) )
3244       getWindow( it.key() );
3245   }
3246
3247   for ( WinMap::ConstIterator it = myWin.begin(); it != myWin.end(); ++it )
3248   {
3249     QWidget* wid = it.value();
3250     if ( winMap.contains( it.key() ) )
3251       wid->setVisible( true );
3252     else
3253       delete wid;
3254   }
3255
3256   loadDockWindowsState();
3257 }
3258
3259 /*!
3260   Updates view managers
3261 */
3262 void LightApp_Application::updateViewManagers()
3263 {
3264   QStringList lst;
3265   currentViewManagers( lst );
3266
3267   for ( QStringList::const_iterator it = lst.begin(); it != lst.end(); ++it )
3268     getViewManager( *it, true );
3269 }
3270
3271 /*!
3272   Loads windows geometry
3273 */
3274 void LightApp_Application::loadDockWindowsState()
3275 {
3276   if ( !desktop() )
3277     return;
3278   SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
3279   bool storeWin = aResMgr->booleanValue( "Study", "store_positions", true );
3280   bool storeTb = aResMgr->booleanValue( "Study", "store_tool_positions", true );
3281
3282   QString modName;
3283   if ( activeModule() )
3284     modName = activeModule()->name();
3285   else if ( activeStudy() )
3286     modName = "nomodule";
3287
3288   QtxResourceMgr::WorkingMode prevMode = aResMgr->setWorkingMode( QtxResourceMgr::IgnoreUserValues );
3289   QByteArray aDefaultState;
3290   aResMgr->value( "windows_geometry", modName, aDefaultState );
3291   QByteArray aDefaultVisibility;
3292   aResMgr->value( "windows_visibility", modName, aDefaultVisibility );
3293   bool hasDefaultVisibility = !aDefaultVisibility.isEmpty();
3294   aResMgr->setWorkingMode( prevMode );
3295   
3296   if( !storeWin && !storeTb && aDefaultState.isEmpty() && !hasDefaultVisibility)
3297     return;
3298
3299   if ( aResMgr->hasValue("windows_geometry" ,modName ) ) {
3300     long version = Qtx::versionToId( aResMgr->stringValue( "windows_geometry_version", modName, "" ) );
3301     QByteArray arr;
3302     if ( version > Qtx::versionToId( "7.4.1" ) )
3303       aResMgr->value( "windows_geometry", modName , arr );
3304     else
3305       arr = aDefaultState;
3306     QByteArray aTargetArray = processState(arr, storeWin, storeTb, true, aDefaultState);
3307     desktop()->restoreState( aTargetArray );
3308   }
3309
3310   QStringList mainToolbarsNames;
3311   mainToolbarsNames << "SalomeStandard" << "SalomeModules";
3312   QList<QToolBar*> mainToolbars = findToolBars( mainToolbarsNames );
3313   foreach( QToolBar* tb, mainToolbars ) tb->setVisible( true );
3314   /*
3315   if ( !myWinVis.contains( modName ) && aDefaultVisibility.isEmpty())
3316     return;
3317
3318   QMap<QString, bool> *tbMap = 0;
3319   QMap<QString, bool> *dwMap = 0;
3320   
3321   QMap<QString, bool> userTbMap, userDwMap;
3322   dockWindowsState( myWinVis[modName], userTbMap, userDwMap );
3323
3324   QMap<QString, bool> defaultTbMap, defaultDwMap;
3325   if(hasDefaultVisibility) {
3326     dockWindowsState( aDefaultVisibility, defaultTbMap, defaultDwMap);    
3327   }
3328
3329   if(storeTb) {
3330     tbMap =  &userTbMap;
3331   } else {
3332     if(hasDefaultVisibility){
3333       tbMap =  &defaultTbMap;
3334     }
3335   }
3336
3337   if(storeWin) {
3338     dwMap =  &userDwMap;
3339   } else {
3340     if(hasDefaultVisibility){
3341       dwMap =  &defaultDwMap;
3342     }
3343   }
3344
3345   if(tbMap) {
3346     QList<QToolBar*> tbList = findToolBars();
3347     for ( QList<QToolBar*>::iterator tit = tbList.begin(); tit != tbList.end(); ++tit )
3348       { 
3349         QToolBar* tb = *tit;
3350         if ( tbMap->contains( tb->objectName() ) ) {      
3351           tb->setVisible( (*tbMap)[tb->objectName()] );
3352         }
3353       }
3354   }
3355
3356   if(dwMap) {
3357     QList<QDockWidget*> dwList = qFindChildren<QDockWidget*>( desktop() );
3358     for ( QList<QDockWidget*>::iterator dit = dwList.begin(); dit != dwList.end(); ++dit )
3359       {
3360         QDockWidget* dw = *dit;
3361         
3362         QObject* po = Qtx::findParent( dw, "QMainWindow" );
3363         if ( po != desktop() )
3364           continue;
3365         
3366         if ( dwMap->contains( dw->objectName() ) )
3367           dw->setVisible( (*dwMap)[dw->objectName()] );
3368       }
3369   }
3370   */
3371 }
3372
3373
3374 /*!
3375   Saves windows geometry
3376 */
3377 void LightApp_Application::saveDockWindowsState()
3378 {
3379   if ( !desktop() )
3380     return;
3381
3382   bool storeWin = resourceMgr()->booleanValue( "Study", "store_positions", true );
3383   bool storeTb = resourceMgr()->booleanValue( "Study", "store_tool_positions", true );
3384
3385   if( !storeWin && !storeTb )
3386     return;
3387
3388   QString modName;
3389   if ( activeModule() )
3390     modName = activeModule()->name();
3391   else if ( activeStudy() )
3392     modName = "nomodule";
3393
3394   QString versionId = GUI_VERSION_STR;
3395 #if GUI_DEVELOPMENT > 0
3396   versionId += "dev";
3397 #endif
3398
3399   QByteArray arr = desktop()->saveState();
3400   resourceMgr()->setValue( "windows_geometry", modName, processState(arr, storeWin, storeTb, false) );
3401   resourceMgr()->setValue( "windows_geometry_version", modName, versionId );
3402
3403   QByteArray visArr;
3404   if ( myWinVis.contains( modName ) )
3405     visArr = myWinVis[modName];
3406
3407   QMap<QString, bool> tbMap, dwMap;
3408   dockWindowsState( visArr, tbMap, dwMap );
3409
3410   QList<QToolBar*> tbList = qFindChildren<QToolBar*>( desktop() );
3411   for ( QList<QToolBar*>::iterator it = tbList.begin(); it != tbList.end(); ++it )
3412   {
3413     QToolBar* tb = *it;
3414     tbMap.insert( tb->objectName(), tb->toggleViewAction()->isChecked() );
3415   }
3416
3417   QList<QDockWidget*> dwList = qFindChildren<QDockWidget*>( desktop() );
3418   for ( QList<QDockWidget*>::iterator it = dwList.begin(); it != dwList.end(); ++it )
3419   {
3420     QDockWidget* wid = *it;
3421     dwMap.insert( wid->objectName(), wid->toggleViewAction()->isChecked() );
3422   }
3423
3424   visArr = dockWindowsState( tbMap, dwMap );
3425
3426   myWinVis.insert( modName, visArr );
3427 }
3428
3429 QByteArray LightApp_Application::dockWindowsState( const QMap<QString, bool>& tb, const QMap<QString, bool>& dw ) const
3430 {
3431   QByteArray visArr;
3432   QDataStream stream( &visArr, QIODevice::WriteOnly );
3433
3434   stream << (uchar)ToolBarMarker;
3435   stream << tb.size();
3436   for ( QMap<QString, bool>::const_iterator tit = tb.begin(); tit != tb.end(); ++tit )
3437   {
3438     stream << tit.key();
3439     stream << (uchar)( tit.value() ? 1 : 0 );
3440   }
3441
3442   stream << (uchar)DockWidgetMarker;
3443   stream << dw.size();
3444   for ( QMap<QString, bool>::const_iterator wit = dw.begin(); wit != dw.end(); ++wit )
3445   {
3446     stream << wit.key();
3447     stream << (uchar)( wit.value() ? 1 : 0 );
3448   }
3449
3450   return visArr;
3451 }
3452
3453 void LightApp_Application::dockWindowsState( const QByteArray& arr, QMap<QString, bool>& tb, QMap<QString, bool>& dw ) const
3454 {
3455   tb.clear();
3456   dw.clear();
3457
3458   QByteArray visArr = arr;
3459   QDataStream stream( &visArr, QIODevice::ReadOnly );
3460
3461   uchar marker;
3462   stream >> marker;
3463   if ( marker != ToolBarMarker )
3464     return;
3465
3466   int lines;
3467   stream >> lines;
3468   for ( int i = 0; i < lines; ++i )
3469   {
3470     QString objectName;
3471     stream >> objectName;
3472     uchar shown;
3473     stream >> shown;
3474     tb.insert( objectName, shown );
3475   }
3476
3477   stream >> marker;
3478   if ( marker != DockWidgetMarker )
3479     return;
3480
3481   stream >> lines;
3482   for ( int j = 0; j < lines; ++j )
3483   {
3484     QString objectName;
3485     stream >> objectName;
3486     uchar shown;
3487     stream >> shown;
3488     dw.insert( objectName, shown );
3489   }
3490 }
3491
3492 /*!
3493   Adds icon names for modules
3494 */
3495 void LightApp_Application::moduleIconNames( QMap<QString, QString>& iconMap ) const
3496 {
3497   iconMap.clear();
3498
3499   SUIT_ResourceMgr* resMgr = resourceMgr();
3500   if ( !resMgr )
3501     return;
3502
3503   QStringList modList;
3504   modules( modList, false );
3505
3506   for ( QStringList::const_iterator it = modList.begin(); it != modList.end(); ++it )
3507   {
3508     QString modName = *it;
3509     QString modIntr = moduleName( modName );
3510     QString modIcon = resMgr->stringValue( modIntr, "icon", QString() );
3511
3512     if ( modIcon.isEmpty() )
3513       continue;
3514
3515     if ( SUIT_Tools::extension( modIcon ).isEmpty() )
3516       modIcon += QString( ".png" );
3517
3518     iconMap.insert( modName, modIcon );
3519   }
3520 }
3521
3522 /*!
3523   Inserts items in popup, which necessary for current application
3524 */
3525 void LightApp_Application::contextMenuPopup( const QString& type, QMenu* thePopup, QString& title )
3526 {
3527   //Add "Rename" item
3528   LightApp_SelectionMgr* selMgr = LightApp_Application::selectionMgr();
3529   bool cacheIsOn = selMgr->isSelectionCacheEnabled();
3530   selMgr->setSelectionCacheEnabled( true );
3531
3532   SUIT_DataBrowser* ob = objectBrowser();
3533
3534   CAM_Application::contextMenuPopup( type, thePopup, title );
3535
3536   if ( ob && type == ob->popupClientType() ) {
3537     thePopup->addSeparator();
3538     QAction* a = thePopup->addAction( tr( "MEN_REFRESH" ), this, SLOT( onRefresh() ) );
3539     if ( ob->shortcutKey(SUIT_DataBrowser::UpdateShortcut) )
3540       a->setShortcut( ob->shortcutKey(SUIT_DataBrowser::UpdateShortcut) );
3541   }
3542
3543 #ifndef DISABLE_SALOMEOBJECT
3544   if ( selMgr && ob ) {
3545     SALOME_ListIO selected;
3546     selMgr->selectedObjects( selected );
3547     if(selected.Extent() == 1){
3548       Handle(SALOME_InteractiveObject) anIObject = selected.First();
3549       SUIT_DataObject* obj = findObject(anIObject->getEntry());
3550       if(obj && obj->renameAllowed()) {
3551         QAction* a = new QAction(tr("MEN_RENAME_OBJ"), thePopup);
3552         connect( a, SIGNAL( triggered(bool) ), ob, SLOT( onStartEditing() ) );
3553         if ( ob->shortcutKey(SUIT_DataBrowser::RenameShortcut) )
3554           a->setShortcut( ob->shortcutKey(SUIT_DataBrowser::RenameShortcut) );
3555
3556         QList<QAction*> acts = thePopup->actions();
3557         QAction* firstAction = acts.count() > 0 ? acts.first() : 0;
3558         thePopup->insertAction(firstAction,a);
3559       }
3560     }
3561   }
3562 #endif
3563
3564   selMgr->setSelectionCacheEnabled( cacheIsOn );
3565 }
3566
3567 /*!
3568   Create empty study
3569 */
3570 void LightApp_Application::createEmptyStudy()
3571 {
3572   CAM_Application::createEmptyStudy();
3573
3574   if ( objectBrowser() )
3575     objectBrowser()->updateTree();
3576
3577   SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
3578   if ( aResMgr && activeStudy() ) {
3579     int autoSaveInterval = aResMgr->integerValue( "Study", "auto_save_interval", 0 );
3580     if ( autoSaveInterval > 0 ) myAutoSaveTimer->start( autoSaveInterval*60000 );
3581   }
3582 }
3583
3584 /*!Set desktop:*/
3585 void LightApp_Application::setDesktop( SUIT_Desktop* desk )
3586 {
3587   CAM_Application::setDesktop( desk );
3588
3589   if ( desk ) {
3590     connect( desk, SIGNAL( message( const QString& ) ),
3591              this, SLOT( onDesktopMessage( const QString& ) ), Qt::UniqueConnection );
3592     connect( desk, SIGNAL( windowActivated( SUIT_ViewWindow* ) ),
3593              this, SLOT( onWindowActivated( SUIT_ViewWindow* ) ), Qt::UniqueConnection );
3594   }
3595 }
3596
3597 /*!
3598   Activates module
3599   \param mod - module to be activated
3600 */
3601 bool LightApp_Application::activateModule( CAM_Module* mod )
3602 {
3603   bool res = CAM_Application::activateModule( mod );
3604
3605   if ( objectBrowser() )
3606     objectBrowser()->updateTree();
3607
3608   return res;
3609 }
3610
3611 /*!
3612   \return keyborad accelerators manager object
3613 */
3614 SUIT_Accel* LightApp_Application::accel() const
3615 {
3616   return myAccel;
3617 }
3618
3619 /*!
3620   Removes dead widget container from map
3621 */
3622 void LightApp_Application::onWCDestroyed( QObject* ob )
3623 {
3624   // remove destroyed widget container from windows map
3625   for ( WinMap::ConstIterator itr = myWin.begin(); itr != myWin.end(); ++itr )
3626   {
3627     if ( itr.value() != ob )
3628       continue;
3629
3630     int key = itr.key();
3631     myWin.remove( key );
3632     break;
3633   }
3634 }
3635
3636 void LightApp_Application::onMRUActivated( const QString& name )
3637 {
3638   SUIT_Session* s = SUIT_Session::session();
3639   if ( s && s->activeApplication() == this )
3640     onOpenDoc( name );
3641 }
3642
3643 void LightApp_Application::onStylePreferences()
3644 {
3645   Style_PrefDlg dlg( desktop() );
3646   dlg.exec();
3647
3648   resourceMgr()->setValue( "Style", "use_salome_style", Style_Salome::isActive() );
3649 }
3650
3651 void LightApp_Application::onFullScreen(){
3652   if(myScreenHelper) {
3653     if(desktop()->isFullScreen())
3654       myScreenHelper->switchToNormalScreen();
3655     else
3656       myScreenHelper->switchToFullScreen();
3657   }
3658 }
3659
3660 /*!
3661   Connects just added view manager
3662 */
3663 void LightApp_Application::addViewManager( SUIT_ViewManager* vm )
3664 {
3665   connect( vm, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
3666            this, SLOT( onCloseView( SUIT_ViewManager* ) ) );
3667   CAM_Application::addViewManager( vm );
3668 }
3669
3670 /*!
3671   Remove view manager from memory
3672 */
3673 void LightApp_Application::removeViewManager( SUIT_ViewManager* vm )
3674 {
3675   disconnect( vm, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
3676            this, SLOT( onCloseView( SUIT_ViewManager* ) ) );
3677   LightApp_Study* aStudy = dynamic_cast<LightApp_Study*>(activeStudy());
3678   if (aStudy )
3679     aStudy->removeObjectProperties( vm->getGlobalId() );
3680
3681   CAM_Application::removeViewManager( vm );
3682
3683   LightApp_SelectionMgr* selMgr = selectionMgr();
3684   QList<SUIT_Selector*> selectors;
3685   selMgr->selectors( selectors );
3686   foreach( SUIT_Selector* selector, selectors ) {
3687     if ( selector->owner() == vm->getViewModel() ) {
3688       delete selector;
3689     }
3690   }
3691
3692   // IPAL22894: Crash on closing OCC view
3693   //delete vm;
3694   vm->deleteLater();
3695 }
3696
3697 /*!
3698   Renames active window of desktop
3699 */
3700 void LightApp_Application::onRenameWindow()
3701 {
3702   if( !desktop() )
3703     return;
3704
3705   QWidget* w = desktop()->activeWindow();
3706   if( !w )
3707     return;
3708
3709   bool ok;
3710   QString name = QInputDialog::getText( w, tr( "TOT_RENAME" ), tr( "PRP_RENAME" ), QLineEdit::Normal, w->windowTitle(), &ok );
3711   if( ok && !name.isEmpty() )
3712     w->setWindowTitle( name );
3713 }
3714
3715 /*!
3716   Closes active window of desktop
3717 */
3718 void LightApp_Application::onCloseWindow()
3719 {
3720   if( !desktop() )
3721     return;
3722
3723   QWidget* w = desktop()->activeWindow();
3724   if( !w )
3725     return;
3726
3727   w->close();
3728 }
3729
3730 /*!
3731   Closes all windows of desktop
3732 */
3733 void LightApp_Application::onCloseAllWindow()
3734 {
3735   STD_TabDesktop* desk = dynamic_cast<STD_TabDesktop*>( desktop() );
3736   if( !desk )
3737     return;
3738
3739   QList<SUIT_ViewWindow*> wndList = desk->windows();
3740   SUIT_ViewWindow* wnd;
3741   foreach( wnd, wndList )
3742   {
3743     if ( wnd )
3744       wnd->close();
3745   }
3746 }
3747
3748 /*!
3749   Groups all windows of desktop
3750 */
3751 void LightApp_Application::onGroupAllWindow()
3752 {
3753   STD_TabDesktop* desk = dynamic_cast<STD_TabDesktop*>( desktop() );
3754   if( !desk )
3755     return;
3756
3757   QtxWorkstack* wgStack = desk->workstack();
3758   if ( wgStack )
3759     wgStack->stack();
3760 }
3761
3762 /*!
3763   \return if the library of module exists
3764   \param moduleTitle - title of module
3765 */
3766 bool LightApp_Application::isLibExists( const QString& moduleTitle ) const
3767 {
3768   if( moduleTitle.isEmpty() )
3769     return false;
3770
3771   QString lib = moduleLibrary( moduleTitle );
3772
3773   //abd: changed libSalomePyQtGUI to SalomePyQtGUI for WIN32
3774   bool isPythonModule = lib.contains("SalomePyQtGUI");
3775   bool isPythonLightModule = lib.contains("SalomePyQtGUILight");
3776
3777   QStringList paths;
3778 #ifdef WIN32
3779   paths = QString(::getenv( "PATH" )).split( ";", QString::SkipEmptyParts );
3780 #else
3781   paths = QString(::getenv( "LD_LIBRARY_PATH" )).split( ":", QString::SkipEmptyParts );
3782 #endif
3783
3784   bool isLibFound = false;
3785   QStringList::const_iterator anIt = paths.begin(), aLast = paths.end();
3786   for( ; anIt!=aLast; anIt++ )
3787   {
3788     QFileInfo inf( Qtx::addSlash( *anIt ) + lib );
3789
3790     if( inf.exists() )
3791       {
3792         isLibFound = true;
3793         break;
3794       }
3795   }
3796
3797   if ( !isLibFound )
3798     {
3799       INFOS( "\n****************************************************************" << std::endl
3800           << "*    Warning: library " << lib.toLatin1().constData() << " cannot be found" << std::endl
3801           << "*    Module " << moduleTitle.toLatin1().constData() << " will not be available in GUI mode" << std::endl
3802           << "****************************************************************" << std::endl );
3803     }
3804   else if ( !isPythonModule && !isPythonLightModule)
3805     return true;
3806
3807   if ( isPythonModule || isPythonLightModule)
3808     {
3809       QString pylib = moduleName( moduleTitle ) + QString(".py");
3810       QString pylibgui = moduleName( moduleTitle ) + QString("GUI.py");
3811
3812       // Check the python library
3813 // #ifdef WIN32
3814 //       paths = QString(::getenv( "PATH" )).split( ";", QString::SkipEmptyParts );
3815 // #else
3816       paths = QString(::getenv( "PYTHONPATH" )).split( ":", QString::SkipEmptyParts );
3817 // #endif
3818       bool isPyLib = false, isPyGuiLib = false;
3819       QStringList::const_iterator anIt = paths.begin(), aLast = paths.end();
3820       for( ; anIt!=aLast; anIt++ )
3821         {
3822           QFileInfo inf( Qtx::addSlash( *anIt ) + pylib );
3823           QFileInfo infgui( Qtx::addSlash( *anIt ) + pylibgui );
3824
3825           if(!isPythonLightModule)
3826             if( !isPyLib && inf.exists() )
3827               isPyLib = true;
3828
3829           if( !isPyGuiLib && infgui.exists() )
3830             isPyGuiLib = true;
3831
3832           if ((isPyLib || isPythonLightModule ) && isPyGuiLib && isLibFound)
3833             return true;
3834         }
3835
3836       printf( "\n****************************************************************\n" );
3837       printf( "*    Warning: python library for %s cannot be found:\n", moduleTitle.toLatin1().constData() );
3838       if (!isPyLib)
3839         printf( "*    No module named %s\n", moduleName( moduleTitle ).toLatin1().constData() );
3840       if (!isPyGuiLib)
3841         printf( "*    No module named %s\n", (moduleName( moduleTitle ) + QString("GUI")).toLatin1().constData() );
3842       printf( "****************************************************************\n" );
3843       return true;
3844   }
3845   return false;
3846 }
3847
3848 /*!
3849   \return default name for an active study
3850 */
3851 void LightApp_Application::setDefaultStudyName( const QString& theName )
3852 {
3853   QStringList anInfoList;
3854   modules( anInfoList, false );
3855
3856   LightApp_Study* aStudy = (LightApp_Study*)activeStudy();
3857   if( anInfoList.count() == 1 && // to avoid a conflict between different modules
3858       !aStudy->isSaved() )
3859   {
3860     aStudy->setStudyName( theName );
3861     updateDesktopTitle();
3862   }
3863 }
3864
3865 /*!
3866   Custom event handler
3867 */
3868 bool LightApp_Application::event( QEvent* e )
3869 {
3870   if( e && e->type()==2000 )
3871   {
3872     SALOME_CustomEvent* ce = ( SALOME_CustomEvent* )e;
3873     QString* d = ( QString* )ce->data();
3874     if( SUIT_MessageBox::question(0, tr("WRN_WARNING"),
3875                                   d ? *d : "",
3876                                   SUIT_MessageBox::Yes | SUIT_MessageBox::No,
3877                                   SUIT_MessageBox::Yes ) == SUIT_MessageBox::Yes )
3878       showPreferences( tr( "PREF_APP" ) );
3879     if( d )
3880       delete d;
3881     return true;
3882   }
3883   return CAM_Application::event( e );
3884 }
3885
3886 /*! Check data object */
3887 bool LightApp_Application::checkDataObject(LightApp_DataObject* theObj)
3888 {
3889   if (theObj)
3890     {
3891       bool isSuitable = !theObj->entry().isEmpty() &&
3892                         !theObj->componentDataType().isEmpty() &&
3893                         !theObj->name().isEmpty();
3894       return isSuitable;
3895     }
3896
3897   return false;
3898 }
3899
3900 int LightApp_Application::openChoice( const QString& aName )
3901 {
3902   int choice = CAM_Application::openChoice( aName );
3903
3904   if ( choice == OpenExist ) // The document is already open.
3905   {
3906     // Do you want to reload it?
3907     if ( SUIT_MessageBox::question( desktop(), tr( "WRN_WARNING" ), tr( "QUE_DOC_ALREADYOPEN" ).arg( aName ),
3908                                     SUIT_MessageBox::Yes | SUIT_MessageBox::No, SUIT_MessageBox::No ) == SUIT_MessageBox::Yes )
3909       choice = OpenReload;
3910   }
3911
3912   return choice;
3913 }
3914
3915 bool LightApp_Application::openAction( const int choice, const QString& aName )
3916 {
3917   bool res = false;
3918   switch ( choice )
3919   {
3920   case OpenReload:
3921     {
3922       STD_Application* app = 0;
3923       SUIT_Session* session = SUIT_Session::session();
3924       QList<SUIT_Application*> appList = session->applications();
3925       for ( QList<SUIT_Application*>::iterator it = appList.begin(); it != appList.end() && !app; ++it )
3926       {
3927         if ( (*it)->activeStudy() && (*it)->activeStudy()->studyName() == aName )
3928           app = ::qobject_cast<STD_Application*>( *it );
3929       }
3930
3931       if ( app )
3932       {
3933         app->onCloseDoc( false );
3934         appList = session->applications();
3935         STD_Application* other = 0;
3936         for ( QList<SUIT_Application*>::iterator it = appList.begin(); it != appList.end() && !other; ++it )
3937           other = ::qobject_cast<STD_Application*>( *it );
3938
3939         if ( other )
3940           res = other->onOpenDoc( aName );
3941       }
3942     }
3943     break;
3944   default:
3945     res = CAM_Application::openAction( choice, aName );
3946     break;
3947   }
3948
3949   return res;
3950 }
3951
3952 QStringList LightApp_Application::viewManagersTypes() const
3953 {
3954   QStringList aTypesList;
3955   aTypesList += myUserWmTypes;
3956 #ifndef DISABLE_GLVIEWER
3957   aTypesList<<GLViewer_Viewer::Type();
3958 #endif
3959 #ifndef DISABLE_PLOT2DVIEWER
3960   aTypesList<<Plot2d_Viewer::Type();
3961 #endif
3962 #ifndef DISABLE_QXGRAPHVIEWER
3963   aTypesList<<QxScene_Viewer::Type();
3964 #endif
3965 #ifndef DISABLE_PVVIEWER
3966   aTypesList<<PVViewer_Viewer::Type();
3967 #endif
3968 #ifndef DISABLE_OCCVIEWER
3969   aTypesList<<OCCViewer_Viewer::Type();
3970 #endif
3971 #ifndef DISABLE_VTKVIEWER
3972  #ifndef DISABLE_SALOMEOBJECT
3973   aTypesList<<SVTK_Viewer::Type();
3974  #else
3975   aTypesList<<VTKViewer_Viewer::Type();
3976  #endif
3977 #endif
3978   return aTypesList;
3979 }
3980 /*!
3981  * Removes all view managers of known types
3982  * Other view managers are ignored
3983  */
3984 void LightApp_Application::clearKnownViewManagers()
3985 {
3986   QStringList aTypesList = viewManagersTypes();
3987   QList<SUIT_ViewManager*> aMgrList;
3988   viewManagers( aMgrList );
3989   foreach (SUIT_ViewManager* aMgr, aMgrList) {
3990     if (aTypesList.contains(aMgr->getType()))
3991       removeViewManager(aMgr);
3992   }
3993 }
3994
3995 /*!
3996   Copy of current selection
3997  */
3998 void LightApp_Application::onCopy()
3999 {
4000   LightApp_Module* m = dynamic_cast<LightApp_Module*>( activeModule() );
4001   if( m )
4002     m->copy();
4003 }
4004
4005 /*!
4006   Paste of current data in clipboard
4007  */
4008 void LightApp_Application::onPaste()
4009 {
4010   LightApp_Module* m = dynamic_cast<LightApp_Module*>( activeModule() );
4011   if( m )
4012     m->paste();
4013 }
4014
4015 /*!
4016   Browse (i.e. set focus on) the published objects
4017   \param theIsApplyAndClose - flag indicating that the dialog for creating objects
4018                               has been accepted by Ok (or Apply & Close) button
4019   \param theIsOptimizedBrowsing - flag switching to optimized browsing mode
4020                                   (to select the first published object only)
4021   \return entry of the selected object
4022  */
4023 QString LightApp_Application::browseObjects( const QStringList& theEntryList,
4024                                              const bool theIsApplyAndClose,
4025                                              const bool theIsOptimizedBrowsing )
4026 {
4027   QString aResult;
4028   if( SUIT_ResourceMgr* aResourceMgr = resourceMgr() )
4029   {
4030     int aBrowsePolicy = aResourceMgr->integerValue( "ObjectBrowser", "browse_published_object", (int)BP_Never );
4031     switch( aBrowsePolicy )
4032     {
4033       case BP_Never:
4034         return aResult;
4035       case BP_ApplyAndClose:
4036         if( !theIsApplyAndClose )
4037           return aResult;
4038       case BP_Always:
4039       default:
4040         break;
4041     }
4042   }
4043
4044   LightApp_Study* aStudy = dynamic_cast<LightApp_Study*>( activeStudy() );
4045   if( !aStudy )
4046     return aResult;
4047
4048   SUIT_DataBrowser* anOB = objectBrowser();
4049   if( !anOB )
4050     return aResult;
4051
4052   SUIT_AbstractModel* aModel = dynamic_cast<SUIT_AbstractModel*>( anOB->model() );
4053   if( !aModel )
4054     return aResult;
4055
4056   QStringListIterator anIter( theEntryList );
4057   if( theIsOptimizedBrowsing )
4058   {
4059     // go to the last entry
4060     anIter.toBack();
4061     if( anIter.hasPrevious() )
4062       anIter.previous();
4063   }
4064
4065   // scroll to each entry in the list
4066   // (in optimized mode - to the last entry only)
4067   QString anEntry;
4068   LightApp_DataObject* anObject = 0;
4069   while( anIter.hasNext() )
4070   {
4071     anEntry = anIter.next();
4072     if( !anEntry.isEmpty() )
4073     {
4074       anObject = aStudy->findObjectByEntry( anEntry );
4075       if( anObject )
4076       {
4077         QModelIndex anIndex = aModel->index( anObject );
4078         anOB->treeView()->scrollTo( anIndex );
4079       }
4080     }
4081   }
4082
4083   // always select the last object
4084   if( anObject && !anEntry.isEmpty() )
4085   {
4086     QList<SUIT_Selector*> aSelectorList;
4087     selectionMgr()->selectors( "ObjectBrowser", aSelectorList );
4088     if( !aSelectorList.isEmpty() )
4089     {
4090       if( LightApp_OBSelector* aSelector = dynamic_cast<LightApp_OBSelector*>( aSelectorList.first() ) )
4091       {
4092         bool anIsAutoBlock = aSelector->autoBlock();
4093
4094         // temporarily disable auto block, to emit LightApp_SelectionMgr::currentSelectionChanged() signal
4095         aSelector->setAutoBlock( false );
4096
4097         SUIT_DataOwnerPtrList aList;
4098 #ifndef DISABLE_SALOMEOBJECT
4099         Handle(SALOME_InteractiveObject) aSObj = new SALOME_InteractiveObject
4100           ( anObject->entry().toLatin1().constData(),
4101             anObject->componentDataType().toLatin1().constData(),
4102             anObject->name().toLatin1().constData() );
4103         LightApp_DataOwner* owner = new LightApp_DataOwner( aSObj  );
4104 #else
4105         LightApp_DataOwner* owner = new LightApp_DataOwner( anEntry );
4106 #endif
4107
4108         aList.append( owner );
4109         selectionMgr()->setSelected( aList );
4110         aResult = anEntry;
4111
4112         // restore auto block flag
4113         aSelector->setAutoBlock( anIsAutoBlock );
4114       }
4115     }
4116   }
4117
4118   return aResult;
4119 }
4120
4121 SUIT_DataObject* LightApp_Application::findObject( const QString& id ) const
4122 {
4123   LightApp_Study* study = dynamic_cast<LightApp_Study*>( activeStudy() );
4124   return study ? study->findObjectByEntry( id ) : 0;
4125 }
4126
4127 /*!
4128   Checks that an object can be renamed.
4129   \param entry entry of the object
4130   \brief Return \c true if object can be renamed
4131 */
4132 bool LightApp_Application::renameAllowed( const QString& /*entry*/) const {
4133   return false;
4134 }
4135
4136 /*!
4137   Rename object by entry.
4138   \param entry entry of the object
4139   \param name new name of the object
4140   \brief Return \c true if rename operation finished successfully, \c false otherwise.
4141 */
4142 bool LightApp_Application::renameObject( const QString& entry, const QString& ) {
4143   return false;
4144 }
4145
4146 /*! Process standard messages from desktop */
4147 void LightApp_Application::onDesktopMessage( const QString& message )
4148 {
4149   const QString sectionSeparator = "/";
4150
4151   if ( message.toLower() == "updateobjectbrowser" ||
4152        message.toLower() == "updateobjbrowser" ) {
4153     // update object browser
4154     updateObjectBrowser();
4155   }
4156   else if ( message.toLower().startsWith( "activate_viewer" ) ) {
4157     QString vtype = message.split( sectionSeparator ).last();
4158     if ( !vtype.isEmpty() )
4159       getViewManager( vtype, true );
4160   }
4161   else {
4162     QStringList data = message.split( sectionSeparator );
4163     if ( data.count() > 1 ) {
4164       QString msgType = data[0].trimmed();
4165       LightApp_Module* sMod = 0;
4166       CAM_Module* mod = module( msgType );
4167       if ( !mod )
4168         mod = module( moduleTitle( msgType ) );
4169       if ( mod && mod->inherits( "LightApp_Module" ) )
4170         sMod = (LightApp_Module*)mod;
4171
4172       if ( msgType.toLower() == "preferences" ) {
4173         // requested preferences change: should be given as "preferences/<section>/<name>/<value>"
4174         // for example "preferences/Study/multi_file_dump/true"
4175         if ( data.count() > 3 ) {
4176           QString section = data[1].trimmed();
4177           QString param   = data[2].trimmed();
4178           QString value   = QStringList( data.mid(3) ).join( sectionSeparator );
4179           resourceMgr()->setValue( section, param, value );
4180         }
4181       }
4182       else if ( sMod ) {
4183         // received message for the module
4184         QString msg = QStringList( data.mid(1) ).join( sectionSeparator );
4185         sMod->message( msg );
4186       }
4187     }
4188   }
4189 }
4190
4191 /*!
4192   Internal method. 
4193   Returns all top level toolbars.
4194   Note : Result list contains only main window toolbars, not including toolbars from viewers.
4195 */
4196 QList<QToolBar*> LightApp_Application::findToolBars( const QStringList& names )
4197 {
4198   QList<QToolBar*> aResult;
4199   QList<QToolBar*> tbList = qFindChildren<QToolBar*>( desktop() );
4200   for ( QList<QToolBar*>::iterator tit = tbList.begin(); tit != tbList.end(); ++tit ) {
4201     QToolBar* tb = *tit;    
4202     QObject* po = Qtx::findParent( tb, "QMainWindow" );
4203     if ( po != desktop() )
4204       continue; 
4205     if ( names.isEmpty() || names.contains( tb->objectName() ) )
4206       aResult.append(tb);
4207   }
4208   return aResult;
4209 }
4210
4211 /*!
4212   Internal method to parse toolbars and dockable windows state.
4213  */
4214 QByteArray LightApp_Application::processState(QByteArray& input, 
4215                                               const bool processWin, 
4216                                               const bool processTb, 
4217                                               const bool isRestoring, 
4218                                               QByteArray defaultState) {
4219
4220   QByteArray aRes;
4221   bool hasDefaultState  = !defaultState.isEmpty();
4222   bool isDockWinWriten = false;
4223   int nbDocWin = -1;
4224   //Write date from users settings
4225   if(isRestoring){
4226     QDataStream tmpInputData(&input, QIODevice::ReadOnly);
4227     int marker, version;
4228     uchar dockmarker;
4229     tmpInputData >> marker;
4230     tmpInputData >> version;
4231     tmpInputData >> dockmarker;
4232     tmpInputData >> nbDocWin;
4233   }  
4234   if(processWin && processTb && !isRestoring) {
4235     aRes = input;
4236   } else if(!processWin && !processTb ) {
4237     if(hasDefaultState)
4238       aRes = defaultState;
4239   } else {
4240     QDataStream aData(&aRes, QIODevice::WriteOnly);
4241     QList<QToolBar*> aToolBars = findToolBars();
4242
4243     QStringList aNames;
4244     for ( QList<QToolBar*>::iterator tit = aToolBars.begin(); tit != aToolBars.end(); ++tit ) { 
4245       QToolBar* tb = *tit;
4246       aNames.append(tb->objectName());
4247     }
4248
4249     int toolBarMarkerIndex = getToolbarMarkerIndex(input,aNames);
4250     if(toolBarMarkerIndex < 0)
4251       return aRes;
4252     QDataStream anInputData(&input, QIODevice::ReadOnly);
4253
4254     int toolBarMarkerIndexDef;
4255     if(hasDefaultState) {
4256       toolBarMarkerIndexDef = getToolbarMarkerIndex(defaultState, aNames);
4257       if(toolBarMarkerIndexDef < 0)
4258         return aRes;      
4259     }
4260     QDataStream anInputDataDef(&defaultState, QIODevice::ReadOnly);
4261
4262     QDataStream* aTargetData = 0;
4263     int          aTargetIndex = -1;
4264
4265     QByteArray currentArr = desktop()->saveState();
4266     QDataStream anInputDataCur(&currentArr, QIODevice::ReadOnly);
4267     bool useInputData = !isRestoring || (isRestoring && nbDocWin > 0);
4268     if(processWin && useInputData) {
4269       aTargetData = &anInputData;
4270       aTargetIndex = toolBarMarkerIndex;
4271     } else {
4272       //Write date from default settings
4273       if(hasDefaultState) {
4274         aTargetData = &anInputDataDef;
4275         aTargetIndex = toolBarMarkerIndexDef;
4276       } else {
4277         //If no default state, write current snapshot of the dockable windows
4278         if(isRestoring) {
4279           aTargetData = &anInputDataCur;
4280           int toolBarMarkerIndexCur = getToolbarMarkerIndex(currentArr, aNames);
4281           aTargetIndex = toolBarMarkerIndexCur;
4282         }         
4283       }
4284     }
4285
4286     if(aTargetData && aTargetIndex >= 0 ) {
4287       aTargetData->device()->seek(0);
4288       while( aTargetData->device()->pos() < aTargetIndex ) {
4289         uchar ch;
4290         *aTargetData >> ch;
4291         aData<<ch;
4292       }
4293       isDockWinWriten = true;
4294     }
4295     
4296     aTargetData = 0;
4297     aTargetIndex = -1;
4298
4299     if(processTb) {
4300       aTargetData = &anInputData;
4301       aTargetIndex = toolBarMarkerIndex;
4302     } else {
4303       if(hasDefaultState) {
4304         aTargetData = &anInputDataDef;
4305         aTargetIndex = toolBarMarkerIndexDef;   
4306       }      
4307     }
4308
4309     if(aTargetData && aTargetIndex >= 0) {
4310       int index;
4311       if(!isDockWinWriten ) {
4312         //Write version marker
4313         int marker, version;
4314         aTargetData->device()->seek(0);
4315         *aTargetData >> marker;
4316         *aTargetData >> version;
4317         aData << marker;
4318         aData << version;
4319         aData << (uchar) QDockWidgetMarker;
4320         aData << (int) 0;
4321         int shift = 4*sizeof(int) + sizeof(QSize);
4322         index = aTargetIndex - shift;
4323       } else {
4324         index = aTargetIndex;
4325       }
4326       
4327       aTargetData->device()->seek(index);
4328       while(!aTargetData->atEnd()) {
4329         uchar ch;
4330         *aTargetData >> ch;
4331         aData << ch;
4332       }
4333     } else { // Not treat toolbars
4334       aData << (uchar) QToolBarMarker;
4335       aData << (int) 0; //Nb toolbars = 0
4336     }
4337   }
4338   return aRes;
4339 }
4340
4341 /*!
4342   \brief Emits operationFinished signal.
4343   \param theModuleName the name of the module which perfomed the operation
4344   \param theOperationName the operation name
4345   \param theEntryList the list of the created objects entries
4346 */
4347 void LightApp_Application::emitOperationFinished( const QString& theModuleName,
4348                                                   const QString& theOperationName,
4349                                                   const QStringList& theEntryList )
4350 {
4351   emit operationFinished( theModuleName, theOperationName, theEntryList );
4352 }
4353
4354 /*!
4355   Update visibility state of given objects
4356 */
4357 void LightApp_Application::updateVisibilityState( DataObjectList& theList,
4358                                                   SUIT_ViewModel*  theViewModel )
4359 {
4360   if ( !theViewModel || theList.isEmpty() ) return;
4361
4362   LightApp_Study* aStudy = dynamic_cast<LightApp_Study*>(activeStudy());
4363   if ( !aStudy ) return;
4364
4365   SALOME_View* aView = dynamic_cast<SALOME_View*>( theViewModel );
4366
4367   for ( DataObjectList::iterator itr = theList.begin(); itr != theList.end(); ++itr ) {
4368     LightApp_DataObject* obj = dynamic_cast<LightApp_DataObject*>(*itr);
4369
4370     if ( !obj || aStudy->isComponent( obj->entry() ) )
4371       continue;
4372
4373     LightApp_Module* anObjModule = dynamic_cast<LightApp_Module*>(obj->module());
4374     if ( anObjModule ) {
4375       LightApp_Displayer* aDisplayer = anObjModule->displayer();
4376       if ( aDisplayer ) {
4377         Qtx::VisibilityState anObjState = Qtx::UnpresentableState;
4378         if ( aDisplayer->canBeDisplayed( obj->entry(), theViewModel->getType() ) ) {
4379           if ( aView && aDisplayer->IsDisplayed( obj->entry(), aView ) )
4380             anObjState = Qtx::ShownState;
4381           else
4382             anObjState = Qtx::HiddenState;
4383         }
4384         aStudy->setVisibilityState( obj->entry(), anObjState );
4385       }
4386     }
4387   }
4388 }
4389
4390 /*!
4391  * Called when window activated
4392  */
4393 void LightApp_Application::onWindowActivated( SUIT_ViewWindow* theViewWindow )
4394 {
4395   SUIT_DataBrowser* anOB = objectBrowser();
4396   if ( !anOB )
4397     return;
4398   SUIT_DataObject* rootObj = anOB->root();
4399   if ( !rootObj )
4400     return;
4401
4402   DataObjectList listObj = rootObj->children( true );
4403
4404   SUIT_ViewModel* vmod = 0;
4405   if ( SUIT_ViewManager* vman = theViewWindow->getViewManager() )
4406     vmod = vman->getViewModel();
4407   updateVisibilityState( listObj, vmod );
4408 }
4409
4410 /*!
4411   Called then view manager removed
4412 */
4413 void LightApp_Application::onViewManagerRemoved( SUIT_ViewManager* )
4414 {
4415   ViewManagerList lst;
4416   viewManagers( lst );
4417   if ( lst.count() == 1) { // in case if closed last view window
4418     LightApp_Study* aStudy = dynamic_cast<LightApp_Study*>( activeStudy() );
4419     if ( aStudy )
4420       aStudy->setVisibilityStateForAll( Qtx::UnpresentableState );
4421   }
4422 }
4423
4424 /*!
4425   Check existing document.
4426 */
4427 bool LightApp_Application::checkExistingDoc()
4428 {
4429   bool result = true;
4430   if( activeStudy() ) {
4431     int answer = SUIT_MessageBox::question( desktop(), 
4432                                             tr( "APPCLOSE_CAPTION" ), 
4433                                             tr( "STUDYCLOSE_DESCRIPTION" ),
4434                                             tr( "APPCLOSE_SAVE" ), 
4435                                             tr( "APPCLOSE_CLOSE" ),
4436                                             tr( "APPCLOSE_CANCEL" ), 0 );
4437     if(answer == 0) {
4438       if ( activeStudy()->isSaved() ) {
4439         onSaveDoc();
4440         closeDoc( false );
4441       } else if ( onSaveAsDoc() ) {
4442         if( !closeDoc( false ) ) {
4443           result = false;
4444         }
4445       } else {
4446         result = false;
4447       } 
4448     }
4449     else if( answer == 1 ) {
4450       closeDoc( false );
4451     } else if( answer == 2 ) {
4452       result = false;
4453     }
4454   }
4455   return result;
4456 }
4457
4458 #ifndef DISABLE_PYCONSOLE
4459
4460 PyConsole_Interp* LightApp_Application::getPyInterp()
4461 {
4462   static PyConsole_Interp* myInterp = 0;
4463   if ( !myInterp )
4464     myInterp = createPyInterp();
4465   return myInterp;
4466 }
4467
4468 PyConsole_Interp* LightApp_Application::createPyInterp()
4469 {
4470   return new LightApp_PyInterp();
4471 }
4472
4473 #endif // DISABLE_PYCONSOLE