使用C#创建自定义背景色/形状的菜单栏与工具栏

C#对于菜单栏与工具栏都提供了统一的背景色,形状的渲染类,即ToolStripRenderer类,同时根据不同的情形,提供了多个继承类,分别是ToolStripProfessionalRender,ToolStripSystemRenderer,本片文章将通过继承ToolStripProfessionalRender来实现菜单与工具栏的自定义

1.通过VS2008创建一个C#类,并命名为CustomProfessionalRenderer.cs

2.在CustomProfessionalRenderer.cs文件中加入以下引用

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Drawing;
using System.Drawing.Drawing2D;

3.定义CustomProfessionalRenderer类的控件颜色的全局变量

//默认的绘制背景色的颜色
private Color menu_color = Color.Red;      //菜单的背景色
private Color toolbar_color = Color.Red;   //工具栏的背景色
private Color image_color = Color.Red;     //菜单图片栏的背景色
private Color separator_color = Color.Red; //菜单分割条的背景色

4.定义CustomProfessionalRenderer类的构造函数

public CustomProfessionalRenderer()
            : base()
{
}

public CustomProfessionalRenderer(Color mColor, Color iColor, Color sColor)
            : base()
{
    menu_color = mColor;
    image_color = iColor;
    separator_color = sColor;
}

public CustomProfessionalRenderer(Color tColor)
            :base()
{
    toolbar_color = tColor;
}

5.重写绘制菜单栏和工具栏背景色的函数,如下所示

protected override void OnRenderToolStripBackground(ToolStripRenderEventArgs e)
        {
            //判断ToolStrip的类型
            ToolStrip tsType = e.ToolStrip;
            Graphics g = e.Graphics;
            //抗锯齿
            g.SmoothingMode = SmoothingMode.HighQuality;            

            if (tsType is MenuStrip ||
                tsType is ToolStripDropDown)
            {
                //指定填充Menu栏与ToolBar栏的背景色的画刷,使用线性渐变画刷
                LinearGradientBrush lgBursh = new LinearGradientBrush(new Point(0, 0),
                                                                      new Point(0, tsType.Height),
                                                                      Color.FromArgb(255, Color.White),
                                                                      Color.FromArgb(150, menu_color));
                GraphicsPath path = new GraphicsPath(FillMode.Winding);
                int diameter = 10;//直径
                Rectangle rect = new Rectangle(Point.Empty, tsType.Size);
                Rectangle arcRect = new Rectangle(rect.Location, new Size(diameter, diameter));

                path.AddLine(0, 0, 10, 0);
                // 右上角
                arcRect.X = rect.Right - diameter;
                path.AddArc(arcRect, 270, 90);

                // 右下角
                arcRect.Y = rect.Bottom - diameter;
                path.AddArc(arcRect, 0, 90);

                // 左下角
                arcRect.X = rect.Left;
                path.AddArc(arcRect, 90, 90);
                path.CloseFigure();

                //设置控件的窗口区域
                tsType.Region = new Region(path);

                //填充窗口区域
                g.FillPath(lgBursh, path);
            }
            else if (tsType is ToolStrip)
            {
                //指定填充Menu栏与ToolBar栏的背景色的画刷,使用线性渐变画刷
                LinearGradientBrush lgBursh = new LinearGradientBrush(new Point(0, 0),
                                                                      new Point(0, tsType.Height),
                                                                      Color.FromArgb(255, Color.White),
                                                                      Color.FromArgb(150, toolbar_color));
                GraphicsPath path = new GraphicsPath(FillMode.Winding);
                int diameter = 10;//直径
                Rectangle rect = new Rectangle(Point.Empty, tsType.Size);
                Rectangle arcRect = new Rectangle(rect.Location, new Size(diameter, diameter));

                path.AddLine(0, 0, 10, 0);
                // 右上角
                arcRect.X = rect.Right - diameter;
                path.AddArc(arcRect, 270, 90);

                // 右下角
                arcRect.Y = rect.Bottom - diameter;
                path.AddArc(arcRect, 0, 90);

                // 左下角
                arcRect.X = rect.Left;
                path.AddArc(arcRect, 90, 90);
                path.CloseFigure();

                //设置控件的窗口区域
                tsType.Region = new Region(path);

                //填充窗口区域
                g.FillPath(lgBursh, path);
            }
            else
            {
                base.OnRenderToolStripBackground(e);
            }
        }

6.重写绘制菜单栏和工具栏边框的函数,如下所示

