From 72cf329ce1c456222fcc5276bb65e67cbf6760f0 Mon Sep 17 00:00:00 2001
From: C3204 <zhengyabo@lanpucloud.cn>
Date: 星期四, 22 一月 2026 14:52:39 +0800
Subject: [PATCH] 优化主界面显示为行列矩阵形式,实现鼠标左键双击对应窗体最大化,再次双击恢复之前布局。

---
 LB_SmartVision/VisionForm.cs |  883 +++++++++++++++++++++++++++++++++++++++++++++++++++++-----
 1 files changed, 804 insertions(+), 79 deletions(-)

diff --git a/LB_SmartVision/VisionForm.cs b/LB_SmartVision/VisionForm.cs
index 7d8803e..14f66c7 100644
--- a/LB_SmartVision/VisionForm.cs
+++ b/LB_SmartVision/VisionForm.cs
@@ -1,18 +1,28 @@
 锘縰sing HalconDotNet;
+using LB_SmartVision.Forms;
 using LB_SmartVision.Forms.Pages;
 using LB_SmartVision.Forms.Pages.CameraPage;
 using LB_SmartVision.Forms.Pages.CommunicatorPage;
+using LB_SmartVision.Forms.Pages.HistoricalData;
 using LB_SmartVision.Forms.Pages.MESPage;
 using LB_SmartVision.Forms.Pages.MotionControlPage;
 using LB_SmartVision.Forms.Pages.ProcessPage;
 using LB_SmartVision.Forms.Pages.SettingPage;
 using LB_SmartVision.Forms.Pages.UserManagementPage;
 using LB_SmartVision.ProcessRun;
+using LB_SmartVision.SQL;
 using LB_SmartVision.Tool;
+using LB_SmartVisionCommon;
+using LB_SmartVisionLoginUI;
 using LB_VisionProcesses;
 using LB_VisionProcesses.Cameras;
+using LB_VisionProcesses.Cameras.HRCameras;
+using LB_VisionProcesses.Cameras.LBCameras;
 using LB_VisionProcesses.Communicators;
+using LB_VisionProcesses.Communicators.SiemensS7;
 using LB_VisionProcesses.Communicators.TCom;
+using LB_VisionProcesses.Forms;
+using log4net.Config;
 using Newtonsoft.Json;
 using Newtonsoft.Json.Serialization;
 using Sunny.UI;
@@ -34,8 +44,9 @@
 {
     public partial class VisionForm : Form
     {
-        AllProcessesPage AllProcessesPage = new AllProcessesPage();
+        AllProcessesPage AllProcessesPages = new AllProcessesPage();
         CamerasEditPage CamerasEditPage = new CamerasEditPage();
+        HistoricalDataEditPage HistoricalDataEditPage = new HistoricalDataEditPage();
         CommunicatorsEditPage CommunicatorsEditPage = new CommunicatorsEditPage();
         SettingEditPage SettingEditPage = new SettingEditPage();
         MESEditPage MESEditPage = new MESEditPage();
@@ -56,11 +67,16 @@
             Assembly_LB_VisionProcessesDll = Assembly.Load(Assembly_LB_VisionProcessesBytes);
 
             GlobalVar.dicCommunicators.DictionaryChanged += CommunicatorsChanged;
+            GlobalVar.dicCameras.DictionaryChanged += CamerasChanged;
             GlobalVar.dicProcesses.DictionaryChanged += ProcessRunBllChanged;
 
             //鏈�寮�濮嬪氨娓呯┖鎵�鏈塗ab椤�
             materialTabControl.TabPages.Clear();
-            materialTabControl.Controls.Add(AllProcessesPage);
+            AllProcessesPages.controlsPanel.Dock = DockStyle.Fill;
+            materialTabControl.Controls.Add(AllProcessesPages);
+
+            HistoricalDataEditPage.LogInfo += LogInfo;
+            materialTabControl.Controls.Add(new MyPage(HistoricalDataEditPage));
 
             CamerasEditPage.LogInfo += LogInfo;
             materialTabControl.Controls.Add(new MyPage(CamerasEditPage));
@@ -84,7 +100,6 @@
             {
                 //materialTabControl.TabPages[i].Font= new Font("Microsoft YaHei UI", 18F, FontStyle.Regular, GraphicsUnit.Point, 0);
             }
-
             materialTabSelector.BaseTabControl = materialTabControl;
             //materialTabSelector.Font = new Font("Microsoft YaHei UI", 18F, FontStyle.Regular, GraphicsUnit.Point, 0);
         }
@@ -226,12 +241,126 @@
 
         private void CommunicatorsChanged(object? sender, DictionaryChangedEventArgs<string, BaseCommunicator> e)
         {
-
+            try
+            {
+                switch (e.ChangeType)
+                {
+                    case DictionaryChangeType.Added:
+                        e.NewValue.TriggerRunMessageReceived += TriggerRunMessageReceived;
+                        LogInfo($"閫氳鍙{e.NewValue.CommunicatorName}]鍔犺浇瑙﹀彂閫氳", LogInfoType.INFO);
+                        e.NewValue.CommunicatorName = e.NewKey;
+                        break;
+                    case DictionaryChangeType.Renamed:
+                        string OldCommunicatorName = e.OldKey;
+                        string NewCommunicatorName = e.NewKey;
+                        LogInfo(string.Format("閲嶅懡鍚嶉�氳鍙e悕[{0}]淇敼涓篬{1}]", OldCommunicatorName, NewCommunicatorName), LogInfoType.INFO);
+                        e.NewValue.CommunicatorName = NewCommunicatorName;
+                        break;
+                    case DictionaryChangeType.Removed:
+                        if (e.OldValue != null && e.OldValue is BaseCommunicator)
+                            e.OldValue.Disconnect();
+                        e.OldValue.TriggerRunMessageReceived -= TriggerRunMessageReceived;
+                        LogInfo($"閫氳鍙{e.OldValue.CommunicatorName}]绉婚櫎瑙﹀彂閫氳", LogInfoType.INFO);
+                        break;
+                }
+            }
+            catch { }
         }
 
-        private void LogInfo(string arg1, LogInfoType type)
+        private void LogInfo(string strLog, LogInfoType infoType)
         {
+            if (string.IsNullOrEmpty(strLog))
+            {
+                return;
+            }
+            string strInfo = DateTime.Now.ToString("[yyyy:MM:dd:HH:mm:ss:fff] ");
+            strInfo += strLog;
+            if (infoType != LogInfoType.NOSHOW)
+            {
+                // 濡傛灉褰撳墠涓嶆槸 UI 绾跨▼锛屽垯閫氳繃 Invoke 灏嗘搷浣滆皟搴﹀埌 UI 绾跨▼
+                if (this.rich_Info.InvokeRequired)
+                {
+                    this.rich_Info.BeginInvoke(new Action<string>((msg) =>
+                    {
+                        if (this.rich_Info.Lines.Length > 1000)
+                        {
+                            this.rich_Info.Clear();
+                        }
+                        switch (infoType)
+                        {
+                            case LogInfoType.INFO:
+                                {
+                                    this.rich_Info.SelectionColor = Color.Wheat;
+                                    AsyncLogHelper.Info(strLog);
+                                    break;
+                                }
+                            case LogInfoType.WARN:
+                                {
+                                    this.rich_Info.SelectionColor = Color.Yellow;
+                                    AsyncLogHelper.Warn(strLog);
+                                    break;
+                                }
+                            case LogInfoType.PASS:
+                                {
+                                    this.rich_Info.SelectionColor = Color.Green;
+                                    AsyncLogHelper.Info(strLog);
+                                    break;
+                                }
+                            case LogInfoType.ERROR:
+                                {
+                                    this.rich_Info.SelectionColor = Color.Red;
+                                    AsyncLogHelper.Error(strLog);
+                                    break;
+                                }
+                        }
+                        // 鏇存柊 UI 鎺т欢锛屾瘮濡傛樉绀烘帴鏀跺埌鐨勬秷鎭�
+                        this.rich_Info.AppendText(strInfo);
+                        this.rich_Info.AppendText("\r\n");
+                        this.rich_Info.SelectionStart = this.rich_Info.Text.Length;
+                        this.rich_Info.ScrollToCaret();
+                    }), strInfo);
+                }
+                else
+                {
 
+                    if (this.rich_Info.Lines.Length > 1000)
+                    {
+                        this.rich_Info.Clear();
+                    }
+                    // 濡傛灉宸茬粡鍦� UI 绾跨▼涓婏紝鐩存帴鏇存柊 UI
+                    switch (infoType)
+                    {
+                        case LogInfoType.INFO:
+                            {
+                                this.rich_Info.SelectionColor = Color.Wheat;
+                                AsyncLogHelper.Info(strLog);
+                                break;
+                            }
+                        case LogInfoType.WARN:
+                            {
+                                this.rich_Info.SelectionColor = Color.Yellow;
+                                AsyncLogHelper.Warn(strLog);
+                                break;
+                            }
+                        case LogInfoType.PASS:
+                            {
+                                this.rich_Info.SelectionColor = Color.Green;
+                                AsyncLogHelper.Info(strLog);
+                                break;
+                            }
+                        case LogInfoType.ERROR:
+                            {
+                                this.rich_Info.SelectionColor = Color.Red;
+                                AsyncLogHelper.Error(strLog);
+                                break;
+                            }
+                    }
+                    this.rich_Info.AppendText(strInfo);
+                    this.rich_Info.AppendText("\r\n");
+                    this.rich_Info.SelectionStart = this.rich_Info.Text.Length;
+                    this.rich_Info.ScrollToCaret();
+                }
+            }
         }
 
         public static bool SaveAllLayout()
@@ -406,9 +535,58 @@
             }
             catch { return false; }
         }
