簡體   English   中英

JavaFX復雜字符串綁定

[英]JavaFX complex string binding

我是JavaFX的新手,想知道Bindings API是否允許一種更簡單的方法來實現以下目標。 考慮一個模型,該模型包含一個可能為null的數據庫(因為該數據庫是異步加載的)和一個視圖,該視圖顯示反映數據庫狀態的標簽status 如果為null,則應顯示“正在加載...”之類的信息;否則,應顯示數據庫中有多少項。 如果狀態可以反映數據庫的大小(隨着數據庫的增長或縮小),那也將是一個很好的選擇。

到目前為止,我知道可以使用轉換器將整數屬性(數據庫的大小)綁定到標簽的text屬性。 很好,但是我希望標簽顯示的數字多於數字。 一個精確的本地化字符串,例如“已加載{0}個項目”。 並且不要忘了數據庫可能仍然為空。

這是我已有的解決方案

@Override
public void initialize(URL url, ResourceBundle bundle) {
    // Initialize label with default value
    status();
    model.databaseProperty().addListener((obs, old, neu) -> {
        // Update label when database is no longer null
        status();
        // Update label when size of database changes
        neu.sizeProperty().addListener(x -> status());
    });
}

public void status() {
    if (model.database() == null) {
        status.setText(bundle.getString("status.loading"));
    } else {
        String text = bundle.getString("status.ready");
        int size = model.database().size();
        text = new MessageFormat(text).format(size);
        status.setText(text);
    }
}

它有效,但是有沒有辦法用一連串的綁定或至少一部分綁定呢? 我已經看到了布爾綁定有多么強大(和冗長),但是我不確定字符串綁定是否可以實現某些靈活的功能。

您可以使用Bindings.when ,它實質上是一個動態的if / then綁定: *

status.textProperty().bind(
    Bindings.when(model.databaseProperty().isNull())
        .then(bundle.getString("status.loading"))
        .otherwise(
            Bindings.selectInteger(model.databaseProperty(), "size").asString(
                bundle.getString("status.ready")))
);

但是,以上假設bundle.getString("status.ready")返回的是java.util.Formatter字符串,而不是MessageFormat字符串。 換句話說,它將需要是"Loaded %,d items"而不是"Loaded {0,number,integer} items"

綁定不具有對MessageFormat的內置支持,但是如果您真的想堅持使用MessageFormat(這是一個合法的要求,因為MessageFormat可以做某些格式化程序無法做到的事情),則可以使用Bindings.createStringBinding創建自定義綁定。

MessageFormat statusFormat = new MessageFormat(bundle.getString("status.ready"));

status.textProperty().bind(
    Bindings.when(model.databaseProperty().isNull())
        .then(bundle.getString("status.loading"))
        .otherwise(
            Bindings.createStringBinding(
                () -> statusFormat.format(new Object[] { model.getDatabase().getSize() }),
                model.databaseProperty(),
                Bindings.selectInteger(model.databaseProperty(), "size")))
);

*其實更像是三元? :操作員。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM