diff --git a/Common/Context.h b/Common/Context.h
index ec8365d22957ea8ae47f8fdbee57edfa99bec58f..9ad991d3de00087bcf5c7d096a00a446d676dd4d 100644
--- a/Common/Context.h
+++ b/Common/Context.h
@@ -175,7 +175,7 @@ public :
     int points_per_element;
     int optimize;
     double quality;
-    int quality_type;
+    int quality_type, label_type;
     double quality_inf, quality_sup, radius_inf, radius_sup;
     double scaling_factor, lc_factor, rand_factor;
     int dual, interactive;
diff --git a/Common/DefaultOptions.h b/Common/DefaultOptions.h
index 5dd751894e802dc14231505792eb8e33b7d03c34..de943f13741953ddf64c846180e6c5efcf0b24a9 100644
--- a/Common/DefaultOptions.h
+++ b/Common/DefaultOptions.h
@@ -877,6 +877,8 @@ StringXNumber MeshOptions_Number[] = {
   { F|O, "Interactive" , opt_mesh_interactive , 0. ,
     "Show the construction of 2D anisotropic mesh in real time" },
 
+  { F|O, "LabelType" , opt_mesh_label_type , 0. , 
+    "Type of element label (0=element number, 1=elementary entity number, 2=physical entity number, 3=partition number)" },
   { F|O, "Light" , opt_mesh_light , 0. , 
     "Enable lighting for the mesh" },
   { F|O, "LightTwoSide" , opt_mesh_light_two_side , 1. , 
diff --git a/Common/Options.cpp b/Common/Options.cpp
index d7b4bb4b8b2269cce6fe66ba0ea23d648bbb7f0b..6b32b67dbaeafac2536280225d2408ac380195db 100644
--- a/Common/Options.cpp
+++ b/Common/Options.cpp
@@ -1,4 +1,4 @@
-// $Id: Options.cpp,v 1.250 2005-07-08 22:07:37 geuzaine Exp $
+// $Id: Options.cpp,v 1.251 2005-08-02 17:02:08 geuzaine Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -4096,6 +4096,21 @@ double opt_mesh_radius_sup(OPT_ARGS_NUM)
   return CTX.mesh.radius_sup;
 }
 
+double opt_mesh_label_type(OPT_ARGS_NUM)
+{
+  if(action & GMSH_SET) {
+    CTX.mesh.label_type = (int)val;
+    if(CTX.mesh.label_type < 0 || CTX.mesh.label_type > 3)
+      CTX.mesh.label_type = 0;
+  }
+#if defined(HAVE_FLTK)
+  if(WID && (action & GMSH_GUI)){
+    WID->mesh_choice[7]->value(CTX.mesh.label_type);
+  }
+#endif
+  return CTX.mesh.label_type;
+}
+
 double opt_mesh_points(OPT_ARGS_NUM)
 {
   if(action & GMSH_SET) {
diff --git a/Common/Options.h b/Common/Options.h
index 1e97b423d9a7e36b0d144a90ca03bce2511c280c..15fbfe444343e6c785868bd56663293cf80bbe64 100644
--- a/Common/Options.h
+++ b/Common/Options.h
@@ -415,6 +415,7 @@ double opt_mesh_quality_sup(OPT_ARGS_NUM);
 double opt_mesh_quality_type(OPT_ARGS_NUM);
 double opt_mesh_radius_inf(OPT_ARGS_NUM);
 double opt_mesh_radius_sup(OPT_ARGS_NUM);
+double opt_mesh_label_type(OPT_ARGS_NUM);
 double opt_mesh_points(OPT_ARGS_NUM);
 double opt_mesh_lines(OPT_ARGS_NUM);
 double opt_mesh_surfaces_edges(OPT_ARGS_NUM);
diff --git a/Fltk/Callbacks.cpp b/Fltk/Callbacks.cpp
index e333072ef99a2a2c2e8985b75bddf91dad29a088..3d7987e01e358b273cc32a6ae92d9851adc2452f 100644
--- a/Fltk/Callbacks.cpp
+++ b/Fltk/Callbacks.cpp
@@ -1,4 +1,4 @@
-// $Id: Callbacks.cpp,v 1.363 2005-07-14 14:28:15 remacle Exp $
+// $Id: Callbacks.cpp,v 1.364 2005-08-02 17:02:08 geuzaine Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -1198,6 +1198,7 @@ void mesh_options_ok_cb(CALLBACK_ARGS)
 		  DELAUNAY_TETGEN);
   opt_mesh_color_carousel(0, GMSH_SET, WID->mesh_choice[4]->value());
   opt_mesh_quality_type(0, GMSH_SET, WID->mesh_choice[6]->value());
+  opt_mesh_label_type(0, GMSH_SET, WID->mesh_choice[7]->value());
 }
 
 void mesh_cut_plane_cb(CALLBACK_ARGS)
diff --git a/Fltk/GUI.cpp b/Fltk/GUI.cpp
index 51c1b754821765aa321e7975548b57363eb4520a..de21528f2f030621832440b2f106da8462518d05 100644
--- a/Fltk/GUI.cpp
+++ b/Fltk/GUI.cpp
@@ -1,4 +1,4 @@
-// $Id: GUI.cpp,v 1.450 2005-07-14 14:28:15 remacle Exp $
+// $Id: GUI.cpp,v 1.451 2005-08-02 17:02:08 geuzaine Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -2399,21 +2399,32 @@ void GUI::create_option_window()
       mesh_butt[12]->down_box(GMSH_TOGGLE_BOX);
       mesh_butt[12]->selection_color(GMSH_TOGGLE_COLOR);
 
-      mesh_butt[13] = new Fl_Check_Button(L + width / 2, 2 * WB + 2 * BH, BW / 2 - WB, BH, "Line element numbers");
+      mesh_butt[13] = new Fl_Check_Button(L + width / 2, 2 * WB + 2 * BH, BW / 2 - WB, BH, "Line element labels");
       mesh_butt[13]->type(FL_TOGGLE_BUTTON);
       mesh_butt[13]->down_box(GMSH_TOGGLE_BOX);
       mesh_butt[13]->selection_color(GMSH_TOGGLE_COLOR);
 
-      mesh_butt[14] = new Fl_Check_Button(L + width / 2, 2 * WB + 3 * BH, BW / 2 - WB, BH, "Surface element numbers");
+      mesh_butt[14] = new Fl_Check_Button(L + width / 2, 2 * WB + 3 * BH, BW / 2 - WB, BH, "Surface element labels");
       mesh_butt[14]->type(FL_TOGGLE_BUTTON);
       mesh_butt[14]->down_box(GMSH_TOGGLE_BOX);
       mesh_butt[14]->selection_color(GMSH_TOGGLE_COLOR);
 
-      mesh_butt[15] = new Fl_Check_Button(L + width / 2, 2 * WB + 4 * BH, BW / 2 - WB, BH, "Volume element numbers");
+      mesh_butt[15] = new Fl_Check_Button(L + width / 2, 2 * WB + 4 * BH, BW / 2 - WB, BH, "Volume element labels");
       mesh_butt[15]->type(FL_TOGGLE_BUTTON);
       mesh_butt[15]->down_box(GMSH_TOGGLE_BOX);
       mesh_butt[15]->selection_color(GMSH_TOGGLE_COLOR);
 
+      static Fl_Menu_Item menu_label_type[] = {
+        {"Element numbers", 0, 0, 0},
+        {"Elementary entity numbers", 0, 0, 0},
+        {"Physical entity numbers", 0, 0, 0},
+        {"Partition numbers", 0, 0, 0},
+        {0}
+      };
+      mesh_choice[7] = new Fl_Choice(L + width / 2, 2 * WB + 5 * BH, IW, BH, "Labels");
+      mesh_choice[7]->menu(menu_label_type);
+      mesh_choice[7]->align(FL_ALIGN_RIGHT);
+
       mesh_value[4] = new Fl_Value_Input(L + 2 * WB, 2 * WB + 7 * BH, IW / 2, BH);
       mesh_value[4]->minimum(0);
       mesh_value[4]->maximum(1);
diff --git a/Graphics/Mesh.cpp b/Graphics/Mesh.cpp
index 1ed4c85b6af735cbb7aa93f87403fb053cbafbed..f5c9fbef4ae6b9bd3231835da6a92dc07c06d83d 100644
--- a/Graphics/Mesh.cpp
+++ b/Graphics/Mesh.cpp
@@ -1,4 +1,4 @@
-// $Id: Mesh.cpp,v 1.134 2005-06-25 04:05:39 geuzaine Exp $
+// $Id: Mesh.cpp,v 1.135 2005-08-02 17:02:09 geuzaine Exp $
 //
 // Copyright (C) 1997-2005 C. Geuzaine, J.-F. Remacle
 //
@@ -77,15 +77,16 @@ void draw_polygon_2d(double r, double g, double b, int n,
 
 int getFirstPhysical(int type, int num)
 {
-  // If we visualize the mesh by coloring the physical entities, this
+  // If we visualize the mesh by coloring the physical entities, or if
+  // we ask to display physical enyity labels on elements, this
   // routine returns the number of the first physical entity of type
   // "type" that contains the elementary entity "num"
-  if(CTX.mesh.color_carousel == 2){
+  if(CTX.mesh.color_carousel == 2 || CTX.mesh.label_type == 2){
     static int warn = 1;
     if(List_Nbr(THEM->PhysicalGroups) > 100 && warn){
       Msg(WARNING, "There are many physical entities in the mesh (%d)",
 	  List_Nbr(THEM->PhysicalGroups));
-      Msg(WARNING, "You might want to color the mesh by elementary entity instead");
+      Msg(WARNING, "You might want to color and/or label the mesh by elementary entity instead");
       warn = 0;
     }
     for(int i = 0; i < List_Nbr(THEM->PhysicalGroups); i++){
@@ -631,7 +632,14 @@ void Draw_Mesh_Line(void *a, void *b)
 
   if(CTX.mesh.lines_num) {
     glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", s->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", s->iEnt);
+    else
+      sprintf(Num, "%d", s->Num);
     double offset = 0.3 * (CTX.mesh.line_width + CTX.gl_fontsize) * CTX.pixel_equiv_x;
     glRasterPos3d(Xc + offset / CTX.s[0],
                   Yc + offset / CTX.s[1],
@@ -979,7 +987,14 @@ void Draw_Mesh_Triangle(void *a, void *b)
       glColor4ubv((GLubyte *) & CTX.color.mesh.line);
     else
       glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", s->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", s->iEnt);
+    else
+      sprintf(Num, "%d", s->Num);
     glRasterPos3d(Xc, Yc, Zc);
     Draw_String(Num);
   }
@@ -1151,7 +1166,14 @@ void Draw_Mesh_Quadrangle(void *a, void *b)
       glColor4ubv((GLubyte *) & CTX.color.mesh.line);
     else
       glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", q->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", q->iEnt);
+    else
+      sprintf(Num, "%d", q->Num);
     glRasterPos3d(Xc, Yc, Zc);
     Draw_String(Num);
   }
@@ -1342,7 +1364,14 @@ void Draw_Mesh_Tetrahedron(void *a, void *b)
       glColor4ubv((GLubyte *) & CTX.color.mesh.line);
     else
       glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", s->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", s->iEnt);
+    else
+      sprintf(Num, "%d", s->Num);
     glRasterPos3d(Xc, Yc, Zc);
     Draw_String(Num);
   }
@@ -1533,7 +1562,14 @@ void Draw_Mesh_Hexahedron(void *a, void *b)
       glColor4ubv((GLubyte *) & CTX.color.mesh.line);
     else
       glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", h->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", h->iEnt);
