Logo Search packages:      
Sourcecode: plplot version File versions  Download package

plbox.c

/* $Id: plbox.c,v 1.38 2004/06/14 21:51:57 rlaboiss Exp $

      Routines for drawing axes & box around the current viewport.

   Copyright (C) 2004  Joao Cardoso
   Copyright (C) 2004  Alan W. Irwin

   This file is part of PLplot.

   PLplot is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Library Public License as published
   by the Free Software Foundation; either version 2 of the License, or
   (at your option) any later version.

   PLplot is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU Library General Public License for more details.

   You should have received a copy of the GNU Library General Public License
   along with PLplot; if not, write to the Free Software
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/

#include "plplotP.h"

static PLFLT xlog[8] =
{
    0.301030, 0.477121, 0.602060, 0.698970,
    0.778151, 0.845098, 0.903090, 0.954243
};

/* Static function prototypes */

static void
plxybx(const char *opt, const char *label, PLFLT wx1, PLFLT wy1,
       PLFLT wx2, PLFLT wy2, PLFLT vmin, PLFLT vmax,
       PLFLT tick, PLINT nsub, PLINT nolast, PLINT *digits);

static void
plzbx(const char *opt, const char *label, PLINT right, PLFLT dx, PLFLT dy,
      PLFLT wx, PLFLT wy1, PLFLT wy2, PLFLT vmin, PLFLT vmax,
      PLFLT tick, PLINT nsub, PLINT *digits);

static void
plxytx(PLFLT wx1, PLFLT wy1, PLFLT wx2, PLFLT wy2,
       PLFLT disp, PLFLT pos, PLFLT just, const char *text);

static void
plztx(const char *opt, PLFLT dx, PLFLT dy, PLFLT wx, PLFLT wy1,
      PLFLT wy2, PLFLT disp, PLFLT pos, PLFLT just, const char *text);

static void
plform(PLFLT value, PLINT scale, PLINT prec, char *result, PLINT ll, PLINT lf);

static void
grid_box(const char *xopt, PLFLT xtick1, PLINT nxsub1,
       const char *yopt, PLFLT ytick1, PLINT nysub1);

static void
label_box(const char *xopt, PLFLT xtick1, const char *yopt, PLFLT ytick1);

/*--------------------------------------------------------------------------*\
 * void plbox()
 *
 * This draws a box around the current viewport, complete with axes, ticks,
 * numeric labels, and grids, according to input specification.  Just a
 * front-end to plaxes(), which allows arbitrary placement of coordinate
 * axes when plotted (here the origin is at 0,0).  See the documentation for
 * plaxes() for more info.
\*--------------------------------------------------------------------------*/

void
c_plbox(const char *xopt, PLFLT xtick, PLINT nxsub,
      const char *yopt, PLFLT ytick, PLINT nysub)
{
    c_plaxes(0.0, 0.0, xopt, xtick, nxsub, yopt, ytick, nysub);
}

/*--------------------------------------------------------------------------*\
 * void plaxes()
 *
 * This draws a box around the current viewport, complete with axes,
 * ticks, numeric labels, and grids, according to input specification.
 *
 * x0 and y0 specify the origin of the axes.
 *
 * xopt and yopt are character strings which define the box as follows:
 *
 * a: Draw axis (X is horizontal line Y=0, Y is vertical line X=0)
 * b: Draw bottom (X) or left (Y) edge of frame
 * c: Draw top (X) or right (Y) edge of frame
 * f: Always use fixed point numeric labels
 * g: Draws a grid at the major tick interval
 * h: Draws a grid at the minor tick interval
 * i: Inverts tick marks
 * l: Logarithmic axes, major ticks at decades, minor ticks at units
 * n: Write numeric label at conventional location
 * m: Write numeric label at unconventional location
 * t: Draw major tick marks
 * s: Draw minor tick marks
 * v: (for Y only) Label vertically
 *
 * xtick, ytick are the major tick intervals required, zero for
 * automatic selection
 *
 * nxsub, nysub are the number of subtick intervals in a major tick
 * interval
\*--------------------------------------------------------------------------*/

