]> SALOME platform Git repositories - modules/smesh.git/commitdiff
Salome HOME
PAL8238 - Hypothesis for non-regular 1D meshing
authorasl <asl@opencascade.com>
Wed, 23 Nov 2005 09:07:44 +0000 (09:07 +0000)
committerasl <asl@opencascade.com>
Wed, 23 Nov 2005 09:07:44 +0000 (09:07 +0000)
15 files changed:
src/SMESHGUI/Makefile.in
src/SMESHGUI/SMESHGUI_FunctionPreview.cxx [new file with mode: 0644]
src/SMESHGUI/SMESHGUI_FunctionPreview.h [new file with mode: 0644]
src/SMESHGUI/SMESHGUI_aParameter.cxx
src/SMESHGUI/SMESHGUI_aParameter.h
src/SMESHGUI/SMESHGUI_aParameterDlg.cxx
src/SMESHGUI/SMESHGUI_aParameterDlg.h
src/StdMeshers/Makefile.in
src/StdMeshers/StdMeshers_NumberOfSegments.cxx
src/StdMeshers/StdMeshers_NumberOfSegments.hxx
src/StdMeshers/StdMeshers_Regular_1D.cxx
src/StdMeshersGUI/Makefile.in
src/StdMeshersGUI/StdMeshersGUI_CreateHypothesisDlg.cxx
src/StdMeshersGUI/StdMeshersGUI_CreateHypothesisDlg.h
src/StdMeshersGUI/StdMeshersGUI_Parameters.cxx

index 565329b66a979dadcb93b5d68182db8af9440dfb..07a3a7211c085851eb4e8c19de4d1a0d819d1eff 100644 (file)
@@ -44,7 +44,8 @@ EXPORT_HEADERS= SMESHGUI_Swig.hxx \
                SMESHGUI_SpinBox.h \
                SMESHGUI_aParameter.h \
                SMESHGUI_aParameterDlg.h \
-               SMESHGUI_Selection.h
+               SMESHGUI_Selection.h \
+               SMESHGUI_FunctionPreview.h
 
 # .po files to transform in .qm
 PO_FILES = \
@@ -111,7 +112,8 @@ LIB_SRC =   SMESHGUI.cxx \
                SMESHGUI_Dialog.cxx \
                SMESHGUI_MeshDlg.cxx \
                SMESHGUI_MeshOp.cxx \
-               SMESHGUI_Displayer.cxx
+               SMESHGUI_Displayer.cxx \
+               SMESHGUI_FunctionPreview.cxx
 
 LIB_MOC = \
                SMESHGUI.h \
@@ -159,7 +161,8 @@ LIB_MOC = \
                SMESHGUI_SelectionOp.h \
                SMESHGUI_Dialog.h \
                SMESHGUI_MeshDlg.h \
-               SMESHGUI_MeshOp.h
+               SMESHGUI_MeshOp.h \
+               SMESHGUI_FunctionPreview.h
 
 
 LIB_CLIENT_IDL = SALOME_Exception.idl \
@@ -186,13 +189,17 @@ LIB_SERVER_IDL =
 
 CPPFLAGS += $(QT_INCLUDES) $(VTK_INCLUDES) $(OGL_INCLUDES) $(OCC_INCLUDES) $(PYTHON_INCLUDES) \
             -I${KERNEL_ROOT_DIR}/include/salome -I${GUI_ROOT_DIR}/include/salome \
-            -I${GEOM_ROOT_DIR}/include/salome $(BOOST_CPPFLAGS)
+            -I${GEOM_ROOT_DIR}/include/salome $(BOOST_CPPFLAGS) -I${QWTHOME}/include
 
 CXXFLAGS += -I${KERNEL_ROOT_DIR}/include/salome -I${GUI_ROOT_DIR}/include/salome \
-            -I${GEOM_ROOT_DIR}/include/salome
+            -I${GEOM_ROOT_DIR}/include/salome -I${QWTHOME}/include
 
 
-LDFLAGS += -lSMESHObject -lSMESHFiltersSelection -lSMDS -lSMESHControls -lDlgRef $(OCC_KERNEL_LIBS) -lTKBO -L${KERNEL_ROOT_DIR}/lib/salome -L${GUI_ROOT_DIR}/lib/salome -lVTKViewer -lSalomeApp -lSalomePrs -lSalomeNS -lSalomeLifeCycleCORBA -lOpUtil -lSalomeObject -lEvent -lSALOMELocalTrace -lSVTK -lOCCViewer -L${GEOM_ROOT_DIR}/lib/salome -lGEOM -lGEOMClient -lGEOMBase -lGEOMObject -lGEOMFiltersSelection
+LDFLAGS += -lSMESHObject -lSMESHFiltersSelection -lSMDS -lSMESHControls -lDlgRef \
+       $(OCC_KERNEL_LIBS) -lTKBO -lTKAdvTools -L${KERNEL_ROOT_DIR}/lib/salome -L${GUI_ROOT_DIR}/lib/salome \
+       -lVTKViewer -lSalomeApp -lSalomePrs -lSalomeNS -lSalomeLifeCycleCORBA -lOpUtil -lSalomeObject \
+       -lEvent -lSALOMELocalTrace -lSVTK -lOCCViewer -L${GEOM_ROOT_DIR}/lib/salome -lGEOM -lGEOMClient  \
+       -lGEOMBase -lGEOMObject -lGEOMFiltersSelection
 
 LDFLAGSFORBIN += $(LDFLAGS)
 
