【问题标题】:How do I display two javafx GUI screens in the same program如何在同一个程序中显示两个 javafx GUI 屏幕
【发布时间】:2017-06-26 16:05:45
【问题描述】:

我的问题是如何在每个程序中显示多个用户界面屏幕。我确定这个问题之前已经被问过,但我还没有找到适合我的解决方案(或者我应该说我理解)。我正在谈论的场景没有任何异国情调。第一个是简单地验证来自屏幕的输入并在出现错误时重新显示相同的屏幕。

我将根据第二个更复杂的场景提出问题:显示输入数据屏幕,处理输入;然后显示输出。这有点复杂,因为第一个是带有 5 个文本框和一个命令按钮的简单屏幕,使用 FXML 文件,而第二个是多选列表框不使用。流程是:

1。主程序调用

2。加载 FXML 并以某种方式调用的加载程序

3。一个控制器,它接收输入并处理它们以产生输出。

最后一步是以多选列表框的形式显示输出。请注意,第一个 GUI 使用一个单独文件的控制器来处理输入,而第二个 GUI 使用与屏幕定义位于同一文件中的事件处理程序来在用户单击时进行选择命令按钮。

各种 SO 帖子都说,当第一个 GUI 完成后,不要关闭应用程序,而是保持 JavaFX 运行时在后台运行

Platform.setImplicitExit(false);

并定义每个 GUI 并将场景切换到您要显示的场景。但是,鉴于我描述的场景,您将代码放在哪里?第二个 GUI 包含三个部分:屏幕定义、事件处理程序和场景切换代码。你把每个放在哪里? #2 或 #3。如果你把一些放在#2 中,一些放在#3 中,#3 怎么知道你在#2 中做了什么?

#2 FMXL 加载器的代码:

    public class inputData extends Application { 
    public static void load() {       
        launch();
    }
    @Override
    public void start(Stage stage) throws Exception {
                    
        GridPane inpRoot = FXMLLoader.load(getClass().getResource("inputData.fxml"));
        Scene inpScene = new Scene(inpRoot, 300, 275);
        
        stage.setTitle("Amsnag 2.1 - Query Input");
        stage.setScene(inpScene);
        stage.show();
    }   
}

#3 的代码,列表框定义和处理程序,单独运行时运行良好。只有当我尝试将它与程序的其余部分合并时它才会失败。

public class multiList extends Application { 
    public static void load() {       
        launch();  
    }
    public static final ObservableList options = FXCollections.observableArrayList();
    
    @Override
        public void start(final Stage stage) {    
        final ListView<String> listView = new ListView<>();         
        listView.getSelectionModel().setSelectionMode(SelectionMode.MULTIPLE);
// load list from DB
        Connection conn = sql.connect();
        try {
    // initialize option table
            ResultSet rs = sql.select(conn, 
                "select distinct connDesc,accom from option order by connDEsc,accom");
            while (rs.next()) {
                String opt = rs.getString("connDesc") + ": " + rs.getString("accom");
                listView.getItems().add(opt);
            }                                                                    
            conn.close();
        }
        catch (SQLException e) {
            System.out.println(e.getMessage()+ " from init");
        }
// button to display fares
        final Button displayButton = new Button("Display Fares");
// handle button click
        displayButton.setOnAction(new EventHandler<ActionEvent>() {
        @Override public void handle(ActionEvent event) {
            Platform.exit();   // close list box
            ObservableList selectedIndices = listView.getSelectionModel().getSelectedItems();
// lcreate temp table with selected options
            Connection conn = sql.connect();
            try {
// initialize option table
                ResultSet rs = sql.select(conn, 
                    "create temporary table selected (connDesc varchar(200),accom varchar(50))");
                for(Object o : selectedIndices){
                   String option = o.toString();
// extract connDesc+accom from displayed option
                   msg.g(option);
                }        
                conn.close();
            }
            catch (SQLException e) {
               System.out.println(e.getMessage()+ " from init");
            }         
        }
    }    );   // end of display handler
// quit  button
    final Button resetButton = new Button("Quit");
    resetButton.setOnAction(new EventHandler<ActionEvent>() {
    @Override
        public void handle(ActionEvent event) {
            Platform.exit();
        }
    });
    final HBox controls = new HBox(10);
    controls.setAlignment(Pos.CENTER);
    controls.getChildren().addAll(displayButton, resetButton);
 
    final VBox layout = new VBox(10);
    layout.setAlignment(Pos.CENTER);
    layout.setStyle("-fx-padding: 10; -fx-background-color: cornsilk;");
    layout.getChildren().setAll(listView, controls);
    layout.setPrefWidth(320);``enter code here
    
    Scene scene = new Scene(layout);
 //   stage.setScene(new Scene(layout));
    stage.setScene(scene);
    stage.setTitle("Select one or more options");
    stage.show();
  }  
  public static void main(String[] args) { launch(args); }
}

