アプリケーションが機能しない理由はいくつかあります。
- コントローラとアプリケーションを別々のクラスにする必要があります。
- 新しいインスタンスを作成するのではなく、FXMLシステムがTreeViewインスタンスを挿入できるようにする必要があります(Aaronが彼の回答で指摘しているように)。
アプリケーションを現在構造化する方法は次のとおりです。
- Javaシステムは
MyControllerClass
、起動時にのインスタンスを作成します(そしてそのstart
メソッドを呼び出します)。
- は、ファイルがロードされるたびに別のインスタンスを
FXMLLoader
作成します。MyControllerClass
myInterface.fxml
- は新しい
FXMLLoader
インスタンスを作成し、作成した新しいインスタンスのメンバーに対してTreeView
FXMLインジェクションを実行します。locationTreeView
MyControllerClass
- は、新しいメソッド(あなたが持っていないメソッド)
FXMLLoader
を呼び出そうとします。initialize
MyControllerClass
- は、新しいでメソッドを呼び出し
FXMLLoader
ません。start
MyControllerClass
- オリジナルに対するオリジナルの
start
メソッド呼び出しMyControllerClass
は処理を続行し、古いインスタンスのメンバーを設定する別の新しい TreeView
インスタンスを作成します。locationTreeView
MyControllerClass
上記で提案した変更を行うためにコードを更新しましたが、コードは機能するようになりました。更新されたコードが利用可能です。
実行中のコードのサンプルスクリーンショットは次のとおりです。
MyApplicationClass.java
import javafx.animation.*;
import javafx.application.Application;
import javafx.event.*;
import javafx.fxml.FXMLLoader;
import javafx.scene.*;
import javafx.scene.image.Image;
import javafx.scene.input.MouseEvent;
import javafx.stage.*;
import javafx.util.Duration;
/** Sample application to demonstrate programming an FXML interface. */
public class MyApplicationClass extends Application {
@Override public void start(final Stage stage) throws Exception {
// load the scene fxml UI.
// grabs the UI scenegraph view from the loader.
// grabs the UI controller for the view from the loader.
final FXMLLoader loader = new FXMLLoader(getClass().getResource("myInterface.fxml"));
final Parent root = (Parent) loader.load();
final MyControllerClass controller = loader.<MyControllerClass>getController();
// continuously refresh the TreeItems.
// demonstrates using controller methods to manipulate the controlled UI.
final Timeline timeline = new Timeline(
new KeyFrame(
Duration.seconds(3),
new TreeLoadingEventHandler(controller)
)
);
timeline.setCycleCount(Timeline.INDEFINITE);
timeline.play();
// close the app if the user clicks on anywhere on the window.
// just provides a simple way to kill the demo app.
root.addEventFilter(MouseEvent.MOUSE_CLICKED, new EventHandler<MouseEvent>() {
@Override public void handle(MouseEvent t) {
stage.hide();
}
});
// initialize the stage.
stage.setScene(new Scene(root));
stage.initStyle(StageStyle.TRANSPARENT);
stage.getIcons().add(new Image(getClass().getResourceAsStream("myIcon.png")));
stage.show();
}
/** small helper class for handling tree loading events. */
private class TreeLoadingEventHandler implements EventHandler<ActionEvent> {
private MyControllerClass controller;
private int idx = 0;
TreeLoadingEventHandler(MyControllerClass controller) {
this.controller = controller;
}
@Override public void handle(ActionEvent t) {
controller.loadTreeItems("Loaded " + idx, "Loaded " + (idx + 1), "Loaded " + (idx + 2));
idx += 3;
}
}
// main method is only for legacy support - java 8 won't call it for a javafx application.
public static void main(String[] args) { launch(args); }
}
MyControllerClass.java
import javafx.fxml.FXML;
import javafx.scene.control.*;
/** Sample controller class. */
public class MyControllerClass {
// the FXML annotation tells the loader to inject this variable before invoking initialize.
@FXML private TreeView<String> locationTreeView;
// the initialize method is automatically invoked by the FXMLLoader - it's magic
public void initialize() {
loadTreeItems("initial 1", "initial 2", "initial 3");
}
// loads some strings into the tree in the application UI.
public void loadTreeItems(String... rootItems) {
TreeItem<String> root = new TreeItem<String>("Root Node");
root.setExpanded(true);
for (String itemString: rootItems) {
root.getChildren().add(new TreeItem<String>(itemString));
}
locationTreeView.setRoot(root);
}
}
myInterface.fxml
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>
<AnchorPane id="AnchorPane" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" xmlns:fx="http://javafx.com/fxml" fx:controller="test.MyControllerClass">
<TreeView fx:id="locationTreeView" layoutX="0" layoutY="0" prefHeight="193.0" prefWidth="471.0" />
</AnchorPane>