+    else
+      sprintf(Num, "%d", h->Num);
     glRasterPos3d(Xc, Yc, Zc);
     Draw_String(Num);
   }
@@ -1739,7 +1775,14 @@ void Draw_Mesh_Prism(void *a, void *b)
       glColor4ubv((GLubyte *) & CTX.color.mesh.line);
     else
       glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", p->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", p->iEnt);
+    else
+      sprintf(Num, "%d", p->Num);
     glRasterPos3d(Xc, Yc, Zc);
     Draw_String(Num);
   }
@@ -1917,7 +1960,14 @@ void Draw_Mesh_Pyramid(void *a, void *b)
       glColor4ubv((GLubyte *) & CTX.color.mesh.line);
     else
       glColor4ubv((GLubyte *) & col);
-    sprintf(Num, "%d", p->Num);
+    if(CTX.mesh.label_type == 3)
+      sprintf(Num, "%d", iPart);
+    else if(CTX.mesh.label_type == 2)
+      sprintf(Num, "%d", thePhysical);
+    else if(CTX.mesh.label_type == 1)
+      sprintf(Num, "%d", p->iEnt);
+    else
+      sprintf(Num, "%d", p->Num);
     glRasterPos3d(Xc, Yc, Zc);
     Draw_String(Num);
   }
