我有一个用 a 表示的数据对象TreeModel
,我想在我的 -- 中只显示它的一部分,JTree
为了争论,说叶子和他们的父母。如何隐藏/过滤不必要的节点?
7 回答
我的最终实现:
- 有两个
TreeModel
,底层的和过滤的。 - 当底层发生变化时,从头开始
TreeModel
重建过滤器。TreeModel
克隆每个应该可见的节点,并将其添加到过滤器中的第一个可见祖先TreeModel
(如果不可见,则添加到根)。如果您好奇,请参阅下面的 codez。 这具有折叠用户打开的每条路径的不幸副作用。为了解决这个问题,我
TreeModelListener
在过滤后的TreeModel
. 当模型发生变化时,我将展开的路径保存在JTree
(使用getExpandedDescendants()
)中,然后稍后重新展开(使用SwingUtilities.invokeLater()
)。我必须在我正在使用
equals()
的TreeNode
类中覆盖,以便新的克隆节点与旧的克隆节点相同。
...
populateFilteredNode(unfilteredRoot, filteredRoot);
...
void populateFilteredNode(TreeNode unfilteredNode, TreeNode filteredNode)
{
for (int i = 0; i < unfilteredNode.getChildCount(); i++)
{
TreeNode unfilteredChildNode = unfilteredNode.getChildAt(i);
if (unfilteredChildNode.getType() == Type.INVISIBLE_FOLDER)
{
populateFilteredNode(unfilteredChildNode, filteredNode);
}
else
{
TreeNode filteredChildNode = unfilteredChildNode.clone();
filteredNode.add(filteredChildNode);
populateFilteredNode(unfilteredChildNode, filteredChildNode);
}
}
}
您应该知道GlazedLists。这是一个很棒的库,可以轻松进行复杂的表转换。它们也扩展到树木。可能需要对现有代码进行一些重构才能使其进入 GlazedLists 的工作方式。但请查看演示和网络广播,看看它有多强大。(在我看来,它是必不可少的 Swing 库之一,而且它是开源的。)
你试过JXTree吗?(不幸的是,该网站现在已关闭,但您可以谷歌搜索镜像)
看看这个实现:http ://www.java2s.com/Code/Java/Swing-Components/InvisibleNodeTreeExample.htm
它创建 DefaultMutableNode 的子类,添加“isVisible”属性,而不是实际从 TreeModel 中删除/添加节点。
如果您正在寻找商业解决方案,JideSoft 有一个可过滤的树模型。除此之外,SwingX 有一个过滤器 API,可用于 JXTable、JXTreeTable、JXTree 和 JXList。
只要它仍然是您正在显示的树,那么TreeModel
您现有的过滤器TreeModel
应该足够简单。
利用您用于构建 TreeNode 的代码并仅重建 TreeNode(包括您想要的元素)。使用过滤的根节点设置 TreeModel 上的根节点。