diff --git a/src/SMESHGUI/SMESHGUI_FunctionPreview.cxx b/src/SMESHGUI/SMESHGUI_FunctionPreview.cxx
new file mode 100644 (file)
index 0000000..2add301
--- /dev/null
@@ -0,0 +1,252 @@
+
+#include "SMESHGUI_FunctionPreview.h"
+#include <Expr_NamedUnknown.hxx>
+#include <Expr_GeneralExpression.hxx>
+#include <CASCatch_CatchSignals.hxx>
+#include <CASCatch_Failure.hxx> 
+#include <CASCatch_ErrorHandler.hxx>
+#include <OSD.hxx>
+
+SMESHGUI_FunctionPreview::SMESHGUI_FunctionPreview( QWidget* p )
+: QwtPlot( p ),
+  myXmin( 0.0 ),
+  myXmax( 1.0 ),
+  myPoints( 50 ),
+  myIsTable( false ),
+  myVars( 1, 1 ),
+  myValues( 1, 1 ),
+  myIsExp( false ),
+  myIsDone( true )
+{
+  myVars.ChangeValue( 1 ) = new Expr_NamedUnknown( "t" );
+  myCurve = insertCurve( QString() );
+  setCurvePen( myCurve, QPen( Qt::red, 1 ) );
+}
+
+SMESHGUI_FunctionPreview::~SMESHGUI_FunctionPreview()
+{
+}
+
+bool SMESHGUI_FunctionPreview::isTableFunc() const
+{
+  return myIsTable;
+}
+
+void SMESHGUI_FunctionPreview::tableFunc( SMESH::double_array& f ) const
+{
+  f = myTableFunc;
+}
+
+QString SMESHGUI_FunctionPreview::function() const
+{
+  return myFunction;
+}
+
+void SMESHGUI_FunctionPreview::interval( double& xmin, double& xmax ) const
+{
+  xmin = myXmin;
+  xmax = myXmax;
+}
+
+int SMESHGUI_FunctionPreview::pointsCount() const
+{
+  return myPoints;
+}
+
+void SMESHGUI_FunctionPreview::setIsExp( const bool exp, const bool update )
+{
+  myIsExp = exp;
+  if( update )
+    repaint();
+}
+
+bool SMESHGUI_FunctionPreview::setParams( const QString& func,
+                                              const double xmin, const double xmax,
+                                              const int points, const bool update )
+{
+  myIsTable = false;
+  myTableFunc = SMESH::double_array();
+  myFunction = func.isEmpty() ? "0" : func;
+  myXmin = xmin;
+  myXmax = xmax<myXmin ? myXmax : xmax;
+  myPoints = points>0 ? points : 2;
+  bool res = init( func );
+  if( update )
+    repaint();
+  return res;
+}
+
+bool SMESHGUI_FunctionPreview::setParams( const SMESH::double_array& f, const double xmin, const double xmax,
+                                              const bool update )
+{
+  myIsTable = true;
+  myTableFunc = f;
+  if( myTableFunc.length()%2==1 )
+    myTableFunc.length( myTableFunc.length()-1 );
+
+  myFunction = "0";
+  myXmin = xmin;
+  myXmax = xmax<myXmin ? myXmax : xmax;
+  myPoints = myTableFunc.length()/2;
+
+  if( update )
+    repaint();
+
+  return myTableFunc.length()>0;
+}
+
+bool SMESHGUI_FunctionPreview::createTable( SMESH::double_array& func )
+{
+  if( myExpr.IsNull() )
+  {
+    func.length( 0 );
+    return false;
+  }
+
+  double d = (myXmax-myXmin)/double(myPoints-1);
+  func.length( 2*myPoints );
+  int err = 0;
+  for( int i=0, j=0; i<myPoints; j++ )
+  {
+    bool ok;
+    double t = myXmin + d*j, f = funcValue( t, ok );
+    if( ok )
+    {
+      func[2*i] = t;
+      func[2*i+1] = f;
+      i++;
+    }
+    else
+      err++;
+  }
+  func.length( func.length()-2*err );
+  return err==0;
+}
+
+void SMESHGUI_FunctionPreview::drawContents( QPainter* p )
+{
+  SMESH::double_array f;
+  if( isTableFunc() )
+  {
+    myIsDone = true;
+    f = myTableFunc;
+  }
+  else
+    myIsDone = createTable( f );
+
+  int size = f.length()/2;
+  if( size==0 )
+  {
+    setAxisScale( curveXAxis( myCurve ), 0.0, 0.0 );
+    setAxisScale( curveYAxis( myCurve ), 0.0, 0.0 );
+    setCurveData( myCurve, 0, 0, 0 );
+    replot();
+    QwtPlot::drawContents( p );
+    return;
+  }
+
+  double* x = new double[size], *y = new double[size];
+  double min_x, max_x, min_y, max_y;
+  for( int i=0; i<size; i++ )
+  {
+    x[i] = f[2*i];
+    y[i] = myIsExp ? pow( 10.0, f[2*i+1] ) : f[2*i+1];
+    if( i==0 || y[i]<min_y )
+      min_y = y[i];
+    if( i==0 || y[i]>max_y )
+      max_y = y[i];
+    if( i==0 || x[i]<min_x )
+      min_x = x[i];
+    if( i==0 || x[i]>max_x )
+      max_x = x[i];
+  }
+
+  setAxisScale( curveXAxis( myCurve ), min_x, max_x );
+  setAxisScale( curveYAxis( myCurve ), min_y, max_y );
+  setCurveData( myCurve, x, y, size );
+  delete[] x;
+  delete[] y;
+
+  replot();
+  QwtPlot::drawContents( p );
+}
+
+bool isCorrectArg( const Handle( Expr_GeneralExpression )& expr )
+{
+  Handle( Expr_NamedUnknown ) sub = Handle( Expr_NamedUnknown )::DownCast( expr );
+  if( !sub.IsNull() )
+    return sub->GetName()=="t";
+
+  bool res = true;
+  for( int i=1, n=expr->NbSubExpressions(); i<=n && res; i++ )
+  {
+    Handle( Expr_GeneralExpression ) sub = expr->SubExpression( i );
+    Handle( Expr_NamedUnknown ) name = Handle( Expr_NamedUnknown )::DownCast( sub );
+    if( !name.IsNull() )
+    {
+      if( name->GetName()!="t" )
+       res = false;
+    }
+    else
+      res = isCorrectArg( sub );
+  }
+  return res;
+}
+
+bool SMESHGUI_FunctionPreview::init( const QString& str )
+{
+  myExpr = ExprIntrp_GenExp::Create();
+  myExpr->Process( ( Standard_CString ) str.latin1() );
+
+  bool syntax = false, args = false;
+  if( myExpr->IsDone() )
+  {
+    syntax = true;
+    args = isCorrectArg( myExpr->Expression() );
+  }
+
+  bool res = syntax && args;
+  if( !res )
+    myExpr.Nullify();
+  return res;
+}
+
+double SMESHGUI_FunctionPreview::funcValue( const double t, bool& ok )
+{
+  if( myExpr.IsNull() )
+    return 0;
+
+  myValues.ChangeValue( 1 ) = t;
+
+  ok = true;
+  double res = calc( ok );
+
+  return res;
+}
+
+double SMESHGUI_FunctionPreview::calc( bool& ok )
+{
+  OSD::SetSignal( true );
+  double res = 0.0;
+
+  CASCatch_CatchSignals aCatchSignals;
+  aCatchSignals.Activate();
+
+  ok = true;
+  CASCatch_TRY {   
+    res = myExpr->Expression()->Evaluate( myVars, myValues );
+  }
+  CASCatch_CATCH(CASCatch_Failure) {
+    aCatchSignals.Deactivate();
+    Handle(CASCatch_Failure) aFail = CASCatch_Failure::Caught();
+    ok = false;
+    res = 0.0;
+  }
+  aCatchSignals.Deactivate();
+  return res;
+}
+
+bool SMESHGUI_FunctionPreview::isDone() const
+{
+  return myIsDone;
+}
diff --git a/src/SMESHGUI/SMESHGUI_FunctionPreview.h b/src/SMESHGUI/SMESHGUI_FunctionPreview.h
new file mode 100644 (file)
index 0000000..d77126e
--- /dev/null
@@ -0,0 +1,54 @@
+
+#ifndef SMESHGUI_FUNCTION_PREVIEW_HEADER
+#define SMESHGUI_FUNCTION_PREVIEW_HEADER
+
+#include "qwt_plot.h"
+#include <SALOMEconfig.h>
+#include CORBA_SERVER_HEADER(SMESH_Mesh)
+#include <ExprIntrp_GenExp.hxx>
+#include <Expr_Array1OfNamedUnknown.hxx>
+#include <TColStd_Array1OfReal.hxx>
+
+class SMESHGUI_FunctionPreview : public QwtPlot
+{
+  Q_OBJECT
+
+public:
+  SMESHGUI_FunctionPreview( QWidget* );
+  virtual ~SMESHGUI_FunctionPreview();
+
+  QString   function() const;
+  bool      isTableFunc() const;
+  void      tableFunc( SMESH::double_array& ) const;
+  void      interval( double&, double& ) const;
+  int       pointsCount() const;
+  bool      isDone() const;
+
+  bool      setParams( const QString&, const double = 0.0, const double = 1.0, const int = 50, const bool = true );
+  bool      setParams( const SMESH::double_array&, const double = 0.0, const double = 1.0, const bool = true );
+  void      setIsExp( const bool, const bool = true );
+
+protected:
+  virtual   bool   init( const QString& );
+  virtual   double funcValue( const double, bool& );
+  virtual   bool   createTable( SMESH::double_array& );
+  virtual   void   drawContents( QPainter* );
+
+private:
+  double calc( bool& );
+
+private:
+  QString              myFunction;
+  double               myXmin, myXmax;
+  int                  myPoints;
+  bool                 myIsTable;
+  bool                 myIsExp;
+  SMESH::double_array  myTableFunc;
+  long                 myCurve;
+  Handle(ExprIntrp_GenExp)  myExpr;
+  Expr_Array1OfNamedUnknown myVars;
+  TColStd_Array1OfReal  myValues;
+  bool                 myIsDone;
+};
+
+#endif
index 3e513f04bd037ec8c8ed5ef7edd1b8991499ea0f..65b07e75b2af103f45a0559dca53cf3aff2431cc 100644 (file)
 
 #include <QtxDblSpinBox.h>
 
-SMESHGUI_aParameter::~SMESHGUI_aParameter() {}
+SMESHGUI_aParameter::SMESHGUI_aParameter( const QString& label, const bool preview )
+: _needPreview( preview ),
+  _label(label)
+{
+}
+
+SMESHGUI_aParameter::~SMESHGUI_aParameter()
+{
+}
+
+bool SMESHGUI_aParameter::needPreview() const
+{
+  return _needPreview;
+}
+
+QString& SMESHGUI_aParameter::Label()
+{
+  return _label;
+}
 
 QString SMESHGUI_aParameter::sigValueChanged() const
 {
@@ -54,8 +72,9 @@ QString SMESHGUI_aParameter::sigValueChanged() const
 SMESHGUI_intParameter::SMESHGUI_intParameter (const int      theInitValue,
                                               const QString& theLabel,
                                               const int      theBottom,
-                                              const int      theTop)
-     :SMESHGUI_aParameter(theLabel),
+                                              const int      theTop,
+                                             const bool     preview  )
+     :SMESHGUI_aParameter(theLabel, preview),
        _top(theTop), _bottom(theBottom), _initValue(theInitValue),
        _newValue( theInitValue )
 {
@@ -113,8 +132,9 @@ SMESHGUI_doubleParameter::SMESHGUI_doubleParameter (const double   theInitValue,
                                                     const double   theBottom,
                                                     const double   theTop,
                                                     const double   theStep,
-                                                    const int      theDecimals)
-     :SMESHGUI_aParameter(theLabel),
+                                                    const int      theDecimals,
+                                                   const bool     preview )
+     :SMESHGUI_aParameter(theLabel, preview),
        _top(theTop), _bottom(theBottom), _step(theStep),
        _initValue(theInitValue), _decimals(theDecimals)
 {
@@ -172,8 +192,9 @@ QString SMESHGUI_doubleParameter::sigValueChanged() const
 // purpose  :
 //=================================================================================
 SMESHGUI_strParameter::SMESHGUI_strParameter (const QString& theInitValue,
-                                              const QString& theLabel)
-     :SMESHGUI_aParameter(theLabel),
+                                              const QString& theLabel,
+                                             const bool preview )
+     :SMESHGUI_aParameter(theLabel, preview),
       _initValue(theInitValue)
 {
 }
@@ -181,6 +202,7 @@ SMESHGUI_aParameter::Type SMESHGUI_strParameter::GetType() const
 {
   return SMESHGUI_aParameter::STRING;
 }
+
 bool SMESHGUI_strParameter::GetNewInt (int & theValue) const
 {
   return false;
@@ -225,8 +247,8 @@ QString SMESHGUI_strParameter::sigValueChanged() const
 // class    : SMESHGUI_dependParameter
 // purpose  :
 //=================================================================================
-SMESHGUI_dependParameter::SMESHGUI_dependParameter( const QString& label )
-: SMESHGUI_aParameter( label )
+SMESHGUI_dependParameter::SMESHGUI_dependParameter( const QString& label, const bool     preview )
+: SMESHGUI_aParameter( label, preview )
 {
 }
 
@@ -250,8 +272,9 @@ SMESHGUI_dependParameter::ShownMap& SMESHGUI_dependParameter::shownMap()
 //=================================================================================
 SMESHGUI_enumParameter::SMESHGUI_enumParameter( const QStringList& values,
                                                 const int initValue,
-                                                const QString& label )
-: SMESHGUI_dependParameter( label ),
+                                                const QString& label,
+                                               const bool     preview )
+: SMESHGUI_dependParameter( label, preview ),
   myInitValue( initValue ),
   myValue( initValue ),
   myValues( values )
@@ -329,8 +352,9 @@ QString SMESHGUI_enumParameter::sigValueChanged() const
 // purpose  :
 //=================================================================================
 SMESHGUI_boolParameter::SMESHGUI_boolParameter( const bool initValue,
-                                                const QString& label )
-: SMESHGUI_dependParameter( label ),
+                                                const QString& label,
+                                               const bool     preview )
+: SMESHGUI_dependParameter( label, preview ),
   myInitValue( initValue ),
   myValue( myInitValue )
 {
@@ -453,8 +477,10 @@ QWidget* SMESHGUI_doubleItem::createEditor() const
 // class    : SMESHGUI_Table
 // purpose  :
 //=================================================================================
-SMESHGUI_Table::SMESHGUI_Table( int numRows, int numCols, QWidget* parent, const char* name )
-: QTable( numRows, numCols, parent, name )
+SMESHGUI_Table::SMESHGUI_Table( const SMESHGUI_tableParameter* tab, int numRows, int numCols,
+                               QWidget* parent, const char* name )
+: QTable( numRows, numCols, parent, name ),
+  myParam( ( SMESHGUI_tableParameter* )tab )
 {
 }
 
@@ -509,18 +535,99 @@ void SMESHGUI_Table::setValidator( const double minV, const double maxV, const i
     }
 }
 