diff --git a/TODO b/TODO
index 9ac404bb71bc8459e3cf6dff70ff7d761794cb1e..e0dd39aa907596fe2aa5fc9e82a5eefa00a4ef2d 100644
--- a/TODO
+++ b/TODO
@@ -1,10 +1,23 @@
-$Id: TODO,v 1.95 2005-07-26 13:55:24 remacle Exp $
+$Id: TODO,v 1.96 2005-08-02 17:02:07 geuzaine Exp $
 
 ********************************************************************
 
 automatic exterior orientation of boundary surfaces (would greatly
-enhance Netgen/Frontal integration). Easiest way is prabably to
-compute the solid angle using the discretized surface.
+enhance Netgen/Frontal integration). One way is to compute the solid
+angle using the discretized surface. Another (probably more efficient
+way) is to select one element per surface loop, shoot a ray in both
+normal directions, and count the intersections with all other elements
+in the same surface: if we get 0 or an even number, the normal points
+outside. If we get an even number, it points inside.
+
+********************************************************************
+
+add an interactive way to choose the orientation of surfaces in
+surface loops and lines in line loops?
+
+(To make things simple, all line loops should be oriented "aire a
+gauche", and all surface loops whould be oriented with exterior
+normals...)
 
 ********************************************************************
 
@@ -27,7 +40,8 @@ elements
 
 ********************************************************************
 