+        private void EnsureDirectory(string path)
+        {
+            // 濡傛灉鏄浉瀵硅矾寰勶紝杞崲涓虹粷瀵硅矾寰�
+            string fullPath = Path.IsPathRooted(path) ? path : Path.GetFullPath(path);
+
+            if (!Directory.Exists(fullPath))
+            {
+                Directory.CreateDirectory(fullPath);
+                LogInfo($"鉁� 鐩綍鍒涘缓: {fullPath}", LogInfoType.INFO);
+            }
+            else
+            {
+                LogInfo($"鈩癸笍 鐩綍宸插瓨鍦�: {fullPath}", LogInfoType.INFO);
+            }
+        }
+
+        private void CamerasChanged(object sender, DictionaryChangedEventArgs<string, BaseCamera> e)
+        {
+            try
+            {
+                switch (e.ChangeType)
+                {
+                    case DictionaryChangeType.Added:
+                        e.NewValue.TriggerRunMessageReceived += TriggerRunMessageReceived;
+                        LogInfo($"鐩告満[{e.NewValue.SN}]鍔犺浇瑙﹀彂閫氳", LogInfoType.INFO);
+                        e.NewValue.SN = e.NewKey;
+                        break;
+                    case DictionaryChangeType.Removed:
+                        if (e.OldValue != null && e.OldValue is BaseCommunicator)
+                            e.OldValue.CloseDevice();
+                        e.OldValue.TriggerRunMessageReceived -= TriggerRunMessageReceived;
+                        LogInfo($"鐩告満[{e.OldValue.SN}]绉婚櫎瑙﹀彂閫氳", LogInfoType.INFO);
+                        break;
+                }
+            }
+            catch { }
+        }
 
         private void VisionForm_Load(object sender, EventArgs e)
         {
+            XmlConfigurator.Configure(new System.IO.FileInfo("log4net.config"));
+            string[] paths = {
+            @"鐢熶骇鏃ュ織\Run",
+            @"鐢熶骇鏃ュ織\Debug",
+            @"鐢熶骇鏃ュ織\Error",
+            @"鐢熶骇鏃ュ織\Fatal",
+            @"鐢熶骇鏃ュ織\Warn",
+            };
+            foreach (string path in paths)
+            {
+                EnsureDirectory(path);
+            }
             if (!LB_SmartVision.Tool.Tool.ReadStringConfig("鏁版嵁搴撳悕绉�", out string DateBaseName))
             {
                 DateBaseName = "浜у搧0";
@@ -417,72 +595,108 @@
             }
             LB_SmartVision.Tool.Tool.ReadStringConfig("User ID", out string User_ID);
             LB_SmartVision.Tool.Tool.ReadStringConfig("Password", out string Password);
-
             GlobalVar.strProductName = DateBaseName;
-
             //鍔犺浇閫氳
             foreach (BaseCommunicator com in GlobalVar.dicCommunicators.Values)
+            {
                 com.Disconnect();
+            }
             GlobalVar.dicCommunicators.Clear();
             if (LoadAllCommunicators(GlobalVar.allCommunicatorsConnectionStringPath))
+            {
                 LogInfo("閫氳鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("閫氳鍔犺浇澶辫触", LogInfoType.ERROR);
-
+            }
             //鍔犺浇鐩告満
             foreach (BaseCamera camera in GlobalVar.dicCameras.Values)
+            {
                 camera.Dispose();
+            }
             GlobalVar.dicCameras.Clear();
             if (LoadAllCameras(GlobalVar.allCamerasConnectionStringPath))
+            {
                 LogInfo("鐩告満鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("鐩告満鍔犺浇澶辫触", LogInfoType.ERROR);
-
-            //蹇呴』鍏堝姞杞界浉鏈哄拰閫氳绔彛,鍥犱负娴佺▼鍔犺浇杩囩▼涓細鐢ㄥ埌鐩告満鍜岄�氳鍙�
-
+            }
             //鍔犺浇鍏ㄥ眬鍙橀噺
             IProcess.dicGlobalVars.Clear();
             if (LoadAllProcessVars(GlobalVar.allProcessVarsPath))
+            {
                 LogInfo("鍏ㄥ眬鍙橀噺鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("鍏ㄥ眬鍙橀噺鍔犺浇澶辫触", LogInfoType.ERROR);
-
+            }
+            GlobalVar.dicMotionControlData.Clear();
+            if (LoadMotionControlDatas(GlobalVar.allMotionControlDataPath))
+            {
+                LogInfo("杩愬姩鎺у埗鍙傛暟鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
+            else
+            {
+                LogInfo("杩愬姩鎺у埗鍙傛暟鍔犺浇澶辫触", LogInfoType.ERROR);
+            }
             //鍔犺浇娴佺▼
             GlobalVar.dicProcesses.Clear();
             if (LoadAllProcess(GlobalVar.allProcessConnectionStringPath))
+            {
                 LogInfo("娴佺▼鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("娴佺▼鍔犺浇澶辫触", LogInfoType.ERROR);
-
+            }
             //鍔犺浇瑙﹀彂璁剧疆
             if (LoadAllProcessSetting(GlobalVar.allProcessSettingStringPath))
+            {
                 LogInfo("娴佺▼璁剧疆鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("娴佺▼璁剧疆鍔犺浇澶辫触", LogInfoType.ERROR);
+            }
 
             //鍔犺浇娴佺▼甯冨眬
             GlobalVar.dicLayout.Clear();
             if (LoadAllLayout(GlobalVar.allLayoutPath))
+            {
                 LogInfo("娴佺▼甯冨眬鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("娴佺▼甯冨眬鍔犺浇澶辫触", LogInfoType.ERROR);
+            }
 
             //鍔犺浇娴佺▼琛ㄦ牸
             GlobalVar.dicCsvSetting.Clear();
             if (LoadAllCsv(GlobalVar.allCsvPath))
+            {
                 LogInfo("娴佺▼琛ㄦ牸鍔犺浇鎴愬姛", LogInfoType.PASS);
+            }
             else
+            {
                 LogInfo("娴佺▼琛ㄦ牸鍔犺浇澶辫触", LogInfoType.ERROR);
+            }
 
             //鏄剧ず鎵�鏈変骇鍝�
             com_ProductName.Items.Clear();
             LB_SmartVision.Tool.Tool.ReadStringConfig("浜у搧鍒楄〃", out string Products);
             List<string> lstProduct = (Products.Split(',')).ToList();
             foreach (string DatabaseName in lstProduct)
+            {
                 com_ProductName.Items.Add(DatabaseName);
+            }
             com_ProductName.Items.Add("鏂板");
-
             com_ProductName.Text = GlobalVar.strProductName;
+            this.WindowState = FormWindowState.Maximized;
+            DatabaseRecordProductDataHelper.InitializeDatabase();
         }
 
         public void SaveAllSetting()
@@ -494,6 +708,54 @@
             SaveAllProcessSetting();
             SaveAllLayout();
             SaveAllCsv();
+            SaveMotionControlDatas();
+        }
+        public bool LoadMotionControlDatas(string alMotionControlDataPath)
+        {
+            try
+            {
+                GlobalVar.dicMotionControlData = ConfigManager<ConcurrentDictionary<string, ConcurrentDictionary<string, RecordMotionControlData>>>.LoadConfig<ConcurrentDictionary<string, ConcurrentDictionary<string, RecordMotionControlData>>>(alMotionControlDataPath);
+            }
+            catch
+            {
+                return false;
+            }
+            return true;
+        }
+        public bool SaveMotionControlDatas()
+        {
+            try
+            {
+                ConcurrentDictionary<string, List<string>> removeCameraSN = new ConcurrentDictionary<string, List<string>>();
+                foreach (var item in GlobalVar.dicMotionControlData.Keys)
+                {
+                    List<string> list = new List<string>();
+                    foreach (var itemSN in GlobalVar.dicMotionControlData[item].Keys)
+                    {
+                        if (!GlobalVar.dicCameras.Keys.Contains(itemSN))
+                        {
+                            list.Add(itemSN);
+                        }
+                    }
+                    if (list.Count > 0)
+                    {
+                        removeCameraSN.TryAdd(item, list);
+                    }
+                }
+                foreach (var item in removeCameraSN.Keys)
+                {
+                    foreach (var itemSN in removeCameraSN[item])
+                    {
+                        GlobalVar.dicMotionControlData[item].Keys.Remove(itemSN);
+                    }
+                }
+                ConfigManager<ConcurrentDictionary<string, ConcurrentDictionary<string, RecordMotionControlData>>>.SaveConfig<ConcurrentDictionary<string, ConcurrentDictionary<string, RecordMotionControlData>>>(GlobalVar.dicMotionControlData, GlobalVar.allMotionControlDataPath);
+            }
+            catch
+            {
+                return false;
+            }
+            return true;
         }
 
         public bool LoadAllCameras(string allCamerasConnectionStringPath)
@@ -512,7 +774,6 @@
                 strJson = streamReader.ReadToEnd();
                 streamReader.Close();
             }
-
             GlobalVar.allCamerasConnectionString = JsonConvert.DeserializeObject<ConcurrentDictionary<string, string>>(strJson);
             if (GlobalVar.allCamerasConnectionString == null)
             {
@@ -526,18 +787,23 @@
                 switch (brand)
                 {
                     case CameraBrand.HRCamera:
-                        //camera = new HRCamera();
-                        break;
+                        {
+                            camera = new HRCamera();
+                            break;
+                        }
                     case CameraBrand.LBCamera:
-                        //camera = new LBCamera();
-                        break;
+                        {
+                            camera = new LBCamera();
+                            break;
+                        }
                     default:
-                        MessageBox.Show($"[{CameraConnectionString.Key}]鍝佺墝涓嶆敮鎸�!", "寮傚父");
-                        continue;
+                        {
+                            MessageBox.Show($"[{CameraConnectionString.Key}]鍝佺墝涓嶆敮鎸�!", "寮傚父");
+                            continue;
+                        }
                 }
-
                 camera.SN = CameraConnectionString.Key;
-                if (!camera.InitDevice(CameraConnectionString.Key, this.Handle))
+                if (!camera.InitDevice(CameraConnectionString.Key, IntPtr.Zero))
                 {
                     LogInfo($"鍒濆鍖栫浉鏈篬{CameraConnectionString.Key}]澶辫触", LogInfoType.ERROR);
                     if (camera != null)
@@ -563,8 +829,9 @@
                     string CameraBrand = item.Value.Brand.ToString();//"1111"
 
                     if (string.IsNullOrEmpty(CameraSN) || string.IsNullOrEmpty(CameraBrand))
+                    {
                         break;
-
+                    }
                     GlobalVar.allCamerasConnectionString.TryAdd(CameraSN, CameraBrand);
                 }
                 var settings = new JsonSerializerSettings
@@ -629,61 +896,121 @@
                 {
                     string CommunicatorName = CommunicatorConnectionString.Key;
                     string CommunicatorAddress = CommunicatorConnectionString.Value;
-
-                    // 瀹氫箟姝e垯琛ㄨ揪寮忎互鎻愬彇鍗忚銆両P 鍦板潃鍜岀鍙�
-                    //1.    \((.*?)\)锛歕(鍜� \) 鏄敤浜庡尮閰嶆嫭鍙风殑杞箟瀛楃銆�
-                    //      (.*?) 鏄竴涓潪璐┆鐨勫尮閰嶏紝鐢ㄦ潵鍖归厤绫诲悕锛圡yProcesses.Communicators.TCPServer 鎴� MyProcesses.Communicators.UARTPort锛夈��
-                    //2.    ([^:] +)锛氬尮閰嶅啋鍙蜂箣鍓嶇殑閮ㄥ垎锛屽嵆鍦板潃锛�127.0.0.1 鎴� COM5锛夈�傝繖閲屼娇鐢ㄤ簡[^:] 鏉ュ尮閰嶉櫎浜嗗啋鍙蜂箣澶栫殑浠绘剰瀛楃銆�
-                    //3.    (\d +) 锛氬尮閰嶇鍙e彿锛岀‘淇濆畠鍖归厤涓�涓垨澶氫釜鏁板瓧銆�
-
-                    string pattern = @"^\((?<ClassName>[^)]+)\)\[(?<IP>[^]]+)\]\[(?<PORT>[^]]+)\]$";
-                    Match match = Regex.Match(CommunicatorAddress, pattern);
-
-                    if (match.Success)
+                    if (!string.IsNullOrEmpty(CommunicatorAddress) && CommunicatorAddress.Contains("SiemensLBS7"))
                     {
-                        string ClassName = match.Groups["ClassName"].Value;   // "TCP"
-                        string IP = match.Groups["IP"].Value;          // "127.0.0.1"
-                        string PORT = match.Groups["PORT"].Value;        // "1111"
+                        // 瀹氫箟姝e垯琛ㄨ揪寮忎互鎻愬彇鍗忚銆両P 鍦板潃鍜岀鍙�
+                        // 鏇存柊姝e垯浠ユ敮鎸佸彲閫夌殑鏁版嵁绫诲瀷瀛楁
+                        string pattern = @"^\((?<ClassName>[^)]+)\)\[(?<IP>[^]]+)\]\[(?<Slot>[^]]+)\]\[(?<CpuType>[^]]+)\]\[(?<PlcAddress>[^]]+)\](?:\[(?<DataType>[^]]+)\])?$";
+                        Match match = Regex.Match(CommunicatorAddress, pattern);
 
-                        if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(PORT))
-                            break;
-
-                        //鍒╃敤鍙嶅皠鍒涘缓瀹炰緥
-                        Type type = IProcess.GetExecutingAssembly().GetType(ClassName);
-                        if (type == null)
+                        if (match.Success)
                         {
-                            Debug.WriteLine("Class not found.");
-                            return false;
-                        }
-                        var Communicator = Activator.CreateInstance(type, CommunicatorName) as BaseCommunicator;
+                            string ClassName = match.Groups["ClassName"].Value;   // "TCP"
+                            string IP = match.Groups["IP"].Value;          // "127.0.0.1"
+                            string Slot = match.Groups["Slot"].Value;        // "1111"
+                            string CpuType = match.Groups["CpuType"].Value;
+                            string PlcAddress = match.Groups["PlcAddress"].Value;
+                            string DataType = match.Groups["DataType"].Success ? match.Groups["DataType"].Value : "String";
 
-                        if (Communicator == null)
-                        {
-                            Debug.WriteLine("BaseCommunicator not found.");
-                            return false;
-                        }
+                            if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(Slot) || string.IsNullOrEmpty(CpuType) || string.IsNullOrEmpty(PlcAddress))
+                                break;
 
-                        //TCP瀹㈡埛绔渶鍚庡啀杩炴帴
-                        if (Communicator is TCPClient)
-                        {
-                            clientsCommunicatorsConnectionString.TryAdd(CommunicatorConnectionString.Key, CommunicatorConnectionString.Value);
-                            continue;
-                        }
+                            //鍒╃敤鍙嶅皠鍒涘缓瀹炰緥
+                            Type type = IProcess.GetExecutingAssembly().GetType(ClassName);
+                            if (type == null)
+                            {
+                                Debug.WriteLine("Class not found.");
+                                return false;
+                            }
+                            var Communicator = Activator.CreateInstance(type, CommunicatorName) as BaseCommunicator;
 
-                        Communicator.CommunicatorConnections.Add("鍦板潃", IP);
-                        Communicator.CommunicatorConnections.Add("绔彛", PORT);
-                        Communicator.CommunicatorName = CommunicatorName;
-                        if (!Communicator.Connect())
-                            LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]澶辫触,鍘熷洜鏄瘂Communicator.Msg}", LogInfoType.ERROR);
+                            if (Communicator == null)
+                            {
+                                Debug.WriteLine("BaseCommunicator not found.");
+                                return false;
+                            }
+
+                            Communicator.CommunicatorConnections.Add("鍦板潃", IP);
+                            Communicator.CommunicatorConnections.Add("绔彛", Slot);
+                            Communicator.CommunicatorConnections.Add("鍨嬪彿", CpuType);
+                            Communicator.CommunicatorConnections.Add("鍙橀噺鍦板潃", PlcAddress);
+                            Communicator.CommunicatorConnections.Add("鏁版嵁绫诲瀷", DataType);
+                            Communicator.CommunicatorName = CommunicatorName;
+                            if (!Communicator.Connect())
+                            {
+                                LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]澶辫触,鍘熷洜鏄瘂Communicator.Msg}", LogInfoType.ERROR);
+                            }
+                            else
+                            {
+                                LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]鎴愬姛", LogInfoType.PASS);
+                            }
+                            GlobalVar.dicCommunicators.TryAdd(CommunicatorName, Communicator);
+                        }
                         else
-                            LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]鎴愬姛", LogInfoType.PASS);
-                        GlobalVar.dicCommunicators.TryAdd(CommunicatorName, Communicator);
+                        {
+                            Debug.WriteLine("No match found.");
+                        }
                     }
                     else
                     {
-                        Debug.WriteLine("No match found.");
-                    }
+                        // 瀹氫箟姝e垯琛ㄨ揪寮忎互鎻愬彇鍗忚銆両P 鍦板潃鍜岀鍙�
+                        //1.    \((.*?)\)锛歕(鍜� \) 鏄敤浜庡尮閰嶆嫭鍙风殑杞箟瀛楃銆�
+                        //      (.*?) 鏄竴涓潪璐┆鐨勫尮閰嶏紝鐢ㄦ潵鍖归厤绫诲悕锛圡yProcesses.Communicators.TCPServer 鎴� MyProcesses.Communicators.UARTPort锛夈��
+                        //2.    ([^:] +)锛氬尮閰嶅啋鍙蜂箣鍓嶇殑閮ㄥ垎锛屽嵆鍦板潃锛�127.0.0.1 鎴� COM5锛夈�傝繖閲屼娇鐢ㄤ簡[^:] 鏉ュ尮閰嶉櫎浜嗗啋鍙蜂箣澶栫殑浠绘剰瀛楃銆�
+                        //3.    (\d +) 锛氬尮閰嶇鍙e彿锛岀‘淇濆畠鍖归厤涓�涓垨澶氫釜鏁板瓧銆�
 
