/*
 * $Id: LineCartesianRenderer.java,v 1.18 2003/08/22 23:02:32 dwd Exp $
 *
 * This software is provided by NOAA for full, free and open release.  It is
 * understood by the recipient/user that NOAA assumes no liability for any
 * errors contained in the code.  Although this software is released without
 * conditions or restrictions in its use, it is expected that appropriate
 * credit be given to its author and to the National Oceanic and Atmospheric
 * Administration should the software be included by the recipient as an
 * element in other product development.
 */

package  sgtplot;


//import sgtplot.util.GeoDate;

import java.util.Vector;
import java.util.Enumeration;
import java.awt.Graphics;
import java.awt.Event;
import java.awt.Point;
import java.awt.Color;
import java.awt.Rectangle;
import java.beans.PropertyChangeEvent;

import org.freehep.graphics2d.VectorGraphics;

import sgtplot.dm.Collection;
import sgtplot.dm.SGTData;
import sgtplot.dm.SGTLine;
import sgtplot.util.Debug;

/**
 * Produces a line plot with optional coloring from a second data set. If
 * a second data set is specified it must have the same shape as the first.
 *
 * @author Donald Denbo
 * @version $Revision: 1.18 $, $Date: 2003/08/22 23:02:32 $
 * @since 1.0
 */
public class LineCartesianRenderer extends CartesianRenderer {
  /**@shapeType AggregationLink
   * @label attr
   * @undirected
   * @supplierCardinality 1 */
  private LineAttribute attr_ = null;
  /**@shapeType AggregationLink
   * @supplierCardinality 0..1
   * @label line
   * @undirected */
  private SGTLine line_ = null;
  /**@shapeType AggregationLink
   * @supplierCardinality 0..1 */
  private Collection collection_ = null;

  private StrokeDrawer stroke_ = null;

  /**
   * Get the Attribute associated with the data.
   */
  public Attribute getAttribute() {
    return attr_;
  }
  private void drawLine(VectorGraphics g, SGTLine line, LineAttribute attr) {
    int[] xp, yp;
    int[] xout, yout;
    int count, size, nout;
    double[] xValues, yValues;
    long[] xTValues, yTValues;

    if(line.isXTime()) {
      xTValues = line.getGeoDateArray().getTime();
      size = xTValues.length;
      xp = new int[size];
      for(count=0; count < size; count++) {
        xp[count] = cg_.getXUtoD(xTValues[count]);
      }
    } else {
      xValues = line.getXArray();
      size = xValues.length;
      xp = new int[size];
      for(count=0; count < size; count++) {
        xp[count] = cg_.getXUtoD(xValues[count]);
      }
    }
    //
    if(line.isYTime()) {
      yTValues = line.getGeoDateArray().getTime();
      size = yTValues.length;
      yp = new int[size];
      for(count=0; count < size; count++) {
        yp[count] = cg_.getYUtoD(yTValues[count]);
      }
    } else {
      yValues = line.getYArray();
      size = yValues.length;
      yp = new int[size];
      for(count=0; count < size; count++) {
        yp[count] = cg_.getYUtoD(yValues[count]);
      }
    }
    //
    // check for missing values a Double.NaN is converted to a Integer.MIN_VALUE
    //
    int first = 0;
    int lsize = 0;
    xout = new int[size];
    yout = new int[size];
    while (first < size) {
      nout=-1;
    line:
      for(count=first; count < size; count++) {
        if(xp[count] != Integer.MIN_VALUE && yp[count] != Integer.MIN_VALUE) {
          nout++;
          xout[nout] = xp[count];
          yout[nout] = yp[count];
        } else if (nout >= 0) {
          break line;
        }
      }
      first = count + 1;
      lsize = nout + 1;
      if(lsize <= 0) return;
      //
      // draw regular line
      //
      switch(attr.getStyle()) {
      case LineAttribute.MARK:
        drawMark(g, xout, yout, lsize, attr);
        break;
      case LineAttribute.HIGHLIGHT:
        stroke_.drawHighlight(g, xout, yout, lsize, attr);
        break;
      case LineAttribute.HEAVY:
        stroke_.drawHeavy(g, xout, yout, lsize, attr);
        break;
      case LineAttribute.DASHED:
        stroke_.drawDashed(g, xout, yout, lsize, attr);
        break;
      case LineAttribute.STROKE:
        stroke_.drawStroke(g, xout, yout , lsize, attr);
        break;
      case LineAttribute.MARK_LINE:
        drawMark(g, xout, yout, lsize, attr);
      default:
      case LineAttribute.SOLID:
        g.drawPolyline(xout, yout, lsize);
      }
    }
  }
  /**
   * Draw a mark at the requested location. This routine is used by LineCartesianGraph and
   * LineKey.
   *
   * @param g Graphics object
   * @param xp horizontal coordinate
   * @param yp vertical coordinate
   * @param attr line attribute
   * @see LineKey
   */
  protected void drawMark(VectorGraphics g, int[] xp, int[] yp,
                          int npoints, LineAttribute attr) {
    Layer ly = cg_.getLayer();
    PlotMark pm = new PlotMark(attr);

    for(int i=0; i < npoints; i++) {
      pm.paintMark(g, ly, xp[i], yp[i]);
    }
  }

