Java 实时更新饼图

Java 实时更新饼图,java,javafx,javafx-2,javafx-8,Java,Javafx,Javafx 2,Javafx 8,我想创建一个非常有用且简单的实时更新饼图。例如: import javafx.application.Application; import javafx.collections.FXCollections; import javafx.collections.ObservableList; import javafx.event.EventHandler; import javafx.scene.Group; import javafx.scene.Scene; import javafx.s

我想创建一个非常有用且简单的实时更新饼图。例如:

import javafx.application.Application;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.event.EventHandler;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.chart.PieChart;
import javafx.scene.control.Label;
import javafx.scene.input.MouseEvent;
import javafx.scene.paint.Color;
import javafx.stage.Stage;


public class MainApp extends Application {

    @Override
    public void start(Stage stage) {
        Scene scene = new Scene(new Group());
        stage.setTitle("Imported Fruits");
        stage.setWidth(500);
        stage.setHeight(500);

        ObservableList<PieChart.Data> pieChartData =
                FXCollections.observableArrayList(
                new PieChart.Data("Grapefruit", 13),
                new PieChart.Data("Oranges", 25),
                new PieChart.Data("Plums", 10),
                new PieChart.Data("Pears", 22),
                new PieChart.Data("Apples", 30));

        final PieChart chart = new PieChart(pieChartData);
        chart.setTitle("Imported Fruits");
        final Label caption = new Label("");
        caption.setTextFill(Color.DARKORANGE);
        caption.setStyle("-fx-font: 24 arial;");

        for (final PieChart.Data data : chart.getData()) {
            data.getNode().addEventHandler(MouseEvent.MOUSE_PRESSED,
                    new EventHandler<MouseEvent>() {
                        @Override public void handle(MouseEvent e) {
                            caption.setTranslateX(e.getSceneX());
                            caption.setTranslateY(e.getSceneY());
                            caption.setText(String.valueOf(data.getPieValue())
                                + "%");
                        }
                    });
        }

        ((Group) scene.getRoot()).getChildren().addAll(chart, caption);
        stage.setScene(scene);
        stage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }
}

您能告诉我如何编辑代码以使实时更新更易于使用吗?

这是一篇关于使用属性和绑定的介绍性文章


据我所知,所有用于建立
PieChart
的类,比如
PieChart.Data
observelist
都已经设计好了,以便在发生变化时更新
PieChart
,无论是列表本身还是
数据
对象中的值。看看这是怎么做到的。但是您不需要为
PieChart
编写自己的绑定

下面的代码应该满足您的要求。使用
addData(字符串名称,双值)
为饼图创建一个新的
Data
对象,或者像方法的第一个参数一样更新一个具有相同
名称的现有对象。更改列表(添加了新的
数据
对象)或更改了
数据
对象时,
图表将自动播放动画

 //adds new Data to the list
public void naiveAddData(String name, double value)
{
    pieChartData.add(new Data(name, value));
}

//updates existing Data-Object if name matches
public void addData(String name, double value)
{
    for(Data d : pieChartData)
    {
        if(d.getName().equals(name))
        {
            d.setPieValue(value);
            return;
        }
    }
    naiveAddData(name, value);
}

为了防止有人感到极度失落,并且不确定如何实现denhackl的答案,这里有一个他试图解释的工作版本

import javafx.application.Application;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.event.EventHandler;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.chart.PieChart;
import javafx.scene.control.Label;
import javafx.scene.input.MouseEvent;
import javafx.scene.paint.Color;
import javafx.stage.Stage;


public class LivePie extends Application {

    ObservableList<PieChart.Data> pieChartData;

    @Override
    public void start(Stage stage) {
        Scene scene = new Scene(new Group());
        stage.setTitle("Imported Fruits");
        stage.setWidth(500);
        stage.setHeight(500);

       this.pieChartData =
                FXCollections.observableArrayList();

       addData("Test", 5.1);
       addData("Test2", 15.1);
       addData("Test3", 3.1);
       addData("Test1", 4.9);
       addData("Test2", 15.1);
       addData("Test3", 2.1);
       addData("Test5", 20.1);


        final PieChart chart = new PieChart(pieChartData);
        chart.setTitle("Imported Fruits");
        final Label caption = new Label("");
        caption.setTextFill(Color.DARKORANGE);
        caption.setStyle("-fx-font: 24 arial;");



        ((Group) scene.getRoot()).getChildren().addAll(chart, caption);
        stage.setScene(scene);
        stage.show();
    }

