C3031
2026-01-30 0ab0fde3216783ee2694d8d4bfbb94237e25a4bb
新增了图像增强算法及图像滤波算法
已修改20个文件
已添加8个文件
3012 ■■■■■ 文件已修改
LB_SmartVision/Forms/Pages/ProcessPage/ProcessControl.Designer.cs 4 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVision/Forms/Pages/ProcessPage/ProcessControl.cs 14 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVision/ProcessRun/ProcessContext.cs 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVision/ProcessRun/ProcessRunBll.cs 4 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVision/VisionForm.Designer.cs 140 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVision/VisionForm.cs 122 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVisionCommon/FilterData.cs 80 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVisionCommon/FilterManager.cs 152 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVisionCommon/ImageEnhancementData.cs 75 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVisionCommon/ImageEnhancementManager.cs 155 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionFlowNode/FlowPanel.cs 4 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionFlowNode/IFlowContext.cs 8 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/BaseAlgorithm/TAlgorithm.cs 100 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HBlobTool/HBlobTool.cs 11 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HBlobTool/HBlobToolEdit.cs 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterTool.cs 229 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterToolEdit.Designer.cs 613 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterToolEdit.cs 611 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterToolEdit.resx 129 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindCode2dTool/HFindCode2dTool.cs 24 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindLineTool/HFindLineTool.cs 28 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindModelTool/HFindModelTool.cs 22 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindMultiModelTool/HFindMultiModelTool.cs 24 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HImageEnhancementTool/HImageEnhancementTool.cs 95 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HImageEnhancementTool/HImageEnhancementToolEdit.Designer.cs 101 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/Alogrithms/Halcon/2D/HImageEnhancementTool/HImageEnhancementToolEdit.cs 194 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/ProcessEditForm.Designer.cs 22 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_VisionProcesses/ProcessEditForm.resx 39 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
LB_SmartVision/Forms/Pages/ProcessPage/ProcessControl.Designer.cs
@@ -71,6 +71,7 @@
            btnRun.Size = new Size(93, 24);
            btnRun.Text = "单次运行";
            btnRun.ToolTipText = "单次运行";
            btnRun.Visible = false;
            btnRun.Click += btnRun_Click;
            // 
            // btnCircleRun
@@ -82,6 +83,7 @@
            btnCircleRun.Size = new Size(93, 24);
            btnCircleRun.Text = "连续运行";
            btnCircleRun.ToolTipText = "连续";
            btnCircleRun.Visible = false;
            btnCircleRun.Click += btnCircleRun_Click;
            // 
            // panel1
@@ -156,7 +158,7 @@
            BackColor = Color.FromArgb(32, 41, 50);
            Controls.Add(uiPanel1);
            Controls.Add(toolStrip1);
            Margin = new Padding(4, 4, 4, 4);
            Margin = new Padding(4);
            Name = "ProcessControl";
            Size = new Size(450, 287);
            Load += ProcessControl_Load;
LB_SmartVision/Forms/Pages/ProcessPage/ProcessControl.cs
@@ -10,6 +10,16 @@
    {
        UserHSmartWindowControl UserHSmartWindowControl = new UserHSmartWindowControl();
        public event ProcessRunBllRun OnProcessRunBllRun;
        private void onProcessRunBllRun()
        {
            if (OnProcessRunBllRun != null)
            {
                OnProcessRunBllRun();
            }
        }
        public string Title = string.Empty;
        public event Control_MouseDown event_MouseDown;
@@ -130,8 +140,8 @@
            if (isCircleRuning || ProcessRunBll.bRuning)
                ProcessRunBll.LogInfo($"{ProcessRunBll.Name}正在运行", LogInfoType.ERROR);
            ProcessRunBll.Run();
            //ProcessRunBll.Run();
            onProcessRunBllRun();
            msg = ProcessRunBll.Msg;
            return ProcessRunBll.Result;
        }
LB_SmartVision/ProcessRun/ProcessContext.cs
@@ -570,12 +570,20 @@
        [Node("相机取图", "取像工具", "Basic", "相机取图")]
        public void ç›¸æœºå–图(FlowNode node) { RunNodeAsync(node); }
        [Node("Halcon2D斑点工具", "Haclon2D工具", "Basic", "Halcon2D斑点工具")]
        [Node("Halcon2D斑点工具", "Halcon2D工具", "Basic", "Halcon2D斑点工具")]
        public void Halcon2D斑点工具(FlowNode node) { RunNodeAsync(node); }
        [Node("通讯模块", "通讯工具", "Basic", "通讯模块")]
        public void é€šè®¯æ¨¡å—(FlowNode node) { RunNodeAsync(node); }
        [Node("Halcon2D图像增强", "Halcon2D工具", "Basic", "Halcon2D图像增强")]
        public void Halcon2D图像增强(FlowNode node) { RunNodeAsync(node); }
        [Node("Halcon2D图像滤波", "Halcon2D工具", "Basic", "Halcon2D图像滤波")]
        public void Halcon2D图像滤波(FlowNode node) { RunNodeAsync(node); }
        #endregion
LB_SmartVision/ProcessRun/ProcessRunBll.cs
@@ -17,6 +17,8 @@
namespace LB_SmartVision.ProcessRun
{
    public delegate void ProcessRunBllRun();
    public class ProcessRunBll
    {
@@ -648,7 +650,7 @@
                    {
                        dicOutputsMapping.TryAdd(name, new List<string>());
                        dicOutputsMapping[name].Add(name + ".Outputs.Image");
                        //dicOutputsMapping[name].Add(name + ".Outputs.Record");
                        dicOutputsMapping[name].Add(name + ".Outputs.Record");
                        dicOutputsMapping[name].Add(name + ".Outputs.Result");
                        foreach (var item in process.Params.Outputs)
LB_SmartVision/VisionForm.Designer.cs
@@ -35,9 +35,11 @@
            materialTabControl = new MaterialSkin.Controls.MaterialTabControl();
            tlp_VisionMainOperator = new Sunny.UI.UITableLayoutPanel();
            ckb_AllowRun = new Sunny.UI.UICheckBox();
            btn_Login = new ReaLTaiizor.Controls.Button();
            btn_GlobalVar = new ReaLTaiizor.Controls.Button();
            com_ProductName = new ReaLTaiizor.Controls.AloneComboBox();
            btn_SingleRun = new Sunny.UI.UIButton();
            btn_Login = new Sunny.UI.UIButton();
            btn_RunContinuously = new Sunny.UI.UIButton();
            btn_GlobalVar = new Sunny.UI.UIButton();
            materialTabSelector = new MaterialSkin.Controls.MaterialTabSelector();
            grb_Info = new Sunny.UI.UIGroupBox();
            rich_Info = new Sunny.UI.UIRichTextBox();
@@ -89,7 +91,7 @@
            // 
            sc_VisionForm.Panel2.Controls.Add(grb_Info);
            sc_VisionForm.Size = new Size(1416, 781);
            sc_VisionForm.SplitterDistance = 591;
            sc_VisionForm.SplitterDistance = 593;
            sc_VisionForm.SplitterWidth = 5;
            sc_VisionForm.TabIndex = 1;
            // 
@@ -108,7 +110,7 @@
            tlp_MainView.RowStyles.Add(new RowStyle(SizeType.Absolute, 60F));
            tlp_MainView.RowStyles.Add(new RowStyle(SizeType.Absolute, 39F));
            tlp_MainView.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tlp_MainView.Size = new Size(1416, 591);
            tlp_MainView.Size = new Size(1416, 593);
            tlp_MainView.TabIndex = 1;
            tlp_MainView.TagString = null;
            // 
@@ -122,7 +124,7 @@
            materialTabControl.MouseState = MaterialSkin.MouseState.HOVER;
            materialTabControl.Name = "materialTabControl";
            materialTabControl.SelectedIndex = 0;
            materialTabControl.Size = new Size(1412, 488);
            materialTabControl.Size = new Size(1412, 490);
            materialTabControl.TabIndex = 0;
            // 
            // tlp_VisionMainOperator
@@ -139,9 +141,11 @@
            tlp_VisionMainOperator.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 11.1111107F));
            tlp_VisionMainOperator.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 11.1111107F));
            tlp_VisionMainOperator.Controls.Add(ckb_AllowRun, 0, 0);
            tlp_VisionMainOperator.Controls.Add(btn_Login, 1, 0);
            tlp_VisionMainOperator.Controls.Add(btn_GlobalVar, 7, 0);
            tlp_VisionMainOperator.Controls.Add(com_ProductName, 8, 0);
            tlp_VisionMainOperator.Controls.Add(btn_SingleRun, 2, 0);
            tlp_VisionMainOperator.Controls.Add(btn_Login, 1, 0);
            tlp_VisionMainOperator.Controls.Add(btn_RunContinuously, 3, 0);
            tlp_VisionMainOperator.Controls.Add(btn_GlobalVar, 7, 0);
            tlp_VisionMainOperator.Dock = DockStyle.Fill;
            tlp_VisionMainOperator.Location = new Point(4, 64);
            tlp_VisionMainOperator.Margin = new Padding(4);