void
c_plaxes(PLFLT x0, PLFLT y0,
       const char *xopt, PLFLT xtick, PLINT nxsub,
       const char *yopt, PLFLT ytick, PLINT nysub)
{
    PLINT lax, lbx, lcx, lgx, lix, llx, lsx, ltx;
    PLINT lay, lby, lcy, lgy, liy, lly, lsy, lty;
    PLINT xmajor, xminor, ymajor, yminor;
    PLINT i, i1x, i2x, i3x, i4x, i1y, i2y, i3y, i4y;
    PLINT nxsub1, nysub1;
    PLINT lxmin, lxmax, lymin, lymax;
    PLINT pxmin, pxmax, pymin, pymax;
    PLINT vppxmi, vppxma, vppymi, vppyma;
    PLFLT xtick1, ytick1, vpwxmi, vpwxma, vpwymi, vpwyma;
    PLFLT vpwxmin, vpwxmax, vpwymin, vpwymax;
    PLFLT xp0, yp0, tn, tp, temp;

    if (plsc->level < 3) {
      plabort("plbox: Please set up window first");
      return;
    }

/* Open the clip limits to the subpage limits */

    plP_gclp(&lxmin, &lxmax, &lymin, &lymax);
    plP_gphy(&pxmin, &pxmax, &pymin, &pymax);
    plP_sclp(pxmin, pxmax, pymin, pymax);

    vppxmi = plsc->vppxmi;
    vppxma = plsc->vppxma;
    vppymi = plsc->vppymi;
    vppyma = plsc->vppyma;

/* Convert world coordinates to physical */

    xp0 = plP_wcpcx(x0);
    yp0 = plP_wcpcy(y0);

/* Set plot options from input */

    lax = plP_stsearch(xopt, 'a');
    lbx = plP_stsearch(xopt, 'b');
    lcx = plP_stsearch(xopt, 'c');
    lgx = plP_stsearch(xopt, 'g');
    lix = plP_stsearch(xopt, 'i');
    llx = plP_stsearch(xopt, 'l');
    lsx = plP_stsearch(xopt, 's');
    ltx = plP_stsearch(xopt, 't');

    lay = plP_stsearch(yopt, 'a');
    lby = plP_stsearch(yopt, 'b');
    lcy = plP_stsearch(yopt, 'c');
    lgy = plP_stsearch(yopt, 'g');
    liy = plP_stsearch(yopt, 'i');
    lly = plP_stsearch(yopt, 'l');
    lsy = plP_stsearch(yopt, 's');
    lty = plP_stsearch(yopt, 't');

/* Tick and subtick sizes in device coords */

    xmajor = MAX(ROUND(plsc->majht * plsc->ypmm), 1);
    ymajor = MAX(ROUND(plsc->majht * plsc->xpmm), 1);
    xminor = MAX(ROUND(plsc->minht * plsc->ypmm), 1);
    yminor = MAX(ROUND(plsc->minht * plsc->xpmm), 1);

    nxsub1 = nxsub;
    nysub1 = nysub;
    xtick1 = llx ? 1.0 : xtick;
    ytick1 = lly ? 1.0 : ytick;

    plgvpw(&vpwxmin, &vpwxmax, &vpwymin, &vpwymax);
/* n.b. large change; vpwxmi always numerically less than vpwxma, and
 * similarly for vpwymi */
    vpwxmi = (vpwxmax > vpwxmin) ? vpwxmin : vpwxmax;
    vpwxma = (vpwxmax > vpwxmin) ? vpwxmax : vpwxmin;
    vpwymi = (vpwymax > vpwymin) ? vpwymin : vpwymax;
    vpwyma = (vpwymax > vpwymin) ? vpwymax : vpwymin;

    lax = lax && vpwymi < y0 && y0 < vpwyma ;
    lay = lay && vpwxmi < x0 && x0 < vpwxma ;

/* Calculate tick spacing */

    if (ltx || lgx)
      pldtik(vpwxmi, vpwxma, &xtick1, &nxsub1);

    if (lty || lgy)
      pldtik(vpwymi, vpwyma, &ytick1, &nysub1);
/* n.b. large change; xtick1, nxsub1, ytick1, nysub1 always positive. */

/* Set up tick variables */

    if (lix) {
      i1x = xminor;
      i2x = 0;
      i3x = xmajor;
      i4x = 0;
    }
    else {
      i1x = 0;
      i2x = xminor;
      i3x = 0;
      i4x = xmajor;
    }

    if (liy) {
      i1y = yminor;
      i2y = 0;
      i3y = ymajor;
      i4y = 0;
    }
    else {
      i1y = 0;
      i2y = yminor;
      i3y = 0;
      i4y = ymajor;
    }

/* Draw the bottom edge of the box */

    if (lbx) {
      plP_movphy(vppxmi, vppymi);
      if (ltx) {
          tp = xtick1 * floor(vpwxmi / xtick1);
          for (;;) {
            tn = tp + xtick1;
            if (lsx) {
                if (llx) {
                  for (i = 0; i <= 7; i++) {
                      temp = tp + xlog[i];
                      if (BETW(temp, vpwxmi, vpwxma))
                        plxtik(plP_wcpcx(temp), vppymi, i1x, i2x);
                  }
                }
                else {
                  for (i = 1; i <= nxsub1 - 1; i++) {
                      temp = tp + i * xtick1 / nxsub1;
                      if (BETW(temp, vpwxmi, vpwxma))
                        plxtik(plP_wcpcx(temp), vppymi, i1x, i2x);
                  }
                }
            }
            if (!BETW(tn, vpwxmi, vpwxma))
                break;
            plxtik(plP_wcpcx(tn), vppymi, i3x, i4x);
            tp = tn;
          }
      }
      plP_draphy(vppxma, vppymi);
    }

/* Draw right-hand edge of box */

    if (lcy) {
      plP_movphy(vppxma, vppymi);
      if (lty) {
          tp = ytick1 * floor(vpwymi / ytick1);
          for (;;) {
            tn = tp + ytick1;
            if (lsy) {
                if (lly) {
                  for (i = 0; i <= 7; i++) {
                      temp = tp + xlog[i];
                      if (BETW(temp, vpwymi, vpwyma))
                        plytik(vppxma, plP_wcpcy(temp), i2y, i1y);
                  }
                }
                else {
                  for (i = 1; i <= nysub1 - 1; i++) {
                      temp = tp + i * ytick1 / nysub1;
                      if (BETW(temp, vpwymi, vpwyma))
                        plytik(vppxma, plP_wcpcy(temp), i2y, i1y);
                  }
                }
            }
            if (!BETW(tn, vpwymi, vpwyma))
                break;
            plytik(vppxma, plP_wcpcy(tn), i4y, i3y);
            tp = tn;
          }
      }
      plP_draphy(vppxma, vppyma);
    }

/* Draw the top edge of the box */

    if (lcx) {
      plP_movphy(vppxma, vppyma);
      if (ltx) {
          tp = xtick1 * (floor(vpwxma / xtick1) + 1);
          for (;;) {
            tn = tp - xtick1;
            if (lsx) {
                if (llx) {
                  for (i = 7; i >= 0; i--) {
                      temp = tn + xlog[i];
                      if (BETW(temp, vpwxmi, vpwxma))
                        plxtik(plP_wcpcx(temp), vppyma, i2x, i1x);
                  }
                }
                else {
                  for (i = nxsub1 - 1; i >= 1; i--) {
                      temp = tn + i * xtick1 / nxsub1;
                      if (BETW(temp, vpwxmi, vpwxma))
                        plxtik(plP_wcpcx(temp), vppyma, i2x, i1x);
                  }
                }
            }
            if (!BETW(tn, vpwxmi, vpwxma))
                break;
            plxtik(plP_wcpcx(tn), vppyma, i4x, i3x);
            tp = tn;
          }
      }
      plP_draphy(vppxmi, vppyma);
    }

/* Draw left-hand edge of box */

    if (lby) {
      plP_movphy(vppxmi, vppyma);
      if (lty) {
          tp = ytick1 * (floor(vpwyma / ytick1) + 1);
          for (;;) {
            tn = tp - ytick1;
            if (lsy) {
                if (lly) {
                  for (i = 7; i >= 0; i--) {
                      temp = tn + xlog[i];
                      if (BETW(temp, vpwymi, vpwyma))
                        plytik(vppxmi, plP_wcpcy(temp), i1y, i2y);
                  }
                }
                else {
                  for (i = nysub1 - 1; i >= 1; i--) {
                      temp = tn + i * ytick1 / nysub1;
                      if (BETW(temp, vpwymi, vpwyma))
                        plytik(vppxmi, plP_wcpcy(temp), i1y, i2y);
                  }
                }
            }
            if (!BETW(tn, vpwymi, vpwyma))
                break;
            plytik(vppxmi, plP_wcpcy(tn), i3y, i4y);
            tp = tn;
          }
      }
      plP_draphy(vppxmi, vppymi);
    }

/* Draw the horizontal axis */

    if (lax) {
      plP_movphy(vppxmi, yp0);
      if (ltx) {
          tp = xtick1 * floor(vpwxmi / xtick1);
          for (;;) {
            tn = tp + xtick1;
            if (lsx) {
                if (llx) {
                  for (i = 0; i <= 7; i++) {
                      temp = tp + xlog[i];
                      if (BETW(temp, vpwxmi, vpwxma))
                        plxtik(plP_wcpcx(temp), yp0, xminor, xminor);
                  }
                }
                else {
                  for (i = 1; i <= nxsub1 - 1; i++) {
                      temp = tp + i * xtick1 / nxsub1;
                      if (BETW(temp, vpwxmi, vpwxma))
                        plxtik(plP_wcpcx(temp), yp0, xminor, xminor);
                  }
                }
            }
            if (!BETW(tn, vpwxmi, vpwxma))
                break;
            plxtik(plP_wcpcx(tn), yp0, xmajor, xmajor);
            tp = tn;
          }
      }
      plP_draphy(vppxma, yp0);
    }

/* Draw the vertical axis */

    if (lay) {
      plP_movphy(xp0, vppymi);
      if (lty) {
          tp = ytick1 * floor(vpwymi / ytick1);
          for (;;) {
            tn = tp + ytick1;
            if (lsy) {
                if (lly) {
                  for (i = 0; i <= 7; i++) {
                      temp = tp + xlog[i];
                      if (BETW(temp, vpwymi, vpwyma))
                        plytik(xp0, plP_wcpcy(temp), yminor, yminor);
                  }
                }
                else {
                  for (i = 1; i <= nysub1 - 1; i++) {
                      temp = tp + i * ytick1 / nysub1;
                      if (BETW(temp, vpwymi, vpwyma))
                        plytik(xp0, plP_wcpcy(temp), yminor, yminor);
                  }
                }
            }
            if (!BETW(tn, vpwymi, vpwyma))
                break;
            plytik(xp0, plP_wcpcy(tn), ymajor, ymajor);
            tp = tn;
          }
      }
      plP_draphy(xp0, vppyma);
    }

/* Draw grids */

    grid_box(xopt, xtick1, nxsub1, yopt, ytick1, nysub1);

/* Write labels */

    label_box(xopt, xtick1, yopt, ytick1);

/* Restore the clip limits to viewport edge */

    plP_sclp(lxmin, lxmax, lymin, lymax);
}