    public void naiveAddData(String name, double value)
    {
        pieChartData.add(new javafx.scene.chart.PieChart.Data(name, value));
    }

    //updates existing Data-Object if name matches
    public void addData(String name, double value)
    {
        for(javafx.scene.chart.PieChart.Data d : pieChartData)
        {
            if(d.getName().equals(name))
            {
                d.setPieValue(value);
                return;
            }
        }
        naiveAddData(name, value);
    }

    public static void main(String[] args) {
        launch(args);
    }


}
导入javafx.application.application;
导入javafx.collections.FXCollections;
导入javafx.collections.ObservableList;
导入javafx.event.EventHandler;
导入javafx.scene.Group;
导入javafx.scene.scene;
导入javafx.scene.chart.PieChart;
导入javafx.scene.control.Label;
导入javafx.scene.input.MouseEvent;
导入javafx.scene.paint.Color;
导入javafx.stage.stage;
公共类LivePie扩展了应用程序{
可观测数据;
@凌驾
公众假期开始(阶段){
场景=新场景(新组());
阶段.设定名称(“进口水果”);
舞台设置宽度(500);
舞台设置高度(500);
这是一个图表数据=
FXCollections.observableArrayList();
添加数据(“测试”,5.1);
添加数据(“测试2”,15.1);
添加数据(“测试3”,3.1);
添加数据(“测试1”,4.9);
添加数据(“测试2”,15.1);
添加数据(“测试3”,2.1);
添加数据(“测试5”,20.1);
最终PieChart图表=新PieChart(PieChart数据);
图表.setTitle(“进口水果”);
最终标签标题=新标签(“”);
标题.setTextFill(Color.DARKORANGE);
标题.setStyle(“-fx字体:24 arial;”);
((组)scene.getRoot()).getChildren().addAll(图表,标题);
舞台场景;
stage.show();
}
公共数据(字符串名称,双精度值)
{
添加(新的javafx.scene.chart.PieChart.Data(名称、值));
}
//如果名称匹配,则更新现有数据对象
public void addData(字符串名称,双精度值)
{
for(javafx.scene.chart.PieChart.Data d:pieChartData)
{
如果(d.getName().equals(name))
{
d、 setPieValue(值);
返回;
}
}
数据(名称、值);
}
公共静态void main(字符串[]args){
发射(args);
}
}

非常感谢主题的创建者和提供的答案

到目前为止,你尝试了什么?你在尝试的时候遇到了什么问题?我投了赞成票,因为这个想法很有趣,但这个问题太过分了。最有可能的情况是,您应该在图表上设置新值,然后重新布局整个内容。但是我不知道JavaFXAPI。你能粘贴完整的代码吗?这个
pieChartData
不正确。我想你可以自己做。将
pieChartData
声明为类
MainApp
的新属性。这只是对代码的一个小改动。
import javafx.application.Application;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.event.EventHandler;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.chart.PieChart;
import javafx.scene.control.Label;
import javafx.scene.input.MouseEvent;
import javafx.scene.paint.Color;
import javafx.stage.Stage;


public class LivePie extends Application {

    ObservableList<PieChart.Data> pieChartData;

    @Override
    public void start(Stage stage) {
        Scene scene = new Scene(new Group());
        stage.setTitle("Imported Fruits");
        stage.setWidth(500);
        stage.setHeight(500);

       this.pieChartData =
                FXCollections.observableArrayList();

       addData("Test", 5.1);
       addData("Test2", 15.1);
       addData("Test3", 3.1);
       addData("Test1", 4.9);
       addData("Test2", 15.1);
       addData("Test3", 2.1);
       addData("Test5", 20.1);


        final PieChart chart = new PieChart(pieChartData);
        chart.setTitle("Imported Fruits");
        final Label caption = new Label("");
        caption.setTextFill(Color.DARKORANGE);
        caption.setStyle("-fx-font: 24 arial;");



        ((Group) scene.getRoot()).getChildren().addAll(chart, caption);
        stage.setScene(scene);
        stage.show();
    }

    public void naiveAddData(String name, double value)
    {
        pieChartData.add(new javafx.scene.chart.PieChart.Data(name, value));
    }

    //updates existing Data-Object if name matches
    public void addData(String name, double value)
    {
        for(javafx.scene.chart.PieChart.Data d : pieChartData)
        {
            if(d.getName().equals(name))
            {
                d.setPieValue(value);
                return;
            }
        }
        naiveAddData(name, value);
    }

    public static void main(String[] args) {
        launch(args);
    }


}