Salome HOME
84e3d7883bee960a9439879a0963d6279ea0e9b6
[modules/visu.git] / src / VISUGUI / VisuGUI_ClippingPlaneDlg.cxx
1 // Copyright (C) 2007-2011  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 #include "VisuGUI_ClippingPlaneDlg.h"
21 #include "VisuGUI.h"
22 #include "VisuGUI_Tools.h"
23 #include "VisuGUI_ViewTools.h"
24
25 #include <VISU_Gen_i.hh>
26
27 #include <LightApp_Application.h>
28 #include <SUIT_Desktop.h>
29 #include <SUIT_Session.h>
30 #include <SUIT_ViewManager.h>
31 #include <SUIT_MessageBox.h>
32 #include <SUIT_ResourceMgr.h>
33 #include <SVTK_ViewWindow.h>
34 #include <VTKViewer_Utilities.h>
35 #include <SalomeApp_DoubleSpinBox.h>
36
37 #include <QVBoxLayout>
38 #include <QHBoxLayout>
39 #include <QLineEdit>
40 #include <QWidget>
41 #include <QGroupBox>
42 #include <QGridLayout>
43 #include <QCheckBox>
44 #include <QPushButton>
45
46 #include <vtkCallbackCommand.h>
47 #include <vtkImplicitPlaneWidget.h>
48
49
50 #define SIZEFACTOR 1.1
51
52
53
54
55 //****************************************************************
56 //****************************************************************
57 //****************************************************************
58 VisuGUI_ClippingPlaneDlg::VisuGUI_ClippingPlaneDlg(VisuGUI* theModule)
59   : QDialog(VISU::GetDesktop(theModule), Qt::WindowTitleHint | Qt::WindowSystemMenuHint ),
60     myModule(theModule),
61     myCallback( vtkCallbackCommand::New() ),
62     myPreviewWidget(0),
63     myViewWindow(0),
64     myPlaneId(-1)
65 {
66   myViewWindow = VISU::GetActiveViewWindow<SVTK_ViewWindow>(myModule);
67   VISU::ComputeVisiblePropBounds(myViewWindow, myBounds);
68
69   setWindowTitle(tr("TITLE"));
70   setSizeGripEnabled(true);
71   setModal(false);
72
73   myCallback->SetClientData(this); 
74   myCallback->SetCallback(VisuGUI_ClippingPlaneDlg::ProcessEvents);
75
76   QVBoxLayout* aMainLayout = new QVBoxLayout(this);
77
78   QWidget* aPlanesWgt = new QWidget(this);
79   aMainLayout->addWidget(aPlanesWgt);
80   QVBoxLayout* aFrameLayout = new QVBoxLayout(aPlanesWgt);
81
82   QWidget* aNameBox = new QWidget(aPlanesWgt);
83   aFrameLayout->addWidget(aNameBox);
84   QHBoxLayout* aNameLayout = new QHBoxLayout(aNameBox);
85
86   aNameLayout->addWidget(new QLabel(tr("LBL_NAME"), aPlanesWgt));
87   myNameEdt = new QLineEdit();
88   
89   _PTR(Study) aStudy = VISU::GetCStudy(VISU::GetAppStudy(myModule));
90   _PTR(SObject) aFolderSO;
91   if (VISU::getClippingPlanesFolder(aStudy, aFolderSO)) {
92     _PTR(ChildIterator) aIter = aStudy->NewChildIterator(aFolderSO);
93     int i = 1;
94     for (; aIter->More(); aIter->Next()) i++;
95
96     myNameEdt->setText(QString("Plane %1").arg(i));
97   }
98   aNameLayout->addWidget(myNameEdt);
99
100   QGroupBox* aOriginGroup = new QGroupBox( tr( "ORIGIN_TITLE" ), aPlanesWgt );
101   aFrameLayout->addWidget(aOriginGroup);
102   QHBoxLayout* aOriginLayout = new QHBoxLayout(aOriginGroup);
103
104   aOriginLayout->addWidget( new QLabel("X", aOriginGroup) );
105   myXOrigin = new SalomeApp_DoubleSpinBox( aOriginGroup );
106   VISU::initSpinBox( myXOrigin, -1000.0, 1000.0, 0.1, "length_precision" );
107   myXOrigin->setValue( 0.0 );
108   connect(myXOrigin, SIGNAL(valueChanged(double)), this, SLOT(onValueChanged()));
109   aOriginLayout->addWidget( myXOrigin );
110
111   aOriginLayout->addWidget( new QLabel("Y", aOriginGroup) );
112   myYOrigin = new  SalomeApp_DoubleSpinBox( aOriginGroup );
113   VISU::initSpinBox( myYOrigin, -1000.0, 1000.0, 0.1, "length_precision" );  
114   myYOrigin->setValue( 0.0 );
115   connect(myYOrigin, SIGNAL(valueChanged(double)), this, SLOT(onValueChanged()));
116   aOriginLayout->addWidget( myYOrigin );
117
118   aOriginLayout->addWidget( new QLabel("Z", aOriginGroup) );
119   myZOrigin = new SalomeApp_DoubleSpinBox( aOriginGroup );
120   VISU::initSpinBox( myZOrigin, -1000.0, 1000.0, 0.1, "length_precision" );   
121   myZOrigin->setValue( 0.0 );
122   connect(myZOrigin, SIGNAL(valueChanged(double)), this, SLOT(onValueChanged()));
123   aOriginLayout->addWidget( myZOrigin );
124   
125   QGroupBox* aDirGroup = new QGroupBox( tr( "DIRECTION_TITLE" ), aPlanesWgt );
126   aFrameLayout->addWidget(aDirGroup);
127   QHBoxLayout* aDirLayout = new QHBoxLayout(aDirGroup);
128
129   aDirLayout->addWidget( new QLabel("dX", aDirGroup) );
130   myXDir = new SalomeApp_DoubleSpinBox( aDirGroup );
131   VISU::initSpinBox( myXDir, -1000.0, 1000.0, 0.1, "length_precision" );  
132   myXDir->setValue( 0.0 );
133   connect(myXDir, SIGNAL(valueChanged(double)), this, SLOT(onValueChanged()));
134   aDirLayout->addWidget( myXDir );
135
136   aDirLayout->addWidget( new QLabel("dY", aDirGroup) );
137   myYDir = new SalomeApp_DoubleSpinBox( aDirGroup );
138   VISU::initSpinBox( myYDir, -1000.0, 1000.0, 0.1, "length_precision" );  
139   myYDir->setValue( 0.0 );
140   connect(myYDir, SIGNAL(valueChanged(double)), this, SLOT(onValueChanged()));
141   aDirLayout->addWidget( myYDir );
142
143   aDirLayout->addWidget( new QLabel("dZ", aDirGroup) );
144   myZDir = new SalomeApp_DoubleSpinBox( aDirGroup );
145   VISU::initSpinBox( myZDir, -1000.0, 1000.0, 0.1, "length_precision" );   
146   myZDir->setValue( 1.0 );
147   connect(myZDir, SIGNAL(valueChanged(double)), this, SLOT(onValueChanged()));
148   aDirLayout->addWidget( myZDir );
149
150   myAutoApply = new QCheckBox(tr("CHK_AUTOAPPLY"), aPlanesWgt);
151   myAutoApply->setCheckState(Qt::Checked);
152   aFrameLayout->addWidget(myAutoApply);
153
154   // Dialog buttons
155   QGroupBox* aGroupButtons = new QGroupBox (this);
156   aMainLayout->addWidget(aGroupButtons);
157
158   QSizePolicy aSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed );
159   QHBoxLayout* aButtonsLayout = new QHBoxLayout(aGroupButtons);
160
161   QPushButton* aBtnOk = new QPushButton(tr("BUT_OK"), aGroupButtons);
162   aButtonsLayout->addWidget(aBtnOk);
163
164   aButtonsLayout->addStretch();
165
166   QPushButton* aBtnClose = new QPushButton(tr("BUT_CANCEL"), aGroupButtons);
167   aButtonsLayout->addWidget(aBtnClose);
168
169   QPushButton* aBtnHelp = new QPushButton(tr("BUT_HELP"), aGroupButtons);
170   aButtonsLayout->addWidget(aBtnHelp);
171
172   connect(aBtnOk   , SIGNAL(clicked()), this, SLOT(accept()));
173   connect(aBtnClose, SIGNAL(clicked()), this, SLOT(reject()));
174   connect(aBtnHelp , SIGNAL(clicked()), this, SLOT(onHelp()));
175
176
177   myPreviewWidget = createPreviewWidget();
178   myViewWindow->Repaint();
179 }
180
181 VisuGUI_ClippingPlaneDlg::~VisuGUI_ClippingPlaneDlg()
182 {
183   if (myPreviewWidget) {
184     myPreviewWidget->Off();
185     myPreviewWidget->Delete();
186   }
187   myPreviewWidget = 0;
188   myCallback->Delete();
189 }
190
191 //****************************************************************
192 void VisuGUI_ClippingPlaneDlg::ProcessEvents(vtkObject* theObject, 
193                                              unsigned long theEvent,
194                                              void* theClientData, 
195                                              void* vtkNotUsed(theCallData))
196 {
197   vtkImplicitPlaneWidget* aWidget = vtkImplicitPlaneWidget::SafeDownCast(theObject);
198   if (aWidget == NULL) return;
199   if (theClientData == NULL) return;
200
201   VisuGUI_ClippingPlaneDlg* aDlg = (VisuGUI_ClippingPlaneDlg*) theClientData;
202
203   double aOrigin[3];
204   double aDir[3];
205
206   switch(theEvent){
207   case vtkCommand::InteractionEvent:
208     aWidget->GetOrigin(aOrigin);
209     aWidget->GetNormal(aDir);
210
211     aDlg->setOrigin(aOrigin);
212     aDlg->setDirection(aDir);
213
214     break;
215   }
216 }
217
218 //****************************************************************
219 void VisuGUI_ClippingPlaneDlg::setOrigin(double theVal[3])
220 {
221   myXOrigin->setValue(theVal[0]);
222   myYOrigin->setValue(theVal[1]);
223   myZOrigin->setValue(theVal[2]);
224 }
225
226 //****************************************************************
227 void VisuGUI_ClippingPlaneDlg::setDirection(double theVal[3])
228 {
229   myXDir->setValue(theVal[0]);
230   myYDir->setValue(theVal[1]);
231   myZDir->setValue(theVal[2]);
232 }
233
234 //****************************************************************
235 void VisuGUI_ClippingPlaneDlg::onValueChanged()
236 {
237   if (!myPreviewWidget) return;
238   double aOrigin[3];
239   double aDir[3];
240   aOrigin[0] = myXOrigin->value();
241   aOrigin[1] = myYOrigin->value();
242   aOrigin[2] = myZOrigin->value();
243
244   aDir[0] = myXDir->value();
245   aDir[1] = myYDir->value();
246   aDir[2] = myZDir->value();
247
248   myPreviewWidget->SetOrigin(aOrigin);
249   myPreviewWidget->SetNormal(aDir);
250   myViewWindow->Repaint();
251 }
252
253 //****************************************************************
254 vtkImplicitPlaneWidget* VisuGUI_ClippingPlaneDlg::createPreviewWidget()
255 {
256   vtkImplicitPlaneWidget* aPlaneWgt = vtkImplicitPlaneWidget::New();
257   aPlaneWgt->SetInteractor(myViewWindow->getInteractor());
258   aPlaneWgt->SetPlaceFactor(SIZEFACTOR);
259   aPlaneWgt->ScaleEnabledOff();
260   aPlaneWgt->PlaceWidget(myBounds[0],myBounds[1],myBounds[2],myBounds[3],myBounds[4],myBounds[5]);
261   aPlaneWgt->SetOrigin(0,0,0);
262   aPlaneWgt->SetNormal(0,0,1);
263   aPlaneWgt->On();
264
265   //aPlaneWgt->OutlineTranslationOff();
266   //aPlaneWgt->ScaleEnabledOn();
267   aPlaneWgt->AddObserver(vtkCommand::InteractionEvent, 
268                          myCallback.GetPointer(), 
269                          0.);
270   return aPlaneWgt;
271 }
272
273
274 //****************************************************************
275 void VisuGUI_ClippingPlaneDlg::setPlaneId(int theId)
276 {
277   myPlaneId = theId;
278   VISU_ClippingPlaneMgr& aMgr = VISU::GetVisuGen(myModule)->GetClippingPlaneMgr();
279
280   VISU_CutPlaneFunction* aPlane =  aMgr.GetClippingPlane(myPlaneId);
281   if (aPlane) {
282     myNameEdt->setText(QString(aPlane->getName().c_str()));
283     double aOrigin[3], aDir[3];
284     aPlane->GetOrigin(aOrigin);
285     aPlane->GetNormal(aDir);
286
287     myXOrigin->setValue(aOrigin[0]);
288     myYOrigin->setValue(aOrigin[1]);
289     myZOrigin->setValue(aOrigin[2]);
290     myPreviewWidget->SetOrigin(aOrigin);
291
292     myXDir->setValue(aDir[0]);
293     myYDir->setValue(aDir[1]);
294     myZDir->setValue(aDir[2]);
295
296     myPreviewWidget->SetNormal(aDir);
297
298     myAutoApply->setCheckState((aPlane->isAuto())? Qt::Checked : Qt::Unchecked);
299     myViewWindow->Repaint();
300   }
301 }
302 /*void VisuGUI_ClippingPlaneDlg::setPlaneObj(_PTR(SObject) thePlaneObj)
303 {
304   myPlaneObj = thePlaneObj;
305
306   myNameEdt->setText(QString(myPlaneObj->GetName().c_str()));
307
308   _PTR(GenericAttribute) anAttr;
309   if (myPlaneObj->FindAttribute(anAttr, "AttributeSequenceOfReal")) {
310     _PTR(AttributeSequenceOfReal) aArray(anAttr);
311     myXOrigin->setValue(aArray->Value(1));
312     myYOrigin->setValue(aArray->Value(2));
313     myZOrigin->setValue(aArray->Value(3));
314
315     myPreviewWidget->SetOrigin(aArray->Value(1), aArray->Value(2), aArray->Value(3));
316
317     myXDir->setValue(aArray->Value(4));
318     myYDir->setValue(aArray->Value(5));
319     myZDir->setValue(aArray->Value(6));
320
321     myPreviewWidget->SetNormal(aArray->Value(4), aArray->Value(5), aArray->Value(6));
322   }
323   if (myPlaneObj->FindAttribute(anAttr, "AttributeInteger")) {
324     _PTR(AttributeInteger) aFlag(anAttr);
325     myAutoApply->setCheckState((aFlag->Value() == 1)? Qt::Checked : Qt::Unchecked);
326   }
327
328   myViewWindow->Repaint();
329 }*/
330
331 //****************************************************************
332 void VisuGUI_ClippingPlaneDlg::accept()
333 {
334   _PTR(Study) aStudy = VISU::GetCStudy( VISU::GetAppStudy( myModule ) );
335   if(!aStudy->GetProperties()->IsLocked()) {
336     VISU_ClippingPlaneMgr& aMgr = VISU::GetVisuGen(myModule)->GetClippingPlaneMgr();
337     if (myPlaneId == -1) { // Create a New plane
338       myPlaneId = aMgr.CreateClippingPlane(myXOrigin->value(), myYOrigin->value(), myZOrigin->value(),
339                                            myXDir->value(), myYDir->value(), myZDir->value(),
340                                            myAutoApply->checkState() == Qt::Checked,
341                                            qPrintable(myNameEdt->text()));
342     } else { // Edit Plane
343       aMgr.EditClippingPlane(myPlaneId,
344                              myXOrigin->value(), myYOrigin->value(), myZOrigin->value(),
345                              myXDir->value(), myYDir->value(), myZDir->value(),
346                              myAutoApply->checkState() == Qt::Checked,
347                              qPrintable(myNameEdt->text()));
348     }
349     VISU::UpdateObjBrowser(myModule);
350   }
351   /*  _PTR(Study) aStudy = VISU::GetCStudy( VISU::GetAppStudy( myModule ) );
352   if(!aStudy->GetProperties()->IsLocked()) {
353     _PTR(SObject) aFolder;
354     if (VISU::getClippingPlanesFolder(aStudy, aFolder)) {
355       _PTR(StudyBuilder) aBuilder = aStudy->NewBuilder();
356       if (myPlaneObj == 0) { // Create a New plane
357         myPlaneObj = aBuilder->NewObject(aFolder);
358       } 
359       // Save Name
360       _PTR(GenericAttribute) anAttr;
361       anAttr = aBuilder->FindOrCreateAttribute(myPlaneObj,"AttributeName");
362       _PTR(AttributeName) aName(anAttr);
363       aName->SetValue(myNameEdt->text().toStdString());
364
365       //Save Parameters
366       double aParams[6];
367       aParams[0] = myXOrigin->value();
368       aParams[1] = myYOrigin->value();
369       aParams[2] = myZOrigin->value();
370       aParams[3] = myXDir->value();
371       aParams[4] = myYDir->value();
372       aParams[5] = myZDir->value();
373
374       anAttr = aBuilder->FindOrCreateAttribute(myPlaneObj,"AttributeSequenceOfReal");
375       _PTR(AttributeSequenceOfReal) aArray(anAttr);
376       if (aArray->Length() == 6) {
377         for (int i = 0; i < 6; i++)
378           aArray->ChangeValue(i+1, aParams[i]);
379       } else {
380         for (int i = 0; i < 6; i++)
381           aArray->Add(aParams[i]);
382       }
383       // Save Bool Flag
384       anAttr = aBuilder->FindOrCreateAttribute(myPlaneObj,"AttributeInteger");
385       _PTR(AttributeInteger) aFlag(anAttr);
386       aFlag->SetValue((myAutoApply->checkState() == Qt::Checked)? 1 : 0);
387
388       VISU::UpdateObjBrowser(myModule);
389     }
390     }*/
391   QDialog::accept();
392 }
393
394
395 //****************************************************************
396 void VisuGUI_ClippingPlaneDlg::onHelp()
397 {
398   QString aHelpFileName = "clipping_page.html";
399   LightApp_Application* app = (LightApp_Application*)(SUIT_Session::session()->activeApplication());
400   if (app)
401     app->onHelpContextModule(myModule ? app->moduleName(myModule->moduleName()) : QString(""), aHelpFileName);
402   else {
403     QString platform;
404 #ifdef WIN32
405     platform = "winapplication";
406 #else
407     platform = "application";
408 #endif
409     SUIT_MessageBox::warning(0, QObject::tr("WRN_WARNING"),
410                              QObject::tr("EXTERNAL_BROWSER_CANNOT_SHOW_PAGE").
411                              arg(app->resourceMgr()->stringValue("ExternalBrowser", platform)).arg(aHelpFileName),
412                              QObject::tr("BUT_OK"));
413   }
414 }
415