【问题标题】:Why I'm getting javafx.fxml.LoadException even the path of the fxml file is correct为什么我得到 javafx.fxml.LoadException 即使 fxml 文件的路径是正确的
【发布时间】:2015-03-04 00:15:13
【问题描述】:

我明白了

javafx.fxml.LoadException:

当我使用以下代码行加载和 fxml 文件时。

AnchorPane anchorPane = (AnchorPane)loader.load()

这是我的 fxml 文件,不包括 import 语句。

<AnchorPane prefHeight="537.0" prefWidth="374.0"     xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.buddhikajay.controller.NewTransactionDialogController">
   <children>
      <GridPane hgap="5.0" layoutX="30.0" layoutY="10.0" prefHeight="544.0" prefWidth="314.0" vgap="5.0">
    <columnConstraints>
      <ColumnConstraints hgrow="SOMETIMES" maxWidth="142.0" minWidth="10.0" prefWidth="69.0" />
      <ColumnConstraints hgrow="SOMETIMES" maxWidth="226.0" minWidth="10.0" prefWidth="225.0" />
    </columnConstraints>
    <rowConstraints>
      <RowConstraints maxHeight="70.0" minHeight="10.0" prefHeight="33.0" vgrow="SOMETIMES" />
      <RowConstraints maxHeight="105.0" minHeight="10.0" prefHeight="38.0" vgrow="SOMETIMES" />
      <RowConstraints maxHeight="156.0" minHeight="10.0" prefHeight="51.0" vgrow="SOMETIMES" />
        <RowConstraints maxHeight="154.0" minHeight="10.0" prefHeight="43.0" vgrow="SOMETIMES" />
        <RowConstraints maxHeight="160.0" minHeight="10.0" prefHeight="43.0" vgrow="SOMETIMES" />
        <RowConstraints maxHeight="161.0" minHeight="10.0" prefHeight="63.0" vgrow="SOMETIMES" />
        <RowConstraints maxHeight="301.0" minHeight="10.0" prefHeight="180.0" vgrow="SOMETIMES" />
        <RowConstraints maxHeight="231.0" minHeight="10.0" prefHeight="106.0" vgrow="SOMETIMES" />
    </rowConstraints>
     <padding>
        <Insets bottom="5.0" left="5.0" right="5.0" top="5.0" />
     </padding>
     <children>
        <Label text="ID" />
        <Label text="Date" GridPane.rowIndex="1" />
        <Label text="Amont" GridPane.rowIndex="2" />
        <Label text="Person" GridPane.rowIndex="4" />
        <Label text="Type" GridPane.rowIndex="3" />
        <Label text="Resolved" GridPane.rowIndex="5" />
        <Label />
        <Label text="Description" GridPane.rowIndex="6" />
        <TextField fx:id="idTextField" GridPane.columnIndex="1" />
        <TextField fx:id="dateTextField" GridPane.columnIndex="1" GridPane.rowIndex="1" />
        <TextField fx:id="amountTextField" GridPane.columnIndex="1" GridPane.rowIndex="2" />
        <TextArea fx:id="descriptionTextArea" prefHeight="200.0" prefWidth="200.0" GridPane.columnIndex="1" GridPane.rowIndex="6" />
        <HBox maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="50.0" prefWidth="225.0" spacing="20.0" GridPane.columnIndex="1" GridPane.rowIndex="7">
           <GridPane.margin>
              <Insets />
           </GridPane.margin>
           <padding>
              <Insets bottom="10.0" left="20.0" right="10.0" top="10.0" />
           </padding>
           <children>
              <Button fx:id="okButton" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" mnemonicParsing="false" onAction="#okActionFired" prefHeight="25.0" prefWidth="75.0" text="Ok" />
              <Button fx:id="cancleButton" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" mnemonicParsing="false" onAction="#cancleActionFired" prefHeight="25.0" prefWidth="75.0" text="Cancle" />
           </children>
        </HBox>
        <ComboBox fx:id="typeComboBox" prefWidth="150.0" GridPane.columnIndex="1" GridPane.rowIndex="3" />
        <ComboBox fx:id="personComboBox" prefWidth="150.0" GridPane.columnIndex="1" GridPane.rowIndex="4" />
        <ComboBox fx:id="resolvedComboBox" prefWidth="150.0" GridPane.columnIndex="1" GridPane.rowIndex="5" />
     </children>
  </GridPane>
  </children>
