Zixuan 1 week ago
parent
commit
fe29e11685

+ 14 - 2
Analizer/ProximaAnalizer/Data/LineType.cs

@@ -1,4 +1,5 @@
 using System.Collections.ObjectModel;
+using System.Text.Json.Serialization;
 using System.Windows.Media;
 
 namespace ProximaAnalizer.Data;
@@ -42,7 +43,6 @@ internal partial class LineType : ObservableObject
 {
     public LineType(string color, DoubleCollection dash)
     {
-        this.Brush = new SolidColorBrush((Color)ColorConverter.ConvertFromString("#" + color));
         this.HexRGB = color;
         this.DashArray = dash;
         if (dash[1] != 0)
@@ -54,7 +54,19 @@ internal partial class LineType : ObservableObject
     [ObservableProperty]
     private bool _IsEnable = true;
     public ScottPlot.LinePattern LinePattern { get; }
-    public string HexRGB { get; }
+
+    private string? _hex;
+    public string? HexRGB
+    {
+        get { return _hex; }
+        set
+        {
+            _hex = value;
+            this.Brush = new SolidColorBrush((Color)ColorConverter.ConvertFromString("#" + _hex));
+        }
+    }
+
+    [JsonIgnore]
     public Brush? Brush { get; set; }
     public DoubleCollection? DashArray { get; set; }
 }

+ 41 - 0
Analizer/ProximaAnalizer/Data/MFC.cs

@@ -0,0 +1,41 @@
+using Azure.Core.GeoJson;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace ProximaAnalizer.Data;
+
+internal class MFC
+{
+    public string? Name { get; set; }
+    public object? Feedback { get; set; }
+    public object? VirtualFeedBack { get; set; }
+    public object? SetPoint { get; set; }
+    public object? LastSetPoint { get; set; }
+    public object? Ramping { get; set; }
+}
+
+internal class Valve
+{
+    public string? Name { get; set; }
+    public object? Status { get; set; }
+    public object? SetPoint { get; set; }
+}
+
+internal class Heater
+{
+    public string? Name { get; set; }
+    public object? TempFeedback { get; set; }
+    public object? ControlMode { get; set; }
+    public object? TempSetPoint { get; set; }
+    public object? CascadePV { get; set; }
+    public object? CascadeControlModeSV { get; set; }
+    public object? HeaterPV { get; set; }
+    public object? HeaterControlModeSV { get; set; }
+    public object? OverTemp { get; set; }
+    public object? UpRate { get; set; }
+    public object? DownRate { get; set; }
+    public object? WorkingOutput { get; set; }
+}

+ 26 - 24
Analizer/ProximaAnalizer/Helpers/DBDataHelper.cs

@@ -93,19 +93,20 @@ internal class DBDataHelper(SqlSugarCustom sqlSugarCustom)
         _whereFunc = ObjectFuncModel.Create("Format", "time", ">", "{long}:" + $"{startTime.Ticks}", "&&", "time", "<", "{long}:" + $"{endTime.Ticks}");
     }
 
