JavaFX 无法在运行时使用 ID 找到在 FXML 中声明的节点
JavaFX unable to find node declared in FXML at runtime using ID
我无法找到在 FXML 中声明的 ID 为“#mainScrollPaneVbox”的节点 "VBox"。
这是我的 FXML:
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>
<BorderPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.conuretech.video_assembler.FXMLController">
<top>
<MenuBar prefHeight="16.0" prefWidth="600.0" BorderPane.alignment="CENTER">
<menus>
<Menu mnemonicParsing="false" text="File">
<items>
<MenuItem mnemonicParsing="false" onAction="#handleNewAction" text="New" />
<MenuItem mnemonicParsing="false" onAction="#handleOpenProjectAction" text="Open Project" />
<MenuItem mnemonicParsing="false" onAction="#handleSaveAsAction" text="Save As..." />
<MenuItem mnemonicParsing="false" onAction="#handleSaveAction" text="Save..." />
<MenuItem mnemonicParsing="false" onAction="#handleCovertImagesToVideoAction" text="Convert Project To video" />
<MenuItem mnemonicParsing="false" onAction="#handleImportLocalAction" text="Import Local Images" />
<MenuItem mnemonicParsing="false" onAction="#handleImportRemoteAction" text="Import Remote Images" />
<MenuItem mnemonicParsing="false" onAction="#handleExitAction" text="Exit" />
</items>
</Menu>
<Menu mnemonicParsing="false" text="Edit">
<items>
<MenuItem mnemonicParsing="false" text="Add New Frame From" />
<MenuItem mnemonicParsing="false" text="Delete Current Frame" />
<MenuItem mnemonicParsing="false" text="Edit Frame Properties" />
<MenuItem mnemonicParsing="false" text="Video Properties" />
</items>
</Menu>
<Menu mnemonicParsing="false" text="Help">
<items>
<MenuItem mnemonicParsing="false" text="About" />
</items>
</Menu>
</menus>
</MenuBar>
</top>
<left>
<ScrollPane id="#mainScrollPane" prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<content>
<VBox id="#mainScrollPaneVbox" prefHeight="200.0" prefWidth="200.0" />
</content></ScrollPane>
</left>
<center>
<GridPane BorderPane.alignment="CENTER">
<columnConstraints>
<ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" />
<ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" />
</columnConstraints>
<rowConstraints>
<RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
<RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
<RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
</rowConstraints>
</GridPane>
</center>
</BorderPane>
这是 Java 代码,它试图在运行时找到 "Vbox":
VBox vbox = (VBox) MainApp.scene.lookup("#mainScrollPaneVbox");
我也试过了:
VBox vbox = (VBox) MainApp.scene.lookup("mainScrollPaneVbox");
但这仍然returns无效。
有什么想法吗?
谢谢
为什么你的代码不起作用
FXML 中的 id
属性应该只包含节点的 ID,而不是 CSS 查找 ID。换句话说,你有
<VBox id="#mainScrollPaneVbox" ... >
当你需要的时候
<VBox id="mainScrollPaneVbox" ... >
查找应该有 CSS 查找:
VBox vbox = (VBox) MainApp.scene.lookup("#mainScrollPaneVbox");
但无论如何我都不建议这样做,尤其是因为您已经有了控制器 class。
推荐方法
CSS 查找不是很可靠。它们依赖于 String 绑定,并且不是类型安全的。此外,在实际执行查找之前不会捕获任何错误,这可能是在应用程序启动之后(例如,当用户执行某些操作时)。
更好的方法是使用@FXML
注入。虽然这些仍然依赖于 String 绑定并且没有编译时类型检查,但在加载 FXML 文件时会发现错误,因此任何故障都会更早发生。这使得检测和修复错误变得更加容易。
要使用 @FXML
注入,你会做
<VBox fx:id="mainScrollPaneVbox"
然后在你的控制器中 class:
public class FXMLController {
@FXML
private VBox mainScrollPaneVbox ; // same field name as the fx:id
// ...
public void initialize() {
// popuplate mainScrollPaneVbox ...
// can similarly be accessed in event handlers
// ...
}
// ...
}
我无法找到在 FXML 中声明的 ID 为“#mainScrollPaneVbox”的节点 "VBox"。
这是我的 FXML:
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>
<BorderPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.conuretech.video_assembler.FXMLController">
<top>
<MenuBar prefHeight="16.0" prefWidth="600.0" BorderPane.alignment="CENTER">
<menus>
<Menu mnemonicParsing="false" text="File">
<items>
<MenuItem mnemonicParsing="false" onAction="#handleNewAction" text="New" />
<MenuItem mnemonicParsing="false" onAction="#handleOpenProjectAction" text="Open Project" />
<MenuItem mnemonicParsing="false" onAction="#handleSaveAsAction" text="Save As..." />
<MenuItem mnemonicParsing="false" onAction="#handleSaveAction" text="Save..." />
<MenuItem mnemonicParsing="false" onAction="#handleCovertImagesToVideoAction" text="Convert Project To video" />
<MenuItem mnemonicParsing="false" onAction="#handleImportLocalAction" text="Import Local Images" />
<MenuItem mnemonicParsing="false" onAction="#handleImportRemoteAction" text="Import Remote Images" />
<MenuItem mnemonicParsing="false" onAction="#handleExitAction" text="Exit" />
</items>
</Menu>
<Menu mnemonicParsing="false" text="Edit">
<items>
<MenuItem mnemonicParsing="false" text="Add New Frame From" />
<MenuItem mnemonicParsing="false" text="Delete Current Frame" />
<MenuItem mnemonicParsing="false" text="Edit Frame Properties" />
<MenuItem mnemonicParsing="false" text="Video Properties" />
</items>
</Menu>
<Menu mnemonicParsing="false" text="Help">
<items>
<MenuItem mnemonicParsing="false" text="About" />
</items>
</Menu>
</menus>
</MenuBar>
</top>
<left>
<ScrollPane id="#mainScrollPane" prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<content>
<VBox id="#mainScrollPaneVbox" prefHeight="200.0" prefWidth="200.0" />
</content></ScrollPane>
</left>
<center>
<GridPane BorderPane.alignment="CENTER">
<columnConstraints>
<ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" />
<ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" />
</columnConstraints>
<rowConstraints>
<RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
<RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
<RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
</rowConstraints>
</GridPane>
</center>
</BorderPane>
这是 Java 代码,它试图在运行时找到 "Vbox":
VBox vbox = (VBox) MainApp.scene.lookup("#mainScrollPaneVbox");
我也试过了:
VBox vbox = (VBox) MainApp.scene.lookup("mainScrollPaneVbox");
但这仍然returns无效。
有什么想法吗?
谢谢
为什么你的代码不起作用
FXML 中的 id
属性应该只包含节点的 ID,而不是 CSS 查找 ID。换句话说,你有
<VBox id="#mainScrollPaneVbox" ... >
当你需要的时候
<VBox id="mainScrollPaneVbox" ... >
查找应该有 CSS 查找:
VBox vbox = (VBox) MainApp.scene.lookup("#mainScrollPaneVbox");
但无论如何我都不建议这样做,尤其是因为您已经有了控制器 class。
推荐方法
CSS 查找不是很可靠。它们依赖于 String 绑定,并且不是类型安全的。此外,在实际执行查找之前不会捕获任何错误,这可能是在应用程序启动之后(例如,当用户执行某些操作时)。
更好的方法是使用@FXML
注入。虽然这些仍然依赖于 String 绑定并且没有编译时类型检查,但在加载 FXML 文件时会发现错误,因此任何故障都会更早发生。这使得检测和修复错误变得更加容易。
要使用 @FXML
注入,你会做
<VBox fx:id="mainScrollPaneVbox"
然后在你的控制器中 class:
public class FXMLController {
@FXML
private VBox mainScrollPaneVbox ; // same field name as the fx:id
// ...
public void initialize() {
// popuplate mainScrollPaneVbox ...
// can similarly be accessed in event handlers
// ...
}
// ...
}