先看看样式
一个扇形的进度条
对外公开的方法和属性
事件
value_change;//值改变时触发的事件
progress_finshed;//进度条跑完时触发的事件
属性
Max_value//获取最大值
Min_value//获取最小值
Current_value//设置或获取当前值设置
using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Drawing.Drawing2D; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; using System.Threading; namespace WindowsFormsApplication19 { public partial class CustomControl1 : Control { Bitmap background; //进度条的最大值,最小值,和当前值 private int min_value = 0; private int max_value = 100; private int current_value; private int min_value_protect_value = 0;//用户保护max和min变量只赋值一次的值 private int max_value_protect_value = 0;// //控件的最小吃寸 private int min_size; //三个颜色,最外层,中间层和最内填充层 private Color edge_line_color = Color.FromArgb(150, 174, 193); private Color edge_2_line_color = Color.FromArgb(93, 136, 163); private Color inside_fill_color = Color.FromArgb(231, 230, 235); //字体颜色 private Color str_color = Color.Black; //最外层和中间层的宽度 private float edge_line_width = 5f; private float edge_2_line_width = 5f; private DockStyle dock=DockStyle.None; //事件 public delegate void vaule_change_invoke(EventArgs args); public event vaule_change_invoke value_change;//值改变时触发的事件 public event vaule_change_invoke progress_finshed;//进度条跑完时触发的事件 //这里我暂时不对外开放接口,控件样式固定 /* public Color Edge_line_color { get { return edge_line_color; } set { edge_line_color = value; } } public Color Edge_2_line_color { get { return edge_2_line_color; } set { edge_2_line_color = value; } } public Color Inside_fill_color { get { return inside_fill_color; } set { inside_fill_color = value; } } public Color Str_color { get { return str_color; } set { str_color = value; } } public float Edge_line_width { get { return edge_line_width; } set { if (value > 0) edge_line_width = value; } } public float Edge_2_line_width { get { return edge_2_line_width; } set { if (value > 0) edge_2_line_width = value; } } */ [Browsable(false)] public new DockStyle Dock { get { return dock; } set { dock = value; } } /// <summary> /// 获取最小值 /// </summary> [Browsable(false)] public int Min_value { get { return min_value; } private set { if (value >= 0&&value<max_value && min_value_protect_value == 0) { min_value = value; current_value = value; min_value_protect_value = 1; } } } /// <summary> /// 获取最大值 /// </summary> [Browsable(false)] public int Max_value { get { return max_value; } private set { if (value > 0 && value > Min_value && max_value_protect_value == 0) { max_value = value; max_value_protect_value=1; } } } /// <summary> /// 设置或获取当前值,范围0-100 /// </summary> public int Current_value { get { return current_value; } set { if (value >= min_value && value <= max_value) { current_value = value; //触发派生重写方法 this.onvaluechange(new EventArgs()); //重绘控件 this.Invalidate(); if (progress_finshed != null) { //进度条跑完时触发 if (max_value == current_value) this.progress_finshed(new EventArgs()); } if (value_change != null) { //触发事件 this.value_change(new EventArgs()); } } } } public CustomControl1() { InitializeComponent(); setinfo(); //这里触发一次OnInvalidated,保证在onpaint前建立背景位图 this.Invalidate(); min_size = (int)(edge_2_line_width * 2 + edge_line_width * 2 + 50); } /// <summary> /// 绘图优化 /// </summary> private void setinfo() { this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true); this.SetStyle(ControlStyles.ResizeRedraw, true); this.SetStyle(ControlStyles.UserPaint, true); this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); } /// <summary> /// 值修改触发的方法 /// </summary> /// <param name="eventArgs"></param> protected virtual void onvaluechange(EventArgs eventArgs) { } protected override void OnResize(EventArgs e) { //保证控件最小尺寸
//防止拖拽时崩毁
int temp = Math.Min(Width, Height); temp = temp > min_size ? temp : min_size; Width = Height = temp; build_bitmap_buffer(); this.Invalidate(); base.OnResize(e); } /// <summary> /// 控件及子控件重绘 /// </summary> /// <param name="pe"></param> protected override void OnPaint(PaintEventArgs pe) { base.OnPaint(pe); } /// <summary> /// 控件重绘 /// </summary> /// <param name="e"></param> protected override void OnInvalidated(InvalidateEventArgs e) { if (background != null) update_the_progress_bar(); else { build_bitmap_buffer(); } base.OnInvalidated(e); } /// <summary> /// 创建背景缓冲位图 /// </summary> private void build_bitmap_buffer() { if (background != null) { background.Dispose(); } background = new Bitmap(Width, Width); Graphics g = Graphics.FromImage(background); g.Clear(Color.Transparent); g.Dispose(); } /// <summary> /// 根据当前值更新进度条 /// </summary> private void update_the_progress_bar() { Graphics g = Graphics.FromImage(background); Draw_with_HighQuality(g); g.Clear(Color.Transparent); Pen p = new Pen(edge_line_color, edge_line_width); #region 绘制最外部圆 int x_y = (int)(edge_line_width / 2); int w_h = Width - (int)edge_line_width; Rectangle rect = new Rectangle(x_y, x_y, w_h, w_h); g.DrawEllipse(p, rect); #endregion #region 绘制第二层圆 p.Width = edge_2_line_width; p.Color = edge_2_line_color; x_y += (int)(edge_line_width / 2 + edge_2_line_width / 2); w_h = Width - (int)(edge_line_width * 2 + edge_2_line_width); rect = new Rectangle(x_y, x_y, w_h, w_h); g.DrawEllipse(p, rect); #endregion p.Dispose(); #region 绘制扇形 Brush sb = new SolidBrush(inside_fill_color); x_y = (int)(edge_line_width + edge_2_line_width); w_h = Width - x_y * 2; rect = new Rectangle(x_y, x_y, w_h, w_h); float rad = ((float)current_value - min_value) / ((float)max_value - min_value); float frad = (360 * rad); g.FillPie(sb, rect, -90, frad); StringFormat sf = new StringFormat(); sf.Alignment = StringAlignment.Center; sf.LineAlignment = StringAlignment.Center; g.DrawString((rad * 100).ToString() + "%", new Font("宋体", 12, FontStyle.Bold), new SolidBrush(str_color), this.ClientRectangle, sf); #endregion g.Dispose(); this.BackgroundImage = background; } /// <summary> /// 高质量绘图 /// </summary> /// <param name="g">绘图工具graphics</param> private void Draw_with_HighQuality(Graphics g) { g.SmoothingMode = SmoothingMode.AntiAlias; g.InterpolationMode = InterpolationMode.HighQualityBicubic; g.CompositingQuality = CompositingQuality.HighQuality; } } }
源码地址: http://pan.baidu.com/s/1i3N2vlz
压缩文件为测试控件的demo;
cs是控件的源码文件;直接添加到项目中和其他控件一样拖进去就可以了