using LiveCharts.Defaults;
using LiveCharts;
using Prism.Mvvm;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Collections.ObjectModel;
using System.Windows.Input;
using Txgy.Microseismic.BaseLib.Models;
using System.Windows;
using Prism.Events;
using Txgy.EWS.Client.IBLL;
using Txgy.Microseismic.BaseLib.Entitys;
using Txgy.EWS.Client.Common.MessageEvents;
using Arction.Wpf.ChartingMVVM;
using Txgy.EWS.Client.Common;
using Txgy.EWS.Client.Common.Extensions;
using System.IO;
using System.Diagnostics;
using Newtonsoft.Json.Linq;
using Newtonsoft.Json;
using Arction.Wpf.ChartingMVVM.Axes;
using Arction.Wpf.ChartingMVVM.Series3D;
using Arction.Wpf.ChartingMVVM.Titles;
using Arction.Wpf.ChartingMVVM.Views.View3D;
using Txgy.EWS.Client.PageModule.Models;
using System.Windows.Media;
using WW.Cad.Model.Entities;
using WW.Cad.Model;
using WW.Cad.IO;
using Colors = System.Windows.Media.Colors;
using Color = System.Windows.Media.Color;
using Arction.Wpf.ChartingMVVM.Annotations;
using Txgy.EWS.Client.PageModule.Views;
using Txgy.EWS.Client.Entity;

using Arction.Wpf.ChartingMVVM.EventMarkers;
using Arction.Wpf.ChartingMVVM.SeriesXY;
using WW.Math;
using System.Windows.Threading;
using Txgy.EWS.Client.PageModule.Services;
using LiveCharts.Wpf;
using Txgy.EWS.Client.Common.Helpers;
using Txgy.EWS.Client.Models;
using System.Windows.Controls;
using Txgy.EWS.Client.ILog;
using Unity;

namespace Txgy.EWS.Client.PageModule.ViewModels
{
    public class EarlyWarningViewModel : BindableBase
    {
        Dispatcher _dispatcher;
        private readonly IEventAggregator _ea;
        private readonly ILogHelper _logHelper;
        public const int TableShowCount = 21;
        public const int SelectTop = 100;
        private readonly ISearchMsEventBLL _searchMsEventBLL;

        //private bool _isInitializing=false;

        //public bool IsInitializing
        //{
        //    get { return _isInitializing; }
        //    set 
        //    { 
        //        SetProperty(ref _isInitializing, value);
        //    }
        //}


        /// <summary>
        /// 工作状态
        /// </summary>
        private bool _isRunning;

        public bool IsRunning
        {
            get { return _isRunning; }
            set
            {
                SetProperty(ref _isRunning, value);
            }
        }
        private int _runEventCnt = 0;

        public int RunEventCnt
        {
            get { return _runEventCnt; }
            set { SetProperty(ref _runEventCnt, value); }
        }

        private string _runningStr = "开始";

        public string RunningStr
        {
            get { return _runningStr; }
            set { SetProperty(ref _runningStr, value); }
        }
        private string _runSpan = "0小时0分0秒";

        public string RunSpan
        {
            get { return _runSpan; }
            set { SetProperty(ref _runSpan, value); }
        }
        private int _runInt = 0;

        public int RunInt
        {
            get { return _runInt; }

            set
            {
                _runInt = value;
                double h = Math.Floor(_runInt / 3600.0);
                double m = Math.Floor((_runInt - h * 3600) / 60.0);
                double s = Math.Floor((_runInt - h * 3600) % 60);
                RunSpan = h.ToString() + "小时" + m.ToString() + "分" + s.ToString() + "秒";
            }
        }
        public int PreSelectCnt = 20;

        private int eventFrequencyCount = 0;
        /// <summary>
        /// 事件近一小时频度
        /// </summary>
        public int EventFrequencyCount
        {
            get { return eventFrequencyCount; }
            set
            {
                SetProperty(ref eventFrequencyCount, value);
            }
        }
        private double lastAlarmEventML = 0;
        /// <summary>
        /// 最后报警事件震级
        /// </summary>
        public double LastAlarmEventML
        {
            get { return lastAlarmEventML; }
            set
            {
                SetProperty(ref lastAlarmEventML, value);
            }
        }
        private double lastAlarmEventEnergy = 0;
        /// <summary>
        /// 最后报警事件能量
        /// </summary>
        public double LastAlarmEventEnergy
        {
            get { return lastAlarmEventEnergy; }
            set
            {
                SetProperty(ref lastAlarmEventEnergy, value);
            }
        }
        private int lastAlarmEventDominFreq;

        public int LastAlarmEventDominFreq
        {
            get { return lastAlarmEventDominFreq; }
            set
            {
                SetProperty(ref lastAlarmEventDominFreq, value);
            }
        }

        private int energyMaxY = 2000;

        public int EnergyMaxY
        {
            get { return energyMaxY; }
            set
            {
                SetProperty(ref energyMaxY, value);
            }
        }
        private int eventFreMaxY = 20;

        public int EventFreMaxY
        {
            get { return eventFreMaxY; }
            set
            {
                SetProperty(ref eventFreMaxY, value);
            }
        }

        public ChartValues<ObservableValue> ListEventFre { get; set; }
        public ChartValues<ObservableValue> ListDominantFreq { get; set; }
        public ChartValues<ObservableValue> ListEnergy { get; set; }
        public ChartValues<ObservableValue> ListML { get; set; }
        public ChartValues<ObservableValue> ListStress { get; set; }

        private ObservableCollection<string> _eventFreLabels;
        public ObservableCollection<string> EventFreLabels
        {
            get { return _eventFreLabels; }
            set { SetProperty(ref _eventFreLabels, value); }
        }
        private ObservableCollection<string> _eventMLLabels;

        public ObservableCollection<string> EventMLLabels
        {
            get { return _eventMLLabels; }
            set { SetProperty(ref _eventMLLabels, value); }
        }
        private ObservableCollection<string> _eventDominantFreqLabels;

        public ObservableCollection<string> EventDominantFreqLabels
        {
            get { return _eventDominantFreqLabels; }
            set { SetProperty(ref _eventDominantFreqLabels, value); }
        }
        private ObservableCollection<string> _eventEnergyLabels;

        public ObservableCollection<string> EventEnergyLabels
        {
            get { return _eventEnergyLabels; }
            set { SetProperty(ref _eventEnergyLabels, value); }
        }
        private ObservableCollection<string> _eventStressLabels;

        public ObservableCollection<string> EventStressLabels
        {
            get { return _eventStressLabels; }
            set { SetProperty(ref _eventStressLabels, value); }
        }
        public List<MmEventEntity> SelectEvents { get; set; }
        private ObservableCollection<MmEventEntity> _showEvents;
        public ObservableCollection<MmEventEntity> ShowEvents
        {
            get { return _showEvents; }
            set
            {
                _showEvents = value;
            }
        }
        ChartValues<double> cv1 = new ChartValues<double>();
        Random ran = new Random();
        List<Task> taskList = new List<Task>();
        public ICommand AddCommand { get; set; }
        public ICommand StartWorkCommand { get; set; }

        #region LightningChart参数
        public string eventLayerName = "地震事件";
        public Color eventLayerColor = Colors.Red;
        public Color eventColor = Colors.Red;
        public Color eventTextColor = Colors.Blue;
        public double eventLayerLineWeight = 1;
        public double eventTextSize = 12;
        public string cnstLTypeName = "地震事件2";

        public string CadFilePath { get; set; }

        //LCPlanModel _lcModel;
        //public CadLineList cadLineList;

        public List<PointLineSeries3D> eventList;

        private ChartTitle _chartTitle;

        public ChartTitle ChartTitle
        {
            get { return _chartTitle; }
            set
            {
                SetProperty(ref _chartTitle, value);
            }
        }


        private double _scale = 1;
        public double Scale
        {
            get { return _scale; }
            set
            {
                SetProperty(ref _scale, value);
            }
        }

        private int _widthRS = 2000;
        public int WidthRS
        {
            get { return _widthRS; }
            set
            {
                SetProperty(ref _widthRS, value);
            }
        }
        private int _heightRS = 700;
        public int HeightRS
        {
            get { return _heightRS; }
            set
            {
                SetProperty(ref _heightRS, value);
            }
        }
        private int _depthRS = 2000;
        public int DepthRS
        {
            get { return _depthRS; }
            set
            {
                SetProperty(ref _depthRS, value);
            }
        }
        private double _sideRotationRS = 0;
        public double SideRotationRS
        {
            get { return _sideRotationRS; }
            set
            {
                SetProperty(ref _sideRotationRS, value);
            }
        }
        private double _horizontalRotationRS = 0;
        public double HorizontalRotationRS
        {
            get { return _horizontalRotationRS; }
            set
            {
                SetProperty(ref _horizontalRotationRS, value);
            }
        }
        private double _verticalRotationRS = 90;
        public double VerticalRotationRS
        {
            get { return _verticalRotationRS; }
            set
            {
                //Console.WriteLine(value.ToString());
                SetProperty(ref _verticalRotationRS, value);

            }
        }
        private double _distanceRS = 1300;
        public double DistanceRS
        {
            get { return _distanceRS; }
            set
            {
                //Console.WriteLine(value.ToString());
                SetProperty(ref _distanceRS, value);

            }
        }
        private bool _clipDispaly = true;
        public bool ClipDispaly
        {
            get { return _clipDispaly; }
            set
            {
                SetProperty(ref _clipDispaly, value);
            }
        }
        private WallXZ _bottomWall;
        public WallXZ BottomWall
        {
            get { return _bottomWall; }
            set
            {
                SetProperty(ref _bottomWall, value);
            }
        }
        private AxisX3D _axisXPri3D;
        public AxisX3D AxisXPri3D
        {
            get { return _axisXPri3D; }
            set
            {
                SetProperty(ref _axisXPri3D, value);
            }
        }
        private AxisY3D _axisYPri3D;
        public AxisY3D AxisYPri3D
        {
            get { return _axisYPri3D; }
            set
            {
                SetProperty(ref _axisYPri3D, value);
            }
        }
        private AxisZ3D _axisZPri3D;
        public AxisZ3D AxisZPri3D
        {
            get { return _axisZPri3D; }
            set
            {
                SetProperty(ref _axisZPri3D, value);
            }
        }
        private ProjectionType _projectionTypeRS = ProjectionType.Orthographic;
        public ProjectionType ProjectionTypeRS
        {
            get { return _projectionTypeRS; }
            set
            {
                SetProperty(ref _projectionTypeRS, value);
            }
        }
        private Fill _chartBackGround = new Fill();
        public Fill ChartBackGround
        {
            get { return _chartBackGround; }
            set
            {
                SetProperty(ref _chartBackGround, value);
            }
        }
        private ObservableCollection<GridItemEventResult> _alarmEvents = new ObservableCollection<GridItemEventResult>();