-use inria's mesh and solution file formats?
+read inria's mesh and solution file formats? ALMOST DONE with new BDS
+code.
 
 ********************************************************************
 
@@ -57,7 +71,8 @@ disable all replacements)
 
 ********************************************************************
 
-Add a "bitmap" object in the views, e.g. to add a logo
+Add a "bitmap" object in the views, e.g. to add a logo or a niver
+background. Oddly enough, people seem to want that kind of stuff.
 
 ********************************************************************
 
@@ -66,7 +81,7 @@ simple while(1) loop
 
 ********************************************************************
 
-add an option to enable lighting of wireframe plots?
+add an option to enable lighting of wireframe meshes & post-pro plots.
 
 ********************************************************************
 
@@ -76,15 +91,6 @@ strategy
 
 ********************************************************************
 
-add an interactive way to choose the orientation of surfaces in
-surface loops and lines in line loops
-
-(To make things simple, all line loops should be oriented "aire a
-gauche", and all surface loops whould be oriented with exterior
-normals...)
-
-********************************************************************
-
 template the view handling/drawing routines so that we can actually
 use post-pro files with float values (50% file savings can be nice
 for very large maps; would bring the format up to par with an 
@@ -130,7 +136,7 @@ other using 2nd order elements (in the same geometry)?
 ********************************************************************
 
 find a better way to display the time/timestep in the scale... (would
-be solved if we had dynamic labels)
+be solved if we had dynamic labels).
 
 ********************************************************************
 
@@ -177,7 +183,8 @@ Rewrite the View and ColorTable interface in C++
 ********************************************************************
 
 Include Tetgen (the same way we did it with Triangle--the license is
-the same).
+the same). PARTIALLY DONE by Nicolas. Needs testing + regenerate
+surface mesh.
 
 ********************************************************************
 
@@ -199,7 +206,6 @@ post-processing file format:
 - add an integer per simplex (region num)?
 - add a format similar to the msh format (node list + simplex list)?
 - add a structured format?
-
 ...or implement one of the "industry-standard" formats?
 
 ********************************************************************
diff --git a/doc/texinfo/opt_mesh.texi b/doc/texinfo/opt_mesh.texi
index 091996fbb2526282b07073332fed588b9dcf983d..8fcd7a0363a61fa0c20100172d6ee18e664a6cba 100644
--- a/doc/texinfo/opt_mesh.texi
+++ b/doc/texinfo/opt_mesh.texi
@@ -109,6 +109,11 @@ Show the construction of 2D anisotropic mesh in real time@*
 Default value: @code{0}@*
 Saved in: @code{General.OptionsFileName}
 
+@item Mesh.LabelType
+Type of element label (0=element number, 1=elementary entity number, 2=physical entity number, 3=partition number)@*
+Default value: @code{0}@*
+Saved in: @code{General.OptionsFileName}
+
 @item Mesh.Light
 Enable lighting for the mesh@*
 Default value: @code{0}@*
diff --git a/doc/texinfo/opt_plugin.texi b/doc/texinfo/opt_plugin.texi
index 592b9b9d58754947fe0c2e05c67fdf0a670bd59d..2fc5321e72af7f478575329de9704a71e0831e07 100644
--- a/doc/texinfo/opt_plugin.texi
+++ b/doc/texinfo/opt_plugin.texi
@@ -703,7 +703,6 @@ Default value: @code{-1}
 Default value: @code{-1}
 @end table
 
-
 @item Plugin(Transform)
 Plugin(Transform) transforms the homogeneous
 node coordinates (x,y,z,1) of the elements in