1 // SMESH SMESHGUI : GUI for SMESH component
3 // Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
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.
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.
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
20 // See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
24 // File : SMESHGUI_NodesDlg.cxx
25 // Author : Nicolas REJNERI
29 #include "SMESHGUI_NodesDlg.h"
32 #include "SMESHGUI_Utils.h"
33 #include "SMESHGUI_MeshUtils.h"
35 #include "SMESHGUI_VTKUtils.h"
36 #include "SMESH_ActorUtils.h"
38 #include "VTKViewer_ViewFrame.h"
39 #include "SALOME_Actor.h"
41 #include "SMESHGUI_SpinBox.h"
43 #include "QAD_Application.h"
44 #include "QAD_Desktop.h"
45 #include "QAD_WaitCursor.h"
46 #include "QAD_MessageBox.h"
48 #include "SMESH_Actor.h"
49 #include "SMESH_ObjectDef.h"
51 #include "SMDS_Mesh.hxx"
52 #include "SMDS_MeshNode.hxx"
56 #include <vtkIdList.h>
57 #include <vtkIntArray.h>
58 #include <vtkCellArray.h>
59 #include <vtkUnsignedCharArray.h>
60 #include <vtkUnstructuredGrid.h>
61 #include <vtkDataSetMapper.h>
62 #include <vtkActorCollection.h>
63 #include <vtkRenderer.h>
66 #include <qbuttongroup.h>
68 #include <qgroupbox.h>
70 #include <qlineedit.h>
71 #include <qpushbutton.h>
72 #include <qradiobutton.h>
76 #include <qwhatsthis.h>
79 #include <qvalidator.h>
82 #include "utilities.h"
89 void AddNode(SMESH::SMESH_Mesh_ptr theMesh, float x, float y, float z){
92 SALOMEDS::SObject_var aSobj = SMESH::FindSObject(theMesh);
93 CORBA::String_var anEntry = aSobj->GetID();
94 SMESH::SMESH_MeshEditor_var aMeshEditor = theMesh->GetMeshEditor();
95 aMeshEditor->AddNode(x,y,z);
96 SALOMEDS::Study_var aStudy = GetActiveStudyDocument();
97 CORBA::Long anId = aStudy->StudyId();
98 if(TVisualObjPtr aVisualObj = SMESH::GetVisualObj(anId,anEntry.in())){
99 aVisualObj->Update(true);
101 }catch(SALOME::SALOME_Exception& exc) {
102 INFOS("Follow exception was cought:\n\t"<<exc.details.text);
103 }catch(const std::exception& exc){
104 INFOS("Follow exception was cought:\n\t"<<exc.what());
106 INFOS("Unknown exception was cought !!!");
111 class TNodeSimulation{
113 QAD_StudyFrame* myStudyFrame;
114 VTKViewer_ViewFrame* myViewFrame;
116 SALOME_Actor *myPreviewActor;
117 vtkDataSetMapper* myMapper;
122 TNodeSimulation(QAD_Study* theStudy):
124 myStudyFrame(theStudy->getActiveStudyFrame()),
125 myViewFrame(GetVtkViewFrame(theStudy->getActiveStudyFrame()))
127 vtkUnstructuredGrid* aGrid = vtkUnstructuredGrid::New();
130 myPoints = vtkPoints::New();
131 myPoints->SetNumberOfPoints( 1 );
132 myPoints->SetPoint(0,0.0,0.0,0.0);
135 vtkIdList *anIdList = vtkIdList::New();
136 anIdList->SetNumberOfIds( 1 );
138 vtkCellArray *aCells = vtkCellArray::New();
139 aCells->Allocate( 2, 0 );
141 vtkUnsignedCharArray* aCellTypesArray = vtkUnsignedCharArray::New();
142 aCellTypesArray->SetNumberOfComponents( 1 );
143 aCellTypesArray->Allocate( 1 );
145 anIdList->SetId( 0, 0 );
146 aCells->InsertNextCell( anIdList );
147 aCellTypesArray->InsertNextValue( VTK_VERTEX );
149 vtkIntArray* aCellLocationsArray = vtkIntArray::New();
150 aCellLocationsArray->SetNumberOfComponents( 1 );
151 aCellLocationsArray->SetNumberOfTuples( 1 );
153 aCells->InitTraversal();
155 aCellLocationsArray->SetValue( 0, aCells->GetTraversalLocation( npts ) );
157 aGrid->SetCells( aCellTypesArray, aCellLocationsArray, aCells );
159 aGrid->SetPoints( myPoints );
160 aGrid->SetCells( aCellTypesArray, aCellLocationsArray,aCells );
161 aCellLocationsArray->Delete();
162 aCellTypesArray->Delete();
166 // Create and display actor
167 myMapper = vtkDataSetMapper::New();
168 myMapper->SetInput( aGrid );
171 myPreviewActor = SALOME_Actor::New();
172 myPreviewActor->SetInfinitive(true);
173 myPreviewActor->VisibilityOff();
174 myPreviewActor->PickableOff();
175 myPreviewActor->SetMapper( myMapper );
177 vtkProperty* aProp = vtkProperty::New();
178 aProp->SetRepresentationToPoints();
181 anRGB[0] = GetFloat("SMESH:SettingsNodeColorRed",0)/255.;
182 anRGB[1] = GetFloat("SMESH:SettingsNodeColorGreen",255)/255.;
183 anRGB[2] = GetFloat("SMESH:SettingsNodeColorBlue",0)/255.;
184 aProp->SetColor(anRGB[0],anRGB[1],anRGB[2]);
186 float aPointSize = GetFloat("SMESH:SettingsNodesSize",3);
187 aProp->SetPointSize(aPointSize);
189 myPreviewActor->SetProperty( aProp );
192 myViewFrame->AddActor( myPreviewActor );
197 void SetPosition(float x, float y, float z){
198 myPoints->SetPoint(0,x,y,z);
199 myPoints->Modified();
204 void SetVisibility(bool theVisibility){
205 myPreviewActor->SetVisibility(theVisibility);
206 RepaintCurrentView();
211 if(FindVtkViewFrame(myStudy,myStudyFrame)){
212 myViewFrame->RemoveActor(myPreviewActor);
214 myPreviewActor->Delete();
216 myMapper->RemoveAllInputs();
227 //=================================================================================
228 // class : SMESHGUI_NodesDlg()
230 //=================================================================================
231 SMESHGUI_NodesDlg::SMESHGUI_NodesDlg( QWidget* parent,
233 SALOME_Selection* Sel,
236 : QDialog( parent, name, modal, WStyle_Customize | WStyle_NormalBorder | WStyle_Title | WStyle_SysMenu |
237 Qt::WDestructiveClose)
239 mySimulation = new SMESH::TNodeSimulation(SMESH::GetActiveStudy());
241 QPixmap image0(QAD_Desktop::getResourceManager()->loadPixmap( "SMESH",tr("ICON_DLG_NODE")));
243 setName( "SMESHGUI_NodesDlg" );
245 setCaption( tr( "MESH_NODE_TITLE" ) );
246 setSizeGripEnabled( TRUE );
247 SMESHGUI_NodesDlgLayout = new QGridLayout( this );
248 SMESHGUI_NodesDlgLayout->setSpacing( 6 );
249 SMESHGUI_NodesDlgLayout->setMargin( 11 );
251 /***************************************************************/
252 GroupButtons = new QGroupBox( this, "GroupButtons" );
253 GroupButtons->setGeometry( QRect( 10, 10, 281, 48 ) );
254 GroupButtons->setTitle( tr( "" ) );
255 GroupButtons->setColumnLayout(0, Qt::Vertical );
256 GroupButtons->layout()->setSpacing( 0 );
257 GroupButtons->layout()->setMargin( 0 );
258 GroupButtonsLayout = new QGridLayout( GroupButtons->layout() );
259 GroupButtonsLayout->setAlignment( Qt::AlignTop );
260 GroupButtonsLayout->setSpacing( 6 );
261 GroupButtonsLayout->setMargin( 11 );
262 buttonCancel = new QPushButton( GroupButtons, "buttonCancel" );
263 buttonCancel->setText( tr( "SMESH_BUT_CLOSE" ) );
264 buttonCancel->setAutoDefault( TRUE );
265 GroupButtonsLayout->addWidget( buttonCancel, 0, 3 );
266 buttonApply = new QPushButton( GroupButtons, "buttonApply" );
267 buttonApply->setText( tr( "SMESH_BUT_APPLY" ) );
268 buttonApply->setAutoDefault( TRUE );
269 GroupButtonsLayout->addWidget( buttonApply, 0, 1 );
270 QSpacerItem* spacer_9 = new QSpacerItem( 20, 20, QSizePolicy::Expanding, QSizePolicy::Minimum );
271 GroupButtonsLayout->addItem( spacer_9, 0, 2 );
272 buttonOk = new QPushButton( GroupButtons, "buttonOk" );
273 buttonOk->setText( tr( "SMESH_BUT_OK" ) );
274 buttonOk->setAutoDefault( TRUE );
275 buttonOk->setDefault( TRUE );
276 GroupButtonsLayout->addWidget( buttonOk, 0, 0 );
277 SMESHGUI_NodesDlgLayout->addWidget( GroupButtons, 2, 0 );
279 /***************************************************************/
280 GroupConstructors = new QButtonGroup( this, "GroupConstructors" );
281 GroupConstructors->setTitle( tr( "MESH_NODE" ) );
282 GroupConstructors->setExclusive( TRUE );
283 GroupConstructors->setColumnLayout(0, Qt::Vertical );
284 GroupConstructors->layout()->setSpacing( 0 );
285 GroupConstructors->layout()->setMargin( 0 );
286 GroupConstructorsLayout = new QGridLayout( GroupConstructors->layout() );
287 GroupConstructorsLayout->setAlignment( Qt::AlignTop );
288 GroupConstructorsLayout->setSpacing( 6 );
289 GroupConstructorsLayout->setMargin( 11 );
290 Constructor1 = new QRadioButton( GroupConstructors, "Constructor1" );
291 Constructor1->setText( tr( "" ) );
292 Constructor1->setPixmap( image0 );
293 Constructor1->setChecked( TRUE );
294 GroupConstructorsLayout->addWidget( Constructor1, 0, 0 );
295 QSpacerItem* spacer_2 = new QSpacerItem( 20, 20, QSizePolicy::Expanding, QSizePolicy::Minimum );
296 GroupConstructorsLayout->addItem( spacer_2, 0, 1 );
297 SMESHGUI_NodesDlgLayout->addWidget( GroupConstructors, 0, 0 );
299 /***************************************************************/
300 GroupCoordinates = new QGroupBox( this, "GroupCoordinates" );
301 GroupCoordinates->setTitle( tr( "SMESH_COORDINATES" ) );
302 GroupCoordinates->setColumnLayout(0, Qt::Vertical );
303 GroupCoordinates->layout()->setSpacing( 0 );
304 GroupCoordinates->layout()->setMargin( 0 );
305 GroupCoordinatesLayout = new QGridLayout( GroupCoordinates->layout() );
306 GroupCoordinatesLayout->setAlignment( Qt::AlignTop );
307 GroupCoordinatesLayout->setSpacing( 6 );
308 GroupCoordinatesLayout->setMargin( 11 );
309 TextLabel_X = new QLabel( GroupCoordinates, "TextLabel_X" );
310 TextLabel_X->setText( tr( "SMESH_X" ) );
311 GroupCoordinatesLayout->addWidget( TextLabel_X, 0, 0 );
312 TextLabel_Y = new QLabel( GroupCoordinates, "TextLabel_Y" );
313 TextLabel_Y->setText( tr( "SMESH_Y" ) );
314 GroupCoordinatesLayout->addWidget( TextLabel_Y, 0, 2 );
316 TextLabel_Z = new QLabel( GroupCoordinates, "TextLabel_Z" );
317 TextLabel_Z->setText( tr( "SMESH_Z" ) );
318 GroupCoordinatesLayout->addWidget( TextLabel_Z, 0, 4 );
320 SpinBox_X = new SMESHGUI_SpinBox( GroupCoordinates, "SpinBox_X" ) ;
321 GroupCoordinatesLayout->addWidget( SpinBox_X, 0, 1 );
323 SpinBox_Y = new SMESHGUI_SpinBox( GroupCoordinates, "SpinBox_Y" ) ;
324 GroupCoordinatesLayout->addWidget( SpinBox_Y, 0, 3 );
326 SpinBox_Z = new SMESHGUI_SpinBox( GroupCoordinates, "SpinBox_Z" ) ;
327 GroupCoordinatesLayout->addWidget( SpinBox_Z, 0, 5 );
329 SMESHGUI_NodesDlgLayout->addWidget( GroupCoordinates, 1, 0 );
331 /* Initialisation and display */
336 //=======================================================================
337 // function : ~SMESHGUI_NodesDlg()
338 // purpose : Destructor
339 //=======================================================================
340 SMESHGUI_NodesDlg::~SMESHGUI_NodesDlg()
346 //=================================================================================
349 //=================================================================================
350 void SMESHGUI_NodesDlg::Init(SALOME_Selection* Sel)
352 /* Get setting of step value from file configuration */
354 // QString St = QAD_CONFIG->getSetting( "xxxxxxxxxxxxx" ) ; TODO
355 // step = St.toDouble() ; TODO
358 /* min, max, step and decimals for spin boxes */
359 SpinBox_X->RangeStepAndValidator( -999.999, +999.999, step, 3 ) ;
360 SpinBox_Y->RangeStepAndValidator( -999.999, +999.999, step, 3 ) ;
361 SpinBox_Z->RangeStepAndValidator( -999.999, +999.999, step, 3 ) ;
362 SpinBox_X->SetValue( 0.0 ) ;
363 SpinBox_Y->SetValue( 0.0 ) ;
364 SpinBox_Z->SetValue( 0.0 ) ;
367 myMeshGUI = SMESHGUI::GetSMESHGUI() ;
368 myMeshGUI->SetActiveDialogBox( (QDialog*)this ) ;
370 /* signals and slots connections */
371 connect( buttonOk, SIGNAL( clicked() ), this, SLOT( ClickOnOk() ) );
372 connect( buttonCancel, SIGNAL( clicked() ), this, SLOT( ClickOnCancel() ) );
373 connect( buttonApply, SIGNAL( clicked() ), this, SLOT(ClickOnApply() ) );
375 connect( SpinBox_X, SIGNAL ( valueChanged(double) ), SLOT( ValueChangedInSpinBox(double) )) ;
376 connect( SpinBox_Y, SIGNAL ( valueChanged(double) ), SLOT( ValueChangedInSpinBox(double) )) ;
377 connect( SpinBox_Z, SIGNAL ( valueChanged(double) ), SLOT( ValueChangedInSpinBox(double) )) ;
379 connect( mySelection, SIGNAL( currentSelectionChanged() ), SLOT( SelectionIntoArgument() ));
380 connect( myMeshGUI, SIGNAL ( SignalDeactivateActiveDialog() ), SLOT( DeactivateActiveDialog() )) ;
381 /* to close dialog if study frame change */
382 connect( myMeshGUI, SIGNAL ( SignalStudyFrameChanged() ), SLOT( ClickOnCancel() ) ) ;
384 /* Move widget on the botton right corner of main widget */
386 myMeshGUI->DefineDlgPosition( this, x, y ) ;
390 // set selection mode
391 SMESH::SetPointRepresentation(true);
392 QAD_Application::getDesktop()->SetSelectionMode( NodeSelection, true );
394 SelectionIntoArgument();
397 //=================================================================================
398 // function : ValueChangedInSpinBox()
400 //=================================================================================
401 void SMESHGUI_NodesDlg::ValueChangedInSpinBox( double newValue )
403 if(!myMesh->_is_nil()){
404 double vx = SpinBox_X->GetValue() ;
405 double vy = SpinBox_Y->GetValue() ;
406 double vz = SpinBox_Z->GetValue() ;
408 mySimulation->SetPosition(vx,vy,vz);
413 //=================================================================================
414 // function : ClickOnOk()
416 //=================================================================================
417 void SMESHGUI_NodesDlg::ClickOnOk()
419 if ( ClickOnApply() )
423 //=======================================================================
424 // function : ClickOnApply()
426 //=======================================================================
427 bool SMESHGUI_NodesDlg::ClickOnApply()
429 if (myMeshGUI->ActiveStudyLocked())
432 if ( myMesh->_is_nil() ) {
433 QAD_MessageBox::warn1(QAD_Application::getDesktop(),
434 tr("SMESH_WRN_WARNING"),
435 tr("MESH_IS_NOT_SELECTED"),
440 /* Recup args and call method */
441 double x = SpinBox_X->GetValue() ;
442 double y = SpinBox_Y->GetValue() ;
443 double z = SpinBox_Z->GetValue() ;
444 mySimulation->SetVisibility(false);
445 SMESH::AddNode(myMesh,x,y,z) ;
446 SMESH::SetPointRepresentation(true);
449 if ( mySelection->IObjectCount() != 1 ) {
450 if(VTKViewer_ViewFrame* aViewFrame = SMESH::GetCurrentVtkView()) {
451 vtkActorCollection *aCollection = aViewFrame->getRenderer()->GetActors();
452 aCollection->InitTraversal();
453 while(vtkActor *anAct = aCollection->GetNextActor()){
454 if(SMESH_Actor *anActor = dynamic_cast<SMESH_Actor*>(anAct))
456 if(SMESH_MeshObj *aMeshObj = dynamic_cast<SMESH_MeshObj*>(anActor->GetObject().get()))
457 if(myMesh->_is_equivalent( aMeshObj->GetMeshServer() ))
459 mySelection->ClearIObjects();
460 mySelection->AddIObject( anActor->getIO(), false );
470 //=======================================================================
471 // function : ClickOnCancel()
473 //=======================================================================
474 void SMESHGUI_NodesDlg::ClickOnCancel()
476 mySelection->ClearIObjects();
477 mySimulation->SetVisibility(false);
478 SMESH::SetPointRepresentation(false);
479 QAD_Application::getDesktop()->SetSelectionMode( ActorSelection );
480 disconnect( mySelection, 0, this, 0 );
481 myMeshGUI->ResetState();
487 //=================================================================================
488 // function : SelectionIntoArgument()
489 // purpose : Called when selection as changed or other case
490 //=================================================================================
491 void SMESHGUI_NodesDlg::SelectionIntoArgument()
493 if ( !GroupConstructors->isEnabled() )
496 mySimulation->SetVisibility(false);
497 SMESH::SetPointRepresentation(true);
499 if(mySelection->IObjectCount() == 1){
500 Handle(SALOME_InteractiveObject) anIO = mySelection->firstIObject();
501 if(anIO->hasEntry()){
502 myMesh = SMESH::GetMeshByIO(anIO);
503 if(myMesh->_is_nil()) return;
505 if(SMESH::GetNameOfSelectedNodes( mySelection, aText ) == 1){
506 if(SMESH_Actor* anActor = SMESH::FindActorByObject(myMesh.in())){
507 if(SMDS_Mesh* aMesh = anActor->GetObject()->GetMesh()){
508 if(const SMDS_MeshNode* aNode = aMesh->FindNode(aText.toInt())){
509 SpinBox_X->SetValue( aNode->X() );
510 SpinBox_Y->SetValue( aNode->Y() ) ;
511 SpinBox_Z->SetValue( aNode->Z() ) ;
516 mySimulation->SetPosition(SpinBox_X->GetValue(),
517 SpinBox_Y->GetValue(),
518 SpinBox_Z->GetValue());
524 //=======================================================================
525 // function : closeEvent()
527 //=======================================================================
528 void SMESHGUI_NodesDlg::closeEvent(QCloseEvent* e)
530 this->ClickOnCancel() ; /* same than click on cancel button */
533 //=======================================================================
534 //function : hideEvent
535 //purpose : caused by ESC key
536 //=======================================================================
538 void SMESHGUI_NodesDlg::hideEvent ( QHideEvent * e )
540 if ( !isMinimized() )
544 //=================================================================================
545 // function : enterEvent()
546 // purpose : to reactivate this dialog box when mouse enter onto the window
547 //=================================================================================
548 void SMESHGUI_NodesDlg::enterEvent( QEvent* e)
550 if ( !GroupConstructors->isEnabled() )
551 ActivateThisDialog() ;
555 //=================================================================================
556 // function : DeactivateActiveDialog()
557 // purpose : public slot to deactivate if active
558 //=================================================================================
559 void SMESHGUI_NodesDlg::DeactivateActiveDialog()
561 if ( GroupConstructors->isEnabled() ) {
562 GroupConstructors->setEnabled(false) ;
563 GroupCoordinates->setEnabled(false) ;
564 GroupButtons->setEnabled(false) ;
565 mySimulation->SetVisibility(false) ;
566 myMeshGUI->ResetState() ;
567 myMeshGUI->SetActiveDialogBox(0) ;
572 //=================================================================================
573 // function : ActivateThisDialog()
575 //=================================================================================
576 void SMESHGUI_NodesDlg::ActivateThisDialog( )
578 myMeshGUI->EmitSignalDeactivateDialog() ;
579 GroupConstructors->setEnabled(true) ;
580 GroupCoordinates->setEnabled(true) ;
581 GroupButtons->setEnabled(true) ;
583 SMESH::SetPointRepresentation(true);
584 QAD_Application::getDesktop()->SetSelectionMode( NodeSelection, true );
586 SelectionIntoArgument();