@@ -165,50 +169,6 @@
            ckb_AllowRun.TabIndex = 2;
            ckb_AllowRun.Text = "运行模式";
            // 
            // btn_Login
            //
            btn_Login.BackColor = Color.Transparent;
            btn_Login.BorderColor = Color.FromArgb(32, 34, 37);
            btn_Login.Dock = DockStyle.Fill;
            btn_Login.EnteredBorderColor = Color.FromArgb(165, 37, 37);
            btn_Login.EnteredColor = Color.FromArgb(32, 34, 37);
            btn_Login.Font = new Font("宋体", 10.5F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_Login.Image = null;
            btn_Login.ImageAlign = ContentAlignment.MiddleLeft;
            btn_Login.InactiveColor = Color.FromArgb(32, 34, 37);
            btn_Login.Location = new Point(160, 4);
            btn_Login.Margin = new Padding(4);
            btn_Login.Name = "btn_Login";
            btn_Login.PressedBorderColor = Color.FromArgb(165, 37, 37);
            btn_Login.PressedColor = Color.FromArgb(165, 37, 37);
            btn_Login.Size = new Size(148, 23);
            btn_Login.TabIndex = 3;
            btn_Login.Text = "用户登录";
            btn_Login.TextAlignment = StringAlignment.Center;
            btn_Login.Click += btn_Login_Click;
            //
            // btn_GlobalVar
            //
            btn_GlobalVar.BackColor = Color.Gray;
            btn_GlobalVar.BorderColor = Color.FromArgb(32, 34, 37);
            btn_GlobalVar.Dock = DockStyle.Fill;
            btn_GlobalVar.EnteredBorderColor = Color.FromArgb(165, 37, 37);
            btn_GlobalVar.EnteredColor = Color.FromArgb(32, 34, 37);
            btn_GlobalVar.Font = new Font("宋体", 10.5F, FontStyle.Regular, GraphicsUnit.Point, 0);
            btn_GlobalVar.Image = null;
            btn_GlobalVar.ImageAlign = ContentAlignment.MiddleLeft;
            btn_GlobalVar.InactiveColor = Color.FromArgb(32, 34, 37);
            btn_GlobalVar.Location = new Point(1096, 4);
            btn_GlobalVar.Margin = new Padding(4);
            btn_GlobalVar.Name = "btn_GlobalVar";
            btn_GlobalVar.PressedBorderColor = Color.FromArgb(165, 37, 37);
            btn_GlobalVar.PressedColor = Color.FromArgb(165, 37, 37);
            btn_GlobalVar.Size = new Size(148, 23);
            btn_GlobalVar.TabIndex = 4;
            btn_GlobalVar.Text = "全局变量";
            btn_GlobalVar.TextAlignment = StringAlignment.Center;
            btn_GlobalVar.Click += btn_GlobalVar_Click;
            //
            // com_ProductName
            // 
            com_ProductName.Dock = DockStyle.Fill;
@@ -224,6 +184,74 @@
            com_ProductName.Size = new Size(152, 26);
            com_ProductName.TabIndex = 5;
            com_ProductName.SelectedValueChanged += com_ProductName_SelectedValueChanged;
            //
            // btn_SingleRun
            //
            btn_SingleRun.BackColor = Color.FromArgb(39, 51, 63);
            btn_SingleRun.Dock = DockStyle.Fill;
            btn_SingleRun.FillColor = Color.FromArgb(39, 51, 63);
            btn_SingleRun.FillColor2 = Color.FromArgb(39, 51, 63);
            btn_SingleRun.FillSelectedColor = Color.FromArgb(128, 255, 128);
            btn_SingleRun.Font = new Font("宋体", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_SingleRun.Location = new Point(315, 3);
            btn_SingleRun.MinimumSize = new Size(1, 1);
            btn_SingleRun.Name = "btn_SingleRun";
            btn_SingleRun.Size = new Size(150, 25);
            btn_SingleRun.TabIndex = 6;
            btn_SingleRun.Text = "单次运行";
            btn_SingleRun.TipsFont = new Font("宋体", 9F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_SingleRun.Click += btn_Run_Click;
            //
            // btn_Login
            //
            btn_Login.BackColor = Color.FromArgb(39, 51, 63);
            btn_Login.Dock = DockStyle.Fill;
            btn_Login.FillColor = Color.FromArgb(39, 51, 63);
            btn_Login.FillColor2 = Color.FromArgb(39, 51, 63);
            btn_Login.FillSelectedColor = Color.FromArgb(128, 255, 128);
            btn_Login.Font = new Font("宋体", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_Login.Location = new Point(159, 3);
            btn_Login.MinimumSize = new Size(1, 1);
            btn_Login.Name = "btn_Login";
            btn_Login.Size = new Size(150, 25);
            btn_Login.TabIndex = 6;
            btn_Login.Text = "用户登录";
            btn_Login.TipsFont = new Font("宋体", 9F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_Login.Click += btn_Login_Click;
            //
            // btn_RunContinuously
            //
            btn_RunContinuously.BackColor = Color.FromArgb(39, 51, 63);
            btn_RunContinuously.Dock = DockStyle.Fill;
            btn_RunContinuously.FillColor = Color.FromArgb(39, 51, 63);
            btn_RunContinuously.FillColor2 = Color.FromArgb(39, 51, 63);
            btn_RunContinuously.FillSelectedColor = Color.FromArgb(128, 255, 128);
            btn_RunContinuously.Font = new Font("宋体", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_RunContinuously.Location = new Point(471, 3);
            btn_RunContinuously.MinimumSize = new Size(1, 1);
            btn_RunContinuously.Name = "btn_RunContinuously";
            btn_RunContinuously.Size = new Size(150, 25);
            btn_RunContinuously.TabIndex = 6;
            btn_RunContinuously.Text = "连续运行";
            btn_RunContinuously.TipsFont = new Font("宋体", 9F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_RunContinuously.Click += btn_RunContinuously_Click;
            //
            // btn_GlobalVar
            //
            btn_GlobalVar.BackColor = Color.FromArgb(39, 51, 63);
            btn_GlobalVar.Dock = DockStyle.Fill;
            btn_GlobalVar.FillColor = Color.FromArgb(39, 51, 63);
            btn_GlobalVar.FillColor2 = Color.FromArgb(39, 51, 63);
            btn_GlobalVar.FillSelectedColor = Color.FromArgb(128, 255, 128);
            btn_GlobalVar.Font = new Font("宋体", 12F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_GlobalVar.Location = new Point(1095, 3);
            btn_GlobalVar.MinimumSize = new Size(1, 1);
            btn_GlobalVar.Name = "btn_GlobalVar";
            btn_GlobalVar.Size = new Size(150, 25);
            btn_GlobalVar.TabIndex = 6;
            btn_GlobalVar.Text = "全局变量";
            btn_GlobalVar.TipsFont = new Font("宋体", 9F, FontStyle.Regular, GraphicsUnit.Point, 134);
            btn_GlobalVar.Click += btn_GlobalVar_Click;
            // 
            // materialTabSelector
            // 
@@ -249,7 +277,7 @@
            grb_Info.MinimumSize = new Size(1, 1);
            grb_Info.Name = "grb_Info";
            grb_Info.Padding = new Padding(0, 40, 0, 0);
            grb_Info.Size = new Size(1416, 185);
            grb_Info.Size = new Size(1416, 183);
            grb_Info.TabIndex = 1;
            grb_Info.Text = "日志显示区:";
            grb_Info.TextAlignment = ContentAlignment.MiddleLeft;
@@ -265,7 +293,7 @@
            rich_Info.Name = "rich_Info";
            rich_Info.Padding = new Padding(2);
            rich_Info.ShowText = false;
            rich_Info.Size = new Size(1416, 145);
            rich_Info.Size = new Size(1416, 143);
            rich_Info.TabIndex = 0;
            rich_Info.TextAlignment = ContentAlignment.MiddleLeft;
            // 
@@ -321,13 +349,15 @@
        private SplitContainer sc_VisionForm;
        private Sunny.UI.UITableLayoutPanel tlp_VisionMainOperator;
        private Sunny.UI.UICheckBox ckb_AllowRun;
        private ReaLTaiizor.Controls.Button btn_Login;
        private ReaLTaiizor.Controls.Button btn_GlobalVar;
        private Sunny.UI.UIGroupBox grb_Info;
        private Sunny.UI.UIRichTextBox rich_Info;
        private MaterialSkin.Controls.MaterialTabControl materialTabControl;
        private ReaLTaiizor.Controls.AloneComboBox com_ProductName;
        private MaterialSkin.Controls.MaterialTabSelector materialTabSelector;
        private Sunny.UI.UITableLayoutPanel tlp_MainView;
        private Sunny.UI.UIButton btn_SingleRun;
        private Sunny.UI.UIButton btn_Login;
        private Sunny.UI.UIButton btn_RunContinuously;
        private Sunny.UI.UIButton btn_GlobalVar;
    }
}
LB_SmartVision/VisionForm.cs
@@ -1716,6 +1716,128 @@
                communicator.Disconnect();
            }
            FormClosing -= VisionForm_FormClosing;
            //try
            //{
            //    Process[] processes = System.Diagnostics.Process.GetProcesses(); //获得所有进程
            //    foreach (Process p in processes)
            //    {
            //        if (p.ProcessName == "LB_SmartVision" && p.StartTime < DateTime.Now.AddMilliseconds(-300))
            //        {
            //            p.Kill();
            //        }
            //    }
            //}
            //catch { }
            KillAllTargetProcesses();
        }
        /// <summary>
        /// æ€è¿›ç¨‹é€»è¾‘
        /// </summary>
        private void KillAllTargetProcesses()
        {
            try
            {
                // 1. èŽ·å–å½“å‰è¿›ç¨‹ID,避免杀死自己
                int currentProcessId = Process.GetCurrentProcess().Id;
                // 2. æ¨¡ç³ŠåŒ¹é…è¿›ç¨‹åï¼ˆå¿½ç•¥å¤§å°å†™ï¼‰ï¼Œè¦†ç›–vshost/后缀等情况
                var targetProcesses = Process.GetProcesses()
                    .Where(p =>
                        p.ProcessName.IndexOf("LB_SmartVision", StringComparison.OrdinalIgnoreCase) >= 0
                        && p.Id == currentProcessId);
                foreach (var p in targetProcesses)
                {
                    try
                    {
                        if (!p.HasExited)
                        {
                            // å…ˆå°è¯•优雅关闭WinForm程序(比直接Kill更友好)
                            p.CloseMainWindow();
                            // ç­‰å¾…500ms,看是否正常退出
                            if (!p.WaitForExit(500))
                            {
                                p.Kill(); // å¼ºåˆ¶æ€æ­»
                                p.WaitForExit(1000); // ç­‰å¾…进程完全终止
                            }
                        }
                        p.Dispose(); // é‡Šæ”¾è¿›ç¨‹èµ„源,避免句柄泄漏
                    }
                    catch (Exception ex)
                    {
                        // è®°å½•异常但不中断,比如权限不足的情况
                        System.IO.File.AppendAllText("kill_process_log.txt", $"[{DateTime.Now}] æ€æ­»è¿›ç¨‹å¤±è´¥: {ex.Message}\r\n");
                    }
                }
                // é¢å¤–延迟,确保文件句柄完全释放
                Thread.Sleep(1000);
            }
            catch (Exception)
            {
                // é™é»˜å¤±è´¥ï¼Œä¸å½±å“ç¨‹åºé€€å‡º
            }
        }
        private void btn_Run_Click(object sender, EventArgs e)
        {
            var matchedItems = GlobalVar.dicProcessSetting
                                        .Where(item =>
                                        {
                                            var value = item.Value;
                                            var triggerComm = value["触发通讯"];
                                            var triggerChar = value["触发字符"];
                                            return triggerComm != null;
                                            //return triggerComm != null && triggerComm.Equals(name) &&
                                            //       (string.IsNullOrEmpty(triggerChar?.ToString()) ||
                                            //        msg.StartsWith(triggerChar.ToString()));
                                        })
                                        .ToList(); // é¿å…é‡å¤å­—典访问和装箱操作
            if (matchedItems.Count <= 0)
            {
                return;
            }
            TriggerRunMessageReceived(matchedItems[0].Value["触发通讯"], matchedItems[0].Value["触发字符"]);
        }
        private void btn_RunContinuously_Click(object sender, EventArgs e)
        {
            if (btn_RunContinuously.Text.Equals("连续运行"))
            {
                btn_RunContinuously.Text = "暂停运行";
                Task.Factory.StartNew(() =>
                {
                    var matchedItems = GlobalVar.dicProcessSetting
                                                .Where(item =>
                                                {
                                                    var value = item.Value;
                                                    var triggerComm = value["触发通讯"];
                                                    var triggerChar = value["触发字符"];
                                                    return triggerComm != null;
                                                    //return triggerComm != null && triggerComm.Equals(name) &&
                                                    //       (string.IsNullOrEmpty(triggerChar?.ToString()) ||
                                                    //        msg.StartsWith(triggerChar.ToString()));
                                                })
                                                .ToList(); // é¿å…é‡å¤å­—典访问和装箱操作
                    while (btn_RunContinuously.Text.Equals("暂停运行"))
                    {
                        TriggerRunMessageReceived(matchedItems[0].Value["触发通讯"], matchedItems[0].Value["触发字符"]);
                        Thread.Sleep(500);
                    }
                    //this.Invoke(() =>
                    //{
                    //});
                });
            }
            else if (btn_RunContinuously.Text.Equals("暂停运行"))
            {
                btn_RunContinuously.Text = "连续运行";
                Thread.Sleep(100);
            }
        }
    }
}
LB_SmartVisionCommon/FilterData.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,80 @@
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace LB_SmartVisionCommon
{
    /// <summary>
    /// è®°å½•图像增强算子参数
    /// </summary>
    [JsonObject(MemberSerialization.OptOut)]
    [TypeConverter(typeof(PropertySorter))]
    public class RecordFilterData
    {
        /// <summary>
        /// ç®—子类型
        /// </summary>
        [Category("RecordFilterData"), PropertyOrder(1)]
        [DisplayName("滤波类型")]
        [Browsable(true)]
        public FilterType FilterName { get; set; } = FilterType.均值滤波_MeanImage;
        /// <summary>
        /// æŽ©è†œå®½åº¦
        /// </summary>
        [Category("RecordFilterData"), PropertyOrder(2)]
        [DisplayName("掩膜宽度")]
        [Browsable(true)]
        public string MaskWidth { get; set; }
        /// <summary>
        /// æŽ©è†œé«˜åº¦
        /// </summary>
        [Category("RecordFilterData"), PropertyOrder(3)]
        [DisplayName("掩膜高度")]
        [Browsable(true)]
        public string MaskHight { get; set; }
        /// <summary>
        /// å¢žå¼ºå› å­
        /// </summary>
        [Category("RecordFilterData"), PropertyOrder(4)]
        [DisplayName("高斯核尺寸")]
        [Browsable(true)]
        public string GaussSize { get; set; }
        /// <summary>
        /// å¤åˆ¶ç”¨æˆ·æ•°æ®
        /// </summary>
        public RecordFilterData Clone()
        {
            return new RecordFilterData
            {
                MaskWidth = this.MaskWidth,
                MaskHight = this.MaskHight,
                GaussSize = this.GaussSize,
                FilterName = this.FilterName
            };
        }
    }
    /// <summary>
    /// OperatorType
    /// </summary>
    public enum FilterType
    {
        /// <summary>
        /// FilterType:MeanImage
        /// </summary>
        å‡å€¼æ»¤æ³¢_MeanImage,
        /// <summary>
        /// FilterType:GaussFilter
        /// </summary>
        é«˜æ–¯æ»¤æ³¢_GaussFilter,
        /// <summary>
        /// FilterType:MedianRect
        /// </summary>
        ä¸­å€¼æ»¤æ³¢_MedianRect
    }
}
LB_SmartVisionCommon/FilterManager.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,152 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace LB_SmartVisionCommon
{
    public class FilterManager
    {
        private Dictionary<FilterType, RecordFilterData> _filters;
        private readonly string _dataFilePath;
        private RecordFilterData _currentFilter;
        private static FilterManager _instance;
        /// <summary>
        /// çº¿ç¨‹é”
        /// </summary>
        private static readonly object _lock = new object();
        private FilterManager(string dataFilePath = "filters.json")
        {
            _dataFilePath = dataFilePath;
            _filters = new Dictionary<FilterType, RecordFilterData>();
            _currentFilter = null;
            LoadUsers();
        }
        public static FilterManager Instance
        {
            get
            {
                // åŒé‡æ£€æŸ¥é”å®šç¡®ä¿çº¿ç¨‹å®‰å…¨
                if (_instance == null)
                {
                    lock (_lock)
                    {
                        if (_instance == null)
                        {
                            _instance = new FilterManager();
                        }
                    }
                }
                return _instance;
            }
        }
        /// <summary>
        /// æ·»åŠ æ»¤æ³¢ç®—å­
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public bool AddFilter(RecordFilterData filter)
        {
            if (_currentFilter == null)
            {
                _currentFilter = filter;
            }
            try
            {
                RecordFilterData recordFilterData = new RecordFilterData();
                recordFilterData.MaskWidth = filter.MaskWidth;
                recordFilterData.MaskHight = filter.MaskHight;
                recordFilterData.GaussSize = filter.GaussSize;
                recordFilterData.FilterName = filter.FilterName;
                _filters.Add(recordFilterData.FilterName, recordFilterData);
            }
            catch (Exception ex)
            {
                MessageBox.Show("该算子已存在");
            }
            SaveUsers();
            return true;
        }
        /// <summary>
        /// åˆ é™¤å›¾åƒå¢žå¼ºç®—子
        /// </summary>
        /// <param name="filterName"></param>
        /// <returns></returns>
        public bool DeleteUser(RecordFilterData filter)
        {
            try
            {
                // 1. ä»Žå­—典中删除
                if (_filters.ContainsKey(filter.FilterName))
                {
                    _filters.Remove(filter.FilterName);
                }
                // 2. å¦‚果删除的是当前滤波,清空_currentFilter
                if (_currentFilter != null && _currentFilter.FilterName == filter.FilterName)
                {
                    _currentFilter = null;
                }
                // 3. ä¿å­˜æ›´æ”¹
                SaveUsers();
                return true;
            }
            catch (Exception ex)
            {
                // è®°å½•日志
                Console.WriteLine($"删除滤波失败: {ex.Message}");
                return false;
            }
        }
        /// <summary>
        /// èŽ·å–æ‰€æœ‰ç”¨æˆ·åˆ—è¡¨
        /// </summary>
        /// <returns>List<RecordUserData></returns>
        public List<RecordFilterData> GetAllUsers()
        {
            return _filters.Select(u => u.Value.Clone()).ToList();
        }
        #region json文件保存加载
        /// <summary>
        /// ä¿å­˜ç”¨æˆ·æ•°æ®åˆ°JSON文件
        /// </summary>
        private void SaveUsers()
        {
            try
            {
                ConfigManager<Dictionary<FilterType, RecordFilterData>>.SaveConfig<Dictionary<FilterType, RecordFilterData>>(_filters, _dataFilePath);
            }
            catch (Exception ex)
            {
                MessageBox.Show($"保存图像增强算子失败:{ex.Message}", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }
        /// <summary>
        /// ä»ŽJSON文件加载用户数据
        /// </summary>
        private void LoadUsers()
        {
            try
            {
                if (File.Exists(_dataFilePath))
                {
                    _filters = ConfigManager<Dictionary<FilterType, RecordFilterData>>.LoadConfig<Dictionary<FilterType, RecordFilterData>>(_dataFilePath) ?? new Dictionary<FilterType, RecordFilterData>();
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show($"加载图像增强算子失败:{ex.Message}", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
                _filters = new Dictionary<FilterType, RecordFilterData>();
            }
        }
        #endregion
    }
}
LB_SmartVisionCommon/ImageEnhancementData.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,75 @@
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace LB_SmartVisionCommon
{
    /// <summary>
    /// è®°å½•图像增强算子参数
    /// </summary>
    [JsonObject(MemberSerialization.OptOut)]
    [TypeConverter(typeof(PropertySorter))]
    public class RecordImageEnhancementData
    {
        /// <summary>
        /// ç®—子类型
        /// </summary>
        [Category("RecordImageEnhancementData"), PropertyOrder(1)]
        [DisplayName("算子类型")]
        [Browsable(true)]
        public ImageEnhancementDataType FilterName { get; set; } = ImageEnhancementDataType.比例增强_ScaleImageMax;
        /// <summary>
        /// æŽ©è†œå®½åº¦
        /// </summary>
        [Category("RecordImageEnhancementData"), PropertyOrder(2)]
        [DisplayName("掩膜宽度")]
        [Browsable(true)]
        public string MaskWidth { get; set; }
        /// <summary>
        /// æŽ©è†œé«˜åº¦
        /// </summary>
        [Category("RecordImageEnhancementData"), PropertyOrder(3)]
        [DisplayName("掩膜高度")]
        [Browsable(true)]
        public string MaskHight { get; set; }
        /// <summary>
        /// å¢žå¼ºå› å­
        /// </summary>
        [Category("RecordImageEnhancementData"), PropertyOrder(4)]
        [DisplayName("增强因子")]
        [Browsable(true)]
        public string Factor { get; set; }
        /// <summary>
        /// å¤åˆ¶ç”¨æˆ·æ•°æ®
        /// </summary>
        public RecordImageEnhancementData Clone()
        {
            return new RecordImageEnhancementData
            {
                MaskWidth = this.MaskWidth,
                MaskHight = this.MaskHight,
                Factor = this.Factor,
                FilterName = this.FilterName
            };
        }
    }
    /// <summary>
    /// OperatorType
    /// </summary>
    public enum ImageEnhancementDataType
    {
        /// </summary>
        è¾¹ç¼˜å¢žå¼º_ImageEmphasize,
        /// </summary>
        ç›´æ–¹å›¾å‡è¡¡åŒ–_EquHistoImage,
        /// </summary>
        æ¯”例增强_ScaleImageMax
    }
}
LB_SmartVisionCommon/ImageEnhancementManager.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,155 @@
using Microsoft.VisualBasic.ApplicationServices;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace LB_SmartVisionCommon
{
    public class ImageEnhancementManager
    {
        private Dictionary<ImageEnhancementDataType, RecordImageEnhancementData> _filters;
        private readonly string _dataFilePath;
        private RecordImageEnhancementData _currentFilter;
        private static ImageEnhancementManager _instance;
        /// <summary>
        /// çº¿ç¨‹é”
        /// </summary>
        private static readonly object _lock = new object();
        private ImageEnhancementManager(string dataFilePath = "imageEnhancements.json")
        {
            _dataFilePath = dataFilePath;
            _filters = new Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>();
            _currentFilter = null;
            LoadUsers();
        }
        public static ImageEnhancementManager Instance
        {
            get
            {
                // åŒé‡æ£€æŸ¥é”å®šç¡®ä¿çº¿ç¨‹å®‰å…¨
                if (_instance == null)
                {
                    lock (_lock)
                    {
                        if (_instance == null)
                        {
                            _instance = new ImageEnhancementManager();
                        }
                    }
                }
                return _instance;
            }
        }
        /// <summary>
        /// æ·»åŠ å›¾åƒå¢žå¼ºç®—å­
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public bool AddUser(RecordImageEnhancementData filter)
        {
            if (_currentFilter == null)
            {
                _currentFilter = filter;
            }
            try
            {
                RecordImageEnhancementData recordImageEnhancementData = new RecordImageEnhancementData();
                recordImageEnhancementData.MaskWidth = filter.MaskWidth;
                recordImageEnhancementData.MaskHight = filter.MaskHight;
                recordImageEnhancementData.Factor = filter.Factor;
                recordImageEnhancementData.FilterName = filter.FilterName;
                _filters.Add(recordImageEnhancementData.FilterName, recordImageEnhancementData);
            }
            catch (Exception ex)
            {
                MessageBox.Show("该算子已存在");
            }
            SaveUsers();
            return true;
        }
        /// <summary>
        /// åˆ é™¤å›¾åƒå¢žå¼ºç®—子
        /// </summary>
        /// <param name="filter"></param>
        /// <returns></returns>
        public bool DeleteUser(RecordImageEnhancementData filter)
        {
            try
            {
                // 1. ä»Žå­—典中删除
                if (_filters.ContainsKey(filter.FilterName))
                {
                    _filters.Remove(filter.FilterName);
                }
                // 2. å¦‚果删除的是当前滤波,清空_currentFilter
                if (_currentFilter != null && _currentFilter.FilterName == filter.FilterName)
                {
                    _currentFilter = null;
                }
                // 3. ä¿å­˜æ›´æ”¹
                SaveUsers();
                return true;
            }
            catch (Exception ex)
            {
                // è®°å½•日志
                Console.WriteLine($"删除滤波失败: {ex.Message}");
                return false;
            }
        }
        /// <summary>
        /// èŽ·å–æ‰€æœ‰ç”¨æˆ·åˆ—è¡¨
        /// </summary>
        /// <returns>List<RecordUserData></returns>
        public List<RecordImageEnhancementData> GetAllUsers()
        {
            return _filters.Select(u => u.Value.Clone()).ToList();
        }
        #region json文件保存加载
        /// <summary>
        /// ä¿å­˜ç”¨æˆ·æ•°æ®åˆ°JSON文件
        /// </summary>
        private void SaveUsers()
        {
            try
            {
                ConfigManager<Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>>.SaveConfig<Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>>(_filters, _dataFilePath);
            }
            catch (Exception ex)
            {
                MessageBox.Show($"保存图像增强算子失败:{ex.Message}", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }
        /// <summary>
        /// ä»ŽJSON文件加载用户数据
        /// </summary>
        private void LoadUsers()
        {
            try
            {
                if (File.Exists(_dataFilePath))
                {
                    _filters = ConfigManager<Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>>.LoadConfig<Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>>(_dataFilePath) ?? new Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>();
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show($"加载图像增强算子失败:{ex.Message}", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
                _filters = new Dictionary<ImageEnhancementDataType, RecordImageEnhancementData>();
            }
        }
        #endregion
    }
}
LB_VisionFlowNode/FlowPanel.cs
@@ -1,4 +1,5 @@
using System.Collections.Concurrent;
using LB_SmartVisionCommon;
using System.Collections.Concurrent;
using System.Diagnostics;
using System.Xml.Linq;
@@ -305,6 +306,7 @@
            bool result = Context.ExecuteNode(currentNode);
#if DEBUG
            Debug.WriteLine(DateTime.Now.ToString("[yyyy:MM:dd:HH:mm:ss:fff] ") + $"执行节点[{currentNode.Text}],结果为{result}");
            AsyncLogHelper.Debug(DateTime.Now.ToString("[yyyy:MM:dd:HH:mm:ss:fff] ") + $"执行节点[{currentNode.Text}],结果为{result}");
#endif
            context.BranchResults.TryAdd(context.CurrentBranchName, currentNode.Result);
            currentNode.Result = result;
LB_VisionFlowNode/IFlowContext.cs
@@ -280,12 +280,18 @@
        [Node("相机取图", "取像工具", "Basic", "相机取图")]
        public void ç›¸æœºå–图(FlowNode node) { RunNodeAsync(node); }
        [Node("Halcon2D斑点工具", "Haclon2D工具", "Basic", "Halcon2D斑点工具")]
        [Node("Halcon2D斑点工具", "Halcon2D工具", "Basic", "Halcon2D斑点工具")]
        public void Halcon2D斑点工具(FlowNode node) { RunNodeAsync(node); }
        [Node("通讯模块", "通讯模块工具", "Basic", "通讯模块")]
        public void é€šè®¯æ¨¡å—(FlowNode node) { RunNodeAsync(node); }
        //  [Process("Halcon图像增强", Category = "Halcon2D工具", Description = "创建图像增强工具")]
        [Node("Halcon2D图像增强", "Halcon2D工具", "Basic", "Halcon2D图像增强")]
        public void Halcon2D图像增强(FlowNode node) { RunNodeAsync(node); }
        [Node("Halcon2D图像滤波", "Halcon2D工具", "Basic", "Halcon2D图像滤波")]
        public void Halcon2D图像滤波(FlowNode node) { RunNodeAsync(node); }
        #endregion
LB_VisionProcesses/Alogrithms/BaseAlgorithm/TAlgorithm.cs
@@ -3836,58 +3836,90 @@
        /// å›¾åƒå¢žå¼ºç®—法-边缘增强
        /// </summary>
        /// <param name="ho_Image">待测图片</param>
        /// <param name="hv_ImageEnhancementType">滤波器类型(mean/gauss/median)</param>
        /// <param name="hv_Wid">掩膜宽</param>
        /// <param name="hv_High">掩膜高</param>
        /// <param name="hv_Fac">增强因子</param>
        /// <param name="hv_Row1">起始纵坐标</param>
        /// <param name="hv_Column1">起始横坐标</param>
        /// <param name="hv_Row2">结束纵坐标</param>
        /// <param name="hv_Column2">结束横坐标</param>
        public static void ImageEnhancement(HObject ho_Image, out HObject ho_OutImage, HTuple hv_ImageEnhancementType, HTuple hv_Wid, HTuple hv_High, HTuple hv_Fac)
        public static void ImageEnhancement(HObject ho_Image, out HObject ho_OutImage, string hv_ImageEnhancementType, int hv_Wid, int hv_High, double hv_Fac)
        {
            HOperatorSet.GenEmptyObj(out ho_OutImage);
            try
            {
                HTuple hv_ImageEnhancementTypeOut = new HTuple();
                hv_ImageEnhancementTypeOut.Dispose();
                hv_ImageEnhancementTypeOut = new HTuple(hv_ImageEnhancementType);
                hv_Wid.Dispose();
                hv_High.Dispose();
                ho_OutImage.Dispose();
                //设置图像增强算法
                if ((int)(new HTuple(hv_ImageEnhancementTypeOut.TupleEqual("emphasize"))) != 0)
                // æ ¹æ®æ»¤æ³¢å™¨ç±»åž‹æ‰§è¡Œç›¸åº”操作
                switch (hv_ImageEnhancementType.ToLower())
                {
                    hv_ImageEnhancementTypeOut.Dispose();
                    hv_ImageEnhancementTypeOut = "emphasize";
                    case "emphasize":
                    HOperatorSet.Emphasize(ho_Image, out ho_OutImage, hv_Wid, hv_High, hv_Fac);
                }
                else if ((int)(new HTuple(hv_ImageEnhancementTypeOut.TupleEqual("equHisto"))) != 0)
                {
                    hv_ImageEnhancementTypeOut.Dispose();
                    hv_ImageEnhancementTypeOut = "equHisto";
                        break;
                    case "scaleimagemax":
                    HOperatorSet.ScaleImageMax(ho_Image, out ho_OutImage);
                }
                else
                {
                    hv_ImageEnhancementTypeOut.Dispose();
                    hv_ImageEnhancementTypeOut = "scaleMax";
                        break;
                    case "equhisto":
                    HOperatorSet.EquHistoImage(ho_Image, out ho_OutImage);
                        break;
                    default:
                        throw new ArgumentException($"不支持的滤波器类型: {hv_ImageEnhancementType}");
                }
                return;
            }
            catch (HalconException HDevExpDefaultException)
            catch (Exception ex)
            {
                hv_Wid.Dispose();
                hv_High.Dispose();
                throw HDevExpDefaultException;
                // ç¡®ä¿å¼‚常时释放资源
                ho_OutImage?.Dispose();
                throw new Exception($"图像滤波失败: {ex.Message}", ex);
            }
        }
       
        /// <summary>
        /// å›¾åƒæ»¤æ³¢
        /// </summary>
        /// <param name="ho_Image">待测图片</param>
        /// <param name="ho_OutImage">输出图片</param>
        /// <param name="hv_FilterType">滤波器类型(mean/gauss/median)</param>
        /// <param name="hv_Wid">掩膜宽</param>
        /// <param name="hv_High">掩膜高</param>
        /// <param name="hv_Size">高斯核尺寸</param>
        public static void Filter(HObject ho_Image, out HObject ho_OutImage, string hv_FilterType, int hv_Wid, int hv_High, int hv_Size)
        {
            // åˆå§‹åŒ–输出对象
            HOperatorSet.GenEmptyObj(out ho_OutImage);
            try
            {
                // æ ¹æ®æ»¤æ³¢å™¨ç±»åž‹æ‰§è¡Œç›¸åº”操作
                switch (hv_FilterType.ToLower())
                {
                    case "mean":
                        HOperatorSet.MeanImage(ho_Image, out ho_OutImage, hv_Wid, hv_High);
                        break;
                    case "gauss":
                    case "guass":  // å…¼å®¹æ‹¼å†™é”™è¯¯
                        HOperatorSet.GaussFilter(ho_Image, out ho_OutImage, hv_Size);
                        break;
                    case "median":
                        HOperatorSet.MedianRect(ho_Image, out ho_OutImage, hv_Wid, hv_High);
                        break;
                    default:
                        throw new ArgumentException($"不支持的滤波器类型: {hv_FilterType}");
                }
            }
            catch (Exception ex)
            {
                // ç¡®ä¿å¼‚常时释放资源
                ho_OutImage?.Dispose();
                throw new Exception($"图像滤波失败: {ex.Message}", ex);
            }
        }
        /// <summary>
        /// å¡å°ºç®—法
        /// </summary>
        /// <param name="ho_Image">待测图片</param>
LB_VisionProcesses/Alogrithms/Halcon/2D/HBlobTool/HBlobTool.cs
@@ -85,10 +85,13 @@
                    {
                        using (HImage hImage = new HImage())
                        {
                            Rectangle rect = new Rectangle(0, 0, ((Bitmap)InputImage).Width, ((Bitmap)InputImage).Height);
                            BitmapData srcBmpData = ((Bitmap)InputImage).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                            hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)InputImage).Width, ((Bitmap)InputImage).Height, 0, "byte", ((Bitmap)InputImage).Width, ((Bitmap)InputImage).Height, 0, 0, -1, 0);
                            ((Bitmap)InputImage).UnlockBits(srcBmpData);
                            Bitmap bitmap = (Bitmap)InputImage;
                            Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                            BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                            hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                            ((Bitmap)bitmap).UnlockBits(srcBmpData);
                            bitmap.Dispose();
                            bitmap = null;
                            InputImage = null;
                            InputImage = hImage.Clone();
                        }
LB_VisionProcesses/Alogrithms/Halcon/2D/HBlobTool/HBlobToolEdit.cs
@@ -84,6 +84,7 @@
            foreach (string value in IProcess.dicFixtures.Keys)
                cmbFixture.Items.Add(value.ToString());
            ckbDrawRoi.Checked = true;
            cmbTypeRoi.Text = RoiType.None.ToString();
            LoadParas();
@@ -376,6 +377,7 @@
        public override void btnSaveParas_Click(object sender, EventArgs e) { base.btnSaveParas_Click(sender, e); }
        public override void ckbDrawRoi_CheckedChanged(object sender, EventArgs e)
        {
            if (ckbDrawRoi.Checked)
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterTool.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,229 @@
using HalconDotNet;
using LB_SmartVisionCommon;
using LB_VisionControl;
using System;
using System.Collections.Generic;
using System.Drawing.Imaging;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace LB_VisionProcesses.Alogrithms.Halcon
{
    public enum ImageFilterType { Mean, Guass, Median }
    [Process("Halcon2D图像滤波", Category = "Halcon2D工具", Description = "创建滤波工具")]
    public class HFilterTool : TAlgorithm
    {
        public HFilterTool()
        {
            strProcessClass = "LB_VisionProcesses.Alogrithms.Halcon.HFilterTool";
            strProcessName = "Halcon2D图像滤波工具";
            Params.Inputs.Add("滤波器类型", "均值滤波");
            Params.Inputs.Add("掩膜宽", 1);
            Params.Inputs.Add("掩膜高", 1);
            //mean_image(Image : ImageMean : MaskWidth, MaskHeight : )
            Params.Inputs.Add("滤波器类型", "高斯滤波");
            Params.Inputs.Add("高斯核尺寸", 1.0);
            //gauss_filter(Image : ImageGauss : Size : )
            Params.Inputs.Add("滤波器类型", "中值滤波");
            Params.Inputs.Add("掩膜宽", 1);
            Params.Inputs.Add("掩膜高", 1);
            //median_rect(Image : ImageMedian :MaskWidth,MaskHeight:)
            Params.ROI = new HSegment(0, 0, 250, 250);
        }
        List<RecordFilterData> recordFilterDatas = new List<RecordFilterData>();
        /// <summary>
        /// ç®—子逻辑
        /// </summary>
        public override void TAlgorithmMain()
        {
            #region åˆå§‹åŒ–变量
            HObject ho_Regions, ho_LineXld;
            HOperatorSet.GenEmptyObj(out ho_Regions);
            HOperatorSet.GenEmptyObj(out ho_LineXld);
            #endregion
            try
            {
                if (InputImage == null)
                {
                    Msg = "输入图片为空";
                    Result = false;
                    return;
                }
                if (InputImage is Bitmap)
                {
                    try
                    {
                        using (HImage hImage = new HImage())
                        {
                            Bitmap bitmap = (Bitmap)InputImage;
                            Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                            BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                            hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                            ((Bitmap)bitmap).UnlockBits(srcBmpData);
                            bitmap.Dispose();
                            bitmap = null;
                            InputImage = null;
                            InputImage = hImage.Clone();
                        }
                    }
                    catch (Exception ex)
                    {
                    }
                }
                if (!(InputImage is HObject))
                {
                    Msg = "输入图片格式不为HObject";
                    Result = false;
                    return;
                }
                #region è£å‰ªåŒºåŸŸ
                //if (!(Params.ROI is HSegment))
                //{
                //    Msg = "ROI类型错误,必须为HSegment类型";
                //    Result = false;
                //    return;
                //}
                //if (!(InputImage is HObject))
                //{
                //    Msg = "输入图片类型错误,必须为HObject类型";
                //    Result = false;
                //    return;
                //}
                //HObject DomainImage = ((HObject)InputImage)?.CopyObj(1, -1);
                object DomainImage = null;
                if (!ReduceDomainImage(InputImage, ref DomainImage))
                {
                    Msg = "裁剪区域失败";
                    Result = false;
                    return;
                }
                #endregion
                #region ç®—子逻辑
                Record = new ObjectRecord();
                HObject hoDomainImage = DomainImage as HObject;
                HTuple hv_Channels = new HTuple();
                //判断是否为灰度图
                using (HDevDisposeHelper dh = new HDevDisposeHelper())
                {
                    try
                    {
                        HOperatorSet.CountChannels(hoDomainImage, out hv_Channels);
                        if (hv_Channels.TupleInt() != 1)
                            HOperatorSet.Rgb1ToGray(hoDomainImage, out hoDomainImage);
                        //转换后再次检查是否为灰度图
                        HOperatorSet.CountChannels(hoDomainImage, out hv_Channels);
                        if (hv_Channels.TupleInt() != 1)
                        {
                            HOperatorSet.Rgb1ToGray(hoDomainImage, out hoDomainImage);
                            Msg = "输入图片不为灰度图";
                            Result = false;
                            return;
                        }
                    }
                    catch
                    {
                        Msg = "输入图片不为灰度图且转换失败";
                        Result = false;
                        return;
                    }
                }
                int hv_MaskWidth = Convert.ToInt16(Params.Inputs["掩膜宽"]);
                int hv_MaskHight = Convert.ToInt16(Params.Inputs["掩膜高"]);
                int hv_Size = Convert.ToInt16(Params.Inputs["高斯核尺寸"]);
                recordFilterDatas = FilterManager.Instance.GetAllUsers();
                string hv_FilterType = "";
                foreach (var recordFilterData in recordFilterDatas)
                {
                    switch (recordFilterData.FilterName)
                    {
                        case FilterType.均值滤波_MeanImage:
                            hv_FilterType = "mean";
                            hv_MaskWidth = Convert.ToInt16(recordFilterData.MaskWidth);
                            hv_MaskHight = Convert.ToInt16(recordFilterData.MaskHight);
                            Filter(hoDomainImage, out ho_Regions, hv_FilterType, hv_MaskWidth, hv_MaskHight, hv_Size);
                            break;
                        case FilterType.高斯滤波_GaussFilter:
                            hv_FilterType = "gauss";
                            hv_Size = Convert.ToInt16(recordFilterData.GaussSize);
                            Filter(hoDomainImage, out ho_Regions, hv_FilterType, hv_MaskWidth, hv_MaskHight, hv_Size);
                            break;
                        case FilterType.中值滤波_MedianRect:
                            hv_FilterType = "median";
                            hv_MaskWidth = Convert.ToInt16(recordFilterData.MaskWidth);
                            hv_MaskHight = Convert.ToInt16(recordFilterData.MaskHight);
                            Filter(hoDomainImage, out ho_Regions, hv_FilterType, hv_MaskWidth, hv_MaskHight, hv_Size);
                            break;
                        default:
                            hv_FilterType = "median";
                            hv_MaskWidth = Convert.ToInt16(recordFilterData.MaskWidth);
                            hv_MaskHight = Convert.ToInt16(recordFilterData.MaskHight);
                            Filter(hoDomainImage, out ho_Regions, hv_FilterType, hv_MaskWidth, hv_MaskHight, hv_Size);
                            break;
                    }
                }
                #endregion
                #region ç”ŸæˆOutputImage给后续处理
                try
                {
                    OutputImage = hoDomainImage;
                }
                catch (Exception ex)
                {
                    Msg = "生成OutputImage失败,原因是:" + ex.ToString();
                    Result = false;
                    return;
                }
                #endregion
                if (Msg == "运行超时")
                {
                    Result = false;
                    return;
                }
                Msg = "运行成功";
                Result = true;
                return;
            }
            catch (Exception ex)
            {
                Msg = "运行失败,原因是:" + ex.ToString().TrimEnd();
                OutputImage = null;
                Result = false;
                return;
            }
            finally
            {
                if (!Result)
                {
                    Params.Outputs.Add("Segment", new HSegment());
                }
                bCompleted = true;
                #region å†…存释放
                ho_Regions.Dispose();
                #endregion
            }
        }
    }
}
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterToolEdit.Designer.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,613 @@
namespace LB_VisionProcesses.Alogrithms.Halcon
{
    partial class HFilterToolEdit
    {
        /// <summary>
        /// å¿…需的设计器变量。
        /// </summary>
        private System.ComponentModel.IContainer components = null;
        /// <summary>
        /// æ¸…理所有正在使用的资源。
        /// </summary>
        /// <param name="disposing">如果应释放托管资源,为 true;否则为 false。</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }
        #region ç»„件设计器生成的代码
        /// <summary>
        /// è®¾è®¡å™¨æ”¯æŒæ‰€éœ€çš„æ–¹æ³• - ä¸è¦ä¿®æ”¹
        /// ä½¿ç”¨ä»£ç ç¼–辑器修改此方法的内容。
        /// </summary>
        private void InitializeComponent()
        {
            pnlInputImage = new Panel();
            TopToolStrip = new ToolStrip();
            btnRun = new ToolStripButton();
            btnLoadImage = new ToolStripButton();
            btnSaveParas = new ToolStripButton();
            btnLoadParas = new ToolStripButton();
            BtmStatusStrip = new StatusStrip();
            lblResult = new ToolStripStatusLabel();
            lblMsg = new ToolStripStatusLabel();
            lblRunTime = new ToolStripStatusLabel();
            MainTableLayoutPanel = new TableLayoutPanel();
            parasTabControl = new TabControl();
            tabPage1 = new TabPage();
            tableLayoutPanel1 = new TableLayoutPanel();
            dataGridViewFi = new DataGridView();
            tableLayoutPanel4 = new TableLayoutPanel();
            tableLayoutPanel6 = new TableLayoutPanel();
            txtGuassSize = new TextBox();
            labelGuassSize = new Label();
            tableLayoutPanel3 = new TableLayoutPanel();
            cmbFilterType = new ComboBox();
            btnAdd = new Button();
            labelFilterType = new Label();
            btnDel = new Button();
            tableLayoutPanel5 = new TableLayoutPanel();
            labelMaskWidth = new Label();
            labelMaskHeight = new Label();
            txtMaskWidth = new TextBox();
            txtMaskHeight = new TextBox();
            tabPage5 = new TabPage();
            tableLayoutPanel2 = new TableLayoutPanel();
            cmbTypeRoi = new ComboBox();
            label21 = new Label();
            label22 = new Label();
            cmbFixture = new ComboBox();
            ckbDrawRoi = new CheckBox();
            imgTabControl = new TabControl();
            tabPageInputImage = new TabPage();
            tabPageRecordImage = new TabPage();
            pnlRecordImage = new Panel();
            TopToolStrip.SuspendLayout();
            BtmStatusStrip.SuspendLayout();
            MainTableLayoutPanel.SuspendLayout();
            parasTabControl.SuspendLayout();
            tabPage1.SuspendLayout();
            tableLayoutPanel1.SuspendLayout();
            ((System.ComponentModel.ISupportInitialize)dataGridViewFi).BeginInit();
            tableLayoutPanel4.SuspendLayout();
            tableLayoutPanel6.SuspendLayout();
            tableLayoutPanel3.SuspendLayout();
            tableLayoutPanel5.SuspendLayout();
            tabPage5.SuspendLayout();
            tableLayoutPanel2.SuspendLayout();
            imgTabControl.SuspendLayout();
            tabPageInputImage.SuspendLayout();
            tabPageRecordImage.SuspendLayout();
            SuspendLayout();
            //
            // pnlInputImage
            //
            pnlInputImage.Dock = DockStyle.Fill;
            pnlInputImage.Location = new Point(4, 4);
            pnlInputImage.Margin = new Padding(5);
            pnlInputImage.Name = "pnlInputImage";
            pnlInputImage.Size = new Size(782, 603);
            pnlInputImage.TabIndex = 44;
            //
            // TopToolStrip
            //
            TopToolStrip.ImageScalingSize = new Size(20, 20);
            TopToolStrip.Items.AddRange(new ToolStripItem[] { btnRun, btnLoadImage, btnSaveParas, btnLoadParas });
            TopToolStrip.Location = new Point(0, 0);
            TopToolStrip.Name = "TopToolStrip";
            TopToolStrip.Size = new Size(1342, 27);
            TopToolStrip.TabIndex = 45;
            TopToolStrip.Text = "toolStrip1";
            //
            // btnRun
            //
            btnRun.BackgroundImageLayout = ImageLayout.Zoom;
            btnRun.ImageTransparentColor = Color.Magenta;
            btnRun.Name = "btnRun";
            btnRun.Size = new Size(43, 24);
            btnRun.Text = "运行";
            btnRun.Click += btnRun_Click;
            //
            // btnLoadImage
            //
            btnLoadImage.ImageTransparentColor = Color.Magenta;
            btnLoadImage.Name = "btnLoadImage";
            btnLoadImage.Size = new Size(43, 24);
            btnLoadImage.Text = "导图";
            btnLoadImage.Click += btnLoadImage_Click;
            //
            // btnSaveParas
            //
            btnSaveParas.ImageTransparentColor = Color.Magenta;
            btnSaveParas.Name = "btnSaveParas";
            btnSaveParas.Size = new Size(43, 24);
            btnSaveParas.Text = "保存";
            btnSaveParas.Click += btnSaveParas_Click;
            //
            // btnLoadParas
            //
            btnLoadParas.ImageTransparentColor = Color.Magenta;
            btnLoadParas.Name = "btnLoadParas";
            btnLoadParas.Size = new Size(43, 24);
            btnLoadParas.Text = "加载";
            //
            // BtmStatusStrip
            //
            BtmStatusStrip.ImageScalingSize = new Size(20, 20);
            BtmStatusStrip.Items.AddRange(new ToolStripItem[] { lblResult, lblMsg, lblRunTime });
            BtmStatusStrip.Location = new Point(0, 679);
            BtmStatusStrip.Name = "BtmStatusStrip";
            BtmStatusStrip.Padding = new Padding(1, 0, 18, 0);
            BtmStatusStrip.Size = new Size(1342, 26);
            BtmStatusStrip.TabIndex = 46;
            BtmStatusStrip.Text = "statusStrip1";
            //
            // lblResult
            //
            lblResult.Name = "lblResult";
            lblResult.Size = new Size(42, 20);
            lblResult.Text = "True";
            //
            // lblMsg
            //
            lblMsg.Name = "lblMsg";
            lblMsg.Size = new Size(69, 20);
            lblMsg.Text = "运行成功";
            //
            // lblRunTime
            //
            lblRunTime.Name = "lblRunTime";
            lblRunTime.Size = new Size(39, 20);
            lblRunTime.Text = "0ms";
            //
            // MainTableLayoutPanel
            //
            MainTableLayoutPanel.ColumnCount = 2;
            MainTableLayoutPanel.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 40F));
            MainTableLayoutPanel.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 60F));
            MainTableLayoutPanel.Controls.Add(parasTabControl, 0, 0);
            MainTableLayoutPanel.Controls.Add(imgTabControl, 1, 0);
            MainTableLayoutPanel.Dock = DockStyle.Fill;
            MainTableLayoutPanel.Location = new Point(0, 27);
            MainTableLayoutPanel.Margin = new Padding(4);
            MainTableLayoutPanel.Name = "MainTableLayoutPanel";
            MainTableLayoutPanel.RowCount = 1;
            MainTableLayoutPanel.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            MainTableLayoutPanel.Size = new Size(1342, 652);
            MainTableLayoutPanel.TabIndex = 47;
            //
            // parasTabControl
            //
            parasTabControl.Controls.Add(tabPage1);
            parasTabControl.Controls.Add(tabPage5);
            parasTabControl.Dock = DockStyle.Fill;
            parasTabControl.Location = new Point(4, 4);
            parasTabControl.Margin = new Padding(4);
            parasTabControl.Name = "parasTabControl";
            parasTabControl.SelectedIndex = 0;
            parasTabControl.Size = new Size(528, 644);
            parasTabControl.TabIndex = 48;
            //
            // tabPage1
            //
            tabPage1.Controls.Add(tableLayoutPanel1);
            tabPage1.Location = new Point(4, 29);
            tabPage1.Margin = new Padding(4);
            tabPage1.Name = "tabPage1";
            tabPage1.Padding = new Padding(4);
            tabPage1.Size = new Size(520, 611);
            tabPage1.TabIndex = 0;
            tabPage1.Text = "输入参数";
            tabPage1.UseVisualStyleBackColor = true;
            //
            // tableLayoutPanel1
            //
            tableLayoutPanel1.ColumnCount = 1;
            tableLayoutPanel1.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 100F));
            tableLayoutPanel1.Controls.Add(dataGridViewFi, 0, 1);
            tableLayoutPanel1.Controls.Add(tableLayoutPanel4, 0, 0);
            tableLayoutPanel1.Dock = DockStyle.Fill;
            tableLayoutPanel1.Location = new Point(4, 4);
            tableLayoutPanel1.Name = "tableLayoutPanel1";
            tableLayoutPanel1.RowCount = 2;
            tableLayoutPanel1.RowStyles.Add(new RowStyle(SizeType.Absolute, 135F));
            tableLayoutPanel1.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel1.Size = new Size(512, 603);
            tableLayoutPanel1.TabIndex = 1;
            //
            // dataGridViewFi
            //
            dataGridViewFi.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
            dataGridViewFi.Location = new Point(3, 138);
            dataGridViewFi.Name = "dataGridViewFi";
            dataGridViewFi.RowHeadersWidth = 51;
            dataGridViewFi.Size = new Size(506, 462);
            dataGridViewFi.TabIndex = 2;
            //
            // tableLayoutPanel4
            //
            tableLayoutPanel4.ColumnCount = 1;
            tableLayoutPanel4.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 506F));
            tableLayoutPanel4.Controls.Add(tableLayoutPanel6, 0, 2);
            tableLayoutPanel4.Controls.Add(tableLayoutPanel3, 0, 0);
            tableLayoutPanel4.Controls.Add(tableLayoutPanel5, 0, 1);
            tableLayoutPanel4.Location = new Point(3, 3);
            tableLayoutPanel4.Name = "tableLayoutPanel4";
            tableLayoutPanel4.RowCount = 3;
            tableLayoutPanel4.RowStyles.Add(new RowStyle(SizeType.Absolute, 45F));
            tableLayoutPanel4.RowStyles.Add(new RowStyle(SizeType.Absolute, 45F));
            tableLayoutPanel4.RowStyles.Add(new RowStyle(SizeType.Absolute, 45F));
            tableLayoutPanel4.Size = new Size(506, 125);
            tableLayoutPanel4.TabIndex = 3;
            //
            // tableLayoutPanel6
            //
            tableLayoutPanel6.ColumnCount = 4;
            tableLayoutPanel6.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel6.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 165F));
            tableLayoutPanel6.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel6.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 165F));
            tableLayoutPanel6.Controls.Add(txtGuassSize, 1, 0);
            tableLayoutPanel6.Controls.Add(labelGuassSize, 0, 0);
            tableLayoutPanel6.Dock = DockStyle.Fill;
            tableLayoutPanel6.Location = new Point(3, 93);
            tableLayoutPanel6.Name = "tableLayoutPanel6";
            tableLayoutPanel6.RowCount = 1;
            tableLayoutPanel6.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel6.Size = new Size(500, 39);
            tableLayoutPanel6.TabIndex = 2;
            //
            // txtGuassSize
            //
            txtGuassSize.Location = new Point(88, 3);
            txtGuassSize.Name = "txtGuassSize";
            txtGuassSize.Size = new Size(159, 27);
            txtGuassSize.TabIndex = 4;
            //
            // labelGuassSize
            //
            labelGuassSize.AutoSize = true;
            labelGuassSize.Location = new Point(3, 0);
            labelGuassSize.Name = "labelGuassSize";
            labelGuassSize.Size = new Size(69, 39);
            labelGuassSize.TabIndex = 1;
            labelGuassSize.Text = "高斯核尺寸";
            //
            // tableLayoutPanel3
            //
            tableLayoutPanel3.ColumnCount = 4;
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 165F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 50F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 50F));
            tableLayoutPanel3.Controls.Add(cmbFilterType, 1, 0);
            tableLayoutPanel3.Controls.Add(btnAdd, 2, 0);
            tableLayoutPanel3.Controls.Add(labelFilterType, 0, 0);
            tableLayoutPanel3.Controls.Add(btnDel, 3, 0);
            tableLayoutPanel3.Dock = DockStyle.Fill;
            tableLayoutPanel3.Location = new Point(3, 3);
            tableLayoutPanel3.Name = "tableLayoutPanel3";
            tableLayoutPanel3.RowCount = 1;
            tableLayoutPanel3.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel3.Size = new Size(500, 39);
            tableLayoutPanel3.TabIndex = 0;
            //
            // cmbFilterType
            //
            cmbFilterType.FormattingEnabled = true;
            cmbFilterType.Location = new Point(89, 4);
            cmbFilterType.Margin = new Padding(4);
            cmbFilterType.Name = "cmbFilterType";
            cmbFilterType.Size = new Size(157, 28);
            cmbFilterType.TabIndex = 14;
            cmbFilterType.SelectedIndexChanged += cmbFilterType_SelectedIndexChanged;
            //
            // btnAdd
            //
            btnAdd.Location = new Point(253, 3);
            btnAdd.Name = "btnAdd";
            btnAdd.Size = new Size(119, 33);
            btnAdd.TabIndex = 15;
            btnAdd.Text = "添加";
            btnAdd.UseVisualStyleBackColor = true;
            btnAdd.Click += btnAdd_Click;
            //
            // labelFilterType
            //
            labelFilterType.AutoSize = true;
            labelFilterType.Location = new Point(3, 0);
            labelFilterType.MaximumSize = new Size(0, 33);
            labelFilterType.MinimumSize = new Size(0, 33);
            labelFilterType.Name = "labelFilterType";
            labelFilterType.Size = new Size(69, 33);
            labelFilterType.TabIndex = 1;
            labelFilterType.Text = "滤波类型";
            labelFilterType.TextAlign = ContentAlignment.MiddleCenter;
            //
            // btnDel
            //
            btnDel.Location = new Point(378, 3);
            btnDel.Name = "btnDel";
            btnDel.Size = new Size(119, 33);
            btnDel.TabIndex = 16;
            btnDel.Text = "删除";
            btnDel.UseVisualStyleBackColor = true;
            btnDel.Click += btnDel_Click;
            //
            // tableLayoutPanel5
            //
            tableLayoutPanel5.ColumnCount = 4;
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 165F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 165F));
            tableLayoutPanel5.Controls.Add(labelMaskWidth, 0, 0);
            tableLayoutPanel5.Controls.Add(labelMaskHeight, 2, 0);
            tableLayoutPanel5.Controls.Add(txtMaskWidth, 1, 0);
            tableLayoutPanel5.Controls.Add(txtMaskHeight, 3, 0);
            tableLayoutPanel5.Dock = DockStyle.Fill;
            tableLayoutPanel5.Location = new Point(3, 48);
            tableLayoutPanel5.Name = "tableLayoutPanel5";
            tableLayoutPanel5.RowCount = 1;
            tableLayoutPanel5.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel5.Size = new Size(500, 39);
            tableLayoutPanel5.TabIndex = 1;
            //
            // labelMaskWidth
            //
            labelMaskWidth.AutoSize = true;
            labelMaskWidth.Location = new Point(3, 0);
            labelMaskWidth.MaximumSize = new Size(0, 33);
            labelMaskWidth.MinimumSize = new Size(0, 33);
            labelMaskWidth.Name = "labelMaskWidth";
            labelMaskWidth.Size = new Size(54, 33);
            labelMaskWidth.TabIndex = 0;
            labelMaskWidth.Text = "掩膜宽";
            //
            // labelMaskHeight
            //
            labelMaskHeight.AutoSize = true;
            labelMaskHeight.Location = new Point(253, 0);
            labelMaskHeight.Name = "labelMaskHeight";
            labelMaskHeight.Size = new Size(54, 20);
            labelMaskHeight.TabIndex = 1;
            labelMaskHeight.Text = "掩膜高";
            //
            // txtMaskWidth
            //
            txtMaskWidth.Location = new Point(88, 3);
            txtMaskWidth.Name = "txtMaskWidth";
            txtMaskWidth.Size = new Size(159, 27);
            txtMaskWidth.TabIndex = 3;
            //
            // txtMaskHeight
            //
            txtMaskHeight.Location = new Point(338, 3);
            txtMaskHeight.Name = "txtMaskHeight";
            txtMaskHeight.Size = new Size(159, 27);
            txtMaskHeight.TabIndex = 4;
            //
            // tabPage5
            //
            tabPage5.Controls.Add(tableLayoutPanel2);
            tabPage5.Location = new Point(4, 29);
            tabPage5.Margin = new Padding(4);
            tabPage5.Name = "tabPage5";
            tabPage5.Size = new Size(520, 611);
            tabPage5.TabIndex = 2;
            tabPage5.Text = "运行参数";
            tabPage5.UseVisualStyleBackColor = true;
            //
            // tableLayoutPanel2
            //
            tableLayoutPanel2.ColumnCount = 4;
            tableLayoutPanel2.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 77F));
            tableLayoutPanel2.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 193F));
            tableLayoutPanel2.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 26F));
            tableLayoutPanel2.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 100F));
            tableLayoutPanel2.Controls.Add(cmbTypeRoi, 1, 0);
            tableLayoutPanel2.Controls.Add(label21, 0, 0);
            tableLayoutPanel2.Controls.Add(label22, 0, 1);
            tableLayoutPanel2.Controls.Add(cmbFixture, 1, 1);
            tableLayoutPanel2.Controls.Add(ckbDrawRoi, 2, 0);
            tableLayoutPanel2.Location = new Point(4, 4);
            tableLayoutPanel2.Margin = new Padding(4);
            tableLayoutPanel2.Name = "tableLayoutPanel2";
            tableLayoutPanel2.RowCount = 8;
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Absolute, 35F));
            tableLayoutPanel2.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel2.Size = new Size(415, 364);
            tableLayoutPanel2.TabIndex = 4;
            //
            // cmbTypeRoi
            //
            cmbTypeRoi.FormattingEnabled = true;
            cmbTypeRoi.Location = new Point(81, 4);
            cmbTypeRoi.Margin = new Padding(4);
            cmbTypeRoi.Name = "cmbTypeRoi";
            cmbTypeRoi.Size = new Size(154, 28);
            cmbTypeRoi.TabIndex = 1;
            cmbTypeRoi.SelectedIndexChanged += cmbTypeRoi_SelectedIndexChanged;
            //
            // label21
            //
            label21.AutoSize = true;
            label21.Dock = DockStyle.Fill;
            label21.Location = new Point(4, 0);
            label21.Margin = new Padding(4, 0, 4, 0);
            label21.Name = "label21";
            label21.Size = new Size(69, 35);
            label21.TabIndex = 3;
            label21.Text = "ROI";
            label21.TextAlign = ContentAlignment.MiddleCenter;
            //
            // label22
            //
            label22.AutoSize = true;
            label22.Dock = DockStyle.Fill;
            label22.Location = new Point(4, 35);
            label22.Margin = new Padding(4, 0, 4, 0);
            label22.Name = "label22";
            label22.Size = new Size(69, 35);
            label22.TabIndex = 4;
            label22.Text = "Fixture";
            label22.TextAlign = ContentAlignment.MiddleCenter;
            //
            // cmbFixture
            //
            cmbFixture.FormattingEnabled = true;
            cmbFixture.Location = new Point(81, 39);
            cmbFixture.Margin = new Padding(4);
            cmbFixture.Name = "cmbFixture";
            cmbFixture.Size = new Size(154, 28);
            cmbFixture.TabIndex = 5;
            //
            // ckbDrawRoi
            //
            ckbDrawRoi.AutoSize = true;
            ckbDrawRoi.CheckAlign = ContentAlignment.MiddleCenter;
            ckbDrawRoi.Location = new Point(274, 4);
            ckbDrawRoi.Margin = new Padding(4);
            ckbDrawRoi.Name = "ckbDrawRoi";
            ckbDrawRoi.Size = new Size(18, 17);
            ckbDrawRoi.TabIndex = 2;
            ckbDrawRoi.UseVisualStyleBackColor = true;
            ckbDrawRoi.CheckedChanged += ckbDrawRoi_CheckedChanged;
            //
            // imgTabControl
            //
            imgTabControl.Controls.Add(tabPageInputImage);
            imgTabControl.Controls.Add(tabPageRecordImage);
            imgTabControl.Dock = DockStyle.Fill;
            imgTabControl.Location = new Point(540, 4);
            imgTabControl.Margin = new Padding(4);
            imgTabControl.Name = "imgTabControl";
            imgTabControl.SelectedIndex = 0;
            imgTabControl.Size = new Size(798, 644);
            imgTabControl.TabIndex = 49;
            //
            // tabPageInputImage
            //
            tabPageInputImage.Controls.Add(pnlInputImage);
            tabPageInputImage.Location = new Point(4, 29);
            tabPageInputImage.Margin = new Padding(4);
            tabPageInputImage.Name = "tabPageInputImage";
            tabPageInputImage.Padding = new Padding(4);
            tabPageInputImage.Size = new Size(790, 611);
            tabPageInputImage.TabIndex = 0;
            tabPageInputImage.Text = "输入图像";
            tabPageInputImage.UseVisualStyleBackColor = true;
            //
            // tabPageRecordImage
            //
            tabPageRecordImage.Controls.Add(pnlRecordImage);
            tabPageRecordImage.Location = new Point(4, 29);
            tabPageRecordImage.Margin = new Padding(4);
            tabPageRecordImage.Name = "tabPageRecordImage";
            tabPageRecordImage.Padding = new Padding(4);
            tabPageRecordImage.Size = new Size(790, 611);
            tabPageRecordImage.TabIndex = 1;
            tabPageRecordImage.Text = "结果图像";
            tabPageRecordImage.UseVisualStyleBackColor = true;
            //
            // pnlRecordImage
            //
            pnlRecordImage.Dock = DockStyle.Fill;
            pnlRecordImage.Location = new Point(4, 4);
            pnlRecordImage.Margin = new Padding(5);
            pnlRecordImage.Name = "pnlRecordImage";
            pnlRecordImage.Size = new Size(782, 603);
            pnlRecordImage.TabIndex = 45;
            //
            // HFilterToolEdit
            //
            AutoScaleDimensions = new SizeF(9F, 20F);
            AutoScaleMode = AutoScaleMode.Font;
            Controls.Add(MainTableLayoutPanel);
            Controls.Add(BtmStatusStrip);
            Controls.Add(TopToolStrip);
            Margin = new Padding(3, 4, 3, 4);
            Name = "HFilterToolEdit";
            Size = new Size(1342, 705);
            Load += HFilterToolEdit_Load;
            TopToolStrip.ResumeLayout(false);
            TopToolStrip.PerformLayout();
            BtmStatusStrip.ResumeLayout(false);
            BtmStatusStrip.PerformLayout();
            MainTableLayoutPanel.ResumeLayout(false);
            parasTabControl.ResumeLayout(false);
            tabPage1.ResumeLayout(false);
            tableLayoutPanel1.ResumeLayout(false);
            ((System.ComponentModel.ISupportInitialize)dataGridViewFi).EndInit();
            tableLayoutPanel4.ResumeLayout(false);
            tableLayoutPanel6.ResumeLayout(false);
            tableLayoutPanel6.PerformLayout();
            tableLayoutPanel3.ResumeLayout(false);
            tableLayoutPanel3.PerformLayout();
            tableLayoutPanel5.ResumeLayout(false);
            tableLayoutPanel5.PerformLayout();
            tabPage5.ResumeLayout(false);
            tableLayoutPanel2.ResumeLayout(false);
            tableLayoutPanel2.PerformLayout();
            imgTabControl.ResumeLayout(false);
            tabPageInputImage.ResumeLayout(false);
            tabPageRecordImage.ResumeLayout(false);
            ResumeLayout(false);
            PerformLayout();
        }
        #endregion
        private System.Windows.Forms.Panel pnlInputImage;
        private ToolStrip TopToolStrip;
        private ToolStripButton btnRun;
        private StatusStrip BtmStatusStrip;
        private ToolStripStatusLabel lblResult;
        private ToolStripStatusLabel lblMsg;
        private TableLayoutPanel MainTableLayoutPanel;
        private ToolStripButton btnLoadImage;
        private TabControl parasTabControl;
        private TabPage tabPage1;
        private TabPage tabPage5;
        private TabControl imgTabControl;
        private TabPage tabPageInputImage;
        private TabPage tabPageRecordImage;
        private ToolStripButton btnSaveParas;
        private ToolStripButton btnLoadParas;
        private Panel pnlRecordImage;
        private ToolStripStatusLabel lblRunTime;
        private TableLayoutPanel tableLayoutPanel2;
        public ComboBox cmbTypeRoi;
        private Label label21;
        private Label label22;
        private ComboBox cmbFixture;
        private CheckBox ckbDrawRoi;
        private TableLayoutPanel tableLayoutPanel1;
        private TableLayoutPanel tableLayoutPanel3;
        private Label labelFilterType;
        private ComboBox cmbFilterType;
        private DataGridView dataGridViewFi;
        private TableLayoutPanel tableLayoutPanel4;
        private Button btnAdd;
        private TableLayoutPanel tableLayoutPanel5;
        private Label labelMaskWidth;
        private Label labelMaskHeight;
        private TextBox txtMaskWidth;
        private TextBox txtMaskHeight;
        private TableLayoutPanel tableLayoutPanel6;
        private TextBox txtGuassSize;
        private Label labelGuassSize;
        private Button btnDel;
    }
}
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterToolEdit.cs
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,611 @@
using HalconDotNet;
using LB_SmartVisionCommon;
using LB_VisionControl;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace LB_VisionProcesses.Alogrithms.Halcon
{
    public partial class HFilterToolEdit : TAlgorithmEdit
    {
        List<RecordFilterData> recordFilterDatas = new List<RecordFilterData>();
        private int rowriginalHeight;
        public HFilterToolEdit(HFilterTool subject = null)
        {
            if (subject != null && subject is HFilterTool)
                Subject = subject;
            else
                Subject = new HFilterTool();
            //if (!(Subject.Params.ROI is HSegment))
            //    Subject.Params.ROI = new HSegment(0, 0, 250, 250);
            this.Dock = DockStyle.Fill;
            InitializeComponent();
            // ä¿å­˜åŽŸå§‹è¡Œé«˜åº¦
            rowriginalHeight = (int)tableLayoutPanel4.RowStyles[1].Height; //45;
            recordFilterDatas = FilterManager.Instance.GetAllUsers();
            InitializeComboBox();
            InitializeDataGridView();
            this.dataGridViewFi.DataSource = recordFilterDatas;
            this.dataGridViewFi.AutoGenerateColumns = true;
        }
        private void InitializeComboBox()
        {
            // æ·»åŠ æƒé™é€‰é¡¹
            foreach (var item in Enum.GetValues(typeof(FilterType)))
            {
                cmbFilterType.Items.Add(item.ToString());
            }
            // è®¾ç½®é»˜è®¤é€‰æ‹©é¡¹
            cmbFilterType.SelectedIndex = 0;
        }
        private void InitializeDataGridView()
        {
            this.dataGridViewFi.DataSource = recordFilterDatas;
            // è®¾ç½®DataGridView列宽
            dataGridViewFi.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
        }
        /// <summary>
        /// æŽ§ä»¶åŠ è½½äº‹ä»¶
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void HFilterToolEdit_Load(object sender, EventArgs e)
        {
            pnlInputImage.Controls.Add(inputImageHSmartWindowControl);
            inputImageHSmartWindowControl.Dock = DockStyle.Fill;
            pnlRecordImage.Controls.Add(recordImageHSmartWindowControl);
            recordImageHSmartWindowControl.Dock = DockStyle.Fill;
            //遍历可以选择的Roi类型枚举
            foreach (var value in Enum.GetValues(typeof(RoiType)))
                cmbTypeRoi.Items.Add(value.ToString());
            //遍历可以选择的图像滤波类型枚举
            //foreach (var value in Enum.GetValues(typeof(FilterType)))
            //    cmbFilterType.Items.Add(value.ToString());
            //遍历可以选择的Fixture枚举
            cmbFixture.Items.Add("");
            foreach (string value in IProcess.dicFixtures.Keys)
                cmbFixture.Items.Add(value.ToString());
            ckbDrawRoi.Checked = true;
            cmbTypeRoi.Text = RoiType.Segment.ToString();
            cmbFilterType.Text = FilterType.均值滤波_MeanImage.ToString();
            LoadParas();
            if (Subject.Result)
            {
                lblResult.BackColor = Color.Green;
                lblResult.Text = "True";
            }
            else
            {
                lblResult.BackColor = Color.Red;
                lblResult.Text = "False";
            }
            lblMsg.Text = Msg.Length > 50 ? Msg.Substring(0, 50) : Msg;
            lblMsgToolTip.SetToolTip(BtmStatusStrip, Msg);
            lblRunTime.Text = $"{Subject.RunTime}ms";
        }
        private void ClearInputFields()
        {
            txtMaskWidth.Clear();
            txtMaskHeight.Clear();
            txtGuassSize.Clear();
            cmbFilterType.SelectedIndex = 0;
        }
        /// <summary>
        /// æ·»åŠ ç®—å­
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void btnAdd_Click(object sender, EventArgs e)
        {
            // éªŒè¯è¾“å…¥
            switch (cmbFilterType.SelectedIndex)
            {
                case 0:
                    if (string.IsNullOrWhiteSpace(txtMaskWidth.Text) || string.IsNullOrWhiteSpace(txtMaskHeight.Text))
                    {
                        MessageBox.Show("请填写所有必填字段!", "提示",
                            MessageBoxButtons.OK, MessageBoxIcon.Warning);
                        return;
                    }
                    break;
                case 1:
                    if (string.IsNullOrWhiteSpace(txtGuassSize.Text))
                    {
                        MessageBox.Show("请填写所有必填字段!", "提示",
                            MessageBoxButtons.OK, MessageBoxIcon.Warning);
                        return;
                    }
                    break;
                case 2:
                    if (string.IsNullOrWhiteSpace(txtMaskWidth.Text) || string.IsNullOrWhiteSpace(txtMaskHeight.Text))
                    {
                        MessageBox.Show("请填写所有必填字段!", "提示",
                            MessageBoxButtons.OK, MessageBoxIcon.Warning);
                        return;
                    }
                    break;
            }
            RecordFilterData filter = new RecordFilterData();
            filter.MaskWidth = this.txtMaskWidth.Text;
            filter.MaskHight = this.txtMaskHeight.Text;
            filter.GaussSize = this.txtGuassSize.Text;
            filter.FilterName = (FilterType)this.cmbFilterType.SelectedIndex;
            // æ·»åŠ åˆ° UserManager
            bool success = FilterManager.Instance.AddFilter(filter);
            if (success)
            {
                recordFilterDatas.Add(filter);
                //MessageBox.Show("用户添加成功!", "提示",
                //    MessageBoxButtons.OK, MessageBoxIcon.Information);
                // æ¸…空输入框
                ClearInputFields();
            }
            else
            {
                MessageBox.Show("添加用户失败!", "错误",
                    MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            recordFilterDatas = FilterManager.Instance.GetAllUsers();
            this.dataGridViewFi.DataSource = recordFilterDatas;
            this.dataGridViewFi.AutoGenerateColumns = true;
        }
        private void btnDel_Click(object sender, EventArgs e)
        {
            // æ£€æŸ¥æ˜¯å¦æœ‰é€‰ä¸­çš„æ»¤æ³¢ç±»åž‹
            if (cmbFilterType.SelectedIndex < 0)
            {
                MessageBox.Show("请选择要删除的滤波类型!", "提示",
                    MessageBoxButtons.OK, MessageBoxIcon.Warning);
                return;
            }
            try
            {
                DataGridViewRow selectedRow = dataGridViewFi.SelectedRows[0];
                string filterToDel = selectedRow.Cells[0].Value?.ToString();
                FilterType filterToDelete = (FilterType)cmbFilterType.SelectedIndex;
                // æŸ¥æ‰¾å¯¹åº”的记录
                RecordFilterData filterToRemove = null;
                // ä»Žæœ¬åœ°åˆ—表中查找
                foreach (var filter in recordFilterDatas)
                {
                    if (filter.FilterName.ToString() == filterToDel)
                    {
                        filterToRemove = filter;
                        break;
                    }
                }
                if (filterToRemove == null)
                {
                    MessageBox.Show("未找到对应的记录!", "提示",
                        MessageBoxButtons.OK, MessageBoxIcon.Warning);
                    return;
                }
                // ç¡®è®¤åˆ é™¤
                DialogResult result = MessageBox.Show(
                    $"确定要删除 '{filterToDel}' è®°å½•吗?",
                    "确认删除",
                    MessageBoxButtons.YesNo,
                    MessageBoxIcon.Question,
                    MessageBoxDefaultButton.Button2); // é»˜è®¤é€‰æ‹©"否"
                if (result == DialogResult.No)
                    return;
                // ä»Žç®¡ç†å™¨ä¸­åˆ é™¤
                bool success = FilterManager.Instance.DeleteUser(filterToRemove);
                if (success)
                {
                    // ä»Žæœ¬åœ°åˆ—表中删除
                    recordFilterDatas.Remove(filterToRemove);
                    MessageBox.Show("删除成功!", "提示",
                        MessageBoxButtons.OK, MessageBoxIcon.Information);
                }
                else
                {
                    MessageBox.Show("删除失败!", "错误",
                        MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
                recordFilterDatas = FilterManager.Instance.GetAllUsers();
                this.dataGridViewFi.DataSource = recordFilterDatas;
                this.dataGridViewFi.AutoGenerateColumns = true;
            }
            catch (Exception ex)
            {
                MessageBox.Show("请选择要删除的算子");
            }
        }
        #region ç®—法选择下拉框
        private void cmbFilterType_SelectedIndexChanged(object sender, EventArgs e)
        {
            ComboBox cb = sender as ComboBox;
            if (cb.SelectedIndex == 0)
            {
                ShowRow1();
            }
            else if (cb.SelectedIndex == 1)
            {
                ShowRow2();
            }
            else
            {
                ShowRow1();
            }
        }
        private void ShowRow1()
        {
            // æ˜¾ç¤ºRow2(恢复高度)
            tableLayoutPanel4.RowStyles[1].SizeType = SizeType.Absolute;
            tableLayoutPanel4.RowStyles[1].Height = rowriginalHeight;
            tableLayoutPanel4.RowStyles[2].SizeType = SizeType.Absolute;
            tableLayoutPanel4.RowStyles[2].Height = 0;
            // æ˜¾ç¤ºRow2中的控件
            foreach (Control ctrl in tableLayoutPanel4.Controls)
            {
                int row = tableLayoutPanel4.GetRow(ctrl);
                if (row == 1)
                    ctrl.Visible = true;
                if (row == 2)
                    ctrl.Visible = false;
            }
        }
        private void ShowRow2()
        {
            // æ˜¾ç¤ºRow2(恢复高度)
            tableLayoutPanel4.RowStyles[1].SizeType = SizeType.Absolute;
            tableLayoutPanel4.RowStyles[1].Height = 0;
            tableLayoutPanel4.RowStyles[2].SizeType = SizeType.Absolute;
            tableLayoutPanel4.RowStyles[2].Height = rowriginalHeight;
            // æ˜¾ç¤ºRow2中的控件
            foreach (Control ctrl in tableLayoutPanel4.Controls)
            {
                int row = tableLayoutPanel4.GetRow(ctrl);
                if (row == 1)
                    ctrl.Visible = false;
                if (row == 2)
                    ctrl.Visible = true;
            }
        }
        #endregion
        #region ROI
        /// <summary>
        /// æ›´æ–°è¿è¡Œå‚æ•°
        /// </summary>
        public override void UpdataInputs()
        {
            //设置运行参数
            double dResult = 0;
            int iResult = 0;
            if (cmbFixture.Text == "")
                Subject.Params.Fixture = new Fixture();
            else if (IProcess.dicFixtures.ContainsKey(cmbFixture.Text))
                Subject.Params.Fixture = IProcess.dicFixtures[cmbFixture.Text];
            Type type = inputImageHSmartWindowControl.oRoi?.GetType();
            switch (type)
            {
                case Type t when t == typeof(HRectangle2):
                    HRectangle2 hRectangle2 = (HRectangle2)inputImageHSmartWindowControl.oRoi;
                    Subject.Params.ROI
                        = new HRectangle2(hRectangle2.X - Subject.Params.Fixture.X, hRectangle2.Y - Subject.Params.Fixture.Y
                        , hRectangle2.Phi - Subject.Params.Fixture.Phi, hRectangle2.Width, hRectangle2.Height);
                    break;
                case Type t when t == typeof(HCircle):
                    HCircle hCircle = (HCircle)inputImageHSmartWindowControl.oRoi;
                    Subject.Params.ROI
                        = new HCircle(hCircle.X - Subject.Params.Fixture.X, hCircle.Y - Subject.Params.Fixture.Y, hCircle.Radius);
                    break;
                case Type t when t == typeof(HSegment):
                    HSegment hSegment = (HSegment)inputImageHSmartWindowControl.oRoi;
                    Subject.Params.ROI
                        = new HSegment(hSegment.StartX - Subject.Params.Fixture.X, hSegment.StartY - Subject.Params.Fixture.Y
                        , hSegment.EndX - Subject.Params.Fixture.X, hSegment.EndY - Subject.Params.Fixture.Y);
                    break;
                default:
                    Subject.Params.ROI = new ROI();
                    break;
            }
        }
        /// <summary>
        /// åŠ è½½è¿è¡Œå‚æ•°
        /// </summary>
        public override void LoadParas()
        {
            this.BeginInvoke(new Action(() =>
            {
                if (Subject.InputImage != null && Subject.InputImage is HObject)
                    inputImageHSmartWindowControl.ShowHoImage((HObject)Subject.InputImage);
                Type type = Subject.Params.ROI?.GetType();
                if (Subject.Params.ROI != null)
                {
                    switch (type)
                    {
                        case Type t when t == typeof(HRectangle2):
                            cmbTypeRoi.Text = RoiType.Rectangle2.ToString();
                            break;
                        case Type t when t == typeof(HCircle):
                            cmbTypeRoi.Text = RoiType.Circle.ToString();
                            break;
                        case Type t when t == typeof(HSegment):
                            cmbTypeRoi.Text = RoiType.Segment.ToString();
                            break;
                        default:
                            cmbTypeRoi.Text = RoiType.None.ToString();
                            break;
                    }
                    if (cmbTypeRoi.Text.ToString() != "None")
                        ckbDrawRoi.Checked = true;
                    else
                        ckbDrawRoi.Checked = false;
                    inputImageHSmartWindowControl.oRoi = Subject.Params.ROI;
                }
                if (Subject.Params.Fixture != null)
                    cmbFixture.Text = Subject.Params.Fixture.strName;
                else
                    cmbFixture.Text = "";
                switch (type)
                {
                    case Type t when t == typeof(HRectangle2):
                        inputImageHSmartWindowControl.oRoi
                             = new HRectangle2(Subject.Params.ROI.X + Subject.Params.Fixture.X, Subject.Params.ROI.Y + Subject.Params.Fixture.Y
                             , Subject.Params.ROI.Phi + Subject.Params.Fixture.Phi, ((HRectangle2)Subject.Params.ROI).Width, ((HRectangle2)Subject.Params.ROI).Height);
                        break;
                    case Type t when t == typeof(HCircle):
                        inputImageHSmartWindowControl.oRoi
                        = new HCircle(Subject.Params.ROI.X + Subject.Params.Fixture.X, Subject.Params.ROI.Y + Subject.Params.Fixture.Y
                        , ((HCircle)Subject.Params.ROI).Radius);
                        break;
                    case Type t when t == typeof(HSegment):
                        inputImageHSmartWindowControl.oRoi
                        = new HSegment(((HSegment)Subject.Params.ROI).StartX + Subject.Params.Fixture.X, ((HSegment)Subject.Params.ROI).StartY + Subject.Params.Fixture.Y
                        , ((HSegment)Subject.Params.ROI).EndX + Subject.Params.Fixture.X, ((HSegment)Subject.Params.ROI).EndY + Subject.Params.Fixture.Y);
                        break;
                    default:
                        inputImageHSmartWindowControl.oRoi = null;
                        break;
                }
                base.LoadParas();
            }));
        }
        #endregion
        #region å·¥å…·æ æŒ‰é’®äº‹ä»¶
        /// <summary>
        /// ç‚¹å‡»è¿è¡Œ
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        public override void btnRun_Click(object sender, EventArgs e)
        {
            if (Subject.InputImage != null)
                InputImage = Subject.InputImage;
            DateTime StartTime = DateTime.Now;
            Run();
            //更新日志与结果
            this.BeginInvoke(new Action(() =>
            {
                if (Subject.Result)
                {
                    lblResult.BackColor = Color.Green;
                    lblResult.Text = "True";
                    recordImageHSmartWindowControl.SetColor("green");
                }
                else
                {
                    lblResult.BackColor = Color.Red;
                    lblResult.Text = "False";
                    recordImageHSmartWindowControl.SetColor("red");
                }
                lblMsg.Text = Msg.Length > 50 ? Msg.Substring(0, 50) : Msg;
                lblMsgToolTip.SetToolTip(BtmStatusStrip, Msg);
                lblRunTime.Text = $"{(DateTime.Now - StartTime).TotalMilliseconds}ms";
                UpdataOutputs();
                imgTabControl.SelectedTab = tabPageRecordImage;
                if (Subject.InputImage != null && Subject.InputImage is HObject)
                {
                    HOperatorSet.GetImageSize((HObject)Subject.InputImage, out HTuple ho_ImageWidth, out HTuple ho_ImageHeight);
                    recordImageHSmartWindowControl.ShowHoImage((HObject)Subject.InputImage);
                }
                //先判断子类再判断父类
                if (Subject.Record != null && Subject.Record is MsgRecord msgRecord)
                {
                    recordImageHSmartWindowControl.DispObj(msgRecord.RecordObject_OK, true);
                    recordImageHSmartWindowControl.DispObj(msgRecord.RecordObject_NG, false);
                    for (int i = 0; i < msgRecord.Msg.Length; i++)
                        recordImageHSmartWindowControl.ShowMsg(msgRecord.Msg[i]
                            , 1 == msgRecord.Result[i] ? true : false, msgRecord.Column[i], msgRecord.Row[i]);
                }
                else if (Subject.Record != null && Subject.Record is ObjectRecord objRecord)
                {
                    recordImageHSmartWindowControl.DispObj(objRecord.RecordObject_OK, true);
                    recordImageHSmartWindowControl.DispObj(objRecord.RecordObject_NG, false);
                }
                GC.Collect();
            }));
        }
        /// <summary>
        /// å·¥å…·æ â€œå¯¼å›¾â€
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        public override void btnLoadImage_Click(object sender, EventArgs e)
        {
            OpenFileDialog openFileDialog = new OpenFileDialog();
            // è®¾ç½®æ–‡ä»¶å¯¹è¯æ¡†çš„属性
            openFileDialog.Multiselect = false; // ä¸å…è®¸å¤šé€‰
            // è®¾ç½®æ–‡ä»¶è¿‡æ»¤å™¨ï¼Œæ”¯æŒå¤šç§æ–‡ä»¶ç±»åž‹
            openFileDialog.Filter = "Image Files (*.png;*.jpg;*.jpeg;*.bmp)|*.png;*.jpg;*.jpeg;*.bmp|All Files (*.*)|*.*";
            // æ˜¾ç¤ºæ–‡ä»¶å¯¹è¯æ¡†
            DialogResult result = openFileDialog.ShowDialog();
            // å¤„理对话框返回结果
            if (result == DialogResult.OK)
            {
                // èŽ·å–ç”¨æˆ·é€‰æ‹©çš„æ–‡ä»¶å
                string[] selectedFiles = openFileDialog.FileNames;
                if (selectedFiles.Length > 0)
                {
                    HOperatorSet.ReadImage(out HObject ho_Image, selectedFiles[0]);
                    //判断是否为灰度图
                    using (HDevDisposeHelper dh = new HDevDisposeHelper())
                    {
                        HOperatorSet.CountChannels(ho_Image, out HTuple hv_Channels);
                        if (hv_Channels.TupleInt() != 1)
                        {
                            HOperatorSet.Rgb1ToGray(ho_Image, out ho_Image);
                            //更新日志与结果
                            this.BeginInvoke(new Action(() =>
                            {
                                lblMsg.Text = "导入图片非灰度图,自动转换为灰度图";
                            }));
                        }
                        InputImage = ho_Image;
                        imgTabControl.SelectedTab = tabPageInputImage;
                        inputImageHSmartWindowControl.oRoi = inputImageHSmartWindowControl.oRoi;
                    }
                }
            }
        }
        /// <summary>
        /// å·¥å…·æ â€œä¿å­˜â€
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        public override void btnSaveParas_Click(object sender, EventArgs e) { base.btnSaveParas_Click(sender, e); }
        #endregion
        #region ROI功能
        /// <summary>
        /// æ˜¯å¦å¯ç”¨ROI
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        public override void ckbDrawRoi_CheckedChanged(object sender, EventArgs e)
        {
            if (ckbDrawRoi.Checked)
            {
                inputImageHSmartWindowControl.bAollowDraw = true;
                imgTabControl.SelectedTab = tabPageInputImage;
            }
            else
            {
                inputImageHSmartWindowControl.bAollowDraw = false;
                Subject.Params.ROI = new ROI();
            }
        }
        /// <summary>
        /// ROI下拉框改变事件
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        public override void cmbTypeRoi_SelectedIndexChanged(object sender, EventArgs e)
        {
            try
            {
                if (Enum.TryParse(cmbTypeRoi.Text.ToString(), out RoiType type))
                {
                    HTuple hv_imageWidth = 0;
                    HTuple hv_imageHeight = 0;
                    if (InputImage != null && InputImage is HObject)
                        HOperatorSet.GetImageSize((HObject)InputImage, out hv_imageWidth, out hv_imageHeight);
                    switch (type)
                    {
                        case RoiType.Rectangle2:
                            inputImageHSmartWindowControl.oRoi
                                = new HRectangle2(hv_imageWidth.TupleReal() / 2, hv_imageHeight.TupleReal() / 2, 0
                                , hv_imageWidth.TupleReal() / 4, hv_imageHeight.TupleReal() / 4);
                            break;
                        case RoiType.Circle:
                            inputImageHSmartWindowControl.oRoi
                                = new HCircle(hv_imageWidth.TupleReal() / 2, hv_imageHeight.TupleReal() / 2, hv_imageWidth.TupleReal() / 4);
                            break;
                        case RoiType.Segment:
                            inputImageHSmartWindowControl.oRoi
                                = new HSegment(0, 0, hv_imageWidth.TupleReal() / 4, hv_imageHeight.TupleReal() / 4);
                            break;
                        case RoiType.None:
                        default:
                            inputImageHSmartWindowControl.oRoi = null;
                            break;
                    }
                }
            }
            catch { }
        }
        public override void cmbFixture_SelectedIndexChanged(object sender, EventArgs e)
        {
            try
            {
                if (IProcess.dicFixtures.ContainsKey(cmbFixture.Text))
                    Subject.Params.Fixture = IProcess.dicFixtures[cmbFixture.Text];
                else
                    Subject.Params.Fixture = new Fixture();
            }
            catch { }
        }
        #endregion
    }
}
LB_VisionProcesses/Alogrithms/Halcon/2D/HFilterTool/HFilterToolEdit.resx
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,129 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
  <!--
    Microsoft ResX Schema
    Version 2.0
    The primary goals of this format is to allow a simple XML format
    that is mostly human readable. The generation and parsing of the
    various data types are done through the TypeConverter classes
    associated with the data types.
    Example:
    ... ado.net/XML headers & schema ...
    <resheader name="resmimetype">text/microsoft-resx</resheader>
    <resheader name="version">2.0</resheader>
    <resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
    <resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
    <data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
    <data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
    <data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
        <value>[base64 mime encoded serialized .NET Framework object]</value>
    </data>
    <data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
        <value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
        <comment>This is a comment</comment>
    </data>
    There are any number of "resheader" rows that contain simple
    name/value pairs.
    Each data row contains a name, and value. The row also contains a
    type or mimetype. Type corresponds to a .NET class that support
    text/value conversion through the TypeConverter architecture.
    Classes that don't support this are serialized and stored with the
    mimetype set.
    The mimetype is used for serialized objects, and tells the
    ResXResourceReader how to depersist the object. This is currently not
    extensible. For a given mimetype the value must be set accordingly:
    Note - application/x-microsoft.net.object.binary.base64 is the format
    that the ResXResourceWriter will generate, however the reader can
    read any of the formats listed below.
    mimetype: application/x-microsoft.net.object.binary.base64
    value   : The object must be serialized with
            : System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
            : and then encoded with base64 encoding.
    mimetype: application/x-microsoft.net.object.soap.base64
    value   : The object must be serialized with
            : System.Runtime.Serialization.Formatters.Soap.SoapFormatter
            : and then encoded with base64 encoding.
    mimetype: application/x-microsoft.net.object.bytearray.base64
    value   : The object must be serialized into a byte array
            : using a System.ComponentModel.TypeConverter
            : and then encoded with base64 encoding.
    -->
  <xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
    <xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
    <xsd:element name="root" msdata:IsDataSet="true">
      <xsd:complexType>
        <xsd:choice maxOccurs="unbounded">
          <xsd:element name="metadata">
            <xsd:complexType>
              <xsd:sequence>
                <xsd:element name="value" type="xsd:string" minOccurs="0" />
              </xsd:sequence>
              <xsd:attribute name="name" use="required" type="xsd:string" />
              <xsd:attribute name="type" type="xsd:string" />
              <xsd:attribute name="mimetype" type="xsd:string" />
              <xsd:attribute ref="xml:space" />
            </xsd:complexType>
          </xsd:element>
          <xsd:element name="assembly">
            <xsd:complexType>
              <xsd:attribute name="alias" type="xsd:string" />
              <xsd:attribute name="name" type="xsd:string" />
            </xsd:complexType>
          </xsd:element>
          <xsd:element name="data">
            <xsd:complexType>
              <xsd:sequence>
                <xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
                <xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
              </xsd:sequence>
              <xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
              <xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
              <xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
              <xsd:attribute ref="xml:space" />
            </xsd:complexType>
          </xsd:element>
          <xsd:element name="resheader">
            <xsd:complexType>
              <xsd:sequence>
                <xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
              </xsd:sequence>
              <xsd:attribute name="name" type="xsd:string" use="required" />
            </xsd:complexType>
          </xsd:element>
        </xsd:choice>
      </xsd:complexType>
    </xsd:element>
  </xsd:schema>
  <resheader name="resmimetype">
    <value>text/microsoft-resx</value>
  </resheader>
  <resheader name="version">
    <value>2.0</value>
  </resheader>
  <resheader name="reader">
    <value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
  </resheader>
  <resheader name="writer">
    <value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
  </resheader>
  <metadata name="lblMsgToolTip.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
    <value>17, 17</value>
  </metadata>
  <metadata name="TopToolStrip.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
    <value>183, 17</value>
  </metadata>
  <metadata name="BtmStatusStrip.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
    <value>340, 17</value>
  </metadata>
</root>
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindCode2dTool/HFindCode2dTool.cs
@@ -2,6 +2,7 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Imaging;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
@@ -64,9 +65,30 @@
                        Result = false;
                        return;
                    }
                    if (InputImage is Bitmap)
                    {
                        try
                        {
                            using (HImage hImage = new HImage())
                            {
                                Bitmap bitmap = (Bitmap)InputImage;
                                Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                                BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                                hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                                ((Bitmap)bitmap).UnlockBits(srcBmpData);
                                bitmap.Dispose();
                                bitmap = null;
                                InputImage = null;
                                InputImage = hImage.Clone();
                            }
                        }
                        catch (Exception ex)
                        {
                        }
                    }
                    if (!(InputImage is HObject))
                    {
                        Msg = "输入图片格式不为Mat";
                        Msg = "输入图片格式不为HObject";
                        Result = false;
                        return;
                    }
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindLineTool/HFindLineTool.cs
@@ -3,6 +3,7 @@
using LB_VisionProcesses.Alogrithms.Halcon;
using System;
using System.Collections.Generic;
using System.Drawing.Imaging;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
@@ -61,6 +62,33 @@
                    Result = false;
                    return;
                }
                if (InputImage is Bitmap)
                {
                    try
                    {
                        using (HImage hImage = new HImage())
                        {
                            Bitmap bitmap = (Bitmap)InputImage;
                            Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                            BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                            hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                            ((Bitmap)bitmap).UnlockBits(srcBmpData);
                            bitmap.Dispose();
                            bitmap = null;
                            InputImage = null;
                            InputImage = hImage.Clone();
                        }
                    }
                    catch (Exception ex)
                    {
                    }
                }
                if (!(InputImage is HObject))
                {
                    Msg = "输入图片格式不为HObject";
                    Result = false;
                    return;
                }
                #region è£å‰ªåŒºåŸŸ
                if (!(Params.ROI is HSegment))
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindModelTool/HFindModelTool.cs
@@ -5,6 +5,7 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Drawing.Imaging;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
@@ -93,6 +94,27 @@
                        Result = false;
                        return;
                    }
                    if (InputImage is Bitmap)
                    {
                        try
                        {
                            using (HImage hImage = new HImage())
                            {
                                Bitmap bitmap = (Bitmap)InputImage;
                                Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                                BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                                hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                                ((Bitmap)bitmap).UnlockBits(srcBmpData);
                                bitmap.Dispose();
                                bitmap = null;
                                InputImage = null;
                                InputImage = hImage.Clone();
                            }
                        }
                        catch (Exception ex)
                        {
                        }
                    }
                    if (!(InputImage is HObject))
                    {
                        Msg = "输入图片格式不为HObject";
LB_VisionProcesses/Alogrithms/Halcon/2D/HFindMultiModelTool/HFindMultiModelTool.cs
@@ -5,6 +5,7 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Drawing.Imaging;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
@@ -88,9 +89,30 @@
                        Result = false;
                        return;
                    }
                    if (InputImage is Bitmap)
                    {
                        try
                        {
                            using (HImage hImage = new HImage())
                            {
                                Bitmap bitmap = (Bitmap)InputImage;
                                Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                                BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                                hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                                ((Bitmap)bitmap).UnlockBits(srcBmpData);
                                bitmap.Dispose();
                                bitmap = null;
                                InputImage = null;
                                InputImage = hImage.Clone();
                            }
                        }
                        catch (Exception ex)
                        {
                        }
                    }
                    if (!(InputImage is HObject))
                    {
                        Msg = "输入图片格式不为Mat";
                        Msg = "输入图片格式不为HObject";
                        Result = false;
                        return;
                    }
LB_VisionProcesses/Alogrithms/Halcon/2D/HImageEnhancementTool/HImageEnhancementTool.cs
@@ -1,7 +1,9 @@
using HalconDotNet;
using LB_SmartVisionCommon;
using LB_VisionControl;
using System;
using System.Collections.Generic;
using System.Drawing.Imaging;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
@@ -11,13 +13,13 @@
{
    public enum ImageEnhancementType { Emphasize, EquHisto, ScaleMax }
    [Process("Halcon图像增强", Category = "Halcon2D工具", Description = "创建图像增强工具")]
    [Process("Halcon2D图像增强", Category = "Halcon2D工具", Description = "创建图像增强工具")]
    public class HImageEnhancementTool : TAlgorithm
    {
        public HImageEnhancementTool()
        {
            strProcessClass = "LB_VisionProcesses.Alogrithms.Halcon.HImageEnhancementTool";
            strProcessName = "Halcon图像增强工具";
            strProcessName = "Halcon2D图像增强工具";
            Params.Inputs.Add("滤波器类型", "边缘增强");
            Params.Inputs.Add("掩膜宽", 1);
@@ -34,6 +36,7 @@
            Params.ROI = new HSegment(0, 0, 250, 250);
        }
    
        List<RecordImageEnhancementData> recordImageEnhancementDatas = new List<RecordImageEnhancementData>();
        /// <summary>
        /// ç®—子逻辑
        /// </summary>
@@ -53,23 +56,56 @@
                    Result = false;
                    return;
                }
                #region è£å‰ªåŒºåŸŸ
                if (!(Params.ROI is HSegment))
                if (InputImage is Bitmap)
                {
                    Msg = "ROI类型错误,必须为HSegment类型";
                    Result = false;
                    return;
                    try
                    {
                        using (HImage hImage = new HImage())
                        {
                            Bitmap bitmap = (Bitmap)InputImage;
                            Rectangle rect = new Rectangle(0, 0, ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height);
                            BitmapData srcBmpData = ((Bitmap)bitmap).LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppRgb);
                            hImage.GenImageInterleaved(srcBmpData.Scan0, "rgbx", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, "byte", ((Bitmap)bitmap).Width, ((Bitmap)bitmap).Height, 0, 0, -1, 0);
                            ((Bitmap)bitmap).UnlockBits(srcBmpData);
                            bitmap.Dispose();
                            bitmap = null;
                            InputImage = null;
                            InputImage = hImage.Clone();
                }
                    }
                    catch (Exception ex)
                    {
                    }
                }
                if (!(InputImage is HObject))
                {
                    Msg = "输入图片类型错误,必须为HObject类型";
                    Msg = "输入图片格式不为HObject";
                    Result = false;
                    return;
                }
                #region è£å‰ªåŒºåŸŸ
                //if (!(Params.ROI is HSegment))
                //{
                //    Msg = "ROI类型错误,必须为HSegment类型";
                //    Result = false;
                //    return;
                //}
                HObject DomainImage = ((HObject)InputImage)?.CopyObj(1, -1);
                //if (!(InputImage is HObject))
                //{
                //    Msg = "输入图片类型错误,必须为HObject类型";
                //    Result = false;
                //    return;
                //}
                //HObject DomainImage = ((HObject)InputImage)?.CopyObj(1, -1);
                object DomainImage = null;
                if (!ReduceDomainImage(InputImage, ref DomainImage))
                {
                    Msg = "裁剪区域失败";
                    Result = false;
                    return;
                }
                #endregion
                #region ç®—子逻辑
@@ -107,29 +143,36 @@
                int hv_MaskHight = Convert.ToInt16(Params.Inputs["掩膜高"]);
                double hv_Factor = Convert.ToDouble(Params.Inputs["增强因子"]);
                Enum.TryParse(Params.Inputs["图像增强类型"]?.ToString(), out ImageEnhancementType imageEnhancementType);
                string hv_ImageEnhancementType = "scaleMax";
                switch (imageEnhancementType)
                recordImageEnhancementDatas = ImageEnhancementManager.Instance.GetAllUsers();
                string hv_ImageEnhancementType = "";
                foreach (var recordImageEnhancementData in recordImageEnhancementDatas)
                {
                    case ImageEnhancementType.Emphasize:
                    switch (recordImageEnhancementData.FilterName)
                    {
                        case ImageEnhancementDataType.边缘增强_ImageEmphasize:
                        hv_ImageEnhancementType = "emphasize";
                            hv_MaskWidth = Convert.ToInt16(recordImageEnhancementData.MaskWidth);
                            hv_MaskHight = Convert.ToInt16(recordImageEnhancementData.MaskHight);
                            hv_Factor = Convert.ToDouble(recordImageEnhancementData.Factor);
                            ImageEnhancement(hoDomainImage, out ho_Regions, hv_ImageEnhancementType, hv_MaskWidth, hv_MaskHight, hv_Factor);
                        break;
                    case ImageEnhancementType.EquHisto:
                        hv_ImageEnhancementType = "equHisto";
                        case ImageEnhancementDataType.直方图均衡化_EquHistoImage:
                            hv_ImageEnhancementType = "equhisto";
                            ImageEnhancement(hoDomainImage, out ho_Regions, hv_ImageEnhancementType, hv_MaskWidth, hv_MaskHight, hv_Factor);
                        break;
                    case ImageEnhancementType.ScaleMax:
                        case ImageEnhancementDataType.比例增强_ScaleImageMax:
                            hv_ImageEnhancementType = "scaleimageMax";
                            ImageEnhancement(hoDomainImage, out ho_Regions, hv_ImageEnhancementType, hv_MaskWidth, hv_MaskHight, hv_Factor);
                            break;
                    default:
                        hv_ImageEnhancementType = "scaleMax";
                            hv_ImageEnhancementType = "scaleImageMax";
                            ImageEnhancement(hoDomainImage, out ho_Regions, hv_ImageEnhancementType, hv_MaskWidth, hv_MaskHight, hv_Factor);
                        break;
                }
                double hv_Row1 = Convert.ToDouble(((HSegment)Params.ROI).BeginRow + Params.Fixture.Row);
                double hv_Column1 = Convert.ToDouble(((HSegment)Params.ROI).BeginColumn + Params.Fixture.Column);
                double hv_Row2 = Convert.ToDouble(((HSegment)Params.ROI).EndRow + Params.Fixture.Row);
                double hv_Column2 = Convert.ToDouble(((HSegment)Params.ROI).EndColumn + Params.Fixture.Column);
                ImageEnhancement(hoDomainImage, out ho_Regions, hv_ImageEnhancementType, hv_Column1, hv_Row2, hv_Column2);
                }
                #endregion
LB_VisionProcesses/Alogrithms/Halcon/2D/HImageEnhancementTool/HImageEnhancementToolEdit.Designer.cs
@@ -50,6 +50,7 @@
            cmbImageEnhancement = new ComboBox();
            btnAdd = new Button();
            labelImageEnhancement = new Label();
            btnDel = new Button();
            tableLayoutPanel5 = new TableLayoutPanel();
            labelMaskWidth = new Label();
            labelMaskHeight = new Label();
@@ -91,7 +92,7 @@
            pnlInputImage.Location = new Point(4, 4);
            pnlInputImage.Margin = new Padding(5);
            pnlInputImage.Name = "pnlInputImage";
            pnlInputImage.Size = new Size(782, 603);
            pnlInputImage.Size = new Size(768, 603);
            pnlInputImage.TabIndex = 44;
            // 
            // TopToolStrip
@@ -111,6 +112,7 @@
            btnRun.Name = "btnRun";
            btnRun.Size = new Size(43, 24);
            btnRun.Text = "运行";
            btnRun.Click += btnRun_Click;
            // 
            // btnLoadImage
            // 
@@ -118,6 +120,7 @@
            btnLoadImage.Name = "btnLoadImage";
            btnLoadImage.Size = new Size(43, 24);
            btnLoadImage.Text = "导图";
            btnLoadImage.Click += btnLoadImage_Click;
            // 
            // btnSaveParas
            // 
@@ -125,6 +128,7 @@
            btnSaveParas.Name = "btnSaveParas";
            btnSaveParas.Size = new Size(43, 24);
            btnSaveParas.Text = "保存";
            btnSaveParas.Click += btnSaveParas_Click;
            // 
            // btnLoadParas
            // 
@@ -165,8 +169,8 @@
            // MainTableLayoutPanel
            // 
            MainTableLayoutPanel.ColumnCount = 2;
            MainTableLayoutPanel.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 40F));
            MainTableLayoutPanel.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 60F));
            MainTableLayoutPanel.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 41F));
            MainTableLayoutPanel.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 59F));
            MainTableLayoutPanel.Controls.Add(parasTabControl, 0, 0);
            MainTableLayoutPanel.Controls.Add(imgTabControl, 1, 0);
            MainTableLayoutPanel.Dock = DockStyle.Fill;