        public ObservableCollection<GridItemEventResult> AlarmEvents
        {
            get { return _alarmEvents; }
            set
            {
                SetProperty(ref _alarmEvents, value);
            }
        }
        private ObservableCollection<GridItemEventResult> _receviedEvents = new ObservableCollection<GridItemEventResult>();

        public ObservableCollection<GridItemEventResult> ReceviedEvents
        {
            get { return _receviedEvents; }
            set
            {
                SetProperty(ref _receviedEvents, value);
            }
        }
        private string _testText = "abc";

        public string TestText
        {
            get { return _testText; }
            set
            {
                SetProperty(ref _testText, value);
            }
        }
        private GridItemEventResult _selectedAlramEvent;

        public GridItemEventResult SelectedAlarmEvent
        {
            get { return _selectedAlramEvent; }
            set
            {
                SetProperty(ref _selectedAlramEvent, value);
                if (_selectedAlramEvent != null)
                {
                    this._ea.GetEvent<SelectAlarmEventMessage>().Publish(_selectedAlramEvent);
                }
            }
        }
        private GridItemEventResult _selectedReceviedEvent;

        public GridItemEventResult SelectedReceviedEvent
        {
            get { return _selectedReceviedEvent; }
            set
            {
                SetProperty(ref _selectedReceviedEvent, value);
                if (_selectedReceviedEvent != null)
                {
                    this._ea.GetEvent<SelectAlarmEventMessage>().Publish(_selectedReceviedEvent);
                }
            }
        }

        public Light3DCollection Lights { get; set; }
        public Polygon3DCollection Polygons { get; set; }
        public PointLineSeries3DCollection ChartPointLineCollection { get; set; }
        public Annotation3DCollection ChartAnnotationCollection { get; set; }
        public List<PointLineSeries3D> cadImage3DList { get; set; }
        #endregion       

        public ICommand TestCommand
        {
            get => new Prism.Commands.DelegateCommand(() =>
            {
                //Type type = Type.GetType("Txgy.EWS.Client.PageModule.Views.EarlyWarningView");
                //string str = (Activator.CreateInstance(type) as EarlyWarningView).chart.ChartName;
                //Console.WriteLine("=============================================================" + str);
                //DateTime dateTime = timeTemp.AddHours(tmp);
                //Stopwatch watch = new Stopwatch();
                //watch.Start();

                ////MmEventEntity mmEvent= searchMsEventBLL.GetLastEvent();
                //var mme = fsqlTencent.Select<RemoteRealtimeResultEntity>()
                //.Where(re => DateTime.Parse(re.EventTime).Ticks <= dateTime.Ticks)
                //.OrderByDescending(re => re.RTEventID).First();

                //watch.Stop();
                //TimeSpan timespan = watch.Elapsed;

                //Console.WriteLine("FreeSql:" + mme.RTEventID + " ++++++++++++++++时长：" + timespan.TotalMilliseconds);

                //GlobalData.AlarmEvents.Add(mme);
                //AlarmEventPayload aep = new AlarmEventPayload(mme);
                //Application.Current.Dispatcher.Invoke(_handleDataGenerated, aep);
                //PutSamplesToChart(aep);
                //Stopwatch watch2 = new Stopwatch();
                //watch.Start();

                //MmEventEntity mmEvent2 = searchMsEventBLL.GetLastEvent();
                ////var mme2 = fsqlTencent.Select<RemoteRealtimeResultEntity>()
                ////.Where(re => DateTime.Parse(re.EventTime).Ticks <= dateTime.Ticks)
                ////.OrderByDescending(re => re.RTEventID).First();

                //watch.Stop();
                //TimeSpan timespan2 = watch.Elapsed;

                //Console.WriteLine(mmEvent2.EventID + " ++++++++++++++++时长：" + timespan2.TotalMilliseconds);
            });
        }