-    public bool GetPMData(out List<dynamic>? pm1)
+    public bool GetPMData(DateTime startTime, DateTime endTime, out List<dynamic>? pm1)
     {
         pm1 = null;
-        if (this._whereFunc is null)
-            return false;
+
         if (sqlSugarCustom.Client is null)
             return false;
         try
         {
+            ObjectFuncModel whereFunc = ObjectFuncModel.Create("Format", "time", ">", "{long}:" + $"{startTime.Ticks}", "&&", "time", "<", "{long}:" + $"{endTime.Ticks}");
+
             pm1 = sqlSugarCustom.Client
                 .Queryable<dynamic>()
-                .AS($"\"{StartTime:yyyyMMdd}.PM1\"")
-                .Where(_whereFunc).ToList();
+                .AS($"\"{startTime:yyyyMMdd}.PM1\"")
+                .Where(whereFunc).ToList();
         }
         catch
         {
@@ -114,27 +115,20 @@ internal class DBDataHelper(SqlSugarCustom sqlSugarCustom)
 
         return true;
     }
-
-    public bool GetPMData(IEnumerable<string> fields, out List<dynamic>? pm1)
+    public bool GetSystemData(DateTime startTime, DateTime endTime, out List<dynamic>? systemData)
     {
-        pm1 = null;
-        if (this._whereFunc is null)
-            return false;
+        systemData = default;
+
         if (sqlSugarCustom.Client is null)
             return false;
-
-        List<SelectModel> selectModels = [];
-
-        foreach (var field in fields)
-            selectModels.Add(new() { FieldName = $"\"{field}\"" });
-
         try
         {
-            pm1 = sqlSugarCustom.Client
+            ObjectFuncModel whereFunc = ObjectFuncModel.Create("Format", "time", ">", "{long}:" + $"{startTime.Ticks}", "&&", "time", "<", "{long}:" + $"{endTime.Ticks}");
+
+            systemData = sqlSugarCustom.Client
                 .Queryable<dynamic>()
-                .AS($"\"{StartTime:yyyyMMdd}.PM1\"")
-                .Select(selectModels)
-                .Where(_whereFunc).ToList();
+                .AS($"\"{startTime:yyyyMMdd}.System\"")
+                .Where(whereFunc).ToList();
         }
         catch
         {
@@ -144,18 +138,25 @@ internal class DBDataHelper(SqlSugarCustom sqlSugarCustom)
         return true;
     }
 
-    public bool GetSystemData(out List<dynamic>? systemData)
+    public bool GetPMData(IEnumerable<string> fields, out List<dynamic>? pm1)
     {
-        systemData = default;
+        pm1 = null;
         if (this._whereFunc is null)
             return false;
         if (sqlSugarCustom.Client is null)
             return false;
+
+        List<SelectModel> selectModels = [];
+
+        foreach (var field in fields)
+            selectModels.Add(new() { FieldName = $"\"{field}\"" });
+
         try
         {
-            systemData = sqlSugarCustom.Client
+            pm1 = sqlSugarCustom.Client
                 .Queryable<dynamic>()
-                .AS($"\"{StartTime:yyyyMMdd}.System\"")
+                .AS($"\"{StartTime:yyyyMMdd}.PM1\"")
+                .Select(selectModels)
                 .Where(_whereFunc).ToList();
         }
         catch
@@ -166,6 +167,7 @@ internal class DBDataHelper(SqlSugarCustom sqlSugarCustom)
         return true;
     }
 
+
     public bool GetSystemData(IEnumerable<string> fields, out List<dynamic>? systemData)
     {
         systemData = default;

+ 1 - 1
Analizer/ProximaAnalizer/Helpers/DisplayDataHelper.cs

@@ -1,6 +1,6 @@
 namespace ProximaAnalizer.Helpers;
 
-internal class DisplayDataHelper(IDictionary<string, object> Left, IDictionary<string, object> Right)
+internal class DisplayDataHelper(IDictionary<string, LineType> Left, IDictionary<string, LineType> Right)
 {
     public List<DateTime> Time { get; } = [];
     public Dictionary<string, List<float>> DataLeft { get; } = [];

+ 80 - 0
Analizer/ProximaAnalizer/Helpers/DisplayHistroyHelper.cs

@@ -0,0 +1,80 @@
+namespace ProximaAnalizer.Helpers;
+
+public partial class DisplayHistroyHelper1(int key, int value, string[] keywords) : ObservableObject
+{
+    [ObservableProperty]
+    private ObservableDictionary<string, object> _Data = [];
+
+    public void UpdateData(List<dynamic>? data)
+    {
+        if (data is null)
+            return;
+
+        if (data.FirstOrDefault() is not IDictionary<string, object> source)
+            return;
+
+        App.Current.Dispatcher?.Invoke(() =>
+        {
+            foreach (var data in source)
+            {
+                string[] keys = data.Key.Split('.');
+                if (keys.Length <= value)
+                    continue;
+
+                if (keywords.Any(t => keys[key].StartsWith(t)))
+                    this.Data[keys[value]] = data.Value;
+            }
+        });
+    }
+
+
+    public void Clear()
+    {
+        this.Data ??= [];
+        this.Data.Clear();
+    }
+}
+
+
+public partial class DisplayHistroyHelper2(int key, int value, string keyWord) : ObservableObject
+{
+    [ObservableProperty]
+    private ObservableDictionary<string, ObservableDictionary<string, object>> _Data = [];
+
+    public void UpdateData(List<dynamic>? data)
+    {
+        if (data is null)
+            return;
+
+        if (data.FirstOrDefault() is not IDictionary<string, object> source)
+            return;
+
+        App.Current.Dispatcher?.Invoke(() =>
+        {
+            foreach (var data in source)
+            {
+                string[] keys = data.Key.Split('.');
+
+                if (keys.Length <= value)
+                    continue;
+
+                if (!keys[1].StartsWith(keyWord))
+                    continue;
+
+                if (!this.Data.TryGetValue(keys[key], out var output) || output is null)
+                {
+                    output = [];
+                    this.Data[keys[key]] = output;
+                }
+
+                output[keys[value]] = data.Value;
+            }
+        });
+    }
+
+    public void Clear()
+    {
+        this.Data ??= [];
+        this.Data.Clear();
+    }
+}

+ 3 - 7
Analizer/ProximaAnalizer/PublicEvent/RefreshRecipeData.cs

@@ -1,10 +1,4 @@
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Text;
-using System.Threading.Tasks;
-
-namespace ProximaAnalizer.PublicEvent;
+namespace ProximaAnalizer.PublicEvent;
 
 internal class RefreshRecipeData : PubSubEvent
 {
@@ -12,4 +6,6 @@ internal class RefreshRecipeData : PubSubEvent
 
 internal class RefreshAlarmData : PubSubEvent
 {
+    public EventData? Selected { get; set; }
+    public Pages FromPage { get; set; }
 }

+ 231 - 28
Analizer/ProximaAnalizer/ViewModels/DBInfoAlarmViewModel.cs

@@ -1,7 +1,8 @@
-using Mapster;
+using Newtonsoft.Json.Serialization;
 using Prism.Events;
-using ProximaAnalizer.Data;
 using ProximaAnalizer.Helpers;
+using SqlSugar;
+using System.Text;
 using System.Windows;
 using Universal;
 
@@ -17,17 +18,112 @@ internal partial class DBInfoAlarmViewModel : ObservableObject
         this._traceData = traceData;
         this._DBDataHelper = dBDataHelper;
         this._dialogService = dialogService;
+        this._eventAggregator = eventAggregator;
+        CurrentChangedQueue = new(CurrentChangedQueueHandler);
+
         eventAggregator.GetEvent<RefreshAlarmData>().Subscribe(InitDisplayData);
+
     }
+    private readonly IEventAggregator _eventAggregator;
     private readonly IDialogService _dialogService;
     private readonly DBDataHelper _DBDataHelper;
     private readonly TraceData _traceData;
+    private readonly EventQueue<long> CurrentChangedQueue;
+    private Timer? _AutoPlayTimer;
+    private Pages? _FromPage;
+
+    private void InitDisplayData()
+    {
+        this.RecipeSteps.Clear();
+        this.Alarms.Clear();
+        this.MFCs.Clear();
+        this.Heaters.Clear();
+        this.GaslineHeaters.Clear();
+        this.FFUs.Clear();
+        this.Valves.Clear();
+        this.LeakChecks.Clear();
+        this.Pressures.Clear();
+        this.APCs.Clear();
+        this.APCVATGVs.Clear();
+
+
+        RefreshAlarmData alarmData = _eventAggregator.GetEvent<RefreshAlarmData>();
+        this._FromPage = alarmData.FromPage;
+
+        if (_traceData.ProcessData is null)
+            return;
+
+        this.RecipeName = _traceData.ProcessData.Recipe_Name;
+        if (!this._DBDataHelper.GetRecipeSteps(_traceData.ProcessData.Guid, out string reason, out List<RecipeStepData>? recipeSteps) || recipeSteps is null)
+        {
+            MessageBox.Show(reason, "Warning", MessageBoxButton.OK, MessageBoxImage.Warning);
+            return;
+        }
+
+        recipeSteps.Foreach(t => this.RecipeSteps.TryAdd(TimeRounder.IngoreMillionSeconds(t.Step_Begin_Time.Ticks), t));
+        this.Start = recipeSteps.First().Step_Begin_Time;
+        this.End = recipeSteps.Last().Step_End_Time;
+
+
+        this._DBDataHelper.SetTimeRange(this.Start, this.End);
+
+        if (!this._DBDataHelper.GetAlarmData(out List<EventData>? alarms) || alarms is null)
+            return;
+
+        foreach (var alarm in alarms)
+        {
+            if (alarm is null || string.IsNullOrEmpty(alarm.Level))
+                continue;
+
+            DateTime occorTime = TimeRounder.IngoreMillionSeconds(alarm.Occur_Time.Ticks);
+
+            if (!this.Alarms.TryGetValue(occorTime, out StringBuilder? events) || events is null)
+            {
+                events = new();
+                this.Alarms[occorTime] = events;
+                events.Append(alarm.Description);
+                continue;
+            }
+
+            events.Append(Environment.NewLine);
+            events.Append(alarm.Description);
+        }
+
+        if (alarmData.Selected is not null)
+        {
+            DateTime time = TimeRounder.IngoreMillionSeconds(alarmData.Selected.Occur_Time.Ticks);
+            this.Current = time;
+            this.CurrentLong = time.Ticks;
+        }
+        else
+        {
+            this.Current = this.Start;
+            this.CurrentLong = this.Start.Ticks;
+        }
+
+    }
+
+    [ObservableProperty]
+    private RecipeStepData? _CurrentRecipeStep;
+
+    [ObservableProperty]
+    private ObservableDictionary<DateTime, RecipeStepData> _RecipeSteps = [];
 
     [ObservableProperty]
-    private ObservableDictionary<DateTime, SelectRecipeStep> _RecipeSteps = [];
+    private ObservableDictionary<DateTime, StringBuilder> _Alarms = [];
 
     [ObservableProperty]
-    private ObservableDictionary<DateTime, List<EventData>> _Alarms = [];
+    private KeyValuePair<DateTime, StringBuilder>? _SelectedAlarm;
+    partial void OnSelectedAlarmChanged(KeyValuePair<DateTime, StringBuilder>? value)
+    {
+        if (value is null)
+            return;
+        this.CurrentLong = value.Value.Key.Ticks;
+    }
+
+
+    [ObservableProperty]
+    private string? _RecipeName;
 
     [ObservableProperty]
     private DateTime _Start;
@@ -39,40 +135,79 @@ internal partial class DBInfoAlarmViewModel : ObservableObject
     [ObservableProperty]
     private long _CurrentLong;
 
-    partial void OnCurrentLongChanged(long value)
+    partial void OnCurrentLongChanged(long value) => this.CurrentChangedQueue.Enqueue(value);
+    private void CurrentChangedQueueHandler(long value)
     {
-        this.Current = new(value);
+        if (CurrentChangedQueue.Count != 0)
+            return;
+
+        DateTime time = TimeRounder.IngoreMillionSeconds(value);
+
+        RecipeStepData? step = this.RecipeSteps.Where(t => t.Key <= this.Current).LastOrDefault().Value;
+        App.Current.Dispatcher?.Invoke(() =>
+        {
+            if (this.Alarms.ContainsKey(time))
+                this.SelectedAlarm = this.Alarms.Where(t => t.Key == time).FirstOrDefault();
+            else
+                this.SelectedAlarm = null;
+
+            this.Current = time;
+            this.CurrentRecipeStep = step;
+        });
+
+        DateTime startTime = time.AddMilliseconds(-500);
+        DateTime endTime = time.AddMilliseconds(500);
+        this._DBDataHelper.GetSystemData(startTime, endTime, out List<dynamic>? systemData);
+        this._DBDataHelper.GetPMData(startTime, endTime, out List<dynamic>? pmData);
+
+        Parallel.Invoke(
+            () => this.MFCs.UpdateData(pmData),
+            () => this.Heaters.UpdateData(systemData),
+            () => this.GaslineHeaters.UpdateData(pmData),
+            () => this.FFUs.UpdateData(pmData),
+            () => this.Valves.UpdateData(pmData),
+
+            () => this.LeakChecks.UpdateData(pmData),
+            () => this.Pressures.UpdateData(pmData),
+            () => this.APCs.UpdateData(pmData),
+            () => this.APCVATGVs.UpdateData(pmData));
     }
 
 
-    private void InitDisplayData()
-    {
-        if (_traceData.ProcessData is null)
-            return;
+    [ObservableProperty]
+    private Visibility _PlayVis = Visibility.Visible;
+    [ObservableProperty]
+    private Visibility _StopVis = Visibility.Collapsed;
 
-        if (!this._DBDataHelper.GetRecipeSteps(_traceData.ProcessData.Guid, out string reason, out List<RecipeStepData>? recipeSteps) || recipeSteps is null)
+    [RelayCommand]
+    private void Play(string para)
+    {
+        switch (para)
         {
-            MessageBox.Show(reason, "Warning", MessageBoxButton.OK, MessageBoxImage.Warning);
-            return;
+            case "play":
+                this._AutoPlayTimer ??= new(TimerCallback, null, 0, 1000);
+                this.PlayVis = Visibility.Collapsed;
+                this.StopVis = Visibility.Visible;
+                break;
+            case "stop":
+                this._AutoPlayTimer?.Dispose();
+                this._AutoPlayTimer = null;
+                this.PlayVis = Visibility.Visible;
+                this.StopVis = Visibility.Collapsed;
+                break;
+            default:
+                break;
         }
+    }
 
-        recipeSteps.ForEach(t => this.RecipeSteps.TryAdd(t.Step_Begin_Time, t.Adapt<SelectRecipeStep>()));
-        this.Start = recipeSteps.First().Step_Begin_Time;
-        this.End = recipeSteps.Last().Step_End_Time;
-        this.Current = recipeSteps.First().Step_Begin_Time;
-
-        this._DBDataHelper.SetTimeRange(this.Start, this.End);
-        if (!this._DBDataHelper.GetAlarmData(out List<EventData>? alarms) || alarms is null)
-            return;
-        foreach (var alarm in alarms)
+    private void TimerCallback(object? state)
+    {
+        if (this.CurrentLong >= this.End.Ticks)
         {
-            if (this.Alarms.TryGetValue(alarm.Occur_Time, out List<EventData>? events) || events is null)
-            {
-                events = [];
-                this.Alarms[alarm.Occur_Time] = events;
-            }
-            events.Add(alarm);
+            this.Play("stop");
+            return;
         }
+        App.Current.Dispatcher?.Invoke(() => this.CurrentLong += 10000000);
     }
 
     [RelayCommand]
@@ -92,9 +227,77 @@ internal partial class DBInfoAlarmViewModel : ObservableObject
             case "--":
                 this.CurrentLong -= 600000000;
                 break;
+            case "---":
+                {
+                    DateTime alarm = this.Alarms.Where(t => t.Key < this.Current).LastOrDefault().Key;
+                    if (alarm == DateTime.MinValue)
+                        break;
+                    this.CurrentLong = alarm.Ticks;
+                }
+                break;
+            case "+++":
+                {
+                    DateTime alarm = this.Alarms.Where(t => t.Key > this.Current).FirstOrDefault().Key;
+                    if (alarm == DateTime.MinValue)
+                        break;
+                    this.CurrentLong = alarm.Ticks;
+                }
+                break;
             default:
                 break;
         }
     }
 
+    [RelayCommand]
+    private void Return()
+    {
+        _eventAggregator.GetEvent<WindowSwitch>().Page = _FromPage is null ? Pages.RecipeStepNavi : _FromPage.Value;
+        _eventAggregator.GetEvent<WindowSwitch>().Publish();
+    }
+
+    [ObservableProperty]
+    private DisplayHistroyHelper2 _Heaters = new(1, 2, "Heater");
+    [ObservableProperty]
+    private DisplayHistroyHelper2 _MFCs = new(1, 2, "MFC");
+    [ObservableProperty]
+    private DisplayHistroyHelper2 _Valves = new(2, 3, "IoValve");
+    [ObservableProperty]
+    private DisplayHistroyHelper2 _FFUs = new(1, 2, "FFU");
+    [ObservableProperty]
+    private DisplayHistroyHelper2 _GaslineHeaters = new(1, 2, "GaslineHeater");
+
+    [ObservableProperty]
+    private DisplayHistroyHelper1 _LeakChecks = new(1, 1, ["LeakCheck"]);
+    [ObservableProperty]
+    private DisplayHistroyHelper1 _Pressures = new(1, 1, ["VG", "PS", "PG"]);
+    [ObservableProperty]
+    private DisplayHistroyHelper1 _APCs = new(1, 2, ["APC"]);
+    [ObservableProperty]
+    private DisplayHistroyHelper1 _APCVATGVs = new(1, 2, ["APCVATGV"]);
+
+    [ObservableProperty]
+    private object? _Selected;
+
+    partial void OnSelectedChanged(object? value)
+    {
+        switch (value)
+        {
+            case KeyValuePair<string, ObservableDictionary<string, object>> sel:
+                break;
+            case KeyValuePair<string, object> sel:
+                break;
+            default:
+                break;
+        }
+
+    }
 }
+
+internal class TimeRounder
+{
+    public static DateTime IngoreMillionSeconds(long ticks)
+    {
+        ticks -= ticks % 10000000;
+        return new(ticks);
+    }
+}

+ 159 - 7
Analizer/ProximaAnalizer/ViewModels/DBInfoTraceViewModel.cs

@@ -1,10 +1,17 @@
 using Mapster;
+using Microsoft.Win32;
+using Prism.Events;
 using ProximaAnalizer.Helpers;
 using ScottPlot;
 using ScottPlot.WPF;
 using SqlSugar;
 using System.Collections.ObjectModel;
+using System.IO;
+using System.Text;
+using System.Text.Json;
 using System.Windows;
+using System.Windows.Controls;
+using System.Windows.Media;
 using Universal;
 
 namespace ProximaAnalizer.ViewModels;
@@ -20,6 +27,7 @@ internal partial class DBInfoTraceViewModel : ObservableObject
         this._DBDataHelper = dBDataHelper;
         this._traceData = traceData;
         this._dialogService = dialogService;
+        this._eventAggregator = eventAggregator;
         this.Left = [];
         this.Right = [];
         this.PlotControl = new();
@@ -30,6 +38,7 @@ internal partial class DBInfoTraceViewModel : ObservableObject
     }
     private readonly TraceData _traceData;
     private readonly IDialogService _dialogService;
+    private readonly IEventAggregator _eventAggregator;
 
     private readonly PlotHepler _PlotHelper;
     private readonly DBDataHelper _DBDataHelper;
@@ -149,13 +158,13 @@ internal partial class DBInfoTraceViewModel : ObservableObject
 
     #region Line Operations
     [ObservableProperty]
-    private ObservableDictionary<string, object> _Left = [];
+    private ObservableDictionary<string, LineType> _Left = [];
 
     [ObservableProperty]
-    private ObservableDictionary<string, object> _Right = [];
+    private ObservableDictionary<string, LineType> _Right = [];
 
     [RelayCommand]
-    private void EditLine(KeyValuePair<string, object> item)
+    private void EditLine(KeyValuePair<string, LineType> item)
     {
         IDialogParameters para = new DialogParameters() { { "Line", item.Key } };
         _dialogService.Show("LinePicker", para, AddLineCallback);
@@ -168,7 +177,9 @@ internal partial class DBInfoTraceViewModel : ObservableObject
         if (lineType is null || string.IsNullOrEmpty(line) || string.IsNullOrEmpty(Axis))
             return;
 
-        ObservableDictionary<string, object>? lineCollection = Axis switch
+        lineType.IsEnable = false;
+
+        ObservableDictionary<string, LineType>? lineCollection = Axis switch
         {
             "L" => Left,
             "R" => Right,
@@ -178,7 +189,7 @@ internal partial class DBInfoTraceViewModel : ObservableObject
         if (lineCollection is null)
             return;
 
-        if (lineCollection.TryGetValue(line, out object? oldType) && oldType is LineType oldLine)
+        if (lineCollection.TryGetValue(line, out LineType? oldType) && oldType is LineType oldLine)
             oldLine.IsEnable = true;
 
         lineCollection[line] = lineType;
@@ -201,7 +212,7 @@ internal partial class DBInfoTraceViewModel : ObservableObject
     [RelayCommand]
     private void RemoveLeft(string key)
     {
-        this.Left.TryRemove(key, out object? line);
+        this.Left.TryRemove(key, out LineType? line);
         if (line is LineType lineType)
             lineType.IsEnable = true;
     }
@@ -209,12 +220,125 @@ internal partial class DBInfoTraceViewModel : ObservableObject
     [RelayCommand]
     private void RemoveRight(string key)
     {
-        this.Right.TryRemove(key, out object? line);
+        this.Right.TryRemove(key, out LineType? line);
         if (line is LineType lineType)
             lineType.IsEnable = true;
     }
 
     [RelayCommand]
+    private void SaveLoad(string para)
+    {
+        switch (para)
+        {
+            case "Save":
+                {
+                    SaveFileDialog saveFileDialog = new()
+                    {
+                        Filter = "Line Picker |*.lpr;",
+                        FileName = "Default.lpr",
+                        InitialDirectory = Environment.GetFolderPath(Environment.SpecialFolder.Desktop)
+                    };
+
+                    if (saveFileDialog.ShowDialog() != true)
+                        return;
+
+                    List<LineSave> left = [];
+                    foreach (var item in this.Left)
+                    {
+                        LineSave save = new()
+                        {
+                            Direction = "L",
+                            Name = item.Key,
+                            Dash = item.Value.DashArray,
+                            Color = item.Value.HexRGB
+                        };
+                        left.Add(save);
+                    }
+
+                    foreach (var item in this.Right)
+                    {
+                        LineSave save = new()
+                        {
+                            Direction = "R",
+                            Name = item.Key,
+                            Dash = item.Value.DashArray,
+                            Color = item.Value.HexRGB
+                        };
+                        left.Add(save);
+                    }
+
+                    try
+                    {
+                        using StreamWriter sw = new(saveFileDialog.FileName);
+                        sw.WriteLine(JsonSerializer.Serialize(left));
+                        MessageBox.Show("文件保存成功", "Save Line Picker File", MessageBoxButton.OK, MessageBoxImage.Information);
+                    }
+                    catch
+                    {
+                        MessageBox.Show("文件保存失败", "Save Line Picker File", MessageBoxButton.OK, MessageBoxImage.Error);
+                    }
+
+                    return;
+                }
+
+            case "Load":
+                {
+                    OpenFileDialog open = new()
+                    {
+                        Filter = "Line Picker |*.lpr;",
+                        FileName = "Default.lpr",
+                        InitialDirectory = Environment.GetFolderPath(Environment.SpecialFolder.Desktop)
+                    };
+
+                    if (open.ShowDialog() != true)
+                        return;
+
+                    try
+                    {
+                        using StreamReader sr = new(open.FileName);
+                        string? left = sr.ReadToEnd();
+                        if (string.IsNullOrEmpty(left))
+                        {
+                            MessageBox.Show("文件读取失败", "Save Line Picker File", MessageBoxButton.OK, MessageBoxImage.Error);
+                            return;
+                        }
+
+                        if (JsonSerializer.Deserialize<List<LineSave>>(left) is not List<LineSave> lines)
+                        {
+                            MessageBox.Show("文件读取失败", "Save Line Picker File", MessageBoxButton.OK, MessageBoxImage.Error);
+                            return;
+                        }
+
+                        this.Left.Clear();
+                        this.Right.Clear();
+
+                        foreach (var line in lines)
+                        {
+                            if (string.IsNullOrEmpty(line.Name) || string.IsNullOrEmpty(line.Color) || line.Dash is null)
+                                continue;
+
+                            DialogResult result = new();
+                            result.Parameters.Add("Line", new LineType(line.Color, line.Dash));
+                            result.Parameters.Add("Name", line.Name);
+                            result.Parameters.Add("Axis", line.Direction!);
+                            this.AddLineCallback(result);
+                        }
+
+                    }
+                    catch
+                    {
+                        MessageBox.Show("文件读取失败", "Save Line Picker File", MessageBoxButton.OK, MessageBoxImage.Error);
+                    }
+
+                    return;
+                }
+            default:
+                break;
+        }
+
+    }
+
+    [RelayCommand]
     private void Clear(string para)
     {
         switch (para)
@@ -396,8 +520,36 @@ internal partial class DBInfoTraceViewModel : ObservableObject
         this.PlotControl.Refresh();
     }
     #endregion
+
+    [RelayCommand]
+    private void AlarmDetail(object para)
+    {
+        if (para is not EventData eventData)
+            return;
+
+        _eventAggregator.GetEvent<WindowSwitch>().Page = Pages.HistoryData;
+        _eventAggregator.GetEvent<WindowSwitch>().Publish();
+        RefreshAlarmData alarmData = _eventAggregator.GetEvent<RefreshAlarmData>();
+        alarmData.Selected = eventData;
+        alarmData.FromPage = Pages.MainWindow;
+        alarmData.Publish();
+    }
+
+    [RelayCommand]
+    private void ReturnPage()
+    {
+        _eventAggregator.GetEvent<WindowSwitch>().Page = Pages.RecipeStepNavi;
+        _eventAggregator.GetEvent<WindowSwitch>().Publish();
+    }
 }
 
+public class LineSave
+{
+    public string? Direction { get; set; }
+    public string? Name { get; set; }
+    public string? Color { get; set; }
+    public DoubleCollection? Dash { get; set; }
+}
 
 
 public partial class SelectRecipeStep : ObservableObject

+ 5 - 4
Analizer/ProximaAnalizer/ViewModels/RecipeStepNaviViewModel.cs

@@ -1,7 +1,5 @@
-using DryIoc.FastExpressionCompiler.LightExpression;
-using ProximaAnalizer.Data;
+using ProximaAnalizer.Data;
 using System.Collections.ObjectModel;
-using System.Net.NetworkInformation;
 using System.Windows;
 
 namespace ProximaAnalizer.ViewModels;
@@ -60,7 +58,10 @@ internal partial class RecipeStepNaviViewModel(IEventAggregator eventAggregator,
                 {
                     eventAggregator.GetEvent<WindowSwitch>().Page = Pages.HistoryData;
                     eventAggregator.GetEvent<WindowSwitch>().Publish();
-                    eventAggregator.GetEvent<RefreshAlarmData>().Publish();
+                    RefreshAlarmData alarmData = eventAggregator.GetEvent<RefreshAlarmData>();
+                    alarmData.Selected = null;
+                    alarmData.FromPage = Pages.RecipeStepNavi;
+                    alarmData.Publish();
                 });
             }
             finally

+ 661 - 101
Analizer/ProximaAnalizer/Views/DBInfoAlarm.xaml

@@ -9,117 +9,677 @@
              mc:Ignorable="d" 
              d:DesignHeight="450" d:DesignWidth="800">
     <UserControl.Resources>
-        <ResourceDictionary Source="/UICommon;component/Resources.xaml"/>
+        <!--<ResourceDictionary Source="/UICommon;component/Resources.xaml"/>-->
+        <ResourceDictionary>
+            <ResourceDictionary.MergedDictionaries>
+                <ResourceDictionary Source="/UICommon;component/Resources.xaml"/>
+            </ResourceDictionary.MergedDictionaries>
+            <local:MFCUnitConverter x:Key="MFCUnitConvert"/>
+            <local:LeakCheckNameConvert x:Key="LeakCheckName"/>
+        </ResourceDictionary>
     </UserControl.Resources>
-    <Grid Margin="8">
-        <Grid.ColumnDefinitions>
-            <ColumnDefinition Width="auto"/>
-            <ColumnDefinition Width="4"/>
-            <ColumnDefinition/>
-        </Grid.ColumnDefinitions>
+    <Grid Margin="4">
+
         <Grid.RowDefinitions>
-            <RowDefinition/>
-            <RowDefinition Height="4"/>
             <RowDefinition Height="auto"/>
+            <RowDefinition Height="4"/>
+            <RowDefinition Height="226"/>
+            <RowDefinition Height="4"/>
+            <RowDefinition Height="*"/>
         </Grid.RowDefinitions>
-        <Expander ExpandDirection="Right"  IsExpanded="True" Margin="0,6" Padding="0,-2" TextElement.FontSize="14">
-            <Expander.Header>
-                <TextBlock Text="Alarms" HorizontalAlignment="Center" Margin="4">
-                    <TextBlock.LayoutTransform>
-                        <RotateTransform Angle="-90"/>
-                    </TextBlock.LayoutTransform>
-                </TextBlock>
-            </Expander.Header>
-            <DataGrid ItemsSource="{Binding Alarms}" 
-                      IsReadOnly="True"
-                      CanUserAddRows="False"
-                      CanUserDeleteRows="False"
-                      CanUserResizeRows="False"
-                      CanUserSortColumns="False"
-                      Background="{StaticResource BackgroundColor}" >
-                <DataGrid.Columns>
-                    <DataGridTextColumn Header="Datetime" Binding="{Binding Key, StringFormat=yyyy-MM-dd HH:mm:ss}" Width="auto"/>
-                    <DataGridTemplateColumn>
-                        <DataGridTemplateColumn.CellTemplate>
-                            <DataTemplate>
-                                <ItemsControl Grid.Column="2" ItemsSource="{Binding Value}" VerticalAlignment="Center" HorizontalAlignment="Left" MaxWidth="360">
-                                    <ItemsControl.ItemTemplate>
-                                        <DataTemplate>
-                                            <Grid >
-                                                <TextBlock Margin="4,2" HorizontalAlignment="Left" Text="{Binding Description}" TextWrapping="Wrap"></TextBlock>
-                                            </Grid>
-                                        </DataTemplate>
-                                    </ItemsControl.ItemTemplate>
-                                </ItemsControl>
-                            </DataTemplate>
-                        </DataGridTemplateColumn.CellTemplate>
-                    </DataGridTemplateColumn>
-
-                </DataGrid.Columns>
-            </DataGrid>
-
-            <!--<ItemsControl ItemsSource="{Binding Alarms}">
-                    <ItemsControl.ItemTemplate>
-                        <DataTemplate>
-                            <Border BorderBrush="{StaticResource DarkBorderColor}" BorderThickness="1,1,0,0">
-
-                                <Grid>
-                                    <Grid.ColumnDefinitions>
-                                        <ColumnDefinition Width="auto"/>
-                                        <ColumnDefinition Width="8"/>
-                                        <ColumnDefinition Width="auto"/>
-                                    </Grid.ColumnDefinitions>
-                                    <TextBlock Text="{Binding Key, StringFormat=yyyy-MM-dd HH:mm:ss}" Margin="2"/>
-
-                                    <ItemsControl Grid.Column="2" ItemsSource="{Binding Value}" VerticalAlignment="Center">
-                                        <ItemsControl.ItemTemplate>
-                                            <DataTemplate>
-                                                <Grid>
-                                                    <Grid.ColumnDefinitions>
-                                                        <ColumnDefinition Width="auto"/>
-                                                        <ColumnDefinition Width="4"/>
-                                                        <ColumnDefinition Width="auto"/>
-                                                    </Grid.ColumnDefinitions>
-                                                    <TextBlock Text="{Binding Description}"></TextBlock>
-                                                </Grid>
-                                            </DataTemplate>
-                                        </ItemsControl.ItemTemplate>
-                                    </ItemsControl>
-                                </Grid>
-                            </Border>
-                        </DataTemplate>
-                    </ItemsControl.ItemTemplate>
-                </ItemsControl>-->
 
-        </Expander>
-
-        <Grid Grid.Row="2" Grid.ColumnSpan="3">
+        <Grid Margin="4">
             <Grid.RowDefinitions>
                 <RowDefinition Height="auto"/>
                 <RowDefinition Height="4"/>
-                <RowDefinition Height="auto"/>
+                <RowDefinition/>
             </Grid.RowDefinitions>
+            <Grid.ColumnDefinitions>
+                <ColumnDefinition Width="360"/>
+                <ColumnDefinition Width="8"/>
+                <ColumnDefinition />
+                <ColumnDefinition Width="8"/>
+                <ColumnDefinition MinWidth="520"/>
+                <ColumnDefinition Width="8"/>
+                <ColumnDefinition Width="auto"/>
+            </Grid.ColumnDefinitions>
+            <GroupBox Header="基本信息">
+                <Grid Margin="8" VerticalAlignment="Top">
+                    <Grid.RowDefinitions>
+                        <RowDefinition Height="auto"/>
+                        <RowDefinition Height="8"/>
+                        <RowDefinition Height="auto"/>
+                        <RowDefinition Height="8"/>
+                        <RowDefinition Height="auto"/>
+                        <!--<RowDefinition Height="8"/>
+                        <RowDefinition Height="48"/>-->
+                    </Grid.RowDefinitions>
+                    <Grid.ColumnDefinitions>
+                        <ColumnDefinition Width="auto"/>
+                        <ColumnDefinition Width="0"/>
+                        <ColumnDefinition/>
+                    </Grid.ColumnDefinitions>
+
+                    <TextBlock Grid.Column="0" Grid.Row="0" VerticalAlignment="Center">配方名称:</TextBlock>
+                    <TextBlock Grid.Column="2" Grid.Row="0" VerticalAlignment="Center" Text="{Binding RecipeName}" ToolTip="{Binding RecipeName}"/>
+
+                    <TextBlock Grid.Column="0" Grid.Row="2" VerticalAlignment="Center">所属步法:</TextBlock>
+                    <TextBlock Grid.Column="2" Grid.Row="2" VerticalAlignment="Center" Text="{Binding CurrentRecipeStep.Step_Name}"/>
+
+                    <TextBlock Grid.Column="0" Grid.Row="4" VerticalAlignment="Center">日期时间:</TextBlock>
+                    <TextBlock Grid.Column="2" Grid.Row="4" VerticalAlignment="Center" Text="{Binding Current, StringFormat=yyyy-MM-dd HH:mm:ss}"/>
+                </Grid>
+            </GroupBox>
+            <GroupBox Grid.Column="2" Header="报警信息">
+                <Grid Margin="8">
+
+                    <ComboBox Grid.Column="2" Grid.Row="6" ItemsSource="{Binding Alarms}" SelectedValue="{Binding SelectedAlarm}" Background="Transparent">
+                        <ComboBox.ItemTemplate>
+                            <DataTemplate>
+                                <Grid Margin="0,0,18,0">
+                                    <Grid.RowDefinitions>
+                                        <RowDefinition Height="auto"/>
+                                        <RowDefinition Height="0"/>
+                                        <RowDefinition/>
+                                    </Grid.RowDefinitions>
+                                    <TextBlock Text="{Binding Key, StringFormat=HH:mm:ss}" HorizontalAlignment="Left" VerticalAlignment="Center"/>
+                                    <TextBlock Grid.Row="2" Text="{Binding Value}" HorizontalAlignment="Center" TextWrapping="Wrap"></TextBlock>
+                                </Grid>
+                            </DataTemplate>
+                        </ComboBox.ItemTemplate>
+                        <ComboBox.ItemsPanel>
+                            <ItemsPanelTemplate>
+                                <VirtualizingStackPanel />
+                            </ItemsPanelTemplate>
+                        </ComboBox.ItemsPanel>
+                    </ComboBox>
+                </Grid>
+            </GroupBox>
+
+            <GroupBox Header="时间轴" Grid.Column="4">
+                <Grid Margin="8" VerticalAlignment="Top">
+                    <Grid.RowDefinitions>
+                        <RowDefinition Height="auto"/>
+                        <RowDefinition Height="8"/>
+                        <RowDefinition Height="auto"/>
+                        <RowDefinition Height="2"/>
+                        <RowDefinition Height="auto"/>
+                    </Grid.RowDefinitions>
 
-            <Grid>
-                <Grid.ColumnDefinitions>
-                    <ColumnDefinition Width="auto"/>
-                    <ColumnDefinition/>
-                    <ColumnDefinition Width="auto"/>
-                </Grid.ColumnDefinitions>
-                <TextBlock Grid.Column="0" VerticalAlignment="Center" Text="{Binding Start, StringFormat=yyyy-MM-dd HH:mm:ss}"/>
-
-                <StackPanel Grid.Column="1" Orientation="Horizontal" HorizontalAlignment="Center">
-                    <Button VerticalAlignment="Center" HorizontalAlignment="Center" Style="{StaticResource FunctionButton}" Content="&lt;&lt;" Command="{Binding TimeOperaCommand}" CommandParameter="--"/>
-                    <Button VerticalAlignment="Center" HorizontalAlignment="Center" Style="{StaticResource FunctionButton}" Content="&lt;" Command="{Binding TimeOperaCommand}" CommandParameter="-" Margin="4,0"/>
-                    <TextBlock Margin="8,0" VerticalAlignment="Center" Text="{Binding Current , StringFormat=yyyy-MM-dd HH:mm:ss}"/>
-                    <Button VerticalAlignment="Center" HorizontalAlignment="Center" Style="{StaticResource FunctionButton}" Content="&gt;" Command="{Binding TimeOperaCommand}" CommandParameter="+" Margin="4,0"/>
-                    <Button VerticalAlignment="Center" HorizontalAlignment="Center" Style="{StaticResource FunctionButton}" Content="&gt;&gt;" Command="{Binding TimeOperaCommand}" CommandParameter="++"/>
-                </StackPanel>
-
-                <TextBlock Grid.Column="2" VerticalAlignment="Center" Text="{Binding End, StringFormat=yyyy-MM-dd HH:mm:ss}"/>
-            </Grid>
-
-            <Slider x:Name="sli" Grid.Row="2" Minimum="{Binding Start.Ticks}" Maximum="{Binding End.Ticks}" TickFrequency="10000000" Value="{Binding CurrentLong, Mode=TwoWay}"/>
+                    <Grid Grid.Row="0">
+                        <Grid.ColumnDefinitions>
+                            <ColumnDefinition Width="auto"/>
+                            <ColumnDefinition Width="8"/>
+                            <ColumnDefinition Width="auto"/>
+                            <ColumnDefinition Width="8"/>
+                            <ColumnDefinition Width="auto"/>
+                            <ColumnDefinition Width="*"/>
+                            <ColumnDefinition Width="auto"/>
+                            <ColumnDefinition Width="8"/>
+                            <ColumnDefinition Width="auto"/>
+                            <ColumnDefinition Width="8"/>
+                            <ColumnDefinition Width="auto"/>
+                        </Grid.ColumnDefinitions>
+                        <Button Grid.Column="0" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Content="Prev Alarm" Command="{Binding TimeOperaCommand}" CommandParameter="---"/>
+                        <Button Grid.Column="2" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Content="-1 min" Command="{Binding TimeOperaCommand}" CommandParameter="--"/>
+                        <Button Grid.Column="4" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Content="-1s" Command="{Binding TimeOperaCommand}" CommandParameter="-"/>
+
+                        <StackPanel Grid.Column="5" Orientation="Horizontal" HorizontalAlignment="Center">
+                            <Button Margin="4,0" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Visibility="{Binding PlayVis}" Command="{Binding PlayCommand}" CommandParameter="play">
+                                <Image Source="{StaticResource Icon_Start}" Height="16"/>
+                            </Button>
+                            <Button Margin="4,0" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Visibility="{Binding StopVis}" Command="{Binding PlayCommand}" CommandParameter="stop">
+                                <Image Source="{StaticResource Icon_Pause}" Height="16"/>
+                            </Button>
+                        </StackPanel>
+
+                        <Button Grid.Column="6" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Content="+1s" Command="{Binding TimeOperaCommand}" CommandParameter="+" />
+                        <Button Grid.Column="8" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Content="+1 min" Command="{Binding TimeOperaCommand}" CommandParameter="++"/>
+                        <Button Grid.Column="10" VerticalAlignment="Center" Style="{StaticResource FunctionButton}" Content="Next Alarm" Command="{Binding TimeOperaCommand}" CommandParameter="+++"/>
+                    </Grid>
+
+                    <Slider Grid.Row="2" Grid.ColumnSpan="5" Style="{StaticResource MySliderStyle}" Minimum="{Binding Start.Ticks}" Maximum="{Binding End.Ticks}" TickFrequency="10000000" Value="{Binding CurrentLong, Mode=TwoWay}"/>
+
+                    <Grid Grid.Row="4">
+                        <Grid.ColumnDefinitions>
+                            <ColumnDefinition Width="auto"/>
+                            <ColumnDefinition/>
+                            <ColumnDefinition Width="auto"/>
+                        </Grid.ColumnDefinitions>
+                        <TextBlock Grid.Column="0" VerticalAlignment="Top" Text="{Binding Start, StringFormat=yyyy-MM-dd HH:mm:ss}"/>
+                        <TextBlock Grid.Column="1" HorizontalAlignment="Center" VerticalAlignment="Center" Text="{Binding Current, StringFormat=HH:mm:ss}"/>
+
+                        <TextBlock Grid.Column="2" VerticalAlignment="Top" Text="{Binding End, StringFormat=yyyy-MM-dd HH:mm:ss}"/>
+                    </Grid>
+                </Grid>
+            </GroupBox>
+
+            <GroupBox Grid.Column="6" Header="视图">
+
+                <Grid Grid.Column="6" Margin="2">
+                    <Grid.RowDefinitions>
+                        <RowDefinition Height="auto"/>
+                        <RowDefinition/>
+                        <RowDefinition Height="auto"/>
+                        <RowDefinition Height="2"/>
+                        <RowDefinition Height="auto"/>
+                    </Grid.RowDefinitions>
+                    <Button Grid.Row="0" Style="{StaticResource FunctionButton}" Command="{Binding ReturnCommand}" Background="{StaticResource WarningColor}">返回</Button>
+                    <Button Grid.Row="2" Style="{StaticResource FunctionButton}" Command="{Binding ReturnCommand}">数据</Button>
+                    <Button Grid.Row="4" Style="{StaticResource FunctionButton}" Command="{Binding ReturnCommand}">气路图</Button>
+                </Grid>
+            </GroupBox>
         </Grid>
+
+        <ScrollViewer Grid.Row="2" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Disabled">
+            <WrapPanel>
+                <GroupBox Header="Heater" Margin="4">
+                    <DataGrid ItemsSource="{Binding Heaters.Data}" x:Name="HeaterGrid"
+                              SelectedItem="{Binding Selected}"
+                             Margin="8"
+                             IsReadOnly="True"
+                             CanUserAddRows="False"
+                             CanUserDeleteRows="False"
+                             CanUserResizeRows="False"
+                             CanUserSortColumns="False"
+                             GridLinesVisibility="All"
+                             HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             AutoGenerateColumns="False"
+                             ColumnHeaderHeight="22"
+                             RowHeight="22"
+                             VerticalAlignment="Top"
+                             BorderBrush="{StaticResource DarkBorderColor}"                              
+                             Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="120" Header="Heater Zone">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Feedback">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[TempFeedback] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="SetPoint">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[TempSetPoint] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Mode">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[ControlMode]}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="CascadePV">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[CascadePV] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="CascadeSV">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[CascadeControlModeSV] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="HeaterPV">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[HeaterPV] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="HeaterSV">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[HeaterControlModeSV] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="HeaterMode">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[HeaterControlModeSV]}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="OverTemp">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[OverTemp] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="UpRate">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[UpRate] ,StringFormat=0.0}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="DownRate">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[DownRate] ,StringFormat=0.0}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Output">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock >
+                                        <Run Text="{Binding Value[WorkingOutput] ,StringFormat=0.0}"/>
+                                        <Run>%</Run>
+                                        </TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="APCVATGV" Margin="4">
+                    <DataGrid ItemsSource="{Binding APCVATGVs.Data}"
+                              SelectedItem="{Binding Selected}"
+
+                             Margin="8"
+                             IsReadOnly="True"
+                             CanUserAddRows="False"
+                             CanUserDeleteRows="False"
+                             CanUserResizeRows="False"
+                             CanUserSortColumns="False"
+                             GridLinesVisibility="All"
+                             HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             AutoGenerateColumns="False"
+                             ColumnHeaderHeight="22"
+                             RowHeight="22"
+                             VerticalAlignment="Top"
+                             BorderBrush="{StaticResource DarkBorderColor}"                              
+                             Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}" Margin="8,0"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="60" Header="Value">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="Pressure" Margin="4">
+                    <DataGrid ItemsSource="{Binding Pressures.Data}"
+                              SelectedItem="{Binding Selected}"
+                             Margin="8"
+                             IsReadOnly="True"
+                             CanUserAddRows="False"
+                             CanUserDeleteRows="False"
+                             CanUserResizeRows="False"
+                             CanUserSortColumns="False"
+                             GridLinesVisibility="All"
+                             HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             AutoGenerateColumns="False"
+                             ColumnHeaderHeight="22"
+                             RowHeight="22"
+                             VerticalAlignment="Top"
+                             BorderBrush="{StaticResource DarkBorderColor}"                              
+                             Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}" Margin="8,0"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="60" Header="Torr">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="LeakCheck"  Margin="4">
+                    <DataGrid ItemsSource="{Binding LeakChecks.Data}" 
+                              SelectedItem="{Binding Selected}"
+                             Margin="8"
+                             IsReadOnly="True"
+                             CanUserAddRows="False"
+                             CanUserDeleteRows="False"
+                             CanUserResizeRows="False"
+                             CanUserSortColumns="False"
+                             GridLinesVisibility="All"
+                             HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             AutoGenerateColumns="False"
+                             ColumnHeaderHeight="22"
+                             RowHeight="22"
+                             VerticalAlignment="Top"
+                             BorderBrush="{StaticResource DarkBorderColor}"                              
+                             Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key, Converter={StaticResource ResourceKey=LeakCheckName}}" Margin="8,0"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="60" Header="Value">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+            </WrapPanel>
+        </ScrollViewer>
+
+        <ScrollViewer Grid.Row="4" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Disabled">
+            <WrapPanel >
+                <GroupBox Header="MFC" Margin="4">
+                    <DataGrid ItemsSource="{Binding MFCs.Data}"
+                              SelectedItem="{Binding Selected}"
+                             Margin="8"
+                             IsReadOnly="True"
+                             CanUserAddRows="False"
+                             CanUserDeleteRows="False"
+                             CanUserResizeRows="False"
+                             CanUserSortColumns="False"
+                             GridLinesVisibility="All"
+                             HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                             AutoGenerateColumns="False"
+                             ColumnHeaderHeight="22"
+                             RowHeight="22"
+                             VerticalAlignment="Top"
+                             BorderBrush="{StaticResource DarkBorderColor}"                              
+                             Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="FeedBack">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[Feedback] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="VirtualFeedBack">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[VirtualFeedBack] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="SetPoint">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[SetPoint] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="LastSetPoint">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[LastSetPoint] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Ramp">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[Ramping] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Unit">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[MFCUnitEnum] ,Converter={StaticResource MFCUnitConvert}}"/>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="Valve" Margin="4">
+                    <DataGrid ItemsSource="{Binding Valves.Data}"
+                              SelectedItem="{Binding Selected}"
+                           Margin="8"
+                           IsReadOnly="True"
+                           CanUserAddRows="False"
+                           CanUserDeleteRows="False"
+                           CanUserResizeRows="False"
+                           CanUserSortColumns="False"
+                           GridLinesVisibility="All"
+                           HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                           VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                           AutoGenerateColumns="False"
+                           ColumnHeaderHeight="22"
+                           RowHeight="22"
+                           VerticalAlignment="Top"
+                           BorderBrush="{StaticResource DarkBorderColor}"                              
+                           Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Actual">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[Status] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="SetPoint">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[SetPoint]}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="GaslineHeater" Margin="4">
+                    <DataGrid ItemsSource="{Binding GaslineHeaters.Data}"
+                              SelectedItem="{Binding Selected}"
+                               Margin="8"
+                               IsReadOnly="True"
+                               CanUserAddRows="False"
+                               CanUserDeleteRows="False"
+                               CanUserResizeRows="False"
+                               CanUserSortColumns="False"
+                               GridLinesVisibility="All"
+                               HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                               VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                               AutoGenerateColumns="False"
+                               ColumnHeaderHeight="22"
+                               RowHeight="22"
+                                VerticalAlignment="Top"
+                                BorderBrush="{StaticResource DarkBorderColor}"                              
+                               Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}" Margin="8,0"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Feedback">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[TempFeedback] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="SetPoint">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[TempSetPoint],StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="FFU" Margin="4">
+                    <DataGrid ItemsSource="{Binding FFUs.Data}"
+                              SelectedItem="{Binding Selected}"
+                               Margin="8"
+                               IsReadOnly="True"
+                               CanUserAddRows="False"
+                               CanUserDeleteRows="False"
+                               CanUserResizeRows="False"
+                               CanUserSortColumns="False"
+                               GridLinesVisibility="All"
+                               HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                               VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                               AutoGenerateColumns="False"
+                               ColumnHeaderHeight="22"
+                               RowHeight="22"
+                                VerticalAlignment="Top"
+                                BorderBrush="{StaticResource DarkBorderColor}"
+                               Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}" Margin="8,0"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="IsSwitch">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[IsSwitch] ,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Speed">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value[CurrentSpeed]}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+                <GroupBox  Header="APC" Margin="4">
+                    <DataGrid ItemsSource="{Binding APCs.Data}"
+                              SelectedItem="{Binding Selected}"
+                                Margin="8"
+                                IsReadOnly="True"
+                                CanUserAddRows="False"
+                                CanUserDeleteRows="False"
+                                CanUserResizeRows="False"
+                                CanUserSortColumns="False"
+                                GridLinesVisibility="All"
+                                HorizontalGridLinesBrush="{StaticResource DarkBorderColor}"
+                                VerticalGridLinesBrush="{StaticResource DarkBorderColor}"
+                                AutoGenerateColumns="False"
+                                ColumnHeaderHeight="22"
+                                RowHeight="22"
+                                VerticalAlignment="Top"
+                                BorderBrush="{StaticResource DarkBorderColor}"
+                                Background="{StaticResource BackgroundColor}" >
+                        <DataGrid.Columns>
+                            <DataGridTemplateColumn Width="auto" MinWidth="100" Header="Name">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Key}" Margin="8,0"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+
+                            <DataGridTemplateColumn Width="auto" MinWidth="80" Header="Value">
+                                <DataGridTemplateColumn.CellTemplate>
+                                    <DataTemplate>
+                                        <TextBlock Text="{Binding Value,StringFormat=0.00}"></TextBlock>
+                                    </DataTemplate>
+                                </DataGridTemplateColumn.CellTemplate>
+                            </DataGridTemplateColumn>
+                        </DataGrid.Columns>
+                    </DataGrid>
+                </GroupBox>
+
+            </WrapPanel>
+        </ScrollViewer>
     </Grid>