@@ -187,7 +191,7 @@
            parasTabControl.Margin = new Padding(4);
            parasTabControl.Name = "parasTabControl";
            parasTabControl.SelectedIndex = 0;
            parasTabControl.Size = new Size(528, 644);
            parasTabControl.Size = new Size(542, 644);
            parasTabControl.TabIndex = 48;
            // 
            // tabPage1
@@ -197,7 +201,7 @@
            tabPage1.Margin = new Padding(4);
            tabPage1.Name = "tabPage1";
            tabPage1.Padding = new Padding(4);
            tabPage1.Size = new Size(520, 611);
            tabPage1.Size = new Size(534, 611);
            tabPage1.TabIndex = 0;
            tabPage1.Text = "输入参数";
            tabPage1.UseVisualStyleBackColor = true;
@@ -214,16 +218,17 @@
            tableLayoutPanel1.RowCount = 2;
            tableLayoutPanel1.RowStyles.Add(new RowStyle(SizeType.Absolute, 135F));
            tableLayoutPanel1.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel1.Size = new Size(512, 603);
            tableLayoutPanel1.Size = new Size(526, 603);
            tableLayoutPanel1.TabIndex = 1;
            // 
            // dataGridViewIE
            // 
            dataGridViewIE.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
            dataGridViewIE.Dock = DockStyle.Fill;
            dataGridViewIE.Location = new Point(3, 138);
            dataGridViewIE.Name = "dataGridViewIE";
            dataGridViewIE.RowHeadersWidth = 51;
            dataGridViewIE.Size = new Size(506, 462);
            dataGridViewIE.Size = new Size(520, 462);
            dataGridViewIE.TabIndex = 2;
            // 
            // tableLayoutPanel4