protected override void OnRenderToolStripBorder(ToolStripRenderEventArgs e)
        {
            //判断ToolStrip的类型
            ToolStrip tsType = e.ToolStrip;
            Graphics g = e.Graphics;
            //抗锯齿
            g.SmoothingMode = SmoothingMode.HighQuality;                        

            if (tsType is MenuStrip ||
                tsType is ToolStripDropDown)
            {
                //设置画笔
                Pen LinePen = new Pen(menu_color);
                GraphicsPath path = new GraphicsPath(FillMode.Winding);
                int diameter = 10;//直径
                Rectangle rect = new Rectangle(Point.Empty, tsType.Size);
                Rectangle arcRect = new Rectangle(rect.Location, new Size(diameter, diameter));

                path.AddLine(0, 0, 10, 0);
                // 右上角
                arcRect.X = rect.Right - diameter;
                path.AddArc(arcRect, 270, 90);

                // 右下角
                arcRect.Y = rect.Bottom - diameter;
                path.AddArc(arcRect, 0, 90);

                // 左下角
                arcRect.X = rect.Left;
                path.AddArc(arcRect, 90, 90);
                path.CloseFigure();

                //画边框
                g.DrawPath(LinePen, path);
            }
            else if (tsType is ToolStrip)
            {
                //设置画笔
                Pen LinePen = new Pen(toolbar_color);
                GraphicsPath path = new GraphicsPath(FillMode.Winding);
                int diameter = 10;//直径
                Rectangle rect = new Rectangle(Point.Empty, tsType.Size);
                Rectangle arcRect = new Rectangle(rect.Location, new Size(diameter, diameter));

                path.AddLine(0, 0, 10, 0);
                // 右上角
                arcRect.X = rect.Right - diameter;
                path.AddArc(arcRect, 270, 90);

                // 右下角
                arcRect.Y = rect.Bottom - diameter;
                path.AddArc(arcRect, 0, 90);

                // 左下角
                arcRect.X = rect.Left;
                path.AddArc(arcRect, 90, 90);
                path.CloseFigure();

                //画边框
                g.DrawPath(LinePen, path);
            }
            else
            {
                base.OnRenderToolStripBorder(e);
            }
        }

7.当菜单上存在多级目录时,会显示相应的小箭头,想修改,请重写如下函数

protected override void OnRenderArrow(ToolStripArrowRenderEventArgs e)
        {
            e.ArrowColor = menu_color;
            base.OnRenderArrow(e);
        }

8.重写子菜单的渲染函数,如下所示

protected override void OnRenderMenuItemBackground(ToolStripItemRenderEventArgs e)
        {
            Graphics g = e.Graphics;
            ToolStripItem item = e.Item;
            ToolStrip tsType = e.ToolStrip;

            g.SmoothingMode = SmoothingMode.HighQuality;

            //渲染顶级项
            if (tsType is MenuStrip)
            {
                if (e.Item.Selected)
                {
                    Pen LinesPen = new Pen(Color.FromArgb(205, 226, 252));
                    Point[] LinePoint = { new Point(0, 2),
                                           new Point(item.Size.Width - 1, 2),
                                           new Point(item.Size.Width - 1, item.Size.Height - 3),
                                           new Point(0, item.Size.Height - 3),
                                           new Point(0, 2)};
                    g.DrawLines(LinesPen, LinePoint);

                    SolidBrush brush = new SolidBrush(Color.FromArgb(197, 228, 253));
                    Rectangle rect = new Rectangle(0, 2, item.Size.Width - 1, item.Size.Height - 5);
                    g.FillRectangle(brush, rect);
                }
                if (item.Pressed)
                {
                    Pen LinesPen = new Pen(Color.FromArgb(197, 228, 253));
                    Point[] LinePoint = { new Point(0, 2),
                                           new Point(item.Size.Width - 1, 2),
                                           new Point(item.Size.Width - 1, item.Size.Height - 3),
                                           new Point(0, item.Size.Height - 3),
                                           new Point(0, 2)};
                    g.DrawLines(LinesPen, LinePoint);
                }
            }
            //渲染下拉项
            else if (tsType is ToolStripDropDown)
            {
                g.SmoothingMode = SmoothingMode.HighQuality;
                LinearGradientBrush lgbrush = new LinearGradientBrush(new Point(0, 0), new Point(item.Width, 0), Color.FromArgb(200, menu_color), Color.FromArgb(0, Color.White));
                if (item.Selected)
                {
                    GraphicsPath gp = GetRoundedRectPath(new Rectangle(0, 0, item.Width, item.Height), 10);
                    g.FillPath(lgbrush, gp);
                }
            }
            else
            {
                base.OnRenderMenuItemBackground(e);
            }
        }

9.重写菜单上分割线的函数,如下所示