+                        string pattern = @"^\((?<ClassName>[^)]+)\)\[(?<IP>[^]]+)\]\[(?<PORT>[^]]+)\]$";
+                        Match match = Regex.Match(CommunicatorAddress, pattern);
+
+                        if (match.Success)
+                        {
+                            string ClassName = match.Groups["ClassName"].Value;   // "TCP"
+                            string IP = match.Groups["IP"].Value;          // "127.0.0.1"
+                            string PORT = match.Groups["PORT"].Value;        // "1111"
+
+                            if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(PORT))
+                                break;
+
+                            //鍒╃敤鍙嶅皠鍒涘缓瀹炰緥
+                            Type type = IProcess.GetExecutingAssembly().GetType(ClassName);
+                            if (type == null)
+                            {
+                                Debug.WriteLine("Class not found.");
+                                return false;
+                            }
+                            var Communicator = Activator.CreateInstance(type, CommunicatorName) as BaseCommunicator;
+
+                            if (Communicator == null)
+                            {
+                                Debug.WriteLine("BaseCommunicator not found.");
+                                return false;
+                            }
+
+                            //TCP瀹㈡埛绔渶鍚庡啀杩炴帴
+                            if (Communicator is TCPClient)
+                            {
+                                clientsCommunicatorsConnectionString.TryAdd(CommunicatorConnectionString.Key, CommunicatorConnectionString.Value);
+                                continue;
+                            }
+
+                            Communicator.CommunicatorConnections.Add("鍦板潃", IP);
+                            Communicator.CommunicatorConnections.Add("绔彛", PORT);
+                            Communicator.CommunicatorName = CommunicatorName;
+                            if (!Communicator.Connect())
+                            {
+                                LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]澶辫触,鍘熷洜鏄瘂Communicator.Msg}", LogInfoType.ERROR);
+                            }
+                            else
+                            {
+                                LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]鎴愬姛", LogInfoType.PASS);
+                            }
+                            GlobalVar.dicCommunicators.TryAdd(CommunicatorName, Communicator);
+                        }
+                        else
+                        {
+                            Debug.WriteLine("No match found.");
+                        }
+                    }
                 }
 
                 //TCP瀹㈡埛绔渶鍚庤繛鎺�
@@ -708,7 +1035,9 @@
                         string PORT = match.Groups[3].Value;        // "1111"
 
                         if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(PORT))
+                        {
                             break;
+                        }
 
                         //鍒╃敤鍙嶅皠鍒涘缓瀹炰緥
                         Type type = IProcess.GetExecutingAssembly().GetType(ClassName);
@@ -729,10 +1058,13 @@
                         Communicator.CommunicatorConnections.Add("绔彛", PORT);
                         Communicator.CommunicatorName = CommunicatorName;
                         if (!Communicator.Connect())
+                        {
                             LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]澶辫触,鍘熷洜鏄瘂Communicator.Msg}", LogInfoType.ERROR);
+                        }
                         else
+                        {
                             LogInfo($"鍒濆鍖栭�氳鍙{CommunicatorName}]鎴愬姛", LogInfoType.PASS);
-
+                        }
                         GlobalVar.dicCommunicators.TryAdd(CommunicatorName, Communicator);
                     }
                     else
@@ -753,20 +1085,36 @@
             {
                 string strJson = string.Empty;
                 GlobalVar.allCommunicatorsConnectionString = new ConcurrentDictionary<string, string>();
-
                 foreach (var item in GlobalVar.dicCommunicators)
                 {
                     string ClassName = item.Value.GetType().FullName;// "TCP"
                     string IP = item.Value.CommunicatorConnections["鍦板潃"].ToString();//"127.0.0.1"
                     string PORT = item.Value.CommunicatorConnections["绔彛"].ToString();//"1111"
+                    if (!string.IsNullOrEmpty(ClassName) && ClassName.Contains("SiemensLBS7"))
+                    {
+                        string CpuType = item.Value.CommunicatorConnections["鍨嬪彿"].ToString();
+                        string PlcAddress = item.Value.CommunicatorConnections["鍙橀噺鍦板潃"].ToString();
+                        string DataType = item.Value.CommunicatorConnections.Contains("鏁版嵁绫诲瀷") ?
+                                          item.Value.CommunicatorConnections["鏁版嵁绫诲瀷"].ToString() : "String";
 
-                    if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(PORT))
-                        break;
-
-                    string CommunicatorConnectionString = $"({ClassName})[{IP}][{PORT}]";
-                    GlobalVar.allCommunicatorsConnectionString.TryAdd(item.Key, CommunicatorConnectionString);
+                        if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(PORT) || string.IsNullOrEmpty(CpuType) || string.IsNullOrEmpty(PlcAddress))
+                        {
+                            break;
+                        }
+                        string CommunicatorConnectionString = $"({ClassName})[{IP}][{PORT}][{CpuType}][{PlcAddress}][{DataType}]";
+                        GlobalVar.allCommunicatorsConnectionString.TryAdd(item.Key, CommunicatorConnectionString);
+                    }
+                    else
+                    {
+                        if (string.IsNullOrEmpty(ClassName) || string.IsNullOrEmpty(IP) || string.IsNullOrEmpty(PORT))
+                        {
+                            break;
+                        }
+                        string CommunicatorConnectionString = $"({ClassName})[{IP}][{PORT}]";
+                        GlobalVar.allCommunicatorsConnectionString.TryAdd(item.Key, CommunicatorConnectionString);
+                    }
+                    GlobalVar.dicCommunicators[item.Key].ClassName = ClassName;
                 }
