我有一個JavaFX服務,並希望在服務更新自定義屬性時通過回調得到通知。通常,這樣做的方式是該服務具有一些內置的屬性,如「狀態」,「workDone」,「價值」等。最想與我想模仿的是名爲「value」的屬性。 「value」屬性在服務類中定義如下。收聽SimpleListProperty <T>來自JavaFX服務的更新
private final ObjectProperty<V> value = new SimpleObjectProperty<>(this, "value");
@Override public final V getValue() { checkThread(); return value.get(); }
@Override public final ReadOnlyObjectProperty<V> valueProperty() { checkThread(); return value; }
In my case I needed to listen to updates to a pair of message objects being updated by my JavaFX service thread, so I added a custom named property for each one as shown below.
// add 'heartbeat' bound property
private final ObjectProperty<CAServiceHeartbeatMessage> heartbeat =
new SimpleObjectProperty<>(this, "heartbeat", null);
public CAServiceHeartbeatMessage getHeartbeat() {
return heartbeat.get();
}
public void setHeartbeatMessage(CAServiceHeartbeatMessage aHeartbeat) {
heartbeat.set(aHeartbeat);
}
public ObjectProperty<CAServiceHeartbeatMessage> heartbeatProperty() {
return heartbeat;
}
// add 'memberSystemStatus' bound property
private final ObjectProperty<MemberSystemStatusMessage> memberSystemStatus =
new SimpleObjectProperty<>(this, "memberStatus", null);
public MemberSystemStatusMessage getMemberStatus() {
return memberSystemStatus.get();
}
public void setMemberSystemMessage(MemberSystemStatusMessage aMemberSystemStatus) {
memberSystemStatus.set(aMemberSystemStatus);
}
public ObjectProperty<MemberSystemStatusMessage> memberSystemStatusProperty() {
return memberSystemStatus;
}
然後在控制器類添加以下代碼來更新基於變化到每個這些屬性的GUI:
// heartbeatMessageProperty listener
// Update the GUI widgets when a new CAServiceHeartbeatMessage (heartbeatMessage) is updated
mListenerService.heartbeatProperty().addListener(
(ObservableValue<? extends CAServiceHeartbeatMessage> observer,
CAServiceHeartbeatMessage oldValue, CAServiceHeartbeatMessage newValue) -> {
// this is where we need to intelligently update the appropriate
// heartbeat service entries
System.out.println("updated CAServiceHeartbeatMessage");
});
// 'memberSystemMessage' bound property listener
mListenerService.memberSystemStatusProperty().addListener(
(ObservableValue<? extends MemberSystemStatusMessage> observer,
MemberSystemStatusMessage oldValue, MemberSystemStatusMessage newValue) -> {
if (newValue == null) {
。 。 。
我的問題是,我怎樣才能替換多個SimpleObjectProperties
在我的JavaFX服務類中使用單個SimpleListProperty
或SimpleMapProperty
。我不知道如何,或者是否需要遵循一些屬性命名約定來公開我的線程中的一些簡單的列表屬性,就像我使用2個特定的和單獨命名的消息屬性一樣。 IT可能值得注意的是,這些消息共享一個通用的基類消息類 - 因此它們可以存儲在一個簡單的列表類型中。我還希望看到一個示例,說明如何處理更新,以便在更改發生時更新GUI,特別是我不知道如何確定列表或映射中的哪些元素髮生了更改。
感謝詳細的解答,我是新來的Java 8流和lambda表達式 - 我真的不明白是什麼在消息回事 - >新的可觀測[] {消息.messageProperty()}它的一個奇怪的語法,而相當混亂。此外,我的消息對象不能修改爲包含StringProperty - 它們是使用Javolution的有效結構,因此我無法更改它們的大小。我將如何將您的示例應用到公共類MyService extends Service {...}在我的情況下在類中我有2個單獨的SimpleObjectProperties,我想合併到一個ObservableArrayList? –
johnco3
如果你不需要監聽消息對象中元素的變化,你可以使用像上面展示的那樣的ListChangeListener。將你的消息放在一個'ObservableList'中,並且與你的基類消息類的類型相關,並附加這個監聽器。'ObservableList messages = FXCollections.observableArrayList(); messages.addAll(status1,status2,beat1,beat2); messages.addListener(...);' –
jns
這將允許您查看對消息列表進行的更改,例如添加節拍,移除狀態,但不會看到對列表元素本身所做的更改。這就是工廠方法的提取器所使用的。它將偵聽器附加到您指定的屬性,例如messageProperty():'FXCollections.observableArrayList(message - > new Observable [] {message.messageProperty()})' – jns