C# 自定义进度条

887 查看

需求:

由于这段时间一直在写电子称的串口,因为客户是做原液的所有的重量要求特别严格,不能多一克也不能少一克,所有需要给他们写一个进度条来表示重量,能够观察是否超出范围;

分析:

拿到这个需求的时候,就有几个问题,进度条是有精读,以及刻度的,并且还得有分割线,那就得设计自定义控件了,当重量超过某一个分割线的时候里面的条就变颜色大致情况如下;


ZAC4PH3AU2$UVYD7(_QSK_Q.png

思路:

我的想法是这样首先绘制会2个矩形,然后呢外矩形的高度不变,内矩形的高度就来表示我们串口所接收的Weight数据,当值增加或者减少的时候也就等于绘制其内矩形的高度,然后绘制线条刻度,以及刻度下面的文字;
C#自定义控件跟android 的也差不了多少,重写其onPaint 方法,进行绘制,onPaint方法代码如下,比较简单重要的地方我都已经给出了注释就不在讲解了;

        protected override void OnPaint(PaintEventArgs e)
        {

            greenPen = new Pen(System.Drawing.Color.Green);
            redPen = new Pen(System.Drawing.Color.Red);
            yellowPen = new Pen(System.Drawing.Color.Yellow);

            // 相当于android 的画笔
            Pen out_Pen = new Pen(System.Drawing.Color.Gray);
            //
            Pen inner_pen = new Pen(System.Drawing.Color.Blue);
            //这其实也就相当于android canvas;
            g = e.Graphics;
            //外 矩形
            mOuterRectWeight = this.Width - 40;
            mOuterRectHeight = this.Height - 100;
            Rectangle rect = new Rectangle(0, 0, OuterRectWeight, OuterRectHeight);
            g.DrawRectangle(out_Pen, rect);


            //内 矩形
            Rectangle innerRect = new Rectangle(0, OuterRectHeight - (int)(InnerRectHeight), OuterRectWeight, (int)(InnerRectHeight));
            g.DrawRectangle(inner_pen, innerRect);
            // 色刷
            SolidBrush b1 = new SolidBrush(Color.Blue);

            if (InnerRectHeight >= GreenValues && InnerRectHeight <= YellowVlues)
            {
                b1.Color = Color.Green;
                greenPen.Color = System.Drawing.Color.Black;
            }
            if (InnerRectHeight >= YellowVlues && InnerRectHeight <= RedVlues)
            {
                b1.Color = Color.Yellow;
                yellowPen.Color = System.Drawing.Color.Black;
                greenPen.Color = System.Drawing.Color.Black;
            }
            if (InnerRectHeight >= RedVlues)
            {
                b1.Color = Color.Red;
                redPen.Color = System.Drawing.Color.Black;
                greenPen.Color = System.Drawing.Color.Black;
                yellowPen.Color = System.Drawing.Color.Black;
            }
            //充满
            g.FillRectangle(b1, innerRect);

            // Draw Line
            onDrawGreentLine();

            onDrawYelloLine();

            onDrawRedLin();

            //drawContent
            drawBottomContent();
            //
        }

        private void onDrawGreentLine()
        {
            greenPen.Width = 2.0f;
            int greentVlues = (int)(GreenValues);
            g.DrawLine(greenPen, 0, OuterRectHeight - greentVlues, OuterRectWeight, OuterRectHeight - greentVlues);

            // 重量标识
            drawContent(GreenValues.ToString(), font, OuterRectWeight, OuterRectHeight - greentVlues);
        }


        private void onDrawYelloLine()
        {

            yellowPen.Width = 2.0f;
            int yellowVlues = (int)(YellowVlues);
            g.DrawLine(yellowPen, 0, OuterRectHeight - yellowVlues, OuterRectWeight, OuterRectHeight - yellowVlues);
            // 标识
            SolidBrush s = new SolidBrush(Color.Yellow);
            drawContent(YellowVlues.ToString(), font, OuterRectWeight, OuterRectHeight - yellowVlues);

        }
        private void onDrawRedLin()
        {

            redPen.Width = 2.0f;
            int redVlues = (int)RedVlues;
            g.DrawLine(redPen, 0, OuterRectHeight - redVlues, OuterRectWeight, OuterRectHeight - redVlues);
            // 标识
            SolidBrush s = new SolidBrush(Color.Red);
            drawContent(RedVlues.ToString(), font, OuterRectWeight, OuterRectHeight - redVlues);

        }
        private void drawContent(string content, Font f, float x, float y)
        {
            SolidBrush s = new SolidBrush(Color.Black);
            g.DrawString(content, f, s, x, y);
        }

这其中你也可以将很多属性通过get、set方法公布出去;

调用代码如下:

                myTestProgressBar1.RedVlues = 230.33M;
                myTestProgressBar1.YellowVlues = 150.3M;
                myTestProgressBar1.GreenValues = 70.5M;

                while (true)
                {
                    myTestProgressBar1.InnerRectHeight =
                    myTestProgressBar1.InnerRectHeight + 1;
                    myTestProgressBar1.Content = myTestProgressBar1.InnerRectHeight.ToString();
                    myTestProgressBar1.Refresh();
                    Thread.Sleep(100);
                }

最终运行效果图如下:


gif工具玩的不好!.gif

额。。录制的工具会太会玩,特别简单的一个进度条,当然还有很多可以优化的地方,也可以在这个基础上增加更多的功能,比如进度条的style等,因为最近工作比较忙,所有都没有时间总结,接下来会好好整理近期的问题,记录下来;

Download code

有什么问题可以留言;