+bool SMESHGUI_Table::eventFilter( QObject* o, QEvent* e )
+{
+  if( o && e && e->type()==QEvent::KeyPress )
+  {
+    QKeyEvent* ke = ( QKeyEvent* )e;
+    if( ke->key()==Qt::Key_Tab || ke->key()==Qt::Key_Backtab || ke->key()==Qt::Key_Return )
+    {
+      keyPressEvent( ke );
+      return true;
+    }
+  }
+
+  return QTable::eventFilter( o, e );
+}
+
+void SMESHGUI_Table::keyPressEvent( QKeyEvent* e )
+{
+  if( e )
+  {
+    bool shift = ( e->state() & Qt::ShiftButton );
+    int col = currentColumn(), row = currentRow();
+    if( e->key()==Qt::Key_Tab || e->key()==Qt::Key_Backtab )
+    {
+      if( e->key()==Qt::Key_Tab )
+       col++;
+      else 
+       col--;
+      if( col<0 )
+      {
+       col = numCols()-1;
+       row--;
+       if( row<0 )
+       {
+         col = 0;
+         row = 0;
+       }
+      }
+      if( col>=numCols() )
+      {
+       col = 0;
+       row++;
+       if( row>=numRows() )
+         row = numRows()-1;
+      }
+      e->accept();
+    }
+    else if( e->key()==Qt::Key_Return )
+    {
+      col = 0;
+      if( shift )
+       row--;
+      else
+       row++;
+      if( row<0 )
+       row = 0;
+      else if( row>=numRows() )
+      {
+       //add row
+       myParam->onEdit( this, SMESHGUI_TableFrame::ADD_ROW, 1 );
+      }
+      e->accept();
+    }
+    if( e->isAccepted() )
+    {
+      clearSelection();
+      setCurrentCell( row, col );
+    }
+    else
+      QTable::keyPressEvent( e );
+  }
+}
+
+QWidget* SMESHGUI_Table::createEditor( int r, int c, bool init ) const
+{
+  QWidget* w = QTable::createEditor( r, c, init );
+  if( w )
+    w->installEventFilter( this );
+  return w;
+}
+
 
 
 //=================================================================================
 // class    : SMESHGUI_TableFrame
 // purpose  :
 //=================================================================================
-SMESHGUI_TableFrame::SMESHGUI_TableFrame( QWidget* parent )
+SMESHGUI_TableFrame::SMESHGUI_TableFrame( const SMESHGUI_tableParameter* param, QWidget* parent )
 : QFrame( parent )
 {
   QVBoxLayout* main = new QVBoxLayout( this, 0, 0 );
 
-  myTable = new SMESHGUI_Table( 1, 1, this );
+  myTable = new SMESHGUI_Table( param, 1, 1, this );
+  connect( myTable, SIGNAL( valueChanged( int, int ) ), this, SIGNAL( valueChanged( int, int ) ) );
   
   QFrame* aButFrame = new QFrame( this );
   QHBoxLayout* butLay = new QHBoxLayout( aButFrame, 5, 5 );
@@ -616,8 +723,9 @@ void SMESHGUI_TableFrame::onButtonClicked()
 // purpose  :
 //=================================================================================
 SMESHGUI_tableParameter::SMESHGUI_tableParameter( const double init,
-                                                  const QString& label )
-: SMESHGUI_aParameter( label ),
+                                                  const QString& label,
+                                                 const bool preview )
+: SMESHGUI_aParameter( label, preview ),
   myInitValue( init ),
   myColsInt( 1 ),
   myRowsInt( 1 ),
@@ -630,6 +738,54 @@ SMESHGUI_tableParameter::~SMESHGUI_tableParameter()
 {
 }
 
+bool operator<( const QPair<double,double>& p1, const QPair<double,double>& p2 )
+{
+  return p1.first < p2.first;
+}
+
+void SMESHGUI_tableParameter::sortData( SMESH::double_array& arr )
+{
+  QValueList< QPair<double,double> > aData;
+  if( arr.length()%2==1 )
+    arr.length( arr.length()-1 );
+
+  int aLen = arr.length();
+  for( int i=0; i<aLen/2; i++ )
+    aData.append( QPair<double,double>( arr[2*i], arr[2*i+1] ) );
+
+  qHeapSort( aData );
+
+  QValueList< QPair<double,double> >::const_iterator anIt = aData.begin(), aLast = aData.end();
+  QValueList<double> unique_values;
+  double prev; int i=0;
+  if( (*anIt).first>0.0 )
+  {
+    unique_values.append( 0.0 );
+    unique_values.append( 0.0 );
+    i++; prev = 0.0;
+  }
+  for( ; anIt!=aLast; anIt++ )
+  {
+    if( i==0 || (*anIt).first>prev )
+    {
+      unique_values.append( (*anIt).first );
+      unique_values.append( (*anIt).second );
+      i++;
+    }
+    prev = (*anIt).first;
+  }
+  if( prev<1.0 )
+  {
+    unique_values.append( 1.0 );
+    unique_values.append( 0.0 );
+  }
+
+  arr.length( unique_values.count() );
+  QValueList<double>::const_iterator anIt1 = unique_values.begin(), aLast1 = unique_values.end();
+  for( int j=0; anIt1!=aLast1; anIt1++, j++ )
+    arr[j] = *anIt1;
+}
+
 SMESHGUI_aParameter::Type SMESHGUI_tableParameter::GetType() const
 {
   return TABLE;
@@ -652,7 +808,7 @@ bool SMESHGUI_tableParameter::GetNewText( QString& ) const
 
 QWidget* SMESHGUI_tableParameter::CreateWidget( QWidget* par ) const
 {
-  SMESHGUI_TableFrame* t = new SMESHGUI_TableFrame( par );
+  SMESHGUI_TableFrame* t = new SMESHGUI_TableFrame( this, par );
   connect( t,    SIGNAL( toEdit( SMESHGUI_TableFrame::Button, int ) ),
            this, SLOT  ( onEdit( SMESHGUI_TableFrame::Button, int ) ) );
   
@@ -705,7 +861,7 @@ void SMESHGUI_tableParameter::InitializeWidget( QWidget* w ) const
     for( int i=0, m=row; i<m; i++ )
       for( int j=0, n=col; j<n; j++ )
         if( row*j+i<myData.length() )
-          tab->item( i, j )->setText( QString( "%1" ).arg( myData[row*j+i] ) );
+          tab->item( i, j )->setText( QString( "%1" ).arg( myData[col*i+j] ) );
   }
 }
 
@@ -728,11 +884,13 @@ void SMESHGUI_tableParameter::TakeValue( QWidget* w )
 void SMESHGUI_tableParameter::data( SMESH::double_array& v ) const
 {
   v = myData;
+  sortData( v );
 }
 
 void SMESHGUI_tableParameter::setData( const SMESH::double_array& d )
 {
   myData = d;
+  sortData( myData );
 }
 
 void SMESHGUI_tableParameter::update( QWidget* w ) const
@@ -874,68 +1032,77 @@ void SMESHGUI_tableParameter::onEdit( SMESHGUI_TableFrame::Button b, int n )
   {
     SMESHGUI_TableFrame* fr = ( SMESHGUI_TableFrame* )sender();
     SMESHGUI_Table* tab = fr->table();
+    onEdit( tab, b, n );
+  }
+}
 
