JTree實現電腦資源管理器

0.前言

  最近老師佈置了一項用Java寫資源管理器的任務,一開始覺得簡單,可是實際操做起來,卻發現網上的資源用起來相對生疏。在使用中,我也遇到了許多問題,雖然不能像其餘博主同樣,寫的很是齊全,但我仍是分享一下我寫的代碼。java

1.準備知識

  • JTree是樹形結構,是咱們作資源管理器的必要組件。其構造函數的參數能夠是節點,或者樹模型。
  • JTree只有放在JScrollPane裏,才能夠很好的顯示(由於有時候樹很大,要拉很長才能看到),固然不放也能夠。
  • JTree是經過增長節點,來實現多層目錄的。
  • 通常使用DefaultMutableTreeNode來實現節點,能夠經過add()函數,添加孩子節點。
  • 還有些瑣碎的知識點,會在第三部分一一講述。

2.思路

  一開始的思路是用DFS深搜,可是實現後發現,至關的慢。node

  因此,我就想先寫一個「個人電腦」節點,而後往下加磁盤分區,而後當我點擊一個節點的時候(用事件監聽,這裏用到TreeSelectionListener),再往下展開(添加節點)git

3.分段代碼

  1.獲取系統的磁盤目錄

1 //獲取磁盤目錄
2 File roots[] = File.listRoots();
3 //添加至父節點
4 for(int i=0; i<roots.length; i++) {
5     father_node.add(new DefaultMutableTreeNode(roots[i]));
6 }

  2.設置一顆無缺的樹,並加入面板

  &&強調&&必定要先把Tree設置好以後,再添加至JScrollPane上,不然可能會出現無顯示的狀況&&多線程

 1 //設置樹的模式,也能夠不設置
 2 DefaultMutableTreeNode top_node= new DefaultMutableTreeNode("個人電腦");
 3 DefaultTreeModel treeModel = new DefaultTreeModel(top);
 4 //設置樹
 5 JTree tree = new JTree(treeModel);        //能夠直接用節點初始化 
 6 tree.setEditable(true);                //設置能夠編輯節點名     
 7 tree.getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);//設置僅單選
 8 tree.setShowsRootHandles(true);
 9 //將樹添加至面板
10 JScrollPane jsp = new JScrollPane(tree);
11 jsp.setPreferredSize(new Dimension(200, 405));
12 JPanel jpl = new JPanel();
13 jpl.add(jsp);

   3.將TreeNode轉化成String

  &&TreeNode得到到的是一個列表,其中有各個節點的名字。應該是沒有辦法直接轉換成路徑的,我查了好多資料,全部就先轉換成String而後在轉換成File&&jsp

1 TreeNode[] tn= node.getPath();
2 String path = tn[1].toString();
3 for(int i=2; i<tn.length; i++) {
4     path += tn[i] + "\\";
5 }

  4.將TreePath轉化成String

  &&TreePath和TreeNode有點類似,可是TreePath沒法逐一獲取元素,須要先用函數getPath()轉換成Object而後在轉換成String&&ide

1 //path的類型是TreePath
2 Object tmp[] = path.getPath();
3 String tmp_path = tmp[1].toString();
4 for(int i=2; i<tmp.length; i++) {
5     tmp_path += tmp[i] + "\\";
6 }

   5.事件處理中獲取當前的節點

1 public void valueChanged(TreeSelectionEvent e) {
2     DefaultMutableTreeNode node = (DefaultMutableTreeNode) (e.getPath().getLastPathComponent());
3 }

   6.直接使用updateUI()後,點擊節點報錯問題

  &&多線程&&這裏涉及到了多線程的知識&&函數

1 SwingUtilities.invokeLater(new Runnable(){ 
2 public void run(){
3     tree.updateUI();
4 }});

 

