IoHeater.cs 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532
  1. using System;
  2. using System.Xml;
  3. using Aitex.Core.Common.DeviceData;
  4. using Aitex.Core.RT.DataCenter;
  5. using Aitex.Core.RT.Device;
  6. using Aitex.Core.RT.Event;
  7. using Aitex.Core.RT.IOCore;
  8. using Aitex.Core.RT.OperationCenter;
  9. using Aitex.Core.RT.SCCore;
  10. using Aitex.Core.RT.Tolerance;
  11. using Aitex.Core.Util;
  12. namespace Aitex.Core.RT.Device.Unit
  13. {
  14. public class IoHeater : BaseDevice, IDevice
  15. {
  16. public double SetPointLimit
  17. {
  18. get
  19. {
  20. if (_aoSetPointLimit != null)
  21. //return _aoSetPointLimit.Value;
  22. return _GetRealFloat(_aoSetPointLimit);
  23. return 100;
  24. }
  25. }
  26. [Subscription(AITHeaterPropertyName.CoolantInletTempFeedback)]
  27. public float CoolantInletTcFeedback
  28. {
  29. get
  30. {
  31. if (_aiCoolantInletTempFeedback == null) return -1;
  32. //return _aiMonitorTcFeedback.Value;
  33. return _GetRealFloat(_aiCoolantInletTempFeedback);
  34. }
  35. }
  36. [Subscription(AITHeaterPropertyName.CoolantOutletTempFeedback)]
  37. public float CoolantOutletTcFeedback
  38. {
  39. get
  40. {
  41. if (_aiCoolantOutletTempFeedback == null) return -1;
  42. //return _aiMonitorTcFeedback.Value;
  43. return _GetRealFloat(_aiCoolantOutletTempFeedback);
  44. }
  45. }
  46. [Subscription(AITHeaterPropertyName.MonitorTcFeedback)]
  47. public float MonitorTcFeedback
  48. {
  49. get
  50. {
  51. if (_aiMonitorTcFeedback == null) return -1;
  52. //return _aiMonitorTcFeedback.Value;
  53. return _GetRealFloat(_aiMonitorTcFeedback);
  54. }
  55. }
  56. [Subscription(AITHeaterPropertyName.ControlTcFeedback)]
  57. public float ControlTcFeedback
  58. {
  59. get
  60. {
  61. //if (Name == "ForelineHeater")
  62. //{
  63. // if (_aiControlTcFeedback == null) return -1;
  64. // return _GetRealFloat(_aiControlTcFeedback);
  65. //}
  66. if (_aiControlTcFeedback == null) return -1;
  67. float real = _GetRealFloat(_aiControlTcFeedback);
  68. if (Name == "LEHeater1")
  69. {
  70. return real - GetHeater1OffsetSetting(real - _offset);
  71. }
  72. else if (Name == "LEHeater2")
  73. {
  74. return real - GetHeater2OffsetSetting(real - _offset);
  75. }
  76. return _GetRealFloat(_aiControlTcFeedback);
  77. //return ((real - GetHeaterOffsetSetting(real - _offset)) >= ControlTcSetPoint - _offset) ? (real - _offset) : (real - GetHeaterOffsetSetting(real - _offset));
  78. }
  79. }
  80. [Subscription(AITHeaterPropertyName.ControlTcFeedbackNoOffSet)]
  81. public float ControlTcFeedbackNoOffSet
  82. {
  83. get
  84. {
  85. if (_aiControlTcFeedback == null) return -1;
  86. return _GetRealFloat(_aiControlTcFeedback);
  87. }
  88. }
  89. [Subscription(AITHeaterPropertyName.ControlTcSetPoint)]
  90. public float ControlTcSetPoint
  91. {
  92. get
  93. {
  94. if (_aoSetPoint != null)
  95. {
  96. float real = _GetRealFloat(_aoSetPoint);
  97. if (Name == "LEHeater1")
  98. {
  99. return real - GetHeater1OffsetSetting(real - _offset);
  100. }
  101. else if (Name == "LEHeater2")
  102. {
  103. return real - GetHeater2OffsetSetting(real - _offset);
  104. }
  105. return _GetRealFloat(_aoSetPoint);
  106. }
  107. return 0;
  108. }
  109. private set
  110. {
  111. if (_aoSetPoint != null)
  112. {
  113. //_aoSetPoint.Value = (short)setpoint;
  114. _SetRealFloat(_aoSetPoint, value);
  115. }
  116. }
  117. }
  118. [Subscription(AITHeaterPropertyName.IsMonitorTcBroken)]
  119. public bool IsMonitorTcBroken
  120. {
  121. get
  122. {
  123. if (_diMonitorTcBroken != null)
  124. return _diMonitorTcBroken.Value;
  125. return false;
  126. }
  127. }
  128. [Subscription(AITHeaterPropertyName.IsTcDeviation)]
  129. public bool IsTcDeviation
  130. {
  131. get
  132. {
  133. if (_diDeviation != null)
  134. return _diDeviation.Value;
  135. return false;
  136. }
  137. }
  138. [Subscription(AITHeaterPropertyName.IsControlTcBroken)]
  139. public bool IsControlTcBroken
  140. {
  141. get
  142. {
  143. if (_diControlTcBroken != null)
  144. return _diControlTcBroken.Value;
  145. return false;
  146. }
  147. }
  148. [Subscription(AITHeaterPropertyName.IsPowerOnFeedback)]
  149. public bool IsPowerOnFeedback
  150. {
  151. get
  152. {
  153. if (_diPowerOnFeedback != null)
  154. return _diPowerOnFeedback.Value;
  155. if (_doPowerOn != null)
  156. return _doPowerOn.Value;
  157. return false;
  158. }
  159. }
  160. [Subscription(AITHeaterPropertyName.ControlTcSetPointView)]
  161. public float ControlTcSetPointView
  162. {
  163. get
  164. {
  165. return _controlTcSetPointView;
  166. }
  167. }
  168. [Subscription(AITHeaterPropertyName.IsPowerOnSetPoint)]
  169. public bool IsPowerOnSetPoint
  170. {
  171. get
  172. {
  173. if (_doPowerOn != null)
  174. return _doPowerOn.Value;
  175. return false;
  176. }
  177. }
  178. public string Unit { get; set; }
  179. //private int _stage = 0;
  180. private float _controlTcSetPointView = 0f;
  181. //private int _stageSet = 0;
  182. private float _offset = 0f;
  183. //private float _offsetSet = 0f;
  184. private readonly DIAccessor _diPowerOnFeedback;
  185. private readonly DIAccessor _diControlTcBroken;
  186. private readonly DIAccessor _diMonitorTcBroken;
  187. private readonly DIAccessor _diDeviation;
  188. private readonly DOAccessor _doPowerOn;
  189. private readonly AIAccessor _aiControlTcFeedback;
  190. private readonly AIAccessor _aiMonitorTcFeedback;
  191. private readonly AIAccessor _aiCoolantInletTempFeedback;
  192. private readonly AIAccessor _aiCoolantOutletTempFeedback;
  193. private readonly AOAccessor _aoSetPoint;
  194. private AOAccessor _aoSetPointLimit;
  195. private readonly SCConfigItem _scSetPointLimit;
  196. private readonly R_TRIG _trigMonitorTcBroken = new R_TRIG();
  197. private readonly R_TRIG _trigControlTcBroken = new R_TRIG();
  198. private readonly R_TRIG _trigDeviation = new R_TRIG();
  199. private SCConfigItem _scEnableToleranceCheck;
  200. private SCConfigItem _scDeviationAlarmRange;
  201. private SCConfigItem _scDeviationAlarmTime;
  202. private SCConfigItem _scDeviationWarningRange;
  203. private SCConfigItem _scDeviationWarningTime;
  204. private DeviceTimer _timerAlarm = new DeviceTimer();
  205. private DeviceTimer _timerWarning = new DeviceTimer();
  206. private readonly R_TRIG _trigWarning = new R_TRIG();
  207. private readonly R_TRIG _trigAlarm = new R_TRIG();
  208. private ToleranceChecker _checkerWarning = new ToleranceChecker();
  209. private ToleranceChecker _checkerAlarm = new ToleranceChecker();
  210. private string HeaterDeviationAlarm = "HeaterDeviationAlarm";
  211. public IoHeater(string module, XmlElement node, string ioModule = "")
  212. {
  213. base.Module = module;
  214. base.Name = node.GetAttribute("id");
  215. base.Display = node.GetAttribute("display");
  216. base.DeviceID = node.GetAttribute("schematicId");
  217. Unit = node.GetAttribute("unit");
  218. _diPowerOnFeedback = ParseDiNode("diPowerOnFeedback", node, ioModule);
  219. _diControlTcBroken = ParseDiNode("diControlTcBroken", node, ioModule);
  220. _diMonitorTcBroken = ParseDiNode("diMonitorTcBroken", node, ioModule);
  221. _doPowerOn = ParseDoNode("doPowerOn", node, ioModule);
  222. _diDeviation = ParseDiNode("diDeviation", node, ioModule);
  223. _aiControlTcFeedback = ParseAiNode("aiFeedback", node, ioModule);
  224. _aiMonitorTcFeedback = ParseAiNode("aiMonitor", node, ioModule);
  225. _aiCoolantInletTempFeedback = ParseAiNode("aiCoolantInletTemp", node, ioModule);
  226. _aiCoolantOutletTempFeedback = ParseAiNode("aiCoolantOutletTemp", node, ioModule);
  227. _aoSetPoint = ParseAoNode("aoSetPoint", node, ioModule);
  228. _aoSetPointLimit = ParseAoNode("aoSetPointLimit", node, ioModule);
  229. _scSetPointLimit = ParseScNodeEx("scSetPointLimit", node, ioModule);
  230. }
  231. //public void UpdateConfig(double setPointLimit)
  232. //{
  233. // if (_aoSetPointLimit != null)
  234. // _aoSetPointLimit.Value = (short)setPointLimit;
  235. //}
  236. public bool Initialize()
  237. {
  238. DATA.Subscribe($"{Module}.{Name}.DeviceData", () =>
  239. {
  240. AITHeaterData data = new AITHeaterData()
  241. {
  242. Module = Module,
  243. DeviceName = Name,
  244. DeviceSchematicId = DeviceID,
  245. DisplayName = Display,
  246. FeedBack = ControlTcFeedback,
  247. MonitorTcFeedBack = MonitorTcFeedback,
  248. CoolantInletTcFeedback = CoolantInletTcFeedback,
  249. CoolantOutletTcFeedback = CoolantOutletTcFeedback,
  250. Scale = SetPointLimit,
  251. SetPoint = ControlTcSetPointView,
  252. IsPowerOn = IsPowerOnFeedback,
  253. IsPowerOnSetPoint = IsPowerOnSetPoint,
  254. IsControlTcBroken = IsControlTcBroken,
  255. IsMonitorTcBroken = IsMonitorTcBroken,
  256. Unit = Unit,
  257. IsTcDeviation = IsTcDeviation,
  258. };
  259. return data;
  260. }, SubscriptionAttribute.FLAG.IgnoreSaveDB);
  261. DATA.Subscribe($"{Module}.{Name}.Temperature", () => ControlTcFeedback);
  262. OP.Subscribe($"{Module}.{Name}.{AITHeaterOperation.SetPowerOnOff}", (functionName, param) =>
  263. {
  264. bool isEnable = Convert.ToBoolean((string)param[0]);
  265. return this.TurnOnOff(isEnable);
  266. });
  267. OP.Subscribe($"{Module}.{Name}.{AITHeaterOperation.Ramp}", (functionName, param) =>
  268. {
  269. float setpoint = (float)Convert.ToDouble((string)param[0]);
  270. if (!RampTemp(setpoint)) return false;
  271. return true;
  272. });
  273. this.SetBySC(_aoSetPointLimit, _scSetPointLimit);
  274. if(Name== "LEHeater2"|| Name == "LEHeater1")
  275. {
  276. _scEnableToleranceCheck = SC.GetConfigItem($"{Module}.HeaterChamber.HeaterEnableTolerance");
  277. _scDeviationAlarmRange = SC.GetConfigItem($"{Module}.HeaterChamber.HeaterAlarmRange");
  278. _scDeviationAlarmTime = SC.GetConfigItem($"{Module}.HeaterChamber.HeaterAlarmTime");
  279. _scDeviationWarningRange = SC.GetConfigItem($"{Module}.HeaterChamber.HeaterWarningRange");
  280. _scDeviationWarningTime = SC.GetConfigItem($"{Module}.HeaterChamber.HeaterWarningTime");
  281. }
  282. if (Name == "HeaterChamber")
  283. {
  284. _scEnableToleranceCheck = SC.GetConfigItem($"{Module}.HeaterChamberWall.HeaterEnableTolerance");
  285. _scDeviationAlarmRange = SC.GetConfigItem($"{Module}.HeaterChamberWall.HeaterAlarmRange");
  286. _scDeviationAlarmTime = SC.GetConfigItem($"{Module}.HeaterChamberWall.HeaterAlarmTime");
  287. _scDeviationWarningRange = SC.GetConfigItem($"{Module}.HeaterChamberWall.HeaterWarningRange");
  288. _scDeviationWarningTime = SC.GetConfigItem($"{Module}.HeaterChamberWall.HeaterWarningTime");
  289. }
  290. EV.Subscribe(new EventItem("Event", HeaterDeviationAlarm, "Heater Deviation Out of Tolerance", EventLevel.Alarm, EventType.HostNotification));
  291. return true;
  292. }
  293. public bool TurnOnOff(bool on)
  294. {
  295. if (!_doPowerOn.SetValue(on, out string reason))
  296. {
  297. EV.PostWarningLog(Module, reason);
  298. return false;
  299. }
  300. EV.PostInfoLog(Module, $"Set Heater {Name} Power {(on ? "ON" : "OFF")}");
  301. return true;
  302. }
  303. public bool RampTemp(float setpoint)
  304. {
  305. //_stageSet = (setpoint < 100) ? 3 : (setpoint < 200 && setpoint >= 100) ? 5 : (setpoint >= 200) ? 6 : 0;
  306. if (Name == "LEHeater1")
  307. {
  308. _offset = GetHeater1OffsetSetting(setpoint);
  309. }
  310. else if (Name == "LEHeater2")
  311. {
  312. _offset = GetHeater2OffsetSetting(setpoint);
  313. }
  314. else
  315. {
  316. _offset = 0;
  317. }
  318. // offset 处理后的设定值
  319. _controlTcSetPointView = setpoint;
  320. if (Name == "ForelineHeater"||Name== "HeaterChamber")
  321. ControlTcSetPoint = setpoint;
  322. else
  323. ControlTcSetPoint = setpoint + _offset;
  324. // 是否越界
  325. if (setpoint > SetPointLimit || setpoint < 0)
  326. {
  327. EV.PostAlarmLog(Module, $"{Name} 温度设定 {setpoint} 无效, 正确范围是 (0, {SetPointLimit})");
  328. return false;
  329. }
  330. EV.PostInfoLog(Module, $"设定 {Display} 温度到 {setpoint}");
  331. return true;
  332. }
  333. public void Stop()
  334. {
  335. if (_aoSetPoint != null)
  336. {
  337. _aoSetPoint.Value = 0;
  338. }
  339. }
  340. public void Terminate()
  341. {
  342. }
  343. public void Monitor()
  344. {
  345. _trigControlTcBroken.CLK = IsControlTcBroken;
  346. if (_trigControlTcBroken.Q)
  347. {
  348. EV.PostAlarmLog(Module, $"{Display}, Found control TC broken");
  349. }
  350. _trigMonitorTcBroken.CLK = IsMonitorTcBroken;
  351. if (_trigMonitorTcBroken.Q)
  352. {
  353. EV.PostAlarmLog(Module, $"{Display}, Found monitor TC broken");
  354. }
  355. _trigDeviation.CLK = IsTcDeviation;
  356. if (_trigDeviation.Q)
  357. {
  358. EV.PostAlarmLog(Module, $"{Display}, Found TC Deviation out of range");
  359. }
  360. this.SetBySC(_aoSetPointLimit, _scSetPointLimit);
  361. CheckDeviation();
  362. }
  363. private void CheckDeviation()
  364. {
  365. if (_scEnableToleranceCheck==null || !_scEnableToleranceCheck.BoolValue||!((Name == "HeaterChamber")|| (Name == "LEHeater1") || (Name == "LEHeater2")) || !IsPowerOnFeedback)
  366. return;
  367. _checkerWarning.Monitor(ControlTcFeedback, ControlTcSetPoint - Math.Abs(_scDeviationWarningRange.IntValue)
  368. , ControlTcSetPoint + Math.Abs(_scDeviationWarningRange.IntValue), _scDeviationWarningTime.IntValue);
  369. if (_checkerWarning.Trig)
  370. {
  371. if(Name == "HeaterChamber")
  372. {
  373. EV.PostWarningLog(Module, $"HeaterChamberWall temperature feedback deviation than {Math.Abs(_scDeviationWarningRange.IntValue)} from setpoint for {_scDeviationWarningTime.IntValue} seconds");
  374. }
  375. else
  376. {
  377. EV.PostWarningLog(Module, $"{Name} temperature feedback deviation than {Math.Abs(_scDeviationWarningRange.IntValue)} from setpoint for {_scDeviationWarningTime.IntValue} seconds");
  378. }
  379. }
  380. _checkerAlarm.Monitor(ControlTcFeedback, ControlTcSetPoint - Math.Abs(_scDeviationAlarmRange.IntValue)
  381. , ControlTcSetPoint + Math.Abs(_scDeviationAlarmRange.IntValue), _scDeviationAlarmTime.IntValue);
  382. if (_checkerAlarm.Trig)
  383. {
  384. if (Name == "HeaterChamber")
  385. {
  386. EV.PostAlarmLog(Module, $"HeaterChamberWall temperature feedback deviation than {Math.Abs(_scDeviationAlarmRange.IntValue)} from setpoint for {_scDeviationAlarmTime.IntValue} seconds");
  387. }
  388. else
  389. {
  390. EV.PostAlarmLog(Module, $"{Name} temperature feedback deviation than {Math.Abs(_scDeviationAlarmRange.IntValue)} from setpoint for {_scDeviationAlarmTime.IntValue} seconds");
  391. }
  392. EV.Notify(HeaterDeviationAlarm);
  393. }
  394. }
  395. public void Reset()
  396. {
  397. _trigControlTcBroken.RST = true;
  398. _trigMonitorTcBroken.RST = true;
  399. _trigDeviation.RST = true;
  400. _checkerWarning.RST = true;
  401. _checkerAlarm.RST = true;
  402. }
  403. private void SetBySC(AOAccessor acc, SCConfigItem scItem)
  404. {
  405. if (scItem != null && acc != null)
  406. {
  407. //acc.Value = (short)scItem.IntValue;
  408. _SetRealFloat(acc, scItem.IntValue);
  409. }
  410. }
  411. private float GetHeater1OffsetSetting(double val)
  412. {
  413. if (!SC.ContainsItem($"{Module}.BiasRf1.EnableBiasRF") || SC.GetValue<bool>($"{Module}.BiasRf1.EnableBiasRF")) return 0;
  414. if (!SC.ContainsItem($"{Module}.Chiller1.EnableChiller") || SC.GetValue<bool>($"{Module}.Chiller1.EnableChiller")) return 0;
  415. int[] iTempPoint = new int[10];
  416. float[] fOffsetValue = new float[10];
  417. try
  418. {
  419. for (int i = 1; i < 10; i++)
  420. {
  421. iTempPoint[i] = SC.GetValue<int>($"{Module}.HeaterChamber1.TempOffsetPoint_{i}");
  422. fOffsetValue[i] = (float)SC.GetValue<double>($"{Module}.HeaterChamber1.OffsetValue_{i}");
  423. if (val < iTempPoint[i])
  424. {
  425. return (fOffsetValue[i] - fOffsetValue[i - 1]) / (iTempPoint[i] - iTempPoint[i - 1]) * ((float)val - iTempPoint[i - 1]) + fOffsetValue[i - 1];
  426. }
  427. }
  428. }
  429. catch
  430. { }
  431. return 0;
  432. }
  433. private float GetHeater2OffsetSetting(double val)
  434. {
  435. if (!SC.ContainsItem($"{Module}.BiasRf1.EnableBiasRF") || SC.GetValue<bool>($"{Module}.BiasRf1.EnableBiasRF")) return 0;
  436. if (!SC.ContainsItem($"{Module}.Chiller1.EnableChiller") || SC.GetValue<bool>($"{Module}.Chiller1.EnableChiller")) return 0;
  437. int[] iTempPoint = new int[10];
  438. float[] fOffsetValue = new float[10];
  439. try
  440. {
  441. for (int i = 1; i < 10; i++)
  442. {
  443. iTempPoint[i] = SC.GetValue<int>($"{Module}.HeaterChamber2.TempOffsetPoint_{i}");
  444. fOffsetValue[i] = (float)SC.GetValue<double>($"{Module}.HeaterChamber2.OffsetValue_{i}");
  445. if (val < iTempPoint[i])
  446. {
  447. return (fOffsetValue[i] - fOffsetValue[i - 1]) / (iTempPoint[i] - iTempPoint[i - 1]) * ((float)val - iTempPoint[i - 1]) + fOffsetValue[i - 1];
  448. }
  449. }
  450. }
  451. catch
  452. { }
  453. return 0;
  454. }
  455. }
  456. }