-    switch( b )
-    {
-      case SMESHGUI_TableFrame::ADD_COLUMN:
-      {
-        if( !myEditCols || myCols.get() )
-          return;
-
-        myColsInt++; update( fr );
-        if( n>=0 )
-          for( int i=0; i<myRowsInt; i++ )
-            for( int j=myColsInt-1; j>=n; j-- )
-              if( j==n )
-                tab->setText( i, j, QString( "%1" ).arg( myInitValue ) );
-              else
-                tab->setText( i, j, tab->text( i, j-1 ) );
-        break;
-      }
-      
-      case SMESHGUI_TableFrame::REMOVE_COLUMN:
-      {
-        if( !myEditCols || myCols.get() || myColsInt<=1 )
-          return;
+void SMESHGUI_tableParameter::onEdit( SMESHGUI_Table* tab, SMESHGUI_TableFrame::Button b, int n )
+{
+  if( !tab )
+    return;
 
-        if( n>=0 )
-          for( int i=0; i<myRowsInt; i++ )
-            for( int j=n; j<myColsInt-1; j++ )
-              tab->setText( i, j, tab->text( i, j+1 ) );
-        myColsInt--; update( fr );
+  SMESHGUI_TableFrame* fr = dynamic_cast<SMESHGUI_TableFrame*>( tab->parent() );
 
-        break;
-      }
+  switch( b )
+  {
+  case SMESHGUI_TableFrame::ADD_COLUMN:
+    {
+      if( !myEditCols || myCols.get() )
+       return;
+
+      myColsInt++; update( fr );
+      if( n>=0 )
+       for( int i=0; i<myRowsInt; i++ )
+         for( int j=myColsInt-1; j>=n; j-- )
+           if( j==n )
+             tab->setText( i, j, QString( "%1" ).arg( myInitValue ) );
+           else
+             tab->setText( i, j, tab->text( i, j-1 ) );
+      break;
+    }
+    
+  case SMESHGUI_TableFrame::REMOVE_COLUMN:
+    {
+      if( !myEditCols || myCols.get() || myColsInt<=1 )
+       return;
+
+      if( n>=0 )
+       for( int i=0; i<myRowsInt; i++ )
+         for( int j=n; j<myColsInt-1; j++ )
+           tab->setText( i, j, tab->text( i, j+1 ) );
+      myColsInt--; update( fr );
       
-      case SMESHGUI_TableFrame::ADD_ROW:
-      {
-        if( !myEditRows || myRows.get() )
-          return;
-
-        myRowsInt++; update( fr );
-        if( n>=0 )
-          for( int i=myRowsInt-1; i>=n; i-- )
-            for( int j=0; j<myColsInt; j++ )
-              if( i==n )
-                tab->setText( i, j, QString( "%1" ).arg( myInitValue ) );
-              else
-                tab->setText( i, j, tab->text( i-1, j ) );
-        break;        
-      }
+      break;
+    }
       
-      case SMESHGUI_TableFrame::REMOVE_ROW:
-      {
-        if( !myEditRows || myRows.get() || myRowsInt<=1 )
-          return;
-
-        if( n>=0 )
-          for( int i=n; i<myRowsInt-1; i++ )
-            for( int j=0; j<myColsInt; j++ )
-              tab->setText( i, j, tab->text( i+1, j ) );
-        myRowsInt--; update( fr );
-
-        break;
-      }
+  case SMESHGUI_TableFrame::ADD_ROW:
+    {
+      if( !myEditRows || myRows.get() )
+       return;
+
+      myRowsInt++; update( fr );
+      if( n>=0 )
+       for( int i=myRowsInt-1; i>=n; i-- )
+         for( int j=0; j<myColsInt; j++ )
+           if( i==n )
+             tab->setText( i, j, QString( "%1" ).arg( myInitValue ) );
+           else
+             tab->setText( i, j, tab->text( i-1, j ) );
+      break;        
+    }
+      
+  case SMESHGUI_TableFrame::REMOVE_ROW:
+    {
+      if( !myEditRows || myRows.get() || myRowsInt<=1 )
+       return;
+
+      if( n>=0 )
+       for( int i=n; i<myRowsInt-1; i++ )
+         for( int j=0; j<myColsInt; j++ )
+           tab->setText( i, j, tab->text( i+1, j ) );
+      myRowsInt--; update( fr );
+      
+      break;
     }
   }
 }
index 8613b50dd1a8a2ef1b7a6891e566d56bcb73aa7a..dcd8c717770f1b339dde71bca413a6b036a5c450 100644 (file)
@@ -47,7 +47,9 @@ typedef boost::shared_ptr<SMESHGUI_aParameter> SMESHGUI_aParameterPtr;
 class SMESHGUI_aParameter
 { 
 public:
-  SMESHGUI_aParameter(const QString& label):_label(label) {}
+  typedef bool (*VALIDATION_FUNC)( SMESHGUI_aParameter* );
+
+  SMESHGUI_aParameter(const QString& label, const bool = false );
   virtual ~SMESHGUI_aParameter();
 
   enum Type { INT, DOUBLE, STRING, ENUM, BOOL, TABLE };
@@ -59,15 +61,18 @@ public:
   virtual QWidget* CreateWidget( QWidget* ) const = 0;
   virtual void InitializeWidget( QWidget* ) const = 0;
 
+  bool needPreview() const;
+
   /*!
    *  \brief Returns string representation of signal emitted when value in corrsponding widget is changed
    */
   virtual QString sigValueChanged() const;
 
-  QString & Label() { return _label; }
+  QString & Label();
   
 private:
   QString _label;
+  bool    _needPreview;
 };
 
 /*!
@@ -79,7 +84,8 @@ public:
   SMESHGUI_intParameter(const int      initValue = 0,
                        const QString& label     = QString::null,
                        const int      bottom    = 0,
-                       const int      top       = 1000);
+                       const int      top       = 1000,
+                       const bool = false );
   int & InitValue() { return _initValue; }
   int & Top()       { return _top; }
   int & Bottom()    { return _bottom; }
@@ -109,7 +115,8 @@ public:
                           const double   bottom    = -1E6,
                           const double   top       = +1E6,
                           const double   step      = 1.0,
-                          const int      decimals  = 3);
+                          const int      decimals  = 3,
+                          const bool = false);
   double & InitValue() { return _initValue; }
   double & Top()       { return _top; }
   double & Bottom()    { return _bottom; }
@@ -138,7 +145,8 @@ class SMESHGUI_strParameter: public SMESHGUI_aParameter
 { 
 public:
   SMESHGUI_strParameter( const QString& initValue = "",
-                         const QString& label     = QString::null);
+                         const QString& label     = QString::null,
+                        const bool = false );
   QString& InitValue() { return _initValue; }
   virtual Type GetType() const;
   virtual bool GetNewInt( int & Value ) const;
@@ -171,7 +179,7 @@ public:
   typedef QMap< int, IntList >  ShownMap;
 
 public:
-  SMESHGUI_dependParameter( const QString& = QString::null );
+  SMESHGUI_dependParameter( const QString& = QString::null, const bool = false );
 
   const ShownMap&    shownMap() const;
   ShownMap&          shownMap();
@@ -192,7 +200,8 @@ public:
    */
   SMESHGUI_enumParameter( const QStringList& values,
                           const int init = 0,
-                          const QString& label = QString::null );
+                          const QString& label = QString::null,
+                         const bool = false );
   virtual ~SMESHGUI_enumParameter();
 
   /*!
@@ -224,7 +233,8 @@ class SMESHGUI_boolParameter: public SMESHGUI_dependParameter
 {
 public:
   SMESHGUI_boolParameter( const bool = false,
-                          const QString& = QString::null );
+                          const QString& = QString::null,
+                         const bool = false );
   virtual ~SMESHGUI_boolParameter();
 
   bool& InitValue() { return myInitValue; }
@@ -244,6 +254,8 @@ private:
 
 
 class QButton;
+class SMESHGUI_tableParameter;
+
 
 /*!
  *  \brief This class represents custom table. It has only double values and
@@ -254,7 +266,7 @@ class SMESHGUI_Table : public QTable
   Q_OBJECT
   
 public:
-  SMESHGUI_Table( int numRows, int numCols, QWidget* = 0, const char* = 0 );
+  SMESHGUI_Table( const SMESHGUI_tableParameter*, int numRows, int numCols, QWidget* = 0, const char* = 0 );
   virtual ~SMESHGUI_Table();
 
 /*!
@@ -278,6 +290,14 @@ public:
   void setValidator( const double, const double, const int,
                      const int rmin = -1, const int rmax = -1,
                      const int cmin = -1, const int cmax = -1 );  
+
+protected:
+  virtual void keyPressEvent( QKeyEvent* );
+  virtual bool eventFilter( QObject*, QEvent* );
+  virtual QWidget* createEditor( int, int, bool ) const;
+
+private:
+  SMESHGUI_tableParameter*   myParam;
 };
 
 
@@ -295,7 +315,7 @@ public:
   typedef enum { ADD_COLUMN, REMOVE_COLUMN, ADD_ROW, REMOVE_ROW } Button;
 
 public:
-  SMESHGUI_TableFrame( QWidget* );
+  SMESHGUI_TableFrame( const SMESHGUI_tableParameter*, QWidget* );
   ~SMESHGUI_TableFrame();
 
   SMESHGUI_Table* table() const;
@@ -324,6 +344,7 @@ signals:
  *         this object resize table ( returned by table() ) automatically
  */
   void toEdit( SMESHGUI_TableFrame::Button, int );
+  void valueChanged( int, int );
 
 private:
   QButton *myAddColumn, *myRemoveColumn, *myAddRow, *myRemoveRow;
@@ -345,7 +366,8 @@ public:
  *         and if new column or row is added then it is filled with default value
  */
   SMESHGUI_tableParameter( const double init = 0.0,
-                           const QString& label = QString::null );
+                           const QString& label = QString::null,
+                          const bool preview = false );
   virtual ~SMESHGUI_tableParameter();
 
   virtual Type GetType() const;
@@ -356,6 +378,8 @@ public:
   virtual void InitializeWidget( QWidget* ) const;
   virtual void TakeValue( QWidget* );
 
+  static void sortData( SMESH::double_array& );
+
 /*!
  *  \brief Updates look of widget in accordance with all parameters of this object
  */
@@ -416,6 +440,7 @@ public:
 
 private slots:
   void onEdit( SMESHGUI_TableFrame::Button, int );
+  void onEdit( SMESHGUI_Table*, SMESHGUI_TableFrame::Button, int );
 
 private:
   void setItems( QWidget*, int = -1, int = -1, int = -1, int = -1 ) const;
@@ -437,6 +462,9 @@ private:
   ValidatorsMap            myValidators;
   bool                     myEditCols, myEditRows;
   QMap< int, QString >     myColNames;
+
+  friend class SMESHGUI_Table;
 };
 
 #endif // SMESHGUI_aParameter.h
+
index 7e824a7b9031c2875a6b1014d40788468617a394..b9c9f1d3b3091c97c6a3e10fa96fe12e66cf32b7 100644 (file)
@@ -31,6 +31,7 @@
 #include "SMESHGUI.h"
 #include "SMESHGUI_SpinBox.h"
 #include "SMESHGUI_Utils.h"
+#include "SMESHGUI_FunctionPreview.h"
 
 #include "SUIT_Tools.h"
 #include "SUIT_Desktop.h"
@@ -94,7 +95,8 @@ void SMESHGUI_aParameterDlg::init()
   GroupC1Layout->setMargin(11);
   /* Spin boxes with labels */
   list<SMESHGUI_aParameterPtr>::iterator paramIt = myParamList.begin();
-  for (int row = 0; paramIt != myParamList.end(); paramIt++ , row++)
+  int row;
+  for( row = 0; paramIt != myParamList.end(); paramIt++ , row++)
   {
     SMESHGUI_aParameterPtr param = (*paramIt);
     QLabel * label = new QLabel(GroupC1, "TextLabel");
@@ -107,7 +109,7 @@ void SMESHGUI_aParameterDlg::init()
       aSpinWidget->setMinimumSize(150, 0);
 
       QString sig = param->sigValueChanged();
-      if( !sig.isEmpty() && param->GetType()!=SMESHGUI_aParameter::TABLE )
+      if( !sig.isEmpty() /*&& param->GetType()!=SMESHGUI_aParameter::TABLE*/ )
         connect( aSpinWidget, sig.latin1(), this, SLOT( onValueChanged() ) );
       
       param->InitializeWidget(aSpinWidget);
@@ -116,11 +118,17 @@ void SMESHGUI_aParameterDlg::init()
     }
   }
 
+  myPreview = new SMESHGUI_FunctionPreview( GroupC1 );
+  GroupC1Layout->addWidget( myPreview, row, 1 );
+
   paramIt = myParamList.begin();
   std::list<QWidget*>::const_iterator anIt = mySpinList.begin();
   for( ; paramIt!=myParamList.end(); paramIt++, anIt++ )
+  {
+    (*paramIt)->TakeValue( *anIt );
     UpdateShown( *paramIt, *anIt );
-  
+    FunctionPreview( *paramIt, *anIt );
+  }
 
   /***************************************************************/
   QGroupBox* GroupButtons = new QGroupBox(this, "GroupButtons");
@@ -196,6 +204,38 @@ bool SMESHGUI_aParameterDlg::Parameters( SMESHGUI* theModule,
   return false;
 }
 