-
                 var settings = new JsonSerializerSettings
                 {
                     Formatting = Formatting.Indented,
@@ -790,6 +1138,11 @@
                     { }
                 }
                 File.WriteAllText(GlobalVar.allCommunicatorsConnectionStringPath, strJson, Encoding.UTF8);
+                foreach (var item in GlobalVar.dicCommunicators)
+                {
+                    string ClassName = item.Value.GetType().FullName;// "TCP"
+                }
+                ConfigManager<ObservableConcurrentDictionary<string, BaseCommunicator>>.SaveConfig<ObservableConcurrentDictionary<string, BaseCommunicator>>(GlobalVar.dicCommunicators, GlobalVar.strApplicationPath + "\\鎵�鏈変骇鍝乗\" + GlobalVar.strProductName + "\\dicCommunicators.json");
                 return true;
             }
             catch { return false; }
@@ -817,17 +1170,19 @@
                 List<string> lstProcessName = JsonConvert.DeserializeObject<List<string>>(strJson);
 
                 if (lstProcessName == null)
+                {
                     return false;
-
+                }
                 // 浣跨敤鏂瑰紡
                 var sortedKeys = lstProcessName
                     .OrderBy(k => k, new NaturalStringComparer())
                     .ToList();
                 GlobalVar.dicProcesses.Clear();
                 foreach (var ProcessName in sortedKeys)