        public EarlyWarningViewModel(IUnityContainer unityContainer, IEventAggregator ea, ISearchMsEventBLL searchMsEventBLL, ILogHelper logHelper)
        {
            _dispatcher = unityContainer.Resolve<Dispatcher>();
            this._ea = ea;
            this._logHelper = logHelper;
            this._searchMsEventBLL = searchMsEventBLL;
            ListEventFre = new ChartValues<ObservableValue>();
            ListEventFre.NoisyCollectionChanged += EventFre_NoisyCollectionChanged;
            EventFreLabels = new ObservableCollection<string>();

            ListDominantFreq = new ChartValues<ObservableValue>();
            ListDominantFreq.NoisyCollectionChanged += DominantFreq_NoisyCollectionChanged;
            EventDominantFreqLabels = new ObservableCollection<string>();

            ListML = new ChartValues<ObservableValue>();
            ListML.NoisyCollectionChanged += MLS_NoisyCollectionChanged;
            EventMLLabels = new ObservableCollection<string>();

            ListEnergy = new ChartValues<ObservableValue>();
            ListEnergy.NoisyCollectionChanged += ListEnergy_NoisyCollectionChanged;
            EventEnergyLabels = new ObservableCollection<string>();

            ListStress = new ChartValues<ObservableValue>();
            ListStress.NoisyCollectionChanged += Stress_NoisyCollectionChanged;
            EventStressLabels = new ObservableCollection<string>();

            #region 设置Chart
            CadFilePath = GlobalConfig.ProjectConfig.CadFileName;
            _chartBackGround.GradientFill = GradientFill.Solid;
            _chartBackGround.GradientColor = Colors.White;

            ChartTitle = new ChartTitle();
            ChartTitle.Text = "平面视图";
            _bottomWall = new WallXZ();
            _bottomWall.Material = new Material3D() { DiffuseColor = Color.FromArgb(0, 248, 248, 255) };
            _bottomWall.SetGridStripColor1(Color.FromArgb(0, 248, 248, 255));
            _bottomWall.SetGridStripColor2(Color.FromArgb(0, 248, 248, 255));
            Lights = View3D.CreateDefaultLights();
            Lights[1].Location.SetValues((GlobalConfig.ProjectConfig.WorkArea.EMax - GlobalConfig.ProjectConfig.WorkArea.EMin) / 2f, 100,
                (GlobalConfig.ProjectConfig.WorkArea.NMax - GlobalConfig.ProjectConfig.WorkArea.NMin) / 2f);
            //_widthRS = (int)((GlobalConfig.ProjectConfig.WorkArea.EMax - GlobalConfig.ProjectConfig.WorkArea.EMin) / Scale);
            //_heightRS = (int)((GlobalConfig.ProjectConfig.WorkArea.ZMax - GlobalConfig.ProjectConfig.WorkArea.ZMin) / Scale);
            //_depthRS = (int)((GlobalConfig.ProjectConfig.WorkArea.NMax - GlobalConfig.ProjectConfig.WorkArea.NMin) / Scale);

            AxisXPri3D = new AxisX3D();
            AxisXPri3D.Maximum = GlobalConfig.ProjectConfig.WorkArea.EMax / Scale;
            AxisXPri3D.Minimum = GlobalConfig.ProjectConfig.WorkArea.EMin / Scale;

            AxisXPri3D.Title.Text = "横轴";
            AxisXPri3D.Title.Visible = false;

            AxisXPri3D.LabelsColor = Colors.Black;
            AxisXPri3D.LabelsNumberFormat = "00000000";
            AxisXPri3D.AutoFormatLabels = false;
            AxisXPri3D.Orientation = PlaneXAxis3D.XZ;
            AxisXPri3D.Location = AxisXLocation3D.TopFront;

            AxisYPri3D = new AxisY3D();
            AxisYPri3D.Maximum = 30;
            AxisYPri3D.Minimum = 0;
            AxisYPri3D.Visible = false;

            AxisZPri3D = new AxisZ3D();
            AxisZPri3D.Maximum = GlobalConfig.ProjectConfig.WorkArea.NMax / Scale;
            AxisZPri3D.Minimum = GlobalConfig.ProjectConfig.WorkArea.NMin / Scale;

            AxisZPri3D.Title.Text = "纵轴";
            AxisZPri3D.Title.Visible = false;

            AxisZPri3D.LabelsColor = Colors.Black;
            AxisZPri3D.LabelsNumberFormat = "0000000";
            AxisZPri3D.AutoFormatLabels = false;
            AxisZPri3D.Orientation = PlaneZAxis3D.XZ;
            AxisZPri3D.Location = AxisZLocation3D.TopRight;

            ChartPointLineCollection = new PointLineSeries3DCollection();
            ChartAnnotationCollection = new Annotation3DCollection();
            //CreateBackgroudByDwg();

            #endregion
            this._ea = ea;
            this._searchMsEventBLL = searchMsEventBLL;
            ShowEvents = new ObservableCollection<MmEventEntity>();

            Task.Run(async () => { await InitEventList(); });


            //InitEventList();
            this._ea.GetEvent<UpdateEventFrequencyEvent>().Subscribe(u =>
            {
                InvokeOnDispatcher(() =>
                {
                    ListEventFre.Add(new ObservableValue(u));
                    EventFrequencyCount = u;
                    if (EventFreLabels.Count >= TableShowCount)
                    {
                        EventFreLabels.RemoveAt(0);
                    }
                    EventFreLabels.Add(DateTime.Now.ToString("HH:mm"));
                    EventFreMaxY = (int)(ListEventFre.Max(le => le.Value) + 4);
                });
            });
            //最后预警事件
            this._ea.GetEvent<UpdateLastAlarmEvent>().Subscribe(u =>
            {
                InvokeOnDispatcher(() =>
                {
                    LastAlarmEventEnergy = u.Energy;
                    ListEnergy.Add(new ObservableValue(u.Energy));

                    //EventEnergyLabels.Add(u.EventTime.Substring(0, 1));
                    LastAlarmEventML = u.ML;
                    ListML.Add(new ObservableValue(u.ML));

                    //Random rnd = new Random((int)DateTime.Now.Ticks);
                    //int domainFreq = rnd.Next(15, 60);
                    //LastAlarmEventDominFreq = domainFreq;
                    //ListDominantFreq.Add(new ObservableValue(domainFreq));
                });
            });
            //事件主频
            this._ea.GetEvent<UpdateEventDominFreqMessage>().Subscribe(u =>
            {
                //Random rnd = new Random((int)DateTime.Now.Ticks);
                //int domainFreq = rnd.Next(15, 60);
                LastAlarmEventDominFreq = u;
                ListDominantFreq.Add(new ObservableValue(u));
            });
            //开始监控，初始化列表           
            this._ea.GetEvent<StartRunMonitorMessage>().Subscribe(() =>
            {
                //ReceviedEvents = new ObservableCollection<GridItemEventResult>();
                //AlarmEvents = new ObservableCollection<GridItemEventResult>();
            });
            this._ea.GetEvent<ClearWarningDataEvent>().Subscribe(ClearWarningData, ThreadOption.UIThread);
            //更新接收到的事件
            this._ea.GetEvent<UpdateReceivedEventMessage>().Subscribe(gier =>
            {
                if (!GlobalConfig.IsDesign)
                {
                    //从接收事件列表中删除超过指定时间范围的数据
                    var timeoutReceivedEvents = ReceviedEvents.Where(re =>
                    (DateTime.Now - DateTime.Parse(re.EventTime)).TotalHours >= GlobalConfig.DataLookbackHours).ToArray();
                    InvokeOnDispatcher(() =>
                    {
                        if (timeoutReceivedEvents.Length > 0)
                        {
                            for (int i = timeoutReceivedEvents.Length - 1; i >= 0; i--)
                            {
                                GridItemEventResult dg = timeoutReceivedEvents[i];
                                ReceviedEvents.Remove(dg);
                            }
                        }
                    });
                }
                InvokeOnDispatcher(() =>
                {
                    ReceviedEvents.Insert(0, gier);
                });

                //ReceivedEvents = new ObservableCollection<GridItemEventResult>();
                //AlarmEvents = new ObservableCollection<GridItemEventResult>();
            });
            //更新预警事件
            this._ea.GetEvent<UpdateAlarmEventMessage>().Subscribe(gier =>
            {
                //从接收事件列表中删除超过指定时间范围的数据
                if (!GlobalConfig.IsDesign)
                {
                    var timeoutAlarmEvents = AlarmEvents.Where(re =>
                    (DateTime.Now - DateTime.Parse(re.EventTime)).TotalHours >= GlobalConfig.DataLookbackHours).ToArray();
                    InvokeOnDispatcher(() =>
                    {
                        if (timeoutAlarmEvents.Length > 0)
                        {
                            for (int i = timeoutAlarmEvents.Length - 1; i >= 0; i--)
                            {
                                GridItemEventResult dg = timeoutAlarmEvents[i];
                                AlarmEvents.Remove(dg);
                            }
                        }
                    });
                }
                InvokeOnDispatcher(() =>
                {
                    AlarmEvents.Insert(0, gier);
                });

                //ReceivedEvents = new ObservableCollection<GridItemEventResult>();
                //AlarmEvents = new ObservableCollection<GridItemEventResult>();
            });          
        }

