using System; using System.Collections.Generic; using System.ComponentModel; using System.Drawing.Drawing2D; using System.Drawing.Text; using System.Drawing; using System.Linq; using System.Net; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; namespace Mesnac.Controls.ChemicalWeighing { /// 一个传送带的控件 [Description("传送带控件,支持正反方向设置,支持转速设置,颜色设置")] public class HslConveyer : UserControl { private StringFormat sf = (StringFormat)null; private float moveSpeed = 0.3f; private float startAngle = 0.0f; private float startOffect = 0.0f; private Timer timer = (Timer)null; private bool isConveyerActive = false; private float circularRadius = 20f; private HslConveyerStyle conveyerStyle = HslConveyerStyle.Horizontal; /// 必需的设计器变量。 private IContainer components = (IContainer)null; /// 实例化一个传送带的控件对象 public HslConveyer() { this.InitializeComponent(); this.sf = new StringFormat(); this.sf.Alignment = StringAlignment.Center; this.sf.LineAlignment = StringAlignment.Center; this.SetStyle(ControlStyles.UserPaint | ControlStyles.SupportsTransparentBackColor, true); this.SetStyle(ControlStyles.ResizeRedraw, true); this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true); this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); base.ForeColor = Color.FromArgb(142, 196, 216); this.timer = new Timer(); this.timer.Interval = 50; this.timer.Tick += new EventHandler(this.Timer_Tick); this.timer.Start(); } /// 获取或设置控件的背景色 [Browsable(true)] [Description("获取或设置控件的背景色")] [Category("HslControls")] [DefaultValue(typeof(Color), "Transparent")] [EditorBrowsable(EditorBrowsableState.Always)] public override Color BackColor { get => base.BackColor; set => base.BackColor = value; } /// 获取或设置当前控件的文本 [Browsable(true)] [Description("获取或设置当前控件的文本")] [Category("HslControls")] [EditorBrowsable(EditorBrowsableState.Always)] [Bindable(true)] [DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)] public override string Text { get => base.Text; set { base.Text = value; this.Invalidate(); } } /// 获取或设置控件的背景色 [Browsable(true)] [Description("获取或设置控件的前景色")] [Category("HslControls")] [DefaultValue(typeof(Color), "[142, 196, 216]")] [EditorBrowsable(EditorBrowsableState.Always)] public override Color ForeColor { get => base.ForeColor; set { base.ForeColor = value; this.Invalidate(); } } /// 获取或设置传送带流动的速度,0为静止,正数为正向流动,负数为反向流动,一般情况值范围为 -9 ~ 9 [Browsable(true)] [Description("获取或设置传送带流动的速度,0为静止,正数为正向流动,负数为反向流动,一般情况值范围为 -9 ~ 9")] [Category("HslControls")] [DefaultValue(0.3f)] public virtual float MoveSpeed { get => this.moveSpeed; set { this.moveSpeed = value; this.Invalidate(); } } /// 获取或设置管道线是否激活液体显示 [Browsable(true)] [Description("获取或设置管道线是否激活液体显示")] [Category("HslControls")] [DefaultValue(false)] public virtual bool ConveyerActive { get => this.isConveyerActive; set { this.isConveyerActive = value; this.Invalidate(); } } /// 获取或设置两侧的圆圈的半径,当且仅当ConveyerStyle属性不为Horizontal枚举时成立 [Browsable(true)] [Description("获取或设置两侧的圆圈的半径,当且仅当ConveyerStyle属性不为Horizontal枚举时成立")] [Category("HslControls")] [DefaultValue(HslConveyerStyle.Horizontal)] public virtual float CircularRadius { get => this.circularRadius; set { if ((double)value > (double)(this.Width / 2) || (double)value > (double)(this.Height / 2)) return; this.circularRadius = value; this.Invalidate(); } } /// 获取或设置传送带的样式,水平,还是上坡,还是下坡 [Browsable(true)] [Description("获取或设置传送带的样式,水平,还是上坡,还是下坡")] [Category("HslControls")] [DefaultValue(HslConveyerStyle.Horizontal)] public virtual HslConveyerStyle ConveyerStyle { get => this.conveyerStyle; set { this.conveyerStyle = value; this.Invalidate(); } } private void Timer_Tick(object sender, EventArgs e) { if ((double)this.moveSpeed == 0.0) return; if (this.isConveyerActive) { this.startOffect -= this.moveSpeed; if ((double)this.startOffect <= -10.0 || (double)this.startOffect >= 10.0) this.startOffect = 0.0f; } this.startAngle += (float)((double)this.moveSpeed * 180.0 / Math.PI / 10.0); while ((double)this.startAngle < -360.0) this.startAngle += 360f; while ((double)this.startAngle >= 360.0) this.startAngle -= 360f; this.Invalidate(); } /// 重绘控件的界面信息 /// 事件 protected override void OnPaint(PaintEventArgs e) { e.Graphics.SmoothingMode = SmoothingMode.AntiAlias; e.Graphics.TextRenderingHint = TextRenderingHint.ClearTypeGridFit; this.PaintHslControls(e.Graphics, this.Width, this.Height); base.OnPaint(e); } /// public void PaintHslControls(Graphics g, int width, int height) { int margin = 5; int offect = 5; if (this.conveyerStyle == HslConveyerStyle.Horizontal) this.PaintMain(g, (float)width, (float)height, (float)margin, (float)offect); else if (this.conveyerStyle == HslConveyerStyle.Upslope) { PointF pointF1 = new PointF((float)(margin + offect) + this.circularRadius, (float)(height - 1 - margin - offect) - this.circularRadius); PointF pointF2 = new PointF((float)(width - margin - offect - 1) - this.circularRadius, (float)(margin + offect) + this.circularRadius); float num1 = (float)Math.Sqrt(Math.Pow((double)pointF2.Y - (double)pointF1.Y, 2.0) + Math.Pow((double)pointF2.X - (double)pointF1.X, 2.0)); float num2 = (float)(Math.Acos(((double)pointF2.X - (double)pointF1.X) / (double)num1) * 180.0 / Math.PI); g.TranslateTransform(pointF1.X, pointF1.Y); g.RotateTransform(-num2); g.TranslateTransform((float)(-margin - offect) - this.circularRadius, (float)(-margin - offect) - this.circularRadius); this.PaintMain(g, (float)((double)num1 + (double)(2 * margin) + (double)(2 * offect) + 2.0 * (double)this.circularRadius), (float)(2 * margin + 2 * offect) + 2f * this.circularRadius, (float)margin, (float)offect); g.ResetTransform(); } else { PointF pointF3 = new PointF((float)(margin + offect) + this.circularRadius, (float)(margin + offect) + this.circularRadius); PointF pointF4 = new PointF((float)(width - margin - offect - 1) - this.circularRadius, (float)(height - 1 - margin - offect) - this.circularRadius); float num = (float)Math.Sqrt(Math.Pow((double)pointF4.Y - (double)pointF3.Y, 2.0) + Math.Pow((double)pointF4.X - (double)pointF3.X, 2.0)); float angle = (float)(Math.Acos(((double)pointF4.X - (double)pointF3.X) / (double)num) * 180.0 / Math.PI); g.TranslateTransform(pointF3.X, pointF3.Y); g.RotateTransform(angle); g.TranslateTransform((float)(-margin - offect) - this.circularRadius, (float)(-margin - offect) - this.circularRadius); this.PaintMain(g, (float)((double)num + (double)(2 * margin) + (double)(2 * offect) + 2.0 * (double)this.circularRadius), (float)(2 * margin + 2 * offect) + 2f * this.circularRadius, (float)margin, (float)offect); g.ResetTransform(); } } private void PaintMain(Graphics g, float width, float height, float margin, float offect) { float num1 = (float)(((double)height - (double)margin * 2.0 - (double)offect * 2.0) / 2.0); float startAngle = this.startAngle; Pen pen1 = new Pen(this.ForeColor, 1f); Pen pen2 = new Pen(this.ForeColor, (double)num1 > 100.0 ? 7f : ((double)num1 > 20.0 ? 5f : ((double)num1 > 5.0 ? 3f : 1f))); pen2.StartCap = LineCap.Round; pen2.EndCap = LineCap.Round; Brush brush = (Brush)new SolidBrush(this.ForeColor); GraphicsPath path = new GraphicsPath(); path.AddArc(margin, margin, (float)((double)num1 * 2.0 + (double)offect * 2.0), (float)((double)num1 * 2.0 + (double)offect * 2.0), 90f, 180f); path.AddLine(margin + offect + num1, margin, (float)((double)width - (double)margin - (double)offect - (double)num1 - 1.0), margin); path.AddArc((float)((double)width - (double)margin - (double)num1 * 2.0 - (double)offect * 2.0), margin, (float)((double)num1 * 2.0 + (double)offect * 2.0), (float)((double)num1 * 2.0 + (double)offect * 2.0), -90f, 180f); path.CloseFigure(); g.DrawPath(pen1, path); g.DrawEllipse(pen1, margin + offect, margin + offect, num1 * 2f, num1 * 2f); g.DrawEllipse(pen1, (float)((double)width - (double)margin - (double)num1 * 2.0) - offect, margin + offect, num1 * 2f, num1 * 2f); float num2 = (float)Math.Sqrt(2.0 * (double)offect * (double)num1 + (double)offect * (double)offect); float num3 = (float)(Math.Asin((double)num1 / ((double)num1 + (double)offect)) * 180.0 / Math.PI); path.Reset(); path.AddArc(margin, margin, (float)((double)num1 * 2.0 + (double)offect * 2.0), (float)((double)num1 * 2.0 + (double)offect * 2.0), -num3, num3 * 2f); path.AddLine(margin + offect + num1 + num2, height - margin - offect, (float)((double)width - (double)margin - (double)offect - (double)num1 - 1.0) - num2, height - margin - offect); path.AddArc((float)((double)width - (double)margin - (double)num1 * 2.0 - (double)offect * 2.0), margin, (float)((double)num1 * 2.0 + (double)offect * 2.0), (float)((double)num1 * 2.0 + (double)offect * 2.0), 180f - num3, num3 * 2f); path.CloseFigure(); g.DrawPath(pen1, path); g.TranslateTransform(margin + offect + num1, margin + offect + num1); g.RotateTransform(startAngle); g.DrawLine(pen2, (float)(-(double)num1 / 2.0), 0.0f, num1 / 2f, 0.0f); g.DrawLine(pen2, 0.0f, (float)(-(double)num1 / 2.0), 0.0f, num1 / 2f); g.RotateTransform(-startAngle); g.TranslateTransform(-margin - offect - num1, -margin - offect - num1); g.TranslateTransform(width - margin - num1 - offect, margin + offect + num1); g.RotateTransform(startAngle); g.DrawLine(pen2, (float)(-(double)num1 / 2.0), 0.0f, num1 / 2f, 0.0f); g.DrawLine(pen2, 0.0f, (float)(-(double)num1 / 2.0), 0.0f, num1 / 2f); g.RotateTransform(-startAngle); g.TranslateTransform(-width + margin + num1 + offect, -margin - offect - num1); if (this.isConveyerActive) { using (Pen pen3 = new Pen(this.ForeColor, 5f)) { pen3.DashStyle = DashStyle.Custom; pen3.DashPattern = new float[2] { 5f, 5f }; pen3.DashOffset = this.startOffect; path.Reset(); path.AddArc(margin + offect / 2f, margin + offect / 2f, num1 * 2f + offect, num1 * 2f + offect, 90f, 180f); path.AddLine((float)((double)margin + (double)offect + (double)num1 + 1.0), margin + offect / 2f, (float)((double)width - (double)margin - (double)offect - (double)num1 - 2.0), margin + offect / 2f); path.AddArc((float)((double)width - (double)margin - (double)num1 * 2.0 - (double)offect * 2.0 + (double)offect / 2.0), margin + offect / 2f, num1 * 2f + offect, num1 * 2f + offect, -90f, 180f); path.CloseFigure(); g.DrawPath(pen3, path); } } g.DrawString(this.Text, this.Font, brush, new RectangleF(0.0f, 0.0f, width, height), this.sf); path.Dispose(); pen1.Dispose(); pen2.Dispose(); brush.Dispose(); } /// 清理所有正在使用的资源。 /// 如果应释放托管资源,为 true;否则为 false。 protected override void Dispose(bool disposing) { if (disposing && this.components != null) this.components.Dispose(); base.Dispose(disposing); } /// /// 设计器支持所需的方法 - 不要修改 /// 使用代码编辑器修改此方法的内容。 /// private void InitializeComponent() { this.SuspendLayout(); this.AutoScaleMode = AutoScaleMode.None; this.BackColor = Color.Transparent; this.Name = nameof(HslConveyer); this.Size = new Size(461, 61); this.ResumeLayout(false); } } }