2014年11月15日 星期六

[C#] SCP-like WinForm Application Part 1: TreeView



        首先,是TreeView的部份。 就直接從工具箱裡拉一個TreeView到表單上,調整好大小,屬性這邊也不用調整,我們接下來會開始塞節點(node)到這個TreeView裡面。另外再拉一個ImageList,這裡會放幾張圖示,之後會畫進TreeView裡,看起來會好一些。


        接著是TreeView的重點之一,從系統資訊中取出所需的硬碟及資料夾結構。我在google時找到了這篇code project的文章,他是用System.Management這個命名空間來執行我想要的工作,查詢指令跟SQL有點類似,很方便就能上手。

        要開始塞節點了,首先要自己自訂一個「我的電腦」,當作整個TreeView的根節點,再從根節點開始,逐一塞入硬碟節點,在這個範例中有依序將實體硬碟,光碟機跟網路硬碟排好,看起來就跟平常用的一樣。在這個函式,裡我每次執行時都會清空一次TreeView,這些相關的控制就依各人所需吧!
        private void buildTreeView(TreeView _TreeView)
        {
            ManagementObjectSearcher query = new ManagementObjectSearcher("SELECT * From Win32_LogicalDisk");
            ManagementObjectCollection result = query.Get();
            int imageIdx = 0;
            int selectIdx = 0;

            TreeNode nodeTreeNode;
            _TreeView.Nodes.Clear();
            nodeTreeNode = new TreeNode("我的電腦", 0, 0);
            _TreeView.Nodes.Add(nodeTreeNode);

            TreeNodeCollection _TreeNodeCollection = nodeTreeNode.Nodes;
            foreach (ManagementObject mo in result)
            { 
                switch(int.Parse(mo["DriveType"].ToString()))
                {
                    case 2:
                        imageIdx = 5;
                        selectIdx = 5;
                        break;

                    case 3:
                        imageIdx = 6;
                        selectIdx = 6;
                        break;

                    case 4:
                        imageIdx = 8;
                        selectIdx = 8;
                        break;

                    case 5:
                        imageIdx = 7;
                        selectIdx = 7;
                        break;

                    default:
                        imageIdx = 2;
                        selectIdx = 3;
                        break;
                }

                nodeTreeNode = new TreeNode(mo["Name"].ToString() + @"\", imageIdx, selectIdx);
                _TreeNodeCollection.Add(nodeTreeNode);
            }

            return;
        }

         再來是實作TreeView所要的控制功能,回到設計介面,在事件清單中找到「AfterSelected」,這就是我需要的事件。我希望做出以下功能:如果使用者選擇了根節點,則更新整個TreeView;如果使用者選擇了TreeView內的硬碟或資料夾,則展開節點,讓使用者能夠看見裡面的資料夾。TreeEventArgsNode屬性相當重要,提供了很多資訊跟參數讓設計師使用,以第一次觸發這個事件為例,你可以在e.Node裡找到使用者所選擇的硬碟。然後呼叫PopulateDirectory,根據所選硬碟的路徑,來取出裡面的所有資料夾並插入nodeTreeView裡。


        別忘了記下使用者選擇的資料夾路徑並記得更新它。
        private void treeView1_AfterSelect(object sender, TreeViewEventArgs e)
        {
            //Populate folders and files when a folder is selected
            this.Cursor = Cursors.WaitCursor;

            //get current selected drive or folder
            TreeNode nodeCurrent = e.Node;
            string temp = "";
            //clear all sub-folders
            nodeCurrent.Nodes.Clear();
            
            if (nodeCurrent.SelectedImageIndex == 0)
            {
                //Selected My Computer - repopulate drive list
                buildTreeView(treeView1);
            }
            else
            {
                temp = getFullPath(e.Node.FullPath).Replace("\\\\", "\\");
                //webBrowser1.Url = new Uri(temp, UriKind.Absolute);
                
                //populate sub-folders and folder files
                PopulateDirectory(nodeCurrent, nodeCurrent.Nodes);
            }

            e.Node.Expand();
            if(Directory.Exists(temp))
            {
                label2.Text = temp;
                DirectoryInfo _di = new DirectoryInfo(temp);
                currentDirectorySrc = _di;
                buildListView(listView1);
            }
            this.Cursor = Cursors.Default;
        }

沒有留言:

張貼留言