4.所有代碼

  【在對節點操做時,必定要先選中節點】佈局

  實現的節點操做功能:複製;粘貼;刪除學習

  但願你們不要徹底抄錄,有所思考,不會的地方,能夠在下方評論,我會盡我可能解答,和你們一塊兒學習!this

  gitee可下載源碼:https://gitee.com/XiaoLuBanBi/codes/mqtvn5iaj8ehlbgorpwdx44

  1 import java.awt.*;
  2 import java.awt.event.ActionEvent;
  3 import java.awt.event.ActionListener;
  4 import java.awt.event.MouseEvent;
  5 import java.awt.event.MouseListener;
  6 import java.io.File;
  7 
  8 import javax.swing.*;
  9 import javax.swing.event.TreeSelectionEvent;
 10 import javax.swing.event.TreeSelectionListener;
 11 import javax.swing.filechooser.FileSystemView;
 12 import javax.swing.tree.*;
 13 
 14 /**
 15  *     對節點進行操做時,必定要先選中節點
 16  * @author a1126
 17  *
 18  */
 19 public class Src_manage extends JFrame 
 20                 implements TreeSelectionListener, MouseListener, ActionListener {
 21     //設置樹結構
 22     private JTree tree = new JTree();
 23     private DefaultTreeModel treeModel;
 24     private DefaultMutableTreeNode top;
 25     //設置右擊菜單項
 26     private JPopupMenu jp = new JPopupMenu();
 27     private JMenuItem copy = new JMenuItem("複製");
 28     private JMenuItem paste = new JMenuItem("粘貼");
 29     private JMenuItem delete = new JMenuItem("刪除");
 30     //設置複製黏貼臨時存儲
 31     private File copy_path = null;
 32     private File now_path = null;
 33     private DefaultMutableTreeNode now_node = null;
 34     
 35     /**
 36      *     構造函數
 37      */
 38     public Src_manage() {
 39         //設置佈局
 40         this.setLayout(new BorderLayout());
 41         this.add(createPC(), BorderLayout.CENTER);
 42         this.add(createPW(), BorderLayout.WEST);
 43         ini_right_click();
 44         //設置窗體
 45         this.setSize(550, 450);                    //設置大小
 46         this.setVisible(true);                    //設置窗體可見
 47         this.setTitle("資源管理器");                //設置標題
 48         this.setResizable(false);                //設置不容許縮放
 49         setLocationRelativeTo(null);            //窗口居中
 50         setDefaultCloseOperation(EXIT_ON_CLOSE);//窗口點擊關閉時,退出程序
 51     }
 52     /**
 53      *     設置西邊面板
 54      * @return
 55      */
 56     public JPanel createPW() {
 57         JPanel pw = new JPanel();
 58         //設置樹的模式,也能夠不設置
 59         top = new DefaultMutableTreeNode("個人電腦");
 60         treeModel = new DefaultTreeModel(top);
 61         //設置樹
 62         tree = new JTree(treeModel);        //能夠直接用節點初始化
 63         tree.setEditable(true);                //設置能夠編輯節點名
 64         tree.getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);//設置僅單選
 65         tree.setShowsRootHandles(true);
 66         //設置監聽
 67         tree.addTreeSelectionListener(this);
 68         tree.addMouseListener(this);
 69         //設置磁盤節點,加在top上
 70         File roots[] = File.listRoots();
 71         for(int i=0; i<roots.length; i++) {
 72             top.add(new DefaultMutableTreeNode(roots[i]));
 73         }
 74         //添加至面板
 75         JScrollPane jsp = new JScrollPane(tree);
 76         jsp.setPreferredSize(new Dimension(200, 405));
 77         pw.add(jsp);
 78         //返回
 79         return pw;
 80     }
 81     /**
 82      * 設置中部面板
 83      * @return
 84      */
 85     public JPanel createPC() {
 86         return new JPanel();
 87     }
 88     /**
 89      *     建立節點
 90      * @param path    文件路徑
 91      * @param node    默認節點
 92      */
 93     public void createNode(File path, DefaultMutableTreeNode node) {
 94         //若是是文件,則跳出
 95         if(path.isFile())
 96             return;
 97         //不然,獲取子文件,建立子節點
 98         File childs[] = path.listFiles();
 99         for(int i=0; i<childs.length; i++) {
100             //若是是隱藏文件,則跳過
101             if(childs[i].isHidden())
102                 continue;
103             //根據文件名,建立節點
104             DefaultMutableTreeNode tmp = new DefaultMutableTreeNode(childs[i].getName());
105             //加入樹中
106             treeModel.insertNodeInto(tmp, node, node.getChildCount());
107             //若是是文件夾,則建立空子節點(在後面會刪掉)
108             if(childs[i].isDirectory())
109                 tmp.add(new DefaultMutableTreeNode());
110         }
111     }
112     /**
113      *     初始化右鍵菜單
114      */
115     public void ini_right_click() {
116         jp.add(copy);
117         jp.add(paste);
118         jp.add(delete);
119         copy.addActionListener(this);
120         paste.addActionListener(this);
121         delete.addActionListener(this);
122     }
123     /**
124      *     主函數
125      * @param args
126      */
127     public static void main(String[] args) {
128         // TODO 自動生成的方法存根
129         new Src_manage();
130     }
131     //選擇節點時,往下更新子節點
132     @Override
133     public void valueChanged(TreeSelectionEvent e) {
134         // TODO 自動生成的方法存根
135         //獲取選擇的節點
136         DefaultMutableTreeNode node = (DefaultMutableTreeNode) (e.getPath().getLastPathComponent());
137         now_node = node;
138         //若爲根節點,跳出
139         if(node.isRoot())
140             return;
141         //根據獲取到的樹中路徑,建立磁盤絕對路徑
142         TreeNode[] tp = node.getPath();
143         String path = tp[1].toString();
144         for(int i=2; i<tp.length; i++) {
145             path += tp[i] + "\\";
146         }
147         //刪除子文件
148         node.removeAllChildren();
149         SwingUtilities.invokeLater(new Runnable(){ 
150             public void run(){
151                 tree.updateUI();
152         }});//處理updateUI()拋空指針的問題
153         //調用  增長節點函數
154         createNode( new File(path), node);
155     }
156     @Override
157     public void mouseClicked(MouseEvent e) {
158         // TODO 自動生成的方法存根
159         //獲取右擊點的節點路徑
160         TreePath path = tree.getPathForLocation(e.getX(), e.getY());
161         //右擊事件
162         if (e.getButton() == MouseEvent.BUTTON3 && path != null) {
163             // 肯定當前節點
164             Object tmp[] = path.getPath();
165             if(tmp.length == 1)    //若是獲取的字符串長度爲1,便是最上一層,則跳出
166                 return;
167             String tmp_path = tmp[1].toString();
168             for(int i=2; i<tmp.length; i++) {
169                 tmp_path += tmp[i] + "\\";
170             }
171             now_path = new File(tmp_path);
172             // 彈出菜單
173             jp.show(e.getComponent(), e.getX(), e.getY());
174         }
175     }
176     @Override
177     public void mouseEntered(MouseEvent e) {
178         // TODO 自動生成的方法存根
179         
180     }
181     @Override
182     public void mouseExited(MouseEvent e) {
183         // TODO 自動生成的方法存根
184         
185     }
186     @Override
187     public void mousePressed(MouseEvent e) {
188         // TODO 自動生成的方法存根
189         
190     }
191     @Override
192     public void mouseReleased(MouseEvent e) {
193         // TODO 自動生成的方法存根
194         
195     }
196     /**
197      *     實現右鍵功能
198      */
199     @Override
200     public void actionPerformed(ActionEvent e) {
201         // TODO 自動生成的方法存根
202         if(e.getSource() == copy) {    //複製按鈕
203             copy_path = now_path;
204         }else if (e.getSource() == paste) {    //粘貼按鈕
205             now_node.add(new DefaultMutableTreeNode(copy_path.getName()));
206             //若是複製的節點下面還有子節點,也一塊兒複製
207             if(copy_path.isDirectory())
208                 createNode(copy_path, now_node);
209         }else if(e.getSource() == delete) {    //刪除按鈕
210             treeModel.removeNodeFromParent(now_node);
211         }
212     }
213 }
相關文章
相關標籤/搜索