+//=======================================================================
+// function : FunctionPreview
+// purpose  : 
+//=======================================================================
+void SMESHGUI_aParameterDlg::FunctionPreview( const SMESHGUI_aParameterPtr p, QWidget* w )
+{
+  if( !w || !w->isShown() )
+    return;
+
+  SMESHGUI_strParameter* str_param = dynamic_cast<SMESHGUI_strParameter*>( p.operator->() );
+  SMESHGUI_tableParameter* tab_param = dynamic_cast<SMESHGUI_tableParameter*>( p.operator->() );
+  SMESHGUI_boolParameter* bool_param = dynamic_cast<SMESHGUI_boolParameter*>( p.operator->() );
+  if( str_param && str_param->needPreview() )
+  {
+    QString val; str_param->GetNewText( val );
+    if( !val.isNull() )
+      myPreview->setParams( val );
+  }
+  else if( tab_param && tab_param->needPreview() )
+  {
+    SMESH::double_array d;
+    tab_param->data( d );
+    myPreview->setParams( d );
+  }
+  else if( bool_param && bool_param->needPreview() )
+  {
+    int exp=0;
+    bool_param->GetNewInt( exp );
+    myPreview->setIsExp( exp );
+  }
+}
+
 //=======================================================================
 // function : onValueChanged
 // purpose  : 
@@ -206,7 +246,6 @@ void SMESHGUI_aParameterDlg::onValueChanged()
   {
     QWidget* w = ( QWidget* )sender();
 
-    SMESHGUI_aParameterPtr param;
 
     std::list<QWidget*>::const_iterator anIt = mySpinList.begin(),
                                         aLast = mySpinList.end();
@@ -216,6 +255,7 @@ void SMESHGUI_aParameterDlg::onValueChanged()
       {
         (*aPIt)->TakeValue( w );
         UpdateShown( *aPIt, w );
+       FunctionPreview( *aPIt, w );
         break;
       }
   }
@@ -246,10 +286,19 @@ void SMESHGUI_aParameterDlg::UpdateShown( const SMESHGUI_aParameterPtr param, QW
   std::list<QWidget*>::const_iterator anIt = mySpinList.begin(),
                                       aLast = mySpinList.end(),
                                       aLIt = myLabelList.begin();
-  for( int i=0; anIt!=aLast; anIt++, aLIt++, i++ )
+  std::list<SMESHGUI_aParameterPtr>::iterator aPIt = myParamList.begin();
+  bool preview = false;
+  for( int i=0; anIt!=aLast; anIt++, aLIt++, i++, aPIt++ )
   {
     bool shown = hasValue && map[ val ].contains( i );
     (*anIt)->setShown( shown );
     (*aLIt)->setShown( shown );
+    if( shown )
+    {
+      SMESHGUI_strParameter* str_param = dynamic_cast<SMESHGUI_strParameter*>( (*aPIt).operator->() );
+      SMESHGUI_tableParameter* tab_param = dynamic_cast<SMESHGUI_tableParameter*>( (*aPIt).operator->() );
+      preview = preview || ( str_param && str_param->needPreview() ) || ( tab_param && tab_param->needPreview() );
+    }
   }
+  myPreview->setShown( preview );
 }
index 7fd28a96f564bcf3b3e8cf03371a943cf709402e..f749aeedd3e5b39f970026f4ca13cfa6cfedfce9 100644 (file)
@@ -39,6 +39,7 @@ class QLabel;
 class QPushButton;
 class SMESHGUI;
 class QWidget;
+class SMESHGUI_FunctionPreview;
 
 //=================================================================================
 // class    : SMESHGUI_aParameterDlg
@@ -69,6 +70,9 @@ private slots:
     void ClickOnOk();
     void UpdateShown( const SMESHGUI_aParameterPtr, QWidget* );
 
+private:
+    void FunctionPreview( const SMESHGUI_aParameterPtr, QWidget* );
+
 private:
     SMESHGUI*       mySMESHGUI;
 
@@ -77,6 +81,7 @@ private:
 
     std::list<QWidget*>               mySpinList, myLabelList;
     std::list<SMESHGUI_aParameterPtr> myParamList;
+    SMESHGUI_FunctionPreview* myPreview;
 };
 
 #endif // SMESHGUI_aParameterDlg.h
index 385d643a5809598ad038d4b93448a4b5ff1d846b..9b2f65b613692e868eefb751c702571d37d88afd 100644 (file)
@@ -87,6 +87,7 @@ BIN_SRC =
 CPPFLAGS+= $(OCC_INCLUDES) -I${KERNEL_ROOT_DIR}/include/salome $(BOOST_CPPFLAGS)
 CXXFLAGS+= $(OCC_CXXFLAGS) -I${KERNEL_ROOT_DIR}/include/salome -I${GEOM_ROOT_DIR}/include/salome
 
-LDFLAGS+= -lSMESHimpl -lMEFISTO2D $(OCC_LDPATH) -lTKAdvTools -L${KERNEL_ROOT_DIR}/lib/salome -L${GEOM_ROOT_DIR}/lib/salome
+LDFLAGS+= -lSMESHimpl -lMEFISTO2D $(OCC_LDPATH) -lTKAdvTools -L${KERNEL_ROOT_DIR}/lib/salome -L${GEOM_ROOT_DIR}/lib/salome \
+         -lCASCatch
 
 @CONCLUDE@
index 44ac15909556441460b8eb169bfee02e39b2ad42..ecceafd146ce1e0d1a890961321ba1853ea775e4 100644 (file)
@@ -33,6 +33,13 @@ using namespace std;
 #include <TCollection_AsciiString.hxx>
 #include <ExprIntrp_GenExp.hxx>
 #include <Expr_NamedUnknown.hxx>
+#include <CASCatch_CatchSignals.hxx>
+#include <CASCatch_Failure.hxx> 
+#include <CASCatch_ErrorHandler.hxx>
+#include <OSD.hxx>
+#include <Expr_Array1OfNamedUnknown.hxx>
+#include <TColStd_Array1OfReal.hxx>
+
 
 const double PRECISION = 1e-7;
 
