⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 treegraph.cs

📁 二叉树的创建与打印 二叉树的创建与打印
💻 CS
字号:
using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;

namespace BinaryTree
{
    /// <summary>
    /// 绘图函数
    /// 是连接底层数据结构和窗体显示的桥梁
    /// </summary>
    class TreeGraph
    {
        /// <summary>
        /// 绘图相关变量
        /// </summary>
        private int distanceHeight;    // 两个节点之间的高度差
        private int distanceWidth;     // 两个节点之间的宽度差
        private int nodeRadius;        // 节点圆圈的半径
        private Point middlePoint;     // 绘图的中心点

        private Graphics myGraphics;
        private Color backColor;       // 窗体的背景颜色
        private Brush fontBrush;       // 字体颜色
        private SolidBrush cirBrush;   // 圆圈的颜色
        private Pen myPen;             // 连线的颜色
        private Font myFont;           // 字体



        /// <summary>
        /// 数据(树)相关变量
        /// </summary>
        private BinaryTree myBT = new BinaryTree();



        /// <summary>
        /// 构造函数
        /// </summary>
        /// <param name="gc"></param>
        public TreeGraph(Graphics gc)
        {
            /* 初始化绘图相关变量 */
            distanceHeight = Setting.distanceHeight;
            distanceWidth  = Setting.distanceWidth;
            nodeRadius     = Setting.nodeRadius;
            middlePoint = new Point(Setting.middleX, Setting.middleY);

            myGraphics = gc;
            backColor = Setting.backColor;
            cirBrush = Setting.cirBrush;
            fontBrush = Setting.fontBrush;
            myPen = Setting.myPen;
            myFont = Setting.myFont;

            /* 初始化树 */
            foreach (int i in Setting.initTree)
            {
                myBT.Insert(i);
            }
        }

        public Form_Tree Form_Tree
        {
            get
            {
                throw new System.NotImplementedException();
            }
            set
            {
            }
        }

        /// <summary>
        /// 增加节点
        /// </summary>
        /// <param name="data">要增加的节点的值</param>
        public void AddNode(int data)
        {
            myBT.Insert(data);
        }

        /// <summary>
        /// 删除节点
        /// </summary>
        /// <param name="data">要删除的节点的值</param>
        public void DelNode(int data)
        {
            myBT.Remove(data);
        }

        /// <summary>
        /// 删除整个树
        /// </summary>
        public void DestoryTree()
        {
            myBT = new BinaryTree();
        }

        /// <summary>
        /// 设置字体颜色
        /// </summary>
        /// <param name="color"></param>
        public void SetFontColor(Color color)
        {
            fontBrush = new SolidBrush(color);
        }

        /// <summary>
        /// 设置圆圈颜色
        /// </summary>
        /// <param name="color"></param>
        public void SetLineColor(Color color)
        {
            myPen.Color = color;
            cirBrush.Color = color;
        }

        /// <summary>
        /// 设置背景颜色
        /// </summary>
        /// <param name="color"></param>
        public void SetBackColor(Color color)
        {
            backColor = color;
        }



        /// <summary>
        /// 绘图
        /// </summary>
        public void Draw()
        {
            myGraphics.Clear(backColor);
            int high = myBT.Height() * distanceHeight;
            Point top = new Point(middlePoint.X, middlePoint.Y - high / 2);
            Draw(myBT.root, top, top, myBT.Height()-2);
        }

        /// <summary>
        /// 增加两个节点之间的高度差
        /// </summary>
        public void IncreaseDisH()
        {
            int high = (myBT.Height()-1) * distanceHeight;
            if (high + nodeRadius > Setting.screenH)
            {
                return;
            }
            distanceHeight += Setting.disHChange;
        }

        /// <summary>
        /// 减少两个节点之间的高度差
        /// </summary>
        public void ReduceDisH()
        {
            if (distanceHeight <= nodeRadius * 2)
            {
                return;
            }
            distanceHeight -= Setting.disHChange;
        }