@@ -232,45 +237,50 @@
            tableLayoutPanel4.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 100F));
            tableLayoutPanel4.Controls.Add(tableLayoutPanel3, 0, 0);
            tableLayoutPanel4.Controls.Add(tableLayoutPanel5, 0, 1);
            tableLayoutPanel4.Dock = DockStyle.Fill;
            tableLayoutPanel4.Location = new Point(3, 3);
            tableLayoutPanel4.Name = "tableLayoutPanel4";
            tableLayoutPanel4.RowCount = 2;
            tableLayoutPanel4.RowStyles.Add(new RowStyle(SizeType.Absolute, 45F));
            tableLayoutPanel4.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel4.Size = new Size(506, 125);
            tableLayoutPanel4.Size = new Size(520, 129);
            tableLayoutPanel4.TabIndex = 3;
            // 
            // tableLayoutPanel3
            // 
            tableLayoutPanel3.ColumnCount = 3;
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 125F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 100F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 125F));
            tableLayoutPanel3.ColumnCount = 4;
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 172F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 50F));
            tableLayoutPanel3.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 50F));
            tableLayoutPanel3.Controls.Add(cmbImageEnhancement, 1, 0);
            tableLayoutPanel3.Controls.Add(btnAdd, 2, 0);
            tableLayoutPanel3.Controls.Add(labelImageEnhancement, 0, 0);
            tableLayoutPanel3.Controls.Add(btnDel, 3, 0);
            tableLayoutPanel3.Location = new Point(3, 3);
            tableLayoutPanel3.Name = "tableLayoutPanel3";
            tableLayoutPanel3.RowCount = 1;
            tableLayoutPanel3.RowStyles.Add(new RowStyle(SizeType.Percent, 100F));
            tableLayoutPanel3.Size = new Size(500, 38);
            tableLayoutPanel3.TabIndex = 1;
            tableLayoutPanel3.Size = new Size(514, 38);
            tableLayoutPanel3.TabIndex = 0;
            // 
            // cmbImageEnhancement
            // 
            cmbImageEnhancement.DropDownStyle = ComboBoxStyle.DropDownList;
            cmbImageEnhancement.FormattingEnabled = true;
            cmbImageEnhancement.Location = new Point(129, 4);
            cmbImageEnhancement.ImeMode = ImeMode.Off;
            cmbImageEnhancement.Location = new Point(89, 4);
            cmbImageEnhancement.Margin = new Padding(4);
            cmbImageEnhancement.Name = "cmbImageEnhancement";
            cmbImageEnhancement.Size = new Size(242, 28);
            cmbImageEnhancement.Size = new Size(164, 28);
            cmbImageEnhancement.TabIndex = 14;
            cmbImageEnhancement.SelectedIndexChanged += cmbImageEnhancement_SelectedIndexChanged;
            // 
            // btnAdd
            // 
            btnAdd.Location = new Point(378, 3);
            btnAdd.Location = new Point(260, 3);
            btnAdd.Name = "btnAdd";
            btnAdd.Size = new Size(119, 30);
            btnAdd.Size = new Size(122, 30);
            btnAdd.TabIndex = 15;
            btnAdd.Text = "添加";
            btnAdd.UseVisualStyleBackColor = true;
