Salome HOME
Update from BR_V5_DEV 13Feb2009
[modules/gui.git] / src / SVTK / SVTK_SetRotationPointDlg.cxx
1 //  Copyright (C) 2007-2008  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 //  Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 //  This library is free software; you can redistribute it and/or
7 //  modify it under the terms of the GNU Lesser General Public
8 //  License as published by the Free Software Foundation; either
9 //  version 2.1 of the License.
10 //
11 //  This library is distributed in the hope that it will be useful,
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 //  Lesser General Public License for more details.
15 //
16 //  You should have received a copy of the GNU Lesser General Public
17 //  License along with this library; if not, write to the Free Software
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 //  See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22 //  SALOME VTKViewer : build VTK viewer into Salome desktop
23 //  File   : 
24 //  Author : 
25 //  Module : SALOME
26 //  $Header$
27 //
28 #include "SVTK_SetRotationPointDlg.h"
29 #include "SVTK_ViewWindow.h"
30 #include "SVTK_RenderWindowInteractor.h"
31 #include "SVTK_Event.h"
32 #include "SVTK_InteractorStyle.h"
33
34 #include "VTKViewer_Utilities.h"
35
36 #include "QtxAction.h"
37
38 #include <QLineEdit>
39 #include <QGroupBox>
40 #include <QLabel>
41 #include <QPushButton>
42 #include <QGridLayout>
43 #include <QDoubleValidator>
44 #include <QCheckBox>
45
46 #include <vtkCallbackCommand.h>
47
48 using namespace std;
49
50 /*!
51   Constructor
52 */
53 SVTK_SetRotationPointDlg
54 ::SVTK_SetRotationPointDlg(QtxAction* theAction,
55                            SVTK_ViewWindow* theParent,
56                            const char* theName):
57   SVTK_DialogBase(theAction,
58                   theParent, 
59                   theName),
60   myMainWindow(theParent),
61   myPriority(0.0),
62   myEventCallbackCommand(vtkCallbackCommand::New()),
63   myRWInteractor(theParent->GetInteractor())
64 {
65   setWindowTitle(tr("DLG_TITLE"));
66   setSizeGripEnabled(TRUE);
67
68   // Create layout for this dialog
69   QGridLayout* layoutDlg = new QGridLayout (this);
70   layoutDlg->setSpacing(6);
71   layoutDlg->setMargin(11);
72
73   // Create check box "Use Bounding Box Center"
74   QHBoxLayout* aCheckBox = new QHBoxLayout;
75
76   myIsBBCenter = new QCheckBox(tr("USE_BBCENTER"));
77   myIsBBCenter->setChecked(true);
78   aCheckBox->addWidget(myIsBBCenter);
79   connect(myIsBBCenter, SIGNAL(stateChanged(int)), SLOT(onBBCenterChecked()));
80
81   // Create croup button with radio buttons
82   myGroupBoxSel = new QGroupBox( "", this );
83   QVBoxLayout *vbox = new QVBoxLayout( myGroupBoxSel );
84   vbox->setMargin(11);
85   vbox->addStretch(1);
86   
87   // Create "Set to Origin" button
88   myToOrigin = new QPushButton(myGroupBoxSel);
89   myToOrigin->setText(tr("LBL_TOORIGIN"));
90   vbox->addWidget(myToOrigin);
91   connect(myToOrigin, SIGNAL(clicked()), this, SLOT(onToOrigin()));
92
93   // Create "Select Point from View" button
94   mySelectPoint = new QPushButton(myGroupBoxSel);
95   mySelectPoint->setText(tr("LBL_SELECTPOINT"));
96   mySelectPoint->setCheckable(true);
97   vbox->addWidget(mySelectPoint);
98   connect(mySelectPoint, SIGNAL(clicked()), this, SLOT(onSelectPoint()));
99
100   // Create croup box with grid layout
101   myGroupBoxCoord = new QGroupBox(this);
102   myGroupBoxCoord->setObjectName("GroupBox");
103   QHBoxLayout* aHBoxLayout = new QHBoxLayout(myGroupBoxCoord);
104   aHBoxLayout->setMargin(11);
105   aHBoxLayout->setSpacing(6);
106
107   // "X" coordinate
108   QLabel* TextLabelX = new QLabel (tr("LBL_X"), myGroupBoxCoord );
109   TextLabelX->setObjectName("TextLabelX");
110   TextLabelX->setFixedWidth(15);
111   myX = new QLineEdit(myGroupBoxCoord);
112   myX->setValidator(new QDoubleValidator(myX));
113   myX->setText(QString::number(0.0));
114   connect(myX, SIGNAL(textChanged(const QString&)), this, SLOT(onCoordChanged()));
115
116   // "Y" coordinate
117   QLabel* TextLabelY = new QLabel (tr("LBL_Y"), myGroupBoxCoord );
118   TextLabelY->setObjectName("TextLabelY");
119   TextLabelY->setFixedWidth(15);
120   myY = new QLineEdit(myGroupBoxCoord);
121   myY->setValidator(new QDoubleValidator(myY));
122   myY->setText(QString::number(0.0));
123   connect(myY, SIGNAL(textChanged(const QString&)), this, SLOT(onCoordChanged()));
124
125   // "Z" coordinate
126   QLabel* TextLabelZ = new QLabel (tr("LBL_Z"), myGroupBoxCoord );
127   TextLabelZ->setObjectName("TextLabelZ");
128   TextLabelZ->setFixedWidth(15);
129   myZ = new QLineEdit(myGroupBoxCoord);
130   myZ->setValidator(new QDoubleValidator(myZ));
131   myZ->setText(QString::number(0.0));
132   connect(myZ, SIGNAL(textChanged(const QString&)), this, SLOT(onCoordChanged()));
133
134   // Layout widgets in the horizontal group box
135   aHBoxLayout->addWidget(TextLabelX);
136   aHBoxLayout->addWidget(myX);
137   aHBoxLayout->addWidget(TextLabelY);
138   aHBoxLayout->addWidget(myY);
139   aHBoxLayout->addWidget(TextLabelZ);
140   aHBoxLayout->addWidget(myZ);
141
142   // "Close" button
143   QGroupBox* aGroupBox = new QGroupBox(this);
144   QHBoxLayout* aHBoxLayout2 = new QHBoxLayout(aGroupBox);
145   aHBoxLayout2->setMargin(11);
146   aHBoxLayout2->setSpacing(6);
147
148   QPushButton* m_bClose = new QPushButton(tr("&Close"), aGroupBox );
149   m_bClose->setObjectName("m_bClose");
150   m_bClose->setAutoDefault(TRUE);
151   m_bClose->setFixedSize(m_bClose->sizeHint());
152   connect(m_bClose, SIGNAL(clicked()), this, SLOT(onClickClose()));
153
154   // Layout buttons
155   aHBoxLayout2->addWidget(m_bClose);
156
157   // Layout top level widgets
158   layoutDlg->addLayout(aCheckBox,0,0);
159   layoutDlg->addWidget(myGroupBoxSel,1,0);
160   layoutDlg->addWidget(myGroupBoxCoord,2,0);
161   layoutDlg->addWidget(aGroupBox,3,0);
162   
163   setEnabled(myGroupBoxSel,!myIsBBCenter->isChecked());
164   setEnabled(myGroupBoxCoord,!myIsBBCenter->isChecked());
165
166   this->resize(400, this->sizeHint().height());
167
168   myEventCallbackCommand->Delete();
169   myEventCallbackCommand->SetClientData(this);
170   myEventCallbackCommand->SetCallback(SVTK_SetRotationPointDlg::ProcessEvents);
171   myIsObserverAdded = false;
172 }
173
174 /*
175  *  Destroys the object and frees any allocated resources
176  */
177 SVTK_SetRotationPointDlg
178 ::~SVTK_SetRotationPointDlg()
179 {
180   // no need to delete child widgets, Qt does it all for us
181 }
182
183 void
184 SVTK_SetRotationPointDlg
185 ::addObserver()
186 {
187   if ( !myIsObserverAdded ) {
188     vtkInteractorStyle* aIStyle = myRWInteractor->GetInteractorStyle();
189     aIStyle->AddObserver(SVTK::BBCenterChanged, myEventCallbackCommand.GetPointer(), myPriority);
190     aIStyle->AddObserver(SVTK::RotationPointChanged, myEventCallbackCommand.GetPointer(), myPriority);
191     myIsObserverAdded = true;
192   }
193 }
194
195 /*!
196   Return true if it is the first show for this dialog
197 */
198 bool
199 SVTK_SetRotationPointDlg
200 ::IsFirstShown()
201 {
202   return myIsBBCenter->isChecked() && myX->text().toDouble() == 0.
203     && myY->text().toDouble() == 0. && myZ->text().toDouble() == 0.;
204 }
205
206 /*!
207   Processes events
208 */
209 void 
210 SVTK_SetRotationPointDlg
211 ::ProcessEvents(vtkObject* vtkNotUsed(theObject), 
212                 unsigned long theEvent,
213                 void* theClientData, 
214                 void* theCallData)
215 {
216   SVTK_SetRotationPointDlg* self = reinterpret_cast<SVTK_SetRotationPointDlg*>(theClientData);
217   vtkFloatingPointType* aCoord = (vtkFloatingPointType*)theCallData;
218   
219   switch ( theEvent ) {
220   case SVTK::BBCenterChanged:
221     if ( self->myIsBBCenter->isChecked()
222          ||
223          IsBBEmpty(self->myMainWindow->getRenderer()) )
224     {
225       if ( aCoord )
226       {
227         self->myX->setText( QString::number(aCoord[0]) );
228         self->myY->setText( QString::number(aCoord[1]) );
229         self->myZ->setText( QString::number(aCoord[2]) );
230       }
231     }
232     break;
233   case SVTK::RotationPointChanged:
234     if ( aCoord )
235     {
236       self->myX->setText( QString::number(aCoord[0]) );
237       self->myY->setText( QString::number(aCoord[1]) );
238       self->myZ->setText( QString::number(aCoord[2]) );
239     }
240     if ( !self->myIsBBCenter->isChecked() )
241       self->mySelectPoint->toggle();
242   }
243 }
244
245 void 
246 SVTK_SetRotationPointDlg
247 ::setEnabled(QGroupBox* theGrp, const bool theState)
248 {
249   QObjectList aChildren(theGrp->children());
250   QObject* anObj;
251   for(int i = 0; i < aChildren.size(); i++)
252   {
253     anObj = aChildren.at(i);
254     if (anObj !=0 && anObj->inherits("QLineEdit"))
255       ((QLineEdit*)anObj)->setReadOnly(!theState);
256     if (anObj !=0 && anObj->inherits("QPushButton"))
257       ((QLineEdit*)anObj)->setEnabled(theState);
258   }
259   
260 }
261
262 void 
263 SVTK_SetRotationPointDlg
264 ::onBBCenterChecked()
265 {
266   setEnabled(myGroupBoxSel,!myIsBBCenter->isChecked());
267   setEnabled(myGroupBoxCoord,!myIsBBCenter->isChecked());
268   
269   if ( myIsBBCenter->isChecked() )
270   { 
271     if ( mySelectPoint->isChecked() )
272       mySelectPoint->toggle();
273     // activate mode : the rotation point is the center of the bounding box
274     // send the data to the SVTK_InteractorStyle: set the type of the rotation point
275     //                                            calculate coordinates of the rotation point
276     myMainWindow->activateSetRotationGravity();
277   }
278   else
279   {
280     QString aX = myX->text();
281     myX->setText(QString::number(aX.toDouble()+1.));
282     myX->setText(aX);
283   }
284 }
285
286 void
287 SVTK_SetRotationPointDlg
288 ::onToOrigin()
289 {
290   if ( mySelectPoint->isChecked() )
291     mySelectPoint->toggle();
292   myX->setText(QString::number(0.0));
293   myY->setText(QString::number(0.0));
294   myZ->setText(QString::number(0.0));
295 }
296
297 void
298 SVTK_SetRotationPointDlg
299 ::onSelectPoint()
300 {
301   if ( mySelectPoint->isChecked() )
302     myMainWindow->activateStartPointSelection();
303   else
304     mySelectPoint->toggle();
305 }
306
307 void
308 SVTK_SetRotationPointDlg
309 ::onCoordChanged()
310 {
311   if ( !myIsBBCenter->isChecked() ) {
312     if ( mySelectPoint->isChecked()
313          &&
314          ( myX->hasFocus() || myY->hasFocus() || myZ->hasFocus() ) )
315       mySelectPoint->toggle();
316     vtkFloatingPointType aCenter[3] = {myX->text().toDouble(), 
317                                        myY->text().toDouble(), 
318                                        myZ->text().toDouble()};
319     myMainWindow->activateSetRotationSelected((void*)aCenter);
320   }
321   else
322     myMainWindow->activateSetRotationGravity();
323 }
324
325 void
326 SVTK_SetRotationPointDlg
327 ::onClickClose()
328 {
329   reject();
330 }
331
332