四联光电智能照明论坛

标题: C# TreeView使用技巧 [打印本页]

作者: gxm771208    时间: 2016-11-3 11:50
标题: C# TreeView使用技巧
原文地址:http://www.cnblogs.com/luxiaoxun/p/3288003.html

节点勾选设置
TreeView树中节点勾选要求:
1、不选中一个节点,则其所有的子节点都不被选中。
2、选中一个节点,则其所有的子节点都被选中。
3、当一个节点的所有子节点都没有被选中时,该节点也没有被选中。
4、当一个节点的所有子节点中有一个被选中时,则该节点也被选中。

代码中对事件参数e.Action的判断,可以避免在改变节点的Checked的状态时,再次进入AfterCheck(),这样当在AfterCheck()中有其他逻辑响应时,可以做到每次勾选时,其他逻辑也只响应一次。

参考代码:

  1.         private void treeView_AfterCheck(object sender, TreeViewEventArgs e)
  2.         {
  3.             //通过鼠标或者键盘触发事件,防止修改节点的Checked状态时候再次进入
  4.             if (e.Action == TreeViewAction.ByMouse || e.Action == TreeViewAction.ByKeyboard)
  5.             {
  6.                 SetChildNodeCheckedState(e.Node, e.Node.Checked);
  7.                 SetParentNodeCheckedState(e.Node, e.Node.Checked);
  8.             }
  9.         }

  10.         //设置子节点状态
  11.         private void SetChildNodeCheckedState(TreeNode currNode, bool isCheckedOrNot)
  12.         {
  13.             if (currNode.Nodes == null) return; //没有子节点返回
  14.             foreach (TreeNode tmpNode in currNode.Nodes)
  15.             {
  16.                 tmpNode.Checked = isCheckedOrNot;
  17.                 SetChildNodeCheckedState(tmpNode, isCheckedOrNot);
  18.             }
  19.         }

  20.         //设置父节点状态
  21.         private void SetParentNodeCheckedState(TreeNode currNode, bool isCheckedOrNot)
  22.         {
  23.             if (currNode.Parent == null) return; //没有父节点返回
  24.             if (isCheckedOrNot) //如果当前节点被选中,则设置所有父节点都被选中
  25.             {
  26.                 currNode.Parent.Checked = isCheckedOrNot;
  27.                 SetParentNodeCheckedState(currNode.Parent, isCheckedOrNot);
  28.             }
  29.             else //如果当前节点没有被选中,则当其父节点的子节点有一个被选中时,父节点被选中,否则父节点不被选中
  30.             {
  31.                 bool checkedFlag = false;
  32.                 foreach (TreeNode tmpNode in currNode.Parent.Nodes)
  33.                 {
  34.                     if (tmpNode.Checked)
  35.                     {
  36.                         checkedFlag = true;
  37.                         break;
  38.                     }
  39.                 }
  40.                 currNode.Parent.Checked = checkedFlag;
  41.                 SetParentNodeCheckedState(currNode.Parent, checkedFlag);
  42.             }
  43.         }
复制代码

TreeView隐藏部分节点

WinForm中的TreeView没法根据每个节点的情况设置是否有checkbox,只能用CheckBoxes设置整个树是否有Checkbox,可通过如下方式隐藏部分节点的checkbox。

  1. this.treeView1.CheckBoxes = true;
  2. this.treeView1.DrawMode = TreeViewDrawMode.OwnerDrawAll;
  3. this.treeView1.DrawNode += new DrawTreeNodeEventHandler(treeView1_DrawNode);
复制代码


隐藏节点:

  1.         void treeView1_DrawNode(object sender, DrawTreeNodeEventArgs e)
  2.         {
  3.             //隐藏节点前的checkbox
  4.             if (e.Node.Level == 0 || e.Node.Level == 1)
  5.                 HideCheckBox(this.treeView1, e.Node);
  6.             e.DrawDefault = true;
  7.         }

  8.         [StructLayout(LayoutKind.Sequential, Pack = 8, CharSet = CharSet.Auto)]
  9.         private struct TVITEM
  10.         {
  11.             public int mask;
  12.             public IntPtr hItem;
  13.             public int state;
  14.             public int stateMask;
  15.             [MarshalAs(UnmanagedType.LPTStr)]
  16.             public string lpszText;
  17.             public int cchTextMax;
  18.             public int iImage;
  19.             public int iSelectedImage;
  20.             public int cChildren;
  21.             public IntPtr lParam;
  22.         }

  23.         [DllImport("user32.dll", CharSet = CharSet.Auto)]
  24.         private static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, ref TVITEM lParam);

  25.         private const int TVIF_STATE = 0x8;
  26.         private const int TVIS_STATEIMAGEMASK = 0xF000;
  27.         private const int TV_FIRST = 0x1100;
  28.         private const int TVM_SETITEM = TV_FIRST + 63;

  29.         private void HideCheckBox(TreeView tvw, TreeNode node)
  30.         {
  31.             TVITEM tvi = new TVITEM();
  32.             tvi.hItem = node.Handle;
  33.             tvi.mask = TVIF_STATE;
  34.             tvi.stateMask = TVIS_STATEIMAGEMASK;
  35.             tvi.state = 0;
  36.             SendMessage(tvw.Handle, TVM_SETITEM, IntPtr.Zero, ref tvi);
  37.         }
复制代码


TreeView递归加载节点

C#遍历指定文件夹下所有子文件夹及文件并添加到目录树:

  1.     private void Form1_Load(object sender, EventArgs e)
  2.         {
  3.             TreeNode root = new TreeNode();
  4.            //根目录名称
  5.             root.Text = "目录";
  6.            //根目录路径
  7.             GetFiles(@"E:\Tools", root);
  8.             treeView1.Nodes.Add(root);
  9.         }

  10.         private void GetFiles(string filePath, TreeNode node)
  11.         {
  12.             DirectoryInfo folder = new DirectoryInfo(filePath);
  13.             node.Text = folder.Name;
  14.             node.Tag = folder.FullName;
  15.             
  16.             FileInfo[] chldFiles = folder.GetFiles("*.*");
  17.             foreach (FileInfo chlFile in chldFiles)
  18.             {
  19.                 TreeNode chldNode = new TreeNode();
  20.                 chldNode.Text = chlFile.Name;
  21.                 chldNode.Tag = chlFile.FullName;
  22.                 node.Nodes.Add(chldNode);
  23.             }

  24.             DirectoryInfo[] chldFolders = folder.GetDirectories();
  25.             foreach (DirectoryInfo chldFolder in chldFolders)
  26.             {
  27.                 TreeNode chldNode = new TreeNode();
  28.                 chldNode.Text = folder.Name;
  29.                 chldNode.Tag = folder.FullName;
  30.                 node.Nodes.Add(chldNode);
  31.                 GetFiles(chldFolder.FullName, chldNode);
  32.             }
  33.         }
复制代码





欢迎光临 四联光电智能照明论坛 (http://5xhome.com/) Powered by Discuz! X3.2