@@ -288,13 +298,23 @@
            labelImageEnhancement.Text = "滤波类型";
            labelImageEnhancement.TextAlign = ContentAlignment.MiddleCenter;
            // 
            // btnDel
            //
            btnDel.Location = new Point(388, 3);
            btnDel.Name = "btnDel";
            btnDel.Size = new Size(123, 32);
            btnDel.TabIndex = 16;
            btnDel.Text = "删除";
            btnDel.UseVisualStyleBackColor = true;
            btnDel.Click += btnDel_Click;
            //
            // tableLayoutPanel5
            // 
            tableLayoutPanel5.ColumnCount = 4;
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 25F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 25F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 25F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 25F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 172F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 85F));
            tableLayoutPanel5.ColumnStyles.Add(new ColumnStyle(SizeType.Absolute, 172F));
            tableLayoutPanel5.Controls.Add(labelMaskWidth, 0, 0);
            tableLayoutPanel5.Controls.Add(labelMaskHeight, 2, 0);
            tableLayoutPanel5.Controls.Add(labelFactor, 0, 1);
@@ -306,8 +326,8 @@
            tableLayoutPanel5.RowCount = 2;
            tableLayoutPanel5.RowStyles.Add(new RowStyle(SizeType.Percent, 50F));
            tableLayoutPanel5.RowStyles.Add(new RowStyle(SizeType.Percent, 50F));
            tableLayoutPanel5.Size = new Size(500, 74);
            tableLayoutPanel5.TabIndex = 2;
            tableLayoutPanel5.Size = new Size(514, 74);
            tableLayoutPanel5.TabIndex = 1;
            // 
            // labelMaskWidth
            // 