</AnchorPane>

编译器报错第1行有错误,我确定fxml文件的路径是正确的。我的代码有什么问题?

这是完整的错误堆栈

javafx.fxml.LoadException: 
/C:/Users/Buddhika/Documents/Programming/IdeaProjects/VirtualCreditDesktop/out/production/VirtualCreditDesktop/com/buddhikajay/view/NewTransactionDialog.fxml:9

    at javafx.fxml.FXMLLoader.constructLoadException(FXMLLoader.java:2595)
    at javafx.fxml.FXMLLoader.access$700(FXMLLoader.java:104)
    at javafx.fxml.FXMLLoader$ValueElement.processAttribute(FXMLLoader.java:928)
    at javafx.fxml.FXMLLoader$InstanceDeclarationElement.processAttribute(FXMLLoader.java:967)
    at javafx.fxml.FXMLLoader$Element.processStartElement(FXMLLoader.java:216)
    at javafx.fxml.FXMLLoader$ValueElement.processStartElement(FXMLLoader.java:740)
    at javafx.fxml.FXMLLoader.processStartElement(FXMLLoader.java:2701)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2521)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2435)
    at javafx.fxml.FXMLLoader.load(FXMLLoader.java:2403)
    at com.buddhikajay.controller.NewTransactionDialogController.showNewTransactionDialog(NewTransactionDialogController.java:68)
    at com.buddhikajay.controller.MainApp.start(MainApp.java:51)
    at com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$153(LauncherImpl.java:821)
    at com.sun.javafx.application.LauncherImpl$$Lambda$50/1976027283.run(Unknown Source)
    at com.sun.javafx.application.PlatformImpl.lambda$runAndWait$166(PlatformImpl.java:323)
    at com.sun.javafx.application.PlatformImpl$$Lambda$46/301541210.run(Unknown Source)
    at com.sun.javafx.application.PlatformImpl.lambda$null$164(PlatformImpl.java:292)
    at com.sun.javafx.application.PlatformImpl$$Lambda$48/474926796.run(Unknown Source)
    at java.security.AccessController.doPrivileged(Native Method)
    at com.sun.javafx.application.PlatformImpl.lambda$runLater$165(PlatformImpl.java:291)
    at com.sun.javafx.application.PlatformImpl$$Lambda$47/1662429848.run(Unknown Source)
    at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95)
    at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
    at com.sun.glass.ui.win.WinApplication.lambda$null$141(WinApplication.java:102)
    at com.sun.glass.ui.win.WinApplication$$Lambda$38/519284171.run(Unknown Source)
    at java.lang.Thread.run(Thread.java:745)
Caused by: java.lang.InstantiationException: com.buddhikajay.controller.NewTransactionDialogController
    at java.lang.Class.newInstance(Class.java:423)
    at sun.reflect.misc.ReflectUtil.newInstance(ReflectUtil.java:51)
    at javafx.fxml.FXMLLoader$ValueElement.processAttribute(FXMLLoader.java:923)
    ... 23 more
Caused by: java.lang.NoSuchMethodException: com.buddhikajay.controller.NewTransactionDialogController.<init>()
    at java.lang.Class.getConstructor0(Class.java:3074)
    at java.lang.Class.newInstance(Class.java:408)
    ... 25 more

