在 JFreechart 中使用多个渲染器

Using Multiple Renderers in JFreechart

我有要表示为盒须图的数据,并且为此设置了类别图。但是,此外,我想添加一个折线图,显示每个数据点的平均值的累积。

现在我的代码是这样的

DefaultBoxAndWhiskerCategoryDataset dataSet = new DefaultBoxAndWhiskerCategoryDataset();
int i = 0;
for (List<Integer> categoryList : categoryLists) {
    dataSet.add(categoryList, i, "BoxAndWhiskers");
    i++;
}
BoxAndWhiskerRenderer renderer = new BoxAndWhiskerRenderer();

double sum = 0;
i = 0;
DefaultCategoryDataset averageDataSet = new DefaultCategoryDataset();
for (double average : averages) {
    sum += average;
    averageDataSet.add(sum, i, "Average");
    i++;
}
LineAndShapeRenderer lineAndShapeRenderer = new LineAndShapeRenderer();


CategoryAxis xAxis = new CategoryAxis("Type");
NumberAxis yAxis = new NumberAxis("Value");
CategoryPlot plot = new CategoryPlot(dataSet, xAxis, yAxis, renderer);

plot.setDataset(1, averageDataSet);
plot.setRenderer(1, lineAndShapeRenderer);

JFreeChart chart = new JFreeChart(
    "Box-and-Whisker",
    new Font("SansSerif", Font.BOLD, 14),
    plot,
    true
);

BufferedImage outputImage = chart.createBufferedImage(800, 600);

ImageIO.write(outputImage, "png", new File("output.png"));

但是,当我查看我的 output.png 时,我只看到了框和胡须渲染(没有线条和形状图)。

我还需要做些什么才能在输出图像中同时使用渲染器和数据集吗?此外,是否有更好的方法来为我的方框和须线图中的平均值获取累积线?

I'm trying to figure out how to lay the points on top of the box and whiskers points properly.

如图所示 here for CategoryDataset,每个 rowKey 是一个系列,每个 columnKey 是系列中的一个元素。在下面的示例中,catData"Mean" 行包含 boxData 中每个 columnKey 的条目。使用setDatasetRenderingOrder()指定DatasetRenderingOrder.

import java.awt.Dimension;
import java.awt.EventQueue;
import java.util.Arrays;
import javax.swing.JFrame;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.axis.CategoryAxis;
import org.jfree.chart.axis.NumberAxis;
import org.jfree.chart.plot.CategoryPlot;
import org.jfree.chart.plot.DatasetRenderingOrder;
import org.jfree.chart.renderer.category.BoxAndWhiskerRenderer;
import org.jfree.chart.renderer.category.LineAndShapeRenderer;
import org.jfree.data.category.DefaultCategoryDataset;
import org.jfree.data.statistics.DefaultBoxAndWhiskerCategoryDataset;

/**
 * @see 
 */
public class Test {

    private void display() {
        JFrame f = new JFrame("Test");
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        DefaultBoxAndWhiskerCategoryDataset boxData = new DefaultBoxAndWhiskerCategoryDataset();
        boxData.add(Arrays.asList(30, 36, 46, 55, 65, 76, 81, 80, 71, 59, 44, 34), "Planet", "Endor");
        boxData.add(Arrays.asList(22, 25, 34, 44, 54, 63, 69, 67, 59, 48, 38, 28), "Planet", "Hoth");
        BoxAndWhiskerRenderer boxRenderer = new BoxAndWhiskerRenderer();
        DefaultCategoryDataset catData = new DefaultCategoryDataset();
        catData.addValue(boxData.getMeanValue(0, 0), "Mean", boxData.getColumnKey(0));
        catData.addValue(boxData.getMeanValue(0, 1), "Mean", boxData.getColumnKey(1));
        LineAndShapeRenderer lineRenderer = new LineAndShapeRenderer();
        CategoryAxis xAxis = new CategoryAxis("Type");
        NumberAxis yAxis = new NumberAxis("Value");
        yAxis.setAutoRangeIncludesZero(false);
        CategoryPlot plot = new CategoryPlot(boxData, xAxis, yAxis, boxRenderer);
        plot.setDataset(1, catData);
        plot.setRenderer(1, lineRenderer);
        plot.setDatasetRenderingOrder(DatasetRenderingOrder.FORWARD);
        JFreeChart chart = new JFreeChart("Test", JFreeChart.DEFAULT_TITLE_FONT, plot, true);
        f.add(new ChartPanel(chart){
            @Override
            public Dimension getPreferredSize() {
                return new Dimension(320, 480);
            }
        });
        f.pack();
        f.setLocationRelativeTo(null);
        f.setVisible(true);
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new Test()::display);
    }
}