octave-maintainers
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Stem update, rough guess.


From: John W. Eaton
Subject: Re: Stem update, rough guess.
Date: Mon, 9 Apr 2007 19:15:06 -0400

On  9-Apr-2007, Daniel J Sebald wrote:

| John W. Eaton wrote:
| 
| > | How does one get the axis line now?  The
| > | 
| > |    set (gca, "?axisline?", "on");
| > | 
| > | sort of thing?  E.g.,
| > | 
| > |    stem([-10:10]);
| > 
| > I think stem should just draw another black line.
| 
| Like what it was doing?

Yes.

| I guess, but what that did was look to the limits of the plot, x_min
| and x_max, and draw a line at the origin between them.  But what
| then if someone changes the limits using set() to make them slightly
| bigger?  Then that line will not run from one end of the plot to the
| other.

I'm willing to live with that bug for now.

|  Using the gnuplot command
| 
| | +  fputs (plot_stream, "set xzeroaxis linetype -1 linewidth 
0.5;\nreplot;\n");
| 
| will automatically adjust the length of the axis line.

Yes, but if we do that, then the properties don't look much like what
Matlab is doing for stem, so this will be a point of incompatibility
that someone will no doubt complain about.

The Matlab docs say that stem returns a "stemseries" object.  The data
appears to be transformed so that a single x-y pair represents all the
stem lines and NaNs are used to indicate where the data skips.  The
data for the lines are stored as children of the stemseries object.
The baseline and basevalue properties of the stemseries object are
used to handle the baseline, with basevalue normally set to 0.  The
baseline property is a handle pointing to the line object for the
baseline.  If the axes are resized after drawning a stem plot,
baseline is magically modified.  I guess this happens when the
stemseries object is drawn.

There seems to be some other magic going on here, as in addition to
the baseline handle, there is another line object representing the
baseline that is a child of the axis object that the stem plot is
drawn in.  Deleting the stemseries baseline handle also appears to
invalidate this handle.

Also, a stemseries object appears to be just an hggroup object.  I
don't know how one tells that it is actually a "stemseries".

Or maybe I'm misunderstanding what is happening.  Someone who really
wants to understand this minutiae will have to investigate and explain
it to us properly if my interpretation is not right.

In any case, Octave doesn't have hggroup objects yet, so we can't do
exactly what Matlab does, but it seems it would be better to get a
little closer than we are now by at least having only one line object
for each x-y pair (which come from the columns of X and Y that are
passed to stem).  Then we can also have a line object that handles the
baseline.  That it doesn't stretch with changes in the axes seems like
a minor bug to me compared to having stem return N line objects.

I just checked in the following change to make __go_draw_axes__ do the
right thing with NaNs in the data, so at least stem could be modified
to return a smaller number of handles to lines with breaks (one per
column of data in the X/Y matrices that it is given) instead of a
separate handle for each line segment.

jwe


scripts/ChangeLog:

2007-04-09  John W. Eaton  <address@hidden>

        * plot/__go_draw_axes__.m (__gnuplot_write_data__): New function.
        (__go_draw_axes__): Use it to write data to plot stream.


Index: scripts/plot/__go_draw_axes__.m
===================================================================
RCS file: /cvs/octave/scripts/plot/__go_draw_axes__.m,v
retrieving revision 1.13
diff -u -u -r1.13 __go_draw_axes__.m
--- scripts/plot/__go_draw_axes__.m     27 Mar 2007 14:29:46 -0000      1.13
+++ scripts/plot/__go_draw_axes__.m     9 Apr 2007 22:54:46 -0000
@@ -663,23 +663,7 @@
        if (is_image_data(i))
          fwrite (plot_stream, data{i}, "float32");
        else
-         if (nd == 2)
-           fprintf (plot_stream,
-                    strcat (repmat ("%g ", 1, rows (data{i})), "\n"),
-                    data{i});
-         else
-           if (parametric(i))
-             fprintf (plot_stream, "%g %g %g\n", data{i});
-           else
-             tmp = data{i};
-             nc = columns (tmp);
-             for j = 1:3:nc
-               fprintf (plot_stream, "%g %g %g\n", tmp(:,j:j+2)');
-               fputs (plot_stream, "\n");
-             endfor
-           endif
-         endif
-         fputs (plot_stream, "e\n");
+         __gnuplot_write_data__ (plot_stream, data{i}, nd, parametric(i));
        endif
       endfor
     else
@@ -896,3 +880,44 @@
   fputs (plot_stream, ";\n");
 
 endfunction
+
+function __gnuplot_write_data__ (plot_stream, data, nd, parametric)
+  
+  ## DATA is already transposed.
+
+  ## FIXME -- this may need to be converted to C++ for speed.
+
+  if (nd == 2)
+    nan_elts = find (sum (isnan (data)));
+    fmt = strcat (repmat ("%g ", 1, rows (data)), "\n");
+    if (isempty (nan_elts))
+      fprintf (plot_stream, fmt, data);
+    else
+      n = columns (data);
+      have_nans = true;
+      num_nan_elts = numel (nan_elts);
+      k = 1;
+      for i = 1:n
+       if (have_nans && i == nan_elts(k))
+         fputs (plot_stream, "\n");
+         have_nans = ++k <= num_nan_elts;
+       else
+         fprintf (plot_stream, fmt, data(:,i));
+       endif
+      endfor
+    endif
+  else
+    ## FIXME -- handle NaNs here too?
+    if (parametric)
+      fprintf (plot_stream, "%g %g %g\n", data);
+    else
+      nc = columns (data);
+      for j = 1:3:nc
+       fprintf (plot_stream, "%g %g %g\n", data(:,j:j+2)');
+       fputs (plot_stream, "\n");
+      endfor
+    endif
+  endif
+  fputs (plot_stream, "e\n");
+
+endfunction

reply via email to

[Prev in Thread] Current Thread [Next in Thread]