【问题讨论】:

    标签: javafx fxml fxmlloader


    【解决方案1】:

    堆栈跟踪中描述了问题:

    引起:java.lang.NoSuchMethodException: com.buddhikajay.controller.NewTransactionDialogController.()
    

    这基本上是说您的控制器类没有零参数构造函数。

    默认情况下,FXMLLoader 将通过调用其零参数构造函数来创建控制器。删除您在控制器类中定义的构造函数,或删除它采用的参数。

    如果您确实需要将参数传递给控制器​​的构造函数,您可以在 Java 代码中创建控制器并将其传递给 FXMLLoader:

    NewTransactionDialogController controller = new NewTransactionDialogController(someValue);
    FXMLLoader loader = new FXMLLoader();
    loader.setLocation(...);
    loader.setController(controller);
    AnchorPane anchorPane = loader.load();
    

    (使用此代码,您必须从 FXML 中删除 fx:controller 属性。)

    或者,设置控制器工厂:

    FXMLLoader loader = new FXMLLoader();
    loader.setLocation(...);
    loader.setControllerFactory(clazz -> {
        if (clazz == NewTransactionDialogController.class) {
            return new NewTransactionDialogController(someValue);
        } else {
            // default behavior:
            try {
                return clazz.newInstance();
            } catch (Exception exc) {
                throw new RuntimeException(exc);
            }
        }
    });
    
    AnchorPane anchorPane = loader.load();
    

    (在此版本中,将 fx:controller 属性保留在 FXML 文件中。)

    【讨论】:

    • 非常感谢@JAmes_D。我在主应用程序中创建了控制器并将其传递给 FXMLLoader 并且它可以工作..
    • 我认为 fx:controller 中只有一个错字不是吗? () 之前的点看起来很可疑!
    • 不幸的是,这不是 ONLY 的原因。我有一个空的构造函数,FXML 工作得很好,谢谢。 但是当我为按钮添加 ActionEvent 处理程序时,我收到了类似这样的消息:“avafx fxml LoadException: Error resolving onAction='#handleButtonAction', either the event handler is not in the Namespace or there is an error in the script. **unknown path**
    • (...continued) ...我认为有问题的 path 是一个类路径,但是当没有指定“#handleButtonAction”时控制器工作。奇怪的?是的,这是因为我粘贴了示例“单击我”按钮的代码,删除了空的构造函数,并且当我指定一个操作时,我只(仍然)得到一个错误。
    • 当没有要粘贴的控制器代码时,很难在代码中粘贴...如果您有与 OP 的问题不同的问题,您应该发布它...
    【解决方案2】:

    正如@James_D 所说,我正要输入一个不同的问题,因为直到我阅读了关于这个问题的 FXML 的第一行,我曾认为我有一个不同的问题。

    对于我的罪过,我将挑战简化为一个简单的示例,即一个控制器和两个 FXML 文件。一个工作,第二个失败/失败。

    起点是 Netbeans 示例“[Click me!]”示例。代码粘贴在下面。而且,首先是一个解决方案。

    作为序言,让我说似乎每个人 都将这些加载错误归咎于 Java 控制器。几年前,我在一个项目中遇到了很多这样的错误。我们用尽了“controller”调试,最终通过使用 ScendBuilder 重新构建 FXML 屏幕继续前进。那时我没有时间进一步调查。

    上周我完美运行的 FXML 屏幕开始无法加载,因为我们将它移到了运行时目录(之前它位于 JAR 资源区域中)。

    克伦克!

    在调整了 3 或 4 天之后,我在这里对我的错误发表了评论:

    • unknown path: 7
    • Javafx fxml LoadException: Error resolving onAction='#handleButtonAction', either the event handler is not in the Namespace or there is an error in the script.

    仅适用于“simple.fxml”文件,而不适用于“Scene.fxml”文件.文件“simple.fxml”是从最初给出问题的应用程序 FXML 文件中减少的。那个原始文件的变量太多了,所以chop-chop-chop来匹配罐头演示。

    当你只使用这个时:

    xmlns:fx="http://javafx.com/fxml"
    

    从应用程序文件夹下磁盘上的文件加载 FXML 就像您希望它们那样工作(好吧,无论如何,就像我想要的那样)。查看上面的 FXML,它使用了一个更“脆弱”的命名空间,即。

    Queston 的原始 FXML:

      <AnchorPane ...
                  xmlns="http://javafx.com/javafx/8" 
                  xmlns:fx="http://javafx.com/fxml/1" ... >
    

    通过使用 diff,我慢慢地将“simple.fxml”变形为尽可能接近“Scene.fxml”,而“simple”只是一直无法加载。请注意;总是使用同一个控制器

    使用其他元数据加载 FXML 无法始终如一地移动 FXML 文件。我没有解释如何这是这样的。

    例如,FXML 保存在名为“test/resources/fxml/simple.fxml”的目录中。当我在项目 JAR 中使用这两个文件进行构建时,两种情况下的“same”FXML 都按预期加载并工作。对我来说,关于文件加载过程的各个方面有些事情没有说清楚。再次对我来说,这是不可取的,因为外部场景定义的 KEY 值会互换。

    XML 标记中的这些熊陷阱(显然)没有被 SceneBuilder 或 FXMLLoader() 等开发工具拾取,这些陷阱阻碍了实时项目的进展,这些项目没有时间研究深奥的像这样的怪异

    我们之前的项目经验证明了这一点——使用 SceneBuilder 整体重新编辑复杂的屏幕比跟踪像这样的加载问题更容易。号召性用语是:诊断 FXML 负载 -- FXML Lint 几乎是必需的。


    控制器,SimpleController.java:

      package ex.view.views;
    
      import java.net.URL;
      import java.util.ResourceBundle;
      import javafx.event.ActionEvent;
      import javafx.fxml.FXML;
      import javafx.fxml.Initializable;
      import javafx.scene.control.Label;
    
      public class SimpleController implements Initializable {
    
          @FXML
          private Label label;
    
          @FXML
          private void handleButtonAction(ActionEvent event) {
              System.out.println("You clicked me!");
              label.setText("Hello World!");
          }
    
          @Override
          public void initialize(URL url, ResourceBundle rb) {
              // TODO
          }    
      }
    

    失败的 FXML 最初是 Maven 原型之一(我认为),并且该文件运行良好,直到我将 FXML 文件移动到一个文件夹并从 InputStream 加载它们。 p>

    为了便于阅读,我已将 AnchorPane 标记格式化为多行。

    simple.fxml:

      <?xml version="1.0" encoding="UTF-8"?>
    
      <?import javafx.scene.control.Button?>
      <?import javafx.scene.control.Label?>
      <?import javafx.scene.layout.AnchorPane?>
    
      <AnchorPane id="AnchorPane" prefHeight="200" prefWidth="320" 
                  xmlns="http://javafx.com/javafx/8.0.65" 
                  xmlns:fx="http://javafx.com/fxml/1"
                   fx:controller="ex.view.views.SimpleController">
          <children>
              <Button fx:id="button" layoutX="126" layoutY="90" text="Click Me!" />
              <Label fx:id="label" layoutX="126" layoutY="120" minHeight="16" minWidth="69" />
          </children>
      </AnchorPane>
    

    有效的 FXML 标记来自 Netbeans 8.1 示例。

    场景.fxml:

      <?xml version="1.0" encoding="UTF-8"?>
    
      <?import java.lang.*?>
      <?import java.util.*?>
      <?import javafx.scene.*?>
      <?import javafx.scene.control.*?>
      <?import javafx.scene.layout.*?>
    
      <AnchorPane id="AnchorPane" prefHeight="200" prefWidth="320" 
                  xmlns:fx="http://javafx.com/fxml" 
                  fx:controller="ex.view.views.SimpleController">
          <children>
              <Button layoutX="126" layoutY="90" text="Click Me!" onAction="#handleButtonAction" fx:id="button" />
              <Label layoutX="126" layoutY="120" minHeight="16" minWidth="69" fx:id="label" />
          </children>
      </AnchorPane>
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-12-26
      • 1970-01-01
      • 2016-04-25
      • 2015-02-14
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多