axislabellayout.java
来自「用applet实现很多应用小程序」· Java 代码 · 共 598 行 · 第 1/2 页
JAVA
598 行
package prefuse.action.layout;
import java.awt.geom.Rectangle2D;
import java.text.NumberFormat;
import java.util.Iterator;
import java.util.logging.Logger;
import prefuse.Constants;
import prefuse.data.Schema;
import prefuse.data.query.ObjectRangeModel;
import prefuse.data.tuple.TupleSet;
import prefuse.data.util.Index;
import prefuse.util.MathLib;
import prefuse.util.PrefuseLib;
import prefuse.util.ui.ValuedRangeModel;
import prefuse.visual.VisualItem;
import prefuse.visual.VisualTable;
/**
* Layout Action that positions axis grid lines and labels for a given
* range model.
*
* @author <a href="http://jheer.org">jeffrey heer</a>
*/
public class AxisLabelLayout extends Layout {
public static final String FRAC = "frac";
public static final String LABEL = "_label";
public static final String VALUE = "_value";
private AxisLayout m_layout; // pointer to matching layout, if any
private ValuedRangeModel m_model;
private double m_lo, m_hi, m_prevlo, m_prevhi;
private NumberFormat m_nf = NumberFormat.getInstance();
private int m_axis;
private boolean m_asc = true;
private int m_scale = Constants.LINEAR_SCALE;
private double m_spacing; // desired spacing between axis labels
/**
* Create a new AxisLabelLayout layout.
* @param group the data group of the axis lines and labels
* @param axis the axis type, either {@link prefuse.Constants#X_AXIS}
* or {@link prefuse.Constants#Y_AXIS}.
* @param values the range model that defines the span of the axis
*/
public AxisLabelLayout(String group, int axis, ValuedRangeModel values)
{
this(group, axis, values, null);
}
/**
* Create a new AxisLabelLayout layout.
* @param group the data group of the axis lines and labels
* @param axis the axis type, either {@link prefuse.Constants#X_AXIS}
* or {@link prefuse.Constants#Y_AXIS}.
* @param values the range model that defines the span of the axis
* @param bounds the layout bounds within which to place the axis marks
*/
public AxisLabelLayout(String group, int axis, ValuedRangeModel values,
Rectangle2D bounds)
{
super(group);
if ( bounds != null )
setLayoutBounds(bounds);
m_model = values;
m_axis = axis;
m_spacing = 50;
}
/**
* Create a new AxisLabelLayout layout.
* @param group the data group of the axis lines and labels
* @param layout an {@link AxisLayout} instance to model this layout after.
* The axis type and range model of the provided instance will be used.
*/
public AxisLabelLayout(String group, AxisLayout layout) {
this(group, layout, null, 50);
}
/**
* Create a new AxisLabelLayout layout.
* @param group the data group of the axis lines and labels
* @param layout an {@link AxisLayout} instance to model this layout after.
* The axis type and range model of the provided instance will be used.
* @param bounds the layout bounds within which to place the axis marks
*/
public AxisLabelLayout(String group, AxisLayout layout, Rectangle2D bounds) {
this(group, layout, bounds, 50);
}
/**
* Create a new AxisLabelLayout layout.
* @param group the data group of the axis lines and labels
* @param layout an {@link AxisLayout} instance to model this layout after.
* The axis type and range model of the provided instance will be used.
* @param bounds the layout bounds within which to place the axis marks
* @param spacing the minimum spacing between axis labels
*/
public AxisLabelLayout(String group, AxisLayout layout, Rectangle2D bounds,
double spacing)
{
super(group);
if ( bounds != null )
setLayoutBounds(bounds);
m_layout = layout;
m_model = layout.getRangeModel();
m_axis = layout.getAxis();
m_scale = layout.getScale();
m_spacing = spacing;
}
// ------------------------------------------------------------------------
/**
* Get the formatter used to format labels for numerical values.
* @return the <code>NumberFormat</code> used to format numerical labels.
*/
public NumberFormat getNumberFormat() {
return m_nf;
}
/**
* Set the formatter used to format labels for numerical values.
* @param nf the <code>NumberFormat</code> used to format numerical labels.
*/
public void setNumberFormat(NumberFormat nf) {
m_nf = nf;
}
/**
* Get the required minimum spacing between axis labels.
* @return the axis label spacing
*/
public double getSpacing() {
return m_spacing;
}
/**
* Set the required minimum spacing between axis labels.
* @param spacing the axis label spacing to use
*/
public void setSpacing(double spacing) {
m_spacing = spacing;
}
/**
* Returns the scale type used for the axis. This setting only applies
* for numerical data types (i.e., when axis values are from a
* <code>NumberValuedRange</code>).
* @return the scale type. One of
* {@link prefuse.Constants#LINEAR_SCALE},
* {@link prefuse.Constants#SQRT_SCALE}, or
* {@link Constants#LOG_SCALE}.
*/
public int getScale() {
return m_scale;
}
/**
* Sets the scale type used for the axis. This setting only applies
* for numerical data types (i.e., when axis values are from a
* <code>NumberValuedRange</code>).
* @param scale the scale type. One of
* {@link prefuse.Constants#LINEAR_SCALE},
* {@link prefuse.Constants#SQRT_SCALE}, or
* {@link Constants#LOG_SCALE}.
*/
public void setScale(int scale) {
if ( scale < 0 || scale >= Constants.SCALE_COUNT ) {
throw new IllegalArgumentException(
"Unrecognized scale type: "+scale);
}
m_scale = scale;
}
/**
* Indicates if the axis values should be presented in ascending order
* along the axis.
* @return true if data values increase as pixel coordinates increase,
* false if data values decrease as pixel coordinates increase.
*/
public boolean isAscending() {
return m_asc;
}
/**
* Sets if the axis values should be presented in ascending order
* along the axis.
* @param asc true if data values should increase as pixel coordinates
* increase, false if data values should decrease as pixel coordinates
* increase.
*/
public void setAscending(boolean asc) {
m_asc = asc;
}
/**
* Sets the range model used to layout this axis.
* @param model the range model
*/
public void setRangeModel(ValuedRangeModel model) {
m_model = model;
}
// ------------------------------------------------------------------------
/**
* @see prefuse.action.GroupAction#run(double)
*/
public void run(double frac) {
if ( m_model == null && m_layout != null )
m_model = m_layout.getRangeModel();
if ( m_model == null ) {
Logger.getLogger(this.getClass().getName())
.warning("Axis labels missing a range model.");
return;
}
VisualTable labels = getTable();
// check the axis label group to see if we can get a
// more precise reading of the previous scale
Double dfrac = (Double)labels.getClientProperty(FRAC);
double fr = dfrac==null ? 1.0 : dfrac.doubleValue();
m_prevlo = m_prevlo + fr*(m_lo-m_prevlo);
m_prevhi = m_prevhi + fr*(m_hi-m_prevhi);
// now compute the layout
if ( m_model instanceof ObjectRangeModel )
{ // ordinal layout
// get the current high and low values
m_lo = m_model.getValue();
m_hi = m_lo + m_model.getExtent();
// compute the layout
ordinalLayout(labels);
}
else
{ // numerical layout
// get the current high and low values
m_lo = ((Number)m_model.getLowValue()).doubleValue();
m_hi = ((Number)m_model.getHighValue()).doubleValue();
// compute the layout
switch ( m_scale ) {
case Constants.LOG_SCALE:
logLayout(labels);
break;
case Constants.SQRT_SCALE:
sqrtLayout(labels);
break;
case Constants.LINEAR_SCALE:
default:
linearLayout(labels);
}
}
// get rid of any labels that are no longer being used
garbageCollect(labels);
}
// ------------------------------------------------------------------------
// Quantitative Axis Layout
/**
* Calculates a quantitative, linearly scaled layout.
*/
protected void linearLayout(VisualTable labels) {
Rectangle2D b = getLayoutBounds();
double breadth = getBreadth(b);
double span = m_hi-m_lo;
double pspan = m_prevhi-m_prevlo;
double vlo = 0;
if ( m_lo >= 0 ) {
vlo = Math.pow(10, Math.floor(MathLib.log10(m_lo)));
} else {
vlo = -Math.pow(10, 1+Math.floor(MathLib.log10(-m_lo)));
}
//if ( vlo == 10 || vlo == 1 || vlo == 0.1 ) vlo = 0;
// mark previously visible labels
Iterator iter = labels.tuples();
while ( iter.hasNext() ) {
VisualItem item = (VisualItem)iter.next();
reset(item);
double v = item.getDouble(VALUE);
double x = span==0 ? 0 : ((v-m_lo)/span)*breadth;
set(item, x, b);
}
Index index = labels.index(VALUE);
double step = getLinearStep(span, span==0 ? 0 : breadth/span);
if ( step == 0 ) step = 1;
int r;
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?