终端一体化运控平台
25개 이상의 토픽을 선택하실 수 없습니다. Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

313 lines
14 KiB

  1. using BPA.Communication.Interfaces;
  2. using System;
  3. using System.Collections.Generic;
  4. using System.Linq;
  5. using System.Reflection;
  6. using System.Text;
  7. using System.Threading.Tasks;
  8. using System.Collections.Concurrent;
  9. using System.Diagnostics;
  10. using BPA.Helper;
  11. using System.Collections.Specialized;
  12. using System.Configuration;
  13. using BPASmartClient.CustomResource.UserControls.MessageShow;
  14. namespace BPASmartClient.Academy._50L
  15. {
  16. public class PlcControl : AddData
  17. {
  18. private volatile static PlcControl _Instance;
  19. public static PlcControl GetInstance => _Instance ?? (_Instance = new PlcControl());
  20. private PlcControl() { }
  21. public bool IsConnect => comm != null && comm.IsConnected();
  22. public DeviceStatus DeviceStatus { get; set; } = new DeviceStatus();
  23. public ConcurrentDictionary<string, string> AlarmInfo { get; private set; } = new ConcurrentDictionary<string, string>();
  24. private ICommSiemens comm = CommHelper.Siemens;
  25. public string id { get; set; } = "";
  26. public DateTime ProductStartTime { get; set; }
  27. public void Init()
  28. {
  29. AlarmInfoGet();
  30. Task.Factory.StartNew(() =>
  31. {
  32. CommHelper.CreateSiemens(CpuType.S7200Smart, Json<DevicePar>.Data.IpAddress).OnSuccess(s =>
  33. {
  34. comm = s.Content;
  35. WriteHeartBeat();
  36. Read();
  37. });
  38. });
  39. }
  40. private volatile bool _isReadSuccess;
  41. public void AlarmInfoGet()
  42. {
  43. var x = (NameValueCollection)ConfigurationManager.GetSection("Reactor_50L_Alarm/Alarm");
  44. if (x != null)
  45. {
  46. x.AllKeys.ToList().ForEach(o =>
  47. {
  48. if (!AlarmInfo.ContainsKey(o))
  49. {
  50. AlarmInfo.TryAdd(o, x.Get(o));
  51. }
  52. });
  53. }
  54. }
  55. public void AlarmRead()
  56. {
  57. if (this.IsConnect)
  58. {
  59. AlarmInfo.Keys.ToList().ForEach(o =>
  60. {
  61. comm.Read<bool>(o).OnSuccess(p =>
  62. {
  63. if (RTrig.GetInstance($"{o}").Start(p.Content))
  64. {
  65. App.Current.Dispatcher.Invoke(() =>
  66. {
  67. NoticeDemoViewModel.OpenMsg(EnumPromptType.Error, App.MainWindow, "报警", this.AlarmInfo[o]);
  68. MessageNotify.GetInstance.ShowAlarmLog(this.AlarmInfo[o]);
  69. });
  70. }
  71. });
  72. });
  73. }
  74. //Thread.Sleep(2000);
  75. }
  76. private void Read()
  77. {
  78. TaskManage.GetInstance.StartLong(() =>
  79. {
  80. comm.Read<bool[]>("DB1.DBX1000.0", 32).OnSuccess(s =>
  81. {
  82. #region V1000
  83. DeviceStatus.IsSetReactTurnMotor = s.Content[0];
  84. DeviceStatus.IsSetFans = s.Content[1];
  85. DeviceStatus.IsSetBrinePumpState = s.Content[2];
  86. DeviceStatus.IsSetReactHomeBit = s.Content[3];
  87. DeviceStatus.IsSetReactOut = s.Content[4];
  88. DeviceStatus.IsSetReactTurnMotorJogging = s.Content[5];
  89. DeviceStatus.IsSetReactHeat = s.Content[6];
  90. DeviceStatus.IsSetReactCool = s.Content[7];
  91. #endregion
  92. #region V1001
  93. DeviceStatus.IsSetCWTCool = s.Content[8];
  94. DeviceStatus.IsSetReactPressureReliefValve = s.Content[9];
  95. DeviceStatus.IsSetReactOutHotGasValve = s.Content[10];
  96. DeviceStatus.IsSetHotGasEmptyValve = s.Content[11];
  97. DeviceStatus.IsSetColdWaterTankInAirValve = s.Content[12];
  98. DeviceStatus.IsSetReactDrainValve = s.Content[13];
  99. DeviceStatus.IsSetReactInCleanWaterValve = s.Content[14];
  100. DeviceStatus.IsSetReactPressureAirInValve = s.Content[15];
  101. #endregion
  102. #region V1002
  103. DeviceStatus.IsSetReactInBrineWaterValve = s.Content[16];
  104. DeviceStatus.IsSetColdWaterTankVacuumValve = s.Content[17];
  105. DeviceStatus.IsSetCompressorRunning = s.Content[18];
  106. DeviceStatus.IsSetReactEnter = s.Content[19];
  107. DeviceStatus.IsSetReactReverse = s.Content[20];
  108. DeviceStatus.IsSetStartEnterBrine = s.Content[21];
  109. DeviceStatus.IsSetStartEmptyWater = s.Content[22];
  110. DeviceStatus.IsSetReactOutColdValve = s.Content[23];
  111. #endregion
  112. #region V1003
  113. DeviceStatus.IsSetColdWaterTankInWaterValve = s.Content[24];
  114. DeviceStatus.IsSetStartClean = s.Content[25];
  115. DeviceStatus.IsSetVacuumDistill = s.Content[26];
  116. DeviceStatus.IsSetGoAddPosition = s.Content[27];
  117. DeviceStatus.IsSetColdWaterTankZero = s.Content[28];
  118. DeviceStatus.IsSetBrineTankZero = s.Content[29];
  119. DeviceStatus.IsSetSystemStart = s.Content[30];
  120. DeviceStatus.IsSetHeartBeat = s.Content[31];
  121. #endregion
  122. });
  123. comm.Read<bool[]>("DB1.DBX2000.0", 31).OnSuccess(s =>
  124. {
  125. //Data[FeedbackData.旋转电机启停反馈] = s.Content[0];
  126. //Data[FeedbackData.负压风机启动反馈] = s.Content[1];
  127. //Data[FeedbackData.压缩空气进气阀反馈] = s.Content[2];
  128. //Data[FeedbackData.排热空气阀反馈] = s.Content[3];
  129. //Data[FeedbackData.泄压阀反馈] = s.Content[4];
  130. //Data[FeedbackData.进冷却水阀反馈] = s.Content[5];
  131. //Data[FeedbackData.出冷却水阀反馈] = s.Content[6];
  132. //Data[FeedbackData.蒸汽梳水阀反馈] = s.Content[7];
  133. //Data[FeedbackData.冷凝水罐进水阀反馈] = s.Content[8];
  134. //Data[FeedbackData.称重水罐负压阀反馈] = s.Content[9];
  135. //Data[FeedbackData.反应釜原点位置反馈] = s.Content[10];
  136. #region V2000
  137. DeviceStatus.ReactTurnMotor = s.Content[0];
  138. DeviceStatus.Fans = s.Content[1];
  139. DeviceStatus.BrinePumpState = s.Content[2];
  140. DeviceStatus.ReactInSteamValue = s.Content[3];
  141. DeviceStatus.ReactInColdValve = s.Content[4];
  142. DeviceStatus.ReactOutColdValve = s.Content[5];
  143. DeviceStatus.ReactDrainValve = s.Content[6];
  144. DeviceStatus.ReactInCleanWaterValve = s.Content[7];
  145. #endregion
  146. #region V2001
  147. DeviceStatus.ReactPressureAirInValve = s.Content[8];
  148. DeviceStatus.ReactInBrineWaterValve = s.Content[9];
  149. DeviceStatus.ReactOutHotGasValve = s.Content[10];
  150. DeviceStatus.HotGasEmptyValve = s.Content[11];
  151. DeviceStatus.ColdWaterTankInAirValve = s.Content[12];
  152. DeviceStatus.ColdWaterTankInWaterValve = s.Content[13];
  153. DeviceStatus.ReactHomeBit = s.Content[14];
  154. DeviceStatus.ReactPressureReliefValve = s.Content[15];
  155. #endregion
  156. #region V2002
  157. DeviceStatus.ColdWaterTankVacuumValve = s.Content[16];
  158. DeviceStatus.CompressorRunning = s.Content[17];
  159. #endregion
  160. });
  161. comm.Read<float[]>("DB1.DBD2006", 11).OnSuccess(s =>
  162. {
  163. //Data[FeedbackData.反应釜温度] = s.Content[0];
  164. //Data[FeedbackData.反应釜蒸汽压力] = s.Content[1];
  165. //Data[FeedbackData.反应釜蒸汽流量] = s.Content[2];
  166. //Data[FeedbackData.冷凝水罐温度] = s.Content[3];
  167. //Data[FeedbackData.冷凝水罐湿度] = s.Content[4];
  168. //Data[FeedbackData.负压流量] = s.Content[5];
  169. //Data[FeedbackData.称重水罐重量] = s.Content[6];
  170. //Data[FeedbackData.反应釜编码器值] = s.Content[7];
  171. //Data[FeedbackData.蒸汽比例阀实际开度] = s.Content[8];
  172. DeviceStatus.ReactTemp = s.Content[0];
  173. DeviceStatus.ReactSteamPressure = s.Content[1];
  174. DeviceStatus.ReactSteamFlow = s.Content[2];
  175. DeviceStatus.ColdWaterTankTemp = s.Content[3];
  176. DeviceStatus.ColdWaterTankHumidity = s.Content[4];
  177. DeviceStatus.VacuumFlow = s.Content[5];
  178. DeviceStatus.WaterTankWeight = s.Content[6];
  179. DeviceStatus.ReactEncoderValue = s.Content[7];
  180. DeviceStatus.SteamProportValveRealOpening = s.Content[8];
  181. DeviceStatus.BrineTankWeight = s.Content[9];
  182. DeviceStatus.ReactPressure = s.Content[10];
  183. if (Delay.GetInstance("趋势数据").Start(_isReadSuccess, 2))
  184. {
  185. _isReadSuccess = false;
  186. }
  187. else if (!_isReadSuccess)
  188. {
  189. if (!string.IsNullOrWhiteSpace(id))
  190. {
  191. SamplingData sampling = new SamplingData()
  192. {
  193. Temperature = s.Content[0],
  194. SteamPressure = s.Content[1],
  195. SteamFlowRate = s.Content[2],
  196. CondensateWaterTemperature = s.Content[3],
  197. CondensateWaterHumidity = s.Content[4],
  198. NegativePressureFlowRate = s.Content[5],
  199. WeighingWaterTankWeight = s.Content[6],
  200. ReactEncoderValue = s.Content[7],
  201. ProportionalValveOpening = s.Content[8],
  202. BrineTankWeight = s.Content[9],
  203. ReactPressure = s.Content[10]
  204. };
  205. sampling.ProductNumberId = id;
  206. SqliteOperate.GetInstance.RealtimeChart(sampling, ProductStartTime);
  207. SqliteOperate.GetInstance.Add(sampling);
  208. }
  209. _isReadSuccess = true;
  210. }
  211. });
  212. comm.Read<bool>("DB1.DBX1003.7", 1).OnSuccess(s => DeviceStatus.HeartBeat = s.Content );
  213. //comm.Read<bool[]>("DB1.DBX2004.0", 16).OnSuccess(s =>
  214. //{
  215. // AlarmHelper.GetInstance.Get<AlarmData>("50L反应釜").EStop = s.Content[0];
  216. // AlarmHelper.GetInstance.Get<AlarmData>("50L反应釜").RotatingMachinesError = s.Content[1];
  217. // AlarmHelper.GetInstance.Get<AlarmData>("50L反应釜").AbnormalNegativePressureFan = s.Content[2];
  218. // AlarmHelper.GetInstance.Get<AlarmData>("50L反应釜").BrinePumpError = s.Content[3];
  219. // AlarmHelper.GetInstance.Get<AlarmData>("50L反应釜").CompressorError = s.Content[4];
  220. // AlarmHelper.GetInstance.Get<AlarmData>("50L反应釜").ReactorPressureLimit = s.Content[5];
  221. //});
  222. AlarmRead();
  223. Thread.Sleep(100);
  224. }, "数据获取", true);
  225. }
  226. private void WriteHeartBeat()
  227. {
  228. Task.Factory.StartNew( async() =>
  229. {
  230. while (true)
  231. {
  232. if (this.IsConnect)
  233. {
  234. //var tokenSource = new CancellationTokenSource();
  235. //tokenSource.CancelAfter(2000);
  236. //await WriteAsync(BoolAddEnum.心跳, true,tokenSource.Token);
  237. Write(BoolAddEnum.心跳, true);
  238. }
  239. //IsConnectChanged?.Invoke(this.IsConnect);
  240. await Task.Delay(2500);
  241. }
  242. },TaskCreationOptions.LongRunning);
  243. }
  244. public OperateResult Write(BoolAddEnum add, bool value)
  245. {
  246. if (boolAdds.ContainsKey(add))
  247. {
  248. return comm.Write(boolAdds[add], value);
  249. }
  250. else
  251. {
  252. return OperateResult.Failed($"未查找到该地址{add.ToString()}");
  253. }
  254. }
  255. public OperateResult Write(FloatAddEnum add, float value)
  256. {
  257. if (floatAdds.ContainsKey(add))
  258. {
  259. return comm.Write(floatAdds[add], value);
  260. }
  261. else
  262. {
  263. return OperateResult.Failed($"未查找到该地址{add.ToString()}");
  264. }
  265. }
  266. public async Task<OperateResult> WriteAsync(BoolAddEnum add, bool value,CancellationToken cancellationToken=default)
  267. {
  268. if (boolAdds.ContainsKey(add))
  269. {
  270. try
  271. {
  272. var result = await Task.Run(() =>
  273. {
  274. return comm.Write(boolAdds[add], value);
  275. }, cancellationToken);
  276. return result;
  277. }
  278. catch (OperationCanceledException)
  279. {
  280. return OperateResult.Failed($"操作被取消");
  281. }
  282. }
  283. else
  284. {
  285. return OperateResult.Failed($"未查找到该地址{add.ToString()}");
  286. }
  287. }
  288. }
  289. }