gpt4 book ai didi

java - 自动更新嵌套项的 TreeView

转载 作者:行者123 更新时间:2023-12-01 12:35:04 27 4
gpt4 key购买 nike

我有一个目标,其中有一个目标列表。目标有一个策略列表。战略有一系列战术。策略有一个任务列表。

我希望能够在 TreeView 中显示它,并且我希望树与项目同步。也就是说,如果我删除一个目标,该目标及其子目标也将从 TreeView 中消失。

到目前为止,这就是我一直在尝试的。

/**
* The base class for all PlanItems, which include ActionItems down to
* ActionTasks, and Objectives down to Tasks.
*
* @author Toni-Tran
*/
public class PlanItem implements Comparable<PlanItem> {
protected ObservableList<PlanItem> childPlanItems = FXCollections
.observableArrayList();
protected TreeItem<PlanItem> treeItem = new TreeItem<>(this);

这是所有这些项目的基类。在其构造函数中:

public PlanItem() {
CustomBinding.bindLists(treeItem.getChildren(), childPlanItems, PlanItem::getTreeItem);
}

我正在使用自定义绑定(bind),它将两个不同对象的列表绑定(bind)在一起。 (或者,我可以使用 EasyBind)。

/**
* Binds a source list's elements to a destination list. Any changes made in
* the source list will reflect in the destination list.
*
* @param <SRC> The source list's object type.
* @param <DEST> The destination list's object type.
* @param dest The destination list that will be bound to the src list.
* @param src The source list to watch for changes, and propagate up to the
* destination list.
* @param transformer A function that will transform a source list data
* type, A, into a destination list data type, B.
*/
public static <SRC extends Object, DEST extends Object> void bindLists(
ObservableList<DEST> dest, ObservableList<SRC> src, Function<SRC, DEST> transformer) {
/*Add the initial data into the destination list.*/
for (SRC a : src) {
dest.add(transformer.apply(a));
}
/*Watch for future data to add to the destination list. Also watch for removal
of data form the source list to remove its respective item in the destination
list.*/
src.addListener((ListChangeListener.Change<? extends SRC> c) -> {
while (c.next()) {
/*Watch for removed data.*/
if (c.wasRemoved()) {
for (SRC a : c.getRemoved()) {
int from = c.getFrom();
dest.remove(from);
}
}
/*Watch for added data.*/
if (c.wasAdded()) {
for (SRC a : c.getAddedSubList()) {
int indexAdded = src.indexOf(a);
dest.add(indexAdded, transformer.apply(a));
}
}
}
});
}

我不确定这是否是正确的方法。子项列表通常是扩展 PlanItem 的对象列表,而不仅仅是 PlanItem 本身。不应该是 ObservableList<? extends PlanItem>然后?这样做会使我的其余代码变得复杂。

计划是创建一个包装 PlanItem 的 TreeItem。然后,将 TreeItem 的子 TreeItem 同步到 PlanItem 的子 PlanItem。这也会对每个嵌套的 PlanItem 递归重复。

最佳答案

您的bindLists方法非常通用,并且可以在不引用您现在正在使用的列表的情况下编写(就像您现在拥有的那样)(即不引用 PlanItem 类)。所以我可能会成功

public static <SRC, DEST> void bindLists(ObservableList<DEST> dest, ObservableList<SRC> src, ...) { ... }

请注意,映射函数只需能够应用于 src 的元素(因此它必须对 src 的元素是一种类型的事物起作用)并生成可以放入 dest 中的东西。列表。所以使用Function<SRC, DEST>可能限制太多。尝试一下

public static <SRC, DEST> void bindLists(ObservableList<DEST> dest, ObservableList<SRC> src, 
Function<? super SRC, ? extends DEST> transformer) { ... }

现在您可以调用

bindLists(ObservableList<TreeItem<PlanItem>>, ObservableList<T>, PlanItem::getTreeItem)

哪里TPlanItem 或任何子类,并且它应该易于使用。

关于java - 自动更新嵌套项的 TreeView,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25656094/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com