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