首页 > 解决方案 > 如何保证每个Controller都能看到模型并且只初始化一次?

问题描述

在我的 mainController 中,我使用以下方法来更改视图:

@FXML
public void handleChangeView(ActionEvent event) {
    try {
        String changeButtonID = ((Button) event.getSource()).getId();
        FXMLLoader loader = new FXMLLoader(getClass().getResource("../../resources/view/" + changeButtonID + ".fxml"));
        mainView.setCenter(loader.load());
    } catch (IOException e){
e.printStackTrace();
    }
}

现在这是可行的,但我有两个问题:

1) 每个按钮单击加载的 FXML 文件的控制器再次触发。例如,在我的另一个控制器中,我有:

            Timeline counterTimeline = new Timeline(new KeyFrame(Duration.seconds(1), e -> System.out.println("Test")));
            counterTimeline.setCycleCount(Animation.INDEFINITE);
            counterTimeline.play();

每次点击似乎都会创建一个新的时间线并设置为播放 - 我如何确保不会发生这种情况?似乎每次单击更改视图按钮时,控制器都会重新初始化。

2)如何确保每个控制器都可以看到模型,同时仍然使用上述方法更改视图?我宁愿避免依赖注入,因为老实说我无法绕开它 - 在尝试让 afterburner.fx 工作 6 小时后,我无法处理它。

标签: javafxmodel-view-controller

解决方案


每种类型只能创建一次新的 fxml 节点:

private final Map <String, Parent> fxmls = new HashMap<>();

@FXML
public void handleChangeView(ActionEvent event) {
   try {
    String changeButtonID = ((Button) event.getSource()).getId();
    Parent newOne = fxmls.get(changeButtonID);
    if (newOne == null) {
      FXMLLoader loader = new FXMLLoader(getClass().getResource("../../resources/view/" + changeButtonID + ".fxml"));
      newOne = loader.load();
      fxmls.put(changeButtonID, newOne):
    }
    mainView.setCenter(newOne);
  } catch (IOException e){
    e.printStackTrace();
  }
}

推荐阅读