Ho una ListView piena di POJO e voglio un'etichetta nella GUI per visualizzare le informazioni dall'elemento selezionato.Come associare un'etichetta JavaFX all'elemento selezionato da un ListView
mio POJO sembra qualcosa di simile:
class Customer {
private String name;
...
public String getName() {
return name;
}
Ora, quando l'utente seleziona un cliente dalla lista Voglio il nome del cliente selezionato visualizzato in un'etichetta.
Ovviamente non posso eseguire il binding allo name
direttamente perché non è un Property
. (E io non voglio sostituire i miei clienti String
s con StringProperty
-Oggetti perché il SimpleStringProperty
non è serializable
e ho bisogno del Customer
da trasferire tramite RMI.)
Ho provato il BeanPathAdapter
da JFXtras (che sembra davvero bello tra l'altro) in questo modo:
BeanPathAdapter<MultipleSelectionModel> customerBeanPathAdapter;
customerBeanPathAdapter = new BeanPathAdapter<>(lstCustomers.getSelectionModel());
customerBeanPathAdapter.bindBidirectional("selectedItem.name", lblCustomerName.textProperty());
Ma questa soluzione mi butta solo un'eccezione:
...
Caused by: java.lang.IllegalArgumentException: Unable to resolve accessor getSelectedItem
at jfxtras.labs.scene.control.BeanPathAdapter$FieldHandle.buildAccessor(BeanPathAdapter.java:3062)
at jfxtras.labs.scene.control.BeanPathAdapter$FieldHandle.buildAccessorWithLikelyPrefixes(BeanPathAdapter.java:3022)
at jfxtras.labs.scene.control.BeanPathAdapter$FieldHandle.updateMethodHandles(BeanPathAdapter.java:2986)
at jfxtras.labs.scene.control.BeanPathAdapter$FieldHandle.<init>(BeanPathAdapter.java:2977)
at jfxtras.labs.scene.control.BeanPathAdapter$FieldBean.performOperation(BeanPathAdapter.java:1348)
at jfxtras.labs.scene.control.BeanPathAdapter$FieldBean.performOperation(BeanPathAdapter.java:1186)
at jfxtras.labs.scene.control.BeanPathAdapter.bindBidirectional(BeanPathAdapter.java:567)
at jfxtras.labs.scene.control.BeanPathAdapter.bindBidirectional(BeanPathAdapter.java:369)
at at.gs1.sync.qm.client.gui.MainWindowController.initialize(MainWindowController.java:61)
... 22 more
Caused by: java.lang.IllegalAccessException: symbolic reference class is not public: class javafx.scene.control.ListView$ListViewBitSetSelectionModel, from jfxtras.labs.scene.control.BeanPathAdapter$FieldHandle
at java.lang.invoke.MemberName.makeAccessException(MemberName.java:512)
at java.lang.invoke.MethodHandles$Lookup.checkSymbolicClass(MethodHandles.java:1113)
at java.lang.invoke.MethodHandles$Lookup.resolveOrFail(MethodHandles.java:1094)
at java.lang.invoke.MethodHandles$Lookup.findVirtual(MethodHandles.java:626)
at jfxtras.labs.scene.control.BeanPathAdapter$FieldHandle.buildAccessor(BeanPathAdapter.java:3049)
... 30 more
Quindi speravo che ci sarebbe stata una soluzione migliore che usare lstCustomers.getSelectionModel().selectedItemProperty().addListener(...)
e gestire manualmente la popolazione delle etichette.
Parte del problema è l'accesso implementazione limitato (sembra la l'adattatore non può gestirlo). Un altro potrebbe essere un errore o un'aspettativa non valida (anche la mia :-) - l'aggiornamento del valore sembra avvenire solo nella direzione dalla proprietà legata alla proprietà adattata (cioè il percorso), non viceversa. Almeno non riusciva a farlo funzionare con i bean più semplici, nessuno dei quali con proprietà fx, né una proprietà java bean core semplice. – kleopatra