我如何获得JavaFX控制器的实例

问题描述 投票:0回答:1

我陷入了我的代码中。我正在写一个包含许多控制器的库系统。这是我的主控制器fxml文件:

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.control.Menu?>
<?import javafx.scene.control.MenuBar?>
<?import javafx.scene.control.MenuItem?>
<?import javafx.scene.control.Tab?>
<?import javafx.scene.control.TabPane?>
<?import javafx.scene.layout.Pane?>
<?import javafx.scene.layout.VBox?>

<Pane prefWidth="800.0" xmlns="http://javafx.com/javafx/8.0.141" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.library.controllers.MainController">
   <children>
  <VBox>
     <children>
        <MenuBar>
           <menus>
              <Menu mnemonicParsing="false" text="Plik">
                 <items>
                    <MenuItem fx:id="Users" mnemonicParsing="false" onAction="#onUsersMenuAction" text="Użytkownicy" />
                    <MenuItem fx:id="Backup" mnemonicParsing="false" onAction="#onBackupMenuAction" text="Wykonaj kopię zapasową" />
                    <MenuItem fx:id="CloseProgram" mnemonicParsing="false" onAction="#onCloseProgramMenuAction" text="Zakończ" />
                 </items>
              </Menu>
              <Menu mnemonicParsing="false" text="Raporty">
                 <items>
                    <MenuItem fx:id="ActiveRentedBooks" mnemonicParsing="false" onAction="#onActiveRentedBooksMenuAction" text="Aktywne wypożyczenia" />
                    <MenuItem fx:id="ActiveBorrowers" mnemonicParsing="false" onAction="#onActiveBorrowersMenuAction" text="Aktualni dłużnicy" />
                    <MenuItem fx:id="ReportOfRentedBooksPerDay" mnemonicParsing="false" onAction="#onReportOfRentedBooksPerDayMenuAction" text="Raport wypożyczeń/dzień" />
                 </items>
              </Menu>
              <Menu mnemonicParsing="false" text="Słowniki">
                 <items>
                    <MenuItem fx:id="Categories" mnemonicParsing="false" onAction="#onCategoriesMenuAction" text="Kategorie" />
                    <MenuItem fx:id="UKDDictionary" mnemonicParsing="false" onAction="#onUKDDictionaryMenuAction" text="Słownik UKD" />
                    <MenuItem fx:id="ReasonsForDefects" mnemonicParsing="false" onAction="#onReasonForDefectsMenuAction" text="Powody ubytków" />
                 </items>
              </Menu>
              <Menu mnemonicParsing="false" text="Wydruki">
                 <items>
                    <MenuItem fx:id="PrintBookLabel" mnemonicParsing="false" onAction="#onPrintBookLabelActionButton" text="Drukuj etykietę książki" />
                    <MenuItem fx:id="PrintCardOfLoans" mnemonicParsing="false" onAction="#onPrintCardOfLoansMenuAction" text="Drukuj kartę wypożyczająćego" />
                 </items>
              </Menu>
              <Menu mnemonicParsing="false" text="Ustawienia">
                 <items>
                    <MenuItem fx:id="GeneralOptions" mnemonicParsing="false" onAction="#onGeneralOptionsMenuAction" text="Ogólne" />
                 </items>
              </Menu>
           </menus>
        </MenuBar>
        <TabPane prefHeight="547.0" prefWidth="800.0" tabClosingPolicy="UNAVAILABLE">
           <tabs>
              <Tab fx:id="KBooks" text="Książki">
                  <fx:include source="Book.fxml" />
              </Tab>
              <Tab fx:id="CReaders" text="Czytelnicy">
                  <fx:include source="Readers.fxml" />
              </Tab>
              <Tab fx:id="WLoans" text="Wypożyczenia">
                  <fx:include source="Borrows.fxml" />
              </Tab>
              <Tab fx:id="ZReturns" text="Zwroty" >
                  <fx:include source="Return.fxml" />
              </Tab>
              <Tab fx:id="Communication" text="Komunikaty" >
                  <fx:include source="Comunication.fxml" />
              </Tab>
           </tabs>
        </TabPane>
     </children>
  </VBox>
   </children>
