软件学习记录:(11) PointCurve 控件

软件学习记录:(11) PointCurve 控件

效果:

一、使用方法

1.连线:

this.pCurveMonitor.AddSinglePoint(new PointF(Convert.ToSingle(this.lbl_XAxisPosition.Text), Convert.ToSingle(this.lbl_YAxisPosition.Text)));

2.清除图片信息:

this.pCurveMonitor.ClearAllPoints();
this.pCurveMonitor.Refresh();

3.图像初始化

this.pCurveMonitor.ClearAllPoints();

二、设计思路

  1. 需要考虑的属性:

    原点坐标 X轴最大坐标值 Y轴最大坐标值 Z轴最大坐标值 取料口X轴坐标
    取料口Y轴坐标 加工处X轴坐标 加工处Y轴坐标 出料口X轴坐标 出料口Y轴坐标
    取料口点颜色 加工处点颜色 出料口点颜色 取料口字符串 加工处字符串
    出料口字符串 绘制点直径 绘制曲线颜色 绘制曲线宽度

    上述属性都要设置 this.Invalidate(); 确保立即进行重绘

  2. 绘制方法

    1. 坐标轴需要使用带有箭头的直线。故使用画笔的CustomEndCap方法
    2. 绘制X轴。首先计算机是以左上角作为原点的。那么X轴的起点位置(x=gap,y=高度-gap),终点位置(x=宽度-gap,y=高度-gap)。然后使用DrawLine画线
    3. 绘制Y轴。Y轴的起点位置(x=gap,y=高度-gap),终点位置(x=gap,y=gap)。然后使用DrawLine画线
    4. 绘制原点,主要是写上"0"这个字符。居中对其,使用DrawString方法,为了不遮挡图像,需要位置微调。
    5. 绘制X轴最大DrawString方法,尽量在到最大的地方,稍微往左一点,让字体在轴的下面,不要超出
    6. 绘制Y轴最大DrawString方法,尽量在到最大的地方,稍微往下一点,让字体在轴的下面,不要超出
    7. 绘制取料点图像,使用画笔的FillEllipse(外切矩形来绘制椭圆),pointdiameter是绘制点的直径。先找到绘制点的位置,然后以绘制点直径作为矩形的长宽绘制出一个圆。就是取料点的图形
    8. 取料点字:微调位置,不遮挡取料点图像
    9. 其他基本相同
    10. 绘制直线:原先外部方法把数值点坐标点加入了pointList中,然后一一取出,映射到坐标轴上,然后加入到point[]数组中,传入到DrawLine方法中,进行绘制

三、代码示例

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;

namespace MotionPlanProject
{
    /// <summary>
    /// 自定义控件
    /// </summary>
    public partial class PointCurve : UserControl
    {
        public PointCurve()
        {
            InitializeComponent();
            //设置控件样式
            this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
            this.SetStyle(ControlStyles.DoubleBuffer, true);
            this.SetStyle(ControlStyles.ResizeRedraw, true);
            this.SetStyle(ControlStyles.Selectable, true);
            this.SetStyle(ControlStyles.SupportsTransparentBackColor, true);
            this.SetStyle(ControlStyles.UserPaint, true);
        }

        #region 绘制对象的创建

        //画布
        private Graphics g;

        //画笔
        private Pen p;

        #endregion

        #region 控件属性

        private int orginGap = 20;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("原点坐标")]
        public int OrginGap
        {
            get { return orginGap; }
            set
            {
                if (value <= 0)
                {
                    return;
                }
                orginGap = value;
                this.Invalidate();
            }
        }

