Contour.c

Go to the documentation of this file.
00001 /*------------------------------------------------------------------------
00002  *    Graphic library
00003  *    Copyright (C) 1998-2001 Enpc/Jean-Philippe Chancelier
00004  *    jpc@cermics.enpc.fr 
00005  --------------------------------------------------------------------------*/
00006 
00007 #include <string.h> /* in case of dbmalloc use */
00008 #include <stdio.h>
00009 #include <math.h>
00010 #include "math_graphics.h"
00011 #include "PloEch.h"
00012 #include "Xcall1.h"
00013 #include "sciprint.h"
00014 #include "MALLOC.h"
00015 #include "Format.h"
00016 #include "Contour.h"
00017 
00018 #include "GetProperty.h"
00019 
00020 typedef void (level_f) __PARAMS((integer ival, double Cont, double xncont,
00021                                double yncont));
00022 typedef void (*ptr_level_f) __PARAMS((integer ival, double Cont, double xncont,
00023                                double yncont));
00024 
00025 
00026 static void 
00027 contourI __PARAMS((ptr_level_f,double *, double *, double *,
00028                   double *, integer *, integer *, integer *));
00029 static void
00030 look __PARAMS((ptr_level_f, integer i, integer j, integer ib,
00031               integer jb, integer qq,double Cont, integer style));
00032 
00033 static integer ffnd __PARAMS((ptr_level_f,integer,integer,integer,integer,integer,
00034                              integer,integer,integer,integer,integer,
00035                              double,integer *));
00036 
00037 static int Gcont_size = 0;
00038 
00039 static void ContourTrace __PARAMS((double Cont, integer style));
00040 static level_f GContStore2;
00041 static void GContStore2Last __PARAMS((void));
00042 static double x_cont __PARAMS((integer i));
00043 static double y_cont __PARAMS((integer i));
00044 static double phi_cont __PARAMS((integer, integer)); 
00045 static double f_intercept  __PARAMS((double, double, double, double, double ));
00046 static integer not_same_sign  __PARAMS((double val1, double val2)); 
00047 static integer get_itg_cont  __PARAMS((integer i, integer j)); 
00048 static void inc_itg_cont  __PARAMS((integer i, integer j, integer val)); 
00049 static integer oddp  __PARAMS((integer i));
00050 
00051 /*-----------------------------------------------------------------------
00052  *  Level curves 
00053  *  The computer journal vol 15 nul 4 p 382 (1972)
00054  *  from the Lisp Macsyma source (M.I.T)
00055  * -------------------------------------------------------------------------*/
00056 
00057 #define HIDDENFRAMECOLOR 2L /* default color for hidden frame */
00058 
00059 /*---------------------------------------------------------------------------
00060  * General functions (could be changed in #define or
00061  *   inline functions to increase speed)
00062  *---------------------------------------------------------------------------*/
00063 
00064 static double *GX,*GY,*GZ;
00065 static integer Gn1,Gn2;
00066 
00067 static double * Gxcont = NULL ;
00068 static double * Gycont = NULL ;
00069 
00070 static integer * xcont = NULL ;
00071 static integer * ycont = NULL ;
00072 
00073 static void InitValues(double *x, double *y, double *z, integer n1, integer n2)
00074 {
00075   Gn1=n1;  Gn2=n2;  GX = x;  GY = y;  GZ = z;
00076 }
00077 
00078 /*--------return the  value of f for a pointeger on the grid-----*/
00079 
00080 static double phi_cont(integer i, integer j)
00081 {
00082   return(GZ[i+Gn1*j]);
00083 }
00084 
00085 /*---------return the coordinates between  [xi,xj] along one axis 
00086  *  for which the value of f is zCont */ 
00087 
00088 static double f_intercept(double zCont, double fi, double xi, double fj, double xj)
00089 {
00090   return( xi+ (zCont-fi)*(xj-xi)/ (fj-fi));
00091 }
00092 
00093 /* check for boundary points */
00094 
00095 static integer  bdyp(integer i, integer j)
00096 {
00097   return (  j == 0 || i == 0 || j == Gn2-1 || i == Gn1-1 );
00098 }
00099 
00100 /* store or get flag values */
00101 
00102 static  integer *itg_cont, *xbd_cont,*ybd_cont;
00103 
00104 static integer get_itg_cont(integer i, integer j)
00105 {
00106   return( itg_cont[i+Gn1*j]);
00107 }
00108 
00109 static void inc_itg_cont(integer i, integer j, integer val)
00110 {
00111   itg_cont[i+Gn1*j] += val;
00112 }
00113 
00114 static integer not_same_sign(double val1, double val2)
00115 {
00116   if ( ISNAN(val1) ==1 || ISNAN(val2) == 1) return(0);
00118   if ( val1 >= 0.0) 
00119     {
00120       if (val2 < 0.0) return(1) ; else return(0);}
00121   else 
00122     {
00123       if ( val2 >= 0.0) return(1) ; else return(0);}
00124 }
00125 
00126 static integer oddp(integer i) { return( i == 1 || i ==3 );}
00127 
00128 /*---------return the x-value of a grid point--------*/
00129 
00130 static double x_cont(integer i) { return GX[i] ;}
00131 
00132 /*---------return the y-value of a grid point --------*/
00133 
00134 static double y_cont(integer i) { return GY[i] ;}
00135 
00136 
00137 static char   ContNumFormat[100];
00138 
00139 /*--------------------------------------------------------------------
00140 *  the level curve is crossing the segment (i,j) (ib,jb)
00141 *  look store the level curve point and try to find the next segment to look at
00142 *  Cont: value of f along the contour 
00143 *  ncont: number of contour 
00144 *  c: indice of the contour Cont 
00145 *---------------------------------------------------------------------*/
00146 
00147 static void look(ptr_level_f func, integer i, integer j, integer ib, integer jb, integer qq, double Cont, integer style)
00148 {
00149   integer ip,jp,im,jm,zds,ent=0,flag=0,wflag;
00150   jp= j+1; ip= i+1; jm=j-1;im=i-1;
00151   /*  on regarde comment est le segment de depart */
00152   if  ( jb == jm)  flag = 1; 
00153   else  { 
00154     if ( ib == im ) flag = 2 ;
00155     else  {
00156       if ( jb == jp ) flag = 3 ;
00157       else  if ( ib == ip ) flag = 4;}}
00158   switch  (  flag)
00159   {
00160   case  1 :
00161     if  (get_itg_cont(i,jm) > 1) return;
00162     ent=1 ; /* le segment est vertical vers le bas */
00163     /* Storing intersection point */
00164     (*func)(0,Cont, x_cont(i), 
00165       f_intercept(Cont,phi_cont(i,jm),
00166       y_cont(jm),phi_cont(i,j),y_cont(j)));
00167     break;
00168   case 2 : 
00169     if  (get_itg_cont(im,j) == 1 || get_itg_cont(im,j)==3 ) return;
00170     ent=2 ; /* le segment est horizontal gauche */
00171     /* Storing intersection point */
00172     (*func)( 0,Cont,
00173       f_intercept(Cont,phi_cont(im,j),
00174       x_cont(im),phi_cont(i,j),x_cont(i)), y_cont(j));
00175     break ; 
00176   case 3 :
00177     if  (get_itg_cont(i,j) > 1 ) return;
00178     ent=3 ; /* le segment est vertical haut */
00179     /* Storing intersection point */
00180     (*func)(0,Cont,x_cont(i), f_intercept(Cont,phi_cont(i,j),
00181       y_cont(j),phi_cont(i,jp),y_cont(jp)));
00182     break ;
00183   case 4 :
00184     if  (get_itg_cont(i,j) == 1 || get_itg_cont(i,j)==3 ) return;
00185     ent=4 ; /* le segment est horizontal droit */
00186     /* Storing intersection point */
00187     (*func)(0,Cont,f_intercept(Cont,phi_cont(i,j),
00188       x_cont(i),phi_cont(ip,j),x_cont(ip)),
00189       y_cont(j));
00190     break;
00191   default :
00192     sciprint(" Error in case wrong value ");
00193     break;
00194   }
00195   wflag=1;
00196   while ( wflag) 
00197   { 
00198     jp= j+1; ip= i+1; jm=j-1;im=i-1;
00199     switch  ( ent) 
00200     {case 1 :
00201     inc_itg_cont(i,jm,2L);
00202     ent = ffnd(func,i,ip,ip,i,j,j,jm,jm,ent,qq,Cont,&zds);
00203     /* on calcule le nouveau point, ent donne la 
00204     direction du segment a explorer */
00205     switch ( ent)
00206     {
00207     case -1: wflag=0; break;
00208     case 1 : i=ip ; break ;
00209     case 2 : i=ip;j=jm; break ;
00210     }
00211     break ;
00212     case 2  :
00213       inc_itg_cont(im,j,1L);
00214       ent = ffnd(func,i,i,im,im,j,jm,jm,j,ent,qq,Cont,&zds);
00215       switch ( ent)
00216       { 
00217       case -1: wflag=0; break;
00218       case 2 : j = jm ;break ;
00219       case  3  : i=im;j=jm; break ;
00220       }
00221       break ;
00222     case 3 :
00223       inc_itg_cont(i,j,2L);
00224       ent = ffnd(func,i,im,im,i,j,j,jp,jp,ent,qq,Cont,&zds);
00225       switch ( ent)
00226       { 
00227       case -1: wflag=0; break;
00228       case 3 : i=im; break ;
00229       case 4 : i=im;j=jp; break ;
00230       }
00231       break ;
00232     case 4 :
00233       inc_itg_cont(i,j,1L);
00234       ent = ffnd(func,i,i,ip,ip,j,jp,jp,j,ent,qq,Cont,&zds);
00235       switch ( ent)
00236       {
00237       case -1: wflag=0; break;
00238       case 4 :j=jp;break ;
00239       case 1 :i=ip;j=jp;break ;
00240       }
00241       break ;
00242     }
00243 
00245     if ( zds == 1) 
00246     {
00247       switch ( ent) 
00248       {
00249       case 1 : inc_itg_cont(i,(j-1),2L); break ; 
00250       case 2 : inc_itg_cont(i-1,j,1L);  break ; 
00251       case 3 : inc_itg_cont(i,j,2L); break ; 
00252       case 4 : inc_itg_cont(i,j,1L); break ; 
00253       }
00255       wflag = 0 ;
00256     }
00258     if ( qq == 2) 
00259     {
00260       switch ( ent) 
00261       {
00262       case 1 : if  ( get_itg_cont (i,j-1)  > 1) wflag = 0 ; break ; 
00263       case 2 : if  ( oddp(get_itg_cont(i-1,j))) wflag = 0 ; break ; 
00264       case 3 : if  ( get_itg_cont(i,j) > 1)     wflag = 0 ; break ; 
00265       case 4 : if  ( oddp(get_itg_cont(i,j)))   wflag = 0 ; break ; 
00266       }
00267     }
00268   }
00269   if ( func == GContStore2 ) 
00270     GContStore2Last();
00271   else 
00272     ContourTrace(Cont,style);
00273 }
00274 
00275 
00276 /*-------------------------------------------------------
00277 *  The function f is given on a grid and we want the level curves 
00278 *  for the zCont[N[2]] values 
00279 *  x : of size N[0] gives the x-values of the grid 
00280 *  y : of size N[1] gives the y-values of the grid 
00281 *  z : of size N[0]*N[1]  gives the f-values on the grid 
00282 *  style: size ncont (=N[2]) or empty integer pointer 
00283 *  gives the dash style for contour i
00284 *-------------------------------------------------------*/
00285 
00286 static void contourI(ptr_level_f func, double *x, double *y, double *z, double *zCont, integer *N, integer *style, integer *err)
00287 {
00288   int check = 1;
00289   char *F;
00290   integer n1,n2,ncont,i,c,j,k,n5;
00291   integer stylec;
00292   n1=N[0];n2=N[1];ncont=N[2];
00293   F=getFPF();
00294   if ( F[0] == '\0') 
00295     ChoixFormatE1(ContNumFormat,zCont,N[2]);
00296   InitValues(x,y,z,n1,n2);
00297   n5 =  2*(n1)+2*(n2)-3;
00298   /* Allocation */
00299   Gcont_size = 0; 
00300   xbd_cont = MALLOC( n5 * sizeof(int) ) ;
00301   ybd_cont = MALLOC( n5 * sizeof(int) ) ;
00302   itg_cont = MALLOC( n1*n2 * sizeof(int) ) ;
00303   if ( (xbd_cont == NULL) && n5 != 0) check= 0;
00304   if ( (ybd_cont == NULL) && n5 != 0) check= 0;
00305   if ( (itg_cont == NULL) && n1*n2 != 0) check= 0;
00306   if ( check == 0) 
00307   {
00308     FREE( xbd_cont ) ;
00309     FREE( ybd_cont ) ;
00310     FREE( itg_cont ) ;
00311     sciprint("contourI_: Running out of memory\n");
00312     return;
00313   }
00314   /* just a parametrization of the boundary points */
00315   for ( i = 0 ; i <  n2 ; i++)
00316   {
00317     ybd_cont[i] = i ;
00318     xbd_cont[i] = 0 ;
00319   }
00320   for ( i = 1 ; i <  n1 ; i++)
00321   {
00322     ybd_cont[n2+i-1] = n2-1 ;
00323     xbd_cont[n2+i-1] = i  ;
00324   }
00325   for ( i = n2-2;  i >= 0  ; i--)
00326   {
00327     ybd_cont[2*n2 +n1-3-i] = i ;
00328     xbd_cont[2*n2 +n1-3-i] = n1-1  ;
00329   }
00330   for ( i = n1-2 ; i >= 0 ; i--)
00331   {
00332     ybd_cont[2*n2 +2*n1-4-i] = 0 ;
00333     xbd_cont[2*n2 +2*n1-4-i] = i  ;
00334   }
00335   for ( c= 0 ; c < ncont ; c++)
00336   {
00337     stylec = ( style != (integer *) 0) ? style[c] : c;
00339     for ( i = 0 ; i < n1; i++)
00340       for ( j =0 ; j < n2 ; j++)
00341         itg_cont[i+n1*j]=0 ;
00343     for ( k = 1 ; k < n5 ; k++)
00344     { integer ib,jb;
00345     i = xbd_cont[k] ; j = ybd_cont[k];
00346     ib = xbd_cont[k-1] ; jb= ybd_cont[k-1];
00347     if  (not_same_sign (phi_cont(i,j)-zCont[c] , 
00348       phi_cont(ib,jb)-zCont[c]))
00349       look(func,i,j,ib,jb,1L,zCont[c],stylec);
00350     }
00352     for ( i = 1 ; i < n1-1; i++)
00353       for ( j = 1 ; j < n2-1 ; j++)
00354         if  (not_same_sign ( phi_cont(i,j)-zCont[c] , 
00355           phi_cont(i, j-1)-zCont[c]))
00356           look(func,i,j,i,j-1,2L,zCont[c],stylec);
00357   }
00358   FREE( xbd_cont ) ;
00359   FREE( ybd_cont ) ;
00360   FREE( itg_cont ) ;
00361 
00362 }
00363 
00364 int C2F(contourif)(double *x, double *y, double *z, integer *n1, integer *n2, integer *flagnz, integer *nz, double *zz, integer *style)
00365 {
00366   integer err=0;
00367   static double *zconst;
00368   double zmin,zmax;
00369   integer N[3],i;
00370 
00371   zmin=(double) Mini(z,*n1*(*n2)); 
00372   zmax=(double) Maxi(z,*n1*(*n2));
00373 
00374   if (*flagnz==0)
00375     {
00376       if ( ( zconst = MALLOC( (*nz) * sizeof(double) ) ) == 0 ) 
00377         {
00378           sciprint("Running out of memory\r\n");
00379           return 0;
00380         }
00381       for ( i =0 ; i < *nz ; i++) 
00382         zconst[i]=zmin + (i+1)*(zmax-zmin)/(*nz+1);
00383       N[0]= *n1;N[1]= *n2;N[2]= *nz;
00384       contourI(GContStore2,x,y,z,zconst,N,style,&err);
00385       FREE(zconst) ;
00386       zconst = NULL ;
00387     }
00388   else
00389     {
00390       N[0]= *n1;N[1]= *n2;N[2]= *nz;
00391       contourI(GContStore2,x,y,z,zz,N,style,&err);
00392     }
00393 
00394   return(0);
00395 }
00396 
00397 
00398 
00399 
00400 
00401 /*-----------------------------------------------------------------------
00402  *   ffnd : cette fonction  recoit en entree quatre points 
00403  *       on sait que la courbe de niveau passe entre le point 1 et le quatre 
00404  *       on cherche a savoir ou elle resort, 
00405  *       et on fixe une nouvelle valeur de ent qui indiquera le segment 
00406  *       suivant a explorer 
00407  *-----------------------------------------------------------------------*/
00408 
00409 static integer ffnd (ptr_level_f func, integer i1, integer i2, integer i3, integer i4, integer jj1, integer jj2, integer jj3, integer jj4, integer ent, integer qq, double Cont, integer *zds)
00410 {
00411   double phi1,phi2,phi3,phi4,xav,yav,phiav;
00412   integer revflag,i;
00413   phi1=phi_cont(i1,jj1)-Cont;
00414   phi2=phi_cont(i2,jj2)-Cont;
00415   phi3=phi_cont(i3,jj3)-Cont;
00416   phi4=phi_cont(i4,jj4)-Cont;
00417   revflag = 0;
00418   *zds = 0;
00419   /* le point au centre du rectangle */
00420   xav = ( x_cont(i1)+ x_cont(i3))/2.0 ; 
00421   yav = ( y_cont(jj1)+ y_cont(jj3))/2.0 ; 
00422   phiav = ( phi1+phi2+phi3+phi4) / 4.0;
00423   if (ISNAN(phiav)==1) 
00424     {
00425       return -1;
00426     }
00427   if (  not_same_sign( phiav,phi4)) 
00428     {
00429       integer l1, k1; 
00430       double phi;
00431       revflag = 1 ; 
00432       l1= i4; k1= jj4;
00433       i4=i1; jj4 = jj1; i1= l1; jj1= k1;
00434       l1= i3; k1= jj3;
00435       i3=i2; jj3= jj2; i2=l1; jj2= k1;
00436       phi = phi1; phi1 = phi4; phi4= phi;
00437       phi = phi3; phi3 = phi2; phi2= phi;
00438     }
00439   /* on stocke un nouveau point  */
00440   (*func)(1,Cont,f_intercept(0.0,phi1,x_cont(i1),phiav,xav),
00441             f_intercept(0.0,phi1,y_cont(jj1),phiav,yav));
00442   /*
00443    * on parcourt les segments du rectangle pour voir sur quelle face
00444    * on sort 
00445    */
00446   for  ( i = 0 ;  ; i++)
00447     { integer l1,k1;
00448       double phi;
00449       if ( not_same_sign ( phi1,phi2))    break ; 
00450       if  ( phiav != 0.0 ) 
00451         {
00452           (*func)(1,Cont,f_intercept(0.0,phi2,x_cont(i2),phiav,xav),
00453                     f_intercept(0.0,phi2,y_cont(jj2),phiav,yav));
00454         } 
00456       l1=i1; k1= jj1;
00457       i1=i2;jj1=jj2;i2=i3;jj2=jj3;i3=i4;jj3=jj4;i4=l1;jj4=k1;
00458       phi=phi1; phi1=phi2;phi2=phi3;phi3=phi4;phi4=phi;
00459     }
00460   (*func)(1,Cont,f_intercept(0.0,phi1,x_cont(i1),phi2,x_cont(i2)),
00461             f_intercept(0.0,phi1,y_cont(jj1),phi2,y_cont(jj2)));
00462   if ( qq==1 && bdyp(i1,jj1) && bdyp(i2,jj2)) *zds = 1 ;
00463   if ( revflag == 1  &&  ! oddp (i) )  i = i+2;
00464   return ( 1 + (  ( i + ent + 2) % 4));
00465 }
00466 
00467 /*--------------------------------------------------------------
00468  * Storing and tracing level curves 
00469  *----------------------------------------------------------------*/
00470 
00471 static integer cont_size ;
00472 
00473 /* 
00474  * Explicit drawing of the current level curve with a dash style 
00475  * The curve level is also drawn as a string according to current 
00476  * floating point format 
00477  */
00478 
00479 static void ContourTrace(double Cont, integer style)
00480 { 
00481   char *F;
00482   integer verbose=0 ,Dnarg,Dvalue[10];
00483   integer close=0, flag=0, uc;
00484   double angle=0.0;
00485   char str[100];
00486 
00487   C2F(dr)("xget","use color",&verbose,&uc,&Dnarg,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00488   if (uc) {
00489     C2F(dr)("xget","color",&verbose,Dvalue,&Dnarg,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00490     C2F(dr)("xset","color",&style,PI0,PI0,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00491     C2F(dr)("xlines","void",&cont_size,xcont,ycont,&close,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00492     C2F(dr)("xset","color",Dvalue,PI0,PI0,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00493   }
00494   else {
00495     C2F(dr)("xget","line style",&verbose,Dvalue,&Dnarg,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00496     C2F(dr)("xset","line style",&style,PI0,PI0,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00497     C2F(dr)("xlines","void",&cont_size,xcont,ycont,&close,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00498     C2F(dr)("xset","line style",Dvalue,PI0,PI0,PI0,PI0,PI0,PD0,PD0,PD0,PD0,0L,0L);
00499   }
00500 
00501   F=getFPF();
00502   if ( F[0] == '\0') 
00503     sprintf(str,ContNumFormat,Cont);
00504   else 
00505     sprintf(str,F,Cont);
00506   C2F(dr)("xstring",str, &xcont[cont_size / 2],&ycont[cont_size /2],
00507           PI0,&flag,PI0,PI0, &angle,PD0,PD0,PD0,0L,0L);
00508 }
00509 
00510 /*--------------------------------------------------------------
00511  * Following code is used to store the current level curves as 
00512  * double in order to access to the stored data at Scilab level 
00513  *----------------------------------------------------------------*/
00514 
00515 static int last=-1;
00516 static int count=0; 
00517  
00520 int C2F(getconts)(double **x, double **y, integer *mm, integer *n)
00521 {
00522   *x = Gxcont;
00523   *y = Gycont;
00524   *mm= 1;
00525   *n= Gcont_size;
00526   return 0;
00527 }
00528 
00529 static void GContStore2(integer ival, double Cont, double xncont, double yncont)
00530 {
00531   int n;
00532   if ( ival == 0) 
00533     {
00534       /* Here : ival == 0 means stop the current level curve and 
00535        * store data at the end but do reset Gcont_size to zero 
00536        */
00537       n= Gcont_size + 2;
00538       if ( Gxcont == NULL )
00539       {
00540         Gxcont = MALLOC( n * sizeof(double) ) ;
00541         Gycont = MALLOC( n * sizeof(double) ) ;
00542       }
00543       else
00544       {
00545         Gxcont = REALLOC( Gxcont, n * sizeof(double) ) ;
00546         Gycont = REALLOC( Gycont, n * sizeof(double) ) ;
00547       }
00548       if ( (Gxcont == NULL) && n != 0) return ; 
00549       if ( (Gycont == NULL) && n != 0) return ;
00550       Gxcont[Gcont_size] = Cont;
00551       if ( last != -1 && last < n ) Gycont[last]= count;
00552       last = Gcont_size;
00553       Gcont_size++;
00554       count = 0;
00555     }
00556   else
00557   {
00558     n = Gcont_size + 1 ;
00559     if ( Gxcont == NULL )
00560     {
00561       Gxcont = MALLOC( n * sizeof(double) ) ;
00562       Gycont = MALLOC( n * sizeof(double) ) ;
00563     }
00564     else
00565     {
00566       Gxcont = REALLOC( Gxcont, n * sizeof(double) ) ;
00567       Gycont = REALLOC( Gycont, n * sizeof(double) ) ;
00568     }
00569     if ( (Gxcont == NULL) && n != 0) return ; 
00570     if ( (Gycont == NULL) && n != 0) return ;
00571   }
00572   Gxcont[Gcont_size]=xncont;
00573   Gycont[Gcont_size++]=yncont;
00574   count++;
00575 }
00576 
00577 static void GContStore2Last(void)
00578 {
00579   if ( last != -1 ) Gycont[last]= count;
00580 }
00581 
00582 
00583 
00584 
00585 
00586 
00587 
00588 
00589 
00590 
00591 

Generated on Sun Mar 4 15:03:51 2007 for Scilab [trunk] by  doxygen 1.5.1