StepControl.cs 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357
  1. using System;
  2. using System.ComponentModel;
  3. using System.Drawing;
  4. using System.Windows.Forms;
  5. using System.Collections.Generic;
  6. using System.Data;
  7. using System.Linq;
  8. using System.Text;
  9. using System.Drawing.Drawing2D;
  10. namespace monitor_main_windows
  11. {
  12. public partial class StepControl : UserControl
  13. {
  14. [Description("步骤更改事件"), Category("自定义")]
  15. public event EventHandler IndexChecked;
  16. private Color m_stepCompleteColor = Color.Green;
  17. private Color m_stepRunningColor = Color.Yellow;
  18. private Color m_stepWaitColor = Color.FromArgb(100, 100, 100);
  19. private Color m_stepErrorColor = Color.Red;
  20. private Timer m_timer = new Timer();
  21. /// <summary>
  22. /// 步骤背景色
  23. /// </summary>
  24. [Description("步骤等待色"), Category("自定义")]
  25. public Color StepWaitColor
  26. {
  27. get { return m_stepWaitColor; }
  28. set { m_stepWaitColor = value; }
  29. }
  30. [Description("步骤运行色"), Category("自定义")]
  31. public Color StepRunningColor
  32. {
  33. get { return m_stepRunningColor; }
  34. set { m_stepRunningColor = value; }
  35. }
  36. [Description("步骤完成色"), Category("自定义")]
  37. public Color StepCompleteColor
  38. {
  39. get { return m_stepCompleteColor; }
  40. set { m_stepCompleteColor = value; }
  41. }
  42. [Description("步骤故障色"), Category("自定义")]
  43. public Color StepErrorColor
  44. {
  45. get { return m_stepErrorColor; }
  46. set { m_stepErrorColor = value; }
  47. }
  48. private Color m_stepFontColor = Color.White;
  49. /// <summary>
  50. /// 步骤文字颜色
  51. /// </summary>
  52. [Description("步骤文字景色"), Category("自定义")]
  53. public Color StepFontColor
  54. {
  55. get { return m_stepFontColor; }
  56. set { m_stepFontColor = value; }
  57. }
  58. private string[] m_steps = new string[] { /*"停车开始", "预定车位","搬运","确认车位","完成"*/ };
  59. private string[] m_back_steps = new string[] { };
  60. [Description("步骤"), Category("自定义")]
  61. public string[] Steps
  62. {
  63. get { return m_steps; }
  64. set
  65. {
  66. if (m_steps == null )
  67. return;
  68. m_steps = value;
  69. Refresh();
  70. }
  71. }
  72. [Description("回退步骤"), Category("自定义")]
  73. public string[] BackSteps
  74. {
  75. get { return m_back_steps; }
  76. set
  77. {
  78. if (m_back_steps == null)
  79. return;
  80. m_back_steps = value;
  81. Refresh();
  82. }
  83. }
  84. private int m_stepIndex = 1;
  85. private string m_label = "车牌:鄂A00000";
  86. [Description("标题文字"), Category("自定义")]
  87. public string Label
  88. {
  89. get { return m_label; }
  90. set { m_label = value; }
  91. }
  92. [Description("步骤位置"), Category("自定义")]
  93. public int StepIndex
  94. {
  95. get { return m_stepIndex; }
  96. set
  97. {
  98. if (m_stepIndex > m_steps.Length+ m_back_steps.Length)
  99. return;
  100. m_stepIndex = value;
  101. Refresh();
  102. if (IndexChecked != null)
  103. {
  104. IndexChecked(this, null);
  105. }
  106. }
  107. }
  108. public StepControl()
  109. {
  110. InitializeComponent();
  111. this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
  112. this.SetStyle(ControlStyles.DoubleBuffer, true);
  113. this.SetStyle(ControlStyles.ResizeRedraw, true);
  114. this.SetStyle(ControlStyles.Selectable, true);
  115. this.SetStyle(ControlStyles.SupportsTransparentBackColor, true);
  116. this.SetStyle(ControlStyles.UserPaint, true);
  117. this.BorderStyle = BorderStyle.FixedSingle;
  118. m_timer.Enabled = true;
  119. m_timer.Tick += Timer_Tick;
  120. m_timer.Interval = 500;
  121. }
  122. private void Timer_Tick(object sender, EventArgs e)
  123. {
  124. m_stepRunningColor = m_stepRunningColor==Color.Green?Color.Yellow:Color.Green;
  125. Refresh();
  126. }
  127. protected override void OnPaint(PaintEventArgs e)
  128. {
  129. base.OnPaint(e);
  130. var g = e.Graphics;
  131. if (BackSteps.Length == 0)
  132. g.Clear(Color.PaleGreen);
  133. else
  134. g.Clear(Color.LightPink);
  135. g.SmoothingMode = SmoothingMode.HighQuality; //图片柔顺模式
  136. g.InterpolationMode = InterpolationMode.HighQualityBicubic;//高质量
  137. g.CompositingQuality = CompositingQuality.HighQuality;//
  138. g.TextRenderingHint = System.Drawing.Text.TextRenderingHint.ClearTypeGridFit;
  139. //g.SmoothingMode = SmoothingMode.AntiAlias; //使绘图质量最高,即消除锯齿
  140. int vertical_line = BackSteps.Length>0?20:0;
  141. int step_w = 25;
  142. System.Drawing.SizeF sizeFirst = g.MeasureString(m_steps[0], this.Font);
  143. if (BackSteps.Length > 0)
  144. {
  145. System.Drawing.SizeF sizeBacKEnd = g.MeasureString(BackSteps[BackSteps.Length-1], this.Font);
  146. if (sizeBacKEnd.Width > sizeFirst.Width)
  147. sizeFirst = sizeBacKEnd;
  148. }
  149. System.Drawing.SizeF sizeLabel = g.MeasureString(Label, this.Font);
  150. int label_x = (Width - (int)sizeLabel.Width) / 2;
  151. label_x = label_x >= 0 ? label_x : 0;
  152. g.DrawString(Label, Font, new SolidBrush(m_stepCompleteColor), new Point(label_x, 3));
  153. int y = 5 + (int)sizeFirst.Height;
  154. if (y < 0)
  155. y = 0;
  156. int intTxtY = y + step_w + 3;
  157. int intLeft = 3;
  158. if (sizeFirst.Width > step_w)
  159. {
  160. intLeft = (int)(sizeFirst.Width - step_w) / 2 + 1;
  161. }
  162. int intRight = 3;
  163. System.Drawing.SizeF sizeEnd = g.MeasureString(m_steps[m_steps.Length - 1], this.Font);
  164. if(BackSteps.Length>0)
  165. {
  166. System.Drawing.SizeF sizeBacKFirst = g.MeasureString(BackSteps[0], this.Font);
  167. if (sizeBacKFirst.Width > sizeEnd.Width)
  168. sizeEnd = sizeBacKFirst;
  169. }
  170. if (sizeEnd.Width > step_w)
  171. {
  172. intRight = (int)(sizeEnd.Width - step_w) / 2 + 1;
  173. }
  174. int intSplitWidth = 0;
  175. intSplitWidth = (this.Width-intLeft - (m_steps.Length * step_w) - intRight) / (m_steps.Length - 1);
  176. if (intSplitWidth < 10)
  177. intSplitWidth = 10;
  178. for (int i = 0; i < m_steps.Length; i++)
  179. {
  180. #region 画圆,横线
  181. g.FillEllipse(new SolidBrush(m_stepWaitColor), new Rectangle(new Point(intLeft + i * (step_w + intSplitWidth), y), new Size(step_w, step_w)));
  182. if (m_stepIndex > i)
  183. {
  184. //存在回退步骤时, 最后一个表示错误
  185. if (m_back_steps.Length > 0 && i == m_steps.Length - 1)
  186. {
  187. g.FillEllipse(new SolidBrush(m_stepErrorColor),
  188. new Rectangle(new Point(intLeft + i * (step_w + intSplitWidth) + 2, y + 2),
  189. new Size(step_w - 4, step_w - 4)));
  190. }
  191. else
  192. {
  193. g.FillEllipse(new SolidBrush(m_stepCompleteColor),
  194. new Rectangle(new Point(intLeft + i * (step_w + intSplitWidth) + 2, y + 2),
  195. new Size(step_w - 4, step_w - 4)));
  196. }
  197. if (i != m_steps.Length - 1)
  198. {
  199. if (m_stepIndex == i + 1)
  200. {
  201. //当前步骤运行中闪烁,完成绿色
  202. g.FillEllipse(new SolidBrush(m_stepRunningColor),
  203. new Rectangle(new Point(intLeft + i * (step_w + intSplitWidth) + 2, y + 2),
  204. new Size(step_w - 4, step_w - 4)));
  205. g.DrawLine(new Pen(m_stepWaitColor, 2), new Point(intLeft + i * (step_w + intSplitWidth) + step_w, y + (step_w / 2)),
  206. new Point(intLeft + (i+1) * (step_w + intSplitWidth) , y + (step_w / 2)));
  207. }
  208. else
  209. {
  210. g.DrawLine(new Pen(m_stepCompleteColor, 2), new Point(intLeft + i * (step_w + intSplitWidth) + step_w, y + (step_w / 2)),
  211. new Point(intLeft + (i+1) * (step_w + intSplitWidth) , y + (step_w / 2)));
  212. }
  213. }
  214. }
  215. else
  216. {
  217. if (i != m_steps.Length - 1)
  218. {
  219. g.DrawLine(new Pen(m_stepWaitColor, 2), new Point(intLeft + i * (step_w + intSplitWidth) + step_w, y + (step_w / 2)),
  220. new Point(intLeft + (i+1) * (step_w + intSplitWidth) , y + (step_w / 2)));
  221. }
  222. }
  223. System.Drawing.SizeF _numSize = g.MeasureString((i + 1).ToString(), this.Font);
  224. g.DrawString((i + 1).ToString(), Font, new SolidBrush(m_stepFontColor),
  225. new Point(intLeft + i * (step_w + intSplitWidth) + (step_w - (int)_numSize.Width) / 2 , y + (step_w - (int)_numSize.Height) / 2 + 1));
  226. #endregion
  227. System.Drawing.SizeF sizeTxt = g.MeasureString(m_steps[i], this.Font);
  228. g.DrawString(m_steps[i], Font, new SolidBrush(m_stepIndex > i ? m_stepCompleteColor : m_stepWaitColor),
  229. new Point(intLeft + i * (step_w + intSplitWidth) + (step_w - (int)sizeTxt.Width) / 2 , intTxtY));
  230. }
  231. //绘制回退
  232. if (m_back_steps.Length > 0)
  233. {
  234. int winHeight = step_w * 2 + vertical_line + 20 + 3 * (int)sizeFirst.Height;
  235. if (Height < winHeight)
  236. Height = winHeight;
  237. int by = intTxtY + (int)sizeFirst.Height + vertical_line;
  238. int brx = intLeft + (m_steps.Length - 1) * (step_w + intSplitWidth);
  239. int back_step_index = m_stepIndex - m_steps.Length;
  240. back_step_index = back_step_index >= 0 ? back_step_index : 0;
  241. if (back_step_index > 0)
  242. {
  243. g.DrawLine(new Pen(m_stepCompleteColor, 2), new Point(brx + step_w / 2, by - vertical_line),
  244. new Point(brx + step_w / 2, by));
  245. }
  246. else
  247. {
  248. g.DrawLine(new Pen(m_stepWaitColor, 2), new Point(brx + step_w / 2, by - vertical_line),
  249. new Point(brx + step_w / 2, by));
  250. }
  251. for (int i = 0; i < m_back_steps.Length; i++)
  252. {
  253. g.FillEllipse(new SolidBrush(m_stepWaitColor),
  254. new Rectangle(new Point(brx - i * (step_w + intSplitWidth), by),
  255. new Size(step_w, step_w)));
  256. if (back_step_index > i)
  257. {
  258. if (back_step_index == i + 1)
  259. {
  260. //当前步骤运行中闪烁,完成绿色
  261. g.FillEllipse(new SolidBrush(m_stepRunningColor),
  262. new Rectangle(new Point(brx - i * (step_w + intSplitWidth) + 2, by + 2),
  263. new Size(step_w - 4, step_w - 4)));
  264. }
  265. else
  266. {
  267. g.FillEllipse(new SolidBrush(m_stepCompleteColor),
  268. new Rectangle(new Point(brx - i * (step_w + intSplitWidth) + 2, by + 2),
  269. new Size(step_w - 4, step_w - 4)));
  270. }
  271. if (i != m_back_steps.Length - 1)
  272. {
  273. if (back_step_index == i + 1)
  274. {
  275. g.DrawLine(new Pen(m_stepWaitColor, 2),
  276. new Point(brx - i * (step_w + intSplitWidth), by + (step_w / 2)),
  277. new Point(brx - (i + 1) * (step_w + intSplitWidth), by + (step_w / 2)));
  278. }
  279. else
  280. {
  281. g.DrawLine(new Pen(m_stepCompleteColor, 2),
  282. new Point(brx - i * (step_w + intSplitWidth), by + (step_w / 2)),
  283. new Point(brx - (i + 1) * (step_w + intSplitWidth), by + (step_w / 2)));
  284. }
  285. }
  286. }
  287. else
  288. {
  289. if (i != m_back_steps.Length - 1)
  290. {
  291. g.DrawLine(new Pen(m_stepWaitColor, 2), new Point(brx - i * (step_w + intSplitWidth), by + (step_w / 2)),
  292. new Point(brx - (i + 1) * (step_w + intSplitWidth), by + (step_w / 2)));
  293. }
  294. }
  295. System.Drawing.SizeF _numSize = g.MeasureString((i + 1).ToString(), this.Font);
  296. g.DrawString((m_steps.Length + i + 1).ToString(), Font, new SolidBrush(m_stepFontColor),
  297. new Point(brx - i * (step_w + intSplitWidth) + step_w / 2 - (int)_numSize.Width / 2, by + (step_w - (int)_numSize.Height) / 2 + 1));
  298. System.Drawing.SizeF sizeTxt = g.MeasureString(m_back_steps[i], this.Font);
  299. g.DrawString(m_back_steps[i], Font, new SolidBrush(back_step_index > i ? m_stepCompleteColor : m_stepWaitColor),
  300. new Point(brx - i * (step_w + intSplitWidth) + (step_w - (int)sizeTxt.Width) / 2 + 1, by + step_w + (int)sizeTxt.Height / 2 + 1));
  301. }
  302. }
  303. }
  304. }
  305. }