diff --git a/Common/Context.h b/Common/Context.h
index 6e864ba277732418a102a931315acc876cb889cd..ecfbd3c2aab55badd3afc8cb11c85b7e48551aae 100644
--- a/Common/Context.h
+++ b/Common/Context.h
@@ -197,7 +197,8 @@ public :
     int smooth_normals;
     double angle_smooth_normals;
     double stl_distance_tol, dihedral_angle_tol;
-    int nb_elem_per_rc, min_elem_size_fact, edge_prolongation_threshold;
+    int edge_prolongation_threshold;
+    double  nb_elem_per_rc ,   min_elem_size_fact , target_elem_size_fact, beta_smooth_metric;
   } mesh;
 
   // post processing options 
diff --git a/Common/DefaultOptions.h b/Common/DefaultOptions.h
index aebacea5756adaf610e0fff6003f29c6f4728ff1..8537c09bc6da37e7e6f9838aea83346c4546892f 100644
--- a/Common/DefaultOptions.h
+++ b/Common/DefaultOptions.h
@@ -899,8 +899,12 @@ StringXNumber MeshOptions_Number[] = {
 
   { F|O, "NbElemsPerRadiusOfCurv" , opt_mesh_nb_elem_per_rc, 5. ,
     "Number of elements per radius of curvature in the remesher" },
+  { F|O, "TargetElmentSizeFact" , opt_mesh_target_elem_size_fact, 20. ,
+    "Target element size factor in the Remesher" },
   { F|O, "MinimumElementSizeFact" , opt_mesh_min_elem_size_fact, 500. ,
-    "Number of elements per radius of curvature in the remesher" },
+    "Minimum element size factor in the Remesher" },
+  { F|O, "BetaSmoothMetric" ,opt_mesh_beta_smooth_metric, 0.9 ,
+    "Maximum ratio of two consecutive edge lengths" },
   { F, "NbHexahedra" , opt_mesh_nb_hexahedra , 0. , 
     "Number of hexahedra in the current mesh (read-only)" },
   { F, "NbNodes" , opt_mesh_nb_nodes , 0. , 
diff --git a/Common/Options.cpp b/Common/Options.cpp
index 2bc9aa9925a2bc5f731a618eba7edf78e82ad92f..0aae12f6a425acf3524133ea32e377b292f8437e 100644
--- a/Common/Options.cpp
+++ b/Common/Options.cpp
@@ -1,4 +1,4 @@
-// $Id: Options.cpp,v 1.260 2005-10-15 19:06:08 geuzaine Exp $
+// $Id: Options.cpp,v 1.261 2005-11-01 16:37:12 remacle Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -4411,14 +4411,33 @@ double opt_mesh_nb_elem_per_rc(OPT_ARGS_NUM)
 double opt_mesh_min_elem_size_fact(OPT_ARGS_NUM)
 {
   if(action & GMSH_SET)
-    CTX.mesh.min_elem_size_fact = (int)val;
+    CTX.mesh.min_elem_size_fact = val;
 #if defined(HAVE_FLTK)
   if(WID && (action & GMSH_GUI))
     WID->mesh_value[23]->value(CTX.mesh.min_elem_size_fact);
 #endif
   return CTX.mesh.min_elem_size_fact;
 }
-
+double opt_mesh_target_elem_size_fact(OPT_ARGS_NUM)
+{
+  if(action & GMSH_SET)
+    CTX.mesh.target_elem_size_fact = val;
+#if defined(HAVE_FLTK)
+  if(WID && (action & GMSH_GUI))
+    WID->mesh_value[24]->value(CTX.mesh.target_elem_size_fact);
+#endif
+  return CTX.mesh.target_elem_size_fact;
+}
+double opt_mesh_beta_smooth_metric(OPT_ARGS_NUM)
+{
+  if(action & GMSH_SET)
+    CTX.mesh.beta_smooth_metric = val;
+#if defined(HAVE_FLTK)
+  if(WID && (action & GMSH_GUI))
+    WID->mesh_value[25]->value(CTX.mesh.beta_smooth_metric);
+#endif
+  return CTX.mesh.beta_smooth_metric;
+}
 double opt_mesh_msh_file_version(OPT_ARGS_NUM)
 {
   if(action & GMSH_SET)
diff --git a/Common/Options.h b/Common/Options.h
index 81c4a166588ab28bc989ab2c75808726e8d5bcbe..4f66ecd25dfe42583b291fa084e2af18d4215cdb 100644
--- a/Common/Options.h
+++ b/Common/Options.h
@@ -440,6 +440,8 @@ double opt_mesh_nb_smoothing(OPT_ARGS_NUM);
 double opt_mesh_stl_distance_tol(OPT_ARGS_NUM);
 double opt_mesh_nb_elem_per_rc(OPT_ARGS_NUM);
 double opt_mesh_min_elem_size_fact(OPT_ARGS_NUM);
+double opt_mesh_target_elem_size_fact(OPT_ARGS_NUM);
+double opt_mesh_beta_smooth_metric(OPT_ARGS_NUM);
 double opt_mesh_dihedral_angle_tol(OPT_ARGS_NUM);
 double opt_mesh_edge_prolongation_threshold(OPT_ARGS_NUM);
 double opt_mesh_nb_partitions(OPT_ARGS_NUM);
diff --git a/Fltk/Callbacks.cpp b/Fltk/Callbacks.cpp
index 26dbff5301a0d74b3b3de80e9e535b7c386d7b5d..a147301a31a2279f2a80ca3a5c93ef4c069a161f 100644
--- a/Fltk/Callbacks.cpp
+++ b/Fltk/Callbacks.cpp
@@ -1,4 +1,4 @@
-// $Id: Callbacks.cpp,v 1.374 2005-10-15 20:38:35 geuzaine Exp $
+// $Id: Callbacks.cpp,v 1.375 2005-11-01 16:37:12 remacle Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -1068,6 +1068,8 @@ void mesh_options_ok_cb(CALLBACK_ARGS)
   opt_mesh_edge_prolongation_threshold(0, GMSH_SET, WID->mesh_value[21]->value());
   opt_mesh_nb_elem_per_rc(0, GMSH_SET, WID->mesh_value[22]->value());
   opt_mesh_min_elem_size_fact(0, GMSH_SET, WID->mesh_value[23]->value());
+  opt_mesh_target_elem_size_fact(0, GMSH_SET, WID->mesh_value[24]->value());
+  opt_mesh_beta_smooth_metric(0, GMSH_SET, WID->mesh_value[25]->value());
 
   opt_mesh_point_type(0, GMSH_SET, WID->mesh_choice[0]->value());
   opt_mesh_line_type(0, GMSH_SET, WID->mesh_choice[1]->value());
diff --git a/Fltk/GUI.cpp b/Fltk/GUI.cpp
index 0a88fa3c88396cbb27b64d29cf2f0e2f6b72d506..7c9363345dfeb08bbd4d7aaedc7a28e048e2eb91 100644
--- a/Fltk/GUI.cpp
+++ b/Fltk/GUI.cpp
@@ -1,4 +1,4 @@
-// $Id: GUI.cpp,v 1.463 2005-10-24 15:53:18 geuzaine Exp $
+// $Id: GUI.cpp,v 1.464 2005-11-01 16:37:12 remacle Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -2255,7 +2255,7 @@ void GUI::create_option_window()
       mesh_value[22] = new Fl_Value_Input(L + 2 * WB, 2 * WB + 4 * BH, IW, BH, "Number of elements per rad. of curv.");
       mesh_value[22]->minimum(1);
       mesh_value[22]->maximum(10);
-      mesh_value[22]->step(1);
+      mesh_value[22]->step(.1);
       mesh_value[22]->align(FL_ALIGN_RIGHT); 
 
       mesh_value[23] = new Fl_Value_Input(L + 2 * WB, 2 * WB + 5 * BH, IW, BH, "LC/Minimum element size");
@@ -2264,6 +2264,18 @@ void GUI::create_option_window()
       mesh_value[23]->step(10);
       mesh_value[23]->align(FL_ALIGN_RIGHT); 
 
+      mesh_value[24] = new Fl_Value_Input(L + 2 * WB, 2 * WB + 6 * BH, IW, BH, "LC/Target element size");
+      mesh_value[24]->minimum(1);
+      mesh_value[24]->maximum(1000);
+      mesh_value[24]->step(1);
+      mesh_value[24]->align(FL_ALIGN_RIGHT); 
+
+      mesh_value[25] = new Fl_Value_Input(L + 2 * WB, 2 * WB + 7 * BH, IW, BH, "BETA smoothing factor");
+      mesh_value[25]->minimum(0);
+      mesh_value[25]->maximum(1);
+      mesh_value[25]->step(.01);
+      mesh_value[25]->align(FL_ALIGN_RIGHT); 
+
       o->end();
     }
 
diff --git a/Mesh/BDS.cpp b/Mesh/BDS.cpp
index dde6a0ef9742701bac547eb51e6fc05a84e9cf78..b0546b7abf4db54048ff3b77275ced4a698940af 100644
--- a/Mesh/BDS.cpp
+++ b/Mesh/BDS.cpp
@@ -1,4 +1,4 @@
-// $Id: BDS.cpp,v 1.39 2005-10-28 08:31:00 remacle Exp $
+// $Id: BDS.cpp,v 1.40 2005-11-01 16:37:12 remacle Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -778,7 +778,7 @@ void BDS_Mesh :: createSearchStructures ( )
 
   Msg(INFO,"creating the ANN search structure\n");
   
-  const double LC_SEARCH = LC *.3e-3;
+  const double LC_SEARCH = LC *1e-2;
 
   for (std::set<BDS_GeomEntity*,GeomLessThan>::iterator it = geom.begin();
        it != geom.end();
@@ -789,9 +789,9 @@ void BDS_Mesh :: createSearchStructures ( )
 	  if ((*it)->t.size() > 5)
 	    {	      
 	      int maxPts = 0;
-
+	      
 	      std::set<BDS_Edge *> edg;
-
+	      
 	      std::list<BDS_Triangle*>::iterator tit  = (*it)->t.begin();
 	      std::list<BDS_Triangle*>::iterator tite = (*it)->t.end();
 
@@ -2407,8 +2407,9 @@ void BDS_Mesh :: compute_metric_edge_lengths (const BDS_Metric & metric)
   }
   //  printf("smoothing\n");
   const int NITER = 3;
+
   for (int I=0;I<NITER;++I)  {     
-    const double BETA = 0.9;
+    const double BETA = metric.beta;
     std::set<BDS_Point*, PointLessThan>::iterator it   = points.begin();
     std::set<BDS_Point*, PointLessThan>::iterator ite  = points.end();
     while (it != ite)
@@ -2440,14 +2441,12 @@ void BDS_Mesh :: compute_metric_edge_lengths (const BDS_Metric & metric)
 }
     
 
-int BDS_Mesh :: adapt_mesh ( double l,  double C1, double C2 , bool smooth, BDS_Mesh *geom_mesh) 
+int BDS_Mesh :: adapt_mesh ( const  BDS_Metric &metric, bool smooth, BDS_Mesh *geom_mesh) 
 {
     int nb_modif = 0;
     SNAP_SUCCESS = 0;
     SNAP_FAILURE = 0;
 
-    BDS_Metric metric ( l , LC/ C1 , LC, C2 );
-
     //    �pr�intf("METRIC %g %g %g\n",LC,metric._min,metric._max);
 
     // add initial set of edges in a list
diff --git a/Mesh/BDS.h b/Mesh/BDS.h
index aa36c3da5538f1fb3d3503d4e3cf7b046b4bfd96..8de723d097d18e2290c1985616d8780d85c9c458 100644
--- a/Mesh/BDS.h
+++ b/Mesh/BDS.h
@@ -48,15 +48,15 @@ double quality_triangle  (BDS_Point *p1, BDS_Point *p2, BDS_Point *p3);
 class BDS_Metric
 {
  public:
-  const double target,_min,_max,treshold;
+  const double target,_min,_max,treshold, beta;
   const double nb_elements_per_radius_of_curvature;
-  BDS_Metric ( double _target , double _mmin, double _mmax, double cc, double _tres = 0.7) 
-    : target(_target),_min(_mmin),_max(_mmax), treshold(_tres),nb_elements_per_radius_of_curvature(cc)
+  BDS_Metric ( double _target , double _mmin, double _mmax, double _b, double cc, double _tres = 0.7) 
+    : target(_target),_min(_mmin),_max(_mmax), beta(_b),treshold(_tres),nb_elements_per_radius_of_curvature(cc)
     {}
   inline double update_target_length( double _target, double old_target_length  ) const
     {
       if (_target <= _min) return _min;
-      if (_target >= _max) return _max;
+      if (_target >= _max && old_target_length > _max) return _max;
       if (old_target_length > _target)return _target ;
       return old_target_length;
 
@@ -643,7 +643,7 @@ class BDS_Mesh
     void color_plane_surf ( double eps , int nb);
     void reverseEngineerCAD ( ) ;
     void createSearchStructures ( ) ;
-    int adapt_mesh(double,double, double,bool smooth = false,BDS_Mesh *geom = 0); 
+    int adapt_mesh(const BDS_Metric & ,bool smooth = false,BDS_Mesh *geom = 0); 
     void compute_metric_edge_lengths (const BDS_Metric & metric);
     void cleanup();
     // io's 
diff --git a/Mesh/DiscreteSurface.cpp b/Mesh/DiscreteSurface.cpp
index 92607d8d52869154774f0fff1953d081e6783d28..403c931b5fe9a05459c9942d690681a9c46a6e99 100644
--- a/Mesh/DiscreteSurface.cpp
+++ b/Mesh/DiscreteSurface.cpp
@@ -1,4 +1,4 @@
-// $Id: DiscreteSurface.cpp,v 1.30 2005-10-28 08:31:00 remacle Exp $
+// $Id: DiscreteSurface.cpp,v 1.31 2005-11-01 16:37:12 remacle Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -373,17 +373,18 @@ int ReMesh(Mesh *M)
 
 int MeshDiscreteSurface(Surface *s)
 { 
-
   const int NITER = 10;
   if(THEM->bds){
+    BDS_Metric metric ( THEM->bds->LC/ CTX.mesh.target_elem_size_fact,  
+			THEM->bds->LC/ CTX.mesh.min_elem_size_fact,
+			THEM->bds->LC,
+			CTX.mesh.beta_smooth_metric,
+			CTX.mesh.nb_elem_per_rc);   
     Msg(STATUS2, "Discrete Surface Mesh Generator...");
     if(!THEM->bds_mesh){
       THEM->bds_mesh = new BDS_Mesh (*(THEM->bds));
       int iter = 0;
-      while(iter < NITER && THEM->bds_mesh->adapt_mesh(CTX.mesh.lc_factor * THEM->bds->LC,
-						       CTX.mesh.min_elem_size_fact,
-						       CTX.mesh.nb_elem_per_rc,
-						       true, THEM->bds)){
+      while(iter < NITER && THEM->bds_mesh->adapt_mesh(metric,true, THEM->bds)){
 	Msg(STATUS2, "Iteration %2d/%d done (%d triangles)\n",iter, NITER,THEM->bds_mesh->triangles.size());
 	iter ++;
       }