using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ComponentModel;

using FObjBase;
using FLY.Thick.Base.IService;
using FLY.Thick.Base.OBJ_INTERFACE;
using FLY.Thick.Base.Common;
using PropertyChanged;

namespace FLY.Thick.Base.Client
{
    public class GetSampleServiceClient : FObj, IGetSampleService
    {
        IFConn mConn;
        UInt32 mServerID;

        public GetSampleServiceClient(UInt32 id)
        {
            mServerID = id;

            for (int i = 0; i < Samples.Count(); i++)
            {
                SampleCell sampleCell = new SampleCell();
                sampleCell.Index = i;
                Samples[i] = sampleCell;
            }

            Features[0] = new SampleFeature() { Name = "正向" };
            Features[1] = new SampleFeature() { Name = "反向" };

        }
        public class SampleCell : ISampleCell
        {

            public int Index { get; set; }
            /// <summary>
            /// 使能
            /// </summary>
            public bool Enable { get; set; }


            /// <summary>
            /// 参数：只检查不标定
            /// </summary>
            public bool JustForCheck { get; set; }

            /// <summary>
            /// 原始AD值
            /// </summary>
            public int OrgAD { get; set; }
            
            /// <summary>
            /// 位置
            /// </summary>
            public int Position { get; set; }
            
            /// <summary>
            /// 状态：当前测量的AD值
            /// </summary>
            public int AD { get; set; }


            /// <summary>
            /// 状态：当前测量的AD值 对应的 样品值
            /// </summary>
            public int SampleValue { get; set; }

            public event PropertyChangedEventHandler PropertyChanged;

        }
        public class SampleFeature : ISampleFeature
        {
            public string Name { get; set; }
            /// <summary>
            /// 使能
            /// </summary>
            public bool Enable { get; set; }

            /// <summary>
            /// 开始位置
            /// </summary>
            public int StartPos { get; set; }

            /// <summary>
            /// 结束位置
            /// </summary>
            public int EndPos { get; set; }


            /// <summary>
            /// 状态：相似度必须高于0.8，失败-1
            /// </summary>
            public double MaxRelevancy { get; set; } = -1;  


            /// <summary>
            /// 状态：最大相似度对应的偏移
            /// </summary>
            public int MaxOffset { get; set; }


            /// <summary>
            /// 状态：扫描数据，从扫描数据提取的相似的一段
            /// 它的单位是 grid, 需要 posOfGrid, 转换为 pos
            /// 开始位置是 StartPos - Search
            /// </summary>
            [DoNotCheckEquality]
            public int[] ScanData { get; set; }
            
            public event PropertyChangedEventHandler PropertyChanged;

        }
        #region IGetSampleService 成员

        /// <summary>
        /// 参数：使能
        /// </summary>
        public bool Enable { get; set; }

        /// <summary>
        /// 参数：间隔
        /// </summary>
        public int Interval { get; set; }

        /// <summary>
        /// 采样计数
        /// </summary>
        public int Timer { get; set; }

        /// <summary>
        /// 参数：速度
        /// </summary>
        public UInt32 Velocity { get; set; }

        /// <summary>
        /// 参数：样品点范围
        /// </summary>
        public int Range { get; set; }


        /// <summary>
        /// 滤波窗口
        /// </summary>
        public int Window { get; set; }

        /// <summary>
        /// 样品
        /// </summary>
        public ISampleCell[] Samples { get; } = new ISampleCell[3];

        /// <summary>
        /// 查找公差
        /// </summary>
        public int Search { get; set; }

        /// <summary>
        /// 特征  相识度 0 正， 1 反
        /// </summary>
        public ISampleFeature[] Features { get; } = new ISampleFeature[2];


        /// <summary>
        /// 状态：从flyad7 得到的。 用于绘制图
        /// </summary>
        public int PosOfGrid { get; set; } = 10;
        