【问题讨论】:

  • 您的应用程序中应该只有一个Application 子类。目前还不清楚你想用两个这样的类做什么。也许stackoverflow.com/questions/32464698/… 有帮助?
  • 对。我没有说清楚第二组代码,multiList 类,是一个可以工作的独立版本。我要做的是显示两个 GUI。
  • 您不能在另一个应用程序中重用 Application 子类。将要重用的部分分解为单独的类。这与我上面链接的问题相同。

标签: user-interface javafx


【解决方案1】:

您不能在不同的应用程序中重用 Application 子类。

Application 类代表整个应用程序,或者更具体地说,它代表它的生命周期。因此,它具有init()start()stop() 等方法,这些方法由FX 应用程序工具包在应用程序生命周期的适当时刻调用。

multiList 的布局(除此之外:请使用proper naming conventions)类是在start() 方法中执行的,因此它只能在应用程序开始时发生。通过将布局代码放在这里,您将无法重用它,以便稍后在不同的应用程序中执行。

所以将MultiList 的布局移动到一个单独的类中:

public class MultiList  { 

    public static final ObservableList options = FXCollections.observableArrayList();

    private final VBox view ;

    public MultiList() {    
        final ListView<String> listView = new ListView<>();         
        listView.getSelectionModel().setSelectionMode(SelectionMode.MULTIPLE);
        // load list from DB
        Connection conn = sql.connect();
        try {
            // initialize option table
            ResultSet rs = sql.select(conn, 
                "select distinct connDesc,accom from option order by connDEsc,accom");
            while (rs.next()) {
                String opt = rs.getString("connDesc") + ": " + rs.getString("accom");
                listView.getItems().add(opt);
            }                                                                    
            conn.close();
        }
        catch (SQLException e) {
            System.out.println(e.getMessage()+ " from init");
        }
        // button to display fares
        final Button displayButton = new Button("Display Fares");
            // handle button click
            displayButton.setOnAction(new EventHandler<ActionEvent>() {
            @Override public void handle(ActionEvent event) {
                Platform.exit();   // close list box
                ObservableList selectedIndices = listView.getSelectionModel().getSelectedItems();
                // create temp table with selected options
                Connection conn = sql.connect();
                try {
                    // initialize option table
                    ResultSet rs = sql.select(conn, 
                        "create temporary table selected (connDesc varchar(200),accom varchar(50))");
                    for(Object o : selectedIndices){
                       String option = o.toString();
    // extract connDesc+accom from displayed option
                       msg.g(option);
                    }        
                    conn.close();
                } catch (SQLException e) {
                   System.out.println(e.getMessage()+ " from init");
                }         
            }
        });   // end of display handler
        // quit  button
        final Button resetButton = new Button("Quit");
        resetButton.setOnAction(new EventHandler<ActionEvent>() {
        @Override
            public void handle(ActionEvent event) {
                Platform.exit();
            }
        });
        final HBox controls = new HBox(10);
        controls.setAlignment(Pos.CENTER);
        controls.getChildren().addAll(displayButton, resetButton);

        view = new VBox(10);
        view.setAlignment(Pos.CENTER);
        view.setStyle("-fx-padding: 10; -fx-background-color: cornsilk;");
        view.getChildren().setAll(listView, controls);
        view.setPrefWidth(320);


    }  

    public Parent getView() {
        return view ;
    }

}

现在如果你想自己测试一下,你可以为它写一个应用程序:

public class MultiListApp extends Application {

    @Override
    public void start(Stage primaryStage) {
        MultiList multiList = new MultiList() ;
        Scene scene = new Scene(multiList.getView());
        primaryStage.setScene(scene);
        primarStage.setTitle("Select one or more options");
        primaryStage.show();
    }
}

或者在InputData.fxml的控制器类中,你可以做同样的事情:

public class InputDataController {

    @FXML
    private void someEventHandler() {
        MultiList multiList = new MultiList() ;
        Scene scene = new Scene(multiList.getView());
        Stage stage = new Stage();
        stage.setScene(scene);
        stage.setTitle("Select one or more options");
        stage.show();
    }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-01-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-02
    相关资源
    最近更新 更多