+
 </UserControl>

+ 48 - 8
Analizer/ProximaAnalizer/Views/DBInfoAlarm.xaml.cs

@@ -1,10 +1,12 @@
 using System;
 using System.Collections.Generic;
+using System.Globalization;
 using System.Linq;
 using System.Text;
 using System.Threading.Tasks;
 using System.Windows;
 using System.Windows.Controls;
+using System.Windows.Controls.Primitives;
 using System.Windows.Data;
 using System.Windows.Documents;
 using System.Windows.Input;
@@ -13,16 +15,54 @@ using System.Windows.Media.Imaging;
 using System.Windows.Navigation;
 using System.Windows.Shapes;
 
-namespace ProximaAnalizer.Views
+namespace ProximaAnalizer.Views;
+
+/// <summary>
+/// Interaction logic for DBInfoAlarm.xaml
+/// </summary>
+public partial class DBInfoAlarm : UserControl
 {
-    /// <summary>
-    /// Interaction logic for DBInfoAlarm.xaml
-    /// </summary>
-    public partial class DBInfoAlarm : UserControl
+    public DBInfoAlarm()
     {
-        public DBInfoAlarm()
+        InitializeComponent();
+    }
+}
+
+
+public class MFCUnitConverter : IValueConverter
+{
+    public object? Convert(object? value, Type targetType, object parameter, CultureInfo culture)
+    {
+        if (value is not float unit)
+            return value;
+
+        return unit switch
         {
-            InitializeComponent();
-        }
+            0f => "SCCM",
+            1f => "SLM",
+            _ => value
+        };
+    }
+
+    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
+    {
+        throw new NotImplementedException();
+    }
+}
+
+public class LeakCheckNameConvert : IValueConverter
+{
+    public object? Convert(object? value, Type targetType, object parameter, CultureInfo culture)
+    {
+        if (value is not string s)
+            return value;
+
+        return s.Replace("LeakCheck", string.Empty);
+
+    }
+
+    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
+    {
+        throw new NotImplementedException();
     }
 }

