【发布时间】:2020-04-16 23:54:23
【问题描述】:
我正在尝试使用 FXML 在 JavaFX 中构建 GUI。为此,我有一个 FXML 主页面,其中包含 3 个我也使用 FXML 创建的自定义组件。这是我的代码目录:
src
App.java
ui
MainView.java
CustomHeader.java
CustomBody.java
fxml
MainView.fxml
CustomHeader.fxml
CustomBody.fxml
controller
MainViewController.java
CustomHeaderController.java
CustomBodyController.java
App.java
package ui;
import javafx.application.Application;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.stage.Stage;
import model.main.TaskItem;
import java.time.LocalDateTime;
import java.util.ArrayList;
public class ProductivityTrackerApp extends Application {
public static Stage primaryStage;
public static final String TITLE = "App";
public static final double WIDTH = 520;
public static final double HEIGHT = 800;
public static void main(String[] args) {
launch(args);
}
public void setPrimaryStage(Stage primaryStage) {
this.primaryStage = primaryStage;
}
public static void setScene(Parent root) {
try {
Scene scene = new Scene(root, WIDTH, HEIGHT);
primaryStage.setTitle(TITLE);
primaryStage.setScene(scene);
primaryStage.show();
} catch (Exception e) {
System.out.println("Failed to load new Scene!");
}
}
@Override
public void start(Stage primaryStage) throws Exception {
setPrimaryStage(primaryStage);
setScene(new MainView());
}
}
Main.fxml
<fx:root xmlns="http://javafx.com/javafx"
xmlns:fx="http://javafx.com/fxml"
fx:controller="controllers.MainController"
fx:id="root"
type="VBox">
<children>
<CustomHeader> </CustomHeader>
<CustomBody> </CustomBody>
</children>
</fx:root>
MainView.java
package ui;
import javafx.fxml.FXMLLoader;
import javafx.scene.layout.VBox;
import java.io.File;
import java.io.IOException;
public class MainView extends VBox {
private static final String FXML = "src/fxml/MainView.fxml";
private File fxmlFile = new File(FXML);
public MainView() {
this.load();
};
private void load() {
try {
FXMLLoader fxmlLoader = new FXMLLoader(fxmlFile.toURI().toURL());
fxmlLoader.setRoot(this);
fxmlLoader.load();
} catch (IOException exception) {
throw new RuntimeException(exception);
}
}
}
CustomHeader.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.*?>
<fx:root xmlns="http://javafx.com/javafx"
xmlns:fx="http://javafx.com/fxml"
fx:controller="controllers.CustomHeaderController"
minHeight="80.0" prefWidth="520.0" type="StackPane">
<BorderPane>
<left>
</left>
<center>
<Label text="App"/>
</center>
<right>
<Button text="Click here" onMouseClicked="#colorBody"/>
</right>
</BorderPane>
</fx:root>
CustomHeader.java
package ui;
import javafx.fxml.FXMLLoader;
import javafx.scene.layout.StackPane;
import java.io.File;
import java.io.IOException;
public class MainView extends StackPane {
private static final String FXML = "src/fxml/CustomHeader.fxml";
private File fxmlFile = new File(FXML);
public CustomHeader() {
this.load();
};
private void load() {
try {
FXMLLoader fxmlLoader = new FXMLLoader(fxmlFile.toURI().toURL());
fxmlLoader.setRoot(this);
fxmlLoader.load();
} catch (IOException exception) {
throw new RuntimeException(exception);
}
}
}
CustomBody.fxml
<fx:root xmlns="http://javafx.com/javafx"
xmlns:fx="http://javafx.com/fxml"
fx:controller="controllers.CustomBodyController"
type="StackPane">
<Rectangle width="240" height="240" StackPane.alignment = "CENTER"/>
</fx:root>
CustomBody.java
package ui;
import javafx.fxml.FXMLLoader;
import javafx.scene.layout.StackPane;
import java.io.File;
import java.io.IOException;
public class MainView extends StackPane {
private static final String FXML = "src/fxml/CustomBody.fxml";
private File fxmlFile = new File(FXML);
public CustomBody() {
this.load();
};
private void load() {
try {
FXMLLoader fxmlLoader = new FXMLLoader(fxmlFile.toURI().toURL());
fxmlLoader.setRoot(this);
fxmlLoader.load();
} catch (IOException exception) {
throw new RuntimeException(exception);
}
}
}
控制器还没有任何功能。因此,我没有包括它们。
我想引入一个功能,即在 CustomHeader 组件中的按钮上的 onClick 操作会改变 CustomBody 组件中矩形的颜色。但是,由于这些组件有单独的控制器,我想知道是否有办法让我从 MainController(父组件的控制器)访问这两个控制器。此外,如果可能,是否有更好的建议来调解两个兄弟组件的通信?
【问题讨论】:
-
通常你会使用自定义控制器和 fx:include 如果你有一个名为“custom”的 fx:id 你可以在父控制器中有一个名为 customController 的变量,控制器将被注入其中在
-
Atm 你正在使用我建议反对的自定义节点(也可以,但不是一个好方法)
标签: user-interface javafx javafx-8