protected override void OnRenderSeparator(ToolStripSeparatorRenderEventArgs e)
        {
            Graphics g = e.Graphics;

            ToolStrip tsType = e.ToolStrip;

            if ( tsType is ToolStripDropDown)
            {
                LinearGradientBrush lgbrush = new LinearGradientBrush(new Point(0, 0),
                                                                  new Point(e.Item.Width, 0),
                                                                  separator_color,
                                                                  Color.FromArgb(0, separator_color));
                g.FillRectangle(lgbrush, new Rectangle(33, e.Item.Height / 2, e.Item.Width / 4 * 3, 1));
            }
        }

10.重写菜单上左边放置图片的区域,如下所示

protected override void OnRenderImageMargin(ToolStripRenderEventArgs e)
        {
            //base.OnRenderImageMargin(e);
            //屏蔽掉左边图片竖条

            Graphics g = e.Graphics;
            g.SmoothingMode = SmoothingMode.HighQuality;
            Rectangle image_rect = e.AffectedBounds;

            //SolidBrush brush = new SolidBrush(image_color);
            LinearGradientBrush lgbrush = new LinearGradientBrush(new Point(0, 0),
                                                                  new Point(image_rect.Width, 0),
                                                                  Color.FromArgb(200, image_color),
                                                                  Color.FromArgb(0, Color.White));
            Rectangle rect = new Rectangle(0, 0, image_rect.Width, image_rect.Height);
            g.FillRectangle(lgbrush, rect);
        }

11.重写绘制工具栏上BUTTON按钮背景色的函数,如下所示

protected override void OnRenderButtonBackground(ToolStripItemRenderEventArgs e)
        {
            Graphics g = e.Graphics;
            g.SmoothingMode = SmoothingMode.HighQuality;
            ToolStripItem item = e.Item;

            if (item.Selected)
            {
                Pen LinesPen = new Pen(Color.FromArgb(205, 226, 252));
                Point[] LinePoint = { new Point(0, 2),
                                           new Point(item.Size.Width - 1, 2),
                                           new Point(item.Size.Width - 1, item.Size.Height - 3),
                                           new Point(0, item.Size.Height - 3),
                                           new Point(0, 2)};
                g.DrawLines(LinesPen, LinePoint);

                SolidBrush brush = new SolidBrush(Color.FromArgb(197, 228, 253));
                Rectangle rect = new Rectangle(0, 2, item.Size.Width - 1, item.Size.Height - 5);
                g.FillRectangle(brush, rect);
            }
            else
            {
                base.OnRenderMenuItemBackground(e);
            }
        }

12.另在代码上加入以下函数

public static GraphicsPath GetRoundedRectPath(Rectangle rect, int radius)
        {
            int diameter = radius;
            Rectangle arcRect = new Rectangle(rect.Location, new Size(diameter, diameter));
            GraphicsPath path = new GraphicsPath();

            // 左上角
            path.AddArc(arcRect, 180, 90);

            // 右上角
            arcRect.X = rect.Right - diameter;
            path.AddArc(arcRect, 270, 90);

            // 右下角
            arcRect.Y = rect.Bottom - diameter;
            path.AddArc(arcRect, 0, 90);

            // 左下角
            arcRect.X = rect.Left;
            path.AddArc(arcRect, 90, 90);
            path.CloseFigure();

            return path;
        }

到此为止,已经写好了菜单与工具栏的渲染类,下面就是如何调用了

1.菜单栏的调用

class CustomMenuStrip : MenuStrip
{
    private Color menu_Color = Color.Gray;
    private Color image_Color = Color.Gray;
    private Color separator_color = Color.Gray;

    public CustomMenuStrip()
    {
        this.Renderer = new CustomProfessionalRenderer(menu_Color, image_Color, separator_color);
    }

    public void SetColor(Color mColor, Color iColor, Color sColor)
    {
        menu_Color = mColor;
        image_Color = iColor;
        separator_color = sColor;
        this.Renderer = new CustomProfessionalRenderer(menu_Color, image_Color, separator_color);
    }
}

2.工具栏的调用

class CunstomToolStrip : ToolStrip
{
    private Color _themeColor = Color.Gray;

    public CunstomToolStrip()
    {
        this.Renderer = new CustomProfessionalRenderer(_themeColor);
    }

    public Color ThemeColor
    {
        get { return _themeColor; }
        set
        {
            _themeColor = value;
            this.Renderer = new CustomProfessionalRenderer(_themeColor);
        }
    }
}

按照上述方式使用之后,大家可以看到如下的菜单/工具栏界面

使用C#创建自定义背景色/形状的菜单栏与工具栏

时间: 2024-08-26 16:46:23

使用C#创建自定义背景色/形状的菜单栏与工具栏的相关文章

Dojo学习笔记(二十一):创建自定义Dojo小部件

