我的要求是在Java桌面应用程序中创建动态时间序列堆积面积图。像this的例子,但我想要堆积面积图。我发现了很多堆积面积图的示例,但它们都是基于静态数据的。

最佳答案

这是this示例的修改版本,用于动态时间序列堆积面积图。

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.Random;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JPanel;
import javax.swing.Timer;
import org.jfree.chart.ChartFactory;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.axis.DateAxis;
import org.jfree.chart.axis.DateTickUnit;
import org.jfree.chart.axis.DateTickUnitType;
import org.jfree.chart.axis.NumberAxis;
import org.jfree.chart.plot.PlotOrientation;
import org.jfree.chart.plot.SeriesRenderingOrder;
import org.jfree.chart.plot.XYPlot;
import org.jfree.chart.renderer.xy.StackedXYAreaRenderer;
import org.jfree.data.time.Second;
import org.jfree.data.time.TimePeriod;
import org.jfree.data.time.TimeTableXYDataset;
import org.jfree.ui.ApplicationFrame;
import org.jfree.ui.RefineryUtilities;

public class DTSCTest extends ApplicationFrame {

    private static final String TITLE = "Dynamic Series";
    private static final String START = "Start";
    private static final String STOP = "Stop";
    private static final float MINMAX = 100;
    private static final int COUNT = 15;
    private static final int FAST = 1000;
    private static final int SLOW = FAST * 5;
    private static final Random random = new Random();
    private Timer timer;
    private static final String SERIES1 = "Positive";
    private static final String SERIES2 = "Negative";

    public DTSCTest(final String title) {
        super(title);
        final TimeTableXYDataset dataset = new TimeTableXYDataset();
        JFreeChart chart = createAreaChart(dataset);

        final JButton run = new JButton(STOP);
        run.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                String cmd = e.getActionCommand();
                if (STOP.equals(cmd)) {
                    timer.stop();
                    run.setText(START);
                } else {
                    timer.start();
                    run.setText(STOP);
                }
            }
        });

        final JComboBox combo = new JComboBox();
        combo.addItem("Fast");
        combo.addItem("Slow");
        combo.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                if ("Fast".equals(combo.getSelectedItem())) {
                    timer.setDelay(FAST);
                } else {
                    timer.setDelay(SLOW);
                }
            }
        });

        this.add(new ChartPanel(chart), BorderLayout.CENTER);
        JPanel btnPanel = new JPanel(new FlowLayout());
        btnPanel.add(run);
        btnPanel.add(combo);
        this.add(btnPanel, BorderLayout.SOUTH);

        timer = new Timer(FAST, new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                TimePeriod period = new Second();
                dataset.add(period, randomValue(), SERIES1);
                dataset.add(period, randomValue(), SERIES2);
                if(dataset.getItemCount() > COUNT) {
                    TimePeriod firstItemTime = dataset.getTimePeriod(0);
                    dataset.remove(firstItemTime, SERIES1);
                    dataset.remove(firstItemTime, SERIES2);
                }
            }
        });
    }

    private float randomValue() {
        float randValue = (float) (random.nextGaussian() * MINMAX / 3);
        return randValue < 0 ? -randValue : randValue;
    }

    private JFreeChart createAreaChart(final TimeTableXYDataset dataset) {
        final JFreeChart chart = ChartFactory.createStackedXYAreaChart(
                "Live Sentiment Chart", "Time", "Sentiments", dataset, PlotOrientation.VERTICAL, true, true, false);

        final StackedXYAreaRenderer render = new StackedXYAreaRenderer();
        render.setSeriesPaint(0, Color.RED);
        render.setSeriesPaint(1, Color.GREEN);

        DateAxis domainAxis = new DateAxis();
        domainAxis.setAutoRange(true);
        domainAxis.setDateFormatOverride(new SimpleDateFormat("HH:mm:ss"));
        domainAxis.setTickUnit(new DateTickUnit(DateTickUnitType.SECOND, 1));

        XYPlot plot = (XYPlot) chart.getPlot();
        plot.setRenderer(render);
        plot.setDomainAxis(domainAxis);
        plot.setSeriesRenderingOrder(SeriesRenderingOrder.FORWARD);
        plot.setForegroundAlpha(0.5f);

        NumberAxis rangeAxis = (NumberAxis) plot.getRangeAxis();
        rangeAxis.setNumberFormatOverride(new DecimalFormat("#,###.#"));
        rangeAxis.setAutoRange(true);

        return chart;
    }

    public void start() {
        timer.start();
    }

    public static void main(final String[] args) {
        EventQueue.invokeLater(new Runnable() {

            @Override
            public void run() {
                DTSCTest demo = new DTSCTest(TITLE);
                demo.pack();
                RefineryUtilities.centerFrameOnScreen(demo);
                demo.setVisible(true);
                demo.start();
            }
        });
    }
}

09-18 21:44