        private void InvokeOnDispatcher(System.Action action)
        {
            if (action == null || _dispatcher == null || _dispatcher.HasShutdownStarted || _dispatcher.HasShutdownFinished)
            {
                return;
            }

            if (_dispatcher.CheckAccess())
            {
                action();
                return;
            }

            _dispatcher.Invoke(action);
        }

        private void ClearWarningData()
        {
            AlarmEvents.Clear();
            ReceviedEvents.Clear();
            ListEnergy.Clear();
            ListML.Clear();
            ListDominantFreq.Clear();
            LastAlarmEventEnergy = 0;
            LastAlarmEventML = 0;
            LastAlarmEventDominFreq = 0;
            EnergyMaxY = 2000;
        }

        private void ListEnergy_NoisyCollectionChanged(IEnumerable<ObservableValue> oldItems, IEnumerable<ObservableValue> newItems)
        {
            if (ListEnergy.Count > TableShowCount)
            {
                ListEnergy.RemoveAt(0);
            }
        }
        private void EventFre_NoisyCollectionChanged(IEnumerable<ObservableValue> oldItems, IEnumerable<ObservableValue> newItems)
        {
            if (ListEventFre.Count > TableShowCount)
            {
                ListEventFre.RemoveAt(0);
            }
        }
        private void Stress_NoisyCollectionChanged(IEnumerable<ObservableValue> oldItems, IEnumerable<ObservableValue> newItems)
        {
            if (ListStress.Count > TableShowCount)
            {
                ListStress.RemoveAt(0);
            }
        }
        private void MLS_NoisyCollectionChanged(IEnumerable<ObservableValue> oldItems, IEnumerable<ObservableValue> newItems)
        {
            if (ListML.Count > TableShowCount)
            {
                ListML.RemoveAt(0);
            }
        }
        private void DominantFreq_NoisyCollectionChanged(IEnumerable<ObservableValue> oldItems, IEnumerable<ObservableValue> newItems)
        {
            if (ListDominantFreq.Count > TableShowCount)
            {
                ListDominantFreq.RemoveAt(0);
            }
        }