+                {
                     GlobalVar.dicProcesses.TryAdd(ProcessName
                         , new ProcessRunBll(ProcessName, GlobalVar.dicCameras, GlobalVar.dicCommunicators));
-
+                }
                 return true;
             }
             catch { return false; }
@@ -864,7 +1219,9 @@
                 foreach (var process in GlobalVar.dicProcesses.Values)
                 {
                     if (!process.Save(out string msg))
+                    {
                         LogInfo($"娴佺▼[{process.Name}]淇濆瓨澶辫触,鍘熷洜:{msg}", LogInfoType.NOSHOW);
+                    }
                 }
 
                 try
@@ -957,7 +1314,6 @@
 
                 File.WriteAllText(GlobalVar.allLayoutPath, strJson, Encoding.UTF8);
                 LogInfo($"鍏ㄥ眬甯冨眬淇濆瓨鎴愬姛", LogInfoType.INFO);
-
                 return true;
             }
             catch { return false; }
@@ -970,6 +1326,7 @@
                 if (!File.Exists(allLayoutPath))
                 {
                     Debug.WriteLine("鏂囦欢涓嶅瓨鍦ㄥ垱寤虹┖鏂囦欢");
+                    AsyncLogHelper.Info("鏂囦欢涓嶅瓨鍦ㄥ垱寤虹┖鏂囦欢");
                     // 鑾峰彇涓嶅甫鏂囦欢鍚嶇殑鐩綍璺緞
                     string directoryPath = Path.GetDirectoryName(allLayoutPath);
                     SaveAllLayout();
@@ -993,5 +1350,373 @@
             }
             catch { return false; }
         }