+ 17 - 18
Analizer/ProximaAnalizer/Views/DBInfoTrace.xaml

@@ -88,8 +88,9 @@
                                 <RowDefinition Height="auto"/>
                                 <RowDefinition Height="4"/>
                                 <RowDefinition Height="*"/>
-                                <!--<RowDefinition Height="4"/>
-                                <RowDefinition Height="auto"/>-->
+                                <RowDefinition Height="4"/>
+                                <RowDefinition Height="auto"/>
+
                             </Grid.RowDefinitions>
                             <Button Grid.Row="0" Style="{StaticResource FunctionButton}" Command="{Binding ReturnCommand}" Margin="4">返回上级</Button>
                             <ScrollViewer Grid.Row="2">
@@ -99,20 +100,19 @@
                                             <Button Content="{Binding Key}" VerticalContentAlignment="Center" HorizontalContentAlignment="Left"
                                             Command="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=local:DBInfoTrace}, Path=DataContext.SelectHierachyCommand}"
                                             CommandParameter="{Binding}" Margin="4" Padding="8,2" Background="Transparent"></Button>
-                                            <!--<TextBlock Text="{Binding Key}"></TextBlock>-->
                                         </DataTemplate>
                                     </ItemsControl.ItemTemplate>
                                 </ItemsControl>
                             </ScrollViewer>