/*--------------------------------------------------------------------------*\
 * void plbox3()
 *
 * This is the 3-d analogue of plbox().
\*--------------------------------------------------------------------------*/

void
c_plbox3(const char *xopt, const char *xlabel, PLFLT xtick, PLINT nsubx,
       const char *yopt, const char *ylabel, PLFLT ytick, PLINT nsuby,
       const char *zopt, const char *zlabel, PLFLT ztick, PLINT nsubz)
{
    PLFLT dx, dy, tx, ty, ux, uy;
    PLFLT xmin, xmax, ymin, ymax, zmin, zmax, zscale;
    PLFLT cxx, cxy, cyx, cyy, cyz;
    PLINT ln;
    PLINT *zbflg, *zbcol, *zbwidth;
    PLFLT *zbtck;
    PLINT xdigmax, xdigits;
    PLINT ydigmax, ydigits;
    PLINT zdigmax, zdigits;

    if (plsc->level < 3) {
      plabort("plbox3: Please set up window first");
      return;
    }

    plP_gw3wc(&cxx, &cxy, &cyx, &cyy, &cyz);
    plP_gdom(&xmin, &xmax, &ymin, &ymax);
    plP_grange(&zscale, &zmin, &zmax);

    plgxax(&xdigmax, &xdigits);
    plgyax(&ydigmax, &ydigits);
    plgzax(&zdigmax, &zdigits);

    xdigits = xdigmax;
    ydigits = ydigmax;
    zdigits = zdigmax;

/* We have to wait until after the plot is drawn to draw back */
/* grid so store this stuff. */

    plP_gzback(&zbflg, &zbcol, &zbtck, &zbwidth);
    *zbflg = plP_stsearch(zopt, 'd');
    if (*zbflg) {
      *zbtck = ztick;         /* save tick spacing */
      *zbcol = plsc->icol0;   /* and color */
      *zbwidth = plsc->width; /* and line width */
    }

    if (cxx >= 0.0 && cxy <= 0.0) {
      ln = plP_stsearch(xopt, 'n');
      tx = plP_w3wcx(xmin, ymin, zmin);
      ty = plP_w3wcy(xmin, ymin, zmin);
      ux = plP_w3wcx(xmax, ymin, zmin);
      uy = plP_w3wcy(xmax, ymin, zmin);
      plxybx(xopt, xlabel, tx, ty, ux, uy,
             xmin, xmax, xtick, nsubx, 0, &xdigits);

      dx = ux - tx;
      dy = uy - ty;
      plzbx(zopt, zlabel, 1, dx, dy, ux, uy,
            plP_w3wcy(xmax, ymin, zmax), zmin, zmax, ztick, nsubz, &zdigits);

      tx = plP_w3wcx(xmin, ymax, zmin);
      ty = plP_w3wcy(xmin, ymax, zmin);
      ux = plP_w3wcx(xmin, ymin, zmin);
      uy = plP_w3wcy(xmin, ymin, zmin);
      plxybx(yopt, ylabel, tx, ty, ux, uy,
             ymax, ymin, ytick, nsuby, ln, &ydigits);

      dx = ux - tx;
      dy = uy - ty;
/* restore zdigits to initial value for second call */
        zdigits = zdigmax;
      plzbx(zopt, zlabel, 0, dx, dy, tx, ty,
            plP_w3wcy(xmin, ymax, zmax), zmin, zmax, ztick, nsubz, &zdigits);
    }
    else if (cxx <= 0.0 && cxy <= 0.0) {
      ln = plP_stsearch(yopt, 'n');
      tx = plP_w3wcx(xmin, ymax, zmin);
      ty = plP_w3wcy(xmin, ymax, zmin);
      ux = plP_w3wcx(xmin, ymin, zmin);
      uy = plP_w3wcy(xmin, ymin, zmin);
      plxybx(yopt, ylabel, tx, ty, ux, uy,
             ymax, ymin, ytick, nsuby, 0, &ydigits);

      dx = ux - tx;
      dy = uy - ty;
      plzbx(zopt, zlabel, 1, dx, dy, ux, uy,
            plP_w3wcy(xmin, ymin, zmax), zmin, zmax, ztick, nsubz, &zdigits);

      tx = plP_w3wcx(xmax, ymax, zmin);
      ty = plP_w3wcy(xmax, ymax, zmin);
      ux = plP_w3wcx(xmin, ymax, zmin);
      uy = plP_w3wcy(xmin, ymax, zmin);
      plxybx(xopt, xlabel, tx, ty, ux, uy,
             xmax, xmin, xtick, nsubx, ln, &xdigits);

      dx = ux - tx;
      dy = uy - ty;
/* restore zdigits to initial value for second call */
        zdigits = zdigmax;
      plzbx(zopt, zlabel, 0, dx, dy, tx, ty,
            plP_w3wcy(xmax, ymax, zmax), zmin, zmax, ztick, nsubz, &zdigits);
    }
    else if (cxx <= 0.0 && cxy >= 0.0) {
      ln = plP_stsearch(xopt, 'n');
      tx = plP_w3wcx(xmax, ymax, zmin);
      ty = plP_w3wcy(xmax, ymax, zmin);
      ux = plP_w3wcx(xmin, ymax, zmin);
      uy = plP_w3wcy(xmin, ymax, zmin);
      plxybx(xopt, xlabel, tx, ty, ux, uy,
             xmax, xmin, xtick, nsubx, 0, &xdigits);

      dx = ux - tx;
      dy = uy - ty;
      plzbx(zopt, zlabel, 1, dx, dy, ux, uy,
            plP_w3wcy(xmin, ymax, zmax), zmin, zmax, ztick, nsubz, &zdigits);

      tx = plP_w3wcx(xmax, ymin, zmin);
      ty = plP_w3wcy(xmax, ymin, zmin);
      ux = plP_w3wcx(xmax, ymax, zmin);
      uy = plP_w3wcy(xmax, ymax, zmin);
      plxybx(yopt, ylabel, tx, ty, ux, uy,
             ymin, ymax, ytick, nsuby, ln, &ydigits);

      dx = ux - tx;
      dy = uy - ty;
/* restore zdigits to initial value for second call */
        zdigits = zdigmax;
      plzbx(zopt, zlabel, 0, dx, dy, tx, ty,
            plP_w3wcy(xmax, ymin, zmax), zmin, zmax, ztick, nsubz, &zdigits);
    }
    else if (cxx >= 0.0 && cxy >= 0.0) {
      ln = plP_stsearch(yopt, 'n');
      tx = plP_w3wcx(xmax, ymin, zmin);
      ty = plP_w3wcy(xmax, ymin, zmin);
      ux = plP_w3wcx(xmax, ymax, zmin);
      uy = plP_w3wcy(xmax, ymax, zmin);
      plxybx(yopt, ylabel, tx, ty, ux, uy,
             ymin, ymax, ytick, nsuby, 0, &ydigits);

      dx = ux - tx;
      dy = uy - ty;
      plzbx(zopt, zlabel, 1, dx, dy, ux, uy,
            plP_w3wcy(xmax, ymax, zmax), zmin, zmax, ztick, nsubz, &zdigits);

      tx = plP_w3wcx(xmin, ymin, zmin);
      ty = plP_w3wcy(xmin, ymin, zmin);
      ux = plP_w3wcx(xmax, ymin, zmin);
      uy = plP_w3wcy(xmax, ymin, zmin);
      plxybx(xopt, xlabel, tx, ty, ux, uy,
             xmin, xmax, xtick, nsubx, ln, &xdigits);

      dx = ux - tx;
      dy = uy - ty;
/* restore zdigits to initial value for second call */
        zdigits = zdigmax;
      plzbx(zopt, zlabel, 0, dx, dy, tx, ty,
            plP_w3wcy(xmin, ymin, zmax), zmin, zmax, ztick, nsubz, &zdigits);
    }
    plsxax(xdigmax, xdigits);
    plsyax(ydigmax, ydigits);
    plszax(zdigmax, zdigits);
}

