/*
* $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.