+
+        private void btn_GlobalVar_Click(object sender, EventArgs e)
+        {
+            GlobalVarForm globalVarForm = new GlobalVarForm(GlobalVar.allProcessVarsPath);
+            globalVarForm.ShowDialog();
+        }
+
+        private void btn_Login_Click(object sender, EventArgs e)
+        {
+            //this.Hide();
+            //MainWindow.InstanceLoginandConfirmation().ShowDialog();
+            //if (!MainWindow.InstanceLoginandConfirmation().isQuit && MainWindow.InstanceLoginandConfirmation().correctUser)
+            //{
+            //    MainWindow.InstanceLoginandConfirmation().closeLoginFrm();
+            //    if (UserManager.Instance.CurrentUser.EmployeePermission == UserPermission.Operator)
+            //    {
+            //        //鎿嶄綔鍛樻潈闄愮晫闈�
+            //    }
+            //    else if (UserManager.Instance.CurrentUser.EmployeePermission == UserPermission.Engineer)
+            //    {
+            //        //鎶�鏈憳鏉冮檺鐣岄潰
+            //    }
+            //    else if (UserManager.Instance.CurrentUser.EmployeePermission == UserPermission.Administrator)
+            //    {
+            //        //绠$悊鍛樻潈闄愮晫闈�
+            //    }
+            //    this.Show();
+            //}
+        }
+
+        private void com_ProductName_SelectedValueChanged(object sender, EventArgs e)
+        {
+            if (com_ProductName.SelectedItem == null || com_ProductName.SelectedItem?.ToString() == GlobalVar.strProductName)
+            {
+                return;
+            }
+            if (com_ProductName.SelectedItem?.ToString() == "鏂板")
+            {
+                using (CreateProductForm createDatabaseForm = new CreateProductForm())
+                {
+                    createDatabaseForm.ShowDialog();
+                }
+            }
+            else
+            {
+                //鍙樻洿鍓嶄繚瀛樼幇鏈夐厤缃�
+                SaveAllSetting();
+                LogInfo($"浜у搧浠巤GlobalVar.strProductName}鍒囨崲{com_ProductName.SelectedItem?.ToString()}", LogInfoType.WARN);
+                //Tool.WriteConfig("鏁版嵁搴撳悕绉�", com_ProductName.SelectedItem?.ToString());
+                GlobalVar.strProductName = com_ProductName.SelectedItem?.ToString();
+                foreach (BaseCamera camera in GlobalVar.dicCameras.Values)
+                {
+                    camera.TriggerRunMessageReceived -= TriggerRunMessageReceived;
+                    camera.Dispose();
+                }
+                GlobalVar.dicCameras.Clear();
+                foreach (BaseCommunicator communicator in GlobalVar.dicCommunicators.Values)
+                {
+                    communicator.TriggerRunMessageReceived -= TriggerRunMessageReceived;
+                    communicator.Disconnect();
+                }
+                GlobalVar.dicCommunicators.Clear();
+                //淇濆瓨瀹岀幇鏈夐厤缃悗鏂紑鎵�鏈変簨浠�
+                foreach (var Process in GlobalVar.dicProcesses.Values)
+                {
+                    Process.LogInfo -= LogInfo;
+                }
+                GlobalVar.dicProcesses.Clear();
+                //閲嶆柊鍔犺浇閰嶇疆
+                this.VisionForm_Load(sender, e);
+            }
+        }
+        private void TriggerRunMessageReceived(string name, string msg)
+        {
+            if (msg == null || msg.Trim('\0', '\r', '\n', ' ', '\uFEFF') == "" || string.IsNullOrEmpty(msg))
+            {
+                return;
+            }
+            LogInfo(string.Format("閫氳[{0}]鎺ユ敹鍒扮殑娑堟伅\"{1}\"", name, msg), LogInfoType.INFO);
+            var matchedItems = GlobalVar.dicProcessSetting
+                .Where(item =>
+                {
+                    var value = item.Value;
+                    var triggerComm = value["瑙﹀彂閫氳"];
+                    var triggerChar = value["瑙﹀彂瀛楃"];
+
+                    return triggerComm != null && triggerComm.Equals(name) &&
+                           (string.IsNullOrEmpty(triggerChar?.ToString()) ||
+                            msg.StartsWith(triggerChar.ToString()));
+                })
+                .ToList(); // 閬垮厤閲嶅瀛楀吀璁块棶鍜岃绠辨搷浣�
+            if (matchedItems.Count <= 0)
+            {
+                return;
+            }
+            if (!ckb_AllowRun.Checked)
+            {
+                LogInfo(string.Format($"妫�鏌ュ埌鍙瑙﹀彂鐨勬祦绋�,褰撳墠涓嶄负杩愯妯″紡!"), LogInfoType.ERROR);
+                return;
+            }
+            GlobalVar.dicProcesses.Values.AsParallel().ForAll(v => v.bCompleted = false);
+            LogInfo(string.Format($"妫�鏌ュ埌鍙瑙﹀彂鐨勬祦绋�,娓呯┖鎵�鏈夋祦绋嬭繍琛屽畬鎴愭爣璁颁綅!"), LogInfoType.INFO);
+            Parallel.ForEach(matchedItems, item =>
+            {
+                string ProcessName = item.Value["娴佺▼鍚�"];
+                LogInfo($"娴佺▼[{ProcessName}]寮�濮嬭繍琛�", LogInfoType.INFO);
+                if (!GlobalVar.dicProcesses.ContainsKey(ProcessName))
+                {
+                    LogInfo(string.Format("娴佺▼[{0}]涓嶅瓨鍦�,璇锋鏌ユ祦绋嬭缃�", ProcessName), LogInfoType.ERROR);
+                    return;
+                }
+                ProcessRunBll RunBll = GlobalVar.dicProcesses[ProcessName];
+                if (RunBll == null || RunBll.bRuning)
+                {
+                    LogInfo(string.Format("娴佺▼[{0}]涓婃鏈繍琛屽畬鎴�,瑙﹀彂澶辫触", ProcessName)
+                        , LogInfoType.ERROR);
+                    return;
+                }
+                try
+                {
+                    bool result = false;
+                    string msg = string.Empty;
+                    int times = Convert.ToInt32(item.Value["閲嶆祴娆℃暟"].ToString());
+                    string ConnecResult = item.Value["鍏宠仈缁撴灉"];
+                    if (times < 0)
+                    {
+                        result = GlobalVar.dicProcesses[ProcessName].Run();
+                        msg = GlobalVar.dicProcesses[ProcessName].Msg;
+                        if (!(string.IsNullOrEmpty(ConnecResult) || ConnecResult.Trim() == "鏈叧鑱�"))
+                        {
+                            GlobalVar.dicProcesses[ProcessName].GetBooleanOutput(ConnecResult, out result);
+                            GlobalVar.dicProcesses[ProcessName].Result = result;
+                        }
+                        if (!result)
+                        {
+                            LogInfo($"娴佺▼[{ProcessName}]琚己鍒惰繍琛屾垚鍔�", LogInfoType.WARN);
+                            GlobalVar.dicProcesses[ProcessName].Result = true;
+                            result = true;
+                        }
+                    }
+                    else
+                    {
+                        while (times >= 0)
+                        {
+                            result = RunBll.Run();
+                            msg = RunBll.Msg;
+                            if (!(string.IsNullOrEmpty(ConnecResult) || ConnecResult.Trim() == "鏈叧鑱�"))
+                            {
+                                RunBll.GetBooleanOutput(ConnecResult, out result);
+                                RunBll.Result = result;
+                            }
+                            if (result)
+                            {
+                                break;
+                            }
+                            else if (!result && times > 0)
+                            {
+                                LogInfo(string.Format("娴佺▼[{0}]杩愯澶辫触閲嶆柊娴嬭瘯,鍓╀綑娆℃暟[{1}]", ProcessName, times), LogInfoType.WARN);
+                            }
+                            times--;
+                        }
+                    }
+                    string ConnectProcess = item.Value["鍏宠仈娴佺▼"];
+                    if (!(ConnectProcess == null || string.IsNullOrEmpty(ConnectProcess) || ConnectProcess.Trim() == ""))
+                    {
+                        //鐢ㄩ�楀彿鎴栬�呭垎鍙峰幓闂撮殧鍏宠仈娴佺▼
+                        string[] arrConnectProcess;
+                        if (ConnectProcess.Split(';').Length >= ConnectProcess.Split(',').Length)
+                        {
+                            arrConnectProcess = ConnectProcess.Split(';');
+                        }
+                        else
+                        {
+                            arrConnectProcess = ConnectProcess.Split(',');
+                        }
+                        foreach (string strConnectProcess in arrConnectProcess)
+                        {
+                            if (GlobalVar.dicProcesses.ContainsKey(strConnectProcess))
+                            {
+                                ProcessRunBll ConnectRunBll = GlobalVar.dicProcesses[strConnectProcess];
+                                int waitTime = 10;
+                                DateTime startTime = DateTime.Now;
+                                while ((DateTime.Now - startTime).TotalSeconds < waitTime
+                                && (ConnectRunBll.bRuning || !ConnectRunBll.bCompleted))
+                                {
+                                    LogInfo(string.Format("鍏宠仈娴佺▼[{0}]鏈繍琛屽畬鎴�,鍓╀綑绛夊緟[{1}]s", strConnectProcess, (waitTime - ((DateTime.Now - startTime).TotalSeconds)))
+                                        , LogInfoType.NOSHOW);
+                                    Thread.Sleep(1000);
+                                    continue;
+                                }
+                                if (ConnectRunBll.bRuning || !ConnectRunBll.bCompleted)
+                                {
+                                    GlobalVar.dicProcesses[ProcessName].Msg = string.Format("娴佺▼[{0}]鏈繍琛屽畬鎴�", ProcessName);
+                                    LogInfo(string.Format("鍏宠仈娴佺▼[{0}]鏈繍琛屽畬鎴�", strConnectProcess), LogInfoType.ERROR);
+                                    result = false;
+                                    break;
+                                }
+                                else if (!ConnectRunBll.bRuning && ConnectRunBll.bCompleted)
+                                {
+                                    LogInfo(string.Format("鍏宠仈娴佺▼[{0}]杩愯瀹屾垚", strConnectProcess), LogInfoType.INFO);
+                                }
+                                result &= ConnectRunBll.Result;
+                                if (!ConnectRunBll.Result)
+                                {
+                                    LogInfo($"娴佺▼[{ProcessName}]鐨勫叧鑱旀祦绋媅{strConnectProcess}]杩愯澶辫触", LogInfoType.ERROR);
+                                    msg = $"鍏宠仈娴佺▼[{strConnectProcess}]杩愯澶辫触";
+                                }
+                            }
+                        }
+                    }
+                    LogInfo(result ? $"娴佺▼[{ProcessName}]杩愯鎴愬姛" : $"娴佺▼[{ProcessName}]杩愯澶辫触,鍘熷洜鏄瘂msg}", result ? LogInfoType.PASS : LogInfoType.ERROR);
+                    string SendComName = result ? item.Value["鎴愬姛閫氳"] : item.Value["澶辫触閫氳"];
+                    string SendMsg = result ? item.Value["鎴愬姛瀛楃"] : item.Value["澶辫触瀛楃"];
+                    if (GlobalVar.dicCommunicators.ContainsKey(SendComName) && (!string.IsNullOrEmpty(SendMsg) || SendMsg.Trim() != ""))
+                    {
+                        GlobalVar.dicCommunicators[SendComName].SendMessage(SendMsg);
+                        LogInfo(string.Format("鍙戦�佺粰[{0}]浜嗘秷鎭痋"{1}\"", SendComName, SendMsg), LogInfoType.INFO);
+                    }
+                }
+                catch (Exception ex)
+                {
+                    LogInfo(string.Format("娴佺▼[{0}]杩愯鍙戠敓浜嗘剰澶�,鍘熷洜鏄�:{1}", ProcessName, ex.Message + $"銆恵ex.StackTrace}銆�"), LogInfoType.ERROR);
+                    RunBll.Result = false;
+                    RunBll.Msg = $"[鎰忓]{ex.Message}";
+                }
+                finally
+                {
+                    #region 浠嶳unSettingPage鍜孡ayout涓幏鍙栨槸鍚︿繚瀛樺浘鐗�
+                    string strImageType = "jpeg";
+                    bool bSaveRunImage = false;
+                    bool bSaveResultImage = false;
+                    long lImageQuality = 100L;
+                    //ckbSaveRunImage
+                    if (GlobalVar.ControlStates.TryGetValue("ckbSaveRunImage_CheckBox", out object oSaveRunImage))
+                    {
+                        if (oSaveRunImage != null && oSaveRunImage is bool)
+                        {
+                            bSaveRunImage = (bool)oSaveRunImage;
+                        }
+                    }
+                    //ckbSaveResultImage
+                    if (GlobalVar.ControlStates.TryGetValue("ckbSaveResultImage_CheckBox", out object oSaveResultImage))
+                    {
+                        if (oSaveResultImage != null && oSaveResultImage is bool)
+                        {
+                            bSaveResultImage = (bool)oSaveResultImage;
+                        }
+                    }
+                    //txtImageQuality
+                    if (GlobalVar.ControlStates.TryGetValue("txtImageQuality_TextBox", out object oImageQuality))
+                    {
+                        if (oImageQuality != null && oImageQuality is string)
+                        {
+                            lImageQuality = Convert.ToInt64((string)oImageQuality);
+                        }
+                    }
+                    //cmbImageType
+                    if (GlobalVar.ControlStates.TryGetValue("cmbImageType_ComboBox", out object oImageType))
+                    {
+                        try
+                        {
+                            // 鍔ㄦ�佽В鏋怌omboBox鏁版嵁
+                            var json = JsonConvert.SerializeObject(oImageType);
+                            var comboData = JsonConvert.DeserializeAnonymousType(json, new
+                            {
+                                Items = new List<object>(),
+                                SelectedIndex = 0
+                            });
+
+                            if (comboData != null && comboData.Items.Count > 0)
+                            {
+                                strImageType = comboData.Items[comboData.SelectedIndex].ToString();
+                            }
+                        }
+                        catch { }
+                    }
+                    // 鐢熸垚鍥剧墖骞舵樉绀哄埌鎺т欢涓�
+                    HObject InputImage = null;
+                    HObject RecordImage = null;
+
+                    foreach (var layout in GlobalVar.dicLayout.Values
+                                .Where(layout => layout.ProcessName == ProcessName)
+                                .ToList())
+                    {
+                        string title = layout.Title;
+                        string strImagePath = layout.SaveImageDir;
+                        if (!AllProcessesPages.dicProcessControls.ContainsKey(title))
+                        {
+                            continue;
+                        }
+                        RunBll.GetImage(layout, out InputImage, out RecordImage);
+                        AllProcessesPages.dicProcessControls[title].ShowHoImage(RecordImage);
+                        if (!string.IsNullOrEmpty(layout.SaveImageDir))
+                        {
+                            string fileNameHead = layout.SaveImageHead;
+                            string result = Regex.Replace(fileNameHead, @"\{[^}]+\}", match =>
+                            {
+                                // 鍘婚櫎{}鍙繚鐣欐嫭鍙峰唴鐨勫唴瀹�
+                                string content = match.Value;
+                                content = content.Trim('{', '}'); // 鍘婚櫎棣栧熬鐨剓}
+
+                                RunBll.GetStringOutput(content, out string str);
+                                return str;
+                            });
+                            string fileName = $"{result}-[{DateTime.Now.ToString("HH.mm.ss.ffff")}]";
+                            // 浣跨敤姝e垯琛ㄨ揪寮忔浛鎹㈡墍鏈夐潪娉曞瓧绗�
+                            string invalidChars = Regex.Escape(new string(Path.GetInvalidFileNameChars()));
+                            string pattern = $"[{invalidChars}]";
+                            fileName = Regex.Replace(fileName, pattern, "-");
+                            strImagePath = Regex.Replace(strImagePath, @"\{[^}]+\}", match =>
+                            {
+                                // 鍘婚櫎{}鍙繚鐣欐嫭鍙峰唴鐨勫唴瀹�
+                                string content = match.Value;
+                                content = content.Trim('{', '}'); // 鍘婚櫎棣栧熬鐨剓}
+                                RunBll.GetStringOutput(content, out string str);
+                                return str;
+                            });
+                            if (bSaveRunImage)
+                            {
+                                // 鏈�鍚庝竴绾х洰褰曞繀椤讳负骞存湀鏃�,浼氭牴鎹椂闂存潵鍒犻櫎鏃у浘鐗�
+                                string directoryPath = Path.Combine(strImagePath, $"{ProcessName}\\鍘熷浘\\{RunBll.Result}\\{DateTime.Now.ToString("yyyyMMdd")}\\");
+                                LB_SmartVision.Tool.Tool.AddRealImage(InputImage, directoryPath, fileName, strImageType, lImageQuality);
+                            }
+                            if (bSaveResultImage)
+                            {
+                                // 鏈�鍚庝竴绾х洰褰曞繀椤讳负骞存湀鏃�,浼氭牴鎹椂闂存潵鍒犻櫎鏃у浘鐗�
+                                string directoryPath = Path.Combine(strImagePath, $"{ProcessName}\\鎴浘\\{RunBll.Result}\\{DateTime.Now.ToString("yyyyMMdd")}\\");
+                                LB_SmartVision.Tool.Tool.AddRealImage(RecordImage, directoryPath, fileName, "jpg", 50L);
+                            }
+                        }
+                    }
+                    foreach (var csv in GlobalVar.dicCsvSetting.Values
+                                .Where(csv => csv.ProcessName == ProcessName)
+                                .ToList())
+                    {
+                        if (RunBll.GetCsv(csv
+                            , out List<string> DataTitle, out Dictionary<string, object> ResultData))
+                        {
+                            string filePath = Path.Combine(GlobalVar.strPathCsv, $"{ProcessName}.csv");
+                            LB_SmartVision.Tool.Tool.SaveData(filePath, DataTitle, ResultData);
+                        }
+                    }
+                    #endregion
+                }
+            });
+        }
+
+        private void VisionForm_FormClosing(object sender, FormClosingEventArgs e)
+        {
+            SaveAllSetting();
+            if (MessageBox.Show("鏄惁鍏抽棴杞欢锛�", "鎻愮ず", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) != DialogResult.OK)//
+            {
+                e.Cancel = true;
+                return;
+            }
+            //鍏抽棴绐椾綋閲婃斁璧勬簮
+            AsyncLogHelper.Dispose();
+            foreach (BaseCamera camera in GlobalVar.dicCameras.Values)
+            {
+                camera.Dispose();
+            }
+            foreach (BaseCommunicator communicator in GlobalVar.dicCommunicators.Values)
+            {
+                communicator.Disconnect();
+            }
+            FormClosing -= VisionForm_FormClosing;
+        }
     }
 }
+

--
Gitblit v1.9.3