JavaFX如何通过其他类构造器实现Stage上的Scene场景切换求助
JavaFX界面切换问题修复方案
核心问题说明
你的代码存在两个核心错误导致切换失败:
- 主类没有保存全局的主Stage实例,无法传递给其他界面类复用现有窗口
food类的构造逻辑错误:没有接收外部传入的主Stage,自身成员变量primaryStage为空时直接调用show()会抛出空指针异常,也没有主动调用start()方法完成界面初始化
修复后代码
主类修改
package application; import javafx.application.Application; import javafx.event.ActionEvent; import javafx.event.EventHandler; import javafx.scene.Scene; import javafx.scene.control.Label; import javafx.scene.control.Menu; import javafx.scene.control.MenuBar; import javafx.scene.control.MenuItem; import javafx.scene.layout.StackPane; import javafx.stage.Stage; public class Main extends Application implements EventHandler<ActionEvent> { StackPane pane; MenuItem item1, item2, item3, item4; Label label; Scene scene; Menu menu; // 新增成员变量存储主Stage实例 private Stage mainStage; public static void main(String args[]){ launch(args); } @Override public void start(Stage primaryStage) { // 保存传入的主Stage this.mainStage = primaryStage; menu = new Menu("Choose"); item1 = new MenuItem("Add Food"); item2 = new MenuItem("Add Exercise"); item3 = new MenuItem("View Log"); item4 = new MenuItem("Exit"); menu.getItems().addAll(item1, item2, item3, item4); MenuBar menuBar = new MenuBar(menu); menuBar.setTranslateX(200); menuBar.setTranslateY(100); item1.setOnAction(this); item2.setOnAction(this); item3.setOnAction(this); item4.setOnAction(this); pane = new StackPane(); label = new Label("Welcome to the Health Tracker!\nWhat would you like to do?"); pane.getChildren().addAll(label,menuBar); scene = new Scene(pane, 400, 400); primaryStage.setTitle("Health Tracker"); primaryStage.setScene(scene); primaryStage.show(); } @Override public void handle(ActionEvent event) { if(event.getSource() == item1) { // 将主Stage传递给food类完成界面切换 new food(mainStage); } else if(event.getSource() == item2) { // exercise类参照food类逻辑修改后即可使用 // new exercise(mainStage); } else if(event.getSource() == item3) { System.out.print("log"); } else if(event.getSource() == item4) { mainStage.close(); System.out.print("exited"); } } }
food类修改
package application; import javafx.event.ActionEvent; import javafx.event.EventHandler; import javafx.scene.Scene; import javafx.scene.control.Label; import javafx.scene.control.Menu; import javafx.scene.control.MenuBar; import javafx.scene.control.MenuItem; import javafx.scene.layout.StackPane; import javafx.stage.Stage; public class food implements EventHandler<ActionEvent> { StackPane pane; MenuItem item1, item2; Label label; Scene scene; Menu menu; Stage primaryStage; // 改造构造器,接收外部传入的主Stage public food(Stage primaryStage) { this.primaryStage = primaryStage; // 主动调用start方法初始化当前界面 start(); } public void start() { menu = new Menu("Choose"); item1 = new MenuItem("Add Food"); item2 = new MenuItem("Exit"); menu.getItems().addAll(item1, item2); MenuBar menuBar = new MenuBar(menu); menuBar.setTranslateX(200); menuBar.setTranslateY(100); item1.setOnAction(this); item2.setOnAction(this); pane = new StackPane(); label = new Label("Welcome to the Food tracker!\nWhat would you like to do?"); pane.getChildren().addAll(label,menuBar); scene = new Scene(pane, 400, 400); primaryStage.setTitle("Food Tracker"); primaryStage.setScene(scene); } @Override public void handle(ActionEvent event) { if(event.getSource() == item1) { // 后续业务逻辑 } if(event.getSource() == item2) { // 示例:返回主界面 new Main().start(primaryStage); } } }
内容的提问来源于stack exchange,提问作者domweng
相关产品推荐
相关产品推荐