/*--------------------------------------------------------------------------*\
 * Support routines for 3d box draw.
\*--------------------------------------------------------------------------*/

/*--------------------------------------------------------------------------*\
 * void plxybx()
 *
 * This draws a sloping line from (wx1,wy1) to (wx2,wy2) which represents an
 * axis of a 3-d graph with data values from "vmin" to "vmax". Depending on
 * "opt", vertical ticks and/or subticks are placed on the line at major tick
 * interval "tick" with "nsub" subticks between major ticks. If "tick" and/or
 * "nsub" is zero, automatic tick positions are computed
 *
 * b: Draw box boundary
 * f: Always use fixed point numeric labels
 * i: Inverts tick marks (i.e. drawn downwards)
 * l: Logarithmic axes, major ticks at decades, minor ticks at units
 * n: Write numeric label
 * t: Draw major tick marks
 * s: Draw minor tick marks
 * u: Write label on line
\*--------------------------------------------------------------------------*/

static void
plxybx(const char *opt, const char *label, PLFLT wx1, PLFLT wy1,
       PLFLT wx2, PLFLT wy2, PLFLT vmin_in, PLFLT vmax_in,
       PLFLT tick, PLINT nsub, PLINT nolast, PLINT *digits)
{
    static char string[40];
    PLINT lb, lf, li, ll, ln, ls, lt, lu;
    PLINT major, minor, mode, prec, scale;
    PLINT i, i1, i2, i3, i4;
    PLINT nsub1;
    PLFLT pos, tn, tp, temp, height, tick1, vmin, vmax;
/* Note that 'tspace' is the minimim distance away (in fractional number
 * of ticks) from the boundary that an X or Y numerical label can be drawn. */
    PLFLT dwx, dwy, lambda, tcrit, tspace = 0.1;

    vmin = (vmax_in > vmin_in) ? vmin_in : vmax_in;
    vmax = (vmax_in > vmin_in) ? vmax_in : vmin_in;

    dwx = wx2 - wx1;
    dwy = wy2 - wy1;

/* Tick and subtick sizes in device coords */

    major = MAX(ROUND(plsc->majht * plsc->ypmm), 1);
    minor = MAX(ROUND(plsc->minht * plsc->ypmm), 1);

    tick1 = tick;
    nsub1 = nsub;

    lb = plP_stsearch(opt, 'b');
    lf = plP_stsearch(opt, 'f');
    li = plP_stsearch(opt, 'i');
    ll = plP_stsearch(opt, 'l');
    ln = plP_stsearch(opt, 'n');
    ls = plP_stsearch(opt, 's');
    lt = plP_stsearch(opt, 't');
    lu = plP_stsearch(opt, 'u');

    if (lu)
      plxytx(wx1, wy1, wx2, wy2, 3.2, 0.5, 0.5, label);
    if (!lb)
      return;

    if (ll)
      tick1 = (vmax > vmin) ? 1.0 : -1.0 ;
    if (lt)
      pldtik(vmin, vmax, &tick1, &nsub1);

    if (li) {
      i1 = minor;
      i2 = 0;
      i3 = major;
      i4 = 0;
    }
    else {
      i1 = 0;
      i2 = minor;
      i3 = 0;
      i4 = major;
    }

/* Draw the line */

    plP_movwor(wx1, wy1);
    if (lt) {
      tp = tick1 * floor(vmin / tick1);
      for (;;) {
          tn = tp + tick1;
          if (ls) {
            if (ll) {
                for (i = 0; i <= 7; i++) {
                  temp = tp + xlog[i];
                  if (BETW(temp, vmin, vmax)) {
                      lambda = (vmax_in > vmin_in)?
                         (temp - vmin) / (vmax - vmin):
                         (vmax - temp) / (vmax - vmin);
                      plxtik(plP_wcpcx((PLFLT) (wx1 + lambda * dwx)),
                           plP_wcpcy((PLFLT) (wy1 + lambda * dwy)),
                           i1, i2);
                  }
                }
            }
            else {
                for (i = 1; i <= nsub1 - 1; i++) {
                  temp = tp + i * (tn - tp) / nsub1;
                  if (BETW(temp, vmin, vmax)) {
                      lambda = (vmax_in > vmin_in)?
                         (temp - vmin) / (vmax - vmin):
                         (vmax - temp) / (vmax - vmin);
                      plxtik(plP_wcpcx((PLFLT) (wx1 + lambda * dwx)),
                           plP_wcpcy((PLFLT) (wy1 + lambda * dwy)),
                           i1, i2);
                  }
                }
            }
          }
          temp = tn;
          if (!BETW(temp, vmin, vmax))
            break;

          lambda = (vmax_in > vmin_in)?
             (temp - vmin) / (vmax - vmin):
             (vmax - temp) / (vmax - vmin);
          plxtik(plP_wcpcx((PLFLT) (wx1 + lambda * dwx)),
               plP_wcpcy((PLFLT) (wy1 + lambda * dwy)), i3, i4);
          tp = tn;
      }
    }

    plP_drawor(wx2, wy2);

/* Label the line */

    if (ln && lt) {
      pldprec(vmin, vmax, tick1, lf, &mode, &prec, *digits, &scale);
      pos = 1.0;
      height = 3.2;
        tcrit = tspace*tick1;
      tp = tick1 * (1. + floor(vmin / tick1));
      for (tn = tp; BETW(tn, vmin, vmax); tn += tick1) {
         if(BETW(tn, vmin+tcrit, vmax-tcrit)) {
          plform(tn, scale, prec, string, ll, lf);
          pos = (vmax_in > vmin_in)?
             (tn - vmin) / (vmax - vmin):
             (vmax - tn) / (vmax - vmin);
          plxytx(wx1, wy1, wx2, wy2, 1.5, pos, 0.5, string);
         }
      }
      *digits = 2;
      if (!ll && mode) {
          sprintf(string, "(x10#u%d#d)", (int) scale);
          plxytx(wx1, wy1, wx2, wy2, height, 1.0, 0.5, string);
      }
    }
}