        /// <summary>
        /// 
        /// </summary>
        public void Apply() 
        {
            GETSAMPLE_OBJ_INTERFACE.Pack_Params p = new GETSAMPLE_OBJ_INTERFACE.Pack_Params
            {
                enable = Enable,
                interval = Interval,
                velocity = Velocity,
                range = Range,
                window = Window,
                samples = new GETSAMPLE_OBJ_INTERFACE.Pack_Params_SampleCell[Samples.Count()],
                search = Search,
                features = new GETSAMPLE_OBJ_INTERFACE.Pack_Params_SampleFeature[Features.Count()]
            };

            for (int i = 0; i < Samples.Count(); i++)
            {
                p.samples[i] = new GETSAMPLE_OBJ_INTERFACE.Pack_Params_SampleCell
                {
                    enable = Samples[i].Enable,
                    justForCheck = Samples[i].JustForCheck,
                    orgad = Samples[i].OrgAD,
                    position = Samples[i].Position
                };
            }
            
            for (int i = 0; i < Features.Count(); i++)
            {
                p.features[i] = new GETSAMPLE_OBJ_INTERFACE.Pack_Params_SampleFeature
                {
                    enable = Features[i].Enable,
                    startpos = Features[i].StartPos,
                    endpos = Features[i].EndPos
                };
            }

            //获取所有数据，设置推送
            CurrObjSys.SetValueEx(
                mConn, mServerID, ID, 
                GETSAMPLE_OBJ_INTERFACE.SET_PARAMS,
                p.ToBytes()
                );
        }
        #endregion




        #region INotifyPropertyChanged 成员

        public event PropertyChangedEventHandler PropertyChanged;

        #endregion

        public override void Dispose()
        {
            CurrObjSys.ObjRemove(
                this, mConn);
        }
        public override void ConnectNotify(IFConn from)
        {
            mConn = from;
            if (from.IsConnected)
            {
                //获取所有数据，设置推送
                CurrObjSys.GetValueEx(
                    mConn, mServerID, ID, 
                    GETSAMPLE_OBJ_INTERFACE.GET_PARAMS);
                CurrObjSys.GetValueEx(
                    mConn, mServerID, ID,
                    GETSAMPLE_OBJ_INTERFACE.GET_STATE);

                CurrObjSys.SenseConfigEx(
                    mConn, mServerID, ID,
                    0xffffffff, SENSE_CONFIG.ADD);

            }
        }
        public override void PushGetValue(IFConn from, uint srcid, ushort memid, byte[] infodata)
        {
            switch (memid)
            {
                case GETSAMPLE_OBJ_INTERFACE.GET_PARAMS:
                    {
                        GETSAMPLE_OBJ_INTERFACE.Pack_Params p = new GETSAMPLE_OBJ_INTERFACE.Pack_Params();
                        if (!p.TryParse(infodata))
                            return;

                        Enable = p.enable;
                        Interval = p.interval;
                        Velocity = p.velocity;
                        Range = p.range;
                        Window = p.window;
                        for (int i = 0; i < Samples.Count() && i < p.samples.Count(); i++)
                        {
                            Samples[i].Enable = p.samples[i].enable;
                            Samples[i].JustForCheck = p.samples[i].justForCheck;
                            Samples[i].OrgAD = p.samples[i].orgad;
                            Samples[i].Position = p.samples[i].position;
                        }
                        Search = p.search;
                        for (int i = 0; i < Features.Count() && i < p.features.Count(); i++)
                        {
                            Features[i].Enable = p.features[i].enable;
                            Features[i].StartPos = p.features[i].startpos;
                            Features[i].EndPos = p.features[i].endpos;
                        }
                    } break;
                case GETSAMPLE_OBJ_INTERFACE.GET_STATE:
                    {
                        GETSAMPLE_OBJ_INTERFACE.Pack_State p = new GETSAMPLE_OBJ_INTERFACE.Pack_State();
                        
                        if (!p.TryParse(infodata ))
                            return;
                        PosOfGrid = p.posOfGrid;

                        for (int i = 0; i < Samples.Count() && i < p.samples.Count(); i++)
                        {
                            Samples[i].AD = p.samples[i].ad;
                            Samples[i].SampleValue = p.samples[i].value;
                        }
                        for (int i = 0; i < Features.Count() && i < p.features.Count(); i++)
                        {
                            Features[i].MaxRelevancy = p.features[i].maxRelevancy;
                            Features[i].MaxOffset = p.features[i].maxOffset;
                            Features[i].ScanData = p.features[i].scanData;
                        }
                    } break;
            }
        }
        public override void PushInfo(IFConn from, uint srcid, ushort infoid, byte[] infodata)
        {
            PushGetValue(from, srcid, infoid, infodata);
        }
    }

}
