none
TreeView 的 TreeNode拖拉 RRS feed

答案

  • 代码有点长,两年前写的(win form):

            #region 增加拖放功能
            /// <summary>
            /// 拖拽处理
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_ItemDrag(object sender, ItemDragEventArgs e)
            {
                DoDragDrop(e.Item, DragDropEffects.Move);

            }

            /// <summary>
            /// 拖放处理
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_DragEnter(object sender, DragEventArgs e)
            {
                // 如果拖放的是TreeNode对象,显示拖放的效果
                if (e.Data.GetDataPresent("System.Windows.Forms.TreeNode", true))
                {
                    e.Effect = DragDropEffects.Move;
                }
                else
                {
                    // 如果不是TreeNode对象,阻止拖放
                    e.Effect = DragDropEffects.None;
                }
            }
            /// <summary>
            /// 拖动放下时,将拖动的节点放到目标功能点下。
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_DragDrop(object sender, DragEventArgs e)
            {
                //不是树节点则返回
                if (!(e.Data.GetDataPresent(typeof(TreeNode)))) return;

                // 目标节点的位置
                Point pt = this.tvwFunctions.PointToClient(new Point(e.X, e.Y));

                // 获取目标节点
                TreeNode nodeTo = this.tvwFunctions.GetNodeAt(pt);

                if (nodeTo == null) return;

                TreeNode nodeFrom = (TreeNode)e.Data.GetData(typeof(TreeNode));

                if (LY.TEC.Framework.Common.Client.BaseForm.MessageBoxShow((IWin32Window)this, "是否将拖动的功能点" + nodeFrom.Text + "移到该功能点" + nodeTo.Text +
                    "下?", "提示确认", MessageBoxButtons.YesNo,1) != DialogResult.Yes)
                {
                    return;
                }

                MoveNode(nodeFrom, nodeTo);

            }

            private TreeNode mLastTreeNode;
            /// <summary>
            /// 拖动中处理
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_DragOver(object sender, DragEventArgs e)
            {
                // 如果拖放的不是TreeNode对象
                if (!e.Data.GetDataPresent("System.Windows.Forms.TreeNode", true))
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 目标节点的位置
                Point pt = this.tvwFunctions.PointToClient(new Point(e.X, e.Y));

                // 获取目标节点
                TreeNode targetNode = this.tvwFunctions.GetNodeAt(pt);

                // 拖动中的节点
                TreeNode dropNode = e.Data.GetData("System.Windows.Forms.TreeNode", true) as TreeNode;

                // 判断放置的目标节点是否就是本身开始拖的节点或者是根节点(模块节点不运行投放)
                // 如果是,不处理
                if (targetNode == dropNode || targetNode == null || dropNode.Parent == null)
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 如果目标对象就是自己的父节点,说明位置没有变,无需处理
                if (dropNode.Parent == targetNode)
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 父亲节点不能拖放到儿子节点上
                if (IsParent(targetNode, dropNode))
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 功能菜单(可认为是叶子节点)不允许放置

                // 上一个鼠标Over过的节点字体颜色回原
                if (this.mLastTreeNode != null)
                {
                    this.mLastTreeNode.ForeColor = System.Drawing.Color.Black;
                }
                // 目标节点颜色变兰以特出显示
                this.mLastTreeNode = targetNode;
                this.mLastTreeNode.ForeColor = System.Drawing.Color.Blue;

                // 其他目标节点允许拖放
                e.Effect = DragDropEffects.Move;
            }
            /// <summary>
            /// 处理功能移动。
            /// </summary>
            /// <param name="nodeFrom">从那个功能节点</param>
            /// <param name="nodeTo">到哪个功能节点</param>
            private void MoveNode(TreeNode nodeFrom, TreeNode nodeTo)
            {
                DataRow drFrom = nodeFrom.Tag as DataRow;

                DataRow drTo = nodeTo.Tag as DataRow;

                string[] sColumns = new string[] { "LAST_UPDATED_DATE", "PRIV_ID","PARENT_PRIV_ID" };

                DataTable dtPriv = mDataAccess.DuplicateDataTable("SYS_PRIV",sColumns);

                DataRow dr = dtPriv.NewRow();

                dr["LAST_UPDATED_DATE"] = drFrom["LAST_UPDATED_DATE"];
                dr["PARENT_PRIV_ID"] = drTo["PRIV_ID"];
                dr["PRIV_ID"] = drFrom["PRIV_ID"];

                dtPriv.Rows.Add(dr);

                dtPriv.AcceptChanges();

                dr.SetModified();

                DataTable dtNew = functionService.SaveFunction(dtPriv);

                nodeFrom.Parent.Nodes.Remove(nodeFrom);
                ShowSubNode(nodeTo);
                nodeTo.Nodes.Add(nodeFrom);

                //移动后修改界面数据,以便下次修改。
                drFrom["LAST_UPDATED_DATE"] = dtNew.Rows[0]["LAST_UPDATED_DATE"];
                drFrom["PARENT_PRIV_ID"] = dtNew.Rows[0]["PARENT_PRIV_ID"];
            }

            /// <summary>
            /// 判断两个节点是否为父子
            /// </summary>
            /// <param name="nodeParent">父节点</param>
            /// <param name="nodeSon">子节点</param>
            /// <returns>是否父子</returns>
            private bool IsParent(TreeNode nodeParent, TreeNode nodeSon)
            {
                if (nodeParent.Nodes.Count < 1) return false;

                if (nodeSon.Parent == nodeParent) return true;

                return false;
            }
            #endregion;

    2010年7月30日 8:30

