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