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