@@ -321,7 +341,7 @@
            // labelMaskHeight
            // 
            labelMaskHeight.AutoSize = true;
            labelMaskHeight.Location = new Point(253, 0);
            labelMaskHeight.Location = new Point(260, 0);
            labelMaskHeight.Name = "labelMaskHeight";
            labelMaskHeight.Size = new Size(54, 20);
            labelMaskHeight.TabIndex = 1;
@@ -338,23 +358,23 @@
            // 
            // txtMaskWidth
            // 
            txtMaskWidth.Location = new Point(128, 3);
            txtMaskWidth.Location = new Point(88, 3);
            txtMaskWidth.Name = "txtMaskWidth";
            txtMaskWidth.Size = new Size(119, 27);
            txtMaskWidth.Size = new Size(166, 27);
            txtMaskWidth.TabIndex = 3;
            // 
            // txtMaskHeight
            // 
            txtMaskHeight.Location = new Point(378, 3);
            txtMaskHeight.Location = new Point(345, 3);
            txtMaskHeight.Name = "txtMaskHeight";
            txtMaskHeight.Size = new Size(119, 27);
            txtMaskHeight.Size = new Size(166, 27);
            txtMaskHeight.TabIndex = 4;
            // 
            // txtFactor
            // 
            txtFactor.Location = new Point(128, 40);
            txtFactor.Location = new Point(88, 40);
            txtFactor.Name = "txtFactor";
            txtFactor.Size = new Size(119, 27);
            txtFactor.Size = new Size(166, 27);
            txtFactor.TabIndex = 5;
            // 
            // tabPage5