-                            <!--<Grid Grid.Row="4">
+                            <Grid Grid.Row="4" TextElement.FontSize="12">
                                 <Grid.ColumnDefinitions>
                                     <ColumnDefinition/>
-                                    <ColumnDefinition Width="2"/>
+                                    <ColumnDefinition Width="4"/>
                                     <ColumnDefinition/>
                                 </Grid.ColumnDefinitions>
-                                <CheckBox Grid.Column="0" Style="{StaticResource FunctionCheckBox}" IsChecked="{Binding DisplayAlarm, Mode=TwoWay}" VerticalAlignment="Center">显示Alarm</CheckBox>
-                                <CheckBox Grid.Column="2" Style="{StaticResource FunctionCheckBox}" IsChecked="{Binding DisplayWarning, Mode=TwoWay}" VerticalAlignment="Center">显示Warning</CheckBox>
-                            </Grid>-->
+                                <Button Grid.Column="0" Height="24" Style="{StaticResource FunctionButton}" Command="{Binding SaveLoadCommand}" CommandParameter="Save">保存预设</Button>
+                                <Button Grid.Column="2" Height="24" Style="{StaticResource FunctionButton}" Command="{Binding SaveLoadCommand}" CommandParameter="Load">读取预设</Button>
+                            </Grid>
                         </Grid>
                     </GroupBox>
                 </Grid>
