• Winform自定义窗体样式,实现标题栏可灵活自定义


    Winform自定义窗体样式,实现标题栏可灵活自定义

    最近在编写C/S结构应用程序时,感觉窗体的标题栏样式太死板了,标题文字不能更改大小、颜色、字体等,按钮不能隐藏等问题,在网上也查找了许多相关的资料,没有找到合适的解决方案,发现许多人也在寻求这个问题,最后我决定自己研究动手画一个标题栏出来,经过今天一天的研究与编写,终于完成全部功能,现公布一下我的设计思路。

    一、去掉Form类自带的标题栏                         

          要去掉自带的标题栏有两种方法,第一方法是直接将FormBorderStyle设为 System.Windows.Forms.FormBorderStyle.None,但设置过后,窗体无法改变大小,考虑到后期这些功能还是需要的,所以我采用了第二种方法,第二种方法是可以忽略FormBorderStyle,只需要将ControlBox设为 false,并将Text设为空即可,这种方法隐藏标题栏,若FormBorderStyle不是固定模式,则可以通过拉伸窗体边框改变大小的。

    二、创建自定义窗体类                                     

    首先创建一个窗体,如下图:

    然后去掉Text默认的文字,并将ControlBox设为 false,此时标题栏将自动隐藏掉了,如下图:

    去掉标题栏后,就需要重画新的标题栏,画标题栏很简单,方法也很多,我这里是采用一个Panel,将Dock设为Top,让其项部固定,并设高度为30像素,再在其中添加三个按钮,依次为:button1(关闭),button2(最大化),button3(最小化),三个按钮的设为Size相同,且将Anchor都设为Top Right Bottom,这样就实现了让三个按钮在右边固定位置,如下图:

    界面部份已经完工,剩下的就是编写代码了,由于代码较多,我先将代码贴出来,稍后再讲解。

    复制代码

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using System.Windows.Forms;
    
    namespace ZControls
    {
        /// <summary>
        /// Copyright Zuowenjun
        /// Site Url:http://www.zuowenjun.cn
        /// QQ:77321032
        /// Description:自定义窗体样式,实现标题可自定义化
        /// </summary>
        public partial class ZForm : Form
        {
            private bool moving = false;
            private Point oldMousePosition;
    
            public new FormBorderStyle FormBorderStyle
            {
                get
                {
                    return base.FormBorderStyle;
                }
                set
                {
                    if (value != FormBorderStyle.Sizable && value != FormBorderStyle.SizableToolWindow)
                    {
                        titlepanel.Controls.Remove(button2);
                    }
                    base.FormBorderStyle = value;
                }
            }
    
            #region 隐藏父类的属性,使其不可见
    
            [Browsable(false)]
            public new string Text
            {
                get
                {
                    return titlelabel.Text;
                }
                set
                { }
            }
    
            [Browsable(false)]
            public new bool ControlBox
            {
                get {
                    return false;
                }
                set
                {
                    base.ControlBox = false;
                }
            }
    
            #endregion
    
            [Browsable(true)]
            [EditorBrowsable(EditorBrowsableState.Always)]
            [Description("窗体标题")]
            public string Title
            {
                get { return titlelabel.Text; }
                set { titlelabel.Text = value; }
            }
    
    
    
            [Browsable(true)]
            [EditorBrowsable(EditorBrowsableState.Always)]
            [Description("窗体标题字体样式")]
            public Font TitleFont
            {
                get
                {
                    return titlelabel.Font;
                }
                set
                {
                    titlelabel.Font = value;
                }
            }
    
    
            [Browsable(true)]
            [EditorBrowsable(EditorBrowsableState.Always)]
            [Description("窗体标题字体颜色")]
            public Color TitleColor
            {
                get
                {
                    return titlelabel.ForeColor;
                }
                set
                {
                    titlelabel.ForeColor = value;
                }
            }
    
            [Browsable(true)]
            [EditorBrowsable(EditorBrowsableState.Always)]
            [Description("窗体标题栏背景色")]
            public Color TitleBarBackColor
            {
                get
                {
                    return titlepanel.BackColor;
                }
                set
                {
                    titlepanel.BackColor = value;
                }
            }
    
    
    
    
            public new bool MaximizeBox
            {
                get
                {
                    return titlepanel.Contains(button2);
                }
                set
                {
                    if (!value)
                    {
                        titlepanel.Controls.Remove(button2);
                    }
                    else if (!titlepanel.Contains(button2))
                    {
                        titlepanel.Controls.Add(button2);
                    }
                }
            }
    
            public new bool MinimizeBox
            {
                get
                {
                    return titlepanel.Contains(button3);
                }
                set
                {
                    if (!value)
                    {
                        titlepanel.Controls.Remove(button3);
                    }
                    else if (!titlepanel.Contains(button3))
                    {
                        titlepanel.Controls.Add(button3);
                    }
                }
            }
    
    
            private void ResetTitlePanel()
            {
                base.ControlBox = false;
                base.Text = null;
                SetToolTip(button1, "关闭");
                button2.Size = button1.Size;
                SetToolTip(button2, "最大化或还原");
                button3.Size = button1.Size;
                SetToolTip(button3, "最小化");
            }
    
            private void SetToolTip(Control ctrl, string tip)
            {
                new ToolTip().SetToolTip(ctrl, tip);
            }
            public ZForm()
            {
                InitializeComponent();
                ResetTitlePanel();
            }
    
            private void Titlebutton_Click(object sender, EventArgs e)
            {
                Button btn = (Button)sender;
                switch (btn.Tag.ToString())
                {
                    case "close":
                        {
                            this.Close();
                            break;
                        }
                    case "max":
                        {
                            if (this.WindowState == FormWindowState.Maximized)
                            {
                                this.WindowState = FormWindowState.Normal;
                            }
                            else
                            {
                                this.WindowState = FormWindowState.Maximized;
                            }
                            break;
                        }
                    case "min":
                        {
                            if (this.WindowState != FormWindowState.Minimized)
                            {
                                this.WindowState = FormWindowState.Minimized;
                            }
                            break;
                        }
                }
            }
    
            private void Titlepanel_MouseDown(object sender, MouseEventArgs e)
            {
                if (this.WindowState == FormWindowState.Maximized)
                {
                    return;
                }
                //Titlepanel.Cursor = Cursors.NoMove2D;
                oldMousePosition = e.Location;
                moving = true;
            }
    
            private void Titlepanel_MouseUp(object sender, MouseEventArgs e)
            {
                //Titlepanel.Cursor = Cursors.Default;
                moving = false;
            }
    
            private void Titlepanel_MouseMove(object sender, MouseEventArgs e)
            {
                if (e.Button == MouseButtons.Left && moving)
                {
                    Point newPosition = new Point(e.Location.X - oldMousePosition.X, e.Location.Y - oldMousePosition.Y);
                    this.Location += new Size(newPosition);
                }
            }
    
            private void Titlepanel_DoubleClick(object sender, EventArgs e)
            {
                if (titlepanel.Contains(button2))
                {
                    button2.PerformClick();
                }
            }
    
            private void titlepanel_ControlRemoved(object sender, ControlEventArgs e)
            {
                switch (e.Control.Name)
                {
                    case "button2":
                        {
                            if (titlepanel.Contains(button3))
                            {
                                button3.Left = button1.Left - button1.Width;
                            }
                            break;
                        }
                }
            }
    
            private void titlepanel_ControlAdded(object sender, ControlEventArgs e)
            {
                switch (e.Control.Name)
                {
                    case "button2":
                        {
                            if (titlepanel.Contains(button3))
                            {
                                button3.Left = button2.Left - button2.Width;
                            }
                            break;
                        }
                    case "button3":
                        {
                            if (titlepanel.Contains(button2))
                            {
                                button3.Left = button2.Left - button2.Width;
                            }
                            break;
                        }
                }
            }
    
        }
    }

    复制代码

    以下是系统自动生成的代码:

    复制代码

    namespace ZControls
    {
        partial class ZForm
        {
            /// <summary>
            /// 必需的设计器变量。
            /// </summary>
            private System.ComponentModel.IContainer components = null;
    
            /// <summary>
            /// 清理所有正在使用的资源。
            /// </summary>
            /// <param name="disposing">如果应释放托管资源,为 true;否则为 false。</param>
            protected override void Dispose(bool disposing)
            {
                if (disposing && (components != null))
                {
                    components.Dispose();
                }
                base.Dispose(disposing);
            }
    
            #region Windows 窗体设计器生成的代码
    
            /// <summary>
            /// 设计器支持所需的方法 - 不要
            /// 使用代码编辑器修改此方法的内容。
            /// </summary>
            private void InitializeComponent()
            {
                this.titlepanel = new System.Windows.Forms.Panel();
                this.titlelabel = new System.Windows.Forms.Label();
                this.button3 = new System.Windows.Forms.Button();
                this.button2 = new System.Windows.Forms.Button();
                this.button1 = new System.Windows.Forms.Button();
                this.titlepanel.SuspendLayout();
                this.SuspendLayout();
                // 
                // titlepanel
                // 
                this.titlepanel.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(192)))), ((int)(((byte)(192)))), ((int)(((byte)(0)))));
                this.titlepanel.Controls.Add(this.titlelabel);
                this.titlepanel.Controls.Add(this.button3);
                this.titlepanel.Controls.Add(this.button2);
                this.titlepanel.Controls.Add(this.button1);
                this.titlepanel.Dock = System.Windows.Forms.DockStyle.Top;
                this.titlepanel.Location = new System.Drawing.Point(0, 0);
                this.titlepanel.Margin = new System.Windows.Forms.Padding(0);
                this.titlepanel.Name = "titlepanel";
                this.titlepanel.Size = new System.Drawing.Size(468, 30);
                this.titlepanel.TabIndex = 0;
                this.titlepanel.ControlAdded += new System.Windows.Forms.ControlEventHandler(this.titlepanel_ControlAdded);
                this.titlepanel.ControlRemoved += new System.Windows.Forms.ControlEventHandler(this.titlepanel_ControlRemoved);
                this.titlepanel.DoubleClick += new System.EventHandler(this.Titlepanel_DoubleClick);
                this.titlepanel.MouseDown += new System.Windows.Forms.MouseEventHandler(this.Titlepanel_MouseDown);
                this.titlepanel.MouseMove += new System.Windows.Forms.MouseEventHandler(this.Titlepanel_MouseMove);
                this.titlepanel.MouseUp += new System.Windows.Forms.MouseEventHandler(this.Titlepanel_MouseUp);
                // 
                // titlelabel
                // 
                this.titlelabel.AutoSize = true;
                this.titlelabel.Location = new System.Drawing.Point(12, 9);
                this.titlelabel.Name = "titlelabel";
                this.titlelabel.Size = new System.Drawing.Size(0, 12);
                this.titlelabel.TabIndex = 3;
                // 
                // button3
                // 
                this.button3.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom) 
                | System.Windows.Forms.AnchorStyles.Right)));
                this.button3.Font = new System.Drawing.Font("微软雅黑 Light", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
                this.button3.Location = new System.Drawing.Point(399, 4);
                this.button3.Name = "button3";
                this.button3.Size = new System.Drawing.Size(23, 23);
                this.button3.TabIndex = 2;
                this.button3.Tag = "min";
                this.button3.Text = "-";
                this.button3.UseVisualStyleBackColor = true;
                this.button3.Click += new System.EventHandler(this.Titlebutton_Click);
                // 
                // button2
                // 
                this.button2.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom) 
                | System.Windows.Forms.AnchorStyles.Right)));
                this.button2.Font = new System.Drawing.Font("微软雅黑 Light", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
                this.button2.Location = new System.Drawing.Point(421, 4);
                this.button2.Name = "button2";
                this.button2.Size = new System.Drawing.Size(23, 23);
                this.button2.TabIndex = 1;
                this.button2.Tag = "max";
                this.button2.Text = "□";
                this.button2.UseVisualStyleBackColor = true;
                this.button2.Click += new System.EventHandler(this.Titlebutton_Click);
                // 
                // button1
                // 
                this.button1.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom) 
                | System.Windows.Forms.AnchorStyles.Right)));
                this.button1.Font = new System.Drawing.Font("微软雅黑 Light", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
                this.button1.Location = new System.Drawing.Point(442, 4);
                this.button1.Name = "button1";
                this.button1.Size = new System.Drawing.Size(23, 23);
                this.button1.TabIndex = 0;
                this.button1.Tag = "close";
                this.button1.Text = "X";
                this.button1.UseVisualStyleBackColor = true;
                this.button1.Click += new System.EventHandler(this.Titlebutton_Click);
                // 
                // ZForm
                // 
                this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F);
                this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
                this.ClientSize = new System.Drawing.Size(468, 246);
                this.ControlBox = false;
                this.Controls.Add(this.titlepanel);
                this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.None;
                this.MaximizeBox = false;
                this.Name = "ZForm";
                this.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen;
                this.titlepanel.ResumeLayout(false);
                this.titlepanel.PerformLayout();
                this.ResumeLayout(false);
    
            }
    
            #endregion
    
            private System.Windows.Forms.Panel titlepanel;
            private System.Windows.Forms.Button button3;
            private System.Windows.Forms.Button button2;
            private System.Windows.Forms.Button button1;
            private System.Windows.Forms.Label titlelabel;
        }
    }

    复制代码

    代码中FormBorderStyle覆盖父类的同名属性,主要是实现根据不同的窗体,能够自动调整标题栏按钮,因为当FormBorderStyle为FormBorderStyle.Sizable或FormBorderStyle.SizableToolWindow时,才需要最大化按钮,否则都是不需要的。不需要的情况下,将移除最大化按钮对象button2,

    titlepanel.Controls.Remove(button2);

    由于隐藏自带的标题栏需要确保Text属性为空,ControlBox为False,所以我这里采取了重写这两个属性,并加上Browsable(false),让其在编辑器中不可见。

    Title,TitleFont,TitleColor,TitleBarBackColor为新增自定义属性,分别用于设置标题文字,标题文字样式,标题文字颜色,标题栏背景色。

    重写MaximizeBox与MinimizeBox两个属性,使其根据设为True与False时,能相应的调整标题栏按钮。

    私有方法:ResetTitlePanel,用于重设标题栏按钮属性。

    方法Titlebutton_Click这个简单,主要用于实现标题栏上三个按钮点击时所要执行的操作。

    Titlepanel_MouseDown,Titlepanel_MouseUp ,Titlepanel_MouseMove 三个方法是用于实现点击鼠标右键并按住移动就能够移动窗体,Titlepanel_DoubleClick方法是实现双击时能够最大化或还原窗体功能。

    最后的titlepanel_ControlRemoved与titlepanel_ControlAdded,实现的功能是当增加或移除按钮时,调整按钮的位置。

    三、使用自定义窗体类                                     

    使用就比较简单了,先是新增一个窗体,然后将窗体类的父类由Form改为自定义窗体类(ZForm)即可,然后再切换到设计视图页面,是不是发现界面已经变化了呢,这时候就可以依据的想法灵活设置窗体标题栏样式,如下图:

    复制代码

        public partial class Form1 : ZControls.ZForm
        {
            public Form1()
            {
                InitializeComponent();
            }
        }

    复制代码

    将MaximizeBox设为False时,运行的效果,是不是有点爽啊!

    好了,都说完了,其实也很简单,我相信大部份高手都是不屑一看的,但此处只是作为一个学习与参考,可能大家有更好的方法,欢迎大家交流,共同进步。

    最后我上传源码,仅大家参考与改进:

    Demo

    ——

    分类: C#

  • 相关阅读:
    11 数值的整数次方
    10 二进制中1的个数
    6 重建二叉树
    5 从尾到头打印链表
    计算机网络面试题
    Http和Https的区别
    UVALive 7749 Convex Contour (计算几何)
    Gym 101190H Hard Refactoring (模拟坑题)
    UVa 11324 The Largest Clique (强连通分量+DP)
    HDU 6006 Engineer Assignment (状压DP)
  • 原文地址:https://www.cnblogs.com/grj001/p/12224959.html
Copyright © 2020-2023  润新知