如何在单独的 GUI 面板中插入 JFreeChart 图表?

How to insert a JFreeChart chart in a panel on a separate GUI?

我想使用 JFreeChart 在 GUI 的特定面板中放置一个图表。我有 2 个 java 文件(一个带有 GUI,另一个用于创建图形),如果可能的话,我希望保持这种方式。

在主 GUI 中,我有一个名为 panelGraph 的面板:

    JPanel panelGraph = new JPanel();
    panelGraph.setBounds(220, 64, 329, 250);
    panelMain.add(panelGraph); //it is inside the main panel
    panelGraph.setLayout(null);

而且我还有一个按钮可以触发图表的出现:

    Button btnGetGraph = new JButton("Draw Graph");
    btnGetGraph.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent arg0) {

            XYLineChart_AWT.runGraph("Cenas", "Titulo", "XLABEL", "YLABEL", panelGraph);

        }
    });
    btnGetGraph.setFont(new Font("Tahoma", Font.BOLD, 13));
    btnGetGraph.setBounds(323, 327, 128, 34);
    panelMain.add(btnGetGraph);

如下,是创建图表的java文件:

  public class XYLineChart_AWT extends JFrame {
  public XYLineChart_AWT( String applicationTitle, String chartTitle, String xLabel, String yLabel, JPanel panel) {

  JFreeChart xylineChart = ChartFactory.createXYLineChart(
     chartTitle ,
     xLabel ,
     yLabel ,
     createDataset() ,
     PlotOrientation.VERTICAL ,
     true , false , false);

  ChartPanel chartPanel = new ChartPanel( xylineChart );
  chartPanel.setPreferredSize( panel.getSize() );


  final XYPlot plot = xylineChart.getXYPlot( );
  plot.setBackgroundPaint(new Color(240, 240, 240));
  XYLineAndShapeRenderer renderer = new XYLineAndShapeRenderer(true,false);
  renderer.setSeriesPaint( 0 , Color.BLACK );
  renderer.setSeriesStroke( 0 , new BasicStroke( 4.0f ) );
  plot.setRenderer( renderer );
  setContentPane(chartPanel);
  panel.add(chartPanel);
  }

private XYDataset createDataset( ){

  final XYSeries seno = new XYSeries ("Sin");
  for(double i=0;i<=1440;i++){
      double temp=Math.sin(i*((2*Math.PI)/640) + Math.PI) + 1;
      seno.add(i/60, temp);
  }


  final XYSeriesCollection dataset = new XYSeriesCollection( );          
  dataset.addSeries(seno);
  return dataset;
}

public static void runGraph(String appTitle, String chartTitle, String xLabel, String yLabel, JPanel panel) {
  XYLineChart_AWT chart = new XYLineChart_AWT(appTitle, chartTitle, xLabel, yLabel, panel);

  chart.pack();
  chart.setVisible(true);
  panel.setVisible(true);

 }
}

这将创建图形并将其放入指定的面板(我通过方法 runGraph() 发送)。 但是,它创建了第二个 JFrame(我知道我做了 chart.setVisible(true),我可以把它设置为 false),我不想在我发送的面板之外创建它。

有没有什么方法可以在不创建额外的 jFrame 的情况下实现它?

P.S.: 另一个问题:setBackgroundPaint() 方法改变了图形显示位置的背面。但是标题和图例所在的部分不会改变。我怎样才能改变这些部分?

感谢您的帮助,

内卡斯

不使用 XYLineChartAWT 构造函数来实例化 ChartPanel,而是将 runGraph() 设为工厂方法,returns 一个 JFreeChart 用于您的主函数GUI 的 ChartPanel。使用图表面板方法 setChart(),它会自动更新您的面板。要更改图表面板的默认大小,请覆盖 getPreferredSize(),如图所示 here