@@ -146,6 +146,7 @@
                         </StackPanel>
                         <StackPanel Orientation="Horizontal" Margin="12,0">
                             <Button Width="120" Height="24" Style="{StaticResource FunctionButton}" Command="{Binding ReScaleCommand}" CommandParameter="">重置缩放</Button>
+                            <Button Width="120" Height="24" Margin="4" Style="{StaticResource FunctionButton}" Command="{Binding ReturnPageCommand}" Background="{StaticResource WarningColor}">返回主页</Button>
                         </StackPanel>
                     </WrapPanel>
 
@@ -194,19 +195,18 @@
                                         <Grid.ColumnDefinitions>
                                             <ColumnDefinition Width="auto"/>
                                             <ColumnDefinition Width="8"/>
+                                            <!--<ColumnDefinition Width="48"/>-->
+                                            <!--<ColumnDefinition Width="8"/>-->
                                             <ColumnDefinition Width="48"/>
                                             <ColumnDefinition Width="8"/>
-                                            <ColumnDefinition Width="48"/>
-                                            <!--<ColumnDefinition Width="8"/>
-                                            <ColumnDefinition Width="180"/>-->
-                                            <ColumnDefinition Width="32"/>
                                             <ColumnDefinition Width="*"/>
                                         </Grid.ColumnDefinitions>
