1 // VISU VISUGUI : GUI of VISU 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 : VisuGUI_Selection.cxx
25 // Author : Laurent CORNABE & Hubert ROLLAND
29 #include "VisuGUI_Selection.h"
31 #include "SALOME_ListIteratorOfListIO.hxx"
32 #include "SALOME_Selection.h"
33 #include "VISU_Actor.h"
34 #include "VISU_PrsObject_i.hh"
35 #include "VISU_Prs3d_i.hh"
36 #include "VISU_PipeLine.hxx"
38 #include "QAD_MessageBox.h"
39 #include "QAD_RightFrame.h"
40 #include "VTKViewer_ViewFrame.h"
42 #include <TColStd_IndexedMapOfInteger.hxx>
51 #include <qhbuttongroup.h>
52 #include <qradiobutton.h>
53 #include <qvalidator.h>
54 #include <qpushbutton.h>
56 #include <vtkDataSetMapper.h>
57 #include <vtkDataSet.h>
58 #include <vtkPointData.h>
59 #include <vtkCellData.h>
62 #include "utilities.h"
66 extern VisuGUI *visuGUI;
67 static QAD_Study* myStudy = NULL;
68 static VisuGUI_SelectionDlg* mySelectionDlg = NULL;
70 VisuGUI_SelectionDlg::VisuGUI_SelectionDlg()
71 : QDialog( QAD_Application::getDesktop(), 0, false,
72 WStyle_Customize | WStyle_NormalBorder | WStyle_Title | WStyle_SysMenu | WDestructiveClose)
75 mySelectionDlg->close(true);
77 setCaption( "Data on elements" );
78 setSizeGripEnabled( TRUE );
80 QGridLayout* TopLayout = new QGridLayout(this);
81 TopLayout->setSpacing(6);
82 TopLayout->setMargin(11);
83 TopLayout->setRowStretch(0, 0);
84 TopLayout->setRowStretch(1, 0);
85 TopLayout->setRowStretch(2, 1);
86 TopLayout->setRowStretch(3, 0);
88 QHButtonGroup* aTypeBox = new QHButtonGroup("Selection", this);
90 QRadioButton* aPointBtn = new QRadioButton("Point", aTypeBox);
91 QRadioButton* aCellBtn = new QRadioButton("Cell", aTypeBox);
92 QRadioButton* aActorBtn = new QRadioButton("Actor", aTypeBox);
93 aPointBtn->setChecked(true);
95 connect(aTypeBox, SIGNAL(clicked(int)), this, SLOT(onSelectionChange(int)));
97 TopLayout->addWidget(aTypeBox, 0, 0);
99 QWidget* aNamePane = new QWidget(this);
100 QGridLayout* aNameLay = new QGridLayout(aNamePane);
102 QLabel* aMeshLbl = new QLabel("Mesh name: ", aNamePane);
103 myMeshName = new QLabel(aNamePane);
105 QLabel* aFieldLbl = new QLabel("Field name: ", aNamePane);
106 myFieldName = new QLabel(aNamePane);
108 aNameLay->addWidget(aMeshLbl, 0, 0);
109 aNameLay->addWidget(myMeshName, 0, 1);
110 aNameLay->addWidget(aFieldLbl, 1, 0);
111 aNameLay->addWidget(myFieldName, 1, 1);
113 TopLayout->addWidget(aNamePane, 1, 0);
115 myWidgetStack = new QWidgetStack(this);
117 // Create Points pane
118 myPointsPane = new QVBox(myWidgetStack);
119 myPointsPane->layout()->setSpacing(6);
121 QGroupBox* aDataGrp = new QGroupBox(2, Qt::Horizontal, "Data of Point", myPointsPane);
122 aDataGrp->layout()->setSpacing(6);
124 QLabel* aIDLbl = new QLabel("ID:", aDataGrp);
125 myIDValLbl = new QLineEdit("", aDataGrp);
126 QIntValidator* aIntValidator = new QIntValidator(myIDValLbl);
127 aIntValidator->setBottom(0);
128 myIDValLbl->setValidator(aIntValidator);
129 connect(myIDValLbl, SIGNAL(textChanged(const QString&)), this, SLOT(onPointIdEdit(const QString&)));
131 QLabel* aValueLbl = new QLabel("Scalar Value:", aDataGrp);
132 myScalarValLbl = new QLabel("", aDataGrp);
133 QLabel* aVectorLbl = new QLabel("Vector Value:", aDataGrp);
134 myVectorValLbl = new QLabel("", aDataGrp);
135 myVectorValLbl->setMinimumWidth(150);
137 QGroupBox* aCoordGrp = new QGroupBox(2, Qt::Horizontal, "Coordinates", myPointsPane);
138 aCoordGrp->layout()->setSpacing(6);
139 QLabel* aXLbl = new QLabel("X:", aCoordGrp);
140 myXValLbl = new QLabel("", aCoordGrp);
141 QLabel* aYLbl = new QLabel("Y:", aCoordGrp);
142 myYValLbl = new QLabel("", aCoordGrp);
143 QLabel* aZLbl = new QLabel("Z:",aCoordGrp );
144 myZValLbl = new QLabel("", aCoordGrp);
147 myWidgetStack->addWidget(myPointsPane, 0);
150 myCellsPane = new QWidget(myWidgetStack);
151 QGridLayout* aCellLayout = new QGridLayout(myCellsPane);
152 aCellLayout->setSpacing(6);
153 aCellLayout->setRowStretch(0, 0);
154 aCellLayout->setRowStretch(1, 1);
156 QGroupBox* aCellGrp = new QGroupBox(2, Qt::Horizontal, "Data of Cell", myCellsPane);
158 QLabel* aCellIDLbl = new QLabel("ID:", aCellGrp);
159 myCellIDValLbl = new QLineEdit("", aCellGrp);
160 myCellIDValLbl->setValidator(aIntValidator);
161 connect(myCellIDValLbl, SIGNAL(textChanged(const QString&)), this, SLOT(onCellIdEdit(const QString&)));
163 QLabel* aCellValueLbl = new QLabel("Scalar Value:", aCellGrp);
164 myCellScalarValLbl = new QLabel("", aCellGrp);
165 QLabel* aCellVectorLbl = new QLabel("Vector Value:", aCellGrp);
166 myCellVectorValLbl = new QLabel("", aCellGrp);
168 aCellLayout->addWidget(aCellGrp, 0, 0);
170 myListPoints = new QTable(myCellsPane);
171 myListPoints->setReadOnly(true);
172 myListPoints->setNumCols(6);
173 myListPoints->setNumRows(0);
174 myListPoints->setColumnWidth(0, 40);
175 myListPoints->setColumnWidth(1, 40);
176 myListPoints->setColumnWidth(2, 40);
177 myListPoints->setColumnWidth(3, 40);
178 myListPoints->setSelectionMode(QTable::NoSelection);
179 QHeader* aHeader = myListPoints->horizontalHeader();
180 aHeader->setLabel( 0, "ID" );
181 aHeader->setLabel( 1, "X" );
182 aHeader->setLabel( 2, "Y" );
183 aHeader->setLabel( 3, "Z" );
184 aHeader->setLabel( 4, "Scalar" );
185 aHeader->setLabel( 5, "Vector" );
187 aCellLayout->addWidget(myListPoints, 1, 0);
189 myWidgetStack->addWidget(myCellsPane, 1);
192 myActorsPane = new QVBox(myWidgetStack);
193 myActorsPane->layout()->setSpacing(6);
195 QGroupBox* aPosGrp = new QGroupBox(2, Qt::Horizontal, "Position", myActorsPane);
196 aPosGrp->layout()->setSpacing(6);
197 QLabel* aXPosLbl = new QLabel("X:", aPosGrp);
198 myXPosLbl = new QLabel("0", aPosGrp);
199 QLabel* aYPosLbl = new QLabel("Y:", aPosGrp);
200 myYPosLbl = new QLabel("0", aPosGrp);
201 QLabel* aZPosLbl = new QLabel("Z:", aPosGrp);
202 myZPosLbl = new QLabel("0", aPosGrp);
204 QGroupBox* aSizeGrp = new QGroupBox(2, Qt::Horizontal, "Size", myActorsPane);
205 aSizeGrp->layout()->setSpacing(6);
206 QLabel* aXSizeLbl = new QLabel("dX:", aSizeGrp);
207 myDXLbl = new QLabel("0", aSizeGrp);
208 QLabel* aYSizeLbl = new QLabel("dY:", aSizeGrp);
209 myDYLbl = new QLabel("0", aSizeGrp);
210 QLabel* aZSizeLbl = new QLabel("dZ:",aSizeGrp );
211 myDZLbl = new QLabel("0", aSizeGrp);
213 myWidgetStack->addWidget(myActorsPane, 2);
216 TopLayout->addWidget(myWidgetStack, 2, 0);
218 // Create buttons group
219 QHBox* aBtnBox = new QHBox(this);
220 QHBoxLayout* aBtnLayout = (QHBoxLayout*)aBtnBox->layout();
221 aBtnLayout->addStretch();
223 QPushButton* aCloseBtn = new QPushButton(tr("BUT_CLOSE"), aBtnBox);
224 connect(aCloseBtn, SIGNAL(clicked()), this, SLOT(close()));
226 TopLayout->addWidget(aBtnBox, 3, 0);
228 myStudy = visuGUI->GetActiveStudy();
229 mySelection = SALOME_Selection::Selection(myStudy->getSelection());
230 connect(mySelection, SIGNAL(currentSelectionChanged()), this, SLOT(onSelectionEvent()));
232 connect(visuGUI, SIGNAL(SignalCloseAllDialogs()), this, SLOT(close()));
235 onSelectionChange(0);
237 mySelectionDlg = this;
241 void VisuGUI_SelectionDlg::onSelectionChange(int theId) {
245 myWidgetStack->raiseWidget(myPointsPane);
246 QAD_Application::getDesktop()->SetSelectionMode(NodeSelection, true);
247 onPointIdEdit(myIDValLbl->text());
250 myWidgetStack->raiseWidget(myCellsPane);
251 QAD_Application::getDesktop()->SetSelectionMode(CellSelection, true);
252 onCellIdEdit(myCellIDValLbl->text());
255 myWidgetStack->raiseWidget(myActorsPane);
256 QAD_Application::getDesktop()->SetSelectionMode(ActorSelection, true);
259 // if (VTKViewer_ViewFrame* vf = visuGUI->GetVtkViewFrame())
264 void VisuGUI_SelectionDlg::closeEvent(QCloseEvent* theEvent) {
265 mySelectionDlg = NULL;
266 myStudy->getActiveStudyFrame()->getRightFrame()->getViewFrame()->SetSelectionMode( ActorSelection );
267 QAD_Application::getDesktop()->SetSelectionMode(ActorSelection, true);
268 disconnect(mySelection,0,0,0);
269 QDialog::closeEvent(theEvent);
272 template<class TData> QString getValue(TData* theData, int theId){
273 if (vtkDataArray *aScalar = theData->GetScalars()){
274 float aVal = aScalar->GetTuple1(theId);
275 return QString::number(aVal);
277 return QString("No data");
281 template<class TData> QString getVector(TData* theData, int theId){
282 if (vtkDataArray *aVector = theData->GetVectors()) {
283 float *aVal = aVector->GetTuple3(theId);
284 return QString("%1; %2; %3").arg(aVal[0]).arg(aVal[1]).arg(aVal[2]);
286 return QString("No data");
291 #define ABS(a) (a>=0)?a:-a
293 void VisuGUI_SelectionDlg::onSelectionEvent() {
296 Handle(SALOME_InteractiveObject) anIO;
297 int aType = myWidgetStack->id(myWidgetStack->visibleWidget());
298 if(VISU::Prs3d_i* aPrs3d = visuGUI->GetSelectedPrs3d(&anIO)){
299 SALOMEDS::SObject_var aSObject = visuGUI->GetStudyDocument()->FindObjectID(anIO->getEntry());
300 QString aMeshName = VisuGUI::getValue(aSObject, "myMeshName");
301 QString aFieldName = VisuGUI::getValue(aSObject, "myFieldName");
302 myMeshName->setText((aMeshName == "NULL")? QString("No name") : aMeshName);
303 myFieldName->setText((aFieldName == "NULL")? QString("No name") : aFieldName);
305 VISU_Actor* anVISUActor = visuGUI->GetActor(aPrs3d);
308 anVISUActor->GetBounds(aCoord);
309 myXPosLbl->setText(QString::number( aCoord[0] ));
310 myYPosLbl->setText(QString::number( aCoord[2] ));
311 myZPosLbl->setText(QString::number( aCoord[4] ));
313 myDXLbl->setText(QString::number( ABS(aCoord[1]-aCoord[0]) ));
314 myDYLbl->setText(QString::number( ABS(aCoord[3]-aCoord[2]) ));
315 myDZLbl->setText(QString::number( ABS(aCoord[5]-aCoord[4]) ));
318 TColStd_IndexedMapOfInteger aMapIndex;
319 typedef map<int,float*> PointsMap;
320 PointsMap aPointsMap;
321 mySelection->GetIndex(anIO, aMapIndex);
323 VISU_Actor* anActor = visuGUI->GetActor(aPrs3d);
326 vtkDataSet* aDataSet = anActor->GetInput();
327 vtkPointData* aPntData = aDataSet->GetPointData();
329 for ( int ind = 1; ind <= aMapIndex.Extent(); ind++){
330 int aID = aMapIndex( ind );
336 aDataSet->GetPoint(aID, aCoord);
337 myXValLbl->setText( QString::number( aCoord[0] ) );
338 myYValLbl->setText( QString::number( aCoord[1] ) );
339 myZValLbl->setText( QString::number( aCoord[2] ) );
340 myIDValLbl->setText( QString::number(aID) );
341 myScalarValLbl->setText(getValue(aPntData, aID));
342 myVectorValLbl->setText(getVector(aPntData, aID));
344 //qApp->processEvents();
349 //int aMaxId = aDataSet->GetNumberOfCells();
350 //cout<<"### MaxId="<<aMaxId<<endl;
351 //cout<<"### SelectedId="<<aID<<endl;
352 vtkCellData* aData = aDataSet->GetCellData();
353 vtkCell* aCell = aDataSet->GetCell(aID);
355 int aNbOfPoints = aCell->GetNumberOfPoints();
356 if (aNbOfPoints <=1 ) { // Cell is point
360 myCellIDValLbl->setText( QString::number(aID) );
361 myCellScalarValLbl->setText(getValue(aData, aID));
362 myCellVectorValLbl->setText(getVector(aData, aID));
365 vtkIdList *aPointList = aCell->GetPointIds();
366 QListViewItem* anItem = NULL;
368 for(int i = 0; i < aNbOfPoints; i++){
369 int idCurrent = aPointList->GetId(i);
370 aCoord = aDataSet->GetPoint(idCurrent);
371 aPointsMap.insert(PointsMap::value_type(idCurrent,aCoord));
380 myListPoints->setNumRows(aPointsMap.size());
381 PointsMap::const_iterator It = aPointsMap.begin();
382 for(int i=0; It!=aPointsMap.end()&&i<myListPoints->numRows() ; It++,i++){
383 myListPoints->verticalHeader()->setLabel(i, QString::number( i ));
385 myListPoints->setText(i, 0, QString::number( id ));
386 float* aCoord = It->second;
387 myListPoints->setText(i, 1, QString::number( aCoord[0] ));
388 myListPoints->setText(i, 2, QString::number( aCoord[1] ));
389 myListPoints->setText(i, 3, QString::number( aCoord[2] ));
390 myListPoints->setText(i, 4, getValue(aPntData, id));
391 myListPoints->setText(i, 5, getVector(aPntData, id));
402 void VisuGUI_SelectionDlg::clearFields() {
403 int aType = myWidgetStack->id(myWidgetStack->visibleWidget());
406 myXValLbl->setText( "" );
407 myYValLbl->setText( "" );
408 myZValLbl->setText( "" );
409 myIDValLbl->setText( "" );
410 myScalarValLbl->setText("");
411 myVectorValLbl->setText("");
414 myCellIDValLbl->setText( "" );
415 myCellScalarValLbl->setText("");
416 myCellVectorValLbl->setText("");
417 myListPoints->setNumRows(0);
420 myXPosLbl->setText("");
421 myYPosLbl->setText("");
422 myZPosLbl->setText("");
423 myDXLbl->setText("");
424 myDYLbl->setText("");
425 myDZLbl->setText("");
429 typedef vtkIdType (vtkDataSet::* TDataSetMethod)();
431 bool onIdEdit(const QString& theText,
432 TDataSetMethod theMethod,
434 SALOME_Selection* theSelection,
437 QLabel* theFieldName)
439 Handle(SALOME_InteractiveObject) anIO;
440 if(VISU::Prs3d_i* aPrs3d = visuGUI->GetSelectedPrs3d(&anIO)){
441 int anId = theText.toInt();
442 vtkDataSet* aDataSet = aPrs3d->GetPL()->GetMapper()->GetInput();
443 int aMaxId = (aDataSet->*theMethod)();
444 if(anId < 0) anId = 0;
445 if(anId >= aMaxId) anId = aMaxId-1;
446 theSelection->ClearIObjects();
447 theSelection->AddIObject(anIO);
448 theSelection->AddOrRemoveIndex( anIO, anId, false );
451 theMeshName->setText(theValue);
452 theFieldName->setText("");
457 void VisuGUI_SelectionDlg::onPointIdEdit(const QString& theText){
459 TDataSetMethod aMethod = &vtkDataSet::GetNumberOfPoints;
460 bool anIsSelected = onIdEdit(theText,aMethod,false,mySelection,
461 myMeshName,tr("WRN_NO_AVAILABLE_DATA"),
467 void VisuGUI_SelectionDlg::onCellIdEdit(const QString& theText){
469 TDataSetMethod aMethod = &vtkDataSet::GetNumberOfCells;
470 bool anIsSelected = onIdEdit(theText,aMethod,true,mySelection,
471 myMeshName,tr("WRN_NO_AVAILABLE_DATA"),