</Pane>

如您所见,每个选项卡都有自己的控制器。我想从一个控制器发送数据到另一个包含控制器(从Readers.fxml控制器到Borrows.fxml控制器。我的代码:READER CONTROLLER

    @FXML
void onCRentActionButton(ActionEvent event) throws IOException {
    if(CTable.getSelectionModel().getSelectedItem()==null)
    {
        Alert alert = new Alert(Alert.AlertType.ERROR);
        alert.setTitle("Błąd !!!");
        alert.setHeaderText("Nie możesz edytować użytkownika, jeśli żadnego"
                + "nie zaznaczyłeś w tabeli!!");
        alert.showAndWait();
    }
    else
    {
        FXMLLoader loader = new FXMLLoader(getClass().getResource("/fxml/Borrows.fxml"));
        loader.load();
        logger.info("Kontroller pliku Borrows.fxml to: "+ loader.<BorrowController>getController().getClass());
        BorrowController controller = loader.<BorrowController>getController();
        ReaderBorrow rb;
        int id=CTable.getSelectionModel().getSelectedItem().getId();

        rb = SQLController.getInstance().getReaderToBorrow(id);
        controller.setReader(rb);
}

BORROW控制器

public void setReader(ReaderBorrow rb)
{
    logger.info("Ustawianie nazwiska: " + rb.getSurname());
    this.WSurname.setText(rb.getSurname());
    logger.info("Odczyt wartości: " + WSurname.getText());
}

我有一个很好的信息,数据成功发送。并且WSurname.getText()方法返回一个很好的信息。但在我看来,WSurname TextField仍然是空的。我想,当我在ReadersController中调用getController方法时,我得到另一个BorrowController实例。如何将数据设置为TextField正确?

javafx textfield
1个回答
0
投票

您有错误的BorrowController实例:在onCRentActionButton()中,您再次加载Borrows.fxml,获取UI的新副本,然后获得与该新副本关联的控制器。由于永远不会显示该UI的新副本,因此您正在更新您看不到的内容。

而是将不同选项卡的控制器注入主控制器。根据documentation,您可以使用fx:id<fx:include>注入控制器,并附加"Controller"

所以在MainController中,添加:

@FXML
private BorrowController borrowController ;
@FXML
private ReaderController readerController ;

fx:ids添加到<fx:include>s:

  <Tab fx:id="CReaders" text="Czytelnicy">
      <fx:include fx:id="reader" source="Readers.fxml" />
  </Tab>

  <Tab fx:id="WLoans" text="Wypożyczenia">
      <fx:include fx:id="borrow" source="Borrows.fxml" />
  </Tab>

要链接控制器,您需要在borrowController中引用ReaderController

public class ReaderController {

    private BorrowController borrowController ;

    public void setBorrowController(BorrowController borrowController) {
        this.borrowController = borrowController ;
    }

    // ...
}

您需要在主控制器的initialize()方法中设置:

public class MainController {

    @FXML
    private BorrowController borrowController ;
    @FXML
    private ReaderController readerController ;

    // ...

    public void initialize() {
        readerController.setBorrowController(borrowController);
        // ...
    }

    // ...
}

最后你可以做到

@FXML
void onCRentActionButton(ActionEvent event) throws IOException {
    if(CTable.getSelectionModel().getSelectedItem()==null) {
        Alert alert = new Alert(Alert.AlertType.ERROR);
        alert.setTitle("Błąd !!!");
        alert.setHeaderText("Nie możesz edytować użytkownika, jeśli żadnego"
                + "nie zaznaczyłeś w tabeli!!");
        alert.showAndWait();
    } else {
        ReaderBorrow rb;
        int id=CTable.getSelectionModel().getSelectedItem().getId();

        rb = SQLController.getInstance().getReaderToBorrow(id);
        borrowController.setReader(rb);
    }
}

如果使用MVC approach并将状态保存在模型类中,则可以避免这些控制器之间的所有耦合。

© www.soinside.com 2019 - 2024. All rights reserved.