@@ -363,7 +383,7 @@
            tabPage5.Location = new Point(4, 29);
            tabPage5.Margin = new Padding(4);
            tabPage5.Name = "tabPage5";
            tabPage5.Size = new Size(520, 611);
            tabPage5.Size = new Size(534, 611);
            tabPage5.TabIndex = 2;
            tabPage5.Text = "运行参数";
            tabPage5.UseVisualStyleBackColor = true;
@@ -397,13 +417,13 @@
            // 
            // cmbTypeRoi
            // 
            cmbTypeRoi.Enabled = false;
            cmbTypeRoi.FormattingEnabled = true;
            cmbTypeRoi.Location = new Point(81, 4);
            cmbTypeRoi.Margin = new Padding(4);
            cmbTypeRoi.Name = "cmbTypeRoi";
            cmbTypeRoi.Size = new Size(154, 28);
            cmbTypeRoi.TabIndex = 1;
            cmbTypeRoi.SelectedIndexChanged += cmbTypeRoi_SelectedIndexChanged;
            // 
            // label21
            // 
@@ -448,17 +468,18 @@
            ckbDrawRoi.Size = new Size(18, 17);
            ckbDrawRoi.TabIndex = 2;
            ckbDrawRoi.UseVisualStyleBackColor = true;
            ckbDrawRoi.CheckedChanged += ckbDrawRoi_CheckedChanged;
            // 
            // imgTabControl
            // 
            imgTabControl.Controls.Add(tabPageInputImage);
            imgTabControl.Controls.Add(tabPageRecordImage);
            imgTabControl.Dock = DockStyle.Fill;
            imgTabControl.Location = new Point(540, 4);
            imgTabControl.Location = new Point(554, 4);
            imgTabControl.Margin = new Padding(4);
            imgTabControl.Name = "imgTabControl";
            imgTabControl.SelectedIndex = 0;
            imgTabControl.Size = new Size(798, 644);
            imgTabControl.Size = new Size(784, 644);
            imgTabControl.TabIndex = 49;
            // 
            // tabPageInputImage
@@ -468,7 +489,7 @@
            tabPageInputImage.Margin = new Padding(4);
            tabPageInputImage.Name = "tabPageInputImage";
            tabPageInputImage.Padding = new Padding(4);
            tabPageInputImage.Size = new Size(790, 611);
            tabPageInputImage.Size = new Size(776, 611);
            tabPageInputImage.TabIndex = 0;
            tabPageInputImage.Text = "输入图像";
            tabPageInputImage.UseVisualStyleBackColor = true;
@@ -480,7 +501,7 @@
            tabPageRecordImage.Margin = new Padding(4);
            tabPageRecordImage.Name = "tabPageRecordImage";
            tabPageRecordImage.Padding = new Padding(4);
            tabPageRecordImage.Size = new Size(790, 611);
            tabPageRecordImage.Size = new Size(776, 611);
            tabPageRecordImage.TabIndex = 1;
            tabPageRecordImage.Text = "结果图像";
            tabPageRecordImage.UseVisualStyleBackColor = true;
@@ -491,7 +512,7 @@
            pnlRecordImage.Location = new Point(4, 4);
            pnlRecordImage.Margin = new Padding(5);
            pnlRecordImage.Name = "pnlRecordImage";
            pnlRecordImage.Size = new Size(782, 603);
            pnlRecordImage.Size = new Size(768, 603);
            pnlRecordImage.TabIndex = 45;
            // 
            // HImageEnhancementToolEdit
@@ -504,6 +525,7 @@
            Margin = new Padding(3, 4, 3, 4);
            Name = "HImageEnhancementToolEdit";
            Size = new Size(1342, 705);
            Load += HImageEnhancementToolEdit_Load;
            TopToolStrip.ResumeLayout(false);
            TopToolStrip.PerformLayout();
            BtmStatusStrip.ResumeLayout(false);
