comet and comet3d, Matlab like functions 68/3868/5
Serge Steer [Tue, 19 Apr 2011 15:28:17 +0000 (17:28 +0200)]
Change-Id: I6162b1158c41d23273f4f831a86317e53e2ad698

SEP/INDEX
SEP/SEP_057_comet.odt [new file with mode: 0644]
scilab/CHANGES_5.3.X
scilab/modules/graphics/help/en_US/2d_plot/comet.xml [new file with mode: 0644]
scilab/modules/graphics/help/en_US/2d_plot/paramfplot2d.xml
scilab/modules/graphics/help/en_US/3d_plot/comet3d.xml [new file with mode: 0644]
scilab/modules/graphics/macros/comet.sci [new file with mode: 0644]
scilab/modules/graphics/macros/comet3d.sci [new file with mode: 0644]

index 7962abf..a519943 100644 (file)
--- a/SEP/INDEX
+++ b/SEP/INDEX
@@ -52,5 +52,6 @@ SEP #050: Xcos Help Folders
 SEP #051: Linear Programming
 SEP #054: Quality argument added to xs2jpg
 SEP #056: Add symetry option to nyquist function
+SEP #057: comet/comet3d
 SEP #059: nyquistfrequencybounds
 SEP #060: CACSD frequency tools
diff --git a/SEP/SEP_057_comet.odt b/SEP/SEP_057_comet.odt
new file mode 100644 (file)
index 0000000..d18b7b2
Binary files /dev/null and b/SEP/SEP_057_comet.odt differ
index 128525c..3e5d224 100644 (file)
@@ -174,6 +174,7 @@ Graphics:
   the exported JPG.
   See bug 5573 and SEP 54.
 
+* New functions 'comet' and 'comet3d' have been added.
 
 Localization:
 =============