        /// <summary>
        /// 增加两个节点之间的宽度差
        /// </summary>
        public void IncreaseDisW()
        {
            int h = myBT.Height()-1;
            int w = distanceWidth;
            int r = nodeRadius;
            int width = (r + w) * (int)(Math.Pow(2.0, (double)h) - 1);
            if (width*2+nodeRadius*2 > Setting.screenW)
            {
                return;
            }
            distanceWidth += Setting.disWChange;
        }

        /// <summary>
        /// 减少两个节点之间的宽度差
        /// </summary>
        public void ReduceDisW()
        {
            if (distanceWidth <= 0)
            {
                return;
            }
            distanceWidth -= Setting.disWChange;
        }

        /// <summary>
        /// 增加节点圆圈的半径
        /// </summary>
        public void IncreaseRadius()
        {
            int h = distanceHeight;
            int w = distanceWidth + nodeRadius;
            if (nodeRadius*2 > h ||
                nodeRadius*2 > w ||
                nodeRadius * nodeRadius*4  > h*h + w*w)
            {
                return;
            }
            h = myBT.Height() - 1;
            w = distanceWidth;
            int r = nodeRadius;
            int width = (r + w) * (int)(Math.Pow(2.0, (double)h) - 1);
            if (width * 2 + nodeRadius * 2 > Setting.screenW)
            {
                return;
            }

            nodeRadius += Setting.radiusChange;

            /* 字体 */
            float currentSize = myFont.Size;
            currentSize += Setting.fontChange;
            myFont = new Font(myFont.Name, currentSize, myFont.Style, myFont.Unit);
            myPen.Width += Setting.myPenChange;

        }

        /// <summary>
        /// 减少节点圆圈的半径
        /// </summary>
        public void ReduceRadius()
        {
            if (nodeRadius <= Setting.radiusMin)
            {
                return;
            }

            nodeRadius -= Setting.radiusChange;

            /* 字体 */
            float currentSize = myFont.Size;
            currentSize -= Setting.fontChange;
            myFont = new Font(myFont.Name, currentSize, myFont.Style, myFont.Unit);
            myPen.Width -= Setting.myPenChange;
        }


        /// <summary>
        /// 绘制树的图形,递归
        /// </summary>
        /// <param name="parent">要绘制的节点</param>
        /// <param name="cur">要绘制的位置</param>
        /// <param name="last">上一次绘制的位置</param>
        /// <param name="deep">深度,用以确定位置</param>
        private void Draw(TreeNode parent, Point cur, Point last, int deep)
        {
            if (parent == null)
            {
                return;
            }

            /* 画圆圈 */
            Size size = new Size(nodeRadius*2, nodeRadius*2);
            Point center = new Point();
            center.X = cur.X - nodeRadius;
            center.Y = cur.Y - nodeRadius;
            Rectangle rec = new Rectangle(center, size);
            myGraphics.FillEllipse(cirBrush, rec);

            /* 画线 */
            myGraphics.DrawLine(myPen, cur, last);

            /* 绘制左右子树 */
            Point left = new Point();
            int len = (int)Math.Pow(2.0, (double)deep);
            //left.X = cur.X - (distanceWidth + nodeRadius) * deep - distanceWidth;
            //left.X = cur.X - (nodeRadius + distanceWidth) * deep;
            left.X = cur.X - (nodeRadius + distanceWidth) * len;
            left.Y = cur.Y + distanceHeight;
            Draw(parent.LeftNode, left, cur, deep-1);

            Point right = new Point();
            //right.X = cur.X + (distanceWidth + nodeRadius) * deep + distanceWidth;
            //right.X = cur.X + (nodeRadius + distanceWidth) * deep;
            right.X = cur.X + (nodeRadius + distanceWidth) * len;
            right.Y = cur.Y + distanceHeight;
            Draw(parent.RightNode, right, cur, deep-1);

            /* 写字 */
            center.X = cur.X - nodeRadius * 9 / 10;
            center.Y = cur.Y - nodeRadius * 9 / 10;
            myGraphics.DrawString(parent.data.ToString(), myFont, fontBrush, center);
        }

    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -