Salome HOME
Minor change.
[modules/hydro.git] / src / HYDROGUI / HYDROGUI_CalculationOp.cxx
1 // Copyright (C) 2007-2013  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
23 #include "HYDROGUI_CalculationOp.h"
24
25 #include "HYDROGUI_DataModel.h"
26 #include "HYDROGUI_CalculationDlg.h"
27 #include "HYDROGUI_Module.h"
28 #include "HYDROGUI_Tool.h"
29 #include "HYDROGUI_UpdateFlags.h"
30 #include "HYDROGUI_Zone.h"
31 #include "HYDROGUI_Region.h"
32
33 #include <HYDROData_Polyline.h>
34 #include <HYDROData_Iterator.h>
35 #include <HYDROData_ImmersibleZone.h>
36 #include <HYDROData_Object.h>
37
38 #include <OCCViewer_ViewManager.h>
39 #include <OCCViewer_ViewModel.h>
40 #include <OCCViewer_ViewWindow.h>
41
42 #include <LightApp_Application.h>
43 #include <LightApp_UpdateFlags.h>
44
45 #include <SUIT_MessageBox.h>
46 #include <SUIT_Desktop.h>
47
48 #include <QApplication>
49
50 HYDROGUI_CalculationOp::HYDROGUI_CalculationOp( HYDROGUI_Module* theModule, bool theIsEdit )
51 : HYDROGUI_Operation( theModule ),
52   myIsEdit( theIsEdit ),
53   myActiveViewManager( NULL ),
54   myPreviewViewManager( NULL )
55 {
56   setName( myIsEdit ? tr( "EDIT_CALCULATION" ) : tr( "CREATE_CALCULATION" ) );
57 }
58
59 HYDROGUI_CalculationOp::~HYDROGUI_CalculationOp()
60 {
61   closePreview();
62 }
63
64 void HYDROGUI_CalculationOp::startOperation()
65 {
66   HYDROGUI_Operation::startOperation();
67   
68   // Begin transaction
69   startDocOperation();
70
71   HYDROGUI_CalculationDlg* aPanel = 
72     ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
73   if ( !aPanel )
74     return;
75
76   myRegionsList.clear();
77   aPanel->reset();
78
79   QString anObjectName = HYDROGUI_Tool::GenerateObjectName( module(), "Case" );
80
81   QStringList aSelectedObjects;
82
83   myEditedObject.Nullify();
84   if ( myIsEdit )
85   {
86     myEditedObject = Handle(HYDROData_CalculationCase)::DownCast( HYDROGUI_Tool::GetSelectedObject( module() ) );
87     if ( !myEditedObject.IsNull() )
88     {
89       anObjectName = myEditedObject->GetName();
90       updateGeomObjectsList(aPanel);
91     }
92   }
93   else
94   {
95     myEditedObject =
96       Handle(HYDROData_CalculationCase)::DownCast( doc()->CreateObject( KIND_CALCULATION ) );
97     myEditedObject->SetName(anObjectName);
98   }
99
100   aPanel->setObjectName( anObjectName );
101   aPanel->setEditedObject( myEditedObject );
102 //  aPanel->setSelectedGeomObjects( aSelectedObjects );
103
104   createPreview();
105 }
106
107 void HYDROGUI_CalculationOp::updateGeomObjectsList( HYDROGUI_CalculationDlg* thePanel ) const
108 {
109   Handle(HYDROData_Object) anObject;
110   Handle(HYDROData_Entity) anEntity;
111   QStringList aList;
112   // Update the list in the dialog
113   HYDROData_SequenceOfObjects aSeq = myEditedObject->GetGeometryObjects();
114   HYDROData_SequenceOfObjects::Iterator anIter( aSeq );
115   for ( ; anIter.More(); anIter.Next() )
116   {
117     anEntity = anIter.Value();
118     if ( !anEntity.IsNull() )
119     {
120       anObject = Handle(HYDROData_Object)::DownCast( anEntity );
121       if ( !anObject.IsNull() )
122       {
123         aList.append( anObject->GetName() );
124       }
125     }
126   }
127   thePanel->setSelectedGeomObjects( aList );
128 }
129
130 void HYDROGUI_CalculationOp::abortOperation()
131 {
132   closePreview();
133   // Abort transaction
134   abortDocOperation();
135   HYDROGUI_Operation::abortOperation();
136 }
137
138 void HYDROGUI_CalculationOp::commitOperation()
139 {
140   closePreview();
141   // Commit transaction
142   commitDocOperation();
143   HYDROGUI_Operation::commitOperation();
144 }
145
146 HYDROGUI_InputPanel* HYDROGUI_CalculationOp::createInputPanel() const
147 {
148   HYDROGUI_CalculationDlg* aPanel = new HYDROGUI_CalculationDlg( module(), getName() );
149
150   // Connect signals and slots
151   connect( aPanel, SIGNAL( addObjects() ), SLOT( onAddObjects() ) );
152   connect( aPanel, SIGNAL( removeObjects() ), SLOT( onRemoveObjects() ) );
153   connect( aPanel, SIGNAL( splitZones() ), SLOT( onSplitZones() ) );
154   connect( aPanel, SIGNAL( clicked( SUIT_DataObject* ) ), SLOT( onSelected( SUIT_DataObject* ) ) );
155   connect( aPanel, SIGNAL( setMergeType( int, QString& ) ), SLOT( onSetMergeType( int, QString& ) ) );
156   connect( aPanel, SIGNAL( moveZones( SUIT_DataObject*, const QList<SUIT_DataObject*>& ) ),
157     SLOT( onMoveZones( SUIT_DataObject*, const QList<SUIT_DataObject*>& ) ) );
158   connect( aPanel, SIGNAL( createRegion( const QList<SUIT_DataObject*>& ) ),
159     SLOT( onCreateRegion( const QList<SUIT_DataObject*>& ) ) );
160
161   return aPanel;
162 }
163
164 void HYDROGUI_CalculationOp::onMoveZones( SUIT_DataObject* theRegionItem, const QList<SUIT_DataObject*>& theZonesList )
165 {
166   HYDROGUI_Region* aRegion = dynamic_cast<HYDROGUI_Region*>(theRegionItem);
167   if ( aRegion )
168   {
169     QList<HYDROGUI_Zone*> aZonesList;
170     HYDROGUI_Zone* aZone;
171     // Get a list of dropped zones
172     for ( int i = 0; i < theZonesList.length(); i++ )
173     {
174       aZone = dynamic_cast<HYDROGUI_Zone*>( theZonesList.at( i ) );
175       if ( aZone )
176       {
177         aZonesList.append( aZone );
178       }
179     }
180     if ( aZonesList.length() > 0 )
181     {
182       aRegion->addZones( aZonesList );
183       HYDROGUI_CalculationDlg* aPanel = 
184         ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
185       if ( aPanel )
186       {
187         aPanel->setEditedObject(myEditedObject);
188       }
189     }
190   }
191 }
192
193 void HYDROGUI_CalculationOp::onCreateRegion( const QList<SUIT_DataObject*>& theZonesList )
194 {
195   QList<HYDROGUI_Zone*> aZonesList;
196   HYDROGUI_Zone* aZone;
197   // Get a list of dropped zones
198   for ( int i = 0; i < theZonesList.length(); i++ )
199   {
200     aZone = dynamic_cast<HYDROGUI_Zone*>( theZonesList.at( i ) );
201     if ( aZone )
202     {
203       aZonesList.append( aZone );
204     }
205   }
206   if ( aZonesList.length() > 0 )
207   {
208     module()->getDataModel()->createNewRegion( myEditedObject, aZonesList );
209     HYDROGUI_CalculationDlg* aPanel = 
210       ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
211     if ( aPanel )
212     {
213       aPanel->setEditedObject(myEditedObject);
214     }
215   }
216 }
217
218 void HYDROGUI_CalculationOp::onSetMergeType( int theMergeType, QString& theBathymetryName )
219 {
220   HYDROGUI_CalculationDlg* aPanel = 
221     ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
222   if ( aPanel )
223   {
224     HYDROGUI_Zone* aZone = aPanel->getCurrentZone();
225     if ( aZone )
226     {
227       aZone->setMergeType( theMergeType, theBathymetryName );
228     }
229     aPanel->refreshZonesBrowser();
230   }
231 }
232
233 void HYDROGUI_CalculationOp::onAddObjects()
234 {
235   // Add geometry objects selected in the module browser to the calculation case
236   Handle(HYDROData_Object) anObject;
237   Handle(HYDROData_Entity) anEntity;
238   QStringList aList;
239   HYDROData_SequenceOfObjects aSeq = HYDROGUI_Tool::GetSelectedObjects( module() );
240   for( Standard_Integer anIndex = 1, aLength = aSeq.Length(); anIndex <= aLength; anIndex++ )
241   {
242     anEntity = aSeq.Value( anIndex );
243     if ( !anEntity.IsNull() )
244     {
245       anObject = Handle(HYDROData_Object)::DownCast( anEntity );
246       if( !anObject.IsNull() )
247       {
248         if (myEditedObject->AddGeometryObject( anObject ))
249         {
250           aList.append( anObject->GetName() );
251         }
252       }
253     }
254   }
255   HYDROGUI_CalculationDlg* aPanel = 
256     ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
257   if ( aPanel )
258   {
259     updateGeomObjectsList( aPanel );
260   }
261 }
262
263 void HYDROGUI_CalculationOp::onRemoveObjects()
264 {
265   // Remove selected objects from the calculation case
266   HYDROGUI_CalculationDlg* aPanel = 
267     ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
268   if ( aPanel )
269   {
270     QStringList aList = aPanel->getSelectedGeomObjects();
271     Handle(HYDROData_Object) anObject;
272     Handle(HYDROData_Entity) anEntity;
273     for (int i = 0; i < aList.length(); i++)
274     {
275       anEntity = HYDROGUI_Tool::FindObjectByName( module(), aList.at(i) );
276       if ( !anEntity.IsNull() )
277       {
278         anObject = Handle(HYDROData_Object)::DownCast( anEntity );
279         if ( !anObject.IsNull() )
280         {
281           myEditedObject->RemoveGeometryObject( anObject );
282         }
283       }
284     }
285     updateGeomObjectsList( aPanel );
286   }
287 }
288
289 bool HYDROGUI_CalculationOp::processApply( int&     theUpdateFlags,
290                                            QString& theErrorMsg )
291 {
292   HYDROGUI_CalculationDlg* aPanel = 
293     ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
294   if ( !aPanel )
295     return false;
296
297   //QString anObjectName = aPanel->getObjectName().simplified();
298   //if ( anObjectName.isEmpty() )
299   //{
300   //  theErrorMsg = tr( "INCORRECT_OBJECT_NAME" );
301   //  return false;
302   //}
303
304   //// check that there are no other objects with the same name in the document
305   //if( !myIsEdit || ( !myEditedObject.IsNull() && myEditedObject->GetName() != anObjectName ) )
306   //{
307   //  Handle(HYDROData_Entity) anObject = HYDROGUI_Tool::FindObjectByName( module(), anObjectName );
308   //  if ( !anObject.IsNull() )
309   //  {
310   //    theErrorMsg = tr( "OBJECT_EXISTS_IN_DOCUMENT" ).arg( anObjectName );
311   //    return false;
312   //  }
313   //}
314
315   //Handle(HYDROData_Document) aDocument = doc();
316
317   //Handle(HYDROData_CalculationCase) aCalculObj = myIsEdit ? myEditedObject :
318   //  Handle(HYDROData_CalculationCase)::DownCast( aDocument->CreateObject( KIND_CALCULATION ) );
319   //if ( aCalculObj.IsNull() )
320   //  return false;
321
322   //aCalculObj->SetName( anObjectName );
323
324   //QStringList aRefObjectNames = aPanel->getSelectedGeomObjects();
325   //HYDROData_SequenceOfObjects aGeomObjects = 
326   //  HYDROGUI_Tool::FindObjectsByNames( module(), aRefObjectNames );
327
328   theUpdateFlags = UF_Model;
329
330   return true;
331 }
332
333 void HYDROGUI_CalculationOp::onApply()
334 {
335   QApplication::setOverrideCursor( Qt::WaitCursor );
336
337   int anUpdateFlags = 0;
338   QString anErrorMsg;
339
340   bool aResult = false;
341   
342   try
343   {
344     aResult = processApply( anUpdateFlags, anErrorMsg );
345   }
346   catch ( Standard_Failure )
347   {
348     Handle(Standard_Failure) aFailure = Standard_Failure::Caught();
349     anErrorMsg = aFailure->GetMessageString();
350     aResult = false;
351   }
352   catch ( ... )
353   {
354     aResult = false;
355   }
356   
357   QApplication::restoreOverrideCursor();
358
359   if ( aResult )
360   {
361     module()->update( anUpdateFlags );
362     commit();
363   }
364   else
365   {
366     abort();
367     QString aMsg = tr( "INPUT_VALID_DATA" );
368     if( !anErrorMsg.isEmpty() )
369       aMsg.prepend( anErrorMsg + "\n" );
370     SUIT_MessageBox::critical( module()->getApp()->desktop(),
371                                tr( "INSUFFICIENT_INPUT_DATA" ),
372                                aMsg ); 
373   }
374 }
375
376 void HYDROGUI_CalculationOp::onSplitZones()
377 {
378   //myRegionsList.clear();
379
380   HYDROGUI_CalculationDlg* aPanel = 
381     ::qobject_cast<HYDROGUI_CalculationDlg*>( inputPanel() );
382   if ( !aPanel )
383     return;
384
385   QApplication::setOverrideCursor( Qt::WaitCursor );
386
387   //QStringList aGeomObjectNames = aPanel->getSelectedGeomObjects();
388   //HYDROData_SequenceOfObjects aGeomObjects = 
389   //  HYDROGUI_Tool::FindObjectsByNames( module(), aGeomObjectNames );
390
391   //QStringList aResSplittedZones;
392
393   //HYDROData_SplitToZonesTool::SplitDataList aSplittedZones =
394   //  HYDROData_SplitToZonesTool::SplitToZones( aGeomObjects );
395
396   //QStringList aUsedNames;
397
398   //HYDROData_SplitToZonesTool::SplitDataListIterator anIter( aSplittedZones );
399   //while( anIter.hasNext() )
400   //{
401   //  Region aRegion;
402   //  aRegion.SplitData = anIter.next();
403
404   //  aRegion.FillingColor = HYDROGUI_Tool::GenerateFillingColor( module(), aRegion.SplitData.ObjectNames );
405   //  aRegion.BorderColor  = QColor( HYDROData_ImmersibleZone::DefaultBorderColor() );
406
407   //  aRegion.RegionName = HYDROGUI_Tool::GenerateObjectName( module(), "Region", aUsedNames );
408
409   //  aUsedNames.append( aRegion.RegionName );
410
411   //  aResSplittedZones.append( aRegion.RegionName );
412
413   //  myRegionsList.append( aRegion );
414   //}
415   //
416
417   myEditedObject->SplitGeometryObjects();
418   aPanel->setEditedObject( myEditedObject );
419   createPreview();
420
421   QApplication::restoreOverrideCursor();
422 }
423
424 void HYDROGUI_CalculationOp::createPreview()
425 {
426   LightApp_Application* anApp = module()->getApp();
427
428   if ( !myActiveViewManager )
429   {
430     if ( myRegionsList.isEmpty() )
431       return;
432
433     myActiveViewManager = anApp->activeViewManager();
434   }
435
436   if ( !myPreviewViewManager )
437   {
438     myPreviewViewManager = ::qobject_cast<OCCViewer_ViewManager*>( 
439       anApp->createViewManager( OCCViewer_Viewer::Type() ) );
440     if ( myPreviewViewManager )
441     {
442       connect( myPreviewViewManager, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
443                this, SLOT( onLastViewClosed( SUIT_ViewManager* ) ) );
444
445       module()->setViewManagerRole( myPreviewViewManager, HYDROGUI_Module::VMR_PreviewCaseZones );
446       myPreviewViewManager->setTitle( tr( "PREVIEW_CASE_ZONES" ) );
447     }
448   }
449
450   if ( !myPreviewViewManager )
451     return;
452
453   if ( OCCViewer_Viewer* aViewer = myPreviewViewManager->getOCCViewer() )
454   {
455     Handle(AIS_InteractiveContext) aCtx = aViewer->getAISContext();
456     if ( !aCtx.IsNull() )
457     {
458       RegionsList::iterator anIter = myRegionsList.begin();
459       for ( ; anIter != myRegionsList.end(); ++anIter )
460       {
461         Region& aRegion = *anIter;
462         if ( aRegion.Shape )
463         {
464           aRegion.Shape->erase( false );
465           delete aRegion.Shape;
466         }
467
468         aRegion.Shape = new HYDROGUI_Shape( aCtx, NULL );
469
470         aRegion.Shape->setFillingColor( aRegion.FillingColor, false, false );
471         aRegion.Shape->setBorderColor( aRegion.BorderColor, false, false );
472         aRegion.Shape->setFace( aRegion.SplitData.Face(), true, false );
473       }
474
475       //Process the draw events for viewer
476       QApplication::processEvents();
477       if ( OCCViewer_ViewWindow* vw = (OCCViewer_ViewWindow*)myPreviewViewManager->getActiveView() )
478         vw->onTopView();
479     }
480   }
481 }
482
483 void HYDROGUI_CalculationOp::onLastViewClosed( SUIT_ViewManager* theViewManager )
484 {
485   closePreview();
486 }
487
488 void HYDROGUI_CalculationOp::closePreview()
489 {
490   RegionsList::iterator anIter= myRegionsList.begin();
491   for ( ; anIter != myRegionsList.end(); ++anIter )
492   {
493     Region& aRegion = *anIter;
494     if ( aRegion.Shape )
495     {
496       aRegion.Shape->erase( false );
497       delete aRegion.Shape;
498       aRegion.Shape = NULL;
499     }
500   }
501
502   if( myPreviewViewManager )
503   {
504     disconnect( myPreviewViewManager, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
505                 this, SLOT( onLastViewClosed( SUIT_ViewManager* ) ) );
506
507     module()->getApp()->removeViewManager( myPreviewViewManager ); // myPreviewViewManager is deleted here
508     myPreviewViewManager = NULL;
509   }
510
511   if( myActiveViewManager )
512   {
513     HYDROGUI_Tool::SetActiveViewManager( module(), myActiveViewManager );
514     myActiveViewManager = NULL;
515   }
516 }
517
518