diff --git a/Plugin/PrincipalStresses.cpp b/Plugin/Eigenvectors.cpp
similarity index 54%
rename from Plugin/PrincipalStresses.cpp
rename to Plugin/Eigenvectors.cpp
index cd12f14238be6fd3aca574b45659e003f7f2ae07..81aba76b352bf46bdaef4a67e2cf7ddebe42e1f3 100644
--- a/Plugin/PrincipalStresses.cpp
+++ b/Plugin/Eigenvectors.cpp
@@ -1,4 +1,4 @@
-// $Id: PrincipalStresses.cpp,v 1.6 2004-12-08 18:41:54 geuzaine Exp $
+// $Id: Eigenvectors.cpp,v 1.1 2004-12-10 03:35:29 geuzaine Exp $
 //
 // Copyright (C) 1997-2004 C. Geuzaine, J.-F. Remacle
 //
@@ -20,7 +20,7 @@
 // Please report all bugs and problems to <gmsh@geuz.org>.
 
 #include "Plugin.h"
-#include "PrincipalStresses.h"
+#include "Eigenvectors.h"
 #include "List.h"
 #include "Views.h"
 #include "Context.h"
@@ -29,55 +29,61 @@
 
 extern Context_T CTX;
 
-StringXNumber PrincipalStressesOptions_Number[] = {
+StringXNumber EigenvectorsOptions_Number[] = {
+  {GMSH_FULLRC, "ScaleByEigenvalues", NULL, 1.},
   {GMSH_FULLRC, "iView", NULL, -1.}
 };
 
 extern "C"
 {
-  GMSH_Plugin *GMSH_RegisterPrincipalStressesPlugin()
+  GMSH_Plugin *GMSH_RegisterEigenvectorsPlugin()
   {
-    return new GMSH_PrincipalStressesPlugin();
+    return new GMSH_EigenvectorsPlugin();
   }
 }
 
-GMSH_PrincipalStressesPlugin::GMSH_PrincipalStressesPlugin()
+GMSH_EigenvectorsPlugin::GMSH_EigenvectorsPlugin()
 {
   ;
 }
 
-void GMSH_PrincipalStressesPlugin::getName(char *name) const
+void GMSH_EigenvectorsPlugin::getName(char *name) const
 {
-  strcpy(name, "Principal Stresses");
+  strcpy(name, "Eigenvectors");
 }
 
-void GMSH_PrincipalStressesPlugin::getInfos(char *author, char *copyright, char *help_text) const
+void GMSH_EigenvectorsPlugin::getInfos(char *author, char *copyright, char *help_text) const
 {
   strcpy(author, "C. Geuzaine (geuz@geuz.org)");
   strcpy(copyright, "DGR (www.multiphysics.com)");
   strcpy(help_text,
-         "Plugin(PrincipalStresses) computes the min,\n"
-	 "mid and max principal stresses of the tensor\n"
-	 "view `iView'. If `iView' < 0, the plugin is run on\n"
-	 "the current view.\n"
+         "Plugin(Eigenvectors) computes the three\n"
+	 "(right) eigenvectors of each tensor in the\n"
+	 "view `iView' and sorts them according to\n"
+	 "the value of the associated eigenvalues.\n"
+	 "If `ScaleByEigenvalues' is set, each\n"
+	 "eigenvector is scaled by its associated\n"
+	 "eigenvalue. The plugin gives an error if\n"
+	 "the eigenvalues are complex. If `iView'\n"
+	 "< 0, the plugin is on the current view.\n"
 	 "\n"
-	 "Plugin(PrincipalStresses) creates three new\n"
+	 "Plugin(Eigenvectors) creates three new\n"
 	 "vector views.\n");
 }
 
-int GMSH_PrincipalStressesPlugin::getNbOptions() const
+int GMSH_EigenvectorsPlugin::getNbOptions() const
 {
-  return sizeof(PrincipalStressesOptions_Number) / sizeof(StringXNumber);
+  return sizeof(EigenvectorsOptions_Number) / sizeof(StringXNumber);
 }
 
-StringXNumber *GMSH_PrincipalStressesPlugin::getOption(int iopt)
+StringXNumber *GMSH_EigenvectorsPlugin::getOption(int iopt)
 {
-  return &PrincipalStressesOptions_Number[iopt];
+  return &EigenvectorsOptions_Number[iopt];
 }
 
-void GMSH_PrincipalStressesPlugin::catchErrorMessage(char *errorMessage) const
+void GMSH_EigenvectorsPlugin::catchErrorMessage(char *errorMessage) const
 {
-  strcpy(errorMessage, "PrincipalStresses failed...");
+  strcpy(errorMessage, "Eigenvectors failed...");
 }
 
 static int nonzero(double v[3])
@@ -87,10 +93,11 @@ static int nonzero(double v[3])
   return 0;
 }
 
