Salome HOME
Update copyright information
[modules/smesh.git] / src / SMESHGUI / SMESHGUI_Hypotheses.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 // SMESH SMESHGUI : GUI for SMESH component
23 // File   : SMESHGUI_Hypotheses.cxx
24 // Author : Julia DOROVSKIKH, Open CASCADE S.A.S.
25 // SMESH includes
26 //
27 #include "SMESHGUI_Hypotheses.h"
28
29 #include "SMESHGUI.h"
30 #include "SMESHGUI_HypothesesUtils.h"
31 #include "SMESHGUI_Utils.h"
32 #include "SMESHGUI_SpinBox.h"
33
34 // SALOME KERNEL includes
35 #include <SALOMEDSClient_Study.hxx>
36 #include <utilities.h>
37
38 // SALOME GUI includes
39 #include <QtxIntSpinBox.h>
40 #include <SUIT_Session.h>
41 #include <SUIT_MessageBox.h>
42 #include <SUIT_ResourceMgr.h>
43 #include <LightApp_Application.h>
44
45 // Qt includes
46 #include <QFrame>
47 #include <QLineEdit>
48 #include <QLabel>
49 #include <QGroupBox>
50 #include <QVBoxLayout>
51 #include <QEventLoop>
52
53 #define SPACING 6
54 #define MARGIN  11
55
56 SMESHGUI_GenericHypothesisCreator::SMESHGUI_GenericHypothesisCreator( const QString& theHypType )
57   : myHypType( theHypType ), myIsCreate( false ), myDlg( 0 ), myEventLoop( 0 )
58 {
59 }
60
61 SMESHGUI_GenericHypothesisCreator::~SMESHGUI_GenericHypothesisCreator()
62 {
63 }
64
65 void SMESHGUI_GenericHypothesisCreator::create( SMESH::SMESH_Hypothesis_ptr initParamsHyp,
66                                                 const QString& theHypName,
67                                                 QWidget* parent)
68 {
69   MESSAGE( "Creation of hypothesis with initial params" );
70
71   if ( !CORBA::is_nil( initParamsHyp ) && hypType() == initParamsHyp->GetName() )
72     myInitParamsHypo = SMESH::SMESH_Hypothesis::_duplicate( initParamsHyp );
73   create( false, theHypName, parent );
74 }
75
76 void SMESHGUI_GenericHypothesisCreator::create( bool isAlgo,
77                                                 const QString& theHypName,
78                                                 QWidget* theParent )
79 {
80   MESSAGE( "Creation of hypothesis" );
81
82   myIsCreate = true;
83
84   // Create hypothesis/algorithm
85   if (isAlgo)
86     SMESH::CreateHypothesis( hypType(), theHypName, isAlgo );
87   else
88   {
89     SMESH::SMESH_Hypothesis_var aHypothesis = 
90       SMESH::CreateHypothesis( hypType(), theHypName, false );
91     if( !editHypothesis( aHypothesis.in(), theHypName, theParent ) )
92     { //remove just created hypothesis
93       _PTR(SObject) aHypSObject = SMESH::FindSObject( aHypothesis.in() );
94       _PTR(Study) aStudy = SMESH::GetActiveStudyDocument();
95       if( aStudy && !aStudy->GetProperties()->IsLocked() )
96       {
97         _PTR(StudyBuilder) aBuilder = aStudy->NewBuilder();
98         aBuilder->RemoveObjectWithChildren( aHypSObject );
99       }
100     }
101   }
102   SMESHGUI::GetSMESHGUI()->updateObjBrowser( true, 0 );
103 }
104
105 void SMESHGUI_GenericHypothesisCreator::edit( SMESH::SMESH_Hypothesis_ptr theHypothesis,
106                                               const QString& theHypName,
107                                               QWidget* theParent )
108 {
109   if( CORBA::is_nil( theHypothesis ) )
110     return;
111
112   MESSAGE("Edition of hypothesis");
113
114   myIsCreate = false;
115
116   if( !editHypothesis( theHypothesis, theHypName, theParent ) )
117     return;
118
119   SMESH::SObjectList listSOmesh = SMESH::GetMeshesUsingAlgoOrHypothesis( theHypothesis );
120   if( listSOmesh.size() > 0 )
121     for( int i = 0; i < listSOmesh.size(); i++ )
122     {
123       _PTR(SObject) submSO = listSOmesh[i];
124       SMESH::SMESH_Mesh_var aMesh = SMESH::SObjectToInterface<SMESH::SMESH_Mesh>( submSO );
125       SMESH::SMESH_subMesh_var aSubMesh = SMESH::SObjectToInterface<SMESH::SMESH_subMesh>( submSO );
126       if( !aSubMesh->_is_nil() )
127         aMesh = aSubMesh->GetFather();
128       _PTR(SObject) meshSO = SMESH::FindSObject( aMesh );
129       SMESH::ModifiedMesh( meshSO, false, aMesh->NbNodes()==0);
130     }
131   SMESHGUI::GetSMESHGUI()->updateObjBrowser( true, 0 );
132 }
133
134 bool SMESHGUI_GenericHypothesisCreator::editHypothesis( SMESH::SMESH_Hypothesis_ptr h, 
135                                                         const QString& theHypName,
136                                                         QWidget* theParent )
137 {
138   if( CORBA::is_nil( h ) )
139     return false;
140
141   bool res = true;
142   myHypName = theHypName;
143   myHypo = SMESH::SMESH_Hypothesis::_duplicate( h );
144
145   SMESHGUI_HypothesisDlg* Dlg = new SMESHGUI_HypothesisDlg( this, theParent );
146   connect( Dlg, SIGNAL( finished( int ) ), this, SLOT( onDialogFinished( int ) ) );
147   myDlg = Dlg;
148   QFrame* fr = buildFrame();
149   if( fr )
150   {
151     Dlg->setCustomFrame( fr );
152     Dlg->setWindowTitle( caption() );
153     Dlg->setObjectName( theHypName );
154     Dlg->setHIcon( icon() );
155     Dlg->setType( type() );
156     retrieveParams();
157     Dlg->show();
158     if ( !myEventLoop )
159       myEventLoop = new QEventLoop( this );
160     myEventLoop->exec(); // make myDlg not modal
161     res = myDlg->result();
162     if( res ) {
163       QString paramValues = storeParams();
164       if ( !paramValues.isEmpty() ) {
165         if ( _PTR(SObject) SHyp = SMESH::FindSObject( myHypo ))
166           SMESH::SetValue( SHyp, paramValues );
167       }
168     }
169   }
170   delete Dlg; myDlg = 0;
171   changeWidgets().clear();
172   myHypo = SMESH::SMESH_Hypothesis::_nil();
173   myInitParamsHypo = SMESH::SMESH_Hypothesis::_nil();
174   return res;
175 }
176   
177 QFrame* SMESHGUI_GenericHypothesisCreator::buildStdFrame()
178 {
179   if( CORBA::is_nil( hypothesis() ) )
180     return 0;
181
182   ListOfStdParams params;
183   if( !stdParams( params ) || params.isEmpty() )
184     return 0;
185
186   QFrame* fr = new QFrame( 0 );
187   QVBoxLayout* lay = new QVBoxLayout( fr );
188   lay->setMargin( 5 );
189   lay->setSpacing( 0 );
190
191   QGroupBox* GroupC1 = new QGroupBox( tr( "SMESH_ARGUMENTS" ), fr );
192   lay->addWidget( GroupC1 );
193
194   QGridLayout* GroupC1Layout = new QGridLayout( GroupC1 );
195   GroupC1Layout->setSpacing( SPACING );
196   GroupC1Layout->setMargin( MARGIN );
197
198   ListOfStdParams::const_iterator anIt = params.begin(), aLast = params.end();
199   for( int i=0; anIt!=aLast; anIt++, i++ )
200   {
201     QLabel* lab = new QLabel( (*anIt).myName, GroupC1 );
202     GroupC1Layout->addWidget( lab, i, 0 );
203
204     QWidget* w = getCustomWidget( *anIt, GroupC1, i );
205     if ( !w ) 
206       switch( (*anIt).myValue.type() )
207       {
208       case QVariant::Int:
209         {
210           QtxIntSpinBox* sb = new QtxIntSpinBox( GroupC1 );
211           sb->setObjectName( (*anIt).myName );
212           attuneStdWidget( sb, i );
213           sb->setValue( (*anIt).myValue.toInt() );
214           connect( sb, SIGNAL( valueChanged( int ) ), this, SLOT( onValueChanged() ) );
215           w = sb;
216         }
217         break;
218       case QVariant::Double:
219         {
220           QtxDoubleSpinBox* sb = new SMESHGUI_SpinBox( GroupC1 );
221           sb->setObjectName( (*anIt).myName );
222           attuneStdWidget( sb, i );
223           sb->setValue( (*anIt).myValue.toDouble() );
224           connect( sb, SIGNAL( valueChanged( double ) ), this, SLOT( onValueChanged() ) );
225           w = sb;
226         }
227         break;
228       case QVariant::String:
229         {
230           QLineEdit* le = new QLineEdit( GroupC1 );
231           le->setObjectName( (*anIt).myName );
232           attuneStdWidget( le, i );
233           le->setText( (*anIt).myValue.toString() );
234           connect( le, SIGNAL( textChanged( const QString& ) ), this, SLOT( onValueChanged() ) );
235           w = le;
236         }
237         break;
238       }
239
240     if( w )
241     {
242       GroupC1Layout->addWidget( w, i, 1 );
243       changeWidgets().append( w );
244     }
245   }
246
247   return fr;
248 }
249
250 void SMESHGUI_GenericHypothesisCreator::onValueChanged()
251 {
252 }
253
254 void SMESHGUI_GenericHypothesisCreator::onDialogFinished( int /*result*/ )
255 {
256   if ( myEventLoop )
257     myEventLoop->exit();
258 }
259
260 bool SMESHGUI_GenericHypothesisCreator::stdParams( ListOfStdParams& ) const
261 {
262   return false;
263 }
264
265 bool SMESHGUI_GenericHypothesisCreator::getStdParamFromDlg( ListOfStdParams& params ) const
266 {
267   bool res = true;
268   StdParam item;
269   ListOfWidgets::const_iterator anIt = widgets().begin(), aLast = widgets().end();
270   for( ; anIt!=aLast; anIt++ )
271   {
272     item.myName = (*anIt)->objectName();
273     if( (*anIt)->inherits( "QtxIntSpinBox" ) )
274     {
275       QtxIntSpinBox* sb = ( QtxIntSpinBox* )( *anIt );
276       item.myValue = sb->value();
277       params.append( item );
278     }
279     
280     else if( (*anIt)->inherits( "QtxDoubleSpinBox" ) )
281     {
282       QtxDoubleSpinBox* sb = ( QtxDoubleSpinBox* )( *anIt );
283       item.myValue = sb->value();
284       params.append( item );
285     }
286
287     else if( (*anIt)->inherits( "QLineEdit" ) )
288     {
289       QLineEdit* line = ( QLineEdit* )( *anIt );
290       item.myValue = line->text();
291       params.append( item );
292     }
293
294     else if ( getParamFromCustomWidget( item, *anIt ))
295     {
296       params.append( item );
297     }
298
299     else
300       res = false;
301   }
302   return res;
303 }
304
305 QString SMESHGUI_GenericHypothesisCreator::stdParamValues( const ListOfStdParams& params)
306 {
307   QString valueStr = "";
308   ListOfStdParams::const_iterator param = params.begin(), aLast = params.end();
309   uint len0 = 0;
310   for( int i=0; param!=aLast; param++, i++ )
311   {
312     if ( valueStr.length() > len0 ) {
313       valueStr += "; ";
314       len0 = valueStr.length();
315     }
316     switch( (*param).myValue.type() )
317     {
318     case QVariant::Int:
319       valueStr += valueStr.number( (*param).myValue.toInt() );
320       break;
321     case QVariant::Double:
322       valueStr += valueStr.number( (*param).myValue.toDouble() );
323       break;
324     case QVariant::String:
325       valueStr += (*param).myValue.toString();
326       break;
327     default:
328       QVariant valCopy = (*param).myValue;
329       valueStr += valCopy.toString();
330     }
331   }
332   return valueStr;
333 }
334
335 SMESH::SMESH_Hypothesis_var SMESHGUI_GenericHypothesisCreator::hypothesis() const
336 {
337   return myHypo;
338 }
339
340 SMESH::SMESH_Hypothesis_var SMESHGUI_GenericHypothesisCreator::initParamsHypothesis() const
341 {
342   if ( CORBA::is_nil( myInitParamsHypo ))
343     return myHypo;
344   return myInitParamsHypo;
345 }
346
347 QString SMESHGUI_GenericHypothesisCreator::hypType() const
348 {
349   return myHypType;
350 }
351
352 QString SMESHGUI_GenericHypothesisCreator::hypName() const
353 {
354   return myHypName;
355 }
356
357 const SMESHGUI_GenericHypothesisCreator::ListOfWidgets& SMESHGUI_GenericHypothesisCreator::widgets() const
358 {
359   return myParamWidgets;
360 }
361
362 SMESHGUI_GenericHypothesisCreator::ListOfWidgets& SMESHGUI_GenericHypothesisCreator::changeWidgets()
363 {
364   return myParamWidgets;
365 }
366
367 QtxDialog* SMESHGUI_GenericHypothesisCreator:: dlg() const
368
369   return myDlg;
370 }
371
372 bool SMESHGUI_GenericHypothesisCreator::isCreation() const
373 {
374   return myIsCreate;
375 }
376
377 void SMESHGUI_GenericHypothesisCreator::attuneStdWidget( QWidget*, const int ) const
378 {
379 }
380
381 QString SMESHGUI_GenericHypothesisCreator::caption() const
382 {
383   return QString();
384 }
385
386 QPixmap SMESHGUI_GenericHypothesisCreator::icon() const
387 {
388   return QPixmap();
389 }
390
391 QString SMESHGUI_GenericHypothesisCreator::type() const
392 {
393   return QString();
394 }
395 QWidget* SMESHGUI_GenericHypothesisCreator::getCustomWidget( const StdParam & /*param*/,
396                                                              QWidget*   /*parent*/,
397                                                              const int  /*index*/) const
398 {
399   return 0;
400 }
401 bool SMESHGUI_GenericHypothesisCreator::getParamFromCustomWidget( StdParam&, QWidget* ) const
402 {
403   return false;
404 }
405
406 void SMESHGUI_GenericHypothesisCreator::onReject()
407 {
408 }
409
410 QString SMESHGUI_GenericHypothesisCreator::helpPage() const
411 {
412   QString aHypType = hypType();
413   QString aHelpFileName;
414   if ( aHypType == "LocalLength" )
415     aHelpFileName = "a1d_meshing_hypo_page.html#average_length_anchor";
416   else if ( aHypType == "Arithmetic1D")
417     aHelpFileName = "a1d_meshing_hypo_page.html#arithmetic_1d_anchor";
418   else if ( aHypType == "MaxElementArea")
419     aHelpFileName = "a2d_meshing_hypo_page.html#max_element_area_anchor";
420   else if ( aHypType == "MaxElementVolume")
421     aHelpFileName = "max_element_volume_hypo_page.html";
422   else if ( aHypType == "StartEndLength")
423     aHelpFileName = "a1d_meshing_hypo_page.html#start_and_end_length_anchor";
424   else if ( aHypType == "Deflection1D")
425     aHelpFileName = "a1d_meshing_hypo_page.html#deflection_1d_anchor";
426   else if ( aHypType == "AutomaticLength")
427     aHelpFileName = "a1d_meshing_hypo_page.html#automatic_length_anchor";
428   else if ( aHypType == "NumberOfSegments")
429     aHelpFileName = "a1d_meshing_hypo_page.html#number_of_segments_anchor";
430   else if ( aHypType == "ProjectionSource1D")
431     aHelpFileName = "projection_algos_page.html";
432   else if ( aHypType == "ProjectionSource2D")
433     aHelpFileName = "projection_algos_page.html";
434   else if ( aHypType == "ProjectionSource3D")
435     aHelpFileName = "projection_algos_page.html";
436   else if ( aHypType == "NumberOfLayers")
437     aHelpFileName = "radial_prism_algo_page.html";
438   else if ( aHypType == "LayerDistribution")
439     aHelpFileName = "radial_prism_algo_page.html";
440   else if ( aHypType == "SegmentLengthAroundVertex")
441     aHelpFileName = "segments_around_vertex_algo.html";
442   else
443     aHelpFileName = "";
444   return aHelpFileName;
445 }
446
447
448
449
450 SMESHGUI_HypothesisDlg::SMESHGUI_HypothesisDlg( SMESHGUI_GenericHypothesisCreator* creator, QWidget* parent )
451 : QtxDialog( parent, false, true ),
452   myCreator( creator )
453 {
454   setMinimumSize( 300, height() );
455 //  setFixedSize( 300, height() );
456   QVBoxLayout* topLayout = new QVBoxLayout( mainFrame() );
457   topLayout->setMargin( 0 );
458   topLayout->setSpacing( 0 );
459
460   QFrame* titFrame = new QFrame( mainFrame() );
461   QHBoxLayout* titLay = new QHBoxLayout( titFrame );
462   titLay->setMargin( 0 );
463   titLay->setSpacing( SPACING );
464   
465   myIconLabel = new QLabel( titFrame );
466   myIconLabel->setScaledContents( false );
467   myIconLabel->setSizePolicy( QSizePolicy( QSizePolicy::Fixed, QSizePolicy::Fixed ) );
468   myTypeLabel = new QLabel( titFrame );
469   if( creator )
470     myTypeLabel->setText( creator->hypType() );
471
472   titLay->addWidget( myIconLabel, 0 );
473   titLay->addWidget( myTypeLabel, 0 );
474   titLay->addStretch( 1 );
475
476   topLayout->addWidget( titFrame, 0 );
477
478   myHelpFileName = creator->helpPage();
479
480   connect( this, SIGNAL( dlgHelp() ), this, SLOT( onHelp() ) );
481 }
482
483 SMESHGUI_HypothesisDlg::~SMESHGUI_HypothesisDlg()
484 {
485 }
486
487 void SMESHGUI_HypothesisDlg::setCustomFrame( QFrame* f )
488 {
489   if( f )
490   {
491     f->setParent( mainFrame() );
492     qobject_cast<QVBoxLayout*>( mainFrame()->layout() )->insertWidget( 1, f, 1 );
493   }
494 }
495
496 void SMESHGUI_HypothesisDlg::accept()
497 {
498   if ( myCreator && !myCreator->checkParams() )
499     return;
500   QtxDialog::accept();
501 }
502
503 void SMESHGUI_HypothesisDlg::reject()
504 {
505   if ( myCreator ) myCreator->onReject();
506   QtxDialog::reject();
507 }
508
509 void SMESHGUI_HypothesisDlg::onHelp()
510 {
511   LightApp_Application* app = (LightApp_Application*)(SUIT_Session::session()->activeApplication());
512   if (app) {
513     SMESHGUI* aSMESHGUI = dynamic_cast<SMESHGUI*>( app->activeModule() );
514     app->onHelpContextModule(aSMESHGUI ? app->moduleName(aSMESHGUI->moduleName()) : QString(""), myHelpFileName);
515   }
516   else {
517     QString platform;
518 #ifdef WIN32
519     platform = "winapplication";
520 #else
521     platform = "application";
522 #endif
523     SUIT_MessageBox::warning(this, tr("WRN_WARNING"),
524                              tr("EXTERNAL_BROWSER_CANNOT_SHOW_PAGE").
525                              arg(app->resourceMgr()->stringValue("ExternalBrowser", 
526                                                                  platform)).
527                              arg(myHelpFileName));
528   }
529 }
530
531 void SMESHGUI_HypothesisDlg::setHIcon( const QPixmap& p )
532 {
533   myIconLabel->setPixmap( p );  
534 }
535
536 void SMESHGUI_HypothesisDlg::setType( const QString& t )
537 {
538   myTypeLabel->setText( t );
539 }
540
541 HypothesisData::HypothesisData( const QString& theTypeName,
542                                 const QString& thePluginName,
543                                 const QString& theServerLibName,
544                                 const QString& theClientLibName,
545                                 const QString& theLabel,
546                                 const QString& theIconId,
547                                 const QList<int>& theDim,
548                                 const bool theIsAux,
549                                 const QStringList& theNeededHypos,
550                                 const QStringList& theOptionalHypos,
551                                 const QStringList& theInputTypes,
552                                 const QStringList& theOutputTypes,
553                                 const bool theIsNeedGeometry,
554                                 const bool supportSub)
555   : TypeName( theTypeName ),
556     PluginName( thePluginName ),
557     ServerLibName( theServerLibName ),
558     ClientLibName( theClientLibName ),
559     Label( theLabel ),
560     IconId( theIconId ),
561     Dim( theDim ),
562     IsAux( theIsAux ),
563     NeededHypos( theNeededHypos ), 
564     OptionalHypos( theOptionalHypos ),
565     InputTypes( theInputTypes ),
566     OutputTypes( theOutputTypes ),
567     IsNeedGeometry( theIsNeedGeometry ),
568     IsSupportSubmeshes( supportSub )
569 {
570 }
571
572 HypothesesSet::HypothesesSet( const QString& theSetName ) 
573   : HypoSetName( theSetName )
574 {
575 }
576
577 HypothesesSet::HypothesesSet( const QString&     theSetName,
578                               const QStringList& theHypoList,
579                               const QStringList& theAlgoList )
580   : HypoSetName( theSetName ), 
581     HypoList( theHypoList ), 
582     AlgoList( theAlgoList )
583 {
584 }