/*--------------------------------------------------------------------------*\
 * void plxytx()
 *
 * Prints out text along a sloping axis joining world coordinates
 * (wx1,wy1) to (wx2,wy2). Parameters are as for plmtext.
\*--------------------------------------------------------------------------*/

static void
plxytx(PLFLT wx1, PLFLT wy1, PLFLT wx2, PLFLT wy2,
       PLFLT disp, PLFLT pos, PLFLT just, const char *text)
{
    PLINT x, y, refx, refy;
    PLFLT shift, cc, ss, wx, wy;
    PLFLT xdv, ydv, xmm, ymm, refxmm, refymm, xform[4], diag;
    PLFLT dispx, dispy;
    PLFLT chrdef, chrht;

    cc = plsc->wmxscl * (wx2 - wx1);
    ss = plsc->wmyscl * (wy2 - wy1);
    diag = sqrt(cc * cc + ss * ss);
    cc /= diag;
    ss /= diag;
    wx = wx1 + pos * (wx2 - wx1);
    wy = wy1 + pos * (wy2 - wy1);

    xform[0] = cc;
    xform[1] = 0.0;
    xform[2] = ss;
    xform[3] = 1.0;

    xdv = plP_wcdcx(wx);
    ydv = plP_wcdcy(wy);

    dispx = 0.;
    dispy = -disp;

    plgchr(&chrdef, &chrht);
    shift = (just == 0.0) ? 0.0 : plstrl(text) * just;

    xmm = plP_dcmmx(xdv) + dispx * chrht;
    ymm = plP_dcmmy(ydv) + dispy * chrht;
    refxmm = xmm - shift * xform[0];
    refymm = ymm - shift * xform[2];

    x = plP_mmpcx(xmm);
    y = plP_mmpcy(ymm);
    refx = plP_mmpcx(refxmm);
    refy = plP_mmpcy(refymm);

    plP_text(0, just, xform, x, y, refx, refy, text);
}

/*--------------------------------------------------------------------------*\
 * void plzbx()
 *
 * This draws a vertical line from (wx,wy1) to (wx,wy2) which represents the
 * vertical axis of a 3-d graph with data values from "vmin" to "vmax".
 * Depending on "opt", ticks and/or subticks are placed on the line at major
 * tick interval "tick" with "nsub" subticks between major ticks. If "tick"
 * and/or "nsub" is zero, automatic tick positions are computed
 *
 * b: Draws left-hand axis
 * c: Draws right-hand axis
 * f: Always use fixed point numeric labels
 * i: Inverts tick marks (i.e. drawn to the left)
 * l: Logarithmic axes, major ticks at decades, minor ticks at units
 * m: Write numeric label on right axis
 * n: Write numeric label on left axis
 * s: Draw minor tick marks
 * t: Draw major tick marks
 * u: Writes left-hand label
 * v: Writes right-hand label
\*--------------------------------------------------------------------------*/