@@ -563,9 +585,10 @@
        private TableLayoutPanel tableLayoutPanel5;
        private Label labelMaskWidth;
        private Label labelMaskHeight;
        private Label labelFactor;
        private TextBox txtMaskWidth;
        private TextBox txtMaskHeight;
        private Label labelFactor;
        private TextBox txtFactor;
        private Button btnDel;
    }
}
LB_VisionProcesses/Alogrithms/Halcon/2D/HImageEnhancementTool/HImageEnhancementToolEdit.cs
@@ -2,6 +2,8 @@
using LB_SmartVisionCommon;
using LB_VisionControl;
using LB_VisionProcesses.Alogrithms.Halcon;
using Microsoft.VisualBasic.ApplicationServices;
using OpenCvSharp;
using Sunny.UI.Win32;
using System;
using System.Collections.Generic;
@@ -12,12 +14,13 @@
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using static System.Windows.Forms.VisualStyles.VisualStyleElement;
namespace LB_VisionProcesses.Alogrithms.Halcon
{
    public partial class HImageEnhancementToolEdit : TAlgorithmEdit
    {
        List<RecordImageEnhancementData> recordImageEnhancementDatas = new List<RecordImageEnhancementData>();
        private int rowriginalHeight;
        public HImageEnhancementToolEdit(HImageEnhancementTool subject = null)
        {
@@ -26,42 +29,47 @@
            else
                Subject = new HImageEnhancementTool();
            if (!(Subject.Params.ROI is HSegment))
                Subject.Params.ROI = new HSegment(0, 0, 250, 250);
            // ä¿å­˜åŽŸå§‹è¡Œé«˜åº¦
            rowriginalHeight = (int)tableLayoutPanel4.RowStyles[1].Height;
            //if (!(Subject.Params.ROI is HSegment))
            //    Subject.Params.ROI = new HSegment(0, 0, 250, 250);
            this.Dock = DockStyle.Fill;
            InitializeComponent();
            // ä¿å­˜åŽŸå§‹è¡Œé«˜åº¦
            rowriginalHeight = (int)tableLayoutPanel4.RowStyles[1].Height;
            InitializeComboBox();
            InitializeDataGridView();
            recordImageEnhancementDatas = ImageEnhancementManager.Instance.GetAllUsers();
            this.dataGridViewIE.DataSource = recordImageEnhancementDatas;
            this.dataGridViewIE.AutoGenerateColumns = true;
        }
        private void InitializeComboBox()
        {
            //// æ·»åŠ æƒé™é€‰é¡¹
            //foreach (var item in Enum.GetValues(typeof(UserPermission)))
            //{
            //    cmbImageEnhancement.Items.Add(item.ToString());
            //}
            cmbImageEnhancement.Items.Add("emphasize边缘增强");
            cmbImageEnhancement.Items.Add("equ_histo_image直方图均衡化");
            cmbImageEnhancement.Items.Add("scale_image_max比例增强");
            // æ·»åŠ æƒé™é€‰é¡¹
            foreach (var item in Enum.GetValues(typeof(ImageEnhancementDataType)))
            {
                cmbImageEnhancement.Items.Add(item.ToString());
            }
            // è®¾ç½®é»˜è®¤é€‰æ‹©é¡¹
            cmbImageEnhancement.SelectedIndex = 2;
        }
        #region å›¾åƒå¢žå¼ºç®—法选择下拉框
        #region ç®—法选择下拉框
        private void cmbImageEnhancement_SelectedIndexChanged(object sender, EventArgs e)
        {
            ComboBox cb = sender as ComboBox;
            System.Windows.Forms.ComboBox cb = sender as System.Windows.Forms.ComboBox;
            if (cb.SelectedIndex == 0)
            {
                ShowRow();
            }
            else if (cb.SelectedIndex == 1)
            {
                HideRow();
            }
            else
            {
                HideRow();
            }
@@ -98,13 +106,7 @@
        #endregion
        private void InitializeDataGridView()
        {
            //this.dataGridViewIE.DataSource = recordUserDatas;
            // è®¾ç½®åˆ—标题
            dataGridViewIE.Columns[0].Name = "滤波器类型";
            dataGridViewIE.Columns[1].Name = "掩膜宽度";
            dataGridViewIE.Columns[2].Name = "掩膜高度";
            dataGridViewIE.Columns[3].Name = "增强因子";
            this.dataGridViewIE.DataSource = recordImageEnhancementDatas;
            // è®¾ç½®DataGridView列宽
            dataGridViewIE.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
@@ -128,8 +130,8 @@
                cmbTypeRoi.Items.Add(value.ToString());
            //遍历可以选择的图像增强类型枚举
            foreach (var value in Enum.GetValues(typeof(ImageEnhancementType)))
                cmbImageEnhancement.Items.Add(value.ToString());
            //foreach (var value in Enum.GetValues(typeof(ImageEnhancementType)))
            //    cmbImageEnhancement.Items.Add(value.ToString());
            //遍历可以选择的Fixture枚举
            cmbFixture.Items.Add("");
@@ -138,7 +140,7 @@
            ckbDrawRoi.Checked = true;
            cmbTypeRoi.Text = RoiType.Segment.ToString();
            cmbImageEnhancement.Text = Transition.Ignore.ToString();
            cmbImageEnhancement.Text = ImageEnhancementType.ScaleMax.ToString();
            LoadParas();
            if (Subject.Result)
@@ -156,7 +158,125 @@
            lblMsgToolTip.SetToolTip(BtmStatusStrip, Msg);
            lblRunTime.Text = $"{Subject.RunTime}ms";
        }
        private void ClearInputFields()
        {
            txtMaskWidth.Clear();
            txtMaskHeight.Clear();
            txtFactor.Clear();
            cmbImageEnhancement.SelectedIndex = 0;
        }
        private void btnAdd_Click(object sender, EventArgs e)
        {
            // éªŒè¯è¾“å…¥
            if (cmbImageEnhancement.SelectedIndex == 0)
            {
                if (string.IsNullOrWhiteSpace(txtMaskWidth.Text) || string.IsNullOrWhiteSpace(txtMaskHeight.Text) || string.IsNullOrWhiteSpace(txtFactor.Text))
                {
                    MessageBox.Show("请填写所有必填字段!", "提示",
                        MessageBoxButtons.OK, MessageBoxIcon.Warning);
                    return;
                }
            }
            RecordImageEnhancementData filter = new RecordImageEnhancementData();
            filter.MaskWidth = this.txtMaskWidth.Text;
            filter.MaskHight = this.txtMaskHeight.Text;
            filter.Factor = this.txtFactor.Text;
            filter.FilterName = (ImageEnhancementDataType)this.cmbImageEnhancement.SelectedIndex;
            // æ·»åŠ åˆ° UserManager
            bool success = ImageEnhancementManager.Instance.AddUser(filter);
            if (success)
            {
                recordImageEnhancementDatas.Add(filter);
                //MessageBox.Show("用户添加成功!", "提示",
                //    MessageBoxButtons.OK, MessageBoxIcon.Information);
                // æ¸…空输入框
                ClearInputFields();
            }
            else
            {
                MessageBox.Show("添加用户失败!", "错误",
                    MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            recordImageEnhancementDatas = ImageEnhancementManager.Instance.GetAllUsers();
            this.dataGridViewIE.DataSource = recordImageEnhancementDatas;
            this.dataGridViewIE.AutoGenerateColumns = true;
        }
        private void btnDel_Click(object sender, EventArgs e)
        {
            // æ£€æŸ¥æ˜¯å¦æœ‰é€‰ä¸­çš„æ»¤æ³¢ç±»åž‹
            if (cmbImageEnhancement.SelectedIndex < 0)
            {
                MessageBox.Show("请选择要删除的滤波类型!", "提示",
                    MessageBoxButtons.OK, MessageBoxIcon.Warning);
                return;
            }
            try
            {
                DataGridViewRow selectedRow = dataGridViewIE.SelectedRows[0];
                string filterToDel = selectedRow.Cells[0].Value?.ToString();
                ImageEnhancementDataType filterToDelete = (ImageEnhancementDataType)cmbImageEnhancement.SelectedIndex;
                // æŸ¥æ‰¾å¯¹åº”的记录
                RecordImageEnhancementData filterToRemove = null;
                // ä»Žæœ¬åœ°åˆ—表中查找
                foreach (var filter in recordImageEnhancementDatas)
                {
                    if (filter.FilterName.ToString() == filterToDel)
                    {
                        filterToRemove = filter;
                        break;
                    }
                }
                if (filterToRemove == null)
                {
                    MessageBox.Show("未找到对应的记录!", "提示",
                        MessageBoxButtons.OK, MessageBoxIcon.Warning);
                    return;
                }
                // ç¡®è®¤åˆ é™¤
                DialogResult result = MessageBox.Show(
                    $"确定要删除 '{filterToDel}' è®°å½•吗?",
                    "确认删除",
                    MessageBoxButtons.YesNo,
                    MessageBoxIcon.Question,
                    MessageBoxDefaultButton.Button2); // é»˜è®¤é€‰æ‹©"否"
                if (result == DialogResult.No)
                    return;
                // ä»Žç®¡ç†å™¨ä¸­åˆ é™¤
                bool success = ImageEnhancementManager.Instance.DeleteUser(filterToRemove);
                if (success)
                {
                    // ä»Žæœ¬åœ°åˆ—表中删除
                    recordImageEnhancementDatas.Remove(filterToRemove);
                    MessageBox.Show("删除成功!", "提示",
                        MessageBoxButtons.OK, MessageBoxIcon.Information);
                }
                else
                {
                    MessageBox.Show("删除失败!", "错误",
                        MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
                recordImageEnhancementDatas = ImageEnhancementManager.Instance.GetAllUsers();
                this.dataGridViewIE.DataSource = recordImageEnhancementDatas;
                this.dataGridViewIE.AutoGenerateColumns = true;
            }
            catch (Exception ex)
            {
                MessageBox.Show("请选择要删除的算子");
            }
        }
        /// <summary>
        /// æ›´æ–°è¿è¡Œå‚æ•°
        /// </summary>
@@ -262,22 +382,8 @@
                }
            }));
        }
        private void btnAdd_Click(object sender, EventArgs e)
        {
            switch (cmbImageEnhancement.SelectedIndex)
            {
                case 0:
                    break;
                case 1:
                    break;
                case 2:
                    break;
            }
        }
        #region å·¥å…·æ æŒ‰é’®äº‹ä»¶
        /// <summary>
        /// ç‚¹å‡»è¿è¡Œ
        /// </summary>
@@ -339,7 +445,7 @@
                GC.Collect();
            }));
        }
        #region å·¥å…·æ æŒ‰é’®äº‹ä»¶
        /// <summary>
        /// å·¥å…·æ â€œå¯¼å›¾â€
        /// </summary>
@@ -449,7 +555,7 @@
            }
            catch { }
        }
        #endregion
        public override void cmbFixture_SelectedIndexChanged(object sender, EventArgs e)
        {
            try
@@ -461,6 +567,8 @@
            }
            catch { }
        }
        #endregion
       
    }
}
LB_VisionProcesses/ProcessEditForm.Designer.cs
@@ -44,11 +44,12 @@
            theme_AlgorithmForm.Font = new Font("Microsoft Sans Serif", 9F);
            theme_AlgorithmForm.Image = (Image)resources.GetObject("theme_AlgorithmForm.Image");
            theme_AlgorithmForm.Location = new Point(0, 0);
            theme_AlgorithmForm.Margin = new Padding(4);
            theme_AlgorithmForm.Name = "theme_AlgorithmForm";
            theme_AlgorithmForm.Padding = new Padding(10, 70, 10, 9);
            theme_AlgorithmForm.Padding = new Padding(12, 88, 12, 11);
            theme_AlgorithmForm.RoundCorners = true;
            theme_AlgorithmForm.Sizable = true;
            theme_AlgorithmForm.Size = new Size(944, 601);
            theme_AlgorithmForm.Size = new Size(1366, 751);
            theme_AlgorithmForm.SmartBounds = true;
            theme_AlgorithmForm.StartPosition = FormStartPosition.WindowsDefaultLocation;
            theme_AlgorithmForm.TabIndex = 0;
@@ -59,10 +60,11 @@
            pnl_ProcessEditForm.BackColor = Color.FromArgb(39, 51, 63);
            pnl_ProcessEditForm.Dock = DockStyle.Fill;
            pnl_ProcessEditForm.EdgeColor = Color.FromArgb(32, 41, 50);
            pnl_ProcessEditForm.Location = new Point(10, 70);
            pnl_ProcessEditForm.Location = new Point(12, 88);
            pnl_ProcessEditForm.Margin = new Padding(4);
            pnl_ProcessEditForm.Name = "pnl_ProcessEditForm";
            pnl_ProcessEditForm.Padding = new Padding(5);
            pnl_ProcessEditForm.Size = new Size(924, 522);
            pnl_ProcessEditForm.Padding = new Padding(6);
            pnl_ProcessEditForm.Size = new Size(1342, 652);
            pnl_ProcessEditForm.SmoothingType = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
            pnl_ProcessEditForm.TabIndex = 1;
            // 
@@ -76,7 +78,8 @@
            controlB_ProcessEditForm.EnableMaximizeButton = false;
            controlB_ProcessEditForm.EnableMinimizeButton = false;
            controlB_ProcessEditForm.ForeColor = Color.FromArgb(155, 155, 155);
            controlB_ProcessEditForm.Location = new Point(844, 18);
            controlB_ProcessEditForm.Location = new Point(1241, 18);
            controlB_ProcessEditForm.Margin = new Padding(4);
            controlB_ProcessEditForm.MaximizeHoverColor = Color.FromArgb(74, 74, 74);
            controlB_ProcessEditForm.MinimizeHoverColor = Color.FromArgb(63, 63, 65);
            controlB_ProcessEditForm.Name = "controlB_ProcessEditForm";
@@ -85,12 +88,13 @@
            // 
            // ProcessEditForm
            // 
            AutoScaleDimensions = new SizeF(96F, 96F);
            AutoScaleDimensions = new SizeF(120F, 120F);
            AutoScaleMode = AutoScaleMode.Dpi;
            ClientSize = new Size(944, 601);
            ClientSize = new Size(1366, 751);
            Controls.Add(theme_AlgorithmForm);
            FormBorderStyle = FormBorderStyle.None;
            MinimumSize = new Size(261, 61);
            Margin = new Padding(4);
            MinimumSize = new Size(326, 76);
            Name = "ProcessEditForm";
            Text = "AlgorithmForm";
            TransparencyKey = Color.Fuchsia;
LB_VisionProcesses/ProcessEditForm.resx
@@ -121,24 +121,27 @@
  <data name="theme_AlgorithmForm.Image" type="System.Drawing.Bitmap, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
    <value>
        iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAABGdBTUEAALGPC/xhBQAAAAlwSFlzAAAO
        wAAADsABataJCQAAA+JJREFUWEftVkuIHGUQbt34iMEoq2S2q3p3yTJsuqpnJ+L6WBRdwaigohfFgEou
        BkVBUPCBCEG8BXNQ48GLeImCehIJxMsqhsSZruod46K4HtSIGjU+4iOr0c1I9fSsM3/PLNtCPO0H36m/
        evz/X11VnreKVRTAHPOZumkY6lFwqURws3BwZ8ywTQnuiCP/+iTCzY1qaUPzdm/Atf3PaHre6XPsjyQM
        2xLGV4XwIyX4QRj+UMK/lPFvJTyhBMeV8IgQvmRJuH4Ko+l5p9UjGBbCJ5RxTgj+VMZmXxKcSAjekHE/
        NNs5DgaTKLinEQYVO4Trf1mkV81wixLUslPmA3bzF2XcKeP+hWY/u3n0fCXcrQwLyjAvjNsb1dI6N05P
        mFAIHlHG73sEypPgGwnhfpn0zzH7jzddcK4Q7kqfKNMI4a9K+MwBDgbdeF04MBWsFYYdQvhbLlBvfhKT
        f+vMtLfG7C0JJXxKGY67WnvCmPAFGRs7z42boul5AzHBfdK6TjdQtzPGk8oos5F/5Y7sfVvPhg+lp+1h
        0yIsxARPmtaN78WEl8eEX+SNclxUhne0glUrNrN9zfMGlPAuZTzaQ99FYfwuDv3ruoLvq5bWaQSvZCfL
        GXUYLwrj240Qxtu2lkSN4FpdWfKZH9jb9RQ1Cq62f9sVOlxUxn3KQXnJ0PO8QxU/jBm1h74v7ZniEG9K
        Hdg/quzvXO709k0Y3u08ucGqWgheX862H4XgxbR47SqU8D1X0EXC2VmGizqDz0xPr0kYH9eO360gNe0b
        jWppozB+1kOQEb5MCLa0C64NoeGrhOGrvH6lhK81GiIvnggmrDLzgvTkvwvDA+5wsU4nhG/m9AUoBD/F
        HFzWN4H0XQn2vF8eXN8Z3FAPYasl59oUYjuB+sTImDB+nhfgYQ39STf4fmu1DHtz+oIUgiM1KkWtwcFw
        sOujVT3hrnaL7UQc+hcL5W+sKIXhw0OVjaW0iwnBc47gqIQ45QY32PKRzv8eTguRYM9SS5YouEEZjv37
        EffbzbjBDdZyxZYQ12EB2qS0bWrJqRVazPDWkojwZbuZrsgZtDJ0iY1g12khEtTicMTvclwn2CKE32YJ
        7G5PORfZ1HtMCH7MOV4BrQ3XCe92+4onk5Nn2PolDAvWXnuOzAwzo6Nnx4Q3SrojwqfKeMxWMpsXWVs+
        2WrfKRdbW1W6Hf0shM/33Y7my4PrleFZIfhAaWjU/e5ivlw+y3S2FySMtynjvcrwsFiLJv/RhPBB2ws1
        hK2WcBLBFf1qawlplwvxaQlxe786OOU4PBWsjSO85mBlQ8n99r/BisSdAas4FfgHpdEUZpwUX7sAAAAA
        SUVORK5CYII=
        vgAADr4B6kKxwAAAA+xJREFUWEftV0loFUkYbvcNFzJi0lWdBEPQruqXKEYdcRgz4AYqeplBwYiXEUVB
        UHAhCEG8iR509OBlmIsOjJ5EBvQSRVHzuvslxjAy8eCG+75GozF+f716L6873fqe2ykffDR59e9/1V8V
        ow99KARtUg72J5aypGNN8xy2yJPWcleylb5gS13HnJdy+KSW6uJx3b8ZA7TKl6PbMPq3SbMsBUcpyf/2
        BP8PDh96kr32BX/rS/4O30789grfO1j/k4LQ6p8POO6XdFgpDNbDSZsn2Bt8u2MpWGdKsCPeBNMm3TZp
        FaUc6/cW20pQEtpsflCllmwxjDbpLKOd9vAZuBPOx5J+86TyMdDbBxsdYLsn+SpUZYQy/imQILLdBIP3
        cxzEU7Dbns3WejXmcNK/NPGHkajabtUiLYO/nyOgXWdRFeUkDmdnWMOg2ACFFwEn8fzfFeaSxlpjIOlT
        EHC0HVm/CstSC13B93sVFaOVszDQpwGuYGtQLipnQDlMyLzH12t2zJ8adH/TbeMbVLYROmmyDvjYRrLK
        aS4Q3Y/gtWjFALtg6KSf4NW02Uj3HwSPzOuw9iAk24sI/p5rm3OV0wyOo+++ww7pzCIViVjvAk+02GyC
        VlWnpUmw2Qggn+AV0eZ/A61oEtYsOttRwjlE5vy4L61KrabQmjBtV3I/JPtRUptcmy9UBuiM+tLc+bHs
        aQ1Rn8rNnEC7Gpvr8KcqF0XoHVCbl0qB8p2OEspS8OZmySZrvwqNtbUDMRm3Yj9kj1uB9NXcwLkfjwyu
        RAhoshuYcHMyGy4DT5T+jKrcjNbJh+yW75QIw62yqhDAvUghwV/Cybrw5UKTDn08GqmTJ9GCx660pscG
        oPoq2MHzlUWjtN8skjZbRsGFdQpiJoBkVVkFnF3tLcCv+7ZZo31mcYZGLY5RL/kCiQrcaRLFTvrikOxc
        YJF2PeZ5ZsTmAkNkCtaiW1YAkcTF1sT4YjXFEM3ekMADz+YztM8AULqlqE5nSL5wor3Zkew51nxU4WnP
        Ij9DlVGLIWCtDhV6FzBWIJH9a3pNaZOGQRsNT6tjWSHB/6LK6OUA/ETJVER/O9dgwcQ7w7XLTG0yjSTO
        Onp7Ny3A92VuuTD0rbcFbXsUMJonaQwnBV8Rniu4y2sGYbEe5emA8cORV6ZGY3n5UNycC9AKvBHZZRh+
        iqxoX9BlRWMZozvLLiSEV5V6HT2Bjz9iX0ftaAWE9sDoBV+UlOufY9FeWTmE5OhdgLH8Kxyvhv5GON3q
        C3NzSvD19C70MTco4JTDZsbtrSzUlLP5DnBV3D745riOp5nr8F/OJcYV65++P2iTfNV/MPoQCcP4AKXR
        FGYxo/VGAAAAAElFTkSuQmCC
</value>
  </data>
  <metadata name="$this.Locked" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
    <value>True</value>
  </metadata>
</root>