能調整大小并可触發點擊事件的多行表頭

来源:互联网 发布:小米手机2a是什么网络 编辑:程序博客网 时间:2024/05/06 11:58

    能調整大小并可触發點擊事件的多行表頭


原理:利用Spliter結合一棵樹來做,主要是靈活設置Dock屬性

    public partial class HeadItem : Panel
    {
        private string text;
        private Button btn ;
        public HeadItem()
        {
            InitializeComponent();
            this.Resize += new EventHandler(HeadPanel_Resize);
        }

        void HeadPanel_Resize(object sender, EventArgs e)
        {
            this.Refresh();
        }
        public new string Text
        {
            get
            {
                return this.text;
            }
            set
            {
                this.text = value;
            }
        }
       
        protected override void OnPaint(PaintEventArgs e)
        {
            ControlPaint.DrawButton(e.Graphics, 1, 1, this.ClientRectangle.Width - 2, this.ClientRectangle.Height - 2, ButtonState.Normal);
            StringFormat format = new StringFormat(StringFormatFlags.FitBlackBox);
            e.Graphics.DrawString(this.Text, this.Font, new SolidBrush(this.ForeColor), new PointF(0, 0),format);
            base.OnPaint(e);
        }

    }

    //--------------
    public partial class Header : Panel
    {
        private TreeNodeCollection headCollection ;
        public TreeNodeCollection HeadCollection
        {
            get
            {
                return this.headCollection;
            }
            set
            {
                this.headCollection = value;
            }
        }
   //畫本身及子控件
        private void LayoutItem(TreeNode node, Panel panel)
        {
            if (node == null)
            {
                return;
            }
            int count = node.Nodes.Count;

            if (count == 0)//沒有子結點的情況
            {
                HeadItem item = new HeadItem();
                item.Dock = DockStyle.Fill;
                item.Text = node.Text;
                panel.Controls.Add(item);
            }
            if (count > 0)//有子節點的情況
            {
                int width = panel.Width / count;

                Panel bottomPn = new Panel();
                bottomPn.Dock = DockStyle.Fill;
                panel.Controls.Add(bottomPn);

                Splitter spli = new Splitter();
                spli.Height = 2; ;
                spli.Dock = DockStyle.Top;
                panel.Controls.Add(spli);

                HeadItem item = new HeadItem();
                item.Dock = DockStyle.Top;
                item.Text = node.Text;
                panel.Controls.Add(item);


                for (int i = count - 1; i >= 0; --i)
                {
                    if (i == count - 1)
                    {
                        //先放最右邊的那個
                        Panel rightPn = new Panel();
                        rightPn.Dock = DockStyle.Fill;
                        rightPn.Text = node.Text;
                        rightPn.Width = bottomPn.Width / count;
                        bottomPn.Controls.Add(rightPn);
                        LayoutItem(node.Nodes[i], rightPn);
                    }
                    else
                    {
                        Splitter spli2 = new Splitter();
                        spli2.Width = 2;
                        spli2.Dock = DockStyle.Left;
                        bottomPn.Controls.Add(spli2);

                        Panel leftPn = new Panel();
                        leftPn.Text = node.Text;
                        leftPn.Dock = DockStyle.Left;
                        leftPn.Width = bottomPn.Width / count;
                        bottomPn.Controls.Add(leftPn);

                        LayoutItem(node.Nodes[i], leftPn);
                    }
                }
            }
        }

        private void LayoutTree(TreeNodeCollection tree, Panel panel)
        {
            this.Controls.Clear();
            int count = tree.Count;

            for (int i = count - 1; i >= 0; --i)
            {
                int width = panel.Width / count;

                if (i == count - 1)
                {
                    Panel pn = new Panel();
                    pn.Dock = DockStyle.Fill;
                    pn.Width = width;
                    panel.Controls.Add(pn);
                    LayoutItem(tree[i], pn);
                }
                else
                {
                    Splitter spli = new Splitter();
                    spli.Width = 2;
                    spli.Dock = DockStyle.Left;
                    panel.Controls.Add(spli);

                    Panel leftPn = new Panel();
                    leftPn.Text = tree[i].Text;
                    leftPn.Dock = DockStyle.Left;
                    leftPn.Width = width;
                    panel.Controls.Add(leftPn);
                    LayoutItem(tree[i], leftPn);
                }
            }
        }
 //1,集合屬性還不知道怎么做
 //2,也不知道該在哪里触發LayoutTree函數,放在OnPaint不行.
 //3.如何触發點擊事件還沒做

    }