static void
plzbx(const char *opt, const char *label, PLINT right, PLFLT dx, PLFLT dy,
      PLFLT wx, PLFLT wy1, PLFLT wy2, PLFLT vmin_in, PLFLT vmax_in,
      PLFLT tick, PLINT nsub, PLINT *digits)
{
    static char string[40];
    PLINT lb, lc, lf, li, ll, lm, ln, ls, lt, lu, lv;
    PLINT i, mode, prec, scale;
    PLINT nsub1, lstring;
    PLFLT pos, tn, tp, temp, height, tick1;
    PLFLT dwy, lambda, diag, major, minor, xmajor, xminor;
    PLFLT ymajor, yminor, dxm, dym, vmin, vmax;

    vmin = (vmax_in > vmin_in) ? vmin_in : vmax_in;
    vmax = (vmax_in > vmin_in) ? vmax_in : vmin_in;

    dwy = wy2 - wy1;

/* Tick and subtick sizes in device coords */

    major = plsc->majht;
    minor = plsc->minht;

    tick1 = tick;
    nsub1 = nsub;

    lb = plP_stsearch(opt, 'b');
    lc = plP_stsearch(opt, 'c');
    lf = plP_stsearch(opt, 'f');
    li = plP_stsearch(opt, 'i');
    ll = plP_stsearch(opt, 'l');
    lm = plP_stsearch(opt, 'm');
    ln = plP_stsearch(opt, 'n');
    ls = plP_stsearch(opt, 's');
    lt = plP_stsearch(opt, 't');
    lu = plP_stsearch(opt, 'u');
    lv = plP_stsearch(opt, 'v');

    if (lu && !right)
      plztx("h", dx, dy, wx, wy1, wy2, 5.0, 0.5, 0.5, label);

    if (lv && right)
      plztx("h", dx, dy, wx, wy1, wy2, -5.0, 0.5, 0.5, label);

    if (right && !lc)
      return;

    if (!right && !lb)
      return;

    if (ll)
      tick1 = 1.0;

    if (lt)
      pldtik(vmin, vmax, &tick1, &nsub1);

    if ((li && !right) || (!li && right)) {
      minor = -minor;
      major = -major;
    }

    dxm = dx * plsc->wmxscl;
    dym = dy * plsc->wmyscl;
    diag = sqrt(dxm * dxm + dym * dym);

    xminor = minor * dxm / diag;
    xmajor = major * dxm / diag;
    yminor = minor * dym / diag;
    ymajor = major * dym / diag;

/* Draw the line */

    plP_movwor(wx, wy1);
    if (lt) {
      tp = tick1 * floor(vmin / tick1);
      for (;;) {
          tn = tp + tick1;
          if (ls) {
            if (ll) {
                for (i = 0; i <= 7; i++) {
                  temp = tp + xlog[i];
                  if (BETW(temp, vmin, vmax)) {
                      lambda = (vmax_in > vmin_in)?
                         (temp - vmin) / (vmax - vmin):
                         (vmax - temp) / (vmax - vmin);
                      plstik(plP_wcmmx(wx),
                           plP_wcmmy((PLFLT) (wy1 + lambda * dwy)),
                           xminor, yminor);
                  }
                }
            }
            else {
                for (i = 1; i <= nsub1 - 1; i++) {
                  temp = tp + i * tick1 / nsub1;
                  if (BETW(temp, vmin, vmax)) {
                      lambda = (vmax_in > vmin_in)?
                         (temp - vmin) / (vmax - vmin):
                         (vmax - temp) / (vmax - vmin);
                      plstik(plP_wcmmx(wx),
                           plP_wcmmy((PLFLT) (wy1 + lambda * dwy)),
                           xminor, yminor);
                  }
                }
            }
          }
          temp = tn;
          if (!BETW(temp, vmin, vmax))
            break;
          lambda = (vmax_in > vmin_in)?
              (temp - vmin) / (vmax - vmin):
              (vmax - temp) / (vmax - vmin);
          plstik(plP_wcmmx(wx), plP_wcmmy((PLFLT) (wy1 + lambda * dwy)),
               xmajor, ymajor);
          tp = tn;
      }
    }

    plP_drawor(wx, wy2);

/* Label the line */

    if ((ln || lm) && lt) {
      pldprec(vmin, vmax, tick1, lf, &mode, &prec, *digits, &scale);
      *digits = 0;
      tp = tick1 * floor(vmin / tick1);
      for (tn = tp + tick1; BETW(tn, vmin, vmax); tn += tick1) {
          plform(tn, scale, prec, string, ll, lf);
          pos = (vmax_in > vmin_in)?
              (tn - vmin) / (vmax - vmin):
              (vmax - tn) / (vmax - vmin);
          if (ln && !right)
            plztx("v", dx, dy, wx, wy1, wy2, 0.5, pos, 1.0, string);

          if (lm && right)
            plztx("v", dx, dy, wx, wy1, wy2, -0.5, pos, 0.0, string);

          lstring = strlen(string);
          *digits = MAX(*digits, lstring);
      }
      if (!ll && mode) {
          sprintf(string, "(x10#u%d#d)", (int) scale);
          pos = 1.15;
          height = 0.5;
          if (ln && !right) {
            plztx("v", dx, dy, wx, wy1, wy2, height, pos, 0.5, string);
          }
          if (lm && right) {
            plztx("v", dx, dy, wx, wy1, wy2,
                  (PLFLT) -height, pos, 0.5, string);
          }
      }
    }
}

/*--------------------------------------------------------------------------*\
 * void plztx()
 *
 * Prints out text along a vertical axis for a 3d plot joining
 * world coordinates (wx,wy1) to (wx,wy2).
\*--------------------------------------------------------------------------*/