-                                        <TextBlock VerticalAlignment="Center" HorizontalAlignment="Left"  Text="{Binding Occur_Time, StringFormat=HH:mm:ss.fff}"/>
-                                        <TextBlock Grid.Column="2" VerticalAlignment="Center" HorizontalAlignment="Center" Text="{Binding Source}" ToolTip="{Binding Source}"/>
-                                        <TextBlock Grid.Column="4" VerticalAlignment="Center" HorizontalAlignment="Center" Text="{Binding Level}" ToolTip="{Binding Level}"/>
-                                        <!--<TextBlock Grid.Column="6" VerticalAlignment="Center" HorizontalAlignment="Left" Text="{Binding Event_Enum}" ToolTip="{Binding Event_Enum}"/>-->
-                                        <TextBlock Grid.Column="8" VerticalAlignment="Center" HorizontalAlignment="Left" TextWrapping="Wrap" Text="{Binding Description}" ToolTip="{Binding Description}"/>
+                                        <TextBlock VerticalAlignment="Center" HorizontalAlignment="Left"  Text="{Binding Occur_Time, StringFormat=HH:mm:ss.f}"/>
+                                        <!--<TextBlock Grid.Column="2" VerticalAlignment="Center" HorizontalAlignment="Center" Text="{Binding Source}" ToolTip="{Binding Source}"/>-->
+                                        <!--<TextBlock Grid.Column="4" VerticalAlignment="Center" HorizontalAlignment="Center" Text="{Binding Level}" ToolTip="{Binding Level}"/>-->
+                                        <Button Grid.Column="2" Background="Transparent" BorderBrush="{StaticResource ThemeColor}" Foreground="{StaticResource ThemeColor}"
+                                                Command="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=local:DBInfoTrace}, Path=DataContext.AlarmDetailCommand}" CommandParameter="{Binding}">Details</Button>
+                                        <TextBlock Grid.Column="4" VerticalAlignment="Center" HorizontalAlignment="Left" Text="{Binding Description}" ToolTip="{Binding Description}"/>
                                     </Grid>
                                 </DataTemplate>
                             </ItemsControl.ItemTemplate>