在这个教程中,我们将会演示如何利用Dojo 和Dijit框架来创建自定义的小部件,主要会使用到dijit/_WidgetBase and dijit/_TemplatedMixin. Dojo的Dijit 库包含了丰富的界面小部件(Widgets),通过使用这些小部件,可以打造出强大的Web应用界面,从高级的表单元素,到复杂页面布局. 假设我们需要开发一个能展示所有Dojo教程作者的简介信息的页面,我们手头的数据源是如下的JSON数据: [     {         "name": 

C++ GUI Qt4编程-创建自定义窗口部件

C++ GUI Qt4编程-创建自定义窗口部件 Qtqt4 通过Qt窗口部件进行子类化或者直接对QWidget进行子类化,就可以创建自定义窗口部件,下面示范两种方式,并且也会说明如何把自定义窗口部件集成到Qt设计师中,这样就可以像使用内置的Qt窗口部件一样来使用它们,最后展示使用双缓冲技术(一种用于快速绘制的强大技术)的自定义窗口部件. 1.自定义Qt窗口部件 我们发现Qt窗口部件需要更多的自定义定制,这些定制可能要比它在Qt设计师里设置的属性或者对它调用的那些函数更多一些,一个简单而直接的解决

【翻译】在Ext JS和Sencha Touch中创建自定义布局

原文:Creating Custom Layouts in Ext JS and Sencha Touch 布局系统是Sencha框架中最强大和最独特的一部分.布局会处理应用程序中每个组件的大小和位置,因而,不需要手动去管理那些碎片.Ext JS与Sencha Touch的布局类有许多相似之处,最近在 Ivan Jouikov的这篇博文中对他们进行了详细的分析. 虽然是这样,但很多Ext JS和Sencha Touch开发人员可能永远都不会去了解布局系统的机制原理.Sencha框架已经提供了最常

UIGestureRecognizer教程:创建自定义手势

原文链接: UIGestureRecognizer教程:创建自定义手势 如果是首次访问,你可能会想订阅我的RSS feed或者在Twitter上粉我.非常感谢你的到来! UIGestureRecognizer 来识别圆*" title=""> 学习如何使用自定义 UIGestureRecognizer 来识别圆 自定义手势可以使app感觉更独特,更有活力,从而取悦用户.如果把基本的点击.拖移和旋转手势比作iOS世界里的通用皮卡,自定义手势则是拥有个性喷漆和水动力,且闪闪

UniGUI的TUniLoginForm窗口自定义背景色和背景图片

雨田家园 UniGUI的TUniLoginForm窗口自定义背景色 uniGUI的TUniLoginForm类创建的登录窗口默认是不带颜色,可以自定义css风格来改变背景颜色. 一般是通过在UniServerModule中,在CustcomSS属性中,修改extjs的css定义来实现,修改登录窗口的背景颜色可以修改 .x-body 的定义来实现,如: {background-color: rgb(11, 80, 184);margin: 0;} 类似的,还可以给UniLoginForm的背景添加

微信公众平台如何创建自定义菜单?

微信现在的功能越来越强大了,申请认证后的开发者能自定义菜单,用户直接点击微信界面下方的菜单,就能直接去到指定的页面,下面小编用[微信公众平台测试号]为大家演示一下怎么创建自定义菜单. 工具/原料 认证后的微信公众平台 微信公众平台切换开发者模式 方法/步骤 登录[微信公众平台],选择[功能]菜单下面的[高级功能],进入[开发模式]. 由于小编的微信公众平台还没通过认证,下面用[申请测试账户]为大家演示. 微信公众平台接口测试帐号申请,无需公众帐号.快速申请接口测试号,直接体验和测试公众平台所有高

Drupal创建自定义表单,上传文件代码

Drupal中创建自定义表单,用来上传文件,对上传文件做一些操作.以下是放在Module中的代码: 一.菜单建立表单路径 /** Implementation of hook_menu(). */ function moduleName_menu () { $items = array(); $items['admin/import'] = array( 'title' => 'title', 'page callback' => 'drupal_get_form', 'page argume

创建自定义存储过程

--创建自定义存储过程--语法:--if exists(select * from sysobjects where name='')-- drop proc ''--go--create proc[edure] usp_名称-- 相当于方法的():创建参数--as-- 相当于方法{}:方法体--go--调用语法:--exec 存储过程名称 参数值,参数值 .....--创建存储过程,获取所有学员信息if exists(select * from sysobjects where name='u

通过反射创建自定义泛型的实例。

比如有这样一个泛型:Demo.GenericsSimple<T,TT> 我想要通过反射创建一个Demo.GenericsSimple<string,int>的实例可以通过下面的格式进行创建: System.Reflection.Assembly.GetExecutingAssembly().CreateInstance("命名空间.User`形参数量N[[1形参类型全名,形参类型所在的程 序集名称],[2形参类型全名,形参类型所在的程序集名称],[3形参类型全名,形参类型