【问题标题】:Javafx tableview with data from multiple classes具有来自多个类的数据的 Javafx 表视图
【发布时间】:2016-04-06 22:07:45
【问题描述】:

用 1 个类的不同数据填充我的 tableview 没有问题。但它不适用于我的多个课程。知道如何解决吗? 我已经在 stackoverflow 上查看了类似的问题。但他们都无法帮助我。如果您对“回调”类提出任何建议,请向我提供完整的导入,因为那里有几个回调类。

public class MainViewController implements Initializable {

    @FXML
    private TableColumn<TaskControl, Boolean> colErledigt;

    @FXML
    private TableColumn<TaskControl, Character> colPrioritaet;

    @FXML
    private TableColumn<TaskControl, String> colBeschreibung;


    @FXML
    private TableColumn<ProjectControl, String> colProjekt;


    @FXML
    private TableView<TaskControl> tblView;





    public final void initialize(final URL location,
            final ResourceBundle resources) {

        initializeTableElements();

    }


    public final void initializeTableElements() {
        colBeschreibung
                .setCellValueFactory(new PropertyValueFactory<>("description"));

        colPrioritaet
                .setCellValueFactory(new PropertyValueFactory<>("priority"));


        colProjekt.setCellValueFactory(new PropertyValueFactory<>("name"));


        colErledigt.setMaxWidth(50);
        colErledigt.setCellValueFactory(
                new PropertyValueFactory<TaskControl, Boolean>("isDone"));
        colErledigt
                .setCellFactory(CheckBoxTableCell.forTableColumn(colErledigt));
        colErledigt.setEditable(true);

        try {
            tblView.setItems(getObsTasks());
        } catch (IDNotValidException | StringNotValidException e1) {
            System.out.print("FEHLER beim getObsTasks");
        }

        tblView.setEditable(true);
    }


    public ObservableList<TaskControl> getObsTasks()
            throws IDNotValidException, StringNotValidException {

        ObservableList<TaskControl> obsTasks = FXCollections
                .observableArrayList();

        Map<Context, Set<Task>> test = TasksContextUtility.INSTANCE
                .getAllContextsAndTasks();

        test.values().forEach(v -> {
            v.forEach(b -> obsTasks.add((TaskControl) b));
        });

        return obsTasks;
    }

进一步的问题:如何在 TableCell 的 HashSet 中显示实例的某个属性。所以我在我的TaskControl 类中有一个HashSet。在那个 HashSet 中有“ProjectControl”类的实例。 ProjectControl 的每个实例都有“name”或“id”等属性。

如果可能,我想在 1 个表格单元格中表示项目实例的所有名称。可能是用逗号分隔的字符串 (project1,project2,project3...)。

任务类(缩短了很多)我的TaskControl类继承自这个类

public abstract class Task
  implements Serializable, IDValidatable
{
  private int id;
  private char priority = ' ';
  private final Set<Project> projects = new HashSet();

  public Task(int oid)
    throws IDNotValidException
  {
    if (isIDValid(oid)) {
      this.id = oid;
    } else {
      throw new IDNotValidException("The ID you have specified is not valid!")
      {
        private static final long serialVersionUID = 99044660889990790L;
      };
    }
  }

  public final void setId(int oid)
    throws IDNotValidException
  {
    if (isIDValid(oid)) {
      this.id = oid;
    } else {
      throw new IDNotValidException("The ID you have specified is not valid!")
      {
        private static final long serialVersionUID = 99044660889990790L;
      };
    }
  }

  public final int getId()
  {
    return this.id;
  }

  public final Collection<Context> getContexts()
  {
    return this.contexts;
  }

  public final void addContext(Context context)
    throws ContextNotValidException
  {
    this.contexts.add(context);
  }

  public final void removeContext(Context context)
    throws ContextNotValidException
  {
    this.contexts.remove(context);
  }

  public final Collection<Project> getProjects()
  {
    return this.projects;
  }

  public final void addProject(Project project)
    throws ProjectNotValidException
  {
    this.projects.add(project);
  }

  public final void removeProject(Project project)
    throws ProjectNotValidException
  {
    this.projects.remove(project);
  }

  public final Map<String, String> getAddons()
  {
    return this.addons;
  }
}

【问题讨论】:

  • a TableView 旨在显示一种类型的行。如果您需要来自各种类型的数据,我认为您最好的选择是创建一个包装类,其中包含两个实例作为字段,并在表中公开您想要的所有属性。
  • 如果TableView 的类型是TaskControl,那么正如@sillyfly 所说,每一行都必须包含TaskControl 类型的项目。 TableColumn 的两种类型依次是行中项目的类型和列的每个单元格中的项目类型。所以TableColumn 中的第一个类型必须 匹配TableView 的类型:没有其他任何意义。为什么要让不同的列有不同类型的行项?
  • 谢谢大家!现在我离解决这个问题更近了。这是新的情况。我的 TaskControl 类中有一组我的 ProjectControl 类的实例。我需要表示每个实例的“名称”属性。 TableCell 可以代表它吗?
  • 你能edit你的问题显示与此相关的代码吗?
  • 完成。如果您需要更多代码,请告诉我。

标签: java javafx tableview tablecolumn observablelist


【解决方案1】:

通过向我的 TaskControl 添加一个额外的字符串来解决它,其中包含它所包含的所有项目的名称。它通过我在为表列创建 ObservableList 之前调用的函数获取名称。

private String projectsAsString;
    ...
public final void convertProjectsToString() {

    String projects = "";

    for (Project p : this.getProjects()) {
        ProjectControl pp = (ProjectControl) p;
        projects += pp.getName() + ", ";
    }
    if (projects != null && projects != "" && projects.length() > 4) {
        projects = projects.substring(0, projects.length() - 2);
    }
    this.projectsAsString = projects;
}

还是谢谢你们帮助我。

【讨论】:

    【解决方案2】:

    在我看来,你只有一个很好的解决方案。

    您需要一个额外的类来保存您的 TaskControl、ContextControl 和 ProjectControl。

    您的代码可能看起来像这样。

    class Wrapper{
     private TaskControl taskControl;
     private ContextControl contextControl;
     private ProjectControl projectControl;
     ...
     public Boolean isDone(){
       return taskControl != null ? taskControl.isDone() : null;
      }
    }
    
    
    @FXML
    private TableView<Wrapper> tblView;
    
    @FXML
    private TableColumn<Wrapper, Boolean> colErledigt;
    
    colErledigt.setCellValueFactory(
                new PropertyValueFactory<Wrapper, Boolean>("isDone"));
    

    【讨论】:

    • 传递给工厂的正确属性名称是"done",而不是"isDone"。否则 PropertyValueFactory 将寻找 getIsDoneisIsDoneisDoneProperty 方法...
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-01-16
    • 1970-01-01
    相关资源
    最近更新 更多