@@ -51,7 +58,7 @@ StdMeshers_NumberOfSegments::StdMeshers_NumberOfSegments(int hypId, int studyId,
     _expMode(false)
 {
   _name = "NumberOfSegments";
-  _param_algo_dim = 1; 
+  _param_algo_dim = 1;
 }
 
 //=============================================================================
@@ -179,6 +186,7 @@ void StdMeshers_NumberOfSegments::SetTableFunction(const std::vector<double>& ta
   double prev = -PRECISION;
   bool isSame = table.size() == _table.size();
 
+  bool pos = false;
   for (i=0; i < table.size()/2; i++) {
     double par = table[i*2];
     double val = table[i*2+1];
@@ -186,8 +194,10 @@ void StdMeshers_NumberOfSegments::SetTableFunction(const std::vector<double>& ta
       throw SALOME_Exception(LOCALIZED("parameter of table function is out of range [0,1]"));
     if ( fabs(par-prev)<PRECISION )
       throw SALOME_Exception(LOCALIZED("two parameters are the same"));
-    if (val < PRECISION)
+    if ( val < 0 )
       throw SALOME_Exception(LOCALIZED("value of table function is not positive"));
+    if( val>PRECISION )
+      pos = true;
     if (isSame)
     {
       double oldpar = _table[i*2];
@@ -198,7 +208,10 @@ void StdMeshers_NumberOfSegments::SetTableFunction(const std::vector<double>& ta
     prev = par;
   }
 
-  if (!isSame)
+  if( !pos )
+    throw SALOME_Exception(LOCALIZED("value of table function is not positive"));
+
+  if( pos && !isSame )
   {
     _table = table;
     NotifySubMeshesHypothesisModification();
@@ -223,23 +236,24 @@ const std::vector<double>& StdMeshers_NumberOfSegments::GetTableFunction() const
 /*! check if only 't' is unknown variable in expression
  */
 //================================================================================
-bool isCorrect( const Handle( Expr_GeneralExpression )& expr )
+bool isCorrectArg( const Handle( Expr_GeneralExpression )& expr )
 {
-  if( expr.IsNull() )
-    return true;
-    
+  Handle( Expr_NamedUnknown ) sub = Handle( Expr_NamedUnknown )::DownCast( expr );
+  if( !sub.IsNull() )
+    return sub->GetName()=="t";
+
   bool res = true;
   for( int i=1, n=expr->NbSubExpressions(); i<=n && res; i++ )
   {
-    Handle( Expr_GeneralExpression ) subexpr = expr->SubExpression( i );
-    Handle( Expr_NamedUnknown ) name = Handle( Expr_NamedUnknown )::DownCast( subexpr );
+    Handle( Expr_GeneralExpression ) sub = expr->SubExpression( i );
+    Handle( Expr_NamedUnknown ) name = Handle( Expr_NamedUnknown )::DownCast( sub );
     if( !name.IsNull() )
     {
       if( name->GetName()!="t" )
-        res = false;
+       res = false;
     }
     else
-      res = isCorrect( subexpr );
+      res = isCorrectArg( sub );
   }
   return res;
 }
@@ -249,25 +263,66 @@ bool isCorrect( const Handle( Expr_GeneralExpression )& expr )
  *  ( result in 'syntax' ) and if only 't' is unknown variable in expression ( result in 'args' )
  */
 //================================================================================
-void casProcess( const TCollection_AsciiString& str, bool& syntax, bool& args )
+bool process( const TCollection_AsciiString& str,
+             bool& syntax, bool& args,
+             bool& non_neg, bool& non_zero,
+             bool& singulars, double& sing_point )
 {
-  // check validity of expression
-  syntax = false;
-  args = false;
-  try
+  Handle( ExprIntrp_GenExp ) myExpr = ExprIntrp_GenExp::Create();
+  myExpr->Process( str.ToCString() );
+
+  if( myExpr->IsDone() )
   {
-    Handle( ExprIntrp_GenExp ) gen = ExprIntrp_GenExp::Create();
-    gen->Process( str );
-        
-    if( gen->IsDone() ) 
-    {
-      syntax = true;
-      args = isCorrect( gen->Expression() );
-    }
+    syntax = true;
+    args = isCorrectArg( myExpr->Expression() );
   }
-  catch (Standard_Failure)
+
+  bool res = syntax && args;
+  if( !res )
+    myExpr.Nullify();
+
+  non_neg = true;
+  singulars = false;
+  non_zero = false;
+
+  if( res )
   {
+    OSD::SetSignal( true );
+    CASCatch_CatchSignals aCatchSignals;
+    aCatchSignals.Activate();
+    double res;
+    Expr_Array1OfNamedUnknown myVars( 1, 1 );
+    TColStd_Array1OfReal  myValues( 1, 1 );
+    myVars.ChangeValue( 1 ) = new Expr_NamedUnknown( "t" );
+
+    const int max = 500;
+    for( int i=0; i<=max; i++ )
+    {
+      double t = double(i)/double(max);
+      myValues.ChangeValue( 1 ) = t;
+      CASCatch_TRY
+      {   
+       res = myExpr->Expression()->Evaluate( myVars, myValues );
+      }
+      CASCatch_CATCH(CASCatch_Failure)
+      {
+       aCatchSignals.Deactivate();
+       Handle(CASCatch_Failure) aFail = CASCatch_Failure::Caught();
+       sing_point = t;
+       singulars = true;
+       break;
+      }
+      if( res<0 )
+      {
+       non_neg = false;
+       break;
+      }
+      if( res>PRECISION )
+       non_zero = true;
+    }
+    aCatchSignals.Deactivate();
   }
+  return res && non_neg && ( !singulars );
 }
 
 //================================================================================
@@ -289,15 +344,31 @@ void StdMeshers_NumberOfSegments::SetExpressionFunction(const char* expr)
   str.RemoveAll('\r');
   str.RemoveAll('\n');
 
-  bool syntax, args;
-  casProcess( str, syntax, args );
-  if( !syntax )
-    throw SALOME_Exception(LOCALIZED("invalid expression syntax"));
-  if( !args )
-    throw SALOME_Exception(LOCALIZED("only 't' may be used as function argument"));
+  bool syntax, args, non_neg, singulars, non_zero;
+  double sing_point;
+  bool res = true;//process( str, syntax, args, non_neg, non_zero, singulars, sing_point );
+  if( !res )
+  {
+    if( !syntax )
+      throw SALOME_Exception(LOCALIZED("invalid expression syntax"));
+    if( !args )
+      throw SALOME_Exception(LOCALIZED("only 't' may be used as function argument"));
+    if( !non_neg )
+      throw SALOME_Exception(LOCALIZED("only non-negative function can be used as density"));
+    if( singulars )
+    {
+      char buf[1024];
+      sprintf( buf, "Function has singular point in %.3f", sing_point );
+      throw SALOME_Exception( buf );
+    }
+    if( !non_zero )
+      throw SALOME_Exception(LOCALIZED("f(t)=0 cannot be used as density"));
 
-  string func(str.ToCString());
-  if (_func != func)
+    return;
+  }
+  
+  std::string func = expr;
+  if( _func != func )
   {
     _func = func;
     NotifySubMeshesHypothesisModification();
index 2f559fb040d6bd325d46bd591fc6b5681197a506..a384752ba7b8f3a4492759bb0357582c812f95b8 100644 (file)
@@ -126,7 +126,7 @@ public:
    * 
    * Throws SALOME_Exception if distribution type is not DT_ExprFunc
    */
-  void SetExpressionFunction(const char* expr)
+  void SetExpressionFunction( const char* expr)
     throw (SALOME_Exception);
 
   /*!
index c9765f03919b2a77be06104ea1435a7f74619675..51df8669dd44badccf07f0fe71fc074784688a2c 100644 (file)
@@ -64,6 +64,12 @@ using namespace std;
 #include <TColStd_Array1OfReal.hxx>
 #include <ExprIntrp_GenExp.hxx>
 
+#include <CASCatch_CatchSignals.hxx>
+#include <CASCatch_Failure.hxx> 
+#include <CASCatch_ErrorHandler.hxx>
+#include <OSD.hxx>
+#include <math_GaussSingleIntegration.hxx>
+
 #include <string>
 #include <math.h>
 
@@ -260,247 +266,333 @@ static void compensateError(double a1, double an,
   }
 }
 
-/*!
- * \brief This class provides interface for a density function
- */
-class Function
+class Function 
 {
 public:
-  Function(bool expMode) : _expMode(expMode) {}
-  double operator() (double t) const;
-  virtual bool IsReady() const = 0;
-protected:
-  virtual double compute(double t) const = 0;
+  Function( const bool exp )
+  : myExp( exp )
+  {
+  }
+
+  virtual ~Function()
+  {
+  }
+
+  virtual bool   value( const double, double& f )
+  {
+    if( myExp )
+      f = pow( 10, f );
+    return true;
+  }
+  virtual double integral( const double, const double ) = 0;
+
 private:
-  bool _expMode;
+  bool myExp;
 };
 
-/*!
- * \brief This class provides computation of density function given by a table
- */
-class TabFunction: public Function
+class FunctionIntegral : public Function
 {
 public:
-  TabFunction(const vector<double>& table, bool expMode);
-  virtual bool IsReady() const;
-protected:
-  virtual double compute(double t) const;
+  FunctionIntegral( Function*, const double );
+  virtual ~FunctionIntegral();
+  virtual bool   value( const double, double& );
+  virtual double integral( const double, const double );
+
 private:
-  const vector<double>& _table;
+  Function* myFunc;
+  double    myStart;
 };
 
-/*!
- * \brief This class provides computation of density function given by an expression
- */
-class ExprFunction: public Function
+FunctionIntegral::FunctionIntegral( Function* f, const double st )
+: Function( false )
+{
+  myFunc = f;
+  myStart = st;
+}
+
+FunctionIntegral::~FunctionIntegral()
+{
+}
+
+bool FunctionIntegral::value( const double t, double& f )
+{
+  f = myFunc ? myFunc->integral( myStart, t ) : 0;
+  return myFunc!=0 && Function::value( t, f );
+}
+
+double FunctionIntegral::integral( const double, const double )
+{
+  return 0;
+}
+
+class FunctionTable : public Function
 {
 public:
-  ExprFunction(const char* expr, bool expMode);
-  virtual bool IsReady() const;
-protected:
-  virtual double compute(double t) const;
+  FunctionTable( const std::vector<double>&, const bool );
+  virtual ~FunctionTable();
+  virtual bool   value( const double, double& );
+  virtual double integral( const double, const double );
+
 private:
-  Handle(Expr_GeneralExpression) _expression;
-  Expr_Array1OfNamedUnknown _var;
-  mutable TColStd_Array1OfReal _val;
+  bool    findBounds( const double, int&, int& ) const;
+
+  //integral from x[i] to x[i+1]
+  double  integral( const int i );
+
+  //integral from x[i] to x[i]+d
+  //warning: function is presented as linear on interaval from x[i] to x[i]+d,
+  //         for correct result d must be >=0 and <=x[i+1]-x[i]
+  double  integral( const int i, const double d );
+
+private:
+  std::vector<double>  myData;
 };
 
-double Function::operator() (double t) const
+FunctionTable::FunctionTable( const std::vector<double>& data, const bool exp )
+: Function( exp )
 {
-  double res = compute(t);
-  if (_expMode)
-    res = pow(10, res);
-  return res;
+  myData = data;
 }
 
-TabFunction::TabFunction(const vector<double>& table, bool expMode)
-  : Function(expMode),
-    _table(table)
+FunctionTable::~FunctionTable()
 {
 }
 
-bool TabFunction::IsReady() const
+bool FunctionTable::value( const double t, double& f )
 {
+  int i1, i2;
+  if( !findBounds( t, i1, i2 ) )
+    return false;
+
+  double
+    x1 = myData[2*i1], y1 = myData[2*i1+1],
+    x2 = myData[2*i2], y2 = myData[2*i2+1];
+
+  Function::value( x1, y1 );
+  Function::value( x2, y2 );
+  
+  f = y1 + ( y2-y1 ) * ( t-x1 ) / ( x2-x1 );
   return true;
 }
 
-double TabFunction::compute (double t) const
+double FunctionTable::integral( const int i )
 {
-  //find place of <t> in table
-  int i;
-  for (i=0; i < _table.size()/2; i++)
-    if (_table[i*2] > t)
-      break;
-  if (i >= _table.size()/2)
-    i = _table.size()/2 - 1;
-
-  if (i == 0)
-    return _table[1];
-
-  // interpolate function value on found interval
-  // (t - x[i-1]) / (x[i] - x[i-1]) = (y - f[i-1]) / (f[i] - f[i-1])
-  // => y = f[i-1] + (f[i] - f[i-1]) * (t - x[i-1]) / (x[i] - x[i-1])
-  double x1 = _table[(i-1)*2];
-  double x2 = _table[i*2];
-  double y1 = _table[(i-1)*2+1];
-  double y2 = _table[i*2+1];
-  if (x2 - x1 < Precision::Confusion())
-    throw SALOME_Exception("TabFunction::compute : confused points");
-  return y1 + (y2 - y1) * ((t - x1) / (x2 - x1));
+  if( i>=0 && i<myData.size()-1 )
+    return integral( i, myData[2*(i+1)]-myData[2*i] );
+  else
+    return 0;
 }
 
-ExprFunction::ExprFunction(const char* expr, bool expMode)
-  : Function(expMode),
-    _var(1,1),
-    _val(1,1)
+double FunctionTable::integral( const int i, const double d )
 {
-  Handle( ExprIntrp_GenExp ) gen = ExprIntrp_GenExp::Create();
-  gen->Process(TCollection_AsciiString((char*)expr));
-  if (gen->IsDone())
-  {
-    _expression = gen->Expression();
-    _var(1) = new Expr_NamedUnknown("t");
-  }
+  double f, res = 0.0;
+  if( value( myData[2*i]+d, f ) )
+    res = ( myData[2*i] + f ) / 2.0 * d;
+
+  return res;
 }
 
-bool ExprFunction::IsReady() const
+double FunctionTable::integral( const double a, const double b )
 {
-  return !_expression.IsNull();
+  int x1s, x1f, x2s, x2f;
+  findBounds( a, x1s, x1f );
+  findBounds( b, x2s, x2f );
+  double J = 0;
+  for( int i=x1s; i<x2s; i++ )
+    J+=integral( i );
+  J-=integral( x1s, a-myData[2*x1s] );
+  J+=integral( x2s, b-myData[2*x2s] );
+  return J;
 }
 
-double ExprFunction::compute (double t) const
+bool FunctionTable::findBounds( const double x, int& x_ind_1, int& x_ind_2 ) const
 {
-  ASSERT(!_expression.IsNull());
-  _val(1) = t;
-  return _expression->Evaluate(_var, _val);
+  int n = myData.size();
+  if( n==0 || x<myData[0] )
+  {
+    x_ind_1 = x_ind_2 = 0;
+    return false;
+  }
+
+  for( int i=0; i<n-1; i++ )
+    if( myData[2*i]<=x && x<=myData[2*(i+1)] )
+    {
+      x_ind_1 = i;
+      x_ind_2 = i+1;
+      return true;
+    }
+  x_ind_1 = n-1;
+  x_ind_2 = n-1;
+  return false;
 }
 
-//================================================================================
-/*!
- * \brief Compute next abscissa when two previous ones are given
-  * \param sm2 - before previous abscissa
-  * \param sm1 - previous abscissa
-  * \param func - function of density
-  * \param reverse - the direction of next abscissa, increase (0) or decrease (1)
-  * \retval double - the new abscissa
- * 
- * The abscissa s is given by the formulae
- *
- * ....|--------|----------------|.....
- *    sm2      sm1               s
- *
- *    func(sm2) / func(sm1)  = (sm1-sm2) / (s-sm1)
- * => (s-sm1) * func(sm2) = (sm1-sm2) * func(sm1)
- * => s = sm1 + (sm1-sm2) * func(sm1) / func(sm2)
- */
-//================================================================================
 
-static double nextAbscissa(double sm2, double sm1, const Function& func, int reverse)
+
+class FunctionExpr : public Function, public math_Function
 {
-  if (reverse)
-  {
-    sm1 = 1.0 - sm1;
-    sm2 = 1.0 - sm2;
-  }
-  return sm1 + (sm1-sm2) * func(sm1) / func(sm2);
+public:
+  FunctionExpr( const char*, const bool );
+  virtual ~FunctionExpr();
+  virtual Standard_Boolean Value( Standard_Real, Standard_Real& );
+  virtual bool   value( const double, double& );  //inherited from Function
+  virtual double integral( const double, const double );
+
+private:
+  Handle(ExprIntrp_GenExp)    myExpr;
+  Expr_Array1OfNamedUnknown   myVars;
+  TColStd_Array1OfReal        myValues;
+};
+
+FunctionExpr::FunctionExpr( const char* str, const bool exp )
+: Function( exp ),
+  myVars( 1, 1 ),
+  myValues( 1, 1 )
+{
+  myExpr = ExprIntrp_GenExp::Create();
+  myExpr->Process( ( Standard_CString )str );
+  if( !myExpr->IsDone() )
+    myExpr.Nullify();
+
+  myVars.ChangeValue( 1 ) = new Expr_NamedUnknown( "t" );
 }
 
-//================================================================================
-/*!
- * \brief Compute distribution of points on a curve following the law of a function
-  * \param C3d - the curve to discretize
-  * \param first - the first parameter on the curve 
-  * \param last - the last parameter on the curve 
-  * \param theReverse - flag indicating that the curve must be reversed
-  * \param nbSeg - number of output segments
-  * \param func - the function f(t)
-  * \param theParams - output points
-  * \retval bool  - true if success
- */
-//================================================================================
+FunctionExpr::~FunctionExpr()
+{
+}
 
-static bool computeParamByFunc(Adaptor3d_Curve& C3d, double first, double last,
-                               double length, bool theReverse, 
-                               int nbSeg, const Function& func,
-                               list<double>& theParams)
+Standard_Boolean FunctionExpr::Value( Standard_Real T, Standard_Real& F )
+{
+  double f;
+  Standard_Boolean res = value( T, f );
+  F = f;
+  return res;
+}
+
+bool FunctionExpr::value( const double t, double& f )
 {
-  if (!func.IsReady())
+  if( myExpr.IsNull() )
     return false;
 
-  // ########## TMP until pb division by zero when func(0.0)==0 is fixed #########
-  if (::Abs(func(0.0)) <= ::RealSmall() ) return false;
-  // ########## TMP until pb division by zero when func(0.0)==0 is fixed #########
+  CASCatch_CatchSignals aCatchSignals;
+  aCatchSignals.Activate();
 
-  vector<double> xxx[2];
-  int nbPnt = 1 + nbSeg;
-  int rev, i;
-  for (rev=0; rev < 2; rev++)
+  myValues.ChangeValue( 1 ) = t;
+  bool ok = true;
+  CASCatch_TRY {
+    f = myExpr->Expression()->Evaluate( myVars, myValues );
+  }
+  CASCatch_CATCH(CASCatch_Failure) {
+    aCatchSignals.Deactivate();
+    Handle(CASCatch_Failure) aFail = CASCatch_Failure::Caught();
+    f = 0.0;
+  }
+
+  aCatchSignals.Deactivate();
+  ok = Function::value( t, f ) && ok;
+  return ok;
+}
+
+double FunctionExpr::integral( const double a, const double b )
+{
+  double res = 0.0;
+  CASCatch_TRY
   {
-    // curv abscisses initialisation
-    vector<double> x(nbPnt, 0.);
-    // the first abscissa is 0.0
+    math_GaussSingleIntegration _int( *this, a, b, 20 );
+    if( _int.IsDone() )
+      res = _int.Value();
+  }
+  CASCatch_CATCH(CASCatch_Failure)
+  {
+    res = 0.0;
+    MESSAGE( "Exception in integral calculating" );
+  }
+  return res;
+}
 
-    // The aim of the algorithm is to find a second abscisse x[1] such as the last
-    // one x[nbSeg] is very close to 1.0 with the epsilon precision
 
-    double x1_too_small = 0.0;
-    double x1_too_large = RealLast();
-    double x1 = 1.0/nbSeg;
-    while (1)
-    {
-      x[1] = x1;
 
-      // Check if the abscissa of the point 2 to N-1
-      // are in the segment ...
 
-      bool ok = true;
-      for (i=2; i <= nbSeg; i++)
-      {
-        x[i] = nextAbscissa(x[i-2], x[i-1], func, rev);
-        if (x[i] - 1.0 > Precision::Confusion())
-        {
-          x[nbSeg] = x[i];
-          ok = false;
-          break;
-        }
-      }
-      if (!ok)
-      {
-        // The segments are to large
-        // Decrease x1 ...
-        x1_too_large = x1;
-        x1 = (x1_too_small+x1_too_large)/2;
-        if ( x1 <= ::RealSmall() )
-          return false; // break infinite loop
-        continue;
-      }
 
-      // Look at the abscissa of the point N
-      // which is to be close to 1.0
 
-      // break condition --> algo converged !!
 
-      if (1.0 - x[nbSeg] < Precision::Confusion())
-        break;
+double dihotomySolve( Function& f, const double val, const double _start, const double _fin, const double eps, bool& ok )
+{
+  double start = _start, fin = _fin, start_val, fin_val; bool ok1, ok2;
+  ok1 = f.value( start, start_val );
+  ok2 = f.value( fin, fin_val );
 
-      // not ok ...
+  if( !ok1 || !ok2 )
+  {
+    ok = false;
+    return 0.0;
+  }
 
-      x1_too_small = x1;
+  bool start_pos = start_val>=val, fin_pos = fin_val>=val;
+  ok = true;
+  
+  while( fin-start>eps )
+  {
+    double mid = ( start+fin )/2.0, mid_val;
+    ok = f.value( mid, mid_val );
+    if( !ok )
+      return 0.0;
 
-      // Modify x1 value
+//    char buf[1024];
+//    sprintf( buf, "start=%f\nfin=%f\nmid_val=%f\n", float( start ), float( fin ), float( mid_val ) );
+//    MESSAGE( buf );
 
-      if (x1_too_large > 1e100)
-        x1 = 2*x1;
-      else
-        x1 = (x1_too_small+x1_too_large)/2;
+    bool mid_pos = mid_val>=val;
+    if( start_pos!=mid_pos )
+    {
+      fin_pos = mid_pos;
+      fin = mid;
     }
-    xxx[rev] = x;
+    else if( fin_pos!=mid_pos )
+    {
+      start_pos = mid_pos;
+      start = mid;
+    }
+    else
+      break;
   }
+  return (start+fin)/2.0;
+}
+
+static bool computeParamByFunc(Adaptor3d_Curve& C3d, double first, double last,
+                               double length, bool theReverse, 
+                               int nbSeg, Function& func,
+                               list<double>& theParams)
+{
+  OSD::SetSignal( true );
+  if( nbSeg<=0 )
+    return false;
 
-  // average
+  MESSAGE( "computeParamByFunc" );
+
+  int nbPnt = 1 + nbSeg;
   vector<double> x(nbPnt, 0.);
-  for (i=0; i < nbPnt; i++)
-    x[i] = (xxx[0][i] + (1.0 - xxx[1][nbPnt-i])) / 2;
+
+  x[0] = 0.0;
+  double J = func.integral( 0.0, 1.0 ) / nbSeg;
+  bool ok;
+  for( int i=1; i<nbSeg; i++ )
+  {
+    FunctionIntegral f_int( &func, x[i-1] );
+    x[i] = dihotomySolve( f_int, J, x[i-1], 1.0, 1E-4, ok );
+    if( !ok )
+      return false;
+  }
+
+  x[nbSeg] = 1.0;
+  MESSAGE( "Points:\n" );
+  char buf[1024];
+  for( int i=0; i<=nbSeg; i++ )
+  {
+    sprintf(  buf, "%f\n", float(x[i] ) );
+    MESSAGE( buf );
+  }
+    
+
 
   // apply parameters in range [0,1] to the space of the curve
   double prevU = first;
@@ -510,7 +602,7 @@ static bool computeParamByFunc(Adaptor3d_Curve& C3d, double first, double last,
     prevU = last;
     sign = -1.;
   }
-  for (i = 1; i < nbSeg; i++)
+  for( int i = 1; i < nbSeg; i++ )
   {
     double curvLength = length * (x[i] - x[i-1]) * sign;
     GCPnts_AbscissaPoint Discret( C3d, curvLength, prevU );
@@ -581,7 +673,7 @@ bool StdMeshers_Regular_1D::computeInternalParameters(const TopoDS_Edge& theEdge
         break;
       case StdMeshers_NumberOfSegments::DT_TabFunc:
         {
-          TabFunction func(_vvalue[ TAB_FUNC_IND ], (bool)_ivalue[ EXP_MODE_IND ]);
+          FunctionTable func(_vvalue[ TAB_FUNC_IND ], (bool)_ivalue[ EXP_MODE_IND ]);
           return computeParamByFunc(C3d, f, l, length, theReverse,
                                     _ivalue[ NB_SEGMENTS_IND ], func,
                                     theParams);
@@ -589,7 +681,7 @@ bool StdMeshers_Regular_1D::computeInternalParameters(const TopoDS_Edge& theEdge
         break;
       case StdMeshers_NumberOfSegments::DT_ExprFunc:
         {
-          ExprFunction func(_svalue[ EXPR_FUNC_IND ].c_str(), (bool)_ivalue[ EXP_MODE_IND ]);
+          FunctionExpr func(_svalue[ EXPR_FUNC_IND ].c_str(), (bool)_ivalue[ EXP_MODE_IND ]);
           return computeParamByFunc(C3d, f, l, length, theReverse,
                                     _ivalue[ NB_SEGMENTS_IND ], func,
                                     theParams);
index 9e0d5039821d3607f485304313a71971cf5c70fc..3deb0e3cedb349352ac3d5a9cf2daa576bb08c6b 100644 (file)
@@ -71,7 +71,8 @@ LIB_SERVER_IDL =
 CPPFLAGS += $(QT_INCLUDES) $(VTK_INCLUDES) $(OGL_INCLUDES) $(OCC_INCLUDES) $(PYTHON_INCLUDES) \
             -I${KERNEL_ROOT_DIR}/include/salome -I${GUI_ROOT_DIR}/include/salome -I${GEOM_ROOT_DIR}/include/salome \
             $(BOOST_CPPFLAGS)
-CXXFLAGS += -I${KERNEL_ROOT_DIR}/include/salome -I${GUI_ROOT_DIR}/include/salome -I${GEOM_ROOT_DIR}/include/salome
+CXXFLAGS += -I${KERNEL_ROOT_DIR}/include/salome -I${GUI_ROOT_DIR}/include/salome -I${GEOM_ROOT_DIR}/include/salome \
+           -I${QWTHOME}/include
 #$(OCC_CXXFLAGS)
 
 LDFLAGS += -lSMESH -lVTKViewer -lSalomeApp -lSMESHObject -lSMESHFiltersSelection $(OCC_KERNEL_LIBS) -lTKBO -L${KERNEL_ROOT_DIR}/lib/salome -L${GEOM_ROOT_DIR}/lib/salome -L${GUI_ROOT_DIR}/lib/salome
index d399b595c901ff70d6edfc5b5cf5129e6a386d95..b43492f5d817710dc4e524c9039f0c4715fa70df 100644 (file)
@@ -34,6 +34,7 @@
 #include "SMESHGUI_Hypotheses.h"
 #include "SMESHGUI_HypothesesUtils.h"
 #include "SMESHGUI_Utils.h"
+#include "SMESHGUI_FunctionPreview.h"
 
 #include "SUIT_Application.h"
 #include "SUIT_Desktop.h"
@@ -133,7 +134,8 @@ void StdMeshersGUI_CreateHypothesisDlg::CreateDlgLayout(const QString & theCapti
 
   /* Spin boxes with labels */
   list<SMESHGUI_aParameterPtr>::iterator paramIt = aParamList.begin();
-  for ( int row = 1; paramIt != aParamList.end(); paramIt++ , row++ )
+  int row;
+  for ( row = 1; paramIt != aParamList.end(); paramIt++ , row++ )
   {
     SMESHGUI_aParameterPtr param = (*paramIt);
     QLabel * label = new QLabel( GroupC1, "TextLabel" );
@@ -147,7 +149,7 @@ void StdMeshersGUI_CreateHypothesisDlg::CreateDlgLayout(const QString & theCapti
       aWidget->setMinimumSize( 150, 0 );
 
       QString sig = param->sigValueChanged();
-      if( !sig.isEmpty() && param->GetType()!=SMESHGUI_aParameter::TABLE )
+      if( !sig.isEmpty() /* && param->GetType()!=SMESHGUI_aParameter::TABLE*/ )
         connect( aWidget, sig.latin1(), this, SLOT( onValueChanged() ) );
          
       param->InitializeWidget( aWidget );
@@ -160,6 +162,8 @@ void StdMeshersGUI_CreateHypothesisDlg::CreateDlgLayout(const QString & theCapti
       myParamMap.insert( param, info );
     }
   }
+  myPreview = new SMESHGUI_FunctionPreview( GroupC1 );
+  GroupC1Layout->addWidget( myPreview, row, 1 );
   
   StdMeshersGUI_CreateHypothesisDlgLayout->addWidget( GroupC1, 1 );
 
@@ -284,7 +288,8 @@ bool StdMeshersGUI_CreateHypothesisDlg::ClickOnApply()
          break;
         }
 
-    SetParameters( Hyp, aParamList );
+    if( !SetParameters( Hyp, aParamList ) )
+      return false;
 
     //set new Attribute Comment for hypothesis which parameters were set
     QString aParams = "";
@@ -394,7 +399,29 @@ void StdMeshersGUI_CreateHypothesisDlg::onValueChanged()
       if( anIt.data().editor == w )
       {
         param = anIt.key();
-        param->TakeValue( w );
+       param->TakeValue( w );
+
+       SMESHGUI_strParameter* str_param = dynamic_cast<SMESHGUI_strParameter*>( param.operator->() );
+       SMESHGUI_tableParameter* tab_param = dynamic_cast<SMESHGUI_tableParameter*>( param.operator->() );
+       SMESHGUI_boolParameter* bool_param = dynamic_cast<SMESHGUI_boolParameter*>( param.operator->() );
+
+       if( str_param && str_param->needPreview() )
+       {
+         QString val; str_param->GetNewText( val );
+         myPreview->setParams( val );
+       }
+       else if( tab_param && tab_param->needPreview() )
+       {
+         SMESH::double_array d;
+         tab_param->data( d );
+         myPreview->setParams( d );
+       }
+       else if( bool_param && bool_param->needPreview() )
+       {
+         int exp=0;
+         bool_param->GetNewInt( exp );
+         myPreview->setIsExp( exp );
+       }
         UpdateShown( param );
         break;
       }
@@ -426,10 +453,18 @@ void StdMeshersGUI_CreateHypothesisDlg::UpdateShown( const SMESHGUI_aParameterPt
 
   ParameterMap::const_iterator anIt = myParamMap.begin(),
                                 aLast = myParamMap.end();
+  bool preview = false;
   for( ; anIt!=aLast; anIt++ )
   {
     bool shown = hasValue && map[ val ].contains( (*anIt).order );
     (*anIt).editor->setShown( shown );
     (*anIt).label->setShown( shown );
+    if( shown )
+    {
+      SMESHGUI_strParameter* str_param = dynamic_cast<SMESHGUI_strParameter*>( anIt.key().operator->() );
+      SMESHGUI_tableParameter* tab_param = dynamic_cast<SMESHGUI_tableParameter*>( anIt.key().operator->() );
+      preview = preview || ( str_param && str_param->needPreview() ) || ( tab_param && tab_param->needPreview() );
+    }
   }
+  myPreview->setShown( preview );
 }
index 5d61f408ba4f2fd3a7c245cc452e5ee801b519af..852fd468d016ed9f35dee3c823225168f966b3aa 100644 (file)
@@ -46,6 +46,7 @@ class QLineEdit;
 class QPushButton;
 class SMESHGUI;
 class SMESHGUI_SpinBox;
+class SMESHGUI_FunctionPreview;
 
 //=================================================================================
 // class    : StdMeshersGUI_CreateHypothesisDlg
@@ -108,6 +109,7 @@ private:
     QPushButton*      buttonOk;
     QPushButton*      buttonApply;
     QPushButton*      buttonCancel;
+    SMESHGUI_FunctionPreview* myPreview;
 
 private slots:
 
index 7d52876d96b7567e8858da08939ee21e5a823b59..67d4f450c7b0b70c6ae5342f0505209501f6d83c 100644 (file)
@@ -134,8 +134,8 @@ void StdMeshersGUI_Parameters::SetInitValue( SMESHGUI_aParameterPtr param,
 #define DOUBLE_PARAM(v,l,b,t,s,d) SMESHGUI_aParameterPtr(new SMESHGUI_doubleParameter(v,l,b,t,s,d))
 #define INT_PARAM(v,l,b,t) SMESHGUI_aParameterPtr(new SMESHGUI_intParameter(v,l,b,t))
 #define ENUM_PARAM(v,i,l) SMESHGUI_aParameterPtr(new SMESHGUI_enumParameter(v,i,l))
-#define STR_PARAM(i,l) SMESHGUI_aParameterPtr(new SMESHGUI_strParameter(i,l))
-#define BOOL_PARAM(i,l) SMESHGUI_aParameterPtr(new SMESHGUI_boolParameter(i,l))
+#define STR_PARAM(i,l,preview) SMESHGUI_aParameterPtr(new SMESHGUI_strParameter(i,l,preview))
+#define BOOL_PARAM(i,l,preview) SMESHGUI_aParameterPtr(new SMESHGUI_boolParameter(i,l,preview))
 
 void StdMeshersGUI_Parameters::GetParameters (const QString&                 hypType,
                                               list<SMESHGUI_aParameterPtr> & paramList )
@@ -183,7 +183,7 @@ void StdMeshersGUI_Parameters::GetParameters (const QString&                 hyp
     paramList.push_back ( DOUBLE_PARAM (1.0,
                                      QObject::tr("SMESH_NB_SEGMENTS_SCALE_PARAM"),
                                      VALUE_SMALL, VALUE_MAX, 0.1, 6 ));
-    SMESHGUI_tableParameter* tab = new SMESHGUI_tableParameter( 0.0, QObject::tr( "SMESH_TAB_FUNC" ) );
+    SMESHGUI_tableParameter* tab = new SMESHGUI_tableParameter( 0.0, QObject::tr( "SMESH_TAB_FUNC" ), true );
     tab->setRowCount( 5 );
     tab->setColCount( 2 );
     //default size of table: 5x2
@@ -198,10 +198,10 @@ void StdMeshersGUI_Parameters::GetParameters (const QString&                 hyp
     paramList.push_back ( SMESHGUI_aParameterPtr( tab ) );
 
     //4-th parameter in list
-    paramList.push_back ( STR_PARAM ( "", QObject::tr( "SMESH_EXPR_FUNC" ) ) );
+    paramList.push_back ( STR_PARAM ( "", QObject::tr( "SMESH_EXPR_FUNC" ), true ) );
 
     //5-th parameter in list
-    paramList.push_back ( BOOL_PARAM ( false, QObject::tr( "SMESH_EXP_MODE" ) ) );
+    paramList.push_back ( BOOL_PARAM ( false, QObject::tr( "SMESH_EXP_MODE" ), true ) );
   }
   else if (hypType.compare("Arithmetic1D") == 0)
   {
@@ -291,7 +291,7 @@ void StdMeshersGUI_Parameters::GetParameters (SMESH::SMESH_Hypothesis_ptr    the
     {
       char* expr_func = NOS->GetExpressionFunction();
       SetInitValue( *anIt, expr_func );
-      delete expr_func;
+      //delete expr_func;
     }
     anIt++;