        async Task InitEventList()
        {
            //DateTime dt=new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, DateTime.Now.Hour, DateTime.Now.Minute, DateTime.Now.Second).AddMinutes(-TableShowCount);
            DateTime dt = DateTime.Now.AddMinutes(-TableShowCount);
            if (GlobalConfig.IsDesign)
            {
                dt = GlobalConfig.DStartTime;
            }
            for (int i = 0; i < TableShowCount; i++)
            {
                string timeStr = dt.AddMinutes(i).ToString("HH:mm");
                EventFreLabels.Add(timeStr);
                EventMLLabels.Add(i.ToString());
                EventEnergyLabels.Add(i.ToString());
                EventDominantFreqLabels.Add(i.ToString());
            }
            //Stopwatch sw = Stopwatch.StartNew();
            //sw.Start();
            await StatEventCount();
            //var task2 = await Task.Run(async () => { await StatEventCount(); });
            //task2.Wait();
            //Task.WhenAll(task2);
            await QueryEvent();

            //sw.Stop();
            //Console.WriteLine(sw.Elapsed.TotalMilliseconds);

        }
        async Task StatEventCount()
        {
            DateTime st = DateTime.Now.AddMinutes(-TableShowCount);
            if (GlobalConfig.IsDesign)
            {
                st = GlobalConfig.DStartTime;
            }
            for (int i = 0; i < TableShowCount; i++)
            {
                int statCount = await this._searchMsEventBLL.StatEventCountAsync(st.AddSeconds(-3600), st);
                ListEventFre.Add(new ObservableValue(statCount));

                st = st.AddMinutes(i + 1);
            }
            EventFreMaxY = (int)(ListEventFre.Max(le => le.Value) + 4);
        }
        async Task QueryEvent()
        {
            List<GridItemEventResult> giers = this._searchMsEventBLL.GetLastTopEvents(TableShowCount);
            //添加测试数据
            //Application.Current.Dispatcher.Invoke(new System.Action(() =>
            //{
            //    ReceviedEvents.AddRange(giers);
            //    AlarmEvents.AddRange(giers);
            //    //foreach (var gier in giers) { AlarmEvents.Add(gier); }
            //}));
            //foreach (var gier in giers) { AlarmEvents.Add(gier); }
            //AlarmEvents.AddRange(giers);
            giers.Sort((f, s) => f.EventID.CompareTo(s.EventID));
            System.Action<GridItemEventResult> callback = (s) =>
            {
                int domin = GlobalData.GetDominFreq(s.EventTime);
                ListDominantFreq.Add(new ObservableValue(domin));
            };
            for (int i = 0; i < giers.Count; i++)
            {
                giers[i].SetEnergy();
                await this._searchMsEventBLL.DownloadJsonDataAsync(giers[i], GlobalConfig.ProjectConfig.MseedFilePath + "\\", callback);

                ListML.Add(new ObservableValue(giers[i].ML));
                ListEnergy.Add(new ObservableValue(CalEnergy(giers[i].ML)));

            }
            EnergyMaxY = (int)((Math.Ceiling(ListEnergy.Max(le => le.Value) / 1000.0)) * 1000);
            //
            //await Task.Delay(100);
        }