  /**
   * Default constructor.
   *
   * @see CartesianGraph
   * @see Graph
   **/
  public LineCartesianRenderer(CartesianGraph cg) {
    this(cg, (SGTLine)null, null);
  }
  /**
   * Construct a LineCartesianRenderer. The default
   * LineAttribute will be used.
   *
   * @param cg the parent CartesianGraph
   * @param data an SGTLine object
   *
   * @see CartesianGraph
   * @see Graph
   **/
  public LineCartesianRenderer(CartesianGraph cg, SGTLine line) {
    this(cg, line, null);
    cg_ = cg;
    line_ = line;
  }
  /**
   * Construct a LineCartesianRenderer.
   *
   * @param cg the parent CartesianGraph
   * @param data an SGTLine
   * @param line the LineAttribute
   * @see CartesianGraph
   * @see Graph
   **/
  public LineCartesianRenderer(CartesianGraph cg, SGTLine line, LineAttribute attr) {
    cg_ = cg;
    line_ = line;
    attr_ = attr;
    if(attr_ != null) attr_.addPropertyChangeListener(this);
    stroke_ = PaneProxy.strokeDrawer;
  }
  /**
   * Construct a LineCartesianRenderer.
   *
   * @param cg the parent CartesianGraph
   * @param col a Collection of SGTLine objects
   * @param line the LineAttribute
   * @see CartesianGraph
   * @see Graph
   **/
  public LineCartesianRenderer(CartesianGraph cg, Collection col, LineAttribute attr) {
    cg_ = cg;
    collection_ = col;
    attr_ = attr;
    if(attr_ != null) attr_.addPropertyChangeListener(this);
    stroke_ = PaneProxy.strokeDrawer;
  }
  /**
   * Render the SGTData. This method should not
   * be directly called.
   *
   * @param g graphics context
   *
   * @see Pane#draw
   */
  public void draw(VectorGraphics g) {
    LineAttribute attr;
    Object line;

    if(cg_.clipping_) {
      int xmin, xmax, ymin, ymax;
      int x, y, width, height;
      if(cg_.xTransform_.isSpace()) {
        xmin = cg_.getXUtoD(cg_.xClipRange_.start);
        xmax = cg_.getXUtoD(cg_.xClipRange_.end);
      } else {
        xmin = cg_.getXUtoD(cg_.tClipRange_.start);
        xmax = cg_.getXUtoD(cg_.tClipRange_.end);
      }
      if(cg_.yTransform_.isSpace()) {
        ymin = cg_.getYUtoD(cg_.yClipRange_.start);
        ymax = cg_.getYUtoD(cg_.yClipRange_.end);
      } else {
        ymin = cg_.getYUtoD(cg_.tClipRange_.start);
        ymax = cg_.getYUtoD(cg_.tClipRange_.end);
      }
      if(xmin < xmax) {
        x = xmin;
        width = xmax - xmin;
      } else {
        x=xmax;
        width = xmin - xmax;
      }
      if(ymin < ymax) {
        y = ymin;
        height = ymax - ymin;
      } else {
        y = ymax;
        height = ymin - ymax;
      }
      g.setClip(x, y, width, height);
    }
    if(attr_ == null) {
      attr = new LineAttribute(LineAttribute.SOLID,
                cg_.getPane().getComponent().getForeground());
    } else {
      attr = attr_;
    }
    g.setColor(attr.getColor());
    if(collection_ == null) {
      drawLine(g, line_, attr);
    } else {
      for(Enumeration li = collection_.elements(); li.hasMoreElements();) {
        line = li.nextElement();
        if(line instanceof SGTLine) {
          drawLine(g, (SGTLine)line, attr);
        }
      }
    }

    //
    // reset clip
    //
    Rectangle rect = cg_.getLayer().getPane().getBounds();
    g.setClip(rect);
  }
  /**
   * Set the LineAttribute. The line appearance is controlled by
   * this object.
   *
   * @param l LineAttribute
   **/
  public void setLineAttribute(LineAttribute l) {
    if(attr_ != null) attr_.removePropertyChangeListener(this);
    attr_ = l;
    if(attr_ != null) attr_.addPropertyChangeListener(this);
  }
  /**
   * Get the LineAttribute.
   *
   * @return LineAttribute
   **/
  public LineAttribute getLineAttribute() {
    return attr_;
  }
  /**
   * Test if a Collection of SGTLine
   * was using to construct this renderer.
   *
   * @return true if Collection was used
   */
  public boolean hasCollection() {
    return (collection_ != null);
  }
  /**
   * Get the Collection of SGTLine objects.
   *
   * @return Collection
   */
  public Collection getCollection() {
    return collection_;
  }
  /**
   * Get the SGTLine object.
   *
   * @return SGTLine
   */
  public SGTLine getLine(){
    return line_;
  }
  /**
   * Get the associated CartesianGraph object.
   *
   * @return CartesianGraph
   */
  public CartesianGraph getCartesianGraph() {
    return cg_;
  }

  public void propertyChange(PropertyChangeEvent evt) {
//      if(Debug.EVENT) {
//        System.out.println("LineCartesianRenderer: " + evt);
//        System.out.println("                       " + evt.getPropertyName());
//      }
    modified("LineCartesianRenderer: propertyChange(" +
             evt.getSource().toString() + "[" +
             evt.getPropertyName() + "]" + ")");
  }
  /**
   * @since 3.0
   */
  public SGTData getDataAt(Point pt) {
    return null;
  }
}

 

Ads help maintain this website.