using FLY.Thick.Base.Server;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;

namespace FLY.Simulation.Battery.RayLaser
{
    public class GageAd
    {
        #region 极片轮廓
        /// <summary>
        /// 极片的横向视图, 精度1mm，
        /// um
        /// </summary>
        public List<DataInfo> HorizontalView = new List<DataInfo>();

        /// <summary>
        /// 极片的一段涂布纵向视图，精度1mm， 第1个数据为 头部
        /// um
        /// </summary>
        public List<DataInfo> SegmentView = new List<DataInfo>();

        /// <summary>
        /// 箔材值， 当上面的视图 IsLight = true， 使用 FoilValue
        /// </summary>
        public double FoilValue { get; set; } = 27;
        #endregion

        #region 机架信息
        /// <summary>
        /// 机架长度 mm
        /// </summary>
        public int TotalLength { get; set; } = 940;

        /// <summary>
        /// 托管左支架位置 mm
        /// </summary>
        public int HoldPosLeft { get; set; } = 57;

        /// <summary>
        /// 托管左支架位置 mm
        /// </summary>
        public int HoldPosRight { get; set; } = 885;

        /// <summary>
        /// 支架宽度 mm
        /// </summary>
        public int HoldWidth { get; set; } = 15;

        /// <summary>
        /// 射线样品值 
        /// </summary>
        public double SampleValueRay { get; set; } = 432;

        /// <summary>
        /// 激光样品值
        /// </summary>
        public double SampleValueLaser { get; set; } = 654;

        /// <summary>
        /// 射线样品宽度 mm
        /// </summary>
        public double SampleWidthRay { get; set; } = 250;

        /// <summary>
        /// 激光样品宽度 mm
        /// </summary>
        public double SampleWidthLaser { get; set; } = 25;
        #endregion

        /// <summary>
        /// 纵向光纤与射线纵向距离 mm
        /// </summary>
        public double VSignOffsetRay { get; set; } = 207;

        /// <summary>
        /// 纵向光纤与激光纵向距离 mm
        /// </summary>
        public double VSignOffsetLaser { get; set; } = 610;


        /// <summary>
        /// 相对于机架 左起始位置 mm
        /// </summary>
        public int FilmBegin { get; set; } = 170;

        /// <summary>
        /// 极片速度 m/min
        /// </summary>
        public double FilmVelocity { get; set; } = 20;

        /// <summary>
        /// 当前极片位置 m
        /// </summary>
        public double FilmPosition { get; set; } = 0;

        /// <summary>
        /// 纵向光纤信号触发了
        /// </summary>
        public bool IsVSignLight { get; set; }

        /// <summary>
        /// 同步信号触发了
        /// </summary>
        public bool IsSyncLight { get; set; }
        public CurveCollection curve_laser;
        public CurveCollection curve_ray;


        public void Init()
        {
            curve_ray = new CurveCollection("curve_ray.json");
            curve_laser = new CurveCollection("curve_laser.json");

            Load();
        }
        void Load()
        {
            Load_DataInfo(HorizontalView, "HorizontalView.csv");
            Load_DataInfo(SegmentView, "SegmentView.csv");
        }
        void Load_DataInfo(List<DataInfo> dataInfos, string csvFilePath)
        {
            dataInfos.Clear();
            using (StreamReader sr = new StreamReader(csvFilePath))
            {
                string header = sr.ReadLine();//标题 , Thick, HSign

                while (!sr.EndOfStream)
                {
                    string s = sr.ReadLine();
                    string[] ss = s.Split(',');

                    double thk = double.Parse(ss[0]);
                    int hsign = int.Parse(ss[1]);
                    dataInfos.Add(new DataInfo()
                    {
                        Thick = thk,
                        IsLight = hsign == 1
                    });
                }
                sr.Close();
            }
        }

        DateTime lastTime = DateTime.MinValue;
        public void OnPoll(DateTime now)
        {


            if (lastTime == DateTime.MinValue)
            {
                lastTime = now;
                return;
            }

            var ts = now - lastTime;

            double ms = 1.0 * ts.Ticks / TimeSpan.TicksPerMillisecond;
            double minute = ms / 1000 / 60;
            if (FilmVelocity != 0)
            {
                FilmPosition += minute * FilmVelocity;
            }

            int index = (int)(FilmPosition * 1000 % SegmentView.Count());
            IsVSignLight = SegmentView[index].IsLight;

            lastTime = now;
        }
        public enum PosType
        {
            /// <summary>
            /// 空气
            /// </summary>
            Air,
            /// <summary>
            /// 极片
            /// </summary>
            Film,
            /// <summary>
            /// 托辊支架
            /// </summary>
            Hold,
            /// <summary>
            /// 样品
            /// </summary>
            Sample
        }


        /// <summary>
        /// 
        /// </summary>
        /// <param name="isRay">是射线？</param>
        /// <param name="mm">相对于机架横向位置mm</param>
        /// <param name="mm_v">相对于极片纵向位置mm</param>
        /// <param name="posType">输出位置类型</param>
        /// <returns></returns>
        public double GetValue(bool isRay, int mm, int mm_v, out PosType posType)
        {


            if (mm >= (HoldPosLeft - HoldWidth / 2) && mm <= (HoldPosLeft + HoldWidth / 2))
            {
                posType = PosType.Hold;
                return 100000;
            }

            if (mm >= FilmBegin && mm < FilmBegin + HorizontalView.Count)
            {
                posType = PosType.Film;
                var dataInfoH = HorizontalView[mm - FilmBegin];
                while (mm_v < 0)
                {
                    mm_v += SegmentView.Count();
                }
                var dataInfoV = SegmentView[mm_v % SegmentView.Count()];

                if ((dataInfoV.IsLight) || (dataInfoH.IsLight))
                {
                    return FoilValue;
                }

                double vValue = dataInfoV.Thick;
                double hValue = dataInfoH.Thick;

                return (vValue + hValue) / 2;
            }

            if (mm >= (HoldPosRight - HoldWidth / 2) && mm <= (HoldPosRight + HoldWidth / 2))
            {
                posType = PosType.Hold;
                return 100000;
            }

            if (isRay)
            {
                if (mm >= (HoldPosRight + HoldWidth / 2) && mm <= (HoldPosRight + HoldWidth / 2 + SampleWidthRay))
                {
                    posType = PosType.Sample;
                    return SampleValueRay;
                }
            }
            else
            {
                if (mm >= (HoldPosRight + HoldWidth / 2) && mm <= (HoldPosRight + HoldWidth / 2 + SampleWidthLaser))
                {
                    posType = PosType.Sample;
                    return SampleValueLaser;
                }
            }


            posType = PosType.Air;
            return 0;
        }
    }

    public class DataInfo
    {
        /// <summary>
        /// 上光纤是亮
        /// </summary>
        public bool IsLight;
        /// <summary>
        /// 厚度值
        /// </summary>
        public double Thick;
    }
}