import java.awt.BasicStroke;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.event.ActionEvent;
import javax.swing.AbstractAction;
import javax.swing.JButton;
import javax.swing.JFrame;
import org.jfree.chart.ChartFactory;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.plot.PlotOrientation;
import org.jfree.chart.plot.XYPlot;
import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
import org.jfree.data.xy.XYDataset;
import org.jfree.data.xy.XYSeries;
import org.jfree.data.xy.XYSeriesCollection;

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

    private void display() {
        JFrame f = new JFrame("Test");
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        final ChartPanel chartPanel = new ChartPanel(null);
        f.add(chartPanel);
        f.add(new JButton(new AbstractAction("Draw Graph") {
            @Override
            public void actionPerformed(ActionEvent e) {
                chartPanel.setChart(
                    new XYLineChartAWT().runGraph("Title", "X", "Y"));
            }
        }), BorderLayout.SOUTH);
        f.pack();
        f.setLocationRelativeTo(null);
        f.setVisible(true);
    }

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

public class XYLineChartAWT {

    public JFreeChart runGraph(String chartTitle, String xLabel, String yLabel) {
        JFreeChart xylineChart = ChartFactory.createXYLineChart(
            chartTitle,
            xLabel,
            yLabel,
            createDataset(),
            PlotOrientation.VERTICAL,
            true, false, false);
        final XYPlot plot = xylineChart.getXYPlot();
        plot.setBackgroundPaint(new Color(240, 240, 240));
        XYLineAndShapeRenderer renderer = new XYLineAndShapeRenderer(true, false);
        renderer.setSeriesPaint(0, Color.BLACK);
        renderer.setSeriesStroke(0, new BasicStroke(4.0f));
        plot.setRenderer(renderer);
        return xylineChart;
    }

    private XYDataset createDataset() {
        final XYSeries seno = new XYSeries("Sin");
        for (double i = 0; i <= 1440; i++) {
            double temp = Math.sin(i * ((2 * Math.PI) / 640) + Math.PI) + 1;
            seno.add(i / 60, temp);
        }
        final XYSeriesCollection dataset = new XYSeriesCollection();
        dataset.addSeries(seno);
        return dataset;
    }
}

我建议使用 Nice Application 1,Jfree 修改后的 jar 可以从 NiceApplication1.BlogSpot.Com 下载。转到博客并下载新的 Nice Application 1 Home Stupendous,然后在解压后,将文件夹转到 dist 文件夹并打开 Java Jar Nice Application 1,这样你将得到一个修改过的 jar jfree_NiceApplication1关于如何使用该 jar 的记事本文件。

饼图示例可用。

jar后只需要输入method-

字符串 ao1 = a1.getText(); 字符串 ao2 = a2.getText();

DefaultPieDataset pieDataset = new DefaultPieDataset();

    pieDataset.setValue("earn", new Double(ao1));
    pieDataset.setValue("Allbilltotal", new Double(ao2));

//注意 pieDataset & ch 将是你的变量。

JFreeChart ch = ChartFactory.createPieChart3D("测试", pieDataset, true, true, true);

    PiePlot3D p = (PiePlot3D) ch.getPlot();

// 导入 org.jfree.chart.Nice_Application_1_JPanel;

    Nice_Application_1_JPanel pant = new Nice_Application_1_JPanel(pieDataset);  
    pieDataset = pant.pieDataset;
    pant.PanelApplication1 = jPanel;   
    pant.size = new java.awt.Dimension(200, 200);
    pant.Nice_Application1(ch);

StandardChartTheme theme = new StandardChartTheme(ch.toString());

theme.setTitlePaint( Color.decode( "#4572a7" ) );
theme.setRangeGridlinePaint( Color.decode("#C0C0C0"));
theme.setPlotBackgroundPaint( Color.blue );
theme.setChartBackgroundPaint( Color.BLACK );
theme.setGridBandPaint( Color.red );
theme.setBarPainter(new StandardBarPainter());
theme.setAxisLabelPaint( Color.decode("#666666")  );

theme.apply( ch );


折线图同样可以打字,只有图表面板打字的地方- // 导入 org.jfree.chart.Nice_Application_1_JPanel;

    Nice_Application_1_JPanel pant = new Nice_Application_1_JPanel(pieDataset);  
    pieDataset = pant.pieDataset;
    pant.PanelApplication1 = jPanel;   
    pant.size = new java.awt.Dimension(200, 200);
    pant.Nice_Application1(ch);