@@ -220,7 +220,6 @@
                     <RowDefinition Height="24"/>
                     <RowDefinition Height="4"/>
                     <RowDefinition/>
-
                 </Grid.RowDefinitions>
                 <TextBlock VerticalAlignment="Center">左侧坐标轴</TextBlock>
                 <Button HorizontalAlignment="Right" Width="80" Style="{StaticResource FunctionButton}" Command="{Binding ClearCommand}" CommandParameter="L">清除</Button>

+ 1 - 1
Analizer/ProximaAnalizer/Views/Summary.xaml

@@ -19,7 +19,7 @@
             <RowDefinition Height="0"/>
             <RowDefinition/>
         </Grid.RowDefinitions>-->
-        <Button Grid.Row="0" HorizontalAlignment="Right" VerticalAlignment="Top" Panel.ZIndex="1" Margin="4" Width="80" Command="{Binding ReturnCommand}" Style="{StaticResource FunctionButton}">返回主页</Button>
+        <!--<Button Grid.Row="0" HorizontalAlignment="Right" VerticalAlignment="Top" Panel.ZIndex="1" Margin="4" Width="80" Command="{Binding ReturnCommand}" Style="{StaticResource FunctionButton}">返回主页</Button>-->
         <!--<StackPanel Orientation="Horizontal">
             <Button Command="{Binding TestCommand}" CommandParameter="DBInfoTrace">Trace</Button>
             <Button Command="{Binding TestCommand}" CommandParameter="DBInfoAlarm">Alarm</Button>

+ 1 - 1
UICommon/DrawImage.xaml

@@ -573,7 +573,7 @@
     <DrawingImage x:Key="Icon_Pause">
         <DrawingImage.Drawing>
             <DrawingGroup ClipGeometry="M0,0 V1024 H1024 V0 H0 Z">
-                <GeometryDrawing Brush="DarkGray" Geometry="F1 M1024,1024z M0,0z M256,810.666667L426.666667,810.666667 426.666667,213.333333 256,213.333333 256,810.666667z M597.333333,213.333333L597.333333,810.666666 768,810.666666 768,213.333333 597.333333,213.333333z" />
+                <GeometryDrawing Brush="White" Geometry="F1 M1024,1024z M0,0z M256,810.666667L426.666667,810.666667 426.666667,213.333333 256,213.333333 256,810.666667z M597.333333,213.333333L597.333333,810.666666 768,810.666666 768,213.333333 597.333333,213.333333z" />
             </DrawingGroup>
         </DrawingImage.Drawing>
     </DrawingImage>

+ 3 - 3
UICommon/Styles/ComboBoxStyle.xaml

@@ -8,8 +8,8 @@
                 <ColumnDefinition Width="25" />
             </Grid.ColumnDefinitions>
             <Rectangle Grid.ColumnSpan="2" HorizontalAlignment="Stretch" x:Name="Rectangle" VerticalAlignment="Stretch" Width="Auto" Height="Auto" RadiusX="2" RadiusY="2" Fill="#f8f8f8" />
-            <Border Margin="2,2,2,2" Grid.Column="1" Background="{StaticResource ThemeColor}" Width="20" Height="20" CornerRadius="3,3,3,3" x:Name="drop_border" />
-            <Path Grid.Column="1" HorizontalAlignment="Center" Width="Auto" x:Name="Arrow" VerticalAlignment="Center" Fill="{x:Null}" Data="M0.5,0.5 L3,6.5 5.5,0.5" Stroke="White" Margin="5,0,5,0" Height="7" StrokeThickness="2" Stretch="Fill" />
+            <!--<Border Margin="2,2,2,2" Grid.Column="1" Background="{StaticResource ThemeColor}" Width="20" Height="20" CornerRadius="3,3,3,3" x:Name="drop_border" />-->
+            <Path Grid.Column="1" HorizontalAlignment="Center" Width="Auto" x:Name="Arrow" VerticalAlignment="Center" Fill="{x:Null}" Data="M0.5,0.5 L3,6.5 5.5,0.5" Stroke="{StaticResource ThemeColor}" Margin="5,0,5,0" Height="7" StrokeThickness="2" Stretch="Fill" />
         </Grid>
     </ControlTemplate>
     
@@ -32,7 +32,7 @@
                                 <Grid MaxHeight="{TemplateBinding MaxDropDownHeight}" MinWidth="{TemplateBinding ActualWidth}" x:Name="DropDown" SnapsToDevicePixels="True">
                                     <Border x:Name="DropDownBorder" Background="#f8f8f8" CornerRadius="3,3,3,3" />
                                     <ScrollViewer  Margin="4,6,4,6" SnapsToDevicePixels="True" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto" CanContentScroll="True" Foreground="{StaticResource {x:Static SystemColors.ActiveCaptionTextBrushKey}}">
-                                        <StackPanel TextElement.FontSize="16" IsItemsHost="True" KeyboardNavigation.DirectionalNavigation="Contained" />
+                                        <VirtualizingStackPanel  IsItemsHost="True" KeyboardNavigation.DirectionalNavigation="Contained" />
                                     </ScrollViewer>
                                 </Grid>
                             </Popup>

+ 2 - 2
UICommon/Styles/OtherStyle.xaml

@@ -21,7 +21,7 @@
                                         <Thumb.Template>
                                             <ControlTemplate TargetType="{x:Type Thumb}">
                                                 <!--<Rectangle Width="14" Height="24" Fill="{StaticResource ThemeColor}"/>-->
-                                                <Ellipse Width="24" Height="24" Fill="{StaticResource ThemeColor}" />
+                                                <Ellipse Width="16" Height="16" Fill="{StaticResource ThemeColor}" />
                                                 <!-- Slider的滑块样式 -->
                                             </ControlTemplate>
                                         </Thumb.Template>
@@ -32,7 +32,7 @@
                                         <!-- 划过的地方 -->
                                         <RepeatButton.Template>
                                             <ControlTemplate TargetType="{x:Type RepeatButton}">
-                                                <Rectangle Fill="{StaticResource SubThemeColor}" Height="10"/>
+                                                <Rectangle Fill="{StaticResource SubThemeColor}" Height="4"/>
                                                 <!-- 划过的地方的样式 -->
                                             </ControlTemplate>
                                         </RepeatButton.Template>