如何将 ObjectProperty<?> 与 fxml 和 PropertyValueFactory 一起使用?

How to use ObjectProperty<?> with fxml and PropertyValueFactory?

我有这个TableView

<TableView fx:id="tableView">
  <columns>
    <TableColumn prefWidth="220.0" text="Source">
      <cellValueFactory>
        <PropertyValueFactory property="sourceContract" />
      </cellValueFactory>
    </TableColumn>
  </columns>
  <items>
    <FXCollections fx:factory="observableArrayList">
      <GridRowModel sourceContract="some contract" />
    </FXCollections>
  </items>
</TableView>

还有这些类

public class GridRowModel {

  private ObjectProperty<ContractConfig> sourceContract = new SimpleObjectProperty<>();

  public GridRowModel() {
  }

  public ObjectProperty<ContractConfig> sourceContractProperty() {
    return sourceContract;
  }

  public ContractConfig getSourceContract() {
    return sourceContract.get();
  }

  public void setSourceContract(ContractConfig sourceContract) {
    this.sourceContract.set(sourceContract);
  }
}

public class ContractConfig {

  private String name;
  private String userFriendlyName;

  public ContractConfig() {
  }

  public ContractConfig(String name) {
    this.name = name;
  }

  public void setName(String name) {
    this.name = name;
  }

  public void setUserFriendlyName(String userFriendlyName) {
    this.userFriendlyName = userFriendlyName;
  }

  public String getName() {
    return name;
  }

  public String getUserFriendlyName() {
    return userFriendlyName;
  }
}

我收到这个明显的错误:

Caused by: java.lang.IllegalArgumentException: Unable to coerce some contract to class com.ui.util.ContractConfig.
    at com.sun.javafx.fxml.BeanAdapter.coerce(BeanAdapter.java:496)
    at com.sun.javafx.fxml.BeanAdapter.put(BeanAdapter.java:258)
    at com.sun.javafx.fxml.BeanAdapter.put(BeanAdapter.java:54)

我也试过这个

  public void setSourceContract(String sourceContract) {
    ContractConfig cc = new ContractConfig();
    cc.setUserFriendlyName(sourceContract);
    this.sourceContract.set(cc);
  }

但是我得到这个错误

Caused by: com.sun.javafx.fxml.PropertyNotFoundException: Property "sourceContract" does not exist or is read-only.
    at com.sun.javafx.fxml.BeanAdapter.put(BeanAdapter.java:253)
    at com.sun.javafx.fxml.BeanAdapter.put(BeanAdapter.java:54)
    at javafx.fxml.FXMLLoader$Element.applyProperty(FXMLLoader.java:512) 

是否可以将 ObjectProperty 与 FXML 值一起使用?如果可以,我如何在 FXML 中使用我的 ContractConfig 对象?

您为您创建的 class 结构使用了错误的 fxml 代码。它应该看起来像这样:

<GridRowModel>
    <sourceContract>
        <ContractConfig name="some contract"/> 
    </sourceContract>
</GridRowModel>

你也可以用@NamedArg添加一个构造函数到GridRowModel并使用

<GridRowModel sourceContract="some contract" />
private final ObjectProperty<ContractConfig> sourceContract;

private GridRowModel(ContractConfig sourceContract) {
    this.sourceContract = new SimpleObjectProperty<>(sourceContract);
}

public GridRowModel() {
    this((ContractConfig) null);
}

public GridRowModel(@NamedArg("sourceContract") String sourceContract) {
    this(new ContractConfig(sourceContract));
}