全部回复

  • 代码有点长,两年前写的(win form):

            #region 增加拖放功能
            /// <summary>
            /// 拖拽处理
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_ItemDrag(object sender, ItemDragEventArgs e)
            {
                DoDragDrop(e.Item, DragDropEffects.Move);

            }

            /// <summary>
            /// 拖放处理
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_DragEnter(object sender, DragEventArgs e)
            {
                // 如果拖放的是TreeNode对象,显示拖放的效果
                if (e.Data.GetDataPresent("System.Windows.Forms.TreeNode", true))
                {
                    e.Effect = DragDropEffects.Move;
                }
                else
                {
                    // 如果不是TreeNode对象,阻止拖放
                    e.Effect = DragDropEffects.None;
                }
            }
            /// <summary>
            /// 拖动放下时,将拖动的节点放到目标功能点下。
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_DragDrop(object sender, DragEventArgs e)
            {
                //不是树节点则返回
                if (!(e.Data.GetDataPresent(typeof(TreeNode)))) return;

                // 目标节点的位置
                Point pt = this.tvwFunctions.PointToClient(new Point(e.X, e.Y));

                // 获取目标节点
                TreeNode nodeTo = this.tvwFunctions.GetNodeAt(pt);

                if (nodeTo == null) return;

                TreeNode nodeFrom = (TreeNode)e.Data.GetData(typeof(TreeNode));

                if (LY.TEC.Framework.Common.Client.BaseForm.MessageBoxShow((IWin32Window)this, "是否将拖动的功能点" + nodeFrom.Text + "移到该功能点" + nodeTo.Text +
                    "下?", "提示确认", MessageBoxButtons.YesNo,1) != DialogResult.Yes)
                {
                    return;
                }

                MoveNode(nodeFrom, nodeTo);

            }

            private TreeNode mLastTreeNode;
            /// <summary>
            /// 拖动中处理
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private void tvwFunctions_DragOver(object sender, DragEventArgs e)
            {
                // 如果拖放的不是TreeNode对象
                if (!e.Data.GetDataPresent("System.Windows.Forms.TreeNode", true))
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 目标节点的位置
                Point pt = this.tvwFunctions.PointToClient(new Point(e.X, e.Y));

                // 获取目标节点
                TreeNode targetNode = this.tvwFunctions.GetNodeAt(pt);

                // 拖动中的节点
                TreeNode dropNode = e.Data.GetData("System.Windows.Forms.TreeNode", true) as TreeNode;

                // 判断放置的目标节点是否就是本身开始拖的节点或者是根节点(模块节点不运行投放)
                // 如果是,不处理
                if (targetNode == dropNode || targetNode == null || dropNode.Parent == null)
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 如果目标对象就是自己的父节点,说明位置没有变,无需处理
                if (dropNode.Parent == targetNode)
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 父亲节点不能拖放到儿子节点上
                if (IsParent(targetNode, dropNode))
                {
                    e.Effect = DragDropEffects.None;
                    return;
                }

                // 功能菜单(可认为是叶子节点)不允许放置

                // 上一个鼠标Over过的节点字体颜色回原
                if (this.mLastTreeNode != null)
                {
                    this.mLastTreeNode.ForeColor = System.Drawing.Color.Black;
                }
                // 目标节点颜色变兰以特出显示
                this.mLastTreeNode = targetNode;
                this.mLastTreeNode.ForeColor = System.Drawing.Color.Blue;

                // 其他目标节点允许拖放
                e.Effect = DragDropEffects.Move;
            }
            /// <summary>
            /// 处理功能移动。
            /// </summary>
            /// <param name="nodeFrom">从那个功能节点</param>
            /// <param name="nodeTo">到哪个功能节点</param>
            private void MoveNode(TreeNode nodeFrom, TreeNode nodeTo)
            {
                DataRow drFrom = nodeFrom.Tag as DataRow;

                DataRow drTo = nodeTo.Tag as DataRow;

                string[] sColumns = new string[] { "LAST_UPDATED_DATE", "PRIV_ID","PARENT_PRIV_ID" };

                DataTable dtPriv = mDataAccess.DuplicateDataTable("SYS_PRIV",sColumns);

                DataRow dr = dtPriv.NewRow();

                dr["LAST_UPDATED_DATE"] = drFrom["LAST_UPDATED_DATE"];
                dr["PARENT_PRIV_ID"] = drTo["PRIV_ID"];
                dr["PRIV_ID"] = drFrom["PRIV_ID"];

                dtPriv.Rows.Add(dr);

                dtPriv.AcceptChanges();

                dr.SetModified();

                DataTable dtNew = functionService.SaveFunction(dtPriv);

                nodeFrom.Parent.Nodes.Remove(nodeFrom);
                ShowSubNode(nodeTo);
                nodeTo.Nodes.Add(nodeFrom);

                //移动后修改界面数据,以便下次修改。
                drFrom["LAST_UPDATED_DATE"] = dtNew.Rows[0]["LAST_UPDATED_DATE"];
                drFrom["PARENT_PRIV_ID"] = dtNew.Rows[0]["PARENT_PRIV_ID"];
            }

            /// <summary>
            /// 判断两个节点是否为父子
            /// </summary>
            /// <param name="nodeParent">父节点</param>
            /// <param name="nodeSon">子节点</param>
            /// <returns>是否父子</returns>
            private bool IsParent(TreeNode nodeParent, TreeNode nodeSon)
            {
                if (nodeParent.Nodes.Count < 1) return false;

                if (nodeSon.Parent == nodeParent) return true;

                return false;
            }
            #endregion;

    2010年7月30日 8:30
  • 3KU Very Much
    2010年8月2日 6:14