        private float maxXAxis = 100000.0f;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("X轴最大坐标值")]
        public float MaxXAxis
        {
            get { return maxXAxis; }
            set
            {
                maxXAxis = value;
                this.Invalidate();
            }
        }

        private float maxYAxis = 100000.0f;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("Y轴最大坐标值")]
        public float MaxYAxis
        {
            get { return maxYAxis; }
            set
            {
                maxYAxis = value;
                this.Invalidate();
            }
        }

        private float maxZAxis = 70000.0f;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("Z轴最大坐标值")]
        public float MaxZAxis
        {
            get { return maxYAxis; }
            set { maxYAxis = value; }
        }


        private int reclaimerXAxis = 0;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("取料口X轴坐标")]
        public int ReclaimerXAxis
        {
            get { return reclaimerXAxis; }
            set
            {
                reclaimerXAxis = value;
                this.Invalidate();
            }
        }


        private int reclaimerYAxis = 0;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("取料口Y轴坐标")]
        public int ReclaimerYAxis
        {
            get { return reclaimerYAxis; }
            set
            {
                reclaimerYAxis = value;
                this.Invalidate();
            }
        }

        private int processXAxis = 0;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("加工处X轴坐标")]
        public int ProcessXAxis
        {
            get { return processXAxis; }
            set
            {
                processXAxis = value;
                this.Invalidate();
            }
        }


        private int processYAxis = 0;
        [Browsable(true)]
        [Category("自定义属性")]
        [Description("加工处Y轴坐标")]
        public int ProcessYAxis
        {
            get { return processYAxis; }
            set
            {
                processYAxis = value;
                this.Invalidate();
            }
        }


        private int outletXAxis = 0;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("出料口X轴坐标")]
        public int OutletXAxis
        {
            get { return outletXAxis; }
            set
            {
                outletXAxis = value;
                this.Invalidate();
            }
        }

        private int outletYAxis = 0;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("出料口Y轴坐标")]
        public int OutletYAxis
        {
            get { return outletYAxis; }
            set
            {
                outletYAxis = value;
                this.Invalidate();
            }
        }


        private Color reclaimerColor = Color.Blue;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("取料口点颜色")]
        public Color ReclaimerColor
        {
            get { return reclaimerColor; }
            set
            {
                reclaimerColor = value;
                this.Invalidate();
            }
        }


        private Color processColor = Color.Green;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("加工处点颜色")]
        public Color ProcessColor
        {
            get { return processColor; }
            set
            {
                processColor = value;
                this.Invalidate();
            }
        }


        private Color outletColor = Color.Red;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("出料口点颜色")]
        public Color OutletColor
        {
            get { return outletColor; }
            set
            {
                outletColor = value;
                this.Invalidate();
            }
        }

        private string reclaimerStr = "取料口";

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("取料口字符串")]
        public string ReclaimerStr
        {
            get { return reclaimerStr; }
            set
            {
                reclaimerStr = value;
                this.Invalidate();
            }
        }


        private string processStr = "加工处";

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("加工处字符串")]
        public string ProcessStr
        {
            get { return processStr; }
            set
            {
                processStr = value;
                this.Invalidate();
            }
        }


        private string outletStr = "出料口";

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("出料口字符串")]
        public string OutletStr
        {
            get { return outletStr; }
            set
            {
                outletStr = value;
                this.Invalidate();
            }
        }

        private int pointdiameter = 5;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("绘制点直径")]
        public int Pointdiameter
        {
            get { return pointdiameter; }
            set
            {
                pointdiameter = value;
                this.Invalidate();
            }
        }

        private Color lineColor = Color.Black;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("绘制曲线颜色")]
        public Color LineColor
        {
            get { return lineColor; }
            set
            {
                lineColor = value;
                this.Invalidate();
            }
        }

        private int lineThickness = 1;

        [Browsable(true)]
        [Category("自定义属性")]
        [Description("绘制曲线宽度")]
        public int LineThickness
        {
            get { return lineThickness; }
            set
            {
                lineThickness = value;
                this.Invalidate();
            }
        }


        private List<PointF> pointList = new List<PointF>();

        public void AddSinglePoint(PointF point)
        {
            pointList.Add(point);
            this.Invalidate();
        }

        public void AddMultiPoints(List<PointF> list)
        {
            AddMultiPoints(list.ToArray());
            this.Invalidate();
        }

        public void AddMultiPoints(PointF[] list)
        {
            pointList.AddRange(list);
            this.Invalidate();
        }

        public void ClearAllPoints()
        {
            pointList = new List<PointF>();
            this.Invalidate();
        }

        #endregion

        protected override void OnPaint(PaintEventArgs e)
        {
            base.OnPaint(e);

            //绘制过程

            //获取画布
            g = e.Graphics;

            //设置画布
            g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;
            g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
            g.TextRenderingHint = System.Drawing.Text.TextRenderingHint.AntiAlias;
            g.TextRenderingHint = System.Drawing.Text.TextRenderingHint.ClearTypeGridFit;

            //正式绘制

            //设置画笔
            p = new Pen(Color.Black, 1.5f);

            p.CustomEndCap = new AdjustableArrowCap(p.Width * 3, p.Width * 4, true);

            //绘制X轴

            g.DrawLine(p, new Point(orginGap, this.Height - orginGap), new Point(this.Width - orginGap, this.Height - orginGap));


            //绘制Y轴

            g.DrawLine(p, new Point(orginGap, this.Height - orginGap), new Point(orginGap, orginGap));


            //绘制原点

            StringFormat sf = new StringFormat();
            sf.Alignment = StringAlignment.Center;
            sf.LineAlignment = StringAlignment.Center;

            g.DrawString("0", this.Font, new SolidBrush(Color.Black), new Rectangle(0, this.Height - orginGap, orginGap, orginGap), sf);


            //绘制X轴最大
            g.DrawString(maxXAxis.ToString(), this.Font, new SolidBrush(Color.Black), new Rectangle(this.Width - 50, this.Height - (orginGap - 5), 50, orginGap - 5), sf);

            //绘制Y轴最大
            g.DrawString(maxYAxis.ToString(), this.Font, new SolidBrush(Color.Black), new Rectangle(0, 0, 50, orginGap), sf);

            //绘制取料点

            float reclaimerX = (this.Width - 2 * orginGap) / maxXAxis * reclaimerXAxis + orginGap;

            float reclaimerY = this.Height - ((this.Height - 2 * orginGap) / maxYAxis * reclaimerYAxis + orginGap);

            g.FillEllipse(new SolidBrush(reclaimerColor), new RectangleF(reclaimerX - 0.5f * pointdiameter, reclaimerY - 0.5f * pointdiameter, pointdiameter, pointdiameter));

            g.DrawString(reclaimerStr, this.Font, new SolidBrush(reclaimerColor), new RectangleF(reclaimerX - 25.0f, reclaimerY - 20.0f, 50.0f, 20.0f), sf);

            //绘制加工点

            float processX = (this.Width - 2 * orginGap) / maxXAxis * processXAxis + orginGap;

            float processY = this.Height - ((this.Height - 2 * orginGap) / maxYAxis * processYAxis + orginGap);

            g.FillEllipse(new SolidBrush(processColor), new RectangleF(processX - 0.5f * pointdiameter, processY - 0.5f * pointdiameter, pointdiameter, pointdiameter));

            g.DrawString(processStr, this.Font, new SolidBrush(processColor), new RectangleF(processX - 25.0f, processY - 20.0f, 50.0f, 20.0f), sf);

            //绘制出料点

            float outletX = (this.Width - 2 * orginGap) / maxXAxis * outletXAxis + orginGap;

            float outletY = this.Height - ((this.Height - 2 * orginGap) / maxYAxis * outletYAxis + orginGap);

            g.FillEllipse(new SolidBrush(outletColor), new RectangleF(outletX - 0.5f * pointdiameter, outletY - 0.5f * pointdiameter, pointdiameter, pointdiameter));

            g.DrawString(outletStr, this.Font, new SolidBrush(outletColor), new RectangleF(outletX - 25.0f, outletY - 20.0f, 50.0f, 20.0f), sf);


            //绘制所有点
            if (this.pointList.Count > 1)
            {
                PointF[] points = new PointF[pointList.Count];
                for (int i = 0; i < pointList.Count; i++)
                {
                    points[i].X = pointList[i].X * (this.Width - 2 * orginGap) / maxXAxis + orginGap;

                    points[i].Y = this.Height - (pointList[i].Y * (this.Height - 2 * orginGap) / maxYAxis + orginGap);
                }

                using (Pen p = new Pen(lineColor, lineThickness))
                {
                    g.DrawLines(p, points);
                }
            }
        }
    }

}
posted @ 2023-03-15 19:57  聆听微风  阅读(107)  评论(0编辑  收藏  举报