2011-08-26 18 views
3

JFreechartでxybubblerendererを使用してカテゴリプロットを実装する方法は? カテゴリごとにいくつかのバブルを示すカテゴリプロットが必要です。 これらのバブルは、バブルのx値を使用してプロットのy軸上に配置され、バブルのy値がその領域を決定します。 したがって、各カテゴリにバブルがあります。プロット上のxの位置はランダムにすることができます。 1つの値はプロット上のyの位置を制御し、別の値は領域を制御します。xybubblerendererでcategoryplotを実装する方法

答えて

0

SymbolAxisとXYBubbleRendererを使用して行うことができます。気泡のx値が範囲[0、n]および[0、n]にあることがシンボル軸に適切なラベルが割り当てられていることが保証されなければならない。ここ

0

そうしないと、あなた自身のCategoryBubbleRendererを記述する必要があり、私はそうしていると、それは動作しますが、私のコード

/** 
* Title: CategoryBubbleRenderer 
* Description: 
* Copyright: Copyright (c) 2001 
* Company: 
* 
* Based on XYBubbleRenderer and BarRenderer 
* 
*/ 



import org.jfree.chart.LegendItem; 
import org.jfree.chart.axis.CategoryAxis; 
import org.jfree.chart.axis.ValueAxis; 
import org.jfree.chart.plot.CategoryPlot; 
import org.jfree.chart.plot.PlotOrientation; 
import org.jfree.chart.renderer.category.AbstractCategoryItemRenderer; 
import org.jfree.chart.renderer.category.CategoryItemRendererState; 
import org.jfree.data.category.CategoryDataset; 
import org.jfree.ui.RectangleEdge; 
import org.jfree.util.PublicCloneable; 