        private void DownloadWaveDataTask(string eventTimeStr, string tableName)
        {
            string downLoadStr = eventTimeStr;
            string datePath = downLoadStr.Substring(0, 4) + downLoadStr.Substring(5, 2) + downLoadStr.Substring(8, 2);
            string mseedStr = "HA." + downLoadStr.Substring(0, 4) + downLoadStr.Substring(5, 2)
                + downLoadStr.Substring(8, 2) + downLoadStr.Substring(10, 3)
                + downLoadStr.Substring(14, 2) + downLoadStr.Substring(17, 2) + ".01" + GlobalConfig.DataTypeString;

            string mseedPath = GlobalConfig.ProjectConfig.MseedFilePath + "\\" + datePath + "\\";
            string savePath = GlobalConfig.ProjectConfig.TxtFilePath + "\\" + datePath + "\\" + mseedStr + ".txt";
            //var taskRunTime = Task.Factory.StartNew(new Action(() =>
            //{
            if (!File.Exists(mseedPath + mseedStr + ".mseed"))
            {
                if (!Directory.Exists(mseedPath))
                {
                    Directory.CreateDirectory(mseedPath);
                }
                _searchMsEventBLL.DownLoadWavedata(downLoadStr, mseedPath, mseedStr, tableName);
                if (!File.Exists(savePath))
                {
                    if (!Directory.Exists(Path.GetDirectoryName(savePath)))
                    {
                        Directory.CreateDirectory(Path.GetDirectoryName(savePath));
                    }
                    Stopwatch sw = Stopwatch.StartNew();
                    sw.Start();
                    MSeed2Asc(mseedPath + mseedStr + ".mseed", savePath);
                    sw.Stop();
                    TimeSpan timeSpan = sw.Elapsed;
                    //Console.WriteLine(timeSpan.TotalMilliseconds);
                }
            }
            else
            {
                if (!File.Exists(savePath))
                {
                    if (!Directory.Exists(Path.GetDirectoryName(savePath)))
                    {
                        Directory.CreateDirectory(Path.GetDirectoryName(savePath));
                    }
                    MSeed2Asc(mseedPath + mseedStr + ".mseed", savePath);
                }
            }
        }
        public void MSeed2Asc(string filePath, string savePath)
        {
            using (Process compiler = new Process())
            {
                compiler.StartInfo.FileName = "mseed2ascii.exe";
                compiler.StartInfo.Arguments = filePath + " -o " + savePath;
                compiler.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
                compiler.Start();
                compiler.WaitForExit();
            }
        }
        /// <summary>
        /// 获取主频
        /// </summary>
        /// <param name="mmEvent"></param>
        /// <returns></returns>
        public int GetDominFreq(string eventTime)
        {
            string downLoadStr = eventTime;
            string datePath = downLoadStr.Substring(0, 4) + downLoadStr.Substring(5, 2) + downLoadStr.Substring(8, 2);
            string jsonStr = "HA." + downLoadStr.Substring(0, 4) + downLoadStr.Substring(5, 2)
                + downLoadStr.Substring(8, 2) + downLoadStr.Substring(10, 3)
                + downLoadStr.Substring(14, 2) + downLoadStr.Substring(17, 2) + ".01" + GlobalConfig.DataTypeString + ".json";
            string jsonFilePath = GlobalConfig.ProjectConfig.MseedFilePath + "\\" + datePath + "\\" + jsonStr;
            int dominantFreq = 0;
            if (File.Exists(jsonFilePath))
            {
                if (new FileInfo(jsonFilePath).Length < 100)
                {
                    return dominantFreq;
                }
                try
                {
                    using (StreamReader sr = System.IO.File.OpenText(jsonFilePath))
                    {
                        JsonTextReader reader = new JsonTextReader(sr);
                        JArray jArray = (JArray)JToken.ReadFrom(reader);
                        //解析普通属性和数组混合的Json文件
                        //数组0是普通属性集合
                        JObject jobj = (JObject)jArray[0];

                        List<double> DominantFreqlist = new List<double>();
                        JArray phaseArr = JArray.FromObject(jobj["phases"]);
                        //List<double> DominantFreqList = new List<double>();
                        for (int i = 0; i < phaseArr.Count; i++)
                        {
                            if (phaseArr[i]["fmd_semi_period"] != null)
                            {
                                DominantFreqlist.Add(double.Parse(phaseArr[i]["fmd_semi_period"].ToString()));
                            }
                        }
                        if (DominantFreqlist.Count > 0)
                        {
                            if (DominantFreqlist.Count > 3)
                            {
                                double min = DominantFreqlist.Min();
                                double max = DominantFreqlist.Max();
                                DominantFreqlist.Remove(min);
                                DominantFreqlist.Remove(max);
                                dominantFreq = (int)((DominantFreqlist.Sum() / (double)DominantFreqlist.Count) * 1000);
                            }
                        }
                    }
                }
                catch (Exception)
                {
                    return 0;
                    //throw ex;                    
                }
            }
            return dominantFreq;
        }
        public void StatEventFre(List<MmEvent> mmEvents)
        {
            for (int i = TableShowCount - 1; i >= 0; i--)
            {
                int a = mmEvents.Count(mm => mm.EventTime > mmEvents[i].EventTime.AddHours(-1) && mm.EventTime <= mmEvents[i].EventTime);
                //CurEventFre = new int();
                //Console.WriteLine(a);
                ListEventFre.Add(new ObservableValue(a));
                EventFreLabels.Add(mmEvents[i].EventTime.ToString("HH:mm"));
            }
        }
        public void AddEvent(MmEventEntity mmEvent)
        {
            ShowEvents.Add(mmEvent);
        }
        public double CalEnergy(double ml)
        {
            double mi = Math.Round(4.83 + 1.47 * ml, 4);
            return Math.Round(Math.Pow(10, mi), 0);           
        }
        int num = 1;
        private void AddCom(object obj)
        {
            //CurEventFre=ran.Next(1,60);
            //CurDominantFreq=ran.Next(1,150);
            //CurML = ran.Next(0, 4);
            //CurStress=ran.Next(10000, 100000);
            MmEventEntity mmEvent = new MmEventEntity();
            mmEvent.X = num++;
            mmEvent.Y = 0;
            mmEvent.EventTime = new DateTime(2022, 03, 09, 00, 00, 00).AddMinutes(num);
            //mmEvent.EventTime.AddMinutes(num);
            mmEvent.LocSta = 10;
            mmEvent.MLSta = 10;
            mmEvent.ML = -3;
            ListEventFre.Add(new ObservableValue(10));

            AddEvent(mmEvent);
            //Console.WriteLine(CurEventFre.ToString());
        }
        public void Dispose()
        {
            try
            {
                //this.IsRunning = false;
                Task.WaitAll(this.taskList.ToArray());
                //ComputerInfo.GetInstance().Dispose();
            }
            catch { }

        }
        #region Cad方法

