Salome HOME
Copyright update 2021
[modules/smesh.git] / src / SMESHGUI / SMESHGUI_GroupDlg.cxx
1 // Copyright (C) 2007-2021  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License, or (at your option) any later version.
10 //
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 // Lesser General Public License for more details.
15 //
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22
23 //  SMESH SMESHGUI : GUI for SMESH component
24 //  File   : SMESHGUI_GroupDlg.cxx
25 //  Author : Natalia KOPNOVA, Open CASCADE S.A.S.
26 //  SMESH includes
27 //
28 #include "SMESHGUI_GroupDlg.h"
29
30 #include "SMESHGUI.h"
31 #include "SMESHGUI_Utils.h"
32 #include "SMESHGUI_VTKUtils.h"
33 #include "SMESHGUI_GroupUtils.h"
34 #include "SMESHGUI_FilterUtils.h"
35 #include "SMESHGUI_GEOMGenUtils.h"
36 #include "SMESHGUI_FilterDlg.h"
37 #include "SMESHGUI_ShapeByMeshDlg.h"
38
39 #include <SMESH_TypeFilter.hxx>
40 #include <SMESH_Actor.h>
41 //#include <SMESH_ActorUtils.h>
42 #include <SMESH_LogicalFilter.hxx>
43
44 // SALOME GEOM includes
45 #include <GEOMBase.h>
46 #include <GEOM_SelectionFilter.h>
47 #include <GEOM_wrap.hxx>
48
49 // SALOME GUI includes
50 #include <QtxColorButton.h>
51
52 #include <SUIT_Desktop.h>
53 #include <SUIT_ResourceMgr.h>
54 #include <SUIT_Session.h>
55 #include <SUIT_MessageBox.h>
56 #include <SUIT_OverrideCursor.h>
57
58 #include <SalomeApp_Tools.h>
59 #include <SalomeApp_Application.h>
60 #include <SalomeApp_Study.h>
61 #include <LightApp_SelectionMgr.h>
62
63 #include <SALOME_ListIO.hxx>
64
65 #include <SVTK_ViewWindow.h>
66
67 #include <VTKViewer_Algorithm.h>
68
69 // SALOME KERNEL includes
70 #include <SALOMEDSClient_Study.hxx>
71
72 // VTK Includes
73 #include <vtkRenderer.h>
74 #include <vtkActorCollection.h>
75
76 // OCCT includes
77 #include <TColStd_MapOfAsciiString.hxx>
78 #include <TColStd_MapOfInteger.hxx>
79
80 // Qt includes
81 #include <QButtonGroup>
82 #include <QGroupBox>
83 #include <QLabel>
84 #include <QLineEdit>
85 #include <QPushButton>
86 #include <QToolButton>
87 #include <QRadioButton>
88 #include <QCheckBox>
89 #include <QGridLayout>
90 #include <QHBoxLayout>
91 #include <QVBoxLayout>
92 #include <QListWidget>
93 #include <QStackedWidget>
94 #include <QKeyEvent>
95 #include <QMenu>
96
97 // STL includes
98 #include <vector>
99 #include <algorithm>
100 #include <set>
101
102 #define SPACING 6
103 #define MARGIN  11
104
105 enum grpSelectionMode {
106   grpNoSelection       = -1,
107   grpNodeSelection     = 0,
108   grp0DSelection       = 1,
109   grpBallSelection     = 2,
110   grpEdgeSelection     = 3,
111   grpFaceSelection     = 4,
112   grpVolumeSelection   = 5,
113   grpSubMeshSelection  = 6,
114   grpGroupSelection    = 7,
115   grpMeshSelection     = 8,
116   grpGeomSelection     = 9,
117   grpAllSelection      = 10,
118 };
119
120 //=================================================================================
121 // function : SMESHGUI_GroupDlg()
122 // purpose  :
123 //=================================================================================
124 SMESHGUI_GroupDlg::SMESHGUI_GroupDlg( SMESHGUI* theModule,
125                                       SMESH::SMESH_Mesh_ptr theMesh )
126   : QDialog( SMESH::GetDesktop( theModule ) ),
127     mySMESHGUI( theModule ),
128     mySelectionMgr( SMESH::GetSelectionMgr( theModule ) ), myStoredShownEntity(0),
129     mySelector( SMESH::GetViewWindow( theModule )->GetSelector() ),
130     myIsBusy( false ),
131     myNameChanged( false ),
132     myNbChangesOfContents(0),
133     myIsApplyAndClose( false )
134 {
135   initDialog( true );
136   if ( !theMesh->_is_nil() )
137     init( theMesh );
138   else
139   {
140     mySelectSubMesh->setEnabled( false );
141     mySelectGroup->setEnabled( false );
142     myGeomGroupBtn->setEnabled( false );
143     myGeomGroupLine->setEnabled( false );
144   }
145 }
146
147 //=================================================================================
148 // function : SMESHGUI_GroupDlg()
149 // purpose  :
150 //=================================================================================
151 SMESHGUI_GroupDlg::SMESHGUI_GroupDlg( SMESHGUI* theModule,
152                                       SMESH::SMESH_GroupBase_ptr theGroup,
153                                       const bool theIsConvert )
154   : QDialog( SMESH::GetDesktop( theModule ) ),
155     mySMESHGUI( theModule ),
156     mySelectionMgr( SMESH::GetSelectionMgr( theModule ) ), myStoredShownEntity(0),
157     mySelector( SMESH::GetViewWindow( theModule )->GetSelector() ),
158     myIsBusy( false ),
159     myNameChanged( false ),
160     myNbChangesOfContents(0) // just not to use uninitialized variable
161 {
162   initDialog( false );
163   if ( !theGroup->_is_nil() )
164     init( theGroup, theIsConvert );
165   else
166   {
167     mySelectSubMesh->setEnabled( false );
168     mySelectGroup->setEnabled( false );
169
170     myCurrentLineEdit = myMeshGroupLine;
171     setSelectionMode( grpGroupSelection );
172   }
173 }
174
175 //=================================================================================
176 // function : SMESHGUI_GroupDlg()
177 // purpose  :
178 //=================================================================================
179 void SMESHGUI_GroupDlg::initDialog( bool create)
180 {
181   setModal( false );
182   setAttribute( Qt::WA_DeleteOnClose, true );
183
184   myFilterDlg = 0;
185   myCreate = create;
186   myCurrentLineEdit = 0;
187
188   myShapeByMeshOp = 0;
189   myGeomPopup = 0;
190   myGeomObjects = new GEOM::ListOfGO();
191   myGeomObjects->length( 0 );
192
193   QPixmap image0( SMESH::GetResourceMgr( mySMESHGUI )->loadPixmap( "SMESH", tr( "ICON_SELECT" ) ) );
194
195   setWindowTitle( create ? tr( "SMESH_CREATE_GROUP_TITLE" ) : tr( "SMESH_EDIT_GROUP_TITLE" ) );
196   myHelpFileName = create ? "creating_groups.html" : "editing_groups.html";
197
198   setSizeGripEnabled( true);
199
200   QGridLayout* aMainLayout = new QGridLayout( this );
201   aMainLayout->setMargin( MARGIN );
202   aMainLayout->setSpacing( SPACING );
203
204   /***************************************************************/
205   QLabel* meshGroupLab = new QLabel( create ? tr( "SMESH_MESH" ) : tr( "SMESH_GROUP" ), this );
206   myMeshGroupBtn = new QPushButton( this );
207   myMeshGroupBtn->setIcon( image0 );
208   myMeshGroupLine = new QLineEdit( this );
209   myMeshGroupLine->setReadOnly( true );
210
211   /***************************************************************/
212   QGroupBox* aTypeBox = new QGroupBox( tr( "SMESH_ELEMENTS_TYPE" ), this );
213   myTypeGroup = new QButtonGroup( this );
214   QHBoxLayout* aTypeBoxLayout = new QHBoxLayout( aTypeBox );
215   aTypeBoxLayout->setMargin( MARGIN );
216   aTypeBoxLayout->setSpacing( SPACING );
217
218   QStringList types;
219   types.append( tr( "MESH_NODE" ) );
220   types.append( tr( "SMESH_ELEM0D" ) );
221   types.append( tr( "SMESH_BALL_ELEM" ) );
222   types.append( tr( "SMESH_EDGE" ) );
223   types.append( tr( "SMESH_FACE" ) );
224   types.append( tr( "SMESH_VOLUME" ) );
225   QRadioButton* rb;
226   for ( int i = 0; i < types.count(); i++ )
227   {
228     rb = new QRadioButton( types[i], aTypeBox );
229     myTypeGroup->addButton( rb, i );
230     aTypeBoxLayout->addWidget( rb );
231   }
232   aTypeBox->setEnabled( create );
233   myTypeId = -1;
234
235   /***************************************************************/
236   QLabel* aName = new QLabel( tr( "SMESH_NAME" ), this );
237   aName->setMinimumWidth( 50 );
238   myName = new QLineEdit( this );
239
240   /***************************************************************/
241   QGroupBox* aGrpTypeBox = new QGroupBox( tr( "SMESH_GROUP_TYPE" ), this );
242   myGrpTypeGroup = new QButtonGroup( this );
243   QHBoxLayout* aGrpTypeBoxLayout = new QHBoxLayout( aGrpTypeBox );
244   aGrpTypeBoxLayout->setMargin( MARGIN );
245   aGrpTypeBoxLayout->setSpacing( SPACING );
246
247   QRadioButton* rb1 = new QRadioButton( tr( "SMESH_GROUP_STANDALONE" ), aGrpTypeBox );
248   QRadioButton* rb2 = new QRadioButton( tr( "SMESH_GROUP_GEOMETRY" ),   aGrpTypeBox );
249   QRadioButton* rb3 = new QRadioButton( tr( "SMESH_GROUP_FILTER" ),     aGrpTypeBox );
250   myGrpTypeGroup->addButton( rb1, 0 );
251   myGrpTypeGroup->addButton( rb2, 1 );
252   myGrpTypeGroup->addButton( rb3, 2 );
253   aGrpTypeBoxLayout->addWidget( rb1 );
254   aGrpTypeBoxLayout->addWidget( rb2 );
255   aGrpTypeBoxLayout->addWidget( rb3 );
256   aGrpTypeBox->setEnabled( create );
257   myGrpTypeId = -1;
258
259   /***************************************************************/
260   myWGStack = new QStackedWidget( this );
261   QWidget* wg1 = new QWidget( myWGStack );
262   QWidget* wg2 = new QWidget( myWGStack );
263   QWidget* wg3 = new QWidget( myWGStack );
264
265   /***************************************************************/
266   QGroupBox* aContentBox         = new QGroupBox( tr( "SMESH_CONTENT" ), wg1 );
267   QGridLayout* aContentBoxLayout = new QGridLayout( aContentBox );
268   aContentBoxLayout->setMargin( MARGIN );
269   aContentBoxLayout->setSpacing( SPACING );
270
271   mySelectAll       = new QCheckBox( tr( "SELECT_ALL" ), aContentBox );
272   myAllowElemsModif = new QCheckBox( tr( "ALLOW_ELEM_LIST_MODIF" ), aContentBox );
273
274   myElementsLab = new QLabel( tr( "SMESH_ID_ELEMENTS" ), aContentBox );
275   myElements    = new QListWidget( aContentBox );
276   myElements->setSelectionMode( QListWidget::ExtendedSelection );
277
278   myFilterBtn = new QPushButton( tr( "SMESH_BUT_FILTER" ), aContentBox );
279   myAddBtn    = new QPushButton( tr( "SMESH_BUT_ADD" ), aContentBox );
280   myRemoveBtn = new QPushButton( tr( "SMESH_BUT_REMOVE" ), aContentBox );
281   mySortBtn   = new QPushButton( tr( "SMESH_BUT_SORT" ), aContentBox );
282
283   aContentBoxLayout->addWidget( mySelectAll,       0, 0 );
284   aContentBoxLayout->addWidget( myAllowElemsModif, 1, 0 );
285   aContentBoxLayout->addWidget( myFilterBtn,       1, 1 );
286   aContentBoxLayout->addWidget( myElementsLab,     2, 0 );
287   aContentBoxLayout->addWidget( myElements,        3, 0, 6, 1 );
288   aContentBoxLayout->addWidget( myAddBtn,          3, 1 );
289   aContentBoxLayout->addWidget( myRemoveBtn,       4, 1 );
290   aContentBoxLayout->addWidget( mySortBtn,         8, 1 );
291
292   aContentBoxLayout->setColumnStretch( 0, 1 );
293   aContentBoxLayout->setRowStretch( 3, 1 );
294   aContentBoxLayout->setRowStretch( 6, 1 );
295
296   /***************************************************************/
297   mySelectBox = new QGroupBox( tr( "SMESH_SELECT_FROM" ), wg1 );
298   QGridLayout* mySelectBoxLayout = new QGridLayout( mySelectBox );
299   mySelectBoxLayout->setMargin( MARGIN );
300   mySelectBoxLayout->setSpacing( SPACING );
301
302   mySelectSubMesh = new QCheckBox( tr( "SMESH_SUBMESH" ), mySelectBox );
303   mySubMeshBtn = new QPushButton( mySelectBox );
304   mySubMeshBtn->setIcon( image0 );
305   mySubMeshLine = new QLineEdit( mySelectBox );
306   mySubMeshLine->setReadOnly( true );
307   onSelectSubMesh( false );
308
309   mySelectGroup = new QCheckBox( tr( "SMESH_GROUP" ), mySelectBox );
310   myGroupBtn = new QPushButton( mySelectBox );
311   myGroupBtn->setIcon( image0 );
312   myGroupLine = new QLineEdit( mySelectBox );
313   myGroupLine->setReadOnly( true );
314   onSelectGroup( false );
315
316   mySelectBoxLayout->addWidget( mySelectSubMesh, 0, 0 );
317   mySelectBoxLayout->addWidget( mySubMeshBtn,    0, 1 );
318   mySelectBoxLayout->addWidget( mySubMeshLine,   0, 2 );
319   mySelectBoxLayout->addWidget( mySelectGroup,   1, 0 );
320   mySelectBoxLayout->addWidget( myGroupBtn,      1, 1 );
321   mySelectBoxLayout->addWidget( myGroupLine,     1, 2 );
322
323   /***************************************************************/
324   QVBoxLayout* wg1Layout = new QVBoxLayout( wg1 );
325   wg1Layout->setMargin( 0 );
326   wg1Layout->setSpacing( SPACING );
327   wg1Layout->addWidget( aContentBox );
328   wg1Layout->addWidget( mySelectBox );
329   wg1Layout->setStretchFactor( aContentBox, 10 );
330
331   /***************************************************************/
332   QLabel* geomObject = new QLabel( tr( "SMESH_OBJECT_GEOM" ), wg2 );
333   myGeomGroupBtn = new QToolButton( wg2 );
334   myGeomGroupBtn->setIcon( image0 );
335   myGeomGroupBtn->setCheckable( true );
336   myGeomGroupLine = new QLineEdit( wg2 );
337   myGeomGroupLine->setReadOnly( true ); //VSR ???
338   onSelectGeomGroup( false );
339
340   myGeomGroupBtn->setEnabled( create );
341   myGeomGroupLine->setEnabled( create );
342
343   /***************************************************************/
344   QGridLayout* wg2Layout = new QGridLayout( wg2 );
345   wg2Layout->setMargin( 0 );
346   wg2Layout->setSpacing( SPACING );
347   wg2Layout->addWidget( geomObject,     0, 0 );
348   wg2Layout->addWidget( myGeomGroupBtn, 0, 1 );
349   wg2Layout->addWidget( myGeomGroupLine,0, 2 );
350   wg2Layout->setRowStretch( 1, 5 );
351
352   /***************************************************************/
353   QPushButton * aFilter2 = new QPushButton( tr( "SMESH_BUT_FILTER" ), wg3 );
354   QGridLayout* wg3Layout = new QGridLayout( wg3 );
355   wg3Layout->setMargin( 0 );
356   wg3Layout->setSpacing( SPACING );
357   wg3Layout->addWidget( aFilter2, 0, 0 );
358   wg3Layout->setRowStretch( 1, 5 );
359
360   /***************************************************************/
361   myWGStack->insertWidget( 0, wg1 );
362   myWGStack->insertWidget( 1, wg2 );
363   myWGStack->insertWidget( 2, wg3 );
364
365   /***************************************************************/
366   QGroupBox* aColorBox = new QGroupBox(tr( "SMESH_SET_COLOR" ), this);
367   QHBoxLayout* aColorBoxLayout = new QHBoxLayout(aColorBox);
368   aColorBoxLayout->setMargin(MARGIN);
369   aColorBoxLayout->setSpacing(SPACING);
370
371   QLabel* aColorLab = new QLabel(tr( "SMESH_CHECK_COLOR" ), aColorBox );
372   myColorBtn = new QtxColorButton(aColorBox);
373   myColorBtn->setSizePolicy( QSizePolicy::MinimumExpanding, 
374                              myColorBtn->sizePolicy().verticalPolicy() );
375
376   aColorBoxLayout->addWidget(aColorLab);
377   aColorBoxLayout->addWidget(myColorBtn);
378
379   /***************************************************************/
380
381   QFrame* aButtons = new QFrame(this);
382   aButtons->setFrameStyle( QFrame::Box | QFrame::Sunken );
383   QHBoxLayout* aBtnLayout = new QHBoxLayout(aButtons);
384   aBtnLayout->setMargin(MARGIN);
385   aBtnLayout->setSpacing(SPACING);
386
387   myOKBtn = new QPushButton(tr( "SMESH_BUT_APPLY_AND_CLOSE" ), aButtons);
388   myOKBtn->setAutoDefault(true);
389   myOKBtn->setDefault(true);
390   myApplyBtn = new QPushButton(tr( "SMESH_BUT_APPLY" ), aButtons);
391   myApplyBtn->setAutoDefault(true);
392   myCloseBtn = new QPushButton(tr( "SMESH_BUT_CLOSE" ), aButtons);
393   myCloseBtn->setAutoDefault(true);
394   myHelpBtn = new QPushButton(tr( "SMESH_BUT_HELP" ), aButtons);
395   myHelpBtn->setAutoDefault(true);
396
397   aBtnLayout->addWidget(myOKBtn);
398   aBtnLayout->addSpacing(10);
399   aBtnLayout->addWidget(myApplyBtn);
400   aBtnLayout->addSpacing(10);
401   aBtnLayout->addStretch();
402   aBtnLayout->addWidget(myCloseBtn);
403   aBtnLayout->addWidget(myHelpBtn);
404
405   /***************************************************************/
406   aMainLayout->addWidget(meshGroupLab,    0, 0);
407   aMainLayout->addWidget(myMeshGroupBtn,  0, 1);
408   aMainLayout->addWidget(myMeshGroupLine, 0, 2);
409   aMainLayout->addWidget(aTypeBox,        1, 0, 1, 3);
410   aMainLayout->addWidget(aName,           2, 0);
411   aMainLayout->addWidget(myName,          2, 2);
412   aMainLayout->addWidget(aGrpTypeBox,     3, 0, 1, 3);
413   aMainLayout->addWidget(myWGStack,       4, 0, 1, 3);
414   aMainLayout->addWidget(aColorBox,       5, 0, 1, 3);
415   aMainLayout->addWidget(aButtons,        6, 0, 1, 3);
416
417   /* signals and slots connections */
418   connect(myMeshGroupBtn,  SIGNAL(clicked()),          this, SLOT(setCurrentSelection()));
419   connect(myGrpTypeGroup,  SIGNAL(buttonClicked(int)), this, SLOT(onGrpTypeChanged(int)));
420   connect(myTypeGroup,     SIGNAL(buttonClicked(int)), this, SLOT(onTypeChanged(int)));
421
422   connect(myName,          SIGNAL(textChanged(const QString&)), this, SLOT(onNameChanged(const QString&)));
423   connect(myElements,      SIGNAL(itemSelectionChanged()),      this, SLOT(onListSelectionChanged()));
424
425   connect(myFilterBtn,     SIGNAL(clicked()),     this, SLOT(setFilters()));
426   connect(aFilter2,        SIGNAL(clicked()),     this, SLOT(setFilters()));
427   connect(mySelectAll,     SIGNAL(toggled(bool)), this, SLOT(onSelectAll()));
428   connect(myAllowElemsModif,SIGNAL(toggled(bool)), this, SLOT(onSelectAll()));
429   connect(myAddBtn,        SIGNAL(clicked()),     this, SLOT(onAdd()));
430   connect(myRemoveBtn,     SIGNAL(clicked()),     this, SLOT(onRemove()));
431   connect(mySortBtn,       SIGNAL(clicked()),     this, SLOT(onSort()));
432
433   connect(mySelectSubMesh, SIGNAL(toggled(bool)), this, SLOT(onSelectSubMesh(bool)));
434   connect(mySelectGroup,   SIGNAL(toggled(bool)), this, SLOT(onSelectGroup(bool)));
435   connect(mySubMeshBtn,    SIGNAL(clicked()),     this, SLOT(setCurrentSelection()));
436   connect(myGroupBtn,      SIGNAL(clicked()),     this, SLOT(setCurrentSelection()));
437   connect(myGeomGroupBtn,  SIGNAL(toggled(bool)), this, SLOT(onGeomSelectionButton(bool)));
438
439   connect(myColorBtn,      SIGNAL(changed( QColor )),  this, SLOT(onColorChanged( QColor )));
440
441   connect(myOKBtn,         SIGNAL(clicked()), this, SLOT(onOK()));
442   connect(myApplyBtn,      SIGNAL(clicked()), this, SLOT(onApply()));
443   connect(myCloseBtn,      SIGNAL(clicked()), this, SLOT(reject()));
444   connect(myHelpBtn,       SIGNAL(clicked()), this, SLOT(onHelp()));
445
446   /* Init selection */
447   mySMESHGUI->SetActiveDialogBox(this);
448
449   SalomeApp_Study* aStudy = dynamic_cast<SalomeApp_Study*>( mySMESHGUI->application()->activeStudy() );
450   mySelectionMode = grpNoSelection;
451
452   myMeshFilter    = new SMESH_TypeFilter(SMESH::MESH);
453   mySubMeshFilter = new SMESH_LogicalFilter(QList<SUIT_SelectionFilter*>(),
454                                             SMESH_LogicalFilter::LO_OR,
455                                             /*takeOwnership=*/true);
456   myGroupFilter   = new SMESH_LogicalFilter(QList<SUIT_SelectionFilter*>(),
457                                             SMESH_LogicalFilter::LO_OR,
458                                             /*takeOwnership=*/true);
459   myGeomFilter    = new GEOM_SelectionFilter( aStudy, true );
460
461   connect(mySMESHGUI, SIGNAL(SignalDeactivateActiveDialog()), this, SLOT(onDeactivate()));
462   connect(mySMESHGUI, SIGNAL(SignalCloseAllDialogs()),        this, SLOT(reject()));
463   connect(mySelectionMgr, SIGNAL(currentSelectionChanged()),  this, SLOT(onObjectSelectionChanged()));
464   connect(mySMESHGUI, SIGNAL(SignalVisibilityChanged()),      this, SLOT(onVisibilityChanged()));
465   connect(mySMESHGUI, SIGNAL(SignalActivatedViewManager()),   this, SLOT(onOpenView()));
466   connect(mySMESHGUI, SIGNAL(SignalCloseView()),              this, SLOT(onCloseView()));
467   rb1->setChecked(true); // VSR !!!
468   onGrpTypeChanged(0); // VSR!!!
469
470   if (myMesh->_is_nil() )
471     myTypeGroup->button(0)->setChecked(true);
472
473   onSelectAll(); //updateButtons();
474 }
475
476 //=================================================================================
477 // function : ~SMESHGUI_GroupDlg()
478 // purpose  : Destroys the object and frees any allocated resources
479 //=================================================================================
480 SMESHGUI_GroupDlg::~SMESHGUI_GroupDlg()
481 {
482   // no need to delete child widgets, Qt does it all for us
483   if ( myFilterDlg != 0 ) {
484     myFilterDlg->setParent( 0 );
485     delete myFilterDlg;
486   }
487   if ( myMeshFilter )    delete myMeshFilter;
488   if ( mySubMeshFilter ) delete mySubMeshFilter;
489   if ( myGroupFilter )   delete myGroupFilter;
490   if ( myGeomFilter )    delete myGeomFilter;
491 }
492
493 //=================================================================================
494 // function : GetDefaultName()
495 // purpose  : Get the Group Name if Create new Group
496 //=================================================================================
497 QString SMESHGUI_GroupDlg::GetDefaultName(const QString& theOperation)
498 {
499   QString aName = "";
500
501   // collect all object names of SMESH component
502   _PTR(Study) aStudy = SMESH::getStudy();
503
504   std::set<std::string> aSet;
505   _PTR(SComponent) aMeshCompo (aStudy->FindComponent( "SMESH" ));
506   if (aMeshCompo) {
507     _PTR(ChildIterator) it (aStudy->NewChildIterator(aMeshCompo));
508     _PTR(SObject) obj;
509     for (it->InitEx(true); it->More(); it->Next()) {
510       obj = it->Value();
511       aSet.insert(obj->GetName());
512     }
513   }
514
515   // build a unique name
516   int aNumber = 0;
517   bool isUnique = false;
518   while (!isUnique) {
519     aName = theOperation + "_" + QString::number(++aNumber);
520     isUnique = (aSet.count(std::string(aName.toUtf8().constData())) == 0);
521   }
522
523   return aName;
524 }
525
526 //=======================================================================
527 //function : setDefaultName
528 //purpose  : 
529 //=======================================================================
530
531 void  SMESHGUI_GroupDlg::setDefaultName() const
532 {
533   QString aResName;
534   const QString aPrefix ="Group_";
535
536   if ( myMesh->_is_nil() )
537   {
538     aResName = aPrefix + "1";
539   }
540   else
541   {
542     SMESH::ListOfGroups_var allGroups = myMesh->GetGroups();
543     TColStd_MapOfAsciiString allNames( allGroups->length() );
544     for ( CORBA::ULong i = 0; i < allGroups->length(); ++i )
545     {
546       CORBA::String_var name = allGroups[i]->GetName();
547       allNames.Add( name.in() );
548     }
549     int i = 1;
550     while ( true )
551     {
552       aResName = aPrefix + QString::number( i++ );
553       if ( !allNames.Contains( aResName.toUtf8().constData() ))
554         break;
555     }
556   }
557   myName->setText(aResName);
558 }
559
560 //=================================================================================
561 // function : Init()
562 // purpose  :
563 //=================================================================================
564 void SMESHGUI_GroupDlg::init (SMESH::SMESH_Mesh_ptr theMesh)
565 {
566   mySelectionMgr->installFilter(myMeshFilter);
567
568   /* init data from current selection */
569   restoreShowEntityMode();
570   myMesh = SMESH::SMESH_Mesh::_duplicate(theMesh);
571   setShowEntityMode();
572   myGroup = SMESH::SMESH_Group::_nil();
573   myGroupOnGeom = SMESH::SMESH_GroupOnGeom::_nil();
574   myGroupOnFilter = SMESH::SMESH_GroupOnFilter::_nil();
575
576   // NPAL19389: create a group with a selection in another group
577   // set actor of myMesh, if it is visible, else try
578   // any visible actor of group or submesh of myMesh
579   SetAppropriateActor();
580
581   setDefaultGroupColor();
582   setDefaultName();
583
584
585   SALOME_ListIO aList;
586   mySelectionMgr->selectedObjects( aList );
587   if( !aList.IsEmpty() )
588   {
589     QString aName = aList.First()->getName();
590     myMeshGroupLine->setText(aName);//??????
591     myMeshGroupLine->home( false );
592   }
593
594   myCurrentLineEdit = 0;
595
596   myTypeGroup->button(0)->setChecked(true);
597   onTypeChanged(0);
598 }
599
600 //=================================================================================
601 // function : Init()
602 // purpose  :
603 //=================================================================================
604 void SMESHGUI_GroupDlg::init (SMESH::SMESH_GroupBase_ptr theGroup,
605                               const bool                 theIsConvert)
606 {
607   restoreShowEntityMode();
608   myMesh = theGroup->GetMesh();
609   setShowEntityMode();
610
611   myNameChanged = true;
612   myName->blockSignals(true);
613   myName->setText(SMESH::fromUtf8(theGroup->GetName()));
614   myName->blockSignals(false);
615   myName->home(false);
616
617   SALOMEDS::Color aColor = theGroup->GetColor();
618   setGroupColor( aColor );
619
620   myMeshGroupLine->setText(theGroup->GetName());
621
622   int aType = 0;
623   switch(theGroup->GetType()) {
624   case SMESH::NODE:   aType = grpNodeSelection;   break;
625   case SMESH::ELEM0D: aType = grp0DSelection;     break;
626   case SMESH::BALL:   aType = grpBallSelection;   break;
627   case SMESH::EDGE:   aType = grpEdgeSelection;   break;
628   case SMESH::FACE:   aType = grpFaceSelection;   break;
629   case SMESH::VOLUME: aType = grpVolumeSelection; break;
630   case SMESH::ALL:
631   case SMESH::NB_ELEMENT_TYPES: break;
632   }
633   myTypeGroup->button(aType)->setChecked(true);
634
635   myGroup         = SMESH::SMESH_Group::_narrow( theGroup );
636   myGroupOnGeom   = SMESH::SMESH_GroupOnGeom::_narrow( theGroup );
637   myGroupOnFilter = SMESH::SMESH_GroupOnFilter::_narrow( theGroup );
638   myFilter        = SMESH::Filter::_nil();
639
640   if (myGroup->_is_nil() && myGroupOnGeom->_is_nil() && myGroupOnFilter->_is_nil() )
641     return;
642
643   // NPAL19389: create a group with a selection in another group
644   // set actor of myMesh, if it is visible, else set
645   // actor of theGroup, if it is visible, else try
646   // any visible actor of group or submesh of myMesh
647   // commented, because an attempt to set selection on not displayed cells leads to error
648   SetAppropriateActor();
649
650   /*  SMESH_Actor* anActor = SMESH::FindActorByObject(myMesh);
651   if ( !anActor )
652     anActor = SMESH::FindActorByObject(theGroup);
653   SMESH::SetPickable(anActor);*/
654
655   int grpType = (!myGroup->_is_nil() ? 0 : (theIsConvert ? 0 : myGroupOnGeom->_is_nil() ? 2 : 1));
656   myGrpTypeGroup->button(grpType)->setChecked(true);
657   onGrpTypeChanged(grpType);
658
659   myTypeId = aType;
660   if ( grpType == 0 ) { // standalone group
661     myCurrentLineEdit = 0;
662     myElements->clear();
663     myAllowElemsModif->setChecked( true );
664
665     setSelectionMode(aType);
666
667     setShowEntityMode(); // depends on myTypeId
668
669     myIdList.clear();
670     if (!theGroup->IsEmpty()) {
671       SMESH::long_array_var anElements = theGroup->GetListOfID();
672       int k = anElements->length();
673       for (int i = 0; i < k; i++) {
674         myIdList.append(anElements[i]);
675         myElements->addItem(QString::number(anElements[i]));
676       }
677       myElements->selectAll();
678     }
679   }
680   else if ( grpType == 1 ) // group on geom
681   {
682     QString aShapeName( "" );
683     _PTR(Study) aStudy = SMESH::getStudy();
684     GEOM::GEOM_Object_var aGroupShape = myGroupOnGeom->GetShape();
685     if (!aGroupShape->_is_nil())
686     {
687       _PTR(SObject) aGroupShapeSO = aStudy->FindObjectID(aGroupShape->GetStudyEntry());
688       if ( aGroupShapeSO )
689         aShapeName = aGroupShapeSO->GetName().c_str();
690     }
691     myGeomGroupLine->setText( aShapeName );
692   }
693   else // group on filter
694   {
695     myFilter = myGroupOnFilter->GetFilter();
696     if ( !myFilter->_is_nil() ) {
697       SMESH::Predicate_var perdicate = myFilter->GetPredicate();
698       if ( perdicate->_is_nil() )
699         myFilter = SMESH::Filter::_nil();
700     }
701   }
702
703   if ( grpType != 0 )
704   {
705     myNameChanged = true;
706     myName->blockSignals(true);
707     myName->setText(theGroup->GetName());
708     myName->blockSignals(false);
709   }
710
711   onSelectAll(); //updateButtons();
712 }
713
714 //=================================================================================
715 // function : updateButtons()
716 // purpose  :
717 //=================================================================================
718 void SMESHGUI_GroupDlg::updateButtons()
719 {
720   bool enable = !myName->text().trimmed().isEmpty();
721   if ( enable )
722   {
723     if (myGrpTypeId == 0) { // standalone
724       if ( !mySelectAll->isChecked() )
725       {
726         if ( myAllowElemsModif->isChecked() )
727         {
728           enable = ( myElements->count() > 0 );
729         }
730         else if ((enable = !myFilter->_is_nil() ))
731         {
732           SMESH::array_of_ElementType_var types = myFilter->GetTypes();
733           enable = types->length();
734         }
735       }
736       enable = enable && (!myGroup->_is_nil() || !myMesh->_is_nil());
737     }
738     else if (myGrpTypeId == 1) // on geom
739     {
740       if (CORBA::is_nil(myGroupOnGeom)) // creation mode
741         enable = ( myGeomObjects->length() > 0 && !myMesh->_is_nil() );
742     }
743     else if (myGrpTypeId == 2) // on filter
744     {
745       if (( enable = !myFilter->_is_nil() ))
746         if (CORBA::is_nil(myGroupOnFilter) )  // creation mode
747           enable = !myMesh->_is_nil();
748     }
749   }
750
751   bool meshHasGeom = ( myMesh->_is_nil() || myMesh->HasShapeToMesh() );
752   if ( myGrpTypeId != 1 )
753   {
754     myGrpTypeGroup->button(1)->setEnabled( meshHasGeom );
755   }
756   else
757   {
758     myGeomGroupBtn->setEnabled( meshHasGeom );
759     myGeomGroupLine->setEnabled( meshHasGeom );
760   }
761
762   myOKBtn->setEnabled(enable);
763   myApplyBtn->setEnabled(enable);
764 }
765
766 //=================================================================================
767 // function : onNameChanged()
768 // purpose  :
769 //=================================================================================
770 void SMESHGUI_GroupDlg::onNameChanged (const QString& /*text*/)
771 {
772   myOldName = myName->text();
773   updateButtons();
774   myNameChanged = !myName->text().trimmed().isEmpty();
775 }
776
777 //=================================================================================
778 // function : onTypeChanged()
779 // purpose  : Group elements type radio button management
780 //=================================================================================
781 void SMESHGUI_GroupDlg::onTypeChanged (int id)
782 {
783   if (myTypeId != id) {
784     myElements->clear();
785     myTypeId = id;
786     if ( myGrpTypeId == 0 && myCurrentLineEdit == 0)
787       setSelectionMode(id);
788     else
789       setSelectionMode( mySelectionMode++ ); // update according to mySelectionMode
790
791     onObjectSelectionChanged();
792     setShowEntityMode();
793   }
794 }
795
796 //=================================================================================
797 // function : onGrpTypeChanged()
798 // purpose  : Group type radio button management
799 //=================================================================================
800 void SMESHGUI_GroupDlg::onGrpTypeChanged (int id)
801 {
802   if (myGrpTypeId != id) {
803     myGrpTypeId = id;
804     myWGStack->setCurrentIndex( id );
805     myName->blockSignals(true);
806     myName->setText(myOldName);
807     myName->blockSignals(false);
808     onSelectGeomGroup(id != 0);
809   }
810   updateButtons();
811 }
812
813 //=================================================================================
814 // function : onColorChanged()
815 // purpose  : Color button management
816 //=================================================================================
817 void SMESHGUI_GroupDlg::onColorChanged(QColor /*theColor*/)
818 {
819   updateButtons();
820 }
821
822 //=================================================================================
823 // function : setSelectionMode()
824 // purpose  : Radio button management
825 //=================================================================================
826 void SMESHGUI_GroupDlg::setSelectionMode (int theMode)
827 {
828   // PAL7314
829   if (myMesh->_is_nil())
830     return;
831   SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI );
832   bool isSelectAll = mySelectAll->isChecked() || !myAllowElemsModif->isChecked() || myGrpTypeId != 0;
833   if (mySelectionMode != theMode) {
834     // [PAL10408] mySelectionMgr->clearSelected();
835     mySelectionMgr->clearFilters();
836     SMESH::RemoveFilters();
837
838     if (myActorsList.count() > 0)
839       for (QListIterator<SMESH_Actor*> it( myActorsList ); it.hasNext(); )
840         it.next()->SetPointRepresentation(false);
841     else
842       SMESH::SetPointRepresentation(false);
843
844     switch (theMode) {
845     case grpNodeSelection:
846       if ( myGrpTypeId == 0 ) // standalone
847       {
848         if (myActorsList.count() > 0)
849           for (QListIterator<SMESH_Actor*> it( myActorsList ); it.hasNext(); )
850             it.next()->SetPointRepresentation(true);
851         else
852           SMESH::SetPointRepresentation(true);
853       }
854       if ( aViewWindow ) aViewWindow->SetSelectionMode(isSelectAll ? ActorSelection : NodeSelection);
855       break;
856     case grpEdgeSelection:
857       if ( aViewWindow ) aViewWindow->SetSelectionMode(isSelectAll ? ActorSelection : EdgeSelection);
858       break;
859     case grpBallSelection:
860       if ( aViewWindow ) aViewWindow->SetSelectionMode(isSelectAll ? ActorSelection : BallSelection);
861       break;
862     case grp0DSelection:
863       if ( aViewWindow ) aViewWindow->SetSelectionMode(isSelectAll ? ActorSelection : Elem0DSelection);
864       break;
865     case grpFaceSelection:
866       if ( aViewWindow ) aViewWindow->SetSelectionMode(isSelectAll ? ActorSelection : FaceSelection);
867       break;
868     case grpVolumeSelection:
869       if ( aViewWindow ) aViewWindow->SetSelectionMode(isSelectAll ? ActorSelection : VolumeSelection);
870       break;
871     case grpSubMeshSelection: {
872
873       SMESH_TypeFilter* f = 0;
874       switch (myTypeId) {
875       case grpNodeSelection:   f = new SMESH_TypeFilter(SMESH::SUBMESH); break;
876       case grpEdgeSelection:   f = new SMESH_TypeFilter(SMESH::SUBMESH_EDGE); break;
877       case grpFaceSelection:   f = new SMESH_TypeFilter(SMESH::SUBMESH_FACE); break;
878       case grpVolumeSelection: f = new SMESH_TypeFilter(SMESH::SUBMESH_SOLID); break;
879       default:                 f = new SMESH_TypeFilter(SMESH::SUBMESH);
880       }
881       QList<SUIT_SelectionFilter*> filtList;
882       filtList.append( f );
883       filtList.append( new SMESH_TypeFilter(SMESH::SUBMESH_COMPOUND));
884       mySubMeshFilter->setFilters( filtList );
885
886       mySelectionMgr->installFilter( mySubMeshFilter );
887
888       if ( aViewWindow ) aViewWindow->SetSelectionMode(ActorSelection);
889       break;
890     }
891     case grpGroupSelection: {
892
893       SMESH_TypeFilter* f = 0;
894       switch (myTypeId) {
895       case grpNodeSelection:   f = new SMESH_TypeFilter(SMESH::GROUP_NODE);   break;
896       case grp0DSelection:     f = new SMESH_TypeFilter(SMESH::GROUP_0D);     break;
897       case grpBallSelection:   f = new SMESH_TypeFilter(SMESH::GROUP_BALL);   break;
898       case grpEdgeSelection:   f = new SMESH_TypeFilter(SMESH::GROUP_EDGE);   break;
899       case grpFaceSelection:   f = new SMESH_TypeFilter(SMESH::GROUP_FACE);   break;
900       case grpVolumeSelection: f = new SMESH_TypeFilter(SMESH::GROUP_VOLUME); break;
901       default:                 f = new SMESH_TypeFilter(SMESH::GROUP);
902       }
903       QList<SUIT_SelectionFilter*> filtList;
904       filtList.append( f );
905       myGroupFilter->setFilters( filtList );
906
907       mySelectionMgr->installFilter(myGroupFilter);
908       if ( aViewWindow ) aViewWindow->SetSelectionMode(ActorSelection);
909       break;
910     }
911     case grpMeshSelection:
912       mySelectionMgr->installFilter(myMeshFilter);
913       if ( aViewWindow ) aViewWindow->SetSelectionMode(ActorSelection);
914       break;
915     case grpGeomSelection:
916       mySelectionMgr->installFilter(myGeomFilter);
917       if ( aViewWindow ) aViewWindow->SetSelectionMode(ActorSelection);
918       break;
919     default:
920       if ( aViewWindow ) aViewWindow->SetSelectionMode(ActorSelection);
921       break;
922     }
923     if ( aViewWindow ) aViewWindow->Repaint();
924     mySelectionMode = theMode;
925   }
926 }
927
928 //=================================================================================
929 // function : onApply()
930 // purpose  :
931 //=================================================================================
932 bool SMESHGUI_GroupDlg::onApply()
933 {
934   if (SMESHGUI::isStudyLocked())
935     return false;
936
937   if (myName->text().trimmed().isEmpty())
938     return false;
939
940   SMESH::ElementType aType = SMESH::ALL;
941   switch (myTypeId) {
942   case grpNodeSelection:   aType = SMESH::NODE;   break;
943   case grp0DSelection:     aType = SMESH::ELEM0D; break;
944   case grpBallSelection:   aType = SMESH::BALL;   break;
945   case grpEdgeSelection:   aType = SMESH::EDGE;   break;
946   case grpFaceSelection:   aType = SMESH::FACE;   break;
947   case grpVolumeSelection: aType = SMESH::VOLUME; break;
948   }
949
950   bool anIsOk = false;
951   QStringList anEntryList;
952
953   SMESH::SMESH_GroupBase_var resultGroup;
954   bool isCreation = false, isConversion = false;
955     
956   SUIT_OverrideCursor wc;
957
958   if (myGrpTypeId == 0)  // standalone
959   {
960     if (!mySelectAll->isChecked() && !myElements->count() && myAllowElemsModif->isChecked())
961       return false;
962
963     mySelectionMgr->clearSelected();
964
965     if (myGroup->_is_nil()) { // creation or conversion
966       // check if group on geometry is not null
967       if (!myGroupOnGeom->_is_nil() || !myGroupOnFilter->_is_nil())
968       {
969         if (myMesh->_is_nil())
970           return false;
971         if ( myGroupOnGeom->_is_nil() )
972           myGroup = myMesh->ConvertToStandalone( myGroupOnFilter );
973         else
974           myGroup = myMesh->ConvertToStandalone( myGroupOnGeom );
975
976         myGroupOnGeom   = SMESH::SMESH_GroupOnGeom::_nil();
977         myGroupOnFilter = SMESH::SMESH_GroupOnFilter::_nil();
978         isConversion    = true;
979       }
980     }
981
982     if (myGroup->_is_nil()) // creation
983     {
984       if (myMesh->_is_nil())
985         return false;
986
987       myGroup = SMESH::AddGroup(myMesh, aType, myName->text());
988
989       resultGroup = SMESH::SMESH_GroupBase::_narrow( myGroup );
990       isCreation = true;
991
992       if ( mySelectAll->isChecked() ) {
993         // select all
994         myGroup->AddFrom(myMesh.in());
995       }
996       else {
997         // select manually
998
999         if ( !myFilter->_is_nil() &&
1000              ( myNbChangesOfContents == 1 || !myAllowElemsModif->isChecked()))
1001         {
1002           myGroup->AddFrom( myFilter );
1003         }
1004         else
1005         {
1006           SMESH::long_array_var anIdList = new SMESH::long_array;
1007           int i, k = myElements->count();
1008           anIdList->length(k);
1009           for (i = 0; i < k; i++) {
1010             anIdList[i] = myElements->item(i)->text().toInt();
1011           }
1012           myGroup->Add(anIdList.inout());
1013         }
1014       }
1015     }
1016
1017     else // edition
1018     {
1019       resultGroup = SMESH::SMESH_GroupBase::_narrow( myGroup );
1020       isCreation = false;
1021
1022       if ( mySelectAll->isChecked() ) {
1023         // select all
1024         myGroup->Clear();
1025         myGroup->AddFrom(myMesh.in());
1026       }
1027       else {
1028         QList<int> aAddList;
1029         
1030         int i, total = myElements->count();
1031         for (i = 0; i < total; i++) {
1032           int anId = myElements->item(i)->text().toInt();
1033           int idx = myIdList.indexOf(anId);
1034           if ( idx == -1 )
1035             aAddList.append(anId);
1036           else
1037             myIdList.removeAt(idx);
1038         }
1039         if (!aAddList.empty()) {
1040           SMESH::long_array_var anIdList = new SMESH::long_array;
1041           int added = aAddList.count();
1042           anIdList->length(added);
1043           for (i = 0; i < added; i++)
1044             anIdList[i] = aAddList[i];
1045           myGroup->Add(anIdList.inout());
1046         }
1047         if (!myIdList.empty()) {
1048           SMESH::long_array_var anIdList = new SMESH::long_array;
1049           int removed = myIdList.count();
1050           anIdList->length(removed);
1051           for (i = 0; i < removed; i++)
1052             anIdList[i] = myIdList[i];
1053           myGroup->Remove(anIdList.inout());
1054         }
1055         /* init for next operation */
1056         myIdList.clear();
1057         for (i = 0; i < total; i++) {
1058           myIdList.append(myElements->item(i)->text().toInt());
1059         }
1060       }
1061     }
1062
1063     anIsOk = true;
1064   }
1065   else if (myGrpTypeId == 1) // on geom object
1066   {
1067     if (CORBA::is_nil(myGroupOnGeom)) { // creation
1068       if (myMesh->_is_nil() || !myGeomObjects->length())
1069         return false;
1070
1071       _PTR(Study) aStudy = SMESH::getStudy();
1072
1073       if (myGeomObjects->length() == 1) {
1074         myGroupOnGeom = myMesh->CreateGroupFromGEOM(aType,
1075                                                     myName->text().toUtf8(),
1076                                                     myGeomObjects[0]);
1077       }
1078       else {
1079         SMESH::SMESH_Gen_var aSMESHGen = SMESHGUI::GetSMESHGen();
1080         if ( aSMESHGen->_is_nil() || myGeomObjects->length() == 0 )
1081           return false;
1082
1083         // create a geometry group
1084         GEOM::GEOM_Gen_var geomGen = SMESH::GetGEOMGen( myGeomObjects[0] );
1085         if (geomGen->_is_nil())
1086           return false;
1087
1088         GEOM::GEOM_IGroupOperations_wrap op = geomGen->GetIGroupOperations();
1089         if (op->_is_nil())
1090           return false;
1091
1092         // check and add all selected GEOM objects: they must be
1093         // a sub-shapes of the main GEOM and must be of one type
1094         TopAbs_ShapeEnum aGroupType = TopAbs_SHAPE;
1095         for ( CORBA::ULong i =0; i < myGeomObjects->length(); i++)
1096         {
1097           TopAbs_ShapeEnum aSubShapeType = (TopAbs_ShapeEnum)myGeomObjects[i]->GetShapeType();
1098           if ( i == 0 )
1099             aGroupType = aSubShapeType;
1100           else if ( aSubShapeType != aGroupType ) {
1101             aGroupType = TopAbs_SHAPE;
1102             break;
1103           }
1104         }
1105
1106         GEOM::GEOM_Object_var  aMeshShape = myMesh->GetShapeToMesh();
1107         GEOM::GEOM_Object_wrap aGroupVar = op->CreateGroup(aMeshShape, aGroupType);
1108         if ( aGroupVar->_is_nil() )
1109           return false;
1110         op->UnionList(aGroupVar, myGeomObjects);
1111
1112         if (op->IsDone()) {
1113           // publish the GEOM group in study
1114           QString aNewGeomGroupName ( "Auto_group_for_" );
1115           aNewGeomGroupName += myName->text();
1116           SALOMEDS::SObject_var aNewGroupSO =
1117             geomGen->AddInStudy(aGroupVar,
1118                                 aNewGeomGroupName.toUtf8(), aMeshShape);
1119         }
1120
1121         myGroupOnGeom = myMesh->CreateGroupFromGEOM(aType,
1122                                                     myName->text().toUtf8(),
1123                                                     aGroupVar);
1124       }
1125       resultGroup = SMESH::SMESH_GroupBase::_narrow( myGroupOnGeom );
1126       isCreation = true;
1127
1128     }
1129     else { // edition
1130
1131       resultGroup = SMESH::SMESH_GroupBase::_narrow( myGroupOnGeom );
1132       isCreation = false;
1133     }
1134     anIsOk = true;
1135   }
1136
1137   if (myGrpTypeId == 2) // group on filter
1138   {
1139     if ( myFilter->_is_nil() ) return false;
1140
1141     if (CORBA::is_nil(myGroupOnFilter)) // creation
1142     {
1143       if (myMesh->_is_nil())
1144         return false;
1145
1146       myGroupOnFilter = myMesh->CreateGroupFromFilter(aType,
1147                                                       myName->text().toUtf8(),
1148                                                       myFilter);
1149       resultGroup = SMESH::SMESH_GroupBase::_narrow( myGroupOnFilter );
1150       isCreation = true;
1151     }
1152     else
1153     {
1154       myGroupOnFilter->SetFilter( myFilter );
1155
1156       resultGroup = SMESH::SMESH_GroupBase::_narrow( myGroupOnFilter );
1157       isCreation = false;
1158     }
1159     anIsOk = true;
1160   }
1161
1162   if ( anIsOk )
1163   {
1164     SALOMEDS::Color aColor = getGroupColor();
1165     resultGroup->SetColor(aColor);
1166
1167     _PTR(SObject) aMeshGroupSO = SMESH::FindSObject( resultGroup );
1168     if( aMeshGroupSO )
1169       anEntryList.append( aMeshGroupSO->GetID().c_str() );
1170
1171     resultGroup->SetName(myName->text().trimmed().toUtf8());
1172
1173     if ( isCreation )
1174     {
1175       SMESH::setFileType ( aMeshGroupSO, "COULEURGROUP" );
1176
1177       /* init for the next operation */
1178       setDefaultName();
1179       myElements->clear();
1180       myGroup         = SMESH::SMESH_Group::_nil();
1181       myGroupOnGeom   = SMESH::SMESH_GroupOnGeom::_nil();
1182       myGroupOnFilter = SMESH::SMESH_GroupOnFilter::_nil();
1183       myFilter        = SMESH::Filter::_nil();
1184
1185       setDefaultGroupColor(); // reset color for case if 'auto-color' feature is enabled.
1186     }
1187     else
1188     {
1189       if ( aMeshGroupSO )
1190       {
1191         if ( SMESH_Actor *anActor = SMESH::FindActorByEntry(aMeshGroupSO->GetID().c_str()))
1192         {
1193           Handle(SALOME_InteractiveObject) anIO = anActor->getIO();
1194           if ( isConversion ) { // need to reset TVisualObj and actor
1195             SMESH::RemoveVisualObjectWithActors( anIO->getEntry(), true );
1196             SMESH::Update( anIO, true );
1197             myActorsList.clear();
1198             anActor = SMESH::FindActorByEntry( anIO->getEntry() );
1199             if ( !anActor ) return false;
1200             myActorsList.append( anActor );
1201           }
1202           anActor->setName(myName->text().toUtf8());
1203           QColor c;
1204           int delta;
1205           switch ( myTypeId ) {
1206           case grpNodeSelection:   anActor->SetNodeColor( aColor.R, aColor.G, aColor.B ); break;
1207           case grp0DSelection:     anActor->Set0DColor  ( aColor.R, aColor.G, aColor.B ); break;
1208           case grpBallSelection:   anActor->SetBallColor( aColor.R, aColor.G, aColor.B ); break;
1209           case grpEdgeSelection:   anActor->SetEdgeColor( aColor.R, aColor.G, aColor.B ); break;
1210           case grpVolumeSelection: 
1211             SMESH::GetColor("SMESH", "volume_color", c , delta, "255,0,170|-100");
1212             anActor->SetVolumeColor( aColor.R, aColor.G, aColor.B, delta ); break;          
1213             break;
1214           case grpFaceSelection:   
1215           default:
1216             SMESH::GetColor("SMESH", "fill_color", c , delta, "0,170,255|-100");
1217             anActor->SetSufaceColor( aColor.R, aColor.G, aColor.B, delta ); break;          
1218             break;
1219           }
1220           // update a visible group according to a changed contents
1221           if ( !isConversion && anActor->GetVisibility() )
1222           {
1223             SMESH::Update( anIO, true );
1224             SMESH::RepaintCurrentView();
1225           }
1226         }
1227       }
1228     }
1229     SMESHGUI::Modified();
1230     mySMESHGUI->updateObjBrowser(true);
1231     mySelectionMgr->clearSelected();
1232
1233     if( LightApp_Application* anApp =
1234         dynamic_cast<LightApp_Application*>( SUIT_Session::session()->activeApplication() ) )
1235       myObjectToSelect = anApp->browseObjects( anEntryList, isApplyAndClose() );
1236   }
1237   return anIsOk;
1238 }
1239
1240 //=================================================================================
1241 // function : onOK()
1242 // purpose  :
1243 //=================================================================================
1244 void SMESHGUI_GroupDlg::onOK()
1245 {
1246   setIsApplyAndClose( true );
1247   if ( onApply() )
1248     reject();
1249   setIsApplyAndClose( false );
1250
1251   if ( myFilterDlg ) myFilterDlg->UnRegisterFilters();
1252 }
1253
1254 //=================================================================================
1255 // function : onListSelectionChanged()
1256 // purpose  : Called when selection in element list is changed
1257 //=================================================================================
1258 void SMESHGUI_GroupDlg::onListSelectionChanged()
1259 {
1260   //MESSAGE( "SMESHGUI_GroupDlg::onListSelectionChanged(); myActorsList.count() = " << myActorsList.count());
1261   if( myIsBusy || myActorsList.count() == 0 ) return;
1262   myIsBusy = true;
1263
1264   if (myCurrentLineEdit == 0) {
1265     mySelectionMgr->clearSelected();
1266     TColStd_MapOfInteger aIndexes;
1267     QList<QListWidgetItem*> selItems = myElements->selectedItems();
1268     QListWidgetItem* anItem;
1269     foreach(anItem, selItems) aIndexes.Add(anItem->text().toInt());
1270     mySelector->AddOrRemoveIndex(myActorsList.first()->getIO(), aIndexes, false);
1271     SALOME_ListIO aList;
1272     aList.Append(myActorsList.first()->getIO());
1273     mySelectionMgr->setSelectedObjects(aList,false);
1274   }
1275   myIsBusy = false;
1276 }
1277
1278 //=================================================================================
1279 // function : onObjectSelectionChanged()
1280 // purpose  : Called when selection in 3D view or ObjectBrowser is changed
1281 //=================================================================================
1282 void SMESHGUI_GroupDlg::onObjectSelectionChanged()
1283 {
1284   if ( myIsBusy || !isEnabled()) return;
1285   if (myCurrentLineEdit == myGeomGroupLine && !myGeomGroupBtn->isChecked()) return;
1286
1287   myIsBusy = true;
1288
1289   SALOME_ListIO aList;
1290   mySelectionMgr->selectedObjects( aList );
1291
1292   int aNbSel = aList.Extent();
1293   myElements->clearSelection();
1294
1295   if (myCurrentLineEdit)
1296   {
1297     myCurrentLineEdit->setText( "" );
1298     QString aString = "";
1299
1300     if (myCurrentLineEdit == myMeshGroupLine)
1301     {
1302       mySelectSubMesh->setEnabled(false);
1303       mySelectGroup->setEnabled(false);
1304       myGroupLine->setText( "" );
1305       mySubMeshLine->setText( "" );
1306
1307       myGeomGroupBtn->setEnabled(false);
1308       myGeomGroupLine->setEnabled(false);
1309       myGeomGroupLine->setText( "" );
1310       myGeomObjects = new GEOM::ListOfGO();
1311       myGeomObjects->length(0);
1312
1313       if (myGeomGroupBtn->isChecked())
1314         myGeomGroupBtn->setChecked(false);
1315       if (!myCreate)
1316         myName->setText( "" );
1317
1318       myElements->clear();
1319
1320       if (aNbSel != 1 ) {
1321         myGroup = SMESH::SMESH_Group::_nil();
1322         myGroupOnGeom = SMESH::SMESH_GroupOnGeom::_nil();
1323         restoreShowEntityMode();
1324         myMesh = SMESH::SMESH_Mesh::_nil();
1325         updateGeomPopup();
1326         updateButtons();
1327         myIsBusy = false;
1328         return;
1329       }
1330       Handle(SALOME_InteractiveObject) IO = aList.First();
1331
1332       if (myCreate) {
1333         restoreShowEntityMode();
1334         myMesh = SMESH::IObjectToInterface<SMESH::SMESH_Mesh>(IO);
1335         setShowEntityMode();
1336         updateGeomPopup();
1337         if (myMesh->_is_nil())
1338         {
1339           updateButtons();
1340           myIsBusy = false;
1341           return;
1342         }
1343
1344         if ( myFilterDlg && !myMesh->_is_nil()){
1345           myFilterDlg->SetMesh( myMesh );
1346         }
1347         myGroup = SMESH::SMESH_Group::_nil();
1348
1349         // NPAL19389: create a group with a selection in another group
1350         // set actor of myMesh, if it is visible, else try
1351         // any visible actor of group or submesh of myMesh
1352         SetAppropriateActor();
1353
1354         setDefaultGroupColor();
1355         if (myName->text().isEmpty())
1356           setDefaultName();
1357
1358         aString = aList.First()->getName();
1359         myMeshGroupLine->setText(aString);
1360         myMeshGroupLine->home( false );
1361
1362         mySelectSubMesh->setEnabled(true);
1363         mySelectGroup->setEnabled(true);
1364         myGeomGroupBtn->setEnabled(true);
1365         myGeomGroupLine->setEnabled(true);
1366         updateButtons();
1367       }
1368       else {
1369         SMESH::SMESH_GroupBase_var aGroup = SMESH::IObjectToInterface<SMESH::SMESH_GroupBase>(IO);
1370         if (aGroup->_is_nil())
1371         {
1372           myIsBusy = false;
1373           return;
1374         }
1375         myIsBusy = false;
1376
1377         myGroup = SMESH::SMESH_Group::_nil();
1378         myGroupOnGeom = SMESH::SMESH_GroupOnGeom::_nil();
1379
1380         init(aGroup);
1381         myIsBusy = true;
1382         mySelectSubMesh->setEnabled(true);
1383         mySelectGroup->setEnabled(true);
1384       }
1385       myCurrentLineEdit = 0;
1386       myIsBusy = false;
1387       if (!myCreate)
1388         return;
1389
1390       if (myGrpTypeId == 0)
1391       {
1392         if (myTypeId == -1)
1393           onTypeChanged(0);
1394         else
1395         {
1396           myElements->clear();
1397           setSelectionMode(myTypeId);
1398         }
1399       }
1400
1401       myIsBusy = false;
1402       return;
1403
1404     }
1405     else if (myCurrentLineEdit == myGeomGroupLine)
1406     {
1407       myGeomObjects = new GEOM::ListOfGO();
1408
1409       // The mesh SObject
1410       _PTR(SObject) aMeshSO = SMESH::FindSObject(myMesh);
1411
1412       if (aNbSel == 0 || !aMeshSO)
1413       {
1414         myGeomObjects->length(0);
1415         updateButtons();
1416         myIsBusy = false;
1417         return;
1418       }
1419
1420       myGeomObjects->length(aNbSel);
1421
1422       GEOM::GEOM_Object_var aGeomGroup;
1423       int i = 0;
1424
1425       SALOME_ListIteratorOfListIO anIt (aList);
1426       for (; anIt.More(); anIt.Next())
1427       {
1428         CORBA::Object_var aGroupObj = SMESH::IObjectToObject(anIt.Value());
1429         if (CORBA::is_nil(aGroupObj))
1430           continue;
1431         // Check if the object is a geometry group
1432         aGeomGroup = GEOM::GEOM_Object::_narrow(aGroupObj);
1433         if (CORBA::is_nil(aGeomGroup))
1434           continue;
1435
1436         // Check if group constructed on the same shape as a mesh or on its child
1437
1438         // The main shape of the group
1439         GEOM::GEOM_Object_var aGroupMainShape;
1440         if (aGeomGroup->GetType() == 37)
1441         {
1442           GEOM::GEOM_IGroupOperations_wrap anOp =
1443             SMESH::GetGEOMGen( aGeomGroup )->GetIGroupOperations();
1444           aGroupMainShape = anOp->GetMainShape( aGeomGroup );
1445           // aGroupMainShape is an existing servant => GEOM_Object_var not GEOM_Object_wrap
1446         }
1447         else
1448         {
1449           aGroupMainShape = aGeomGroup;
1450           aGroupMainShape->Register();
1451         }
1452         CORBA::String_var entry = aGroupMainShape->GetStudyEntry();
1453         _PTR(SObject) aGroupMainShapeSO =
1454           SMESH::getStudy()->FindObjectID( entry.in() );
1455
1456         _PTR(SObject) anObj, aRef;
1457         bool isRefOrSubShape = false;
1458         if (aMeshSO->FindSubObject(1, anObj) &&  anObj->ReferencedObject(aRef)) {
1459           if (aRef->GetID() == aGroupMainShapeSO->GetID()) {
1460             isRefOrSubShape = true;
1461           } else {
1462             _PTR(SObject) aFather = aGroupMainShapeSO->GetFather();
1463             _PTR(SComponent) aComponent = aGroupMainShapeSO->GetFatherComponent();
1464             while (!isRefOrSubShape && aFather->GetID() != aComponent->GetID()) {
1465               if (aRef->GetID() == aFather->GetID())
1466                 isRefOrSubShape = true;
1467               else
1468                 aFather = aFather->GetFather();
1469             }
1470           }
1471         }
1472         if (isRefOrSubShape)
1473           myGeomObjects[i++] = aGeomGroup;
1474       }
1475
1476       myGeomObjects->length(i);
1477       if ( i == 0 )
1478       {
1479         myIsBusy = false;
1480         return;
1481       }
1482
1483       aNbSel = i;
1484     }
1485
1486     if (aNbSel >= 1) {
1487       if (aNbSel > 1) {
1488         if (myCurrentLineEdit == mySubMeshLine)
1489           aString = tr( "SMESH_SUBMESH_SELECTED" ).arg(aNbSel);
1490         else if (myCurrentLineEdit == myGroupLine)
1491           aString = tr( "SMESH_GROUP_SELECTED" ).arg(aNbSel);
1492         else if (myCurrentLineEdit == myGeomGroupLine)
1493           aString = tr( "%1 Objects" ).arg(aNbSel);
1494       }
1495       else {
1496         aString = aList.First()->getName();
1497       }
1498     }
1499
1500     myCurrentLineEdit->setText(aString);
1501     myCurrentLineEdit->home(false);
1502     // 07.06.2008 skl for IPAL19574:
1503     // change name of group only if it is empty
1504     if( myName->text().trimmed().isEmpty() || !myNameChanged ) {
1505       myOldName = myName->text();
1506       myName->blockSignals(true);
1507       myName->setText(aString);
1508       myName->blockSignals(false);
1509     }
1510
1511     updateButtons();
1512   }
1513   else // !myCurrentLineEdit: local selection of nodes or elements
1514   {
1515     if (aNbSel == 1 && myActorsList.count() > 0 )
1516     {
1517       // NPAL19389: create a group with a selection in another group
1518       // Switch myActor to the newly selected one, if the last
1519       // is visible and belongs to group or submesh of myMesh
1520       /*      Handle(SALOME_InteractiveObject) curIO = myActor->getIO();
1521       Handle(SALOME_InteractiveObject) selIO = aList.First();
1522       if (curIO->hasEntry() && selIO->hasEntry()) {
1523         const char* selEntry = selIO->getEntry();
1524         if (strcmp(curIO->getEntry(), selEntry) != 0) {
1525           // different objects: selected and myActor
1526           SVTK_ViewWindow* aViewWindow = SMESH::GetCurrentVtkView();
1527           if (aViewWindow && aViewWindow->isVisible(selIO)) {
1528             // newly selected actor is visible
1529
1530             // mesh entry
1531             _PTR(SObject) aSObject = SMESH::FindSObject(myMesh);
1532             if (aSObject) {
1533               CORBA::String_var meshEntry = aSObject->GetID().c_str();
1534               int len = strlen(meshEntry);
1535
1536               if (strncmp(selEntry, meshEntry, len) == 0) {
1537                 // selected object is myMesh or a part of it
1538                 SMESH_Actor* anActor = SMESH::FindActorByEntry(selEntry);
1539                 if (anActor) {
1540                   myActor = anActor;
1541                   SMESH::SetPickable(myActor);
1542                 }
1543               }
1544             }
1545           }
1546         }
1547       }*/
1548       // NPAL19389 END
1549
1550       QString aListStr = "";
1551       int aNbItems = 0;
1552       if (myTypeId == 0) {
1553         QListIterator<SMESH_Actor*> it( myActorsList );
1554         while ( it.hasNext() ) {
1555           QString tmpStr;
1556           aNbItems += SMESH::GetNameOfSelectedNodes(mySelector, it.next()->getIO(), tmpStr);
1557           aListStr += tmpStr;
1558         }
1559       } else {
1560         QListIterator<SMESH_Actor*> it( myActorsList );
1561         while ( it.hasNext() ) {
1562           QString tmpStr;
1563           aNbItems += SMESH::GetNameOfSelectedElements(mySelector, it.next()->getIO(), tmpStr);
1564           aListStr += tmpStr;
1565         }
1566       }
1567       if (aNbItems > 0) {
1568         QListWidgetItem* anItem;
1569         QList<QListWidgetItem*> listItemsToSel;
1570         QStringList anElements = aListStr.split( " ", QString::SkipEmptyParts);
1571         for (QStringList::iterator it = anElements.begin(); it != anElements.end(); ++it) {
1572           QList<QListWidgetItem*> found = myElements->findItems(*it, Qt::MatchExactly);
1573           foreach(anItem, found)
1574             if (!anItem->isSelected())
1575               listItemsToSel.push_back(anItem);
1576         }
1577         bool blocked = myElements->signalsBlocked();
1578         myElements->blockSignals(true);
1579         foreach(anItem, listItemsToSel) anItem->setSelected(true);
1580         myElements->blockSignals(blocked);
1581         onListSelectionChanged();
1582         listItemsToSel.clear();
1583       }
1584     }
1585   }
1586   
1587   if (myActorsList.count() == 0) {
1588     if (!myGroup->_is_nil()) {
1589       SMESH_Actor* anActor = SMESH::FindActorByObject(myGroup);
1590       if ( anActor )
1591         myActorsList.append( anActor  );
1592     }
1593     else if(!myGroupOnGeom->_is_nil()) {
1594       SMESH_Actor* anActor = SMESH::FindActorByObject(myGroupOnGeom);
1595       if ( anActor )
1596         myActorsList.append( anActor );
1597     }
1598     else {
1599       SMESH_Actor* anActor = SMESH::FindActorByObject( myMesh );
1600       if ( anActor )
1601         myActorsList.append( anActor );
1602     }
1603   }
1604
1605   // somehow, if we display the mesh, while selecting from another actor,
1606   // the mesh becomes pickable, and there is no way to select any element
1607   if (myActorsList.count() > 0) {
1608     QListIterator<SMESH_Actor*> it( myActorsList );
1609     while ( it.hasNext() ) {
1610       SMESH_Actor* anActor = it.next();
1611       if ( IsActorVisible(anActor) )
1612         anActor->SetPickable(true);
1613     }
1614   }
1615
1616   myIsBusy = false;
1617 }
1618
1619 //=================================================================================
1620 // function : onSelectAll()
1621 // purpose  : Called when "Select all" is checked
1622 //=================================================================================
1623 void SMESHGUI_GroupDlg::onSelectAll()
1624 {
1625   bool noElemsModif = ( mySelectAll->isChecked() || !myAllowElemsModif->isChecked() );
1626
1627   myElementsLab->setEnabled( !noElemsModif );
1628   myElements->setEnabled   ( !noElemsModif );
1629   myFilterBtn->setEnabled  ( !noElemsModif );
1630   myAddBtn->setEnabled     ( !noElemsModif );
1631   myRemoveBtn->setEnabled  ( !noElemsModif );
1632   mySortBtn->setEnabled    ( !noElemsModif );
1633   mySelectBox->setEnabled  ( !noElemsModif );
1634   myAllowElemsModif->setEnabled( !mySelectAll->isChecked() );
1635   if ( noElemsModif ) mySMESHGUI->ResetState();
1636   else                mySMESHGUI->SetState(800);
1637
1638   int selMode     = mySelectionMode;
1639   mySelectionMode = grpNoSelection;
1640   setSelectionMode( selMode );
1641   updateButtons();
1642 }
1643
1644 //=================================================================================
1645 // function : onSelectSubMesh()
1646 // purpose  : Called when selection in 3D view or ObjectBrowser is changed
1647 //=================================================================================
1648 void SMESHGUI_GroupDlg::onSelectSubMesh(bool on)
1649 {
1650   if (on) {
1651     if (mySelectGroup->isChecked()) {
1652       mySelectGroup->setChecked(false);
1653     }
1654     //VSR: else if (mySelectGeomGroup->isChecked()) {
1655     //VSR:   mySelectGeomGroup->setChecked(false);
1656     //VSR: }
1657     myCurrentLineEdit = mySubMeshLine;
1658     setSelectionMode(grpSubMeshSelection);
1659   }
1660   else {
1661     mySubMeshLine->setText( "" );
1662     myCurrentLineEdit = 0;
1663     if (myTypeId != -1)
1664       setSelectionMode(myTypeId);
1665   }
1666   mySubMeshBtn->setEnabled(on);
1667   mySubMeshLine->setEnabled(on);
1668 }
1669
1670
1671 //=================================================================================
1672 // function : (onSelectGroup)
1673 // purpose  : Called when selection in 3D view or ObjectBrowser is changed
1674 //=================================================================================
1675 void SMESHGUI_GroupDlg::onSelectGroup(bool on)
1676 {
1677   if (on) {
1678     if (mySelectSubMesh->isChecked()) {
1679       mySelectSubMesh->setChecked(false);
1680     }
1681     myCurrentLineEdit = myGroupLine;
1682     setSelectionMode(grpGroupSelection);
1683   }
1684   else {
1685     myGroupLine->setText( "" );
1686     myCurrentLineEdit = 0;
1687     if (myTypeId != -1)
1688       setSelectionMode(myTypeId);
1689   }
1690   myGroupBtn->setEnabled(on);
1691   myGroupLine->setEnabled(on);
1692 }
1693
1694
1695 //=================================================================================
1696 // function : (onSelectGeomGroup)
1697 // purpose  : Called when group type changed. on == "on geometry" or "on filter"
1698 //=================================================================================
1699 void SMESHGUI_GroupDlg::onSelectGeomGroup(bool on)
1700 {
1701   if (on) {
1702     if (mySelectSubMesh->isChecked()) {
1703       mySelectSubMesh->setChecked(false);
1704     }
1705     else if (mySelectGroup->isChecked()) {
1706       mySelectGroup->setChecked(false);
1707     }
1708     if ( myGrpTypeId == 1 ) { // on geometry
1709       myCurrentLineEdit = myGeomGroupLine;
1710       updateGeomPopup();
1711     }
1712     else { // on filter
1713       myCurrentLineEdit = 0;
1714     }
1715     setSelectionMode(grpAllSelection);
1716   }
1717   else {
1718     myGeomGroupBtn->setChecked(false);
1719     myGeomObjects->length(0);
1720     myGeomGroupLine->setText( "" );
1721     myCurrentLineEdit = 0;
1722     if (myTypeId != -1)
1723       setSelectionMode( myTypeId );
1724   }
1725 }
1726
1727 //=================================================================================
1728 // function : setCurrentSelection()
1729 // purpose  :
1730 //=================================================================================
1731 void SMESHGUI_GroupDlg::setCurrentSelection()
1732 {
1733   QPushButton* send = (QPushButton*)sender();
1734   myCurrentLineEdit = 0;
1735   if (send == myMeshGroupBtn) {
1736     disconnect(myMeshGroupBtn, SIGNAL(clicked()), this, SLOT(setCurrentSelection()));
1737     mySelectionMgr->clearSelected();
1738     if (myCreate)
1739       setSelectionMode(grpMeshSelection);
1740     else
1741       setSelectionMode(grpGroupSelection);
1742     connect(myMeshGroupBtn, SIGNAL(clicked()), this, SLOT(setCurrentSelection()));
1743     myCurrentLineEdit = myMeshGroupLine;
1744     onObjectSelectionChanged();
1745   }
1746   else if (send == mySubMeshBtn) {
1747     myCurrentLineEdit = mySubMeshLine;
1748     onObjectSelectionChanged();
1749   }
1750   else if (send == myGroupBtn) {
1751     myCurrentLineEdit = myGroupLine;
1752     onObjectSelectionChanged();
1753   }
1754 }
1755
1756
1757 //=================================================================================
1758 // function : setFilters()
1759 // purpose  : SLOT. Called when "Filter" button pressed.
1760 //=================================================================================
1761 void SMESHGUI_GroupDlg::setFilters()
1762 {
1763   if(myMesh->_is_nil()) {
1764     SUIT_MessageBox::critical(this,
1765                               tr("SMESH_ERROR"),
1766                               tr("NO_MESH_SELECTED"));
1767    return;
1768   }
1769
1770   SMESH::ElementType aType = SMESH::ALL;
1771   switch ( myTypeId )
1772   {
1773     case grpNodeSelection:   aType = SMESH::NODE;   break;
1774     case grp0DSelection:     aType = SMESH::ELEM0D; break;
1775     case grpBallSelection:   aType = SMESH::BALL;   break;
1776     case grpEdgeSelection:   aType = SMESH::EDGE;   break;
1777     case grpFaceSelection:   aType = SMESH::FACE;   break;
1778     case grpVolumeSelection: aType = SMESH::VOLUME; break;
1779     default:                 return;
1780   }
1781
1782   if ( myFilterDlg == 0 )
1783   {
1784     myFilterDlg = new SMESHGUI_FilterDlg( mySMESHGUI, aType );
1785     connect( myFilterDlg, SIGNAL( Accepted() ), SLOT( onFilterAccepted() ) );
1786   }
1787   else
1788     myFilterDlg->Init( aType );
1789
1790   if ( !myGroupOnFilter->_is_nil() )
1791   {
1792     myFilterDlg->SetFilter( myFilter, aType );
1793     myFilterDlg->Init( aType );
1794   }
1795
1796   bool isStandalone = ( sender() == myFilterBtn );
1797   myFilterDlg->SetEnabled( /*setInViewer=*/isStandalone,
1798                            /*diffSources=*/isStandalone );
1799   myFilterDlg->SetMesh( myMesh );
1800   myFilterDlg->SetGroup( myGroupOnFilter );
1801   myFilterDlg->SetSelection();
1802   myFilterDlg->SetSourceWg( myElements, false );
1803
1804   myFilterDlg->show();
1805 }
1806
1807 //=================================================================================
1808 // function : onFilterAccepted()
1809 // purpose  : SLOT. Called when Filter dlg closed with OK button.
1810 //            Uncheck "Select submesh" and "Select group" checkboxes
1811 //=================================================================================
1812 void SMESHGUI_GroupDlg::onFilterAccepted()
1813 {
1814   if ( mySelectSubMesh->isChecked() || mySelectGroup->isChecked() )
1815   {
1816     mySelectionMode = myTypeId;
1817     mySelectSubMesh->setChecked( false );
1818     mySelectGroup->setChecked( false );
1819   }
1820   // get a filter from myFilterDlg
1821   myFilter = myFilterDlg->GetFilter();
1822   if ( !myFilter->_is_nil() ) {
1823     SMESH::Predicate_var perdicate = myFilter->GetPredicate();
1824     if ( perdicate->_is_nil() )
1825       myFilter = SMESH::Filter::_nil();
1826   }
1827   // set mesh to myFilter
1828   if ( !myFilter->_is_nil() ) {
1829     SMESH::SMESH_Mesh_var mesh = myMesh;
1830     if ( mesh->_is_nil() ) {
1831       if ( !myGroup->_is_nil() )
1832         mesh = myGroup->GetMesh();
1833       else if ( !myGroupOnGeom->_is_nil() )
1834         mesh = myGroupOnGeom->GetMesh();
1835       else if ( !myGroupOnFilter->_is_nil() )
1836         mesh = myGroupOnFilter->GetMesh();
1837     }
1838     myFilter->SetMesh( mesh );
1839
1840     // highlight ids if selection changed in the Viewer (IPAL52924)
1841     myCurrentLineEdit = 0;
1842     onObjectSelectionChanged();
1843   }
1844
1845   updateButtons();
1846 }
1847
1848 //=================================================================================
1849 // function : onAdd()
1850 // purpose  :
1851 //=================================================================================
1852 void SMESHGUI_GroupDlg::onAdd()
1853 {
1854   SALOME_ListIO aList;
1855   mySelectionMgr->selectedObjects( aList );
1856
1857   int aNbSel = aList.Extent();
1858
1859   if (aNbSel == 0 || myActorsList.count() == 0 || myMesh->_is_nil()) return;
1860
1861   SUIT_OverrideCursor wc;
1862
1863   myIsBusy = true;
1864   int sizeBefore = myElements->count();
1865
1866   SMESH::ElementType aType = SMESH::ALL;
1867   switch(myTypeId) {
1868   case grpNodeSelection:
1869     aType = SMESH::NODE;
1870     mySelector->SetSelectionMode(NodeSelection);
1871     break;
1872   case grpBallSelection:
1873     aType = SMESH::BALL;
1874     mySelector->SetSelectionMode(BallSelection);
1875     break;
1876   case grp0DSelection:
1877     aType = SMESH::ELEM0D;
1878     mySelector->SetSelectionMode(Elem0DSelection);
1879     break;
1880   case grpEdgeSelection:
1881     aType = SMESH::EDGE;
1882     mySelector->SetSelectionMode(EdgeSelection);
1883     break;
1884   case grpFaceSelection:
1885     aType = SMESH::FACE;
1886     mySelector->SetSelectionMode(FaceSelection);
1887     break;
1888   case grpVolumeSelection:
1889     aType = SMESH::VOLUME;
1890     mySelector->SetSelectionMode(VolumeSelection);
1891     break;
1892   default:
1893     mySelector->SetSelectionMode(ActorSelection);
1894   }
1895
1896   QListWidgetItem* anItem = 0;
1897   QList<QListWidgetItem*> listItemsToSel;
1898
1899   if ( myCurrentLineEdit == 0 )
1900   {
1901     //if (aNbSel != 1) { myIsBusy = false; return; }
1902     QString aListStr = "";
1903     int aNbItems = 0;
1904     if (myTypeId == 0) {
1905       QListIterator<SMESH_Actor*> it( myActorsList );
1906       while ( it.hasNext() ) {
1907         QString tmpStr;
1908         aNbItems += SMESH::GetNameOfSelectedNodes(mySelector, it.next()->getIO(), tmpStr);
1909         aListStr += tmpStr;
1910       }
1911     }
1912     else {
1913       QListIterator<SMESH_Actor*> it( myActorsList );
1914       while ( it.hasNext() ) {
1915         QString tmpStr;
1916         aNbItems += SMESH::GetNameOfSelectedElements(mySelector, it.next()->getIO(), tmpStr);
1917         aListStr += tmpStr;
1918       }
1919     }
1920     if (aNbItems > 0) {
1921       QStringList anElements = aListStr.split( " ", QString::SkipEmptyParts);
1922       for (QStringList::iterator it = anElements.begin(); it != anElements.end(); ++it) {
1923         QList<QListWidgetItem*> found = myElements->findItems(*it, Qt::MatchExactly);
1924         if (found.count() == 0) {
1925           anItem = new QListWidgetItem(*it);
1926           myElements->addItem(anItem);
1927           if (!anItem->isSelected())
1928             listItemsToSel.push_back(anItem);
1929         }
1930         else {
1931           foreach(anItem, found)
1932             if (!anItem->isSelected())
1933               listItemsToSel.push_back(anItem);
1934         }
1935       }
1936       bool blocked = myElements->signalsBlocked();
1937       myElements->blockSignals(true);
1938       foreach(anItem, listItemsToSel) anItem->setSelected(true);
1939       myElements->blockSignals(blocked);
1940       onListSelectionChanged();
1941       listItemsToSel.clear();
1942     }
1943   }
1944   else if ( myCurrentLineEdit == mySubMeshLine )
1945   {
1946     //SALOME_ListIteratorOfListIO anIt (mySelectionMgr->StoredIObjects());
1947
1948     SALOME_ListIO aList;
1949     mySelectionMgr->selectedObjects( aList );
1950
1951     SALOME_ListIteratorOfListIO anIt (aList);
1952     for ( ; anIt.More(); anIt.Next()) {
1953       SMESH::SMESH_subMesh_var aSubMesh =
1954         SMESH::IObjectToInterface<SMESH::SMESH_subMesh>(anIt.Value());
1955       if (!aSubMesh->_is_nil()) {
1956         // check if mesh is the same
1957         if (aSubMesh->GetFather()->GetId() == myMesh->GetId()) {
1958           try {
1959             SMESH::long_array_var anElements = aSubMesh->GetElementsByType(aType);
1960             int k = anElements->length();
1961             for (int i = 0; i < k; i++) {
1962               QString aText = QString::number(anElements[i]);
1963               QList<QListWidgetItem*> found = myElements->findItems(aText, Qt::MatchExactly);
1964               if (found.count() == 0) {
1965                 anItem = new QListWidgetItem(aText);
1966                 myElements->addItem(anItem);
1967                 if (!anItem->isSelected())
1968                   listItemsToSel.push_back(anItem);
1969               }
1970               else {
1971                 foreach(anItem, found)
1972                   if (!anItem->isSelected())
1973                     listItemsToSel.push_back(anItem);
1974               }
1975             }
1976             bool blocked = myElements->signalsBlocked();
1977             myElements->blockSignals(true);
1978             foreach(anItem, listItemsToSel) anItem->setSelected(true);
1979             myElements->blockSignals(blocked);
1980             onListSelectionChanged();
1981             listItemsToSel.clear();
1982           }
1983           catch (const SALOME::SALOME_Exception& ex) {
1984             SalomeApp_Tools::QtCatchCorbaException(ex);
1985           }
1986         }
1987       }
1988     }
1989     mySelectSubMesh->setChecked(false);
1990     myIsBusy = false;
1991     onListSelectionChanged();
1992
1993   }
1994   else if ( myCurrentLineEdit == myGroupLine )
1995   {
1996     //SALOME_ListIteratorOfListIO anIt (mySelectionMgr->StoredIObjects());
1997     SALOME_ListIO aList;
1998     mySelectionMgr->selectedObjects( aList );
1999
2000     SALOME_ListIteratorOfListIO anIt (aList);
2001     for ( ; anIt.More(); anIt.Next()) {
2002       SMESH::SMESH_GroupBase_var aGroup =
2003         SMESH::IObjectToInterface<SMESH::SMESH_GroupBase>(anIt.Value());
2004       if (!aGroup->_is_nil()) {
2005         // check if mesh is the same
2006         if (aGroup->GetType() == aType && aGroup->GetMesh()->GetId() == myMesh->GetId()) {
2007           SMESH::long_array_var anElements = aGroup->GetListOfID();
2008           int k = anElements->length();
2009           for (int i = 0; i < k; i++) {
2010             QString aText = QString::number(anElements[i]);
2011             QList<QListWidgetItem*> found = myElements->findItems(aText, Qt::MatchExactly);
2012             if (found.count() == 0) {
2013               anItem = new QListWidgetItem(aText);
2014               myElements->addItem(anItem);
2015               if (!anItem->isSelected())
2016                 listItemsToSel.push_back(anItem);
2017             }
2018             else {
2019               foreach(anItem, found)
2020                 if (!anItem->isSelected())
2021                   listItemsToSel.push_back(anItem);
2022             }
2023           }
2024           bool blocked = myElements->signalsBlocked();
2025           myElements->blockSignals(true);
2026           foreach(anItem, listItemsToSel) anItem->setSelected(true);
2027           myElements->blockSignals(blocked);
2028           onListSelectionChanged();
2029           listItemsToSel.clear();
2030         }
2031       }
2032     }
2033     mySelectGroup->setChecked(false);
2034     myIsBusy = false;
2035     onListSelectionChanged();
2036
2037   }
2038   else if ( myCurrentLineEdit == myGeomGroupLine && myGeomObjects->length() == 1 )
2039   {
2040     GEOM::GEOM_IGroupOperations_wrap aGroupOp =
2041       SMESH::GetGEOMGen( myGeomObjects[0] )->GetIGroupOperations();
2042
2043     SMESH::ElementType aGroupType = SMESH::ALL;
2044     switch(aGroupOp->GetType(myGeomObjects[0])) {
2045     case TopAbs_VERTEX: aGroupType = SMESH::NODE; break;
2046     case TopAbs_EDGE:   aGroupType = SMESH::EDGE; break;
2047     case TopAbs_FACE:   aGroupType = SMESH::FACE; break;
2048     case TopAbs_SOLID:  aGroupType = SMESH::VOLUME; break;
2049     default: myIsBusy = false; return;
2050     }
2051
2052     if (aGroupType == aType) {
2053       _PTR(SObject) aGroupSO =
2054         //SMESH::getStudy()->FindObjectIOR(SMESH::getStudy()->ConvertObjectToIOR(myGeomGroup));
2055         SMESH::getStudy()->FindObjectID(myGeomObjects[0]->GetStudyEntry());
2056       // Construct filter
2057       SMESH::FilterManager_var aFilterMgr = SMESH::GetFilterManager();
2058       SMESH::Filter_var aFilter = aFilterMgr->CreateFilter();
2059       SMESH::BelongToGeom_var aBelongToGeom = aFilterMgr->CreateBelongToGeom();
2060       aBelongToGeom->SetGeom(myGeomObjects[0]);
2061       aBelongToGeom->SetShapeName(aGroupSO->GetName().c_str());
2062       aBelongToGeom->SetElementType(aType);
2063       aFilter->SetPredicate(aBelongToGeom);
2064
2065       SMESH::long_array_var anElements = aFilter->GetElementsId(myMesh);
2066
2067       int k = anElements->length();
2068       for (int i = 0; i < k; i++) {
2069         QString aText = QString::number(anElements[i]);
2070         QList<QListWidgetItem*> found = myElements->findItems(aText, Qt::MatchExactly);
2071         if (found.count() == 0) {
2072           anItem = new QListWidgetItem(aText);
2073           myElements->addItem(anItem);
2074           if (!anItem->isSelected())
2075             listItemsToSel.push_back(anItem);
2076         }
2077         else {
2078           foreach(anItem, found)
2079             if (!anItem->isSelected())
2080               listItemsToSel.push_back(anItem);
2081         }
2082       }
2083       bool blocked = myElements->signalsBlocked();
2084       myElements->blockSignals(true);
2085       foreach(anItem, listItemsToSel) anItem->setSelected(true);
2086       myElements->blockSignals(blocked);
2087       onListSelectionChanged();
2088       listItemsToSel.clear();
2089     }
2090
2091     //VSR: mySelectGeomGroup->setChecked(false);
2092     myIsBusy = false;
2093     onListSelectionChanged();
2094   }
2095   myIsBusy = false;
2096   if ( sizeBefore < myElements->count() )
2097     ++myNbChangesOfContents;
2098   //  mySelectionMgr->clearSelected();
2099   updateButtons();
2100 }
2101
2102 //=================================================================================
2103 // function : onRemove()
2104 // purpose  :
2105 //=================================================================================
2106 void SMESHGUI_GroupDlg::onRemove()
2107 {
2108   myIsBusy = true;
2109   int sizeBefore = myElements->count();
2110
2111   if (myCurrentLineEdit == 0) {
2112     QList<QListWidgetItem*> selItems = myElements->selectedItems();
2113     QListWidgetItem* item;
2114     foreach(item, selItems) delete item;
2115   } else {
2116     SALOME_ListIO aList;
2117     mySelectionMgr->selectedObjects( aList );
2118
2119     int aNbSel = aList.Extent();
2120
2121     if (aNbSel == 0) { myIsBusy = false; return; }
2122
2123     SMESH::ElementType aType = SMESH::ALL;
2124     switch(myTypeId) {
2125     case grpNodeSelection:   aType = SMESH::NODE;   break;
2126     case grp0DSelection:     aType = SMESH::ELEM0D; break;
2127     case grpBallSelection:   aType = SMESH::BALL;   break;
2128     case grpEdgeSelection:   aType = SMESH::EDGE;   break;
2129     case grpFaceSelection:   aType = SMESH::FACE;   break;
2130     case grpVolumeSelection: aType = SMESH::VOLUME; break;
2131     }
2132
2133     if (myCurrentLineEdit == mySubMeshLine) {
2134       //SALOME_ListIteratorOfListIO anIt (mySelectionMgr->StoredIObjects());
2135       SALOME_ListIO aList;
2136       mySelectionMgr->selectedObjects( aList );
2137
2138       SALOME_ListIteratorOfListIO anIt (aList);
2139       for ( ; anIt.More(); anIt.Next()) {
2140         SMESH::SMESH_subMesh_var aSubMesh = SMESH::IObjectToInterface<SMESH::SMESH_subMesh>(anIt.Value());
2141         if (!aSubMesh->_is_nil()) {
2142           // check if mesh is the same
2143           if (aSubMesh->GetFather()->GetId() == myMesh->GetId()) {
2144             if (aType == SMESH::NODE) {
2145               try {
2146                 SMESH::long_array_var anElements = aSubMesh->GetNodesId();
2147                 int k = anElements->length();
2148                 for (int i = 0; i < k; i++) {
2149                   QList<QListWidgetItem*> found = 
2150                     myElements->findItems(QString::number(anElements[i]), Qt::MatchExactly);
2151                   QListWidgetItem* anItem;
2152                   foreach(anItem, found) delete anItem;
2153                 }
2154               }
2155               catch (const SALOME::SALOME_Exception& ex) {
2156                 SalomeApp_Tools::QtCatchCorbaException(ex);
2157               }
2158             }
2159             else {
2160               try {
2161                 SMESH::long_array_var anElements = aSubMesh->GetElementsId();
2162                 int k = anElements->length();
2163                 for (int i = 0; i < k; i++) {
2164                   QList<QListWidgetItem*> found = 
2165                     myElements->findItems(QString::number(anElements[i]), Qt::MatchExactly);
2166                   QListWidgetItem* anItem;
2167                   foreach(anItem, found) delete anItem;
2168                 }
2169               }
2170               catch (const SALOME::SALOME_Exception& ex) {
2171                 SalomeApp_Tools::QtCatchCorbaException(ex);
2172               }
2173             }
2174           }
2175         }
2176       }
2177     }
2178     else if (myCurrentLineEdit == myGroupLine) {
2179       SALOME_ListIO aList;
2180       mySelectionMgr->selectedObjects( aList );
2181
2182       SALOME_ListIteratorOfListIO anIt (aList);
2183       for ( ; anIt.More(); anIt.Next()) {
2184         SMESH::SMESH_Group_var aGroup = SMESH::IObjectToInterface<SMESH::SMESH_Group>(anIt.Value());
2185         if (!aGroup->_is_nil()) {
2186           // check if mesh is the same
2187           if (aGroup->GetType() == aType && aGroup->GetMesh()->GetId() == myMesh->GetId()) {
2188             SMESH::long_array_var anElements = aGroup->GetListOfID();
2189             int k = anElements->length();
2190             for (int i = 0; i < k; i++) {
2191               QList<QListWidgetItem*> found = 
2192                 myElements->findItems(QString::number(anElements[i]), Qt::MatchExactly);
2193               QListWidgetItem* anItem;
2194               foreach(anItem, found) delete anItem;
2195             }
2196           }
2197         }
2198       }
2199     }
2200   }
2201   myIsBusy = false;
2202   if ( sizeBefore > myElements->count() )
2203     myNbChangesOfContents += 2; // it's used to detect that "Add" was only once
2204   updateButtons();
2205 }
2206
2207 //=================================================================================
2208 // function : onSort()
2209 // purpose  :
2210 //=================================================================================
2211 void SMESHGUI_GroupDlg::onSort()
2212 {
2213   // PAL5412: sorts items in ascending by "string" value
2214   // myElements->sort(true);
2215   // myElements->update();
2216   int i, k = myElements->count();
2217   if (k > 0) {
2218     myIsBusy = true;
2219     QList<int> aSelected;
2220     std::vector<int> anArray(k);
2221     //    QMemArray<int> anArray(k);
2222     // fill the array
2223     for (i = 0; i < k; i++) {
2224       int id = myElements->item(i)->text().toInt();
2225       anArray[i] = id;
2226       if (myElements->item(i)->isSelected())
2227         aSelected.append(id);
2228     }
2229     // sort & update list
2230     std::sort(anArray.begin(), anArray.end());
2231     //    anArray.sort();
2232     myElements->clear();
2233     QListWidgetItem* anItem;
2234     QList<QListWidgetItem*> listItemsToSel;
2235     for (i = 0; i < k; i++) {
2236       anItem = new QListWidgetItem(QString::number(anArray[i]));
2237       myElements->addItem(anItem);
2238       if (aSelected.contains(anArray[i]))
2239         listItemsToSel.push_back(anItem);
2240     }
2241     bool blocked = myElements->signalsBlocked();
2242     myElements->blockSignals(true);
2243     foreach(anItem, listItemsToSel) anItem->setSelected(true);
2244     myElements->blockSignals(blocked);
2245     listItemsToSel.clear();
2246     myIsBusy = false;
2247   }
2248 }
2249
2250 //=================================================================================
2251 // function : onVisibilityChanged()
2252 // purpose  :
2253 //=================================================================================
2254 void SMESHGUI_GroupDlg::onVisibilityChanged()
2255 {
2256   SetAppropriateActor();
2257 }
2258
2259 //=================================================================================
2260 // function : SMESHGUI_GroupDlg::reject
2261 // purpose  : SLOT called when "Close" button pressed. Close dialog
2262 //=================================================================================
2263 void SMESHGUI_GroupDlg::reject()
2264 {
2265   if (SMESH::GetCurrentVtkView()) {
2266     SMESH::RemoveFilters(); // PAL6938 -- clean all mesh entity filters
2267     SMESH::SetPointRepresentation(false);
2268     SMESH::SetPickable();
2269     restoreShowEntityMode();
2270   }
2271
2272   if( isApplyAndClose() && !myObjectToSelect.isEmpty() ) {
2273     SUIT_DataOwnerPtrList aList;
2274     aList.append( new LightApp_DataOwner( myObjectToSelect ) );
2275     mySelectionMgr->setSelected( aList );
2276   }
2277   else
2278     mySelectionMgr->clearSelected();
2279   if ( SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI ))
2280     aViewWindow->SetSelectionMode(ActorSelection);
2281   mySelectionMgr->clearFilters();
2282   mySMESHGUI->ResetState();
2283
2284   QDialog::reject();
2285
2286   if ( myFilterDlg ) myFilterDlg->UnRegisterFilters();
2287 }
2288
2289 //=================================================================================
2290 // function : onOpenView()
2291 // purpose  :
2292 //=================================================================================
2293 void SMESHGUI_GroupDlg::onOpenView()
2294 {
2295   if ( mySelector ) {
2296     SMESH::SetPointRepresentation(false);
2297   }
2298   else {
2299     mySelector = SMESH::GetViewWindow( mySMESHGUI )->GetSelector();
2300     mySMESHGUI->EmitSignalDeactivateDialog();
2301     setEnabled(true);
2302   }
2303 }
2304
2305 //=================================================================================
2306 // function : onCloseView()
2307 // purpose  :
2308 //=================================================================================
2309 void SMESHGUI_GroupDlg::onCloseView()
2310 {
2311   onDeactivate();
2312   mySelector = 0;
2313 }
2314
2315 //=================================================================================
2316 // function : onHelp()
2317 // purpose  :
2318 //=================================================================================
2319 void SMESHGUI_GroupDlg::onHelp()
2320 {
2321   LightApp_Application* app = (LightApp_Application*)(SUIT_Session::session()->activeApplication());
2322   if (app)
2323   {
2324     app->onHelpContextModule
2325       ( mySMESHGUI ? app->moduleName( mySMESHGUI->moduleName() ) : QString(""), myHelpFileName );
2326   }
2327   else
2328   {
2329 #ifdef WIN32
2330     QString platform = "winapplication";
2331 #else
2332     QString platform = "application";
2333 #endif
2334     SUIT_MessageBox::warning(this, tr( "WRN_WARNING" ),
2335                              tr( "EXTERNAL_BROWSER_CANNOT_SHOW_PAGE" ).
2336                              arg(app->resourceMgr()->stringValue( "ExternalBrowser", platform)).
2337                              arg(myHelpFileName));
2338   }
2339 }
2340
2341 //=================================================================================
2342 // function : SMESHGUI_GroupDlg::onDeactivate
2343 // purpose  : SLOT called when dialog must be deactivated
2344 //=================================================================================
2345 void SMESHGUI_GroupDlg::onDeactivate()
2346 {
2347   mySMESHGUI->ResetState();
2348   setEnabled(false);
2349 }
2350
2351 //=================================================================================
2352 // function : SMESHGUI_GroupDlg::enterEvent
2353 // purpose  : Event filter
2354 //=================================================================================
2355 void SMESHGUI_GroupDlg::enterEvent (QEvent*)
2356 {
2357   if (!isEnabled()) {
2358     SVTK_ViewWindow* aViewWindow = SMESH::GetViewWindow( mySMESHGUI );
2359     if ( aViewWindow && !mySelector) {
2360       mySelector = aViewWindow->GetSelector();
2361     }
2362     mySMESHGUI->EmitSignalDeactivateDialog();
2363     setEnabled(true);
2364     mySelectionMode = grpNoSelection;
2365     setSelectionMode(myTypeId);
2366     mySMESHGUI->SetActiveDialogBox(this);
2367     if ( mySelectBox->isEnabled() ) mySMESHGUI->SetState(800);
2368     else                            mySMESHGUI->ResetState();
2369   }
2370 }
2371
2372 //=================================================================================
2373 // function : keyPressEvent()
2374 // purpose  :
2375 //=================================================================================
2376 void SMESHGUI_GroupDlg::keyPressEvent( QKeyEvent* e )
2377 {
2378   QDialog::keyPressEvent( e );
2379   if ( e->isAccepted() )
2380     return;
2381
2382   if ( e->key() == Qt::Key_F1 )
2383   {
2384     e->accept();
2385     onHelp();
2386   }
2387 }
2388
2389 //================================================================================
2390 /*!
2391  * \brief Enable showing of the popup when Geometry selection btn is clicked
2392  * \param enable - true to enable
2393  */
2394 //================================================================================
2395
2396 enum { DIRECT_GEOM_INDEX = 0, GEOM_BY_MESH_INDEX };
2397
2398 void SMESHGUI_GroupDlg::updateGeomPopup()
2399 {
2400   bool enable = false;
2401
2402   if ( !myMesh->_is_nil() )
2403     enable = myMesh->NbEdges() > 0;
2404
2405   if ( myGeomGroupBtn )
2406   {
2407     disconnect( myGeomGroupBtn, SIGNAL( toggled(bool) ), this, SLOT( onGeomSelectionButton(bool) ));
2408     if ( enable ) {
2409       if ( !myGeomPopup ) {
2410         myGeomPopup = new QMenu(this);
2411         myActions[myGeomPopup->addAction( tr( "DIRECT_GEOM_SELECTION" ) )] = DIRECT_GEOM_INDEX;
2412         myActions[myGeomPopup->addAction( tr( "GEOM_BY_MESH_ELEM_SELECTION" ) )] = GEOM_BY_MESH_INDEX;
2413         connect( myGeomPopup, SIGNAL( triggered( QAction* ) ), SLOT( onGeomPopup( QAction* ) ) );
2414       }
2415       connect( myGeomGroupBtn, SIGNAL( toggled(bool) ), this, SLOT( onGeomSelectionButton(bool) ));
2416     }
2417   }
2418 }
2419
2420
2421 //=================================================================================
2422 // function : onGeomSelectionButton()
2423 // purpose  :
2424 //=================================================================================
2425 void SMESHGUI_GroupDlg::onGeomSelectionButton(bool isBtnOn)
2426 {
2427   if ( myGeomPopup && isBtnOn )
2428   {
2429     myCurrentLineEdit = myGeomGroupLine;
2430     QAction* a = myGeomPopup->exec( QCursor::pos() );
2431     if (!a || myActions[a] == DIRECT_GEOM_INDEX)
2432       setSelectionMode(grpGeomSelection);
2433   }
2434   else if (!isBtnOn)
2435   {
2436     myCurrentLineEdit = 0;
2437     setSelectionMode(grpAllSelection);
2438   }
2439 }
2440
2441 //=================================================================================
2442 // function : onGeomPopup()
2443 // purpose  :
2444 //=================================================================================
2445 void SMESHGUI_GroupDlg::onGeomPopup( QAction* a )
2446 {
2447   int index = myActions[a];
2448   if ( index == GEOM_BY_MESH_INDEX )
2449   {
2450     mySelectionMode = grpNoSelection;
2451     if ( !myShapeByMeshOp ) {
2452       myShapeByMeshOp = new SMESHGUI_ShapeByMeshOp(true);
2453       connect(myShapeByMeshOp, SIGNAL(committed(SUIT_Operation*)),
2454               SLOT(onPublishShapeByMeshDlg(SUIT_Operation*)));
2455       connect(myShapeByMeshOp, SIGNAL(aborted(SUIT_Operation*)),
2456               SLOT(onCloseShapeByMeshDlg(SUIT_Operation*)));
2457     }
2458     // set mesh object to SMESHGUI_ShapeByMeshOp and start it
2459     if ( !myMesh->_is_nil() ) {
2460       myIsBusy = true;
2461       hide(); // stop processing selection
2462       myIsBusy = false;
2463       myShapeByMeshOp->setModule( mySMESHGUI );
2464       myShapeByMeshOp->setStudy( 0 ); // it's really necessary
2465       myShapeByMeshOp->SetMesh( myMesh );
2466       myShapeByMeshOp->start();
2467     }
2468   }
2469 }
2470
2471 //================================================================================
2472 /*!
2473  * \brief SLOT. Is called when Ok is pressed in SMESHGUI_ShapeByMeshDlg
2474  */
2475 //================================================================================
2476
2477 void SMESHGUI_GroupDlg::onPublishShapeByMeshDlg(SUIT_Operation* op)
2478 {
2479   if ( myShapeByMeshOp == op ) {
2480     mySMESHGUI->getApp()->updateObjectBrowser();
2481     show();
2482     // Select a found geometry object
2483     GEOM::GEOM_Object_var aGeomVar = myShapeByMeshOp->GetShape();
2484     if ( !aGeomVar->_is_nil() )
2485     {
2486       QString ID = aGeomVar->GetStudyEntry();
2487       if ( _PTR(SObject) aGeomSO = SMESH::getStudy()->FindObjectID( ID.toLatin1().data() )) {
2488         SALOME_ListIO anIOList;
2489         Handle(SALOME_InteractiveObject) anIO = new SALOME_InteractiveObject
2490           ( aGeomSO->GetID().c_str(), "SMESH", aGeomSO->GetName().c_str() );
2491         anIOList.Append( anIO );
2492         mySelectionMgr->setSelectedObjects( anIOList, false );
2493         onObjectSelectionChanged();
2494       }
2495     }
2496   }
2497 }
2498
2499 //================================================================================
2500 /*!
2501  * \brief SLOT. Is called when Close is pressed in SMESHGUI_ShapeByMeshDlg
2502  */
2503 //================================================================================
2504
2505 void SMESHGUI_GroupDlg::onCloseShapeByMeshDlg(SUIT_Operation* op)
2506 {
2507   if ( myShapeByMeshOp == op )
2508   {
2509     show();
2510     setSelectionMode(grpGeomSelection);
2511   }
2512 }
2513
2514 //=================================================================================
2515 // function : setGroupColor()
2516 // purpose  :
2517 //=================================================================================
2518 void SMESHGUI_GroupDlg::setGroupColor( const SALOMEDS::Color& theColor )
2519 {
2520   QColor aQColor( (int)( theColor.R * 255.0 ),
2521                   (int)( theColor.G * 255.0 ),
2522                   (int)( theColor.B * 255.0 ) );
2523   setGroupQColor( aQColor );
2524 }
2525
2526 //=================================================================================
2527 // function : getGroupColor()
2528 // purpose  :
2529 //=================================================================================
2530 SALOMEDS::Color SMESHGUI_GroupDlg::getGroupColor() const
2531 {
2532   QColor aQColor = getGroupQColor();
2533
2534   SALOMEDS::Color aColor;
2535   aColor.R = (float)aQColor.red() / 255.0;
2536   aColor.G = (float)aQColor.green() / 255.0;
2537   aColor.B = (float)aQColor.blue() / 255.0;
2538
2539   return aColor;
2540 }
2541
2542 //=================================================================================
2543 // function : setGroupQColor()
2544 // purpose  :
2545 //=================================================================================
2546 void SMESHGUI_GroupDlg::setGroupQColor( const QColor& theColor )
2547 {
2548   if( theColor.isValid() )
2549     myColorBtn->setColor( theColor );
2550 }
2551
2552 //=================================================================================
2553 // function : getGroupQColor()
2554 // purpose  :
2555 //=================================================================================
2556 QColor SMESHGUI_GroupDlg::getGroupQColor() const
2557 {
2558   return myColorBtn->color();
2559 }
2560
2561 //=================================================================================
2562 // function : setDefaultGroupColor()
2563 // purpose  :
2564 //=================================================================================
2565 void SMESHGUI_GroupDlg::setDefaultGroupColor()
2566 {
2567   if( myMesh->_is_nil() )
2568     return;
2569
2570   bool isAutoColor = myMesh->GetAutoColor();
2571
2572   QColor aQColor = myColorBtn->color();
2573   if( !isAutoColor )
2574   {
2575     if ( !aQColor.isValid() ) {
2576       int r = 0, g = 0, b = 0;
2577       SMESH::GetColor( "SMESH", "default_grp_color", r, g, b, QColor( 255, 170, 0 ) );
2578       aQColor.setRgb( r, g, b );
2579     }
2580   }
2581   else
2582   {
2583 #ifdef SIMPLE_AUTOCOLOR   // simplified algorithm for auto-colors
2584     SALOMEDS::Color aColor = SMESHGUI::getPredefinedUniqueColor();
2585 #else                     // old algorithm  for auto-colors
2586     SMESH::ListOfGroups aListOfGroups = *myMesh->GetGroups();
2587
2588     QList<SALOMEDS::Color> aReservedColors;
2589     for( int i = 0, n = aListOfGroups.length(); i < n; i++ )
2590     {
2591       SMESH::SMESH_GroupBase_var aGroupObject = aListOfGroups[i];
2592       SALOMEDS::Color aReservedColor = aGroupObject->GetColor();
2593       aReservedColors.append( aReservedColor );
2594     }
2595
2596     SALOMEDS::Color aColor = SMESHGUI::getUniqueColor( aReservedColors );
2597 #endif                    // SIMPLE_AUTOCOLOR
2598
2599     aQColor.setRgb( (int)( aColor.R * 255.0 ),
2600                     (int)( aColor.G * 255.0 ),
2601                     (int)( aColor.B * 255.0 ) );
2602
2603   }
2604
2605   setGroupQColor( aQColor );
2606 }
2607
2608 //=================================================================================
2609 // function : SetAppropriateActor()
2610 // purpose  : Find more appropriate of visible actors, set it to myActor, allow picking
2611 //            NPAL19389: create a group with a selection in another group.
2612 //            if mesh actor is not visible - find any first visible group or sub-mesh
2613 //=================================================================================
2614 bool SMESHGUI_GroupDlg::SetAppropriateActor()
2615 {
2616   bool isActor = false;
2617   myActorsList.clear();
2618
2619   if (myMesh->_is_nil()) return false;
2620
2621   SVTK_ViewWindow* aViewWindow = SMESH::GetCurrentVtkView();
2622
2623   if (myGrpTypeGroup->checkedId() > 0) {   // try current group on geometry actor
2624     SMESH_Actor* anActor = 0;
2625     if (!myGroupOnGeom->_is_nil())
2626       anActor = SMESH::FindActorByObject(myGroupOnGeom);
2627     if (!myGroupOnFilter->_is_nil())
2628       anActor = SMESH::FindActorByObject(myGroupOnFilter);
2629     if (anActor && anActor->hasIO())
2630     {
2631       isActor = true;
2632       if (aViewWindow && !aViewWindow->isVisible(anActor->getIO()))
2633         isActor = false;
2634       else
2635         myActorsList.append(anActor);
2636     }
2637     return anActor;
2638   }
2639   else {
2640     // try mesh actor
2641     SMESH_Actor* anActor = SMESH::FindActorByObject(myMesh);
2642     if (anActor && anActor->hasIO()) {
2643       isActor = true;
2644       if (aViewWindow && !aViewWindow->isVisible(anActor->getIO()))
2645         isActor = false;
2646       else
2647         myActorsList.append(anActor);
2648     }
2649
2650     // try group actor
2651     SMESH_Actor* aGroupActor = 0;
2652     if (!isActor && !myGroup->_is_nil()) {
2653       aGroupActor = SMESH::FindActorByObject(myGroup);
2654       if (aGroupActor && aGroupActor->hasIO())
2655         myActorsList.append(aGroupActor);
2656     }
2657
2658     // try any visible actor of group or sub-mesh of current mesh
2659     if (aViewWindow) {
2660       // mesh entry
2661       _PTR(SObject) aSObject = SMESH::FindSObject(myMesh);
2662       if (aSObject) {
2663         CORBA::String_var meshEntry = aSObject->GetID().c_str();
2664         int len = strlen(meshEntry);
2665
2666         // iterate on all actors in current view window, search for
2667         // any visible actor, that belongs to group or submesh of current mesh
2668         VTK::ActorCollectionCopy aCopy(aViewWindow->getRenderer()->GetActors());
2669         vtkActorCollection *aCollection = aCopy.GetActors();
2670         int nbItems = aCollection->GetNumberOfItems();
2671         for (int i=0; i<nbItems && !isActor; i++)
2672         {
2673           SMESH_Actor *anActor = dynamic_cast<SMESH_Actor*>(aCollection->GetItemAsObject(i));
2674           if (anActor && anActor->hasIO()) {
2675             Handle(SALOME_InteractiveObject) anIO = anActor->getIO();
2676             if (aViewWindow->isVisible(anIO)) {
2677               if (anIO->hasEntry() && strncmp(anIO->getEntry(), meshEntry, len) == 0 && !myActorsList.contains(anActor) )
2678                 myActorsList.append(anActor);
2679             }
2680           }
2681         }
2682       }
2683     }
2684
2685     // Show a standalone group if nothing else is visible (IPAL52227)
2686     if ( myActorsList.count() == 1 &&
2687          myActorsList[0] == aGroupActor &&
2688          aViewWindow && !aViewWindow->isVisible(aGroupActor->getIO()))
2689       SMESH::UpdateView( aViewWindow, SMESH::eDisplay, aGroupActor->getIO()->getEntry() );
2690   }
2691
2692
2693   if (myActorsList.count() > 0) {
2694     QListIterator<SMESH_Actor*> it( myActorsList );
2695     while ( it.hasNext() ) {
2696       SMESH_Actor* anActor = it.next();
2697       if ( IsActorVisible(anActor) )
2698         anActor->SetPickable(true);
2699     }
2700   }
2701
2702   return ( isActor || (myActorsList.count() > 0) );
2703 }
2704
2705 //=======================================================================
2706 //function : setShowEntityMode
2707 //purpose  : make shown only entity corresponding to my type
2708 //=======================================================================
2709 void SMESHGUI_GroupDlg::setShowEntityMode()
2710 {
2711   if ( !myMesh->_is_nil() ) {
2712     if ( SMESH_Actor* actor = SMESH::FindActorByObject(myMesh) ) {
2713       if (!myStoredShownEntity)
2714         myStoredShownEntity = actor->GetEntityMode();
2715       switch ( myTypeId ) {
2716       case grpNodeSelection:   restoreShowEntityMode();                          break;
2717       case grp0DSelection:     actor->SetEntityMode( SMESH_Actor::e0DElements ); break;
2718       case grpBallSelection:   actor->SetEntityMode( SMESH_Actor::eBallElem );   break;
2719       case grpEdgeSelection:   actor->SetEntityMode( SMESH_Actor::eEdges );      break;
2720       case grpFaceSelection:   actor->SetEntityMode( SMESH_Actor::eFaces );      break;
2721       case grpVolumeSelection: actor->SetEntityMode( SMESH_Actor::eVolumes );    break;
2722       }
2723     }
2724   }
2725 }
2726
2727 //=======================================================================
2728 //function : restoreShowEntityMode
2729 //purpose  : restore ShowEntity mode of myActor
2730 //=======================================================================
2731 void SMESHGUI_GroupDlg::restoreShowEntityMode()
2732 {
2733   if ( myStoredShownEntity && !myMesh->_is_nil() ) {
2734     if ( SMESH_Actor* actor = SMESH::FindActorByObject(myMesh) ) {
2735       actor->SetEntityMode(myStoredShownEntity);
2736     }
2737   }
2738   myStoredShownEntity = 0;
2739 }
2740
2741 //=======================================================================
2742 //function : IsActorVisible
2743 //purpose  : return visibility of the actor
2744 //=======================================================================
2745 bool SMESHGUI_GroupDlg::IsActorVisible( SMESH_Actor* theActor )
2746 {
2747   SVTK_ViewWindow* aViewWindow = SMESH::GetCurrentVtkView();
2748   if (theActor && aViewWindow)
2749     return aViewWindow->isVisible(theActor->getIO());
2750   return false;
2751 }
2752
2753 //================================================================
2754 //function : setIsApplyAndClose
2755 //purpose  : Set value of the flag indicating that the dialog is
2756 //           accepted by Apply & Close button
2757 //================================================================
2758 void SMESHGUI_GroupDlg::setIsApplyAndClose( const bool theFlag )
2759 {
2760   myIsApplyAndClose = theFlag;
2761 }
2762
2763 //================================================================
2764 //function : isApplyAndClose
2765 //purpose  : Get value of the flag indicating that the dialog is
2766 //           accepted by Apply & Close button
2767 //================================================================
2768 bool SMESHGUI_GroupDlg::isApplyAndClose() const
2769 {
2770   return myIsApplyAndClose;
2771 }