Salome HOME
Add possibility to define Local Size via a file
[plugins/netgenplugin.git] / src / GUI / NETGENPluginGUI_HypothesisCreator.cxx
1 // Copyright (C) 2007-2016  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, or (at your option) any later version.
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 //  NETGENPlugin GUI: GUI for plugged-in mesher NETGENPlugin
24 //  File   : NETGENPluginGUI_HypothesisCreator.cxx
25 //  Author : Michael Zorin
26 //  Module : NETGENPlugin
27 //
28 #include "NETGENPluginGUI_HypothesisCreator.h"
29
30 #include <SMESHGUI_Utils.h>
31 #include <SMESHGUI_HypothesesUtils.h>
32 #include <SMESHGUI_SpinBox.h>
33 #include <GeomSelectionTools.h>
34
35 #include CORBA_SERVER_HEADER(NETGENPlugin_Algorithm)
36
37 #include <SUIT_FileDlg.h>
38 #include <SUIT_ResourceMgr.h>
39 #include <SUIT_Session.h>
40
41 #include <SalomeApp_Tools.h>
42 #include <LightApp_SelectionMgr.h>
43 #include <SALOME_ListIO.hxx>
44
45 #include <QComboBox>
46 #include <QLabel>
47 #include <QGroupBox>
48 #include <QFrame>
49 #include <QLayout>
50 #include <QLineEdit>
51 #include <QCheckBox>
52 #include <QPixmap>
53 #include <QTableWidget>
54 #include <QHeaderView>
55 #include <QPushButton>
56
57 enum Fineness
58   {
59     VeryCoarse,
60     Coarse,
61     Moderate,
62     Fine,
63     VeryFine,
64     UserDefined
65   };
66
67 enum {
68   STD_TAB = 0,
69   LSZ_TAB
70 };
71
72 enum {
73   LSZ_ENTRY_COLUMN = 0,
74   LSZ_NAME_COLUMN,
75   LSZ_LOCALSIZE_COLUMN,
76   LSZ_NB_COLUMNS
77 };
78
79 enum {
80   LSZ_BTNS = 0,
81   LSZ_VERTEX_BTN,
82   LSZ_EDGE_BTN,
83   LSZ_FACE_BTN,
84   LSZ_SOLID_BTN,
85   LSZ_SEPARATOR2,
86   LSZ_REMOVE_BTN,
87   LSZ_FILE_LE = 9
88 };
89
90 NETGENPluginGUI_HypothesisCreator::NETGENPluginGUI_HypothesisCreator( const QString& theHypType )
91   : SMESHGUI_GenericHypothesisCreator( theHypType )
92 {
93   myGeomSelectionTools = NULL;
94   myLocalSizeMap.clear();
95   myIs2D   = ( theHypType.startsWith("NETGEN_Parameters_2D"));
96   myIsONLY = ( theHypType == "NETGEN_Parameters_2D_ONLY" ||
97                theHypType == "NETGEN_Parameters_3D");
98 }
99
100 NETGENPluginGUI_HypothesisCreator::~NETGENPluginGUI_HypothesisCreator()
101 {
102 }
103
104 bool NETGENPluginGUI_HypothesisCreator::checkParams(QString& msg) const
105 {
106   NetgenHypothesisData data_old, data_new;
107   readParamsFromHypo( data_old );
108   readParamsFromWidgets( data_new );
109   bool res = storeParamsToHypo( data_new );
110   //storeParamsToHypo( data_old ); -- issue 0021364: Dump of netgen parameters has duplicate lines
111   
112   res = myMaxSize->isValid(msg,true) && res;
113   res = myMinSize->isValid(msg,true) && res;
114   res = myGrowthRate->isValid(msg,true) && res; ;
115   if ( myNbSegPerEdge )
116     res = myNbSegPerEdge->isValid(msg,true) && res;
117   if ( myNbSegPerRadius )
118     res = myNbSegPerRadius->isValid(msg,true) && res;
119
120   if ( !res ) //  -- issue 0021364: Dump of netgen parameters has duplicate lines
121     storeParamsToHypo( data_old );
122
123   return res;
124 }
125
126 QFrame* NETGENPluginGUI_HypothesisCreator::buildFrame()
127 {
128   QFrame* fr = new QFrame( 0 );
129   fr->setObjectName( "myframe" );
130   QVBoxLayout* lay = new QVBoxLayout( fr );
131   lay->setMargin( 5 );
132   lay->setSpacing( 0 );
133
134   QTabWidget* tab = new QTabWidget( fr );
135   tab->setTabShape( QTabWidget::Rounded );
136   tab->setTabPosition( QTabWidget::North );
137   lay->addWidget( tab );
138   QWidget* GroupC1 = new QWidget();
139   tab->insertTab( STD_TAB, GroupC1, tr( "SMESH_ARGUMENTS" ) );
140   
141   QGridLayout* aGroupLayout = new QGridLayout( GroupC1 );
142   aGroupLayout->setSpacing( 6 );
143   aGroupLayout->setMargin( 11 );
144   
145   int row = 0;
146   myName = 0;
147   if( isCreation() )
148   {
149     aGroupLayout->addWidget( new QLabel( tr( "SMESH_NAME" ), GroupC1 ), row, 0 );
150     myName = new QLineEdit( GroupC1 );
151     myName->setMinimumWidth(160);
152     aGroupLayout->addWidget( myName, row, 1 );
153     row++;
154   }
155
156   aGroupLayout->addWidget( new QLabel( tr( "NETGEN_MAX_SIZE" ), GroupC1 ), row, 0 );
157   myMaxSize = new SMESHGUI_SpinBox( GroupC1 );
158   myMaxSize->RangeStepAndValidator( 1e-07, 1e+06, 10., "length_precision" );
159   aGroupLayout->addWidget( myMaxSize, row, 1 );
160   row++;
161
162   aGroupLayout->addWidget( new QLabel( tr( "NETGEN_MIN_SIZE" ), GroupC1 ), row, 0 );
163   myMinSize = new SMESHGUI_SpinBox( GroupC1 );
164   myMinSize->RangeStepAndValidator( 0.0, 1e+06, 10., "length_precision" );
165   aGroupLayout->addWidget( myMinSize, row, 1 );
166   row++;
167
168   mySecondOrder = 0;
169   if ( !myIsONLY )
170   {
171     mySecondOrder = new QCheckBox( tr( "NETGEN_SECOND_ORDER" ), GroupC1 );
172     aGroupLayout->addWidget( mySecondOrder, row, 0, 1, 2 );
173     row++;
174   }
175
176   aGroupLayout->addWidget( new QLabel( tr( "NETGEN_FINENESS" ), GroupC1 ), row, 0 );
177   myFineness = new QComboBox( GroupC1 );
178   QStringList types;
179   types << tr( "NETGEN_VERYCOARSE" ) << tr( "NETGEN_COARSE" )   << tr( "NETGEN_MODERATE" ) <<
180            tr( "NETGEN_FINE" )       << tr( "NETGEN_VERYFINE" ) << tr( "NETGEN_CUSTOM" );
181   myFineness->addItems( types );
182   aGroupLayout->addWidget( myFineness, row, 1 );
183   connect( myFineness, SIGNAL( activated( int ) ), this, SLOT( onFinenessChanged() ) );
184   row++;
185
186   aGroupLayout->addWidget( new QLabel( tr( "NETGEN_GROWTH_RATE" ), GroupC1 ), row, 0 );
187   myGrowthRate = new SMESHGUI_SpinBox( GroupC1 );
188   myGrowthRate->RangeStepAndValidator( .0001, 10., .1, "parametric_precision" );
189   aGroupLayout->addWidget( myGrowthRate, row, 1 );
190   row++;
191
192   myNbSegPerEdge = 0;
193   myNbSegPerRadius = 0;
194   if ( !myIsONLY )
195   {
196     const double VALUE_MAX = 1.0e+6;
197
198     aGroupLayout->addWidget( new QLabel( tr( "NETGEN_SEG_PER_EDGE" ), GroupC1 ), row, 0 );
199     myNbSegPerEdge = new SMESHGUI_SpinBox( GroupC1 );
200     myNbSegPerEdge->RangeStepAndValidator( .2, VALUE_MAX, .1, "parametric_precision" );
201     aGroupLayout->addWidget( myNbSegPerEdge, row, 1 );
202     row++;
203
204     aGroupLayout->addWidget( new QLabel( tr( "NETGEN_SEG_PER_RADIUS" ), GroupC1 ), row, 0 );
205     myNbSegPerRadius = new SMESHGUI_SpinBox( GroupC1 );
206     myNbSegPerRadius->RangeStepAndValidator( .2, VALUE_MAX, .1, "parametric_precision" );
207     aGroupLayout->addWidget( myNbSegPerRadius, row, 1 );
208     row++;
209   }
210
211   mySurfaceCurvature = 0;
212   if ( myIs2D || !myIsONLY )
213   {
214     mySurfaceCurvature = new QCheckBox( tr( "NETGEN_SURFACE_CURVATURE" ), GroupC1 );
215     aGroupLayout->addWidget( mySurfaceCurvature, row, 0, 1, 2 );
216     connect( mySurfaceCurvature, SIGNAL( stateChanged( int ) ), this, SLOT( onSurfaceCurvatureChanged() ) );
217     row++;
218   }
219
220   myAllowQuadrangles = 0;
221   if ( myIs2D || !myIsONLY ) // disable only for NETGEN 3D
222   {
223     myAllowQuadrangles = new QCheckBox( tr( "NETGEN_ALLOW_QUADRANGLES" ), GroupC1 );
224     aGroupLayout->addWidget( myAllowQuadrangles, row, 0, 1, 2 );
225     row++;
226   }
227
228   myOptimize = new QCheckBox( tr( "NETGEN_OPTIMIZE" ), GroupC1 );
229   aGroupLayout->addWidget( myOptimize, row, 0, 1, 2 );
230   row++;
231
232   myFuseEdges = 0;
233   if (!myIsONLY)
234   {
235     myFuseEdges = new QCheckBox( tr( "NETGEN_FUSE_EDGES" ), GroupC1 );
236     aGroupLayout->addWidget( myFuseEdges, row, 0, 1, 2 );
237     row++;
238   }
239
240   myLocalSizeTable = 0;
241   //if ( !myIsONLY )
242   {
243     QWidget* localSizeGroup = new QWidget();
244     QGridLayout* localSizeLayout = new QGridLayout(localSizeGroup);
245
246     myLocalSizeTable = new QTableWidget(0, LSZ_NB_COLUMNS, localSizeGroup);
247     localSizeLayout->addWidget(myLocalSizeTable, 1, 0, 8, 2);
248     QStringList localSizeHeaders;
249     localSizeHeaders << tr( "LSZ_ENTRY_COLUMN" )<< tr( "LSZ_NAME_COLUMN" ) << tr( "LSZ_LOCALSIZE_COLUMN" );
250     myLocalSizeTable->setHorizontalHeaderLabels(localSizeHeaders);
251     myLocalSizeTable->horizontalHeader()->hideSection(LSZ_ENTRY_COLUMN);
252 #if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
253     myLocalSizeTable->horizontalHeader()->setResizeMode(QHeaderView::Interactive);
254 #else
255     myLocalSizeTable->horizontalHeader()->setSectionResizeMode(QHeaderView::Interactive);
256 #endif
257     myLocalSizeTable->resizeColumnToContents(LSZ_NAME_COLUMN);
258     myLocalSizeTable->resizeColumnToContents(LSZ_LOCALSIZE_COLUMN);
259     myLocalSizeTable->setAlternatingRowColors(true);
260     myLocalSizeTable->verticalHeader()->hide();
261
262     QPushButton* addVertexButton = new QPushButton(tr("NETGEN_LSZ_VERTEX"), localSizeGroup);
263     localSizeLayout->addWidget(addVertexButton, LSZ_VERTEX_BTN, 2, 1, 1);
264     QPushButton* addEdgeButton = new QPushButton(tr("NETGEN_LSZ_EDGE"), localSizeGroup);
265     localSizeLayout->addWidget(addEdgeButton, LSZ_EDGE_BTN, 2, 1, 1);
266     QPushButton* addFaceButton = new QPushButton(tr("NETGEN_LSZ_FACE"), localSizeGroup);
267     localSizeLayout->addWidget(addFaceButton, LSZ_FACE_BTN, 2, 1, 1);
268     QPushButton* addSolidButton = new QPushButton(tr("NETGEN_LSZ_SOLID"), localSizeGroup);
269     localSizeLayout->addWidget(addSolidButton, LSZ_SOLID_BTN, 2, 1, 1);
270
271     QFrame *line2 = new QFrame(localSizeGroup);
272     line2->setFrameShape(QFrame::HLine);
273     line2->setFrameShadow(QFrame::Sunken);
274     localSizeLayout->addWidget(line2, LSZ_SEPARATOR2, 2, 1, 1);
275
276     QPushButton* removeButton = new QPushButton(tr("NETGEN_LSZ_REMOVE"), localSizeGroup);
277     localSizeLayout->addWidget(removeButton, LSZ_REMOVE_BTN, 2, 1, 1);
278
279     QPushButton* fileBtn = new QPushButton(tr("NETGEN_LSZ_FILE"), localSizeGroup);
280     myMeshSizeFile = new QLineEdit(localSizeGroup);
281     myMeshSizeFile->setReadOnly( true );
282     localSizeLayout->addWidget( fileBtn, LSZ_FILE_LE, 0, 1, 1);
283     localSizeLayout->addWidget( myMeshSizeFile, LSZ_FILE_LE, 1, 1, 2);
284
285     connect( addVertexButton, SIGNAL(clicked()), this, SLOT(onAddLocalSizeOnVertex()));
286     connect( addEdgeButton, SIGNAL(clicked()), this, SLOT(onAddLocalSizeOnEdge()));
287     connect( addFaceButton, SIGNAL(clicked()), this, SLOT(onAddLocalSizeOnFace()));
288     connect( addSolidButton, SIGNAL(clicked()), this, SLOT(onAddLocalSizeOnSolid()));
289     connect( removeButton, SIGNAL(clicked()), this, SLOT(onRemoveLocalSizeOnShape()));
290     connect( myLocalSizeTable, SIGNAL(cellChanged(int, int)), this, SLOT(onSetLocalSize(int, int)));
291     connect( fileBtn, SIGNAL(clicked()), this, SLOT(onSetSizeFile()));
292
293     tab->insertTab(LSZ_TAB, localSizeGroup, tr("NETGEN_LOCAL_SIZE"));
294   }
295   return fr;
296 }
297
298 void NETGENPluginGUI_HypothesisCreator::retrieveParams() const
299 {
300   NetgenHypothesisData data;
301   readParamsFromHypo( data );
302
303   if( myName )
304     myName->setText( data.myName );
305   if(data.myMaxSizeVar.isEmpty())
306     myMaxSize->setValue( data.myMaxSize );
307   else
308     myMaxSize->setText( data.myMaxSizeVar );
309
310   if(data.myMinSizeVar.isEmpty())
311     myMinSize->setValue( data.myMinSize );
312   else
313     myMinSize->setText( data.myMinSizeVar );
314
315   if ( mySecondOrder )
316     mySecondOrder->setChecked( data.mySecondOrder );
317   if ( myOptimize )
318     myOptimize->setChecked( data.myOptimize );
319   myFineness->setCurrentIndex( data.myFineness );
320
321   if(data.myGrowthRateVar.isEmpty())
322     myGrowthRate->setValue( data.myGrowthRate );
323   else
324     myGrowthRate->setText( data.myGrowthRateVar );
325
326   if ( myNbSegPerEdge )
327   {
328     if(data.myNbSegPerEdgeVar.isEmpty())
329       myNbSegPerEdge->setValue( data.myNbSegPerEdge );
330     else
331       myNbSegPerEdge->setText( data.myNbSegPerEdgeVar );
332   }
333   if ( myNbSegPerRadius )
334   {
335     if(data.myNbSegPerRadiusVar.isEmpty())
336       myNbSegPerRadius->setValue( data.myNbSegPerRadius );
337     else
338       myNbSegPerRadius->setText( data.myNbSegPerRadiusVar );
339   }
340   if (myAllowQuadrangles)
341     myAllowQuadrangles->setChecked( data.myAllowQuadrangles );
342
343   if (mySurfaceCurvature)
344     mySurfaceCurvature->setChecked( data.mySurfaceCurvature );
345
346   if (myFuseEdges)
347     myFuseEdges->setChecked( data.myFuseEdges );
348
349   // update widgets
350   ((NETGENPluginGUI_HypothesisCreator*) this )-> onSurfaceCurvatureChanged();
351
352   if ( myLocalSizeTable )
353   {
354     NETGENPluginGUI_HypothesisCreator* that = (NETGENPluginGUI_HypothesisCreator*)this;
355     QMapIterator<QString, QString> i(myLocalSizeMap);
356     GeomSelectionTools* geomSelectionTools = that->getGeomSelectionTools();
357     while (i.hasNext()) {
358       i.next();
359       const QString entry = i.key();
360       std::string shapeName = geomSelectionTools->getNameFromEntry(entry.toStdString());
361       const QString localSize = i.value();
362       int row = myLocalSizeTable->rowCount();
363       myLocalSizeTable->setRowCount(row+1);
364       myLocalSizeTable->setItem(row, LSZ_ENTRY_COLUMN, new QTableWidgetItem(entry));
365       myLocalSizeTable->item(row, LSZ_ENTRY_COLUMN)->setFlags(0);
366       myLocalSizeTable->setItem(row, LSZ_NAME_COLUMN, new QTableWidgetItem(QString::fromStdString(shapeName)));
367       myLocalSizeTable->item(row, LSZ_NAME_COLUMN)->setFlags(0);
368       myLocalSizeTable->setItem(row, LSZ_LOCALSIZE_COLUMN, new QTableWidgetItem(localSize));
369       myLocalSizeTable->item(row, LSZ_LOCALSIZE_COLUMN)->setFlags(Qt::ItemIsSelectable|Qt::ItemIsEditable|Qt::ItemIsEnabled);
370     }
371     myLocalSizeTable->resizeColumnToContents(LSZ_NAME_COLUMN);
372     myLocalSizeTable->resizeColumnToContents(LSZ_LOCALSIZE_COLUMN);
373
374     myMeshSizeFile->setText( data.myMeshSizeFile );
375   }
376 }
377
378 QString NETGENPluginGUI_HypothesisCreator::storeParams() const
379 {
380   NetgenHypothesisData data;
381   readParamsFromWidgets( data );
382   storeParamsToHypo( data );
383
384   QString valStr = tr("NETGEN_MAX_SIZE") + " = " + QString::number( data.myMaxSize ) + "; ";
385   valStr += tr("NETGEN_MIN_SIZE") + " = " + QString::number( data.myMinSize ) + "; ";
386   if ( data.mySecondOrder )
387     valStr +=  tr("NETGEN_SECOND_ORDER") + "; ";
388   if ( data.myOptimize )
389     valStr +=  tr("NETGEN_OPTIMIZE") + "; ";
390   valStr += myFineness->currentText() + "(" +  QString::number( data.myGrowthRate )     + ", " +
391     QString::number( data.myNbSegPerEdge )   + ", " +
392     QString::number( data.myNbSegPerRadius ) + ")";
393
394   if ( myIs2D && data.myAllowQuadrangles )
395     valStr += "; " + tr("NETGEN_ALLOW_QUADRANGLES");
396
397   if ( data.mySurfaceCurvature )
398     valStr += "; " + tr("NETGEN_SURFACE_CURVATURE");
399
400   if ( data.myFuseEdges )
401     valStr += "; " + tr("NETGEN_FUSE_EDGES");
402
403   return valStr;
404 }
405
406 bool NETGENPluginGUI_HypothesisCreator::readParamsFromHypo( NetgenHypothesisData& h_data ) const
407 {
408   NETGENPlugin::NETGENPlugin_Hypothesis_var h =
409     NETGENPlugin::NETGENPlugin_Hypothesis::_narrow( initParamsHypothesis() );
410
411   //HypothesisData* data = SMESH::GetHypothesisData( hypType() );
412   h_data.myName = isCreation() ? hypName() : "";
413
414   h_data.myMaxSize = h->GetMaxSize();
415   h_data.myMaxSizeVar = getVariableName("SetMaxSize");
416   h_data.mySecondOrder = h->GetSecondOrder();
417   h_data.myOptimize = h->GetOptimize();
418
419   h_data.myFineness = (int) h->GetFineness();
420   h_data.myGrowthRate = h->GetGrowthRate();
421   h_data.myGrowthRateVar = getVariableName("SetGrowthRate");
422   h_data.myNbSegPerEdge = h->GetNbSegPerEdge();
423   h_data.myNbSegPerEdgeVar  = getVariableName("SetNbSegPerEdge");
424   h_data.myNbSegPerRadius = h->GetNbSegPerRadius();
425   h_data.myNbSegPerRadiusVar = getVariableName("SetNbSegPerRadius");
426   h_data.myMinSize = h->GetMinSize();
427   h_data.myMinSizeVar = getVariableName("SetMinSize");
428   h_data.mySurfaceCurvature = h->GetUseSurfaceCurvature();
429   h_data.myFuseEdges = h->GetFuseEdges();
430   h_data.myMeshSizeFile = h->GetMeshSizeFile();
431
432   //if ( myIs2D )
433   {
434     NETGENPlugin::NETGENPlugin_Hypothesis_var h =
435       NETGENPlugin::NETGENPlugin_Hypothesis::_narrow( initParamsHypothesis() );
436
437     if ( !h->_is_nil() )
438       h_data.myAllowQuadrangles = h->GetQuadAllowed();
439   }
440
441   NETGENPluginGUI_HypothesisCreator*  that = (NETGENPluginGUI_HypothesisCreator*)this;
442   NETGENPlugin::string_array_var myEntries = h->GetLocalSizeEntries();
443   for ( size_t i = 0; i < myEntries->length(); i++ )
444   {
445     QString entry = myEntries[i].in();
446     double val = h->GetLocalSizeOnEntry(entry.toStdString().c_str());
447     std::ostringstream tmp;
448     tmp << val;
449     QString valstring = QString::fromStdString(tmp.str());
450     if (myLocalSizeMap.contains(entry))
451     {
452       if (myLocalSizeMap[entry] == "__TO_DELETE__")
453       {
454         continue;
455       }
456     }
457     that->myLocalSizeMap[entry] = valstring;
458   }
459
460   return true;
461 }
462
463 bool NETGENPluginGUI_HypothesisCreator::storeParamsToHypo( const NetgenHypothesisData& h_data ) const
464 {
465   NETGENPlugin::NETGENPlugin_Hypothesis_var h =
466     NETGENPlugin::NETGENPlugin_Hypothesis::_narrow( hypothesis() );
467
468   bool ok = true;
469   try
470   {
471     if( isCreation() )
472       SMESH::SetName( SMESH::FindSObject( h ), h_data.myName.toLatin1().data() );
473     h->SetVarParameter( h_data.myMaxSizeVar.toLatin1().constData(), "SetMaxSize");
474     h->SetMaxSize     ( h_data.myMaxSize );
475     h->SetSecondOrder ( h_data.mySecondOrder );
476     h->SetOptimize    ( h_data.myOptimize );
477     int fineness = h_data.myFineness;
478     h->SetFineness    ( fineness );
479
480     if( fineness==UserDefined )
481     {
482       h->SetVarParameter  ( h_data.myGrowthRateVar.toLatin1().constData(), "SetGrowthRate");
483       h->SetGrowthRate    ( h_data.myGrowthRate );
484       h->SetVarParameter  ( h_data.myNbSegPerEdgeVar.toLatin1().constData(), "SetNbSegPerEdge");
485       h->SetNbSegPerEdge  ( h_data.myNbSegPerEdge );
486       h->SetVarParameter  ( h_data.myNbSegPerRadiusVar.toLatin1().constData(), "SetNbSegPerRadius");
487       h->SetNbSegPerRadius( h_data.myNbSegPerRadius );
488     }
489     h->SetVarParameter       ( h_data.myMinSizeVar.toLatin1().constData(), "SetMinSize");
490     h->SetMinSize            ( h_data.myMinSize );
491     h->SetUseSurfaceCurvature( h_data.mySurfaceCurvature );
492     h->SetFuseEdges          ( h_data.myFuseEdges );
493     h->SetMeshSizeFile       ( h_data.myMeshSizeFile.toUtf8().constData() );
494
495     //if ( myIs2D )
496     {
497       // NETGENPlugin::NETGENPlugin_Hypothesis_2D_var h_2d =
498       //   NETGENPlugin::NETGENPlugin_Hypothesis_2D::_narrow( h );
499
500       // if ( !h_2d->_is_nil() )
501       //   h_2d->SetQuadAllowed( h_data.myAllowQuadrangles );
502       h->SetQuadAllowed( h_data.myAllowQuadrangles );
503     }
504
505     QMapIterator<QString,QString> i(myLocalSizeMap);
506     while (i.hasNext()) {
507       i.next();
508       const QString entry = i.key();
509       const QString localSize = i.value();
510       if (localSize == "__TO_DELETE__")
511       {
512         h->UnsetLocalSizeOnEntry(entry.toLatin1().constData());
513       }
514       else
515       {
516         std::istringstream tmp(localSize.toLatin1().constData());
517         double val;
518         tmp >> val;
519         h->SetLocalSizeOnEntry(entry.toLatin1().constData(), val);
520       }
521     }
522   }
523   catch(const SALOME::SALOME_Exception& ex)
524   {
525     SalomeApp_Tools::QtCatchCorbaException(ex);
526     ok = false;
527   }
528   return ok;
529 }
530
531 bool NETGENPluginGUI_HypothesisCreator::readParamsFromWidgets( NetgenHypothesisData& h_data ) const
532 {
533   h_data.myName           = myName ? myName->text() : "";
534   h_data.myMaxSize        = myMaxSize->value();
535   h_data.myMaxSizeVar     = myMaxSize->text();
536   h_data.myMinSize        = myMinSize->value();
537   h_data.myMinSizeVar     = myMinSize->text();
538   if ( mySecondOrder )
539     h_data.mySecondOrder  = mySecondOrder->isChecked();
540   if ( myOptimize )
541     h_data.myOptimize     = myOptimize->isChecked();
542   h_data.myFineness       = myFineness->currentIndex();
543   h_data.myGrowthRate     = myGrowthRate->value();
544   if ( myNbSegPerEdge )
545     h_data.myNbSegPerEdge = myNbSegPerEdge->value();
546   if ( myNbSegPerRadius )
547     h_data.myNbSegPerRadius = myNbSegPerRadius->value();
548
549   h_data.myGrowthRateVar  = myGrowthRate->text();
550   if ( myNbSegPerEdge )
551     h_data.myNbSegPerEdgeVar = myNbSegPerEdge->text();
552   if ( myNbSegPerRadius )
553     h_data.myNbSegPerRadiusVar = myNbSegPerRadius->text();
554
555   
556   if ( myAllowQuadrangles )
557     h_data.myAllowQuadrangles = myAllowQuadrangles->isChecked();
558
559   if ( mySurfaceCurvature )
560     h_data.mySurfaceCurvature = mySurfaceCurvature->isChecked();
561
562   if ( myFuseEdges )
563     h_data.myFuseEdges = myFuseEdges->isChecked();
564
565   if ( myLocalSizeTable )
566   {
567     NETGENPluginGUI_HypothesisCreator* that = (NETGENPluginGUI_HypothesisCreator*)this;
568     int nbRows = myLocalSizeTable->rowCount();
569     for(int row=0 ; row < nbRows ; row++)
570     {
571       QString entry = myLocalSizeTable->item(row, LSZ_ENTRY_COLUMN)->text();
572       QString localSize = myLocalSizeTable->item(row, LSZ_LOCALSIZE_COLUMN)->text().trimmed();
573       that->myLocalSizeMap[entry] = localSize;
574     }
575     h_data.myMeshSizeFile = myMeshSizeFile->text();
576   }
577   return true;
578 }
579
580 void NETGENPluginGUI_HypothesisCreator::onSurfaceCurvatureChanged()
581 {
582   bool isSurfaceCurvature = (mySurfaceCurvature ? mySurfaceCurvature->isChecked() : true);
583   bool isCustom           = (myFineness->currentIndex() == UserDefined);
584   //myFineness->setEnabled(isSurfaceCurvature);
585   myGrowthRate->setEnabled(isCustom);
586   if ( myNbSegPerEdge )
587     myNbSegPerEdge->setEnabled(isCustom && isSurfaceCurvature);
588   if ( myNbSegPerRadius )
589     myNbSegPerRadius->setEnabled(isCustom && isSurfaceCurvature);
590 }
591
592 void NETGENPluginGUI_HypothesisCreator::onFinenessChanged()
593 {
594   bool isCustom = (myFineness->currentIndex() == UserDefined);
595   
596   myGrowthRate->setEnabled(isCustom);
597   if ( myNbSegPerEdge )
598     myNbSegPerEdge->setEnabled(isCustom);
599   if ( myNbSegPerRadius )
600     myNbSegPerRadius->setEnabled(isCustom);
601
602   if (!isCustom)
603     {
604       double aGrowthRate, aNbSegPerEdge, aNbSegPerRadius;
605       
606       switch ( myFineness->currentIndex() )
607         {
608         case VeryCoarse:
609           aGrowthRate = 0.7;
610           aNbSegPerEdge = 0.3;
611           aNbSegPerRadius = 1;
612           break;
613         case Coarse:
614           aGrowthRate = 0.5;
615           aNbSegPerEdge = 0.5;
616           aNbSegPerRadius = 1.5;
617           break;
618         case Fine:
619           aGrowthRate = 0.2;
620           aNbSegPerEdge = 2;
621           aNbSegPerRadius = 3;
622           break;
623         case VeryFine:
624           aGrowthRate = 0.1;
625           aNbSegPerEdge = 3;
626           aNbSegPerRadius = 5;
627           break;
628         case Moderate:
629         default:
630           aGrowthRate = 0.3;
631           aNbSegPerEdge = 1;
632           aNbSegPerRadius = 2;
633           break;
634         }
635       
636       myGrowthRate->setValue( aGrowthRate );
637       if ( myNbSegPerEdge )
638         myNbSegPerEdge->setValue( aNbSegPerEdge );
639       if ( myNbSegPerRadius )
640         myNbSegPerRadius->setValue( aNbSegPerRadius );
641     }
642 }
643
644 void NETGENPluginGUI_HypothesisCreator::onAddLocalSizeOnVertex()
645 {
646   addLocalSizeOnShape(TopAbs_VERTEX);
647 }
648
649 void NETGENPluginGUI_HypothesisCreator::onAddLocalSizeOnEdge()
650 {
651   addLocalSizeOnShape(TopAbs_EDGE);
652 }
653
654 void NETGENPluginGUI_HypothesisCreator::onAddLocalSizeOnFace()
655 {
656   addLocalSizeOnShape(TopAbs_FACE);
657 }
658
659 void NETGENPluginGUI_HypothesisCreator::onAddLocalSizeOnSolid()
660 {
661   addLocalSizeOnShape(TopAbs_SOLID);
662 }
663
664 void NETGENPluginGUI_HypothesisCreator::addLocalSizeOnShape(TopAbs_ShapeEnum typeShapeAsked)
665 {
666   NETGENPlugin::NETGENPlugin_Hypothesis_var h = NETGENPlugin::NETGENPlugin_Hypothesis::_narrow(initParamsHypothesis());
667   GeomSelectionTools* geomSelectionTools = getGeomSelectionTools();
668   LightApp_SelectionMgr* mySel = geomSelectionTools->selectionMgr();
669   SALOME_ListIO ListSelectedObjects;
670   mySel->selectedObjects(ListSelectedObjects, NULL, false );
671   SALOME_ListIteratorOfListIO Object_It(ListSelectedObjects);
672   for ( ; Object_It.More() ; Object_It.Next())
673     {
674       Handle(SALOME_InteractiveObject) anObject = Object_It.Value();
675       std::string entry, shapeName;
676       entry = geomSelectionTools->getEntryOfObject(anObject);
677       shapeName = anObject->getName();
678       TopAbs_ShapeEnum shapeType;
679       shapeType = geomSelectionTools->entryToShapeType(entry);
680       if (shapeType == TopAbs_SHAPE)
681         {
682           // E.A. if shapeType == TopAbs_SHAPE, it is NOT a TopoDS_Shape !!!
683           continue;
684         }
685       // --
686       if(shapeType != typeShapeAsked)
687         {
688           continue;
689         }
690       // --
691       myLocalSizeTable->setFocus();
692       QString shapeEntry;
693       shapeEntry = QString::fromStdString(entry);
694       if (myLocalSizeMap.contains(shapeEntry))
695         {
696           if (myLocalSizeMap[shapeEntry] != "__TO_DELETE__")
697             {
698               continue;
699             }
700         }
701       double phySize = h->GetMaxSize();
702       std::ostringstream oss;
703       oss << phySize;
704       QString localSize;
705       localSize  = QString::fromStdString(oss.str());
706       // --
707       int row = myLocalSizeTable->rowCount() ;
708       myLocalSizeTable->setRowCount(row+1);
709       myLocalSizeTable->setItem(row, LSZ_ENTRY_COLUMN, new QTableWidgetItem(shapeEntry));
710       myLocalSizeTable->item(row, LSZ_ENTRY_COLUMN )->setFlags(0);
711       myLocalSizeTable->setItem(row, LSZ_NAME_COLUMN, new QTableWidgetItem(QString::fromStdString(shapeName)));
712       myLocalSizeTable->item(row, LSZ_NAME_COLUMN )->setFlags(0);
713       myLocalSizeTable->setItem(row, LSZ_LOCALSIZE_COLUMN, new QTableWidgetItem(localSize));
714       myLocalSizeTable->item(row, LSZ_LOCALSIZE_COLUMN )->setFlags(Qt::ItemIsSelectable|Qt::ItemIsEditable|Qt::ItemIsEnabled);
715       myLocalSizeTable->resizeColumnToContents(LSZ_NAME_COLUMN);
716       myLocalSizeTable->resizeColumnToContents(LSZ_LOCALSIZE_COLUMN);
717       myLocalSizeTable->clearSelection();
718       myLocalSizeTable->scrollToItem( myLocalSizeTable->item( row, LSZ_LOCALSIZE_COLUMN ) );
719       // --
720     }
721 }
722
723 void NETGENPluginGUI_HypothesisCreator::onRemoveLocalSizeOnShape()
724 {
725   QList<int> selectedRows;
726   QList<QTableWidgetItem*> selected = myLocalSizeTable->selectedItems();
727   QTableWidgetItem* item;
728   int row;
729   foreach(item, selected) {
730     row = item->row();
731     if (!selectedRows.contains(row))
732       selectedRows.append( row );
733   }
734   qSort( selectedRows );
735   QListIterator<int> it( selectedRows );
736   it.toBack();
737   while (it.hasPrevious())
738     {
739       row = it.previous();
740       QString entry = myLocalSizeTable->item(row,LSZ_ENTRY_COLUMN)->text();
741       if (myLocalSizeMap.contains(entry))
742         {
743           myLocalSizeMap[entry] = "__TO_DELETE__";
744         }
745       myLocalSizeTable->removeRow(row );
746     }
747   myLocalSizeTable->resizeColumnToContents(LSZ_NAME_COLUMN);
748   myLocalSizeTable->resizeColumnToContents(LSZ_LOCALSIZE_COLUMN);
749 }
750
751 void NETGENPluginGUI_HypothesisCreator::onSetLocalSize(int row,int col)
752 {
753   if (col == LSZ_LOCALSIZE_COLUMN) {
754     QString entry = myLocalSizeTable->item(row, LSZ_ENTRY_COLUMN)->text();
755     QString localSize = myLocalSizeTable->item(row, LSZ_LOCALSIZE_COLUMN)->text().trimmed();
756     myLocalSizeMap[entry] = localSize;
757     myLocalSizeTable->resizeColumnToContents(LSZ_LOCALSIZE_COLUMN);
758   }
759 }
760
761 void NETGENPluginGUI_HypothesisCreator::onSetSizeFile()
762 {
763   QString dir = SUIT_FileDlg::getFileName( dlg(), QString(),
764                                            QStringList() << tr( "ALL_FILES_FILTER" ) + "  (*)");
765   myMeshSizeFile->setText( dir );
766 }
767
768 GeomSelectionTools* NETGENPluginGUI_HypothesisCreator::getGeomSelectionTools()
769 {
770   _PTR(Study) aStudy = SMESH::GetActiveStudyDocument();
771   if (myGeomSelectionTools == NULL || myGeomSelectionTools->getMyStudy() != aStudy) {
772     delete myGeomSelectionTools;
773     myGeomSelectionTools = new GeomSelectionTools(aStudy);
774   }
775   return myGeomSelectionTools;
776 }
777
778 QString NETGENPluginGUI_HypothesisCreator::caption() const
779 {
780   return tr( QString( "NETGEN_%1_TITLE" ).arg(myIs2D?QString("2D"):QString("3D")).toLatin1().data() );
781 }
782
783 QPixmap NETGENPluginGUI_HypothesisCreator::icon() const
784 {
785   QString hypIconName = tr( QString("ICON_DLG_NETGEN_PARAMETERS%1").arg(myIs2D?QString("_2D"):QString("")).toLatin1().data() );
786   return SUIT_Session::session()->resourceMgr()->loadPixmap( "NETGENPlugin", hypIconName );
787 }
788
789 QString NETGENPluginGUI_HypothesisCreator::type() const
790 {
791   return tr( QString( "NETGEN_%1_HYPOTHESIS" ).arg(myIs2D?QString("2D"):QString("3D")).toLatin1().data() );
792 }
793
794 QString NETGENPluginGUI_HypothesisCreator::helpPage() const
795 {
796   return "netgen_2d_3d_hypo_page.html";
797 }