我正在和几个人一起开展一个项目,我的任务是编译一个工作的JTree来显示一个set目录的结构。实际上,JTree在类启动时显示正确的文件和文件夹结构。但是,我似乎无法让它能够在添加或减少文件时更新(而不是使用JTree)。在我快乐的无知(非常有远见的那个)中,我添加了一个JButton;
treeModel.reload();
......希望能做到这一点。它确实重新加载了JTree,但是没有改变文件结构,即使在加载类之后添加了几个文件。
因此,我信任这个社区,既指出了我的问题的根源,又指出了语义和逻辑方面的其他缺陷。我是一个愿意学习的人。
public class FileTree extends JPanel {
private JTree tree;
private DefaultMutableTreeNode root;
private DefaultTreeModel treeModel;
public FileTree(JPanel jp) {
jp.setLayout(new BorderLayout());
final File directory = getDir();
createTree(directory);
tree = new JTree(treeModel);
tree.setRootVisible(true);
tree.setShowsRootHandles(true);
tree.getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);
tree.setCellRenderer(new FileTreeCellRenderer());
tree.addMouseListener(new MouseAdapter() {
public void mousePressed(MouseEvent e) {
TreePath selPath = tree.getPathForLocation(e.getX(), e.getY());
if(e.getClickCount() == 2) {
Object n = selPath.getLastPathComponent();
String sel = n.toString();
File nodeFile = new File(sel);
if(nodeFile.isDirectory() && (!nodeFile.isHidden())) {
UserWindow.printToLog("doubble-click event on folder: " + nodeFile.getName());
//TODO:stuff happening here
}
if(nodeFile.isFile() && (!nodeFile.isHidden())) {
UserWindow.printToLog("doubble-click event on file: " + nodeFile.getName());
new FileTreeEventHandler(nodeFile);
}
}
}
});
JScrollPane sp = new JScrollPane(tree);
jp.add(sp);
JButton updateButton = new JButton("Update");
updateButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent arg0) {
treeModel.reload();
}
});
jp.add(updateButton, BorderLayout.SOUTH);
setVisible(true);
}
private void createTree(File directory) {
root = new DefaultMutableTreeNode();
treeModel = new DefaultTreeModel(root);
DefaultMutableTreeNode node = new DefaultMutableTreeNode(directory);
root.add(node);
populate(directory, node);
}
private void populate(File directory, DefaultMutableTreeNode node) {
String[] files = directory.list();
for(String file : files) {
File currentFile = new File(directory, file);
addLeaf(node, currentFile);
}
}
private void addLeaf(DefaultMutableTreeNode node, File currentFile) {
if(currentFile.isFile() && !currentFile.isHidden()) {
DefaultMutableTreeNode leafFile = new DefaultMutableTreeNode(currentFile);
node.add(leafFile);
}
if(currentFile.isDirectory() && !currentFile.isHidden()) {
DefaultMutableTreeNode folder = new DefaultMutableTreeNode(currentFile);
node.add(folder);
populate(currentFile, folder);
}
}
private File getDir() {
String path = new File(System.getProperty("user.dir"), "downloaded content").getAbsolutePath();
File dir = new File(path);
if(!dir.exists()) {
dir.mkdirs();
}
return dir;
}
}
答案 0 :(得分:1)
DefaultTreeModel#reload
基本上陈述......
如果您修改了TreeNodes,则调用此方法 模特取决于。该模型将通知其所有听众 模型在给定节点下面发生了变化。
这假设模型本身已经改变。
你至少有两个基本的行动方案......
你可以......
DefaultTreeModel
或DefaultTreeModel
... 然后重新构建模型。
如果您创建新的TreeModel
,请确保将其设置为JTree
。
这有点沉重,但即使您选择编写填充算法以便检查模型的现有内容,您仍然需要遍历文件结构。
更新模型可以让您保留JTree
的某些状态(例如,扩展或未扩展的节点)
如果您足够幸运使用Java 7,您还可以利用File Watcher API,例如,您可以将每个目录节点设置为观察者服务,以监控它自己的内容和发生更改时更新自身(添加/删除节点)。
答案 1 :(得分:1)
treeModel.reload();
我猜你需要调用:
,而不只是调用上面的代码createTree(directory);
tree.setModel(treeModel);
重新创建TreeModel以反映新的目录结构。