diff --git a/scilab/modules/graphics/help/en_US/2d_plot/comet.xml b/scilab/modules/graphics/help/en_US/2d_plot/comet.xml
new file mode 100644 (file)
index 0000000..75b4335
--- /dev/null
@@ -0,0 +1,180 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ * Add some comments about XML file
+-->
+<refentry xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:svg="http://www.w3.org/2000/svg"  xmlns:mml="http://www.w3.org/1998/Math/MathML" xmlns:db="http://docbook.org/ns/docbook" version="5.0-subset Scilab" xml:lang="en_US" xml:id="comet">
+  <info>
+    <pubdate>$LastChangedDate: 11-03-2011 $</pubdate>
+  </info>
+  <refnamediv>
+    <refname>comet</refname>
+    <refpurpose>2D comet animated plot. </refpurpose>
+  </refnamediv>
+  <refsynopsisdiv>
+    <title>Calling Sequence</title>
+    <synopsis>comet(y)</synopsis>
+    <synopsis>comet(x,y)</synopsis>
+    <synopsis>comet(x,fun)</synopsis>
+    <synopsis>comet(x,y,p)</synopsis>
+    <synopsis>comet(x,fun,p)</synopsis>
+    <synopsis>comet(...,"colors",c)</synopsis>
+  </refsynopsisdiv>
+  <refsection>
+    <title>Parameters</title>
+    <variablelist>
+      <varlistentry>
+        <term>x</term>
+        <listitem>
+          <para>
+            a real vector or matrix. If omitted, it is assumed to be the vector
+            <literal>1:ny</literal> where <literal>ny</literal> is the
+            number of curve points (see below).
+          </para>
+        </listitem>
+      </varlistentry>
+      <varlistentry>
+        <term>y</term>
+        <listitem>
+          <para>
+            a real vector or matrix of length.
+           </para>
+        </listitem>
+      </varlistentry>
+     <varlistentry>
+        <term>p</term>
+        <listitem>
+          <para>
+            a real scalar in the interval<literal>[0 1[</literal>. Default value is 0.1.
+           </para>
+        </listitem>
+      </varlistentry>
+     <varlistentry>
+        <term>fun</term>
+        <listitem>
+          <para>
+            a scilab function with calling sequence <literal>y=fun(x)</literal>.  <literal>fun</literal> can also be a polynomial or a rational fraction.
+           </para>
+        </listitem>
+      </varlistentry>
+    <varlistentry>
+        <term>c</term>
+        <listitem>
+          <para>
+            a vector of  <literal>ny</literal> color index.
+           </para>
+        </listitem>
+      </varlistentry>
+
+    </variablelist>
+  </refsection>
+  <refsection>
+    <title>Description</title>
+    <para>
+      If <literal>(x,y)</literal> are two vectors with the same number
+      of elements, this function draws a 2D comet animated plot
+      showing the progession of the curve
+      <literal>(x(1:k),y(1:k))</literal> for <literal>k</literal>
+      varying from <literal>1</literal> to
+      <literal>size(x,'*')</literal>.  
+    </para>
+    <para>
+      The plot is made of three parts:
+         <variablelist>
+           <varlistentry>
+             <term>a head</term> 
+             mark that shows the current <literal>(x(i),y(i))</literal> position.
+             <listitem>
+               <para>
+               </para>
+             </listitem>
+           </varlistentry>
+           <varlistentry>
+             <term>a body</term> that shows the trailing curve that
+             follows the head: the
+             <literal>(x(i-k:i),y(i-k:i)</literal>) part of the curve.
+             <listitem>
+               <para>
+               </para>
+             </listitem>
+           </varlistentry>
+          <varlistentry>
+             <term>a tail</term> 
+             that shows the  <literal>(x(1:i-k),y(1:i-k))</literal>  part of the curve.
+             <listitem>
+               <para>
+               </para>
+             </listitem>
+           </varlistentry>
+         </variablelist>
+       <para>
+         <literal>comet(x,fun,...)</literal>  is equivalent to <literal>comet(x,feval(x,fun),...)</literal> 
+         </para>
+         <para>
+         <literal>comet(...,p)</literal> can be used to set the
+         relative length of the body. <literal>k</literal> is defined
+         as <literal>k = round(p*ny)</literal>.
+         </para>
+        <para>
+          if <literal>y</literal> is a matrix then animated curves are drawn for each pair  <literal>(x,y(:,l))</literal>.
+          in this case <literal>ny</literal> is the number of rows of <literal>y</literal>.
+        </para>
+        <para>
+          if <literal>x</literal> and <literal>y</literal> are
+          matrices with identical sizes then animated curves are drawn
+          for each pair <literal>(x(:,l),y(:,l))</literal>.  in this
+          case <literal>ny</literal> is the number of rows of
+          <literal>x</literal>and  <literal>y</literal>.
+        </para>
+
+         <para>
+           <literal>comet(...,"colors",c)</literal> can be used to set the colors of each curves.
+         </para>
+
+    </para>
+  </refsection>
+  <refsection>
+    <title>Examples</title>
+    <programlisting role="example"><![CDATA[
+t = linspace(0,10*%pi,500);
+clf();set(gca(),"isoview","on"); //set isoview axes
+comet(t.*sin(t),t.*cos(t))
+    ]]></programlisting>
+    <programlisting role="example"><![CDATA[
+t = linspace(0,10*%pi,500)';
+clf();comet(t.*sin(t),[t.*sin(2*t) t.*sin(3*t)])
+    ]]></programlisting>
+    <programlisting role="example"><![CDATA[
+function y=traj(x),y=1.5*sin(x^2),endfunction
+clf();comet(linspace(0,5,500),traj)
+    ]]></programlisting>
+    <programlisting role="example"><![CDATA[
+clf();comet(linspace(-2,4,500),(%s-3)/(%s^3+2*%s^2+1))
+    ]]></programlisting>
+
+  </refsection>
+  <refsection>
+    <title>See Also</title>
+    <simplelist type="inline">
+      <member>
+        <link linkend="comet3d">comet3d</link>
+      </member>
+      <member>
+        <link linkend="paramfplot2d">paramfplot2d</link>
+      </member>
+
+    </simplelist>
+  </refsection>
+  <refsection>
+    <title>Authors</title>
+    <simplelist type="vert">
+      <member>Serge Steer</member>
+    </simplelist>
+  </refsection>
+  <refsection>
+    <title>History</title>
+    <simplelist type="vert">
+      <member>First version April 2011, for Scilab-5.3.2</member>
+    </simplelist>
+  </refsection>
+
+</refentry>
index 572a26f..56b8142 100644 (file)
   </info>
   <refnamediv>
     <refname>paramfplot2d</refname>
-    <refpurpose> animated 2D plot, curve defined by a function</refpurpose>
+    <refpurpose> animated plot of a 2D parametrized curve.</refpurpose>
   </refnamediv>
   <refsynopsisdiv>
     <title>Calling Sequence</title>
     <synopsis>paramfplot2d(f,x,theta)
 paramfplot2d(f,x,theta,flag)
-paramfplot2d(f,x,theta,flagrect)</synopsis>
+paramfplot2d(f,x,theta,flag,rect)</synopsis>
   </refsynopsisdiv>
   <refsection>
     <title>Arguments</title>
@@ -48,7 +48,7 @@ paramfplot2d(f,x,theta,flagrect)</synopsis>
       <varlistentry>
         <term>flag</term>
         <listitem>
-          <para>string <literal>'no'</literal> or <literal>'yes'</literal>: If "yes" screen is cleared  between two consecutive plots.</para>
+          <para>string <literal>'no'</literal> or <literal>'yes'</literal>: If "yes" screen is not cleared  between two consecutive plots.</para>
         </listitem>
       </varlistentry>
       <varlistentry>
@@ -62,23 +62,49 @@ paramfplot2d(f,x,theta,flagrect)</synopsis>
   <refsection>
     <title>Description</title>
     <para>
-    Animated plot of the function x--&gt;f(x,t) for t=theta(1),theta(2),etc.
-    f can be a either Scilab function or a dynamically linked routine since
-    y=f(x,t) is evaluated as y=feval(x(:),t,f). See feval.
-    f: mapping x,t -&gt; f(x,t) = <literal>R^N</literal>  valued function for x= vector of <literal>R^N</literal>
-    and t=real number. x is a N-vector of x-values and for each t in theta, f(x,t)=N-vector of y-values.</para>
+    Animated plot of the function <literal>x</literal>,
+    <literal>t</literal>--&gt;<literal>f(x,t)</literal> for
+    <literal>t=theta(1),theta(2),etc</literal>.  <literal>f</literal>
+    can be a either Scilab function or a dynamically linked routine
+    since <literal>y=f(x,t)</literal> is evaluated as
+    <literal>y=feval(x(:),t,f)</literal>. See <link
+    linkend="feval">feval</link>.
+  </para>
+  <para>
+    <literal>f</literal> is a mapping <literal>x</literal>,
+    <literal>t</literal>--&gt; <literal>f(x,t) = R^N</literal> valued
+    function for <literal>x</literal> a vector of
+    <literal>R^N</literal> and <literal>t</literal> a real number.
+  </para>
   </refsection>
   <refsection>
     <title>Examples</title>
     <programlisting role="example"><![CDATA[ 
 deff('y=f(x,t)','y=t*sin(x)')
 x=linspace(0,2*%pi,50);theta=0:0.05:1;
-paramfplot2d(f,x,theta);
+clf;paramfplot2d(f,x,theta);
+ ]]></programlisting>
+    <programlisting role="example"><![CDATA[ 
+function V=twosoliton(x,t)
+  a1=6;s1=2;v1=a1^2;
+  a2=4;s2=40;v2=a2^2;
+  
+  f1=exp(-a1*(x-s1-v1*t));
+  f2=exp(-a2*(x-s2-v2*t));
+  r=((a2-1)/(a2+a1))^2;
+  V=2*(v1*f1+v2*f2+2*(a2-a1)^2*f1.*f2+r*(v2*(f1^2).*f2+v1*f1.*(f2^2)))./((1+f1+f2+r*f1.*f2)^2);
+endfunction
+x=linspace(1,100,3000);
+clf;paramfplot2d(twosoliton,x,0:0.05:3);
  ]]></programlisting>
   </refsection>
   <refsection role="see also">
 <title>See Also</title>
     <simplelist type="inline">
+     <member>
+        <link linkend="comet">comet</link>
+      </member>
+
       <member>
         <link linkend="plot2d">plot2d</link>
       </member>
diff --git a/scilab/modules/graphics/help/en_US/3d_plot/comet3d.xml b/scilab/modules/graphics/help/en_US/3d_plot/comet3d.xml
new file mode 100644 (file)
index 0000000..b51de8e
--- /dev/null
@@ -0,0 +1,178 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ * Add some comments about XML file
+-->
+<refentry xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:svg="http://www.w3.org/2000/svg"  xmlns:mml="http://www.w3.org/1998/Math/MathML" xmlns:db="http://docbook.org/ns/docbook" version="5.0-subset Scilab" xml:lang="en_US" xml:id="comet3d">
+  <info>
+    <pubdate>$LastChangedDate: 11-03-2011 $</pubdate>
+  </info>
+  <refnamediv>
+    <refname>comet3d</refname>
+    <refpurpose>3D comet animated plot. </refpurpose>
+  </refnamediv>
+  <refsynopsisdiv>
+    <title>Calling Sequence</title>
+    <synopsis>comet3d(z)</synopsis>
+    <synopsis>comet3d(x,y,z)</synopsis>
+    <synopsis>comet3d(x,y,fun)</synopsis>
+    <synopsis>comet3d(x,y,z,p)</synopsis>
+    <synopsis>comet3d(x,y,fun,p)</synopsis>
+    <synopsis>comet3d(...,"colors",c)</synopsis>
+  </refsynopsisdiv>
+  <refsection>
+    <title>Parameters</title>
+    <variablelist>
+      <varlistentry>
+        <term>x</term>
+        <listitem>
+          <para>
+            a real vector or matrix. If omitted, it is assumed to be the vector
+            <literal>1:nz</literal> where <literal>nz</literal> is the
+            number of curve points given by the <literal>z</literal>
+            parameter.
+          </para>
+        </listitem>
+      </varlistentry>
+     <varlistentry>
+        <term>y</term>
+        <listitem>
+          <para>
+            a real vector or matrix. If omitted, it is assumed to be the vector
+            <literal>1:nz</literal> where <literal>nz</literal> is the
+            number of curve points given by the <literal>z</literal>
+            parameter.
+          </para>
+        </listitem>
+      </varlistentry>
+
+      <varlistentry>
+        <term>z</term>
+        <listitem>
+          <para>
+            a real vector of length <literal>nz</literal> or a matrix with  <literal>nz</literal> rows.
+           </para>
+        </listitem>
+      </varlistentry>
+     <varlistentry>
+        <term>p</term>
+        <listitem>
+          <para>
+            a real scalar in the interval<literal>[0 1[</literal>. Default value is 0.1.
+           </para>
+        </listitem>
+      </varlistentry>
+     <varlistentry>
+        <term>fun</term>
+        <listitem>
+          <para>
+            a scilab function with calling sequence <literal>z=fun(x,y)</literal>.
+           </para>
+        </listitem>
+      </varlistentry>
+      <varlistentry>
+        <term>c</term>
+        <listitem>
+          <para>
+            a vector of  <literal>ny</literal> color index.
+           </para>
+        </listitem>
+      </varlistentry>
+    </variablelist>
+  </refsection>
+  <refsection>
+    <title>Description</title>
+    <para>
+       If <literal>(x,y,z)</literal> are three vectors with the same number of elements, this function draws a 3D comet
+      animated plot. The plot is made of three parts:
+         <variablelist>
+           <varlistentry>
+             <term>a head</term> 
+             mark that shows the current <literal>(x(i),y(i),z(i))</literal> position.
+             <listitem>
+               <para>
+               </para>
+             </listitem>
+           </varlistentry>
+           <varlistentry>
+             <term>a body</term> that shows the trailing curve that
+             follows the head: the
+             <literal>(x(i-k:i),y(i-k:i),z(i-k:i))</literal>) part of the curve.
+             <listitem>
+               <para>
+               </para>
+             </listitem>
+           </varlistentry>
+          <varlistentry>
+             <term>a tail</term> 
+             that shows the  <literal>(x(1:i-k),y(1:i-k),z(1:i-k))</literal>  part of the curve.
+             <listitem>
+               <para>
+               </para>
+             </listitem>
+           </varlistentry>
+         </variablelist>
+         <para>
+           if <literal>z</literal> is a matrix and
+           <literal>(x,y)</literal> are vectors then animated curves
+           are drawn for each triple <literal>(x,y,z(:,l))</literal>.
+           in this case <literal>nz</literal> is the number of rows of
+           <literal>z</literal>.
+         </para>
+         <para>
+           if <literal>x,y,z</literal> are matrices with the same dimensions then animated curves
+           are drawn for each triple <literal>(x(:,l),y(:,l),z(:,l))</literal>.
+         </para>
+
+         <para>
+
+         <literal>comet3d(x,y,fun,...)</literal> computes the
+         <literal>z</literal> vector as
+         <literal>z(i)=fun(x(i),y(i))</literal>
+         </para>
+         <para>
+         <literal>comet3d(...,p)</literal> can be used to set the
+         relative length of the body. <literal>k</literal> is defined
+         as <literal>k = round(p*nz)</literal>.
+         </para>
+
+    </para>
+  </refsection>
+  <refsection>
+    <title>Examples</title>
+    <programlisting role="example"><![CDATA[
+t = linspace(-%pi,%pi,500);
+clf();comet3d(sin(5*t),sin(t),t^2)
+    ]]></programlisting>
+    <programlisting role="example"><![CDATA[
+t = linspace(-%pi,%pi,500)';
+clf();comet3d(sin(5*t),sin(t),[t^2,ones(t)])
+    ]]></programlisting>
+    <programlisting role="example"><![CDATA[
+function z=traj(x,y),z=1.5*sin(x^2)*cos(y),endfunction
+clf();comet3d(cos(t),sin(t),traj)
+    ]]></programlisting>
+  </refsection>
+  <refsection>
+    <title>See Also</title>
+    <simplelist type="inline">
+      <member>
+        <link linkend="comet" >comet</link>
+      </member>
+    </simplelist>
+  </refsection>
+
+  <refsection>
+    <title>Authors</title>
+    <simplelist type="vert">
+      <member>Serge Steer</member>
+    </simplelist>
+  </refsection>
+
+ <refsection>
+   <title>History</title>
+   <simplelist type="vert">
+     <member>First version April 2011, for Scilab-5.3.2</member>
+   </simplelist>
+ </refsection>
+
+</refentry>
diff --git a/scilab/modules/graphics/macros/comet.sci b/scilab/modules/graphics/macros/comet.sci
new file mode 100644 (file)
index 0000000..bca390f
--- /dev/null
@@ -0,0 +1,173 @@
+// Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
+// Copyright (C) 2011 - INRIA - Serge Steer <serge.steer@inria.fr>
+//
+// This file must be used under the terms of the CeCILL.
+// This source file is licensed as described in the file COPYING, which
+// you should have received as part of this distribution.  The terms
+// are also available at;
+// http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
+
+function comet(varargin)
+//Comet-like trajectory.
+//   comet(y) displays an animated comet plot of the vector y.
+//   comet(x,y) displays an animated comet plot of vector y vs. x.
+//   comet(x,y,p) uses a comet of length p*size(y,'*').  Default is p = 0.1.
+
+//   Example:
+//       t = linspace(0,10*%pi,500);
+//       clf();comet(t.*sin(t),t.*cos(t))
+//
+//       function y=traj(x),y=1.5*sin(x^2),endfunction
+//       clf();comet(linspace(0,5,500),traj)
+//
+//       clf();comet(linspace(-2,4,500),(%s-3)/(%s^3+2*%s^2+1))
+  
+  nv=size(varargin)
+  if varargin(nv-1)=='colors' then
+    c=round(varargin(nv))
+    if type(c)<>1|~isreal(c) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet",nv))
+  end
+    varargin=list(varargin(1:$-2))
+  else
+    c=[]
+  end
+  select size(varargin)
+  case 1 then //y
+    y=varargin(1)
+    if or(size(y)==1) then
+      x=1:size(y,'*')
+    else
+      x=1:size(y,1)
+    end
+    p=0.1
+  case 2 then  //x,y
+    [x,y]=varargin(1:2)
+    p=0.1
+  case 3 then  //x,y,p
+    [x,y,p]=varargin(1:3)
+  else
+    error(msprintf(_("%s: Wrong number of input arguments: %d to %d expected.\n"),"comet",1,3))
+  end
+  if type(x)<>1|~isreal(x) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet",1))
+  end
+  if or(type(y)==[11 13]) then //a function
+    prot=funcprot();funcprot(0)
+    y=feval(x,y)
+    funcprot(prot)
+  elseif type(y)==2 then //a polynomial
+    y=horner(y,x)
+  elseif typeof(y)=='rational' then //a rational fraction
+    y=horner(y,x)
+  end
+  if type(y)<>1|~isreal(y) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet",2))
+  end
+  if type(p)<>1|~isreal(p)|size(p,'*')>1 then
+    error(msprintf(_("%s: Wrong type for argument %d: Real scalar expected.\n"),"comet",3))
+  end
+  if p<0|p>=1 then
+    error(msprintf(_("%s: Wrong value for input argument #%d: Must be in the interval %s.\n"),"comet",3,"[0 1["))
+  end
+  
+  if or(size(x)==1) then
+    x=x(:)
+    n=size(x,1)
+    if or(size(y)==1) then
+      if n<>size(y,'*') then
+        error(msprintf(_("%s: Incompatible input arguments #%d and #%d: Same sizes expected.\n"),"comet",1,2))
+      end
+      y=y(:)
+      m=1
+    else
+      m=size(y,2)
+      if size(y,1)<>n then 
+        error(msprintf(_("%s: Incompatible input arguments #%d and #%d: Same number of rows expected.\n"),"comet",1,2))
+      end
+      x=x*ones(1,m)
+    end
+  else
+    n=size(x,1)
+    m=size(x,2)
+    if or(size(y)<>size(x)) then
+      error(msprintf(_("%s: Incompatible input arguments #%d and #%d: Same sizes expected.\n"),"comet",1,2))
+    end
+  end
+  fig=gcf();
+  if c==[] then
+    c=1:m
+  else
+    if size(c,'*')<>m then 
+      error(msprintf(_("%s: Wrong size for argument %d: %d expected.\n"),"comet",nv,m))
+    end
+    if min(c)<1|max(c)>size(fig.color_map,1) then
+       error(msprintf(_( "%s: Wrong value for input argument #%d: Must be in the set {%s}.\n"),"comet",nv,"1,...,"+string(size(fig.color_map,1))))
+    end
+  end
+  axes=gca();
+
+  if axes.children==[] then
+    axes.data_bounds=[min(x) min(y);max(x) max(y)];
+    axes.axes_visible="on";
+  else
+    axes.data_bounds=[min(axes.data_bounds(1,:), [min(x) min(y)]);
+                      max(axes.data_bounds(2,:), [max(x) max(y)])];
+  end
+  //create the head, body and tail polylines
+  drawlater()
+  tail=[];body=[];head=[];
+  for l=1:m
+    xpoly([],[]);tail(l)=gce();
+    tail(l).foreground=c(l);
+    xpoly([],[]);body(l)=gce();
+    body(l).foreground=c(l);
+    body(l).thickness=2;
+    xpoly([],[],'marks');head(l)=gce();
+    head(l).mark_size_unit='point';
+    head(l).mark_size=6;
+    head(l).mark_style=9;
+    head(l).mark_foreground=c(l);
+  end
+  show_window();
+
+
+function anim()
+//animation loop
+  k = round(p*n);
+  step=ceil(n/200); //used to speed up the drawing
+  
+  for i=1:n
+    for l=1:m
+      head(l).data=[x(i),y(i,l)];
+      if i<=k then
+        body(l).data= [body(l).data;[x(i,l),y(i,l)]];
+      else
+        body(l).data= [body(l).data(2:$,:);[x(i,l),y(i,l)]];
+        tail(l).data=[ tail(l).data;[x(i-k+1,l),y(i-k+1,l)]];
+      end
+    end
+    if modulo(i,step)==0 then 
+      fig.immediate_drawing = "on"
+      fig.immediate_drawing = "off"
+    end
+  end
+  fig.immediate_drawing = "on"
+  fig.immediate_drawing = "off"
+  for i=1:k
+    for l=1:m
+      body(l).data= body(l).data(2:$,:);
+      tail(l).data=[tail(l).data;[x(n-k+i,l),y(n-k+i,l)]];
+    end
+    if modulo(i,step)==0 then 
+      //draw(axes),
+      fig.immediate_drawing = "on"
+      fig.immediate_drawing = "off"
+    end
+  end
+  fig.immediate_drawing = "on"
+  delete(body)
+endfunction
+//not to generate an error message if the window is closed
+exec(anim,-1,'errcatch')
+endfunction
diff --git a/scilab/modules/graphics/macros/comet3d.sci b/scilab/modules/graphics/macros/comet3d.sci
new file mode 100644 (file)
index 0000000..aaadc3c
--- /dev/null
@@ -0,0 +1,198 @@
+// Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
+// Copyright (C) 2011 - INRIA - Serge Steer <serge.steer@inria.fr>
+//
+// This file must be used under the terms of the CeCILL.
+// This source file is licensed as described in the file COPYING, which
+// you should have received as part of this distribution.  The terms
+// are also available at;
+// http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
+
+function comet3d(varargin)
+//Comet-like trajectory.
+//   comet(y) displays an animated comet plot of the vector y.
+//   comet(x,y) displays an animated comet plot of vector y vs. x.
+//   comet(x,y,p) uses a comet of length p*size(y,'*').  Default is p = 0.1.
+
+//   Example:
+//       t = linspace(-%pi,%pi,500);
+//       clf();comet3d(sin(5*t),sin(t),t^2)
+//
+//       function z=traj(x,y),z=1.5*sin(x^2)*cos(y),endfunction
+//       clf();comet3d(cos(t),sin(t),traj)
+//
+    nv=size(varargin)
+  if varargin(nv-1)=='colors' then
+    c=round(varargin(nv))
+    if type(c)<>1|~isreal(c) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet3d",nv))
+  end
+    varargin=list(varargin(1:$-2))
+  else
+    c=[]
+  end
+  select size(varargin)
+
+  case 1 then //z
+    z=varargin(1)
+    if or(size(z)==1) then
+      x=1:size(z,'*')
+    else
+      x=1:size(z,1)
+    end
+    y=x
+    p=0.1
+  case 3 then  //x,y,z
+    [x,y,z]=varargin(1:3)
+    p=0.1
+  case 4 then  //x,y,z,p
+    [x,y,z,p]=varargin(1:4)
+  else
+    error(msprintf(_("%s: Wrong number of input arguments: %d or %d to %d expected.\n"),"comet3d",1,3,4))
+  end
+    
+  if type(x)<>1|~isreal(x) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet3d",1))
+  end
+  if type(y)<>1|~isreal(x) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet3d",1))
+  end
+  
+  if (type(z)<>1|~isreal(z))&and(type(z)<>[11 13]) then
+    error(msprintf(_("%s: Wrong type for argument %d: Real vector expected.\n"),"comet3d",3))
+  end
+
+  if or(type(z)==[11 13]) then
+    x=x(:);y=y(:)
+    n=size(x,'*')
+    m=1
+    if n<>size(y,'*') then
+      error(msprintf(_("%s: Incompatible input arguments #%d and #%d: Same sizes expected.\n"),"comet3d",1,2))
+    end
+    prot=funcprot();funcprot(0)
+    zz=z;
+    z=zeros(n,1);
+    for i=1:n
+      z(i)=zz(x(i),y(i))
+    end
+    funcprot(prot)
+  else
+    if or(size(z)==1) then
+      m=1
+      z=z(:)
+      n=size(z,'*')
+    else
+      [n,m]=size(z)
+    end
+    if or(size(x)==1) then
+      x=x(:)
+      if size(x,'*')<>n then
+        error(msprintf(_("%s: Wrong size for argument %d: %d expected.\n"),"comet3d",1,n))
+      end
+      x=x*ones(1,m)
+    else
+      if or(size(x)<>size(z)) then
+        error(msprintf(_("%s: Incompatible input arguments #%d and #%d: Same sizes expected.\n"),"comet3d",1,3))
+      end
+    end
+    if or(size(y)==1) then
+      y=y(:)
+      if size(y,'*')<>n then
+        error(msprintf(_("%s: Wrong size for argument %d: %d expected.\n"),"comet3d",2,n))
+      end
+      y=y*ones(1,m)
+    else
+      if or(size(y)<>size(z)) then
+        error(msprintf(_("%s: Incompatible input arguments #%d and #%d: Same sizes expected.\n"),"comet3d",2,3))
+      end
+
+    end
+  end
+
+  if type(p)<>1|~isreal(p)|size(p,'*')>1 then
+    error(msprintf(_("%s: Wrong type for argument %d: Real scalar expected.\n"),"comet3d",3))
+  end
+  if p<0|p>=1 then
+     error(msprintf(_("%s: Wrong value for input argument #%d: Must be in the interval %s.\n"),"comet3d",3,"[0 1["))
+  end
+  fig=gcf();
+  if c==[] then
+    c=1:m
+  else
+    if size(c,'*')<>m then 
+      error(msprintf(_("%s: Wrong size for argument %d: %d expected.\n"),"comet",nv,m))
+    end
+    if min(c)<1|max(c)>size(fig.color_map,1) then
+       error(msprintf(_( "%s: Wrong value for input argument #%d: Must be in the set {%s}.\n"),"comet",nv,"1,...,"+string(size(fig.color_map,1))))
+    end
+  end
+  axes=gca();
+  axes.view='3d'
+  
+
+  if axes.children==[] then
+    axes.data_bounds=[min(x) min(y) min(z);max(x) max(y) max(z)];
+    axes.axes_visible="on";
+    axes.box="on";
+  else
+    axes.data_bounds=[min(axes.data_bounds(1,:), [min(x) min(y) min(z)]);
+                      max(axes.data_bounds(2,:), [max(x) max(y) max(z)])];
+  end
+  //create the head, body and tail polylines
+  drawlater()
+  for l=1:m
+    xpoly([],[]);tail(l)=gce();
+    tail(l).foreground=c(l);
+
+    xpoly([],[]);body(l)=gce();
+    body(l).foreground=c(l); body(l).thickness=2;
+    xpoly([],[],'marks');head(l)=gce();
+    head(l).mark_size_unit='point';
+    head(l).mark_size=6;
+    head(l).mark_style=9;
+    head(l).mark_foreground=c(l);
+  end
+  show_window();
+
+  function anim()
+  //animation loop
+    k = round(p*n);
+    step=ceil(n/200); //used to speed up the drawing
+
+    for i=1:n
+      for l=1:m
+        head(l).data=[x(i,l),y(i,l),z(i,l)];
+        if i<=k then
+          body(l).data= [body(l).data;[x(i,l),y(i,l),z(i,l)]];
+        else
+          body(l).data= [body(l).data(2:$,:);[x(i,l),y(i,l),z(i,l)]];
+          tail(l).data=[ tail(l).data;[x(i-k,l),y(i-k,l),z(i-k,l)]];
+        end
+      end
+      if modulo(i,step)==0 then 
+        fig.immediate_drawing = "on"
+        fig.immediate_drawing = "off"
+      end
+    end
+    drawnow(),drawlater()
+   
+    for i=n:n+k
+      for l=1:m
+        body(l).data= body(l).data(2:$,:);
+        tail(l).data=[ tail(l).data;[x(i-k,l),y(i-k,l),z(i-k,l)]];
+      end
+      if modulo(i,step)==0 then 
+        //draw(axes),
+        fig.immediate_drawing = "on"
+        fig.immediate_drawing = "off"
+      end
+    end
+    delete(body)
+    drawnow()
+  endfunction
+  //not to generate an error message if the window is closed
+  //exec(anim,-1,'errcatch')
+  exec(anim,-1)
+endfunction