Salome HOME
Join modifications from BR_Dev_For_4_0 tag V4_1_1.
[modules/smesh.git] / src / SMESHGUI / SMESHGUI_CreatePatternDlg.cxx
1 //  SMESH SMESHGUI : GUI for SMESH component
2 //
3 //  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 //  This library is free software; you can redistribute it and/or
7 //  modify it under the terms of the GNU Lesser General Public
8 //  License as published by the Free Software Foundation; either
9 //  version 2.1 of the License.
10 //
11 //  This library is distributed in the hope that it will be useful,
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 //  Lesser General Public License for more details.
15 //
16 //  You should have received a copy of the GNU Lesser General Public
17 //  License along with this library; if not, write to the Free Software
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22 //
23 //
24 //  File   : SMESHGUI_CreatePatternDlg.cxx
25 //  Author : Sergey LITONIN
26 //  Module : SMESH
27
28 #include "SMESHGUI_CreatePatternDlg.h"
29
30 #include "SMESHGUI.h"
31 #include "SMESHGUI_SpinBox.h"
32 #include "SMESHGUI_PatternWidget.h"
33 #include "SMESHGUI_Utils.h"
34 #include "SMESHGUI_VTKUtils.h"
35 #include "SMESHGUI_PatternUtils.h"
36 #include "SMESHGUI_GEOMGenUtils.h"
37
38 #include "SMESH_NumberFilter.hxx"
39
40 #include "SUIT_ResourceMgr.h"
41 #include "SUIT_Desktop.h"
42 #include "SUIT_FileDlg.h"
43 #include "SUIT_Session.h"
44 #include "SUIT_MessageBox.h"
45
46 #include "SalomeApp_Study.h"
47 #include "LightApp_Application.h"
48 #include "LightApp_DataOwner.h"
49 #include "LightApp_SelectionMgr.h"
50 #include "SalomeApp_Tools.h"
51
52 #include "SALOMEDS_SObject.hxx"
53
54 #include "SALOME_ListIO.hxx"
55 #include "SVTK_ViewModel.h"
56 #include "SVTK_ViewWindow.h"
57 #include "SVTK_Selector.h"
58 #include "SVTK_Selection.h"
59
60 // OCCT Includes
61 #include <TColStd_MapOfInteger.hxx>
62
63 // QT Includes
64 #include <qframe.h>
65 #include <qlayout.h>
66 #include <qlineedit.h>
67 #include <qpushbutton.h>
68 #include <qgroupbox.h>
69 #include <qlabel.h>
70 #include <qradiobutton.h>
71 #include <qcheckbox.h>
72 #include <qbuttongroup.h>
73 #include <qmessagebox.h>
74 #include <qapplication.h>
75
76 #define SPACING 5
77 #define MARGIN  10
78
79 /*!
80  *  Class       : SMESHGUI_CreatePatternDlg
81  *  Description : Dialog to specify filters for VTK viewer
82  */
83
84 //=======================================================================
85 // function : SMESHGUI_CreatePatternDlg()
86 // purpose  : Constructor
87 //=======================================================================
88 SMESHGUI_CreatePatternDlg::SMESHGUI_CreatePatternDlg( SMESHGUI*   theModule,
89                                                       const int   theType,
90                                                       const char* theName)
91      : QDialog( SMESH::GetDesktop( theModule ), theName, false,
92                 WStyle_Customize | WStyle_NormalBorder | WStyle_Title | WStyle_SysMenu),
93      mySMESHGUI( theModule ),
94      mySelectionMgr( SMESH::GetSelectionMgr( theModule ) )
95 {
96   setCaption(tr("CAPTION"));
97
98   QVBoxLayout* aDlgLay = new QVBoxLayout (this, MARGIN, SPACING);
99
100   QFrame* aMainFrame = createMainFrame  (this);
101   QFrame* aBtnFrame  = createButtonFrame(this);
102
103   aDlgLay->addWidget(aMainFrame);
104   aDlgLay->addWidget(aBtnFrame);
105
106   aDlgLay->setStretchFactor(aMainFrame, 1);
107
108   if ( SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI ))
109     mySelector = aViewWindow->GetSelector();
110
111   myHelpFileName = "pattern_mapping_page.html";
112
113   Init(theType);
114 }
115
116 //=======================================================================
117 // function : createMainFrame()
118 // purpose  : Create frame containing dialog's input fields
119 //=======================================================================
120 QFrame* SMESHGUI_CreatePatternDlg::createMainFrame (QWidget* theParent)
121 {
122   QPixmap iconSlct     (SMESH::GetResourceMgr( mySMESHGUI )->loadPixmap("SMESH", tr("ICON_SELECT")));
123   QPixmap icon2d       (SMESH::GetResourceMgr( mySMESHGUI )->loadPixmap("SMESH", tr("ICON_PATTERN_2d")));
124   QPixmap icon3d       (SMESH::GetResourceMgr( mySMESHGUI )->loadPixmap("SMESH", tr("ICON_PATTERN_3d")));
125   QPixmap iconSample2d (SMESH::GetResourceMgr( mySMESHGUI )->loadPixmap("SMESH", tr("ICON_PATTERN_SAMPLE_2D")));
126
127   QGroupBox* aMainGrp = new QGroupBox(1, Qt::Horizontal, theParent);
128   aMainGrp->setFrameStyle(QFrame::NoFrame);
129   aMainGrp->setInsideMargin(0);
130
131   // Pattern type group
132
133   myTypeGrp = new QButtonGroup (1, Qt::Vertical, tr("PATTERN_TYPE"), aMainGrp);
134   mySwitch2d = new QRadioButton (myTypeGrp);
135   mySwitch3d = new QRadioButton (myTypeGrp);
136   mySwitch2d->setPixmap(icon2d);
137   mySwitch3d->setPixmap(icon3d);
138   myTypeGrp->insert(mySwitch2d, Type_2d);
139   myTypeGrp->insert(mySwitch3d, Type_3d);
140
141   QGroupBox* aPatternGrp = new QGroupBox(1, Qt::Horizontal, tr("PATTERN"), aMainGrp);
142
143   // Mesh and pattern name group
144
145   QGroupBox* aMeshGrp = new QGroupBox(1, Qt::Vertical, aPatternGrp);
146   aMeshGrp->setFrameStyle(QFrame::NoFrame);
147   aMeshGrp->setInsideMargin(0);
148
149   new QLabel(tr("MESH_OR_SUBMESH"), aMeshGrp);
150
151   QPushButton* aSelBtn = new QPushButton(aMeshGrp);
152   aSelBtn->setPixmap(iconSlct);
153   myMeshEdit = new QLineEdit(aMeshGrp);
154   myMeshEdit->setReadOnly(true);
155
156   QGroupBox* aPattGrp = new QGroupBox(1, Qt::Vertical, aPatternGrp);
157   aPattGrp->setFrameStyle(QFrame::NoFrame);
158   aPattGrp->setInsideMargin(0);
159
160   new QLabel(tr("PATTERN_NAME"), aPattGrp);
161   myName = new QLineEdit(aPattGrp);
162
163   // Picture 2d
164
165   myPicture2d = new SMESHGUI_PatternWidget(aPatternGrp),
166   myPicture2d->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding));
167
168   // Project check box
169
170   myProjectChk = new QCheckBox(tr("PROJECT"), aPatternGrp);
171
172   // Connect signals and slots
173
174   connect(myTypeGrp,    SIGNAL(clicked(int) ), SLOT(onTypeChanged(int)));
175   connect(myProjectChk, SIGNAL(toggled(bool)), SLOT(onProject(bool)   ));
176   connect(aSelBtn,      SIGNAL(clicked()      ), SLOT(onSelBtnClicked()));
177
178   return aMainGrp;
179 }
180
181 //=======================================================================
182 // function : createButtonFrame()
183 // purpose  : Create frame containing buttons
184 //=======================================================================
185 QFrame* SMESHGUI_CreatePatternDlg::createButtonFrame (QWidget* theParent)
186 {
187   QFrame* aFrame = new QFrame(theParent);
188   aFrame->setFrameStyle(QFrame::Box | QFrame::Sunken);
189
190   myOkBtn    = new QPushButton(tr("SMESH_BUT_OK"    ), aFrame);
191   mySaveBtn  = new QPushButton(tr("SAVE"            ), aFrame);
192   myCloseBtn = new QPushButton(tr("SMESH_BUT_CANCEL"), aFrame);
193   myHelpBtn = new QPushButton(tr("SMESH_BUT_HELP"), aFrame);
194
195   QSpacerItem* aSpacer = new QSpacerItem(0, 0, QSizePolicy::Expanding, QSizePolicy::Minimum);
196
197   QHBoxLayout* aLay = new QHBoxLayout(aFrame, MARGIN, SPACING);
198
199   aLay->addWidget(myOkBtn);
200   aLay->addWidget(mySaveBtn);
201   aLay->addItem(aSpacer);
202   aLay->addWidget(myCloseBtn);
203   aLay->addWidget(myHelpBtn);
204
205   connect(myOkBtn,    SIGNAL(clicked()), SLOT(onOk()));
206   connect(myCloseBtn, SIGNAL(clicked()), SLOT(onClose()));
207   connect(mySaveBtn, SIGNAL(clicked()), SLOT(onSave()));
208   connect(myHelpBtn, SIGNAL(clicked()), SLOT(onHelp()));
209
210   return aFrame;
211 }
212
213 //=======================================================================
214 // function : ~SMESHGUI_CreatePatternDlg()
215 // purpose  : Destructor
216 //=======================================================================
217 SMESHGUI_CreatePatternDlg::~SMESHGUI_CreatePatternDlg()
218 {
219   // no need to delete child widgets, Qt does it all for us
220 }
221
222 //=======================================================================
223 // function : onProject()
224 // purpose  : SLOT. Called when state of "Project nodes on ther face"
225 //            checkbox is changed
226 //=======================================================================
227 void SMESHGUI_CreatePatternDlg::onProject (bool)
228 {
229   loadFromObject(false);
230   displayPreview();
231 }
232
233 //=======================================================================
234 // function : Init()
235 // purpose  : Init dialog fields, connect signals and slots, show dialog
236 //=======================================================================
237 void SMESHGUI_CreatePatternDlg::Init( const int theType )
238 {
239   myIsLoaded     = false;
240   myType         = -1;
241   myNbPoints     = -1;
242   mySubMesh      = SMESH::SMESH_subMesh::_nil();
243   myMesh         = SMESH::SMESH_Mesh::_nil();
244   myGeomObj      = GEOM::GEOM_Object::_nil();
245   myPattern      = SMESH::SMESH_Pattern::_nil();
246
247   erasePreview();
248
249   mySMESHGUI->SetActiveDialogBox((QDialog*)this);
250
251   // selection and SMESHGUI
252   connect(mySelectionMgr, SIGNAL(currentSelectionChanged()), SLOT(onSelectionDone()));
253   connect(mySMESHGUI, SIGNAL(SignalDeactivateActiveDialog()), SLOT(onDeactivate()));
254   connect(mySMESHGUI, SIGNAL(SignalCloseAllDialogs()), SLOT(onClose()));
255
256   mySwitch2d->setEnabled(theType == Type_2d);
257   mySwitch3d->setEnabled(theType == Type_3d);
258
259   if (theType == Type_2d)
260     myProjectChk->show();
261   else
262     myProjectChk->hide();
263
264   myTypeGrp->setButton(theType);
265   onTypeChanged(theType);
266
267   myName->setText(getDefaultName());
268   myMeshEdit->setText("");
269
270   setSizePolicy(QSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding));
271   qApp->processEvents();
272   updateGeometry();
273   myPicture2d->updateGeometry();
274   adjustSize();
275   resize(minimumSize());
276
277   activateSelection();
278   onSelectionDone();
279
280   this->show();
281 }
282
283 //=======================================================================
284 // function : SetMesh()
285 // purpose  : Set mesh to dialog
286 //=======================================================================
287 void SMESHGUI_CreatePatternDlg::SetMesh (SMESH::SMESH_Mesh_ptr thePtr)
288 {
289   myMesh = SMESH::SMESH_Mesh::_duplicate(thePtr);
290   mySubMesh = SMESH::SMESH_subMesh::_nil();
291
292   bool isValidMesh = false;
293   if (!myMesh->_is_nil())
294   {
295     _PTR(SObject) aSobj = SMESH::FindSObject(myMesh.in());
296     //Handle(SALOME_InteractiveObject) anIObj =
297     //  new SALOME_InteractiveObject(aSobj->GetID().c_str(), "SMESH");
298     SUIT_DataOwnerPtr anIObj (new LightApp_DataOwner(aSobj->GetID().c_str()));
299
300     isValidMesh = mySelectionMgr->isOk(anIObj);
301   }
302
303   if (isValidMesh) {
304     _PTR(SObject) aSO = SMESH::FindSObject(myMesh.in());
305     myMeshEdit->setText(aSO->GetName().c_str());
306     myGeomObj = SMESH::GetGeom(aSO);
307   } else {
308     myMeshEdit->setText("");
309     myGeomObj = GEOM::GEOM_Object::_nil();
310   }
311
312   if (myType == Type_2d) {
313     loadFromObject(false);
314     displayPreview();
315   }
316 }
317
318 //=======================================================================
319 // function : isValid()
320 // purpose  : Verify validity of entry data
321 //=======================================================================
322 bool SMESHGUI_CreatePatternDlg::isValid()
323 {
324   if (myGeomObj->_is_nil()) {
325     QMessageBox::information(SMESH::GetDesktop( mySMESHGUI ),
326                              tr("SMESH_INSUFFICIENT_DATA"),
327                              tr("SMESHGUI_INVALID_PARAMETERS"),
328                              QMessageBox::Ok);
329     return false;
330   }
331   else
332     return true;
333 }
334
335 //=======================================================================
336 // function : getDefaultName()
337 // purpose  : Get default pattern name
338 //=======================================================================
339 QString SMESHGUI_CreatePatternDlg::getDefaultName() const
340 {
341   return myType == Type_2d ? tr("DEFAULT_2D") : tr("DEFAULT_3D");
342 }
343
344 //=======================================================================
345 // function : onSave()
346 // purpose  : SLOT called when "Save" button pressed. Build pattern and
347 //           save it to disk
348 //=======================================================================
349 void SMESHGUI_CreatePatternDlg::onSave()
350 {
351   try {
352     if (!isValid())
353       return;
354
355     if (!myIsLoaded)
356       loadFromObject(true);
357
358     // Load pattern from object
359     if (!myIsLoaded)
360       return;
361
362     ///////////////////////////////////////////////////////
363     SUIT_FileDlg* aDlg = new SUIT_FileDlg (this, false);
364     aDlg->setCaption(tr("SAVE_PATTERN"));
365     aDlg->setMode(QFileDialog::AnyFile);
366     aDlg->setFilters(tr("PATTERN_FILT"));
367     if (myName->text() != "")
368       aDlg->setSelection(myName->text());
369
370     if (aDlg->exec() != Accepted)
371       return;
372
373     QString fName = aDlg->selectedFile();
374     if (fName.isEmpty())
375       return;
376
377     if (QFileInfo(fName).extension().isEmpty())
378       fName = autoExtension(fName);
379
380     fName = QDir::convertSeparators(fName);
381
382     QString aData (myPattern->GetString());
383     long aLen = aData.length();
384
385     QFile aFile (fName);
386     aFile.open(IO_WriteOnly);
387     long aWritten = aFile.writeBlock(aData, aLen);
388     aFile.close();
389
390     if (aWritten != aLen) {
391       QMessageBox::information(SMESH::GetDesktop( mySMESHGUI ), tr("SMESH_ERROR"),
392                                tr("ERROR_OF_SAVING"), QMessageBox::Ok);
393     } else {
394       //SUIT_Application::getDesktop()->setSelectionModes(ActorSelection);
395       if ( SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI ))
396         aViewWindow->SetSelectionMode(ActorSelection);
397       disconnect(mySelectionMgr, 0, this, 0);
398       disconnect(mySMESHGUI, 0, this, 0);
399       mySMESHGUI->ResetState();
400       accept();
401       emit NewPattern();
402     }
403   } catch (const SALOME::SALOME_Exception& S_ex) {
404     SalomeApp_Tools::QtCatchCorbaException(S_ex);
405   } catch (...) {
406   }
407 }
408
409 //=======================================================================
410 // function : GetPatternName()
411 // purpose  : Get name of pattern
412 //=======================================================================
413 QString SMESHGUI_CreatePatternDlg::GetPatternName() const
414 {
415   return myName->text();
416 }
417
418 //=======================================================================
419 // function : GetPattern()
420 // purpose  : Get result pattern
421 //=======================================================================
422 SMESH::SMESH_Pattern_ptr SMESHGUI_CreatePatternDlg::GetPattern()
423 {
424   return myPattern.in();
425 }
426
427 //=======================================================================
428 // function : onOk()
429 // purpose  : SLOT called when "Ok" button pressed.
430 //=======================================================================
431 void SMESHGUI_CreatePatternDlg::onOk()
432 {
433   try {
434     if (!isValid())
435       return;
436
437     if (!myIsLoaded)
438       loadFromObject(true);
439
440     // Load pattern from object
441     if (!myIsLoaded) {
442       return;
443     } else {
444       //SUIT_Application::getDesktop()->setSelectionModes(ActorSelection);
445       if ( SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI ))
446         aViewWindow->SetSelectionMode(ActorSelection);
447       disconnect(mySelectionMgr, 0, this, 0);
448       disconnect(mySMESHGUI, 0, this, 0);
449       mySMESHGUI->ResetState();
450       accept();
451       emit NewPattern();
452     }
453   } catch (const SALOME::SALOME_Exception& S_ex) {
454     SalomeApp_Tools::QtCatchCorbaException(S_ex);
455   } catch (...) {
456   }
457 }
458
459 //=======================================================================
460 // function : onClose()
461 // purpose  : SLOT called when "Close" button pressed. Close dialog
462 //=======================================================================
463 void SMESHGUI_CreatePatternDlg::onClose()
464 {
465   if ( SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI ))
466     aViewWindow->SetSelectionMode(ActorSelection);
467   disconnect(mySelectionMgr, 0, this, 0);
468   disconnect(mySMESHGUI, 0, this, 0);
469   mySMESHGUI->ResetState();
470   reject();
471   emit Close();
472 }
473
474 //=================================================================================
475 // function : onHelp()
476 // purpose  :
477 //=================================================================================
478 void SMESHGUI_CreatePatternDlg::onHelp()
479 {
480   LightApp_Application* app = (LightApp_Application*)(SUIT_Session::session()->activeApplication());
481   if (app) 
482     app->onHelpContextModule(mySMESHGUI ? app->moduleName(mySMESHGUI->moduleName()) : QString(""), myHelpFileName);
483   else {
484                 QString platform;
485 #ifdef WIN32
486                 platform = "winapplication";
487 #else
488                 platform = "application";
489 #endif
490     SUIT_MessageBox::warn1(0, QObject::tr("WRN_WARNING"),
491                            QObject::tr("EXTERNAL_BROWSER_CANNOT_SHOW_PAGE").
492                            arg(app->resourceMgr()->stringValue("ExternalBrowser", platform)).arg(myHelpFileName),
493                            QObject::tr("BUT_OK"));
494   }
495 }
496
497 //=======================================================================
498 // function : loadFromObject()
499 // purpose  : Load pattern from geom object corresponding to the mesh/submesh
500 //=======================================================================
501 bool SMESHGUI_CreatePatternDlg::loadFromObject (const bool theMess)
502 {
503   try {
504     myIsLoaded = false;
505
506     if (myPattern->_is_nil())
507       myPattern = SMESH::GetPattern();
508
509     if (myMesh->_is_nil() && mySubMesh->_is_nil() || myGeomObj->_is_nil())
510       return false;
511
512     SMESH::SMESH_Mesh_ptr aMesh = mySubMesh->_is_nil() ? myMesh.in() : mySubMesh->GetFather();
513
514     myIsLoaded = myType == Type_2d
515       ? myPattern->LoadFromFace(aMesh, myGeomObj, myProjectChk->isChecked())
516       : myPattern->LoadFrom3DBlock(aMesh, myGeomObj);
517
518     if (!myIsLoaded && theMess) {
519       QString aMess;
520       SMESH::SMESH_Pattern::ErrorCode aCode = myPattern->GetErrorCode();
521
522       if      (aCode == SMESH::SMESH_Pattern::ERR_LOAD_EMPTY_SUBMESH  ) aMess = tr("ERR_LOAD_EMPTY_SUBMESH");
523       else if (aCode == SMESH::SMESH_Pattern::ERR_LOADF_NARROW_FACE   ) aMess = tr("ERR_LOADF_NARROW_FACE");
524       else if (aCode == SMESH::SMESH_Pattern::ERR_LOADF_CLOSED_FACE   ) aMess = tr("ERR_LOADF_CLOSED_FACE");
525       else if (aCode == SMESH::SMESH_Pattern::ERR_LOADF_CANT_PROJECT   ) aMess = tr("ERR_LOADF_CANT_PROJECT");
526       else if (aCode == SMESH::SMESH_Pattern::ERR_LOADV_BAD_SHAPE     ) aMess = tr("ERR_LOADV_BAD_SHAPE");
527       else if (aCode == SMESH::SMESH_Pattern::ERR_LOADV_COMPUTE_PARAMS) aMess = tr("ERR_LOADV_COMPUTE_PARAMS");
528       else                                                              aMess = tr("ERROR_OF_CREATION");
529
530       QMessageBox::information(SMESH::GetDesktop( mySMESHGUI ),
531                                tr("SMESH_ERROR"), aMess, QMessageBox::Ok);
532     }
533   } catch (const SALOME::SALOME_Exception& S_ex) {
534     SalomeApp_Tools::QtCatchCorbaException(S_ex);
535   }
536
537   return myIsLoaded;
538 }
539
540 //=======================================================================
541 // function : onSelectionDone()
542 // purpose  : SLOT called when selection changed
543 //=======================================================================
544 void SMESHGUI_CreatePatternDlg::onSelectionDone()
545 {
546   try {
547     SALOME_ListIO aList;
548     mySelectionMgr->selectedObjects(aList, SVTK_Viewer::Type());
549     if (aList.Extent() != 1)
550       return;
551
552     // Get mesh or sub-mesh from selection
553     Handle(SALOME_InteractiveObject) anIO = aList.First();
554     SMESH::SMESH_Mesh_var aMesh = SMESH::IObjectToInterface<SMESH::SMESH_Mesh>(anIO);
555     SMESH::SMESH_subMesh_var aSubMesh = SMESH::IObjectToInterface<SMESH::SMESH_subMesh>(anIO);
556     if (aMesh->_is_nil() && aSubMesh->_is_nil())
557       return;
558
559     // Get geom object corresponding to the mesh
560     _PTR(SObject) aSO;
561     if (!aMesh->_is_nil())
562       aSO = SMESH::FindSObject(aMesh.in());
563     else
564       aSO = SMESH::FindSObject(aSubMesh.in());
565
566     GEOM::GEOM_Object_var aGeomObj = SMESH::GetGeom(aSO);
567     if (aGeomObj->_is_nil())
568       return;
569
570     myGeomObj = aGeomObj;
571
572     // init class fields
573     if (!aMesh->_is_nil()) {
574       myMesh = aMesh;
575       mySubMesh = SMESH::SMESH_subMesh::_nil();
576     } else {
577       mySubMesh = aSubMesh;
578       myMesh = SMESH::SMESH_Mesh::_nil();
579     }
580
581     QString aName;
582     SMESH::GetNameOfSelectedIObjects(mySelectionMgr, aName);
583     myMeshEdit->setText(aName);
584
585     if (myType == Type_2d) {
586       loadFromObject(true);
587       displayPreview();
588     }
589   } catch (...) {
590     myMesh = SMESH::SMESH_Mesh::_nil();
591     mySubMesh = SMESH::SMESH_subMesh::_nil();
592     myGeomObj = GEOM::GEOM_Object::_nil();
593     erasePreview();
594   }
595 }
596
597 //=======================================================================
598 // function : onDeactivate()
599 // purpose  : SLOT called when dialog must be deativated
600 //=======================================================================
601 void SMESHGUI_CreatePatternDlg::onDeactivate()
602 {
603   disconnect(mySelectionMgr, 0, this, 0);
604   setEnabled(false);
605 }
606
607 //=======================================================================
608 // function : enterEvent()
609 // purpose  : Event filter
610 //=======================================================================
611 void SMESHGUI_CreatePatternDlg::enterEvent (QEvent*)
612 {
613   // there is a stange problem that enterEvent() comes after onSave()
614   if ( isVisible () ) {
615     mySMESHGUI->EmitSignalDeactivateDialog();
616     setEnabled(true);
617     activateSelection();
618     connect(mySelectionMgr, SIGNAL(currentSelectionChanged()), SLOT(onSelectionDone()));
619   }
620 }
621
622 //=================================================================================
623 // function : closeEvent()
624 // purpose  : Close dialog box
625 //=================================================================================
626 void SMESHGUI_CreatePatternDlg::closeEvent (QCloseEvent*)
627 {
628   onClose();
629 }
630
631 //=======================================================================
632 // function : onSelBtnClicked()
633 // purpose  : SLOT. Called when -> button clicked.
634 //=======================================================================
635 void SMESHGUI_CreatePatternDlg::onSelBtnClicked()
636 {
637   onSelectionDone();
638 }
639
640 //================================================================
641 // function : autoExtension()
642 // purpose  : Append extension to the file name
643 //================================================================
644 QString SMESHGUI_CreatePatternDlg::autoExtension (const QString& theFileName) const
645 {
646   QString anExt = theFileName.section('.', -1);
647   return anExt != "smp" && anExt != "SMP" ? theFileName + ".smp" : theFileName;
648 }
649
650 //=======================================================================
651 // function : displayPreview()
652 // purpose  : Display preview
653 //=======================================================================
654 void SMESHGUI_CreatePatternDlg::displayPreview()
655 {
656   // Redisplay preview in dialog
657   try {
658     if (!myIsLoaded) {
659       erasePreview();
660     } else {
661       SMESH::point_array_var pnts = myPattern->GetPoints();
662       SMESH::long_array_var keyPoints = myPattern->GetKeyPoints();
663       SMESH::array_of_long_array_var elemPoints = myPattern->GetElementPoints(false);
664
665       if (pnts->length()       == 0 ||
666           keyPoints->length()  == 0 ||
667           elemPoints->length() == 0) {
668         myIsLoaded = false;
669         erasePreview();
670         return;
671       }
672
673       PointVector aPoints (pnts->length());
674       QValueVector<int> aKeyPoints (keyPoints->length());
675       ConnectivityVector anElemPoints (elemPoints->length());
676
677       for (int i = 0, n = pnts->length(); i < n; i++)
678         aPoints[ i ] = pnts[ i ];
679
680       for (int i2 = 0, n2 = keyPoints->length(); i2 < n2; i2++)
681         aKeyPoints[ i2 ] = keyPoints[ i2 ];
682
683       for (int i3 = 0, n3 = elemPoints->length(); i3 < n3; i3++) {
684         QValueVector<int> aVec (elemPoints[ i3 ].length());
685         for (int i4 = 0, n4 = elemPoints[ i3 ].length(); i4 < n4; i4++)
686           aVec[ i4 ] = elemPoints[ i3 ][ i4 ];
687
688         anElemPoints[ i3 ] = aVec;
689       }
690
691       myPicture2d->SetPoints(aPoints, aKeyPoints, anElemPoints);
692     }
693
694     return;
695
696   } catch (const SALOME::SALOME_Exception& S_ex) {
697     SalomeApp_Tools::QtCatchCorbaException(S_ex);
698   } catch (...) {
699   }
700   erasePreview();
701 }
702
703 //=======================================================================
704 // function : erasePreview()
705 // purpose  : Erase preview
706 //=======================================================================
707 void SMESHGUI_CreatePatternDlg::erasePreview()
708 {
709   // Erase preview in 2D viewer
710   myPicture2d->SetPoints(PointVector(), QValueVector<int>(), ConnectivityVector());
711 }
712
713 //=======================================================================
714 // function : activateSelection()
715 // purpose  : Activate selection in accordance with current pattern type
716 //=======================================================================
717 void SMESHGUI_CreatePatternDlg::activateSelection()
718 {
719   mySelectionMgr->clearFilters();
720   //SUIT_Application::getDesktop()->setSelectionModes(ActorSelection);
721   if ( SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI ))
722     aViewWindow->SetSelectionMode(ActorSelection);
723
724   if (myType == Type_2d) {
725     mySelectionMgr->installFilter(new SMESH_NumberFilter
726       ("SMESH", TopAbs_SHAPE, -1, TopAbs_FACE));
727   } else {
728     TColStd_MapOfInteger aTypes;
729     aTypes.Add(TopAbs_SHELL);
730     aTypes.Add(TopAbs_SOLID);
731     mySelectionMgr->installFilter(new SMESH_NumberFilter
732       ("SMESH", TopAbs_FACE, 6, aTypes, GEOM::GEOM_Object::_nil(), true));
733   }
734 }
735
736 //=======================================================================
737 // function : onTypeChanged()
738 // purpose  : SLOT. Called when pattern type changed.
739 //            Change dialog's look and feel
740 //=======================================================================
741 void SMESHGUI_CreatePatternDlg::onTypeChanged (int theType)
742 {
743   if (myType == theType)
744     return;
745
746   myType = theType;
747
748   if (theType == Type_2d)
749     myPicture2d->show();
750   else
751     myPicture2d->hide();
752 }
753
754 //=================================================================================
755 // function : keyPressEvent()
756 // purpose  :
757 //=================================================================================
758 void SMESHGUI_CreatePatternDlg::keyPressEvent( QKeyEvent* e )
759 {
760   QDialog::keyPressEvent( e );
761   if ( e->isAccepted() )
762     return;
763
764   if ( e->key() == Key_F1 )
765     {
766       e->accept();
767       onHelp();
768     }
769 }