        public void CreateBackgroudByDwg()
        {
            cadImage3DList = new List<PointLineSeries3D>();
            //DwgVersion.
            //版本报错
            DxfModel model = DwgReader.Read(CadFilePath);
            //try
            {
                System.Windows.Media.Color color = System.Windows.Media.Colors.Black;
                double lineWidth = 0.05;
                int lineStyle = 1;
                bool closeLine = true;
                foreach (var item in model.Layers)
                {
                    if (item.Enabled)
                    {
                        //CadLinePropertyModel clpm = CadLineList.LineProperties.Find(lp => lp.Name == item.Name);
                        CadLinePropertyModel clpm = null;
                        if (clpm != null)
                        {
                            color = clpm.LineColor;
                            lineWidth = clpm.LineWidth;
                            closeLine = clpm.CloseLine;
                            var entitys = model.Entities.Where(et => et.Layer.Name == item.Name);
                            if (entitys != null)
                            {
                                foreach (var entity in entitys)
                                {
                                    if (entity.EntityType == "LWPOLYLINE")
                                    {
                                        List<SeriesPoint3D> points = new List<SeriesPoint3D>();
                                        foreach (var point in ((DxfLwPolyline)entity).Vertices)
                                        {
                                            double x = (point.X) / Scale;
                                            double y = (point.Y) / Scale;
                                            points.Add(new SeriesPoint3D(x, clpm.LayerHeight, y, color));
                                        }
                                        cadImage3DList.Add(CreateDxfLwPolyline("cad-" + item.Name, entity.ToString()
                                            , false, lineStyle, lineWidth, points.ToArray(), closeLine));
                                    }

                                    if (entity.EntityType == "TEXT")
                                    {
                                        DxfText et = (DxfText)entity;
                                        if (et.Text.Contains("N"))
                                        {
                                            continue;
                                        }
                                        if (et.AlignmentPoint1.X >= GlobalConfig.ProjectConfig.WorkArea.EMin &&
                                            et.AlignmentPoint1.X <= GlobalConfig.ProjectConfig.WorkArea.EMax &&
                                            et.AlignmentPoint1.Y >= GlobalConfig.ProjectConfig.WorkArea.NMin &&
                                            et.AlignmentPoint1.Y <= GlobalConfig.ProjectConfig.WorkArea.EMax)
                                        {

                                            ChartAnnotationCollection.Add(CreateDxfText(((DxfText)entity), "cad-text", 12, clpm.LayerHeight));
                                        }

                                    }
                                    if (entity.EntityType == "MTEXT")
                                    {
                                        DxfMText et = (DxfMText)entity;
                                        if (et.Text.Contains("N"))
                                        {
                                            continue;
                                        }
                                        //if (et.AlignmentPoint1.X >= GlobalConfig.ProjectConfig.WorkArea.EMin &&
                                        //    et.AlignmentPoint1.X <= GlobalConfig.ProjectConfig.WorkArea.EMax &&
                                        //    et.AlignmentPoint1.Y >= GlobalConfig.ProjectConfig.WorkArea.NMin &&
                                        //    et.AlignmentPoint1.Y <= GlobalConfig.ProjectConfig.WorkArea.EMax)
                                        {
                                            ChartAnnotationCollection.Add(CreateDxfMText(et, "cad-text", 12, clpm.LayerHeight));
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
                ChartPointLineCollection.AddRange(cadImage3DList);
            }
        }
        public static PointLineSeries3D CreateDxfLwPolyline(string tag, string title, bool allowUser, int lineStyle, double lineWidth, SeriesPoint3D[] points, bool closeLine)
        {
            PointLineSeries3D pls3d = new PointLineSeries3D();
            pls3d.Tag = tag;
            pls3d.Title.Text = title;
            pls3d.MultiColorLine = true;
            pls3d.AllowUserInteraction = allowUser;
            pls3d.PointsVisible = false;
            pls3d.LineStyle.LineOptimization = (LineOptimization)lineStyle;
            pls3d.LineStyle.Width = lineWidth;
            pls3d.Points = points;
            pls3d.ClosedLine = closeLine;
            return pls3d;
        }
        public Annotation3D CreateDxfText(DxfText dxfText, string tag, double fontSize, double layerHeight)
        {
            Annotation3D at3d = new Annotation3D();
            at3d.Tag = tag;
            at3d.Style = AnnotationStyle.Rectangle;
            at3d.AllowUserInteraction = false;
            at3d.BorderVisible = false;
            at3d.Shadow.Visible = false;
            at3d.Visible = true;
            at3d.Fill.Style = RectFillStyle.None;
            at3d.TextStyle.Color = Dc2Mc(dxfText.Color);
            at3d.TextStyle.Font = new WpfFont("微软雅黑", fontSize);
            at3d.Text = dxfText.Text;

            at3d.LocationCoordinateSystem = CoordinateSystem.AxisValues;
            at3d.LocationAxisValues.SetValues((dxfText.AlignmentPoint1.X) / Scale, layerHeight,
               (dxfText.AlignmentPoint1.Y) / Scale);

            at3d.Anchor.SetValues(0.5, 0.5);
            return at3d;
        }
        public Annotation3D CreateDxfMText(DxfMText dxfText, string tag, double fontSize, double layerHeight)
        {
            Annotation3D at3d = new Annotation3D();
            at3d.Tag = tag;
            at3d.Style = AnnotationStyle.Rectangle;
            at3d.AllowUserInteraction = false;
            at3d.BorderVisible = false;
            at3d.Shadow.Visible = false;
            at3d.Visible = true;
            at3d.Fill.Style = RectFillStyle.None;
            at3d.TextStyle.Color = Colors.Blue;
            //at3d.TextStyle.Color = Dc2Mc(dxfText.Color);
            at3d.TextStyle.Font = new WpfFont("微软雅黑", fontSize);
            at3d.Text = dxfText.Text;
            at3d.LocationCoordinateSystem = CoordinateSystem.AxisValues;
            at3d.LocationAxisValues.SetValues((dxfText.InsertionPoint.X) / Scale, layerHeight,
               (dxfText.InsertionPoint.Y) / Scale);

            at3d.Anchor.SetValues(0.5, 0.5);
            return at3d;
        }
        /// <summary>
        /// dxfColor2MediaColor
        /// </summary>
        /// <param name="en"></param>
        /// <returns></returns>
        public static Color Dc2Mc(EntityColor en)
        {
            return Color.FromRgb(en.R, en.G, en.B);
        }
        #endregion

    }
}