static void
plztx(const char *opt, PLFLT dx, PLFLT dy, PLFLT wx, PLFLT wy1,
      PLFLT wy2, PLFLT disp, PLFLT pos, PLFLT just, const char *text)
{
    PLINT refx = 0, refy = 0, x = 0, y = 0, vert = 0;
    PLFLT shift, cc, ss, wy;
    PLFLT xdv, ydv, xmm, ymm, refxmm, refymm, xform[4], diag;
    PLFLT dispx, dispy;
    PLFLT chrdef, chrht;

    cc = plsc->wmxscl * dx;
    ss = plsc->wmyscl * dy;
    diag = sqrt(cc * cc + ss * ss);
    cc /= diag;
    ss /= diag;
    wy = wy1 + pos * (wy2 - wy1);

    if (plP_stsearch(opt, 'v'))
      vert = 0;
    else if (plP_stsearch(opt, 'h'))
      vert = 1;

    if (vert) {
      xform[0] = 0.0;
      xform[1] = -cc;
      xform[2] = 1.0;
      xform[3] = -ss;
    } else {
      xform[0] = cc;
      xform[1] = 0.0;
      xform[2] = ss;
      xform[3] = 1.0;
    }

    xdv = plP_wcdcx(wx);
    ydv = plP_wcdcy(wy);

    dispx = -disp * cc;
    dispy = -disp * ss;

    plgchr(&chrdef, &chrht);
    shift = (just == 0.0) ? 0.0 : plstrl(text) * just;

    xmm = plP_dcmmx(xdv) + dispx * chrht;
    ymm = plP_dcmmy(ydv) + dispy * chrht;
    refxmm = xmm - shift * xform[0];
    refymm = ymm - shift * xform[2];

    x = plP_mmpcx(xmm);
    y = plP_mmpcy(ymm);
    refx = plP_mmpcx(refxmm);
    refy = plP_mmpcy(refymm);

    plP_text(0, just, xform, x, y, refx, refy, text);
}

/*--------------------------------------------------------------------------*\
 * void grid_box()
 *
 * Draws grids at tick locations (major and/or minor).
 *
 * Note that 'tspace' is the minimim distance away (in fractional number
 * of ticks or subticks) from the boundary a grid line can be drawn.  If
 * you are too close, it looks bad.
\*--------------------------------------------------------------------------*/

static void
grid_box(const char *xopt, PLFLT xtick1, PLINT nxsub1,
       const char *yopt, PLFLT ytick1, PLINT nysub1)
{
    PLINT lgx, lhx, llx;
    PLINT lgy, lhy, lly;
    PLFLT vpwxmi, vpwxma, vpwymi, vpwyma;
    PLFLT vpwxmin, vpwxmax, vpwymin, vpwymax;
    PLFLT tn, temp, tcrit, tspace = 0.1;
    PLINT i;

/* Set plot options from input */

    lgx = plP_stsearch(xopt, 'g');
    lhx = plP_stsearch(xopt, 'h');
    llx = plP_stsearch(xopt, 'l');

    lgy = plP_stsearch(yopt, 'g');
    lhy = plP_stsearch(yopt, 'h');
    lly = plP_stsearch(yopt, 'l');

    plgvpw(&vpwxmin, &vpwxmax, &vpwymin, &vpwymax);
/* n.b. large change; vpwxmi always numerically less than vpwxma, and
 * similarly for vpwymi */
    vpwxmi = (vpwxmax > vpwxmin) ? vpwxmin : vpwxmax;
    vpwxma = (vpwxmax > vpwxmin) ? vpwxmax : vpwxmin;
    vpwymi = (vpwymax > vpwymin) ? vpwymin : vpwymax;
    vpwyma = (vpwymax > vpwymin) ? vpwymax : vpwymin;

/* Draw grid in x direction. */

    if (lgx) {
      for (tn = xtick1 * floor(vpwxmi/xtick1);
           tn <= vpwxma; tn += xtick1) {
          if (lhx) {
            if (llx) {
                PLFLT otemp = tn;
                for (i = 0; i <= 7; i++) {
                  temp = tn + xlog[i];
                  tcrit = (temp - otemp)*tspace;
                  otemp = temp;
                  if (BETW(temp, vpwxmi+tcrit, vpwxma-tcrit))
                      pljoin(temp, vpwymi, temp, vpwyma);
                }
            }
            else {
                for (i = 1; i <= nxsub1 - 1; i++) {
                  temp = tn + i * xtick1 / nxsub1;
                  tcrit = xtick1 / nxsub1 * tspace;
                  if (BETW(temp, vpwxmi+tcrit, vpwxma-tcrit))
                      pljoin(temp, vpwymi, temp, vpwyma);
                }
            }
          }
          tcrit = xtick1*tspace;
          if (BETW(tn, vpwxmi+tcrit, vpwxma-tcrit))
              pljoin(tn, vpwymi, tn, vpwyma);
      }
    }

/* Draw grid in y direction */

    if (lgy) {
      tn = ytick1 * floor(vpwymi / ytick1 + tspace);
      for (tn = ytick1 * floor(vpwymi/ytick1);
           tn <= vpwyma; tn += ytick1) {
          if (lhy) {
            if (lly) {
                PLFLT otemp = tn;
                for (i = 0; i <= 7; i++) {
                  temp = tn + xlog[i];
                  tcrit = (temp - otemp)*tspace;
                  otemp = temp;
                  if (BETW(temp, vpwymi+tcrit, vpwyma-tcrit))
                      pljoin(vpwxmi, temp, vpwxma, temp);
                }
            }
            else {
                for (i = 1; i <= nysub1 - 1; i++) {
                  temp = tn + i * ytick1 / nysub1;
                  tcrit = ytick1 / nysub1 * tspace;
                  if (BETW(temp, vpwymi+tcrit, vpwyma-tcrit))
                      pljoin(vpwxmi, temp, vpwxma, temp);
                }
            }
          }
          tcrit = ytick1*tspace;
          if (BETW(tn, vpwymi+tcrit, vpwyma-tcrit))
          pljoin(vpwxmi, tn, vpwxma, tn);
      }
    }
}

/*--------------------------------------------------------------------------*\
 * void label_box()
 *
 * Writes numeric labels on side(s) of box.
\*--------------------------------------------------------------------------*/

