Javafx FXMLLoader 类

1 java javafx

在我学习 Javafx 时,我已经研究了舞台、场景和场景图(树数据结构)(分支节点、叶节点)等......所以我知道场景图的基础知识,它必须包含一个根节点及其孩子和场景类采用根节点类型的参数,所以我的问题是当我写这一行时:

FXMLLoader load = new FXMLLoader(getClass.getResource("sample.fxml"));
Run Code Online (Sandbox Code Playgroud)

所以我知道在这里我正在创建 FXMLLoader 的一个对象,所以这里实际发生了什么?我只是想知道当我使用 FXMLLoader 加载我的 .fxml 代码时会发生什么......它是否像没有 javafx 或 CSS 的基本方式一样创建一个没有 .fxml 的类?或者这个 FXMLLoader 是否返回根节点及其子节点。总之,我想知道这个 FXMLLoader 是如何工作的。

Jam*_*s_D 5

FXMLLoader loader = new FXMLLoader(getClass().getResource("sample.fxml"));
Run Code Online (Sandbox Code Playgroud)

与任何其他类似的 Java 代码一样,它创建一个FXMLLoader类的实例。您还将其location属性设置为您指定的 URL(基本上表示与sample.fxml您所在的类位于同一包中的资源)。在您调用之前,这不会加载或读取 FXML 文件

loader.load();
Run Code Online (Sandbox Code Playgroud)

当您调用它时,它会读取并解析 FXML 文件,并创建与 FXML 中的元素相对应的对象层次结构。如果 FXML 指定了一个控制器,它会将任何具有fx:id属性的元素注入到@FXML控制器中与该属性同名的带注释的字段中。完成后,它调用控制器的initialize()方法(如果有),并最终返回与 FXML 文件的根元素对应的对象。这个对象也被设置为root属性,所以下面的代码是一样的:

loader.load();
Parent root = loader.getRoot();
Run Code Online (Sandbox Code Playgroud)

Parent root = loader.load();
Run Code Online (Sandbox Code Playgroud)

例如,假设您的 FXML 是

FXMLLoader loader = new FXMLLoader(getClass().getResource("sample.fxml"));
Run Code Online (Sandbox Code Playgroud)

然后

Parent root = loader.load();
Run Code Online (Sandbox Code Playgroud)

导致执行与在加载器中执行以下效果完全相同的代码:

public class FXMLLoader {

    // not a real method, but functionally equivalent to the load()
    // method for the example FXML above:
    public BorderPane load() {

        example.Controller controller = new example.Controller();
        this.controller = controller ;

        BorderPane borderPane = new BorderPane();
        this.root = borderPane ;

        Label header = new Label();
        controller.header = header ;
        borderPane.setTop(header);

        HBox hbox = new HBox();
        Button okButton = new Button();
        okButton.setText("OK");
        controller.okButton = okButton ;
        hbox.getChildren().add(okButton);

        Button cancelButton = new Button();
        cancelButton.setText("Cancel");
        controller.cancelButton = cancelButton ;
        hbox.getChildren().add(cancelButton);

        borderPane.setBottom(hbox);

        controller.initialize();

        return borderPane ;

    }
}
Run Code Online (Sandbox Code Playgroud)

当然,由于是在运行时读取FXML文件,所以这一切其实都是通过反射来完成的,但是代码的效果是一样的。上面的任何实际代码都不存在。

介绍FXML文档提供了FXML文档的完整规范; 显然,这里的帖子太多了,无法涵盖所有​​内容。