-static void principal_stresses(List_T *inList, int inNb, int nbNod, int nbTime,
-			       List_T *minList, int *minNb, 
-			       List_T *midList, int *midNb, 
-			       List_T *maxList, int *maxNb)
+static void eigenvectors(List_T *inList, int inNb, 
+			 int nbNod, int nbTime, int scale,
+			 List_T *minList, int *minNb, 
+			 List_T *midList, int *midNb, 
+			 List_T *maxList, int *maxNb)
 {
   if(!inNb) return;
 
@@ -120,10 +127,8 @@ static void principal_stresses(List_T *inList, int inNb, int nbNod, int nbTime,
 	EigSolve(3, A, wr, wi, B, itmp, dtmp);
 	EigSort(3, wr, wi, B);
 	nbcomplex += nonzero(wi); 
-	//printf("djf=%g %g %g\n", wr[0], wr[1], wr[2]);
-	//printf("vec1=%g %g %g\n", B[0][0], B[1][0], B[2][0]);
-	//printf("vec1=%g %g %g\n", B[0][1], B[1][1], B[2][1]);
-	//printf("vec1=%g %g %g\n", B[0][2], B[1][2], B[2][2]);
+	if(!scale)
+	  wr[0] = wr[1] = wr[2] = 1.;
 	for(int l = 0; l < 3; l++){
 	  double res;
 	  // wrong if there are complex eigenvals (B contains both
@@ -150,9 +155,10 @@ static void principal_stresses(List_T *inList, int inNb, int nbNod, int nbTime,
     Msg(GERROR, "%d tensors have complex eigenvalues/eigenvectors", nbcomplex);
 }
 
-Post_View *GMSH_PrincipalStressesPlugin::execute(Post_View * v)
+Post_View *GMSH_EigenvectorsPlugin::execute(Post_View * v)
 {
-  int iView = (int)PrincipalStressesOptions_Number[0].def;
+  int scale = (int)EigenvectorsOptions_Number[0].def;
+  int iView = (int)EigenvectorsOptions_Number[1].def;
 
   if(iView < 0)
     iView = v ? v->Index : 0;
@@ -167,22 +173,22 @@ Post_View *GMSH_PrincipalStressesPlugin::execute(Post_View * v)
   Post_View *mid = BeginView(1);
   Post_View *max = BeginView(1);
 
-  principal_stresses(v1->TP, v1->NbTP, 1, v1->NbTimeStep,
- 		     min->VP, &min->NbVP, mid->VP, &mid->NbVP, max->VP, &max->NbVP);
-  principal_stresses(v1->TL, v1->NbTL, 2, v1->NbTimeStep,
-		     min->VL, &min->NbVL, mid->VL, &mid->NbVL, max->VL, &max->NbVL);
-  principal_stresses(v1->TT, v1->NbTT, 3, v1->NbTimeStep,
-		     min->VT, &min->NbVT, mid->VT, &mid->NbVT, max->VT, &max->NbVT);
-  principal_stresses(v1->TQ, v1->NbTQ, 4, v1->NbTimeStep,
-		     min->VQ, &min->NbVQ, mid->VQ, &mid->NbVQ, max->VQ, &max->NbVQ);
-  principal_stresses(v1->TS, v1->NbTS, 4, v1->NbTimeStep,
-		     min->VS, &min->NbVS, mid->VS, &mid->NbVS, max->VS, &max->NbVS);
-  principal_stresses(v1->TH, v1->NbTH, 8, v1->NbTimeStep,
-		     min->VH, &min->NbVH, mid->VH, &mid->NbVH, max->VH, &max->NbVH);
-  principal_stresses(v1->TI, v1->NbTI, 6, v1->NbTimeStep,
-		     min->VI, &min->NbVI, mid->VI, &mid->NbVI, max->VI, &max->NbVI);
-  principal_stresses(v1->TY, v1->NbTY, 5, v1->NbTimeStep,
-		     min->VY, &min->NbVY, mid->VY, &mid->NbVY, max->VY, &max->NbVY);
+  eigenvectors(v1->TP, v1->NbTP, 1, v1->NbTimeStep, scale,
+	       min->VP, &min->NbVP, mid->VP, &mid->NbVP, max->VP, &max->NbVP);
+  eigenvectors(v1->TL, v1->NbTL, 2, v1->NbTimeStep, scale,
+	       min->VL, &min->NbVL, mid->VL, &mid->NbVL, max->VL, &max->NbVL);
+  eigenvectors(v1->TT, v1->NbTT, 3, v1->NbTimeStep, scale,
+	       min->VT, &min->NbVT, mid->VT, &mid->NbVT, max->VT, &max->NbVT);
+  eigenvectors(v1->TQ, v1->NbTQ, 4, v1->NbTimeStep, scale,
+	       min->VQ, &min->NbVQ, mid->VQ, &mid->NbVQ, max->VQ, &max->NbVQ);
+  eigenvectors(v1->TS, v1->NbTS, 4, v1->NbTimeStep, scale,
+	       min->VS, &min->NbVS, mid->VS, &mid->NbVS, max->VS, &max->NbVS);
+  eigenvectors(v1->TH, v1->NbTH, 8, v1->NbTimeStep, scale,
+	       min->VH, &min->NbVH, mid->VH, &mid->NbVH, max->VH, &max->NbVH);
+  eigenvectors(v1->TI, v1->NbTI, 6, v1->NbTimeStep, scale,
+	       min->VI, &min->NbVI, mid->VI, &mid->NbVI, max->VI, &max->NbVI);
+  eigenvectors(v1->TY, v1->NbTY, 5, v1->NbTimeStep, scale,
+	       min->VY, &min->NbVY, mid->VY, &mid->NbVY, max->VY, &max->NbVY);
 
   // copy time data
   for(int i = 0; i < List_Nbr(v1->Time); i++){
@@ -192,14 +198,14 @@ Post_View *GMSH_PrincipalStressesPlugin::execute(Post_View * v)
   }
   // finalize
   char name[1024], filename[1024];
-  sprintf(name, "%s_MinPrincipalStress", v1->Name);
-  sprintf(filename, "%s_MinPrincipalStress.pos", v1->Name);
+  sprintf(name, "%s_MinEigenvectors", v1->Name);
+  sprintf(filename, "%s_MinEigenvectors.pos", v1->Name);
   EndView(min, 1, filename, name);
-  sprintf(name, "%s_MidPrincipalStress", v1->Name);
-  sprintf(filename, "%s_MidPrincipalStress.pos", v1->Name);
+  sprintf(name, "%s_MidEigenvector", v1->Name);
+  sprintf(filename, "%s_MidEigenvectors.pos", v1->Name);
   EndView(mid, 1, filename, name);
-  sprintf(name, "%s_MaxPrincipalStress", v1->Name);
-  sprintf(filename, "%s_MaxPrincipalStress.pos", v1->Name);
+  sprintf(name, "%s_MaxEigenvector", v1->Name);
+  sprintf(filename, "%s_MaxEigenvectors.pos", v1->Name);
   EndView(max, 1, filename, name);
 
   return NULL;
diff --git a/Plugin/PrincipalStresses.h b/Plugin/Eigenvectors.h
similarity index 84%
rename from Plugin/PrincipalStresses.h
rename to Plugin/Eigenvectors.h
index 814cdf5d5c3623e6a3deb4002594f114dc6596aa..ff5ed73a687fcf561617e4210451e1a1b6f0cad4 100644
--- a/Plugin/PrincipalStresses.h
+++ b/Plugin/Eigenvectors.h
@@ -1,5 +1,5 @@
-#ifndef _PRINCIPAL_STRESSES_H_
-#define _PRINCIPAL_STRESSES_H_
+#ifndef _EIGEN_VECTORS_H_
+#define _EIGEN_VECTORS_H_
 
 // Copyright (C) 1997-2004 C. Geuzaine, J.-F. Remacle
 //
@@ -25,13 +25,13 @@
 
 extern "C"
 {
-  GMSH_Plugin *GMSH_RegisterPrincipalStressesPlugin();
+  GMSH_Plugin *GMSH_RegisterEigenvectorsPlugin();
 }
 
-class GMSH_PrincipalStressesPlugin : public GMSH_Post_Plugin
+class GMSH_EigenvectorsPlugin : public GMSH_Post_Plugin
 {
  public:
-  GMSH_PrincipalStressesPlugin();
+  GMSH_EigenvectorsPlugin();
   void getName(char *name) const;
   void getInfos(char *author, char *copyright, char *helpText) const;
   void catchErrorMessage(char *errorMessage) const;
diff --git a/Plugin/Makefile b/Plugin/Makefile
index 464be49dfdd8a06936e6297c6d017affcbf8c8aa..06ff391c000ef62330103b499480c04495e5ba45 100644
--- a/Plugin/Makefile
+++ b/Plugin/Makefile
@@ -1,4 +1,4 @@
-# $Id: Makefile,v 1.63 2004-12-08 03:10:06 geuzaine Exp $
+# $Id: Makefile,v 1.64 2004-12-10 03:35:29 geuzaine Exp $
 #
 # Copyright (C) 1997-2004 C. Geuzaine, J.-F. Remacle
 #
@@ -31,7 +31,7 @@ SRC = Plugin.cpp\
           CutPlane.cpp CutSphere.cpp CutMap.cpp \
         Smooth.cpp CutParametric.cpp\
         Gradient.cpp Lambda2.cpp\
-        PrincipalStresses.cpp\
+        Eigenvectors.cpp\
 	Octree.cpp OctreeInternals.cpp OctreePost.cpp\
           StreamLines.cpp CutGrid.cpp\
         Transform.cpp\
@@ -80,7 +80,7 @@ Plugin.o: Plugin.cpp Plugin.h ../Common/Options.h ../Common/Message.h \
   ../Geo/Geo.h ../Mesh/Mesh.h ../Mesh/Vertex.h ../Mesh/Element.h \
   ../Mesh/Simplex.h ../Mesh/Face.h ../Mesh/Edge.h ../Geo/ExtrudeParams.h \
   ../Mesh/STL.h ../Mesh/Metric.h ../Mesh/Matrix.h ../Common/GmshUI.h \
-  PrincipalStresses.h Evaluate.h ../Common/Context.h
+  Eigenvectors.h Evaluate.h ../Common/Context.h
 Levelset.o: Levelset.cpp Levelset.h Plugin.h ../Common/Options.h \
   ../Common/Message.h ../Common/Views.h ../Common/ColorTable.h \
   ../DataStr/List.h ../Common/VertexArray.h ../Common/SmoothNormals.h \
@@ -129,10 +129,10 @@ Lambda2.o: Lambda2.cpp Plugin.h ../Common/Options.h ../Common/Message.h \
   ../Common/VertexArray.h ../Common/SmoothNormals.h \
   ../Common/GmshMatrix.h ../Common/AdaptiveViews.h Lambda2.h \
   ../Numeric/Numeric.h ../Common/Context.h
-PrincipalStresses.o: PrincipalStresses.cpp Plugin.h ../Common/Options.h \
+Eigenvectors.o: Eigenvectors.cpp Plugin.h ../Common/Options.h \
   ../Common/Message.h ../Common/Views.h ../Common/ColorTable.h \
   ../DataStr/List.h ../Common/VertexArray.h ../Common/SmoothNormals.h \
-  ../Common/GmshMatrix.h ../Common/AdaptiveViews.h PrincipalStresses.h \
+  ../Common/GmshMatrix.h ../Common/AdaptiveViews.h Eigenvectors.h \
   ../Common/Context.h ../DataStr/Malloc.h ../Numeric/Numeric.h
 Octree.o: Octree.cpp Octree.h OctreeInternals.h
 OctreeInternals.o: OctreeInternals.cpp ../Common/Message.h \
diff --git a/Plugin/Plugin.cpp b/Plugin/Plugin.cpp
index cf1748cbd6906aee2f10fd395171123e5febe220..de86bfed819f335c6e643eeb17828f2284308624 100644
--- a/Plugin/Plugin.cpp
+++ b/Plugin/Plugin.cpp
@@ -1,4 +1,4 @@
-// $Id: Plugin.cpp,v 1.65 2004-12-08 03:10:06 geuzaine Exp $
+// $Id: Plugin.cpp,v 1.66 2004-12-10 03:35:29 geuzaine Exp $
 //
 // Copyright (C) 1997-2004 C. Geuzaine, J.-F. Remacle
 //
@@ -49,7 +49,7 @@
 #include "SphericalRaise.h"
 #include "DisplacementRaise.h"
 #include "StructuralSolver.h"
-#include "PrincipalStresses.h"
+#include "Eigenvectors.h"
 #include "Evaluate.h"
 #include "Context.h"
 
@@ -196,7 +196,7 @@ void GMSH_PluginManager::registerDefaultPlugins()
     allPlugins.insert(std::pair < char *, GMSH_Plugin * >
 		      ("Integrate", GMSH_RegisterIntegratePlugin()));
     allPlugins.insert(std::pair < char *, GMSH_Plugin * >
-		      ("PrincipalStresses", GMSH_RegisterPrincipalStressesPlugin()));
+		      ("Eigenvectors", GMSH_RegisterEigenvectorsPlugin()));
 #if defined(HAVE_TRIANGLE)
     allPlugins.insert(std::pair < char *, GMSH_Plugin * >
 		      ("Triangulate", GMSH_RegisterTriangulatePlugin()));
diff --git a/doc/VERSIONS b/doc/VERSIONS
index 4ec5bc9e14fe63c484fdf7d2e36d8034f259b946..0aa4184c6e2c86f6b6566f3ab350b79ba5a77361 100644
--- a/doc/VERSIONS
+++ b/doc/VERSIONS
@@ -1,4 +1,4 @@
-$Id: VERSIONS,v 1.273 2004-12-08 20:18:27 geuzaine Exp $
+$Id: VERSIONS,v 1.274 2004-12-10 03:35:29 geuzaine Exp $
 
 New in 1.57: generalized displacement maps to display arbitrary view
 types; the arrows representing a vector field can now also be colored
@@ -7,7 +7,7 @@ high order visualization mode; new options (Solver.SocketCommand,
 Solver.NameCommand, View.ArrowSizeProportional, View.Normals,
 View.Tangents and General.ClipFactor); fixed display of undesired
 solver plugin popups; enhanced interactive plugin behaviour; new
-plugins (HarmonicToTime, Integrate, PrincipalStresses); tetrahedral
+plugins (HarmonicToTime, Integrate, Eigenvectors); tetrahedral
 mesh file reading speedup (50% faster on large meshes); large memory
 footprint reduction (up to 50%) for the visualization of
 triangular/tetrahadral meshes; the solver interface now supports
diff --git a/doc/texinfo/opt_plugin.texi b/doc/texinfo/opt_plugin.texi
index 6e61e99599b18503bcd2806af11585ba26ba2122..d98bab6edc63f5a03acfb67ba47d10427db842e5 100644
--- a/doc/texinfo/opt_plugin.texi
+++ b/doc/texinfo/opt_plugin.texi
@@ -191,6 +191,28 @@ Default value: @code{-1}
 Default value: @code{-1}
 @end table
 
+@item Plugin(Eigenvectors)
+Plugin(Eigenvectors) computes the three
+(right) eigenvectors of each tensor in the
+view `iView' and sorts them according to
+the value of the associated eigenvalues.
+If `ScaleByEigenvalues' is set, each
+eigenvector is scaled by its associated
+eigenvalue. The plugin gives an error if
+the eigenvalues are complex. If `iView'
+< 0, the plugin is on the current view.
+
+Plugin(Eigenvectors) creates three new
+vector views.
+
+Numeric options:
+@table @code
+@item ScaleByEigenvalues
+Default value: @code{1}
+@item iView
+Default value: @code{-1}
+@end table
+
 @item Plugin(Evaluate)
 Plugin(Evaluate) sets the `Component'-th
 component of the `TimeStep'-th time step
@@ -297,21 +319,6 @@ Default value: @code{-1}
 Default value: @code{0}
 @end table
 
-@item Plugin(PrincipalStresses)
-Plugin(PrincipalStresses) computes the min,
-mid and max principal stresses of the tensor
-view `iView'. If `iView' < 0, the plugin is run on
-the current view.
-
-Plugin(PrincipalStresses) creates three new
-vector views.
-
-Numeric options:
-@table @code
-@item iView
-Default value: @code{-1}
-@end table
-
 @item Plugin(Skin)
 Plugin(Skin) extracts the skin (the boundary) of
 the view `iView'. If `iView' < 0, the plugin is run