From dedcf4174c8540ee3a912daad2ff13e014e495b1 Mon Sep 17 00:00:00 2001
From: alielie <alielie@git.com>
Date: 星期五, 28 三月 2025 16:28:30 +0800
Subject: [PATCH] 优化UI组件;

---
 Plugin.DOControl/DOControl.xaml.cs |  474 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 470 insertions(+), 4 deletions(-)

diff --git a/Plugin.DOControl/DOControl.xaml.cs b/Plugin.DOControl/DOControl.xaml.cs
index e6e4aa3..4ec40cc 100644
--- a/Plugin.DOControl/DOControl.xaml.cs
+++ b/Plugin.DOControl/DOControl.xaml.cs
@@ -1,29 +1,465 @@
 锘縰sing HMI.Base;
+using HMI.Core.Setting;
+using HMI.Core.Util;
+using HMI.UI;
+using HMI.UI.Util;
+using log4net;
+using Panuon.WPF.UI;
+using Plugin.DOControl.Entity;
+using System;
+using System.Collections.Generic;
+using System.Collections.ObjectModel;
+using System.IO;
+using System.Linq;
 using System.Windows;
 using System.Windows.Controls;
+using System.Windows.Documents;
+using System.Windows.Media;
 
-namespace HMI.DOControl
+namespace Plugin.DOControl
 {
     /// <summary>
     /// UserControl1.xaml 鐨勪氦浜掗�昏緫
     /// </summary>
     public partial class DOControl : PluginControl
     {
+        /// <summary>
+        /// 瀹炰緥鍖栨湇鍔″櫒鎺ュ彛鍑芥暟
+        /// </summary>
+        private OpcInterface.OpcInterface lTSCADAApi = new OpcInterface.OpcInterface();
+
+        private ObservableCollection<string> groups;
+        public ObservableCollection<string> Groups
+        {
+            get => groups;
+            set
+            {
+                Set(ref groups, value);
+            }
+        }
+
+        private string selectedGroup;
+        public string SelectedGroup
+        {
+            get => selectedGroup;
+            set
+            {
+                Set(ref selectedGroup, value);
+                if (string.IsNullOrEmpty(value))
+                {
+                    selectedControls.Clear();
+                }
+                else if (GroupMap.ContainsKey(value))
+                {
+                    selectedControls = GroupMap[value];
+                }
+                RefreshControl();
+            }
+        }
+
+        private ObservableCollection<DOControlData> datasource;
+        public ObservableCollection<DOControlData> Datasource
+        {
+            get => datasource;
+            set
+            {
+                Set(ref datasource, value);
+            }
+        }
+
+        private Dictionary<string, List<DOControlData>> GroupMap = new Dictionary<string, List<DOControlData>>();
+
+        private List<FrameworkElement> visiableControls = new List<FrameworkElement>();
+        private List<DOControlData> selectedControls = new List<DOControlData>();
+
+        private System.Timers.Timer motorMonitorTimer;
+
         public DOControl()
         {
+            DataContext = this;
+            motorMonitorTimer = new System.Timers.Timer();
+            motorMonitorTimer.Interval = 200;
+            motorMonitorTimer.AutoReset = false;
+            motorMonitorTimer.Elapsed += MotorMonitorTimer_Elapsed;
             InitializeComponent();
+        }
+
+        public override void Active()
+        {
+            motorMonitorTimer.Enabled = true;
+            base.Active();
+        }
+
+        public override void DeActive()
+        {
+            motorMonitorTimer.Enabled = false;
+            base.DeActive();
+        }
+
+        public override void DoClose(object sender, EventArgs e)
+        {
+            motorMonitorTimer.Enabled = false;
+            base.DoClose(sender, e);
+        }
+
+        public static string FilePath { get; private set; }
+        public static ILog Logger { get; private set; }
+
+        public override void SetBaseFolder(string folder)
+        {
+            FilePath = Path.Combine(folder, "DOControlData.data");
+            base.SetBaseFolder(folder);
+        }
+
+        public override void SetLogger(ILog logger)
+        {
+            Logger = logger;
+            base.SetLogger(logger);
         }
 
         public override void InitFinish()
         {
             base.InitFinish();
-            
+        }
+
+        private void LoadData()
+        {
+            try
+            {
+                motorMonitorTimer.Enabled = false;
+                ObservableCollection<DOControlData> datas = new ObservableCollection<DOControlData>();
+                if (File.Exists(FilePath))
+                {
+                    datas = XmlHelper.DeserializeFromXml<ObservableCollection<DOControlData>>(FilePath);
+                }
+                Datasource = datas;
+                GroupMap = datas.GroupBy(x => x.Group)
+                   .ToDictionary(
+                       group => group.Key,
+                       group => group.ToList()
+                   );
+                Groups = new ObservableCollection<string>(GroupMap.Keys);
+                if (string.IsNullOrEmpty(SelectedGroup) && Groups.Count > 0)
+                {
+                    SelectedGroup = Groups[0];
+                }
+                else
+                {
+                    RefreshControl();
+                }
+            }
+            catch (Exception ex)
+            {
+                log.Error("Load Data Failed.", ex);
+                ToastHelper.Error(this, ex.Message);
+            }
+            finally
+            {
+                motorMonitorTimer.Enabled = true;
+            }
+        }
+
+        private void MotorMonitorTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
+        {
+            try
+            {
+                motorMonitorTimer.Enabled = false;
+                for (int i = visiableControls.Count - 1; i >= 0; i--)
+                {
+                    var ui = visiableControls[i];
+                    ui.Dispatcher.Invoke(() =>
+                    {
+                        DOControlData data = ui.Tag as DOControlData;
+                        if (data == null) return;
+                        string value = GetPlcValue(data.Address);
+                        switch (data.ControlType)
+                        {
+                            case ControlType.Button:
+                                var color = Application.Current.FindResource("VerBar") as Brush;
+                                if (value == data.PressDownValue)
+                                {
+                                    color = Application.Current.FindResource("GreenVerBar") as Brush;
+                                }
+                            ((Button)ui).Background = color;
+                                ((Button)ui).Content = value;
+                                break;
+                            case ControlType.Int16:
+                            case ControlType.Int32:
+                            case ControlType.Real:
+                            case ControlType.LReal:
+                            case ControlType.String:
+                            case ControlType.WString:
+                                ((Button)ui).Content = value;
+                                break;
+                            default:
+                                break;
+                        }
+                    });
+                }
+            }
+            finally
+            {
+                motorMonitorTimer.Enabled = true;
+            }
         }
 
 
+
+        private void RefreshControl()
+        {
+            try
+            {
+                motorMonitorTimer.Enabled = false;
+                panel0.Children.Clear();
+                panel1.Children.Clear();
+                visiableControls.Clear();
+                int index = 0;
+                foreach (string group in GroupMap.Keys)
+                {
+                    int num = index % 2;
+
+                    WrapPanel panel = new WrapPanel
+                    {
+                        Orientation = Orientation.Horizontal
+                    };
+                    GroupBox gb = new GroupBox
+                    {
+                        Header = group,
+                        Content = panel,
+                        Margin = new Thickness(0, 0, 0, 10)
+                    };
+                    var datas = GroupMap[group];
+
+                    foreach (var data in datas)
+                    {
+                        FrameworkElement ui = null;
+                        switch (data.ControlType)
+                        {
+                            case ControlType.Button:
+                            case ControlType.ClickButton:
+                                ui = CreateButton(data);
+                                break;
+                            case ControlType.Int16:
+                            case ControlType.Int32:
+                            case ControlType.Real:
+                            case ControlType.LReal:
+                            case ControlType.String:
+                            case ControlType.WString:
+                                ui = CreateNumberInput(data);
+                                break;
+                            default:
+                                break;
+                        }
+                        if (ui != null)
+                        {
+                            FormGroup fg = new FormGroup
+                            {
+                                Header = data.Name,
+                                Content = ui,
+                                Orientation = Orientation.Vertical,
+                                Margin = new Thickness(10, 0, 0, 10)
+                            };
+                            panel.Children.Add(fg);
+                            visiableControls.Add(ui);
+
+                        }
+                    }
+                    if (num == 0)
+                    {
+                        panel0.Children.Add(gb);
+                    }
+                    else
+                    {
+                        panel1.Children.Add(gb);
+                    }
+                    index++;
+                }
+            }
+            catch
+            {
+            }
+            finally
+            {
+                motorMonitorTimer.Enabled = true;
+            }
+        }
+
+        private Button CreateButton(DOControlData data)
+        {
+            Style btnStyle = Application.Current.FindResource("PrimaryButton") as Style;
+            var btn = new Button
+            {
+                Tag = data,
+                Style = btnStyle,
+                MinWidth = 180,
+                MinHeight = 40
+            };
+            if (data.ControlType == ControlType.Button)
+            {
+                btn.Click += ControlButton_Click;
+            }
+            else if (data.ControlType == ControlType.ClickButton)
+            {
+                btn.Content = data.Address;
+                btn.PreviewMouseLeftButtonDown += Btn_MouseLeftButtonDown;
+                btn.PreviewMouseLeftButtonUp += Btn_MouseLeftButtonUp;
+            }
+            return btn;
+        }
+
+        private void Btn_MouseLeftButtonDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
+        {
+            Button btn = sender as Button;
+            DOControlData data = btn.Tag as DOControlData;
+            try
+            {
+                var color = Application.Current.FindResource("GreenVerBar") as Brush;
+                btn.Background = color;
+                SetPlcValue(data.Address, data.PressDownValue);
+            }
+            catch (Exception ex)
+            {
+                log.Error("PressDownClick", ex);
+                ToastHelper.Error($"{data.Name}: {ex.Message}");
+            }
+        }
+
+        private void Btn_MouseLeftButtonUp(object sender, System.Windows.Input.MouseButtonEventArgs e)
+        {
+            Button btn = sender as Button;
+            DOControlData data = btn.Tag as DOControlData;
+            try
+            {
+                var color = Application.Current.FindResource("VerBar") as Brush;
+                btn.Background = color;
+                SetPlcValue(data.Address, data.PressUpValue);
+            }
+            catch (Exception ex)
+            {
+                log.Error("PressUpClick", ex);
+                ToastHelper.Error($"{data.Name}: {ex.Message}");
+            }
+        }
+
+        private Button CreateNumberInput(DOControlData data)
+        {
+            Style btnStyle = Application.Current.FindResource("PrimaryButton") as Style;
+            var tb = new Button
+            {
+                Tag = data,
+                Style = btnStyle,
+                MinWidth = 180,
+                MinHeight = 40,
+                BorderBrush = Brushes.Black,
+                BorderThickness = new Thickness(1),
+                Background = Brushes.White,
+                Foreground = Brushes.Black
+            };
+            if (data.ReadOnly)
+            {
+                tb.Background = Brushes.LightGray;
+                return tb;
+            }
+
+            if (data.ControlType == ControlType.String || data.ControlType == ControlType.WString)
+            {
+                tb.Click += StringInput_Click;
+            }
+            else
+            {
+                tb.Click += NumberInput_Click;
+            }
+            return tb;
+        }
+
+        /// <summary>
+        /// 璁剧疆plc鍊�
+        /// </summary>
+        /// <param name="address">鍦板潃</param>
+        /// <param name="valueType">绫诲瀷</param>
+        /// <param name="value">鍊�</param>
+        private void SetPlcValue(string key, string value)
+        {
+            if (!lTSCADAApi.DoFctWriteSingle(key, value, out string errMsg))
+            {
+                throw new Exception(errMsg);
+            }
+        }
+
+        private string GetPlcValue(string key)
+        {
+            if (lTSCADAApi.DoFctReadSingle(key, out string Val, out string errMsg))
+            {
+                return Val;
+            }
+            else
+            {
+                return null;
+            }
+        }
+
+        private void ControlButton_Click(object sender, RoutedEventArgs args)
+        {
+            Button btn = sender as Button;
+            DOControlData data = btn.Tag as DOControlData;
+            try
+            {
+                string value = btn.Content?.ToString() == data.PressDownValue ? data.PressUpValue : data.PressDownValue;
+                SetPlcValue(data.Address, value);
+            }
+            catch (Exception ex)
+            {
+                log.Error("ControlButton_Click", ex);
+                ToastHelper.Error($"{data.Name}: {ex.Message}");
+            }
+        }
+
+        private void StringInput_Click(object sender, RoutedEventArgs args)
+        {
+            Button tb = sender as Button;
+            DOControlData data = tb.Tag as DOControlData;
+
+            KeyboardWindow kw = new KeyboardWindow
+            {
+                Title = data.Name,
+                Owner = Window.GetWindow(this)
+            };
+            if (kw.Open(tb.Content?.ToString()) == true)
+            {
+                SetPlcValue(data.Address, kw.Data?.ToString());
+            }
+        }
+
+        private void NumberInput_Click(object sender, RoutedEventArgs args)
+        {
+            Button tb = sender as Button;
+            DOControlData data = tb.Tag as DOControlData;
+            NumberPanel np = new NumberPanel
+            {
+                Title = data.Name,
+                Owner = Window.GetWindow(this)
+            };
+            if (np.Open(tb.Content?.ToString()) == true)
+            {
+                SetPlcValue(data.Address, np.Data?.ToString());
+            }
+        }
+
         private void UserControl_Loaded(object sender, RoutedEventArgs e)
         {
-            
+            LoadData();
+            if (SystemSetting.Instance.PlcEnabled)
+            {
+                if (lTSCADAApi.Connect2("127.0.0.1", 6543, 18888, out string errMsg))
+                {
+                    motorMonitorTimer.Enabled = true;
+                    RefreshControl();
+                }
+                else
+                {
+                    MsgBoxHelper2.Error(errMsg);
+                }
+            }
             Loaded -= UserControl_Loaded;
         }
 
@@ -32,9 +468,14 @@
             Button btn = sender as Button;
             switch (btn.Name)
             {
-                case "queryBtn":
+                case "addBtn":
+                    OpenDataModal(null);
+                    break;
+                case "settingBtn":
+                    OpenDataList();
                     break;
                 case "resetBtn":
+                    LoadData();
                     break;
                 case "exportBtn":
                     break;
@@ -42,5 +483,30 @@
                     break;
             }
         }
+
+        private void OpenDataModal(DOControlData data)
+        {
+            DataModal modal = new DataModal
+            {
+                Title = data == null ? this.lang("App.Add") : this.lang("App.Edit"),
+                Owner = Window.GetWindow(this)
+            };
+            if (modal.Open(data ?? new DOControlData(), Datasource) == true)
+            {
+                LoadData();
+            }
+        }
+
+        private void OpenDataList()
+        {
+            ControlList list = new ControlList
+            {
+                Owner = Window.GetWindow(this)
+            };
+            if (list.Open(Datasource) == true)
+            {
+                LoadData();
+            }
+        }
     }
 }

--
Gitblit v1.9.1