1

因此,我当然会直接创建一个简单的示例。

public class Main extends Application {

URL bla = getClass().getResource("/sample.fxml");

@Override
public void start(Stage primaryStage) throws Exception{
    //If you get weird errors: http://zenjava.com/javafx/maven/fix-classpath.html
        //but not actually my issue. Example displays fine in intellij.

    try {

        FXMLLoader loader = new FXMLLoader(bla);
        Parent root = loader.load(bla);

        primaryStage.setTitle("Hello World");
        primaryStage.setScene(new Scene(root));
        primaryStage.show();

        Controller controller = loader.<Controller>getController() ;
        assert(controller != null);
        controller.getLabel().setText("Kaboom!");
    } catch (Exception e) {
        // Exception gets thrown if the fxml file could not be loaded
        e.printStackTrace();
    }
}

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

我已阅读https://forums.oracle.com/thread/2317621 并且我知道顶部锚窗格需要指向我在 fxml 中的控制器。

<AnchorPane id="AnchorPane" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity"      minWidth="-Infinity" prefHeight="600.0" prefWidth="800.0" xmlns:fx="http://javafx.com/fxml" fx:controller="mypackage.Controller">
  <children>

它显示得很好,但是断言被捕获,因为没有控制器!
initialize()确实运行,这意味着创建了以下控制器!

public class Controller {

@FXML
private Label label ;

public Label getLabel()
{
    return label ;
}

@FXML
public void initialize()
{
    System.out.println("Swear a lot!");
    System.out.println(label);
}
}

如果您正在观看此内容,请向 FX 开发人员说明:

如果您要在指向类的 xml 文件中包含弱耦合字符串,我真的希望 .load() 如果找不到它正在寻找的内容,它会抛出一个有意义的运行时异常。没有任何理由返回 null ......理想情况下,从 GWT 小部件团队获取一个页面,并在您的程序实际运行之前让预编译器失败,或者在流行的 IDE 中使用最好的插件。

此外,您真的应该尽快为 JavaFX 启动并运行 JavaFX 的源代码(将其放入 Maven 中),这样它就可以自动下载,我可以自己找出问题所在。太难。

我敢肯定我做错了一些简单的事情,但是这些工具应该可以使我摆脱困境。

4

2 回答 2

6

为了能够像这样得到控制器类

Controller controller = loader.<Controller>getController();

需要调用实例化的FXMLLoader的加载方法,即
代替

Parent root = loader.load(bla);

这里 load() 是静态的,调用

Parent root = (Parent) loader.load(bla.openStream());

但我同意它应该有据可查。

于 2013-08-23T13:28:21.880 回答
1

Uluk 的回答已经解决了问题中提出的主要问题。

这个“答案”只解决辅助问题。

我真的希望 .load() 如果找不到它正在寻找的东西,它会抛出一个有意义的运行时异常。

JavaFX 问题跟踪器中记录API 更改、异常消息修改或文档改进请求的调整问题。在这种情况下,它听起来像是一个文档和 API 使用说明。

另请注意,使用 FXML 文件是可选的。可以在 FXML 中完成的所有操作也可以直接在 Java API 中完成,因此您不需要“在指向类的 xml 文件中具有弱耦合字符串”。

如果您确实有这种弱字符串耦合,一些开发环境,例如Idea 12.1+,将为您运行增量验证、检查、错误语法突出显示和 fxml/代码导航。因此,当前的工具可以在一定程度上帮助您避免一些陷阱(尽管可能不适用于您帖子中提到的特定问题)。Java 框架在 IDE 中与 XML 集成已经有很长时间了,这并不是完美的结合,但是 IDE 开发人员已经非常擅长解决一些最严重的痛点。

此外,您真的应该尽快为 JavaFX 启动并运行 JavaFX 的源代码(将其放入 Maven 中),这样它就可以自动下载,我可以自己找出问题所在。

在 JavaFX 问题跟踪器中,存在对 JavaFX 源代码与 JDK 捆绑的现有请求。该问题计划在 Java 8 发布之前实施。该解决方案不适用于早期的 JavaFX 版本,例如 JavaFX 2.2,因为这些版本大多是封闭源代码。

同时,您可能对从 open-jfx 存储库获取源代码的替代解决方案感兴趣,该解决方案在以下问题的答案中提供:JavaFX source code not shown 。

我确实看过 openJDK,但它看起来像是一项任务。

可以理解 - 使用 open-jfx 存储库中的源代码比捆绑 src.zip 更复杂,该 src.zip 包含在 JDK 发行版中,并被新的 IDE 项目自动引用(与 IDE 使用当前 jdk src.zip 的方式相同) )。

我确信在 Java 8 发布时,将实现从主要 IDE 轻松访问 JavaFX 源的 JavaFX 源捆绑。

我不认为将 JavaFX 库和代码放在 maven 存储库中是一个好的解决方案,因为这些库本身现在构成了 JDK 发行版的一部分。JDK 发行版中的其他代码不包含在 maven 存储库中。也许当 Java 9 出现模块化 JDK 方法时,这可能会改变。

除非 Scene Builder 可以创建/修改 java 代码,否则您不使用 xml 的建议并不令人心酸。

不建议使用 FXML - 对于那些可能不喜欢将每周类型化字符串语言与强类型化 Java 语言匹配的基​​于 XML 的方法的人来说,它只是一种替代方法。

我曾经就 FXML 的使用提出的唯一真正建议是,当您第一次以 (IMO) 身份开始 JavaFX 开发时,不要使用 FXML 和 SceneBuilder:

  1. 在学习 JavaFX 工具包的原理时,只使用 API 效率更高。
  2. 能学的东西比较少。
  3. 您没有一个 GUI 工具可以自动生成您可能还不知道如何正确使用的复杂 UI 元素。
  4. 您不必担心 FXML 加载器的工作方式有些复杂、令人困惑且文档记录不充分。
  5. 您不必担心在 FXML 文件中的 UI 元素和 Java 代码之间保持同步映射。
  6. 您被迫从低级 API 角度理解布局和场景图结构。

如果您正在专门评估 UI 技术以允许分离关注点,以便布局设计人员可以加入团队......那么您的关注点列表非常无声

当然,从跨职能团队的角度对 JavaFX 技术的任何评估自然会涉及对 FXML 和 SceneBuilder 使用的评估。

为新的 JavaFX 开发人员提供的仅使用 API 执行初始 JavaFX 开发的理由并不是真正值得关注的问题。它们构成了我对为什么开发人员(而不是跨职能评估人员)可能只在最初学习 JavaFX 技术时才坚持使用 API 的看法。

我不认为将其作为文档问题是错误的,因为它对用户的期望过高。

这是一种可以理解的情绪。也许弃用静态 FXMLLoader 加载方法可能是一种更好的方法来防止出现此类用户错误的可能性。

无论如何,请求更改文档或实现的最直接方法是在JavaFX 问题跟踪器中创建问题请求,并在openjfx-dev 邮件列表中与开发人员讨论该问题。JavaFX 目前正在积极开发中,因此这样的请求(如果及时提出)有合理的机会在 Java 8 时间范围内实现。

如果您还有其他辅助问题,我建议您将它们发布到最能处理这些问题类型的论坛(例如Oracle JavaFX 论坛openjfx-dev JavaFX 邮件列表)。

于 2013-08-23T16:45:11.213 回答