import java.awt.Graphics2D; 
import java.awt.Paint; 
import java.awt.Shape; 
import java.awt.Stroke; 
import java.awt.geom.Ellipse2D; 
import java.awt.geom.Rectangle2D; 

    /** 
    * A renderer that draws a circle at each data point with a diameter that is 
    * determined by the z-value in the dataset. 
    */ 
    public class CategoryBubbleRenderer extends AbstractCategoryItemRenderer 
      implements Cloneable, PublicCloneable/*, Serializable*/ { 

    /** For serialization. */ 
    //public static final long serialVersionUID = -5221991598674249125L; 



    public CategoryBubbleRenderer() { 
     super(); 
     setBaseLegendShape(new Ellipse2D.Double(-4.0,-4.0,8.0,8.0)); 
    } 



    /*public void drawItem(Graphics2D g2, XYItemRendererState state, 
         Rectangle2D dataArea, PlotRenderingInfo info, XYPlot plot, 
         ValueAxis domainAxis, ValueAxis rangeAxis, XYDataset dataset, 
         int series, int item, CrosshairState crosshairState, int pass) {*/ 
    public void drawItem(Graphics2D g2, 
         CategoryItemRendererState state, 
         Rectangle2D dataArea, 
         CategoryPlot plot, 
         CategoryAxis domainAxis, 
         ValueAxis rangeAxis, 
         CategoryDataset dataset, 
         int row, 
         int column, 
         int pass) { 



     // nothing is drawn if the row index is not included in the list with 
     // the indices of the visible rows... 
     int visibleRow = state.getVisibleSeriesIndex(row); 
     if (visibleRow < 0) { 
     return; 
     } 
     // nothing is drawn for null values... 
     Number dataValue = dataset.getValue(row, column); 
     if (dataValue == null) { 
     return; 
     } 
     int series = row; 
     int item = column; 

     PlotOrientation orientation = plot.getOrientation(); 

     // get the data point... 
     //double x = dataset.getXValue(series, item); 
     //double y = dataset.getYValue(series, item); 
     double y = dataValue.doubleValue(); 
     double z = Double.NaN; 


     double d1 = rangeAxis.getUpperBound(); 
     double d2 = rangeAxis.getLowerBound(); 
     z = (d2-d1)/10;//just an attempt to calculate a good default value 

     if (!Double.isNaN(z)) { 
     RectangleEdge domainAxisLocation = plot.getDomainAxisEdge(); 
     RectangleEdge rangeAxisLocation = plot.getRangeAxisEdge(); 
     //double transX = domainAxis.valueToJava2D(x, dataArea, domainAxisLocation); 
     //double transX = domainAxis.getCategoryStart(column, getColumnCount(), dataArea, plot.getDomainAxisEdge()); 
     double transX = domainAxis.getCategoryMiddle(column, getColumnCount(), 
       dataArea, plot.getDomainAxisEdge()) - state.getBarWidth() 
       /2.0; 
     double transY = rangeAxis.valueToJava2D(y, dataArea, rangeAxisLocation); 


     double zero2 = rangeAxis.valueToJava2D(0.0, dataArea, 
       rangeAxisLocation); 
     double transRange = zero2 - rangeAxis.valueToJava2D(z, dataArea, 
       rangeAxisLocation); 
     double transDomain = transRange; 


     transDomain = Math.abs(transDomain); 
     transRange = Math.abs(transRange); 
     Ellipse2D circle = null; 
     if (orientation == PlotOrientation.VERTICAL) { 
      circle = new Ellipse2D.Double(transX - transDomain/2.0, 
        transY - transRange/2.0, transDomain, transRange); 
     } 
     else if (orientation == PlotOrientation.HORIZONTAL) { 
      circle = new Ellipse2D.Double(transY - transRange/2.0, 
        transX - transDomain/2.0, transRange, transDomain); 
     } 
     g2.setPaint(getItemPaint(series, item)); 
     g2.fill(circle); 
     g2.setStroke(getItemOutlineStroke(series, item)); 
     g2.setPaint(getItemOutlinePaint(series, item)); 
     g2.draw(circle); 

     if (isItemLabelVisible(series, item)) { 
      if (orientation == PlotOrientation.VERTICAL) { 
      drawItemLabel(g2, orientation, dataset, series, item, 
        transX, transY, false); 
      } 
      else if (orientation == PlotOrientation.HORIZONTAL) { 
      drawItemLabel(g2, orientation, dataset, series, item, 
        transY, transX, false); 
      } 
     } 

     // add an entity if this info is being collected 

     /*EntityCollection entities = null; 
     if (info != null) { 
      entities = info.getOwner().getEntityCollection(); 
      if (entities != null && circle.intersects(dataArea)) { 
      addEntity(entities, circle, dataset, series, item, 
        circle.getCenterX(), circle.getCenterY()); 
      } 
     } 

     int domainAxisIndex = plot.getDomainAxisIndex(domainAxis); 
     int rangeAxisIndex = plot.getRangeAxisIndex(rangeAxis); 
     updateCrosshairValues(crosshairState, x, y, domainAxisIndex, 
       rangeAxisIndex, transX, transY, orientation); 
     */ 
     } 

    } 


    /** 
    * Returns a legend item for the specified series. The default method 
    * is overridden so that the legend displays circles for all series. 
    * 
    * @param datasetIndex the dataset index (zero-based). 
    * @param series the series index (zero-based). 
    * 
    * @return A legend item for the series. 
    */ 
    public LegendItem getLegendItem(int datasetIndex, int series) { 
     LegendItem result = null; 
     CategoryPlot plot = getPlot(); 
     if (plot == null) { 
     return null; 
     } 

     CategoryDataset dataset = plot.getDataset(datasetIndex); 
     if (dataset != null) { 
     if (getItemVisible(series, 0)) { 
      String label = getLegendItemLabelGenerator().generateLabel(
        dataset, series); 
      String description = label; 
      String toolTipText = null; 
      if (getLegendItemToolTipGenerator() != null) { 
      toolTipText = getLegendItemToolTipGenerator().generateLabel(
        dataset, series); 
      } 
      String urlText = null; 
      if (getLegendItemURLGenerator() != null) { 
      urlText = getLegendItemURLGenerator().generateLabel(
        dataset, series); 
      } 
      Shape shape = lookupLegendShape(series); 
      Paint paint = lookupSeriesPaint(series); 
      Paint outlinePaint = lookupSeriesOutlinePaint(series); 
      Stroke outlineStroke = lookupSeriesOutlineStroke(series); 
      result = new LegendItem(label, description, toolTipText, 
        urlText, shape, paint, outlineStroke, outlinePaint); 
      result.setLabelFont(lookupLegendTextFont(series)); 
      Paint labelPaint = lookupLegendTextPaint(series); 
      if (labelPaint != null) { 
      result.setLabelPaint(labelPaint); 
      } 
      result.setDataset(dataset); 
      result.setDatasetIndex(datasetIndex); 
      //result.setSeriesKey(dataset.getSeriesKey(series)); 
      result.setSeriesKey(dataset.getRowKey(series)); 
      result.setSeriesIndex(series); 
     } 
     } 
     return result; 
    } 


    public boolean equals(Object obj) { 
     if (obj == this) { 
     return true; 
     } 
     if (!(obj instanceof CategoryBubbleRenderer)) { 
     return false; 
     } 
     CategoryBubbleRenderer that = (CategoryBubbleRenderer) obj; 
     return super.equals(obj); 
    } 


    public Object clone() throws CloneNotSupportedException { 
     return super.clone(); 
    } 

    } 
関連する問題