APCPIDEditViewModel.cs 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696
  1. using Aitex.Core.RT.SCCore;
  2. using Caliburn.Micro;
  3. using Caliburn.Micro.Core;
  4. using MECF.Framework.Common.DataCenter;
  5. using MECF.Framework.Common.OperationCenter;
  6. using MECF.Framework.Common.RecipeCenter;
  7. using MECF.Framework.UI.Client.CenterViews.Configs.SystemConfig;
  8. using MECF.Framework.UI.Client.CenterViews.Dialogs;
  9. using MECF.Framework.UI.Client.CenterViews.Editors.Recipe;
  10. using MECF.Framework.UI.Client.ClientBase;
  11. using OpenSEMI.ClientBase;
  12. using System;
  13. using System.Collections.Generic;
  14. using System.Collections.ObjectModel;
  15. using System.IO;
  16. using System.Linq;
  17. using System.Text;
  18. using System.Windows;
  19. //using System.Windows.Forms;
  20. using System.Windows.Controls;
  21. using FurnaceUI.Client;
  22. using FurnaceUI.Models;
  23. using FurnaceUI.Views.Editors;
  24. using Aitex.Core.Util;
  25. using Aitex.Core.Common.DeviceData;
  26. using MECF.Framework.UI.Client.CenterViews.Parameter;
  27. using MECF.Framework.Common.ParameterCenter;
  28. using RecipeEditorLib.RecipeModel.Params;
  29. namespace FurnaceUI.Views.Parameter
  30. {
  31. public class APCPIDEditViewModel : FurnaceUIViewModelBase
  32. {
  33. private UIElement _parent;
  34. private bool _isEditEnabled = true;
  35. public bool IsEditEnabled
  36. {
  37. get => _isEditEnabled;
  38. set
  39. {
  40. _isEditEnabled = value;
  41. NotifyOfPropertyChange(nameof(IsEditEnabled));
  42. }
  43. }
  44. public void SetParent(UIElement parent)
  45. {
  46. _parent = parent;
  47. }
  48. private string _fileName = "";
  49. public string FileName
  50. {
  51. get => _fileName;
  52. set
  53. {
  54. _fileName = value;
  55. NotifyOfPropertyChange(nameof(FileName));
  56. }
  57. }
  58. public string RetrunString { get; set; } = "";
  59. private readonly ParameterProvider _parameterProvider = new ParameterProvider();
  60. private Dictionary<string, ObservableCollection<ParameterTemplateColumnBase>> ParameterTemplate;
  61. public APCPIDParameterData CurrentParameter { get; set; } = new APCPIDParameterData();
  62. private ParameterFormatBuilder _columnBuilder = new ParameterFormatBuilder();
  63. private APCPIDTable _selectedParameterStep;
  64. public APCPIDTable SelectedParameterStep
  65. {
  66. get => _selectedParameterStep;
  67. set
  68. {
  69. if (value != null)
  70. {
  71. _selectedParameterStep = value;
  72. NotifyOfPropertyChange("SelectedParameterStep");
  73. }
  74. else
  75. {
  76. _selectedParameterStep = null;
  77. NotifyOfPropertyChange("SelectedParameterStep");
  78. }
  79. }
  80. }
  81. private int _IndexNoDefault = -1;
  82. public int IndexNoDefault
  83. {
  84. get { return _IndexNoDefault; }
  85. set
  86. {
  87. _IndexNoDefault = value;
  88. NotifyOfPropertyChange("IndexNoDefault");
  89. }
  90. }
  91. private bool _appendStepItemIsEnabled;
  92. public bool AppendStepItemIsEnabled
  93. {
  94. get => _appendStepItemIsEnabled;
  95. set
  96. {
  97. _appendStepItemIsEnabled = value;
  98. NotifyOfPropertyChange("AppendStepItemIsEnabled");
  99. }
  100. }
  101. private bool _overWriteCopyIsEnabled;
  102. public bool OverWriteCopyIsEnabled
  103. {
  104. get => _overWriteCopyIsEnabled;
  105. set
  106. {
  107. _overWriteCopyIsEnabled = value;
  108. NotifyOfPropertyChange("OverWriteCopyIsEnabled");
  109. }
  110. }
  111. private bool _insertCopyIsEnabled;
  112. public bool InsertCopyIsEnabled
  113. {
  114. get => _insertCopyIsEnabled;
  115. set
  116. {
  117. _insertCopyIsEnabled = value;
  118. NotifyOfPropertyChange("InsertCopyIsEnabled");
  119. }
  120. }
  121. private bool _prevStepOverwriteIsEnabled;
  122. public bool PrevStepOverwriteIsEnabled
  123. {
  124. get => _prevStepOverwriteIsEnabled;
  125. set
  126. {
  127. _prevStepOverwriteIsEnabled = value;
  128. NotifyOfPropertyChange("PrevStepOverwriteIsEnabled");
  129. }
  130. }
  131. private bool _prevStepInsertIsEnabled;
  132. public bool PrevStepInsertIsEnabled
  133. {
  134. get => _prevStepInsertIsEnabled;
  135. set
  136. {
  137. _prevStepInsertIsEnabled = value;
  138. NotifyOfPropertyChange("PrevStepInsertIsEnabled");
  139. }
  140. }
  141. private bool _prevStepItemIsEnabled;
  142. public bool PrevStepItemIsEnabled
  143. {
  144. get => _prevStepItemIsEnabled;
  145. set
  146. {
  147. _prevStepItemIsEnabled = value;
  148. NotifyOfPropertyChange("PrevStepItemIsEnabled");
  149. }
  150. }
  151. private bool _currStepDeleteIsEnabled;
  152. public bool CurrStepDeleteIsEnabled
  153. {
  154. get => _currStepDeleteIsEnabled;
  155. set
  156. {
  157. _currStepDeleteIsEnabled = value;
  158. NotifyOfPropertyChange("CurrStepDeleteIsEnabled");
  159. }
  160. }
  161. private bool _multStepsDeleteIsEnabled;
  162. public bool MultStepsDeleteIsEnabled
  163. {
  164. get => _multStepsDeleteIsEnabled;
  165. set
  166. {
  167. _multStepsDeleteIsEnabled = value;
  168. NotifyOfPropertyChange("MultStepsDeleteIsEnabled");
  169. }
  170. }
  171. private bool _settingButtonEnable;
  172. public bool SettingButtonEnable
  173. {
  174. get => _settingButtonEnable;
  175. set
  176. {
  177. _settingButtonEnable = value;
  178. NotifyOfPropertyChange("SettingButtonEnable");
  179. }
  180. }
  181. private string _eventSetting;
  182. public string EventSetting
  183. {
  184. get => _eventSetting;
  185. set
  186. {
  187. _eventSetting = value;
  188. NotifyOfPropertyChange("EventSetting");
  189. }
  190. }
  191. public bool IsEnable => CGlobal.ParameterEditViewEnable;//是否是View模式
  192. public string EditRecipeStepName { get; set; }
  193. public void SetCmdIsEnabled()
  194. {
  195. if (CurrentParameter.Steps == null || CurrentParameter.Steps.Count == 0)
  196. {
  197. SelectedStepName = "";
  198. SelectedParameterStep = null;
  199. AppendStepItemIsEnabled = true;
  200. OverWriteCopyIsEnabled = false;
  201. InsertCopyIsEnabled = false;
  202. PrevStepOverwriteIsEnabled = false;
  203. PrevStepInsertIsEnabled = false;
  204. PrevStepItemIsEnabled = false;
  205. CurrStepDeleteIsEnabled = false;
  206. MultStepsDeleteIsEnabled = false;
  207. SettingButtonEnable = false;
  208. }
  209. }
  210. public int SelectedStepNo { get; set; }
  211. private string _selectedStepName;
  212. public string SelectedStepName
  213. {
  214. get
  215. {
  216. return _selectedStepName;
  217. }
  218. set
  219. {
  220. _selectedStepName = value;
  221. NotifyOfPropertyChange("SelectedStepName");
  222. }
  223. }
  224. private List<ConfigNode> _ConfigNodes = new List<ConfigNode>();
  225. public List<ConfigNode> ConfigNodes
  226. {
  227. get { return _ConfigNodes; }
  228. set { _ConfigNodes = value; NotifyOfPropertyChange("ConfigNodes"); }
  229. }
  230. private Step _selectedRecipeStep;
  231. public Step SelectedRecipeStep
  232. {
  233. get => _selectedRecipeStep;
  234. set
  235. {
  236. _selectedRecipeStep = value;
  237. NotifyOfPropertyChange("SelectedRecipeStep");
  238. }
  239. }
  240. private RecipeDataBase _CurrentRecipe;
  241. public RecipeDataBase CurrentRecipe
  242. {
  243. get { return _CurrentRecipe; }
  244. set { _CurrentRecipe = value; this.NotifyOfPropertyChange(nameof(CurrentRecipe)); }
  245. }
  246. public string FullFileName { get; set; }
  247. public string ParameterType { get; set; }
  248. public APCPIDEditViewModel()
  249. {
  250. string prefix = "Parameter\\APCPID";
  251. _parameterProvider.GetParameterFormatXml(prefix);
  252. ParameterTemplate = _parameterProvider.GetGroupParameterTemplate();
  253. _columnBuilder.Build(prefix);
  254. CurrentParameter.PrefixPath = prefix;
  255. }
  256. public APCPIDEditViewModel(string strPrefixPath, string strRecipeName, string permission = "")
  257. {
  258. _parameterProvider.GetParameterFormatXml(strPrefixPath);
  259. ParameterTemplate = _parameterProvider.GetGroupParameterTemplate();
  260. _columnBuilder.Build(strPrefixPath);
  261. CurrentParameter.PrefixPath = strPrefixPath;
  262. CurrentParameter.Name = strRecipeName;
  263. CurrentParameter.Permission = permission;
  264. FileName = $"{strPrefixPath}\\{strRecipeName}";
  265. }
  266. protected override void OnViewLoaded(object view)
  267. {
  268. base.OnViewLoaded(view);
  269. }
  270. protected override void OnActivate()
  271. {
  272. base.OnActivate();
  273. //InvokeClient.Instance.Service.DoOperation($"PM1.SetSensorRecipeOK", "");
  274. }
  275. protected override void OnDeactivate(bool close)
  276. {
  277. base.OnDeactivate(close);
  278. InvokeClient.Instance.Service.DoOperation($"PM1.SetSensorPROCManualOK", "");
  279. }
  280. protected override void OnInitialize()
  281. {
  282. base.OnInitialize();
  283. // GetHeaderConfig();
  284. LoadData();
  285. LoadViewData();
  286. SetCmdIsEnabled();
  287. }
  288. private void LoadData()
  289. {
  290. if (CurrentRecipe != null)
  291. {
  292. CurrentParameter.PrefixPath = $"Parameter\\APCPID";
  293. StringParam pressAPC = CurrentRecipe.ConfigItems.FirstOrDefault(x => x.Name == "Combination.PressAPCPID") as StringParam;
  294. if (pressAPC != null && !string.IsNullOrEmpty(pressAPC.Value))
  295. {
  296. CurrentParameter.Permission = "";
  297. CurrentParameter.Name = pressAPC.Value;
  298. }
  299. else
  300. {
  301. if (CurrentParameter.Steps != null && CurrentParameter.Steps.Count > 0)
  302. {
  303. foreach (var item in CurrentParameter.Steps)
  304. {
  305. var apcPID = (APCPIDTable)item;
  306. apcPID.P.Value = "0";
  307. apcPID.I.Value = "0";
  308. apcPID.D.Value = "0";
  309. apcPID.A.Value = "0";
  310. apcPID.Offset.Value = "0";
  311. apcPID.CH.Value = "0";
  312. apcPID.CL.Value = "0";
  313. }
  314. }
  315. CurrentParameter.Name = "";
  316. CurrentParameter.SlowVacP.Value = "0";
  317. FullFileName = "";
  318. DialogBox.ShowDialog(DialogButton.Cancel, DialogType.INFO, "Please set the Combination default APC PID file!");
  319. return;
  320. }
  321. FullFileName = $"{CurrentParameter.PrefixPath}\\{CurrentParameter.Name}";
  322. }
  323. else
  324. {
  325. CurrentParameter.TableNumber = _columnBuilder.TableNumber;
  326. CurrentParameter.ChamberType = _columnBuilder.ChamberType;
  327. FullFileName = $"{CurrentParameter.PrefixPath}\\{CurrentParameter.Name}";
  328. }
  329. var recipeContent = _parameterProvider.LoadParameter(CurrentParameter.PrefixPath, CurrentParameter.Name);
  330. if (string.IsNullOrEmpty(recipeContent))
  331. {
  332. System.Windows.MessageBox.Show($"{CurrentParameter.PrefixPath}\\{CurrentParameter.Name} is empty, please confirm the file is valid.");
  333. return;
  334. }
  335. CurrentParameter.InitData(CurrentParameter.PrefixPath, CurrentParameter.Name, recipeContent, "");
  336. }
  337. private void LoadViewData()
  338. {
  339. if (CurrentParameter.Steps != null && CurrentParameter.Steps.Count > 0)
  340. {
  341. SelectedStepName = CurrentParameter.Steps[0].Name;
  342. SelectedStepNo = CurrentParameter.Steps[0].StepNo;
  343. SelectTable(CurrentParameter.Steps[0]);
  344. }
  345. }
  346. private void RecipeGasPanelSettingViewModel_ChangedStepEvent(Step step)
  347. {
  348. SelectTable(step);
  349. IndexNoDefault = step.StepNo - 1;
  350. }
  351. public void SelectTable(object step)
  352. {
  353. if (step != null && step is APCPIDTable step1)
  354. {
  355. var SelectedStep = this.CurrentParameter.Steps.Where(x => x.StepNo == step1.StepNo).FirstOrDefault();
  356. SelectedStep.IsChecked = true;
  357. SelectedStepNo = step1.StepNo;
  358. string strName = step1.Name.Trim();
  359. SelectedStepName = strName;
  360. SelectedParameterStep = (APCPIDTable)SelectedStep;
  361. }
  362. SetCmdIsEnabled();
  363. }
  364. public void StepEdit(string stepEditCmd)
  365. {
  366. var windowManager = IoC.Get<IWindowManager>();
  367. switch (stepEditCmd)
  368. {
  369. case "Append":
  370. CurrentParameter.Steps.Add(CurrentParameter.CreateStep());
  371. int TempSelectIndex = 0;
  372. IndexNoDefault = TempSelectIndex;
  373. SelectTable(CurrentParameter.Steps[TempSelectIndex]);
  374. break;
  375. case "InsertCopy":
  376. InsertCopyStep();
  377. break;
  378. case "OverWrite"://任何步骤的内容都可以覆盖到选定的步骤中
  379. OverWriteStep();
  380. break;
  381. case "PrevStepOverwrite"://用上一步的内容覆盖所选步骤
  382. PrevStepOverwriteStep();
  383. break;
  384. case "PrevStepInsert"://在选定步骤之前,插入带有前一步内容的新步骤。
  385. InsertPrevStep();
  386. break;
  387. case "PrevStepItem":
  388. break;
  389. case "MultStepsDelete":
  390. break;
  391. default:
  392. break;
  393. }
  394. }
  395. private void OverWriteStep()
  396. {
  397. var windowManager = IoC.Get<IWindowManager>();
  398. if (CurrentParameter == null) return;
  399. }
  400. private void PrevStepOverwriteStep()
  401. {
  402. int index = -1;
  403. index = SelectedParameterStep.StepNo;
  404. if (index > 1)
  405. {
  406. CurrentParameter.CloneStep(CurrentParameter.Steps.Where(x => x.StepNo == SelectedParameterStep.StepNo).FirstOrDefault(), CurrentParameter.Steps.Where(x => x.StepNo == SelectedParameterStep.StepNo - 1).FirstOrDefault());
  407. }
  408. }
  409. public void InsertPrevStep()
  410. {
  411. }
  412. public void InsertCopyStep()
  413. {
  414. var windowManager = IoC.Get<IWindowManager>();
  415. if (CurrentParameter == null) return;
  416. }
  417. //撤销修改
  418. public void RecipeIsChangeClick(object cmdName, object value)
  419. {
  420. var windowManager = IoC.Get<IWindowManager>();
  421. }
  422. public void TempSetClick(object sender)
  423. {
  424. string stSetValue = ShowNumberKeyboard(sender as Button, "");
  425. }
  426. public void RampSetClick(object sender)
  427. {
  428. string strSetRamp = ShowNumberKeyboard(sender as Button, "");
  429. }
  430. private string ShowNumberKeyboard(Control control, string defaultValue)
  431. {
  432. NumberKeyboard numberKeyboard = new NumberKeyboard("", defaultValue);
  433. var point = control.PointFromScreen(new Point(0, 0));
  434. double wx = SystemParameters.WorkArea.Width;
  435. double hy = SystemParameters.WorkArea.Height;
  436. if (-point.Y + control.ActualHeight + 5 + numberKeyboard.Height < hy)
  437. {
  438. numberKeyboard.Top = -point.Y + control.ActualHeight + 5;
  439. }
  440. else
  441. {
  442. numberKeyboard.Top = -point.Y - numberKeyboard.Height - 5;
  443. }
  444. if (-point.X + numberKeyboard.Width < wx)
  445. {
  446. numberKeyboard.Left = -point.X;
  447. }
  448. else
  449. {
  450. numberKeyboard.Left = -point.X - (numberKeyboard.Width - control.ActualWidth);
  451. }
  452. if ((bool)numberKeyboard.ShowDialog())
  453. return numberKeyboard.ValueString;
  454. else
  455. return "Cancel";
  456. }
  457. public void TempTextClick(string type, object sender)
  458. {
  459. var windowManager = IoC.Get<IWindowManager>();
  460. switch (type)
  461. {
  462. case "Mode":
  463. RecipeTempModeViewModel recipeTempModeViewModel = new RecipeTempModeViewModel();
  464. var rtn = (windowManager as WindowManager)?.ShowDialogWithTitle(recipeTempModeViewModel, null, "Temp Mode");
  465. break;
  466. case "Correct":
  467. TempOffsetTableViewModel tempOffsetTableViewModel = new TempOffsetTableViewModel();
  468. break;
  469. case "PID":
  470. TempOffsetTableViewModel tempOffsetTableViewModel1 = new TempOffsetTableViewModel();
  471. break;
  472. default:
  473. break;
  474. }
  475. }
  476. public void TempTextChanged(string type, object sender, object item)
  477. {
  478. if (!string.IsNullOrEmpty(type) && item != null && sender != null)
  479. {
  480. TempSetData tempData = (TempSetData)item;
  481. string value = ((TextBox)sender).Text;
  482. int stepNo = SelectedParameterStep.StepNo;
  483. var step = CurrentParameter.Steps.Where(x => x.StepNo == stepNo).FirstOrDefault();
  484. }
  485. }
  486. public void ParameterSave()
  487. {
  488. if (IsEditEnabled)
  489. {
  490. var SelectedStep = this.CurrentParameter.Steps.Where(x => x.StepNo == SelectedStepNo).FirstOrDefault();
  491. //RecipePermissionSelectViewModel dialog = new RecipePermissionSelectViewModel("Save recipe and permission", CurrentRecipe.RecipePermission);
  492. //WindowManager wm = new WindowManager();
  493. //bool? dialogReturn = wm.ShowDialog(dialog);
  494. //if (!dialogReturn.HasValue || !dialogReturn.Value)
  495. // return;
  496. List<string> names = new List<string>();
  497. string filmFormula = string.Empty;
  498. ParameterTable step = CurrentParameter.Steps.Where(x => x.StepNo == SelectedParameterStep.StepNo).FirstOrDefault();
  499. this.CurrentParameter.Revisor = BaseApp.Instance.UserContext.LoginName;
  500. this.CurrentParameter.ReviseTime = DateTime.Now;
  501. this.CurrentParameter.Level = this.LevelDisplay;
  502. //this.CurrentRecipe.RecipePermission = dialog.RecipePermission;
  503. var result = this._parameterProvider.SaveParameter(CurrentParameter.PrefixPath, CurrentParameter.Name, CurrentParameter.GetXmlString());
  504. if (result)
  505. ((Window)GetView()).Close();
  506. }
  507. else
  508. {
  509. var step = CurrentParameter.Steps.FirstOrDefault(x => x.IsChecked);
  510. RetrunString = $"{FullFileName},{step.StepNo},{step.Name}";
  511. ((Window)GetView()).DialogResult = true;
  512. }
  513. }
  514. public void RdoCmdSelectTableChecked(object step)
  515. {
  516. }
  517. public void SelectTableStep(object step)
  518. {
  519. var ssss = step;
  520. if (step != null && step is ParameterTable)
  521. {
  522. var tempStep = (ParameterTable)step;
  523. tempStep.IsChecked = !tempStep.IsChecked;
  524. }
  525. }
  526. public void SetValue(object sender, string isFullKeyboard = "")
  527. {
  528. string value = ((TextBox)sender).Text;
  529. if (!string.IsNullOrEmpty(isFullKeyboard))
  530. {
  531. FullKeyboard fullKeyboard1 = new FullKeyboard("", value);
  532. if ((bool)fullKeyboard1.ShowDialog())
  533. {
  534. ((TextBox)sender).Text = fullKeyboard1.ValueString;
  535. }
  536. }
  537. else
  538. {
  539. NumberKeyboard fullKeyboard = new NumberKeyboard("", value);
  540. if ((bool)fullKeyboard.ShowDialog())
  541. {
  542. ((TextBox)sender).Text = fullKeyboard.ValueString;
  543. }
  544. }
  545. }
  546. public void ParameterDownload()
  547. {
  548. var step = CurrentParameter.Steps.FirstOrDefault(x => x.IsChecked);
  549. InvokeClient.Instance.Service.DoOperation($"PM1.APC.SetPID", $"{FullFileName}", step.StepNo);
  550. }
  551. public void ParameterUnload()
  552. {
  553. }
  554. public void ParameterCancel()
  555. {
  556. if (DialogBox.ShowDialog(DialogButton.Yes | DialogButton.No, DialogType.CONFIRM, " You confirm that you want to unsave the recipe and exit the interface?") == DialogButton.No)
  557. return;
  558. ((Window)GetView()).Close();
  559. }
  560. protected override void InvokeAfterUpdateProperty(Dictionary<string, object> data)
  561. {
  562. base.InvokeAfterUpdateProperty(data);
  563. if (CurrentParameter.Steps != null && CurrentParameter.Steps.Count > 0 && CheckValueChange(data))
  564. {
  565. //SelectStep(CurrentRecipe.Steps[EditRecipeStepNo]);
  566. }
  567. oldresult = data;
  568. }
  569. Dictionary<string, object> oldresult;
  570. private bool CheckValueChange(Dictionary<string, object> result)
  571. {
  572. Dictionary<string, object> temp = result;
  573. if (oldresult == null)
  574. {
  575. oldresult = result;
  576. return true;
  577. }
  578. else
  579. {
  580. List<string> strkeys = new List<string>();
  581. foreach (var key in result.Keys)
  582. {
  583. if (_subscribedKeys.Contains(key) && oldresult.ContainsKey(key) && result.ContainsKey(key))
  584. {
  585. if (result[key].GetType() == typeof(AITValveData) && ((AITValveData)oldresult[key]).VirtualFeedback != ((AITValveData)result[key]).VirtualFeedback)
  586. {
  587. return true;
  588. }
  589. else if (result[key].GetType() == typeof(AITMfcData) && ((AITMfcData)oldresult[key]).VirtualSetPoint != ((AITMfcData)result[key]).VirtualSetPoint)
  590. {
  591. return true;
  592. }
  593. else if (result[key].GetType() == typeof(bool) && (bool)oldresult[key] != (bool)result[key])
  594. {
  595. return true;
  596. }
  597. }
  598. }
  599. }
  600. return false;
  601. }
  602. }
  603. }