static void
label_box(const char *xopt, PLFLT xtick1, const char *yopt, PLFLT ytick1)
{
    static char string[40];
    PLINT lfx, lix, llx, lmx, lnx, ltx;
    PLINT lfy, liy, lly, lmy, lny, lty, lvy;
    PLFLT vpwxmi, vpwxma, vpwymi, vpwyma;
    PLFLT vpwxmin, vpwxmax, vpwymin, vpwymax;
    PLFLT pos, tn, tp, offset, height;

/* Set plot options from input */

    lfx = plP_stsearch(xopt, 'f');
    lix = plP_stsearch(xopt, 'i');
    llx = plP_stsearch(xopt, 'l');
    lmx = plP_stsearch(xopt, 'm');
    lnx = plP_stsearch(xopt, 'n');
    ltx = plP_stsearch(xopt, 't');

    lfy = plP_stsearch(yopt, 'f');
    liy = plP_stsearch(yopt, 'i');
    lly = plP_stsearch(yopt, 'l');
    lmy = plP_stsearch(yopt, 'm');
    lny = plP_stsearch(yopt, 'n');
    lty = plP_stsearch(yopt, 't');
    lvy = plP_stsearch(yopt, 'v');

    plgvpw(&vpwxmin, &vpwxmax, &vpwymin, &vpwymax);
/* n.b. large change; vpwxmi always numerically less than vpwxma, and
 * similarly for vpwymi */
    vpwxmi = (vpwxmax > vpwxmin) ? vpwxmin : vpwxmax;
    vpwxma = (vpwxmax > vpwxmin) ? vpwxmax : vpwxmin;
    vpwymi = (vpwymax > vpwymin) ? vpwymin : vpwymax;
    vpwyma = (vpwymax > vpwymin) ? vpwymax : vpwymin;

/* Write horizontal label(s) */

    if ((lmx || lnx) && ltx) {
      PLINT xmode, xprec, xdigmax, xdigits, xscale;

      plgxax(&xdigmax, &xdigits);
      pldprec(vpwxmi, vpwxma, xtick1, lfx, &xmode, &xprec, xdigmax, &xscale);

      tp = xtick1 * (1. + floor(vpwxmi / xtick1));
      for (tn = tp; BETW(tn, vpwxmi, vpwxma); tn += xtick1) {
          plform(tn, xscale, xprec, string, llx, lfx);
          height = lix ? 1.75 : 1.5;
          pos = (vpwxmax > vpwxmin)?
              (tn - vpwxmi) / (vpwxma - vpwxmi):
              (vpwxma - tn) / (vpwxma - vpwxmi);
          if (lnx)
            plmtex("b", height, pos, 0.5, string);
          if (lmx)
            plmtex("t", height, pos, 0.5, string);
      }
      xdigits = 2;
      plsxax(xdigmax, xdigits);

    /* Write separate exponential label if mode = 1. */

      if (!llx && xmode) {
          pos = 1.0;
          height = 3.2;
          sprintf(string, "(x10#u%d#d)", (int) xscale);
          if (lnx)
            plmtex("b", height, pos, 0.5, string);
          if (lmx)
            plmtex("t", height, pos, 0.5, string);
      }
    }

/* Write vertical label(s) */

    if ((lmy || lny) && lty) {
      PLINT ymode, yprec, ydigmax, ydigits, yscale;

      plgyax(&ydigmax, &ydigits);
      pldprec(vpwymi, vpwyma, ytick1, lfy, &ymode, &yprec, ydigmax, &yscale);

      ydigits = 0;
      tp = ytick1 * (1. + floor(vpwymi / ytick1));
      for (tn = tp; BETW(tn, vpwymi, vpwyma); tn += ytick1) {
          plform(tn, yscale, yprec, string, lly, lfy);
          pos = (vpwymax > vpwymin)?
              (tn - vpwymi) / (vpwyma - vpwymi):
              (vpwyma - tn) / (vpwyma - vpwymi);
          if (lny) {
            if (lvy) {
                height = liy ? 1.0 : 0.5;
                plmtex("lv", height, pos, 1.0, string);
            } else {
                height = liy ? 1.75 : 1.5;
                plmtex("l", height, pos, 0.5, string);
            }
          }
          if (lmy) {
            if (lvy) {
                height = liy ? 1.0 : 0.5;
                plmtex("rv", height, pos, 0.0, string);
            } else {
                height = liy ? 1.75 : 1.5;
                plmtex("r", height, pos, 0.5, string);
            }
          }
          ydigits = MAX(ydigits, (PLINT) strlen(string));
      }
      if (!lvy)
          ydigits = 2;

      plsyax(ydigmax, ydigits);

    /* Write separate exponential label if mode = 1. */

      if (!lly && ymode) {
          sprintf(string, "(x10#u%d#d)", (int) yscale);
          offset = 0.02;
          height = 2.0;
          if (lny) {
            pos = 0.0 - offset;
            plmtex("t", height, pos, 1.0, string);
          }
          if (lmy) {
            pos = 1.0 + offset;
            plmtex("t", height, pos, 0.0, string);
          }
      }
    }
}

/*--------------------------------------------------------------------------*\
 * void plform()
 *
 * Formats a PLFLT value in one of the following formats.
 *
 * If ll (logarithmic), then:
 *
 *    -     If lf (fixed), then used fixed point notation, i.e. .1, 1, 10, etc,
 *    with unnecessary trailing .'s or 0's removed.
 *
 *    -     If !lf (default), then use exponential notation, i.e. 10^-1, etc.
 *
 * If !ll (linear), then:
 *
 *    - If scale == 0, use fixed point format with "prec" places after the
 *    decimal point.
 *
 *    -     If scale == 1, use scientific notation with one place before the
 *    decimal point and "prec" places after.  In this case, the value
 *    must be divided by 10^scale.
\*--------------------------------------------------------------------------*/

static void
plform(PLFLT value, PLINT scale, PLINT prec, char *string, PLINT ll, PLINT lf)
{
    if (ll) {

    /* Logarithmic */

      if (lf) {

      /* Fixed point, i.e. .1, 1, 10, etc */

          int exponent = ROUND(value);

          value = pow(10.0, exponent);
          if (exponent < 0) {
            char form[10];
            sprintf(form, "%%.%df", ABS(exponent));
            sprintf(string, form, value);
          }
          else {
            sprintf(string, "%d", (int) value);
          }
      }
      else {

      /* Exponential, i.e. 10^-1, 10^0, 10^1, etc */

          sprintf(string, "10#u%d", (int) ROUND(value));
      }
    }
    else {

    /* Linear */

      PLINT setpre, precis;
      char form[10], temp[30];
      double scale2;

      plP_gprec(&setpre, &precis);

      if (setpre)
          prec = precis;

      if (scale)
          value /= pow(10.,(double)scale);

    /* This is necessary to prevent labels like "-0.0" on some systems */

      scale2 = pow(10., prec);
      value = floor((value * scale2) + .5) / scale2;

      sprintf(form, "%%.%df", (int) prec);
      sprintf(temp, form, value);
      strcpy(string, temp);
    }
}

Generated by  Doxygen 1.6.0   Back to index