using CommunityToolkit.Mvvm.Input;
using FLY.Thick.Base.IService;
using FLY.Thick.Base.UI;
using FLY.Thick.FilmCasting.Common;
using FLY.Thick.FilmCasting.IService;
using System;
using System.ComponentModel;
using System.Windows.Controls;
using Unity;
using IInitParamService = FLY.Thick.Base.IService.IInitParamService;

namespace FLY.Thick.FilmCasting.UI
{
    /// <summary>
    /// PgBoltMapCalender.xaml 的交互逻辑
    /// </summary>
    public partial class PgBoltMap : Page
    {
        PgBoltMapVm viewModel;
        public PgBoltMap()
        {
            InitializeComponent();
        }

        [InjectionMethod]
        public void Init(
            IBoltMapFilmCastingService boltMapCalenderService,
            IInitParamService initParamService,
            IBorderSearchService borderSearchService,
            IFilmCastingProfileService filmCastingProfileService)
        {
            viewModel = new PgBoltMapVm();
            viewModel.Init(boltMapCalenderService, initParamService, borderSearchService,
                filmCastingProfileService);
            this.DataContext = viewModel;
        }
    }
    public class PgBoltMapVm : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        #region 参数
        /// <summary>
        /// 螺丝宽度 mm, 是double, 那就可以设置英寸
        /// </summary>
        public double BoltWidth { get; set; }

        /// <summary>
        /// 总螺丝数 
        /// </summary>
        public int BoltCnt { get; set; }

        /// <summary>
        /// 与机架方向相反
        /// </summary>
        public bool IsReversed { get; set; }

        /// <summary>
        /// 平滑，以前后分区平均滤波 ，=0，只有自己，1，左右各一个
        /// </summary>
        public int Smooth { get; set; }

        #endregion
        /// <summary>
        /// 模头总长 mm BoltCnt*BoltWidth
        /// </summary>
        public double DieLength { get; private set; }

        /// <summary>
        /// 扫描架总长 mm 
        /// </summary>
        public double FrameLength { get; private set; }

        #region profile
        /// <summary>
        /// 左单边不工作螺丝位
        /// </summary>
        public int LeftEmptyBolts { get; set; } = 1;

        /// <summary>
        /// 右单边不工作螺丝位
        /// </summary>
        public int RightEmptyBolts { get; set; } = 1;

        /// <summary>
        /// 收缩率 
        /// </summary>
        public double UniformShrinkPercent { get; set; } = 0.03;

        /// <summary>
        /// 膜中心偏移 mm
        /// </summary>
        public int MidOffset { get; set; }
        /// <summary>
        /// 产品名称
        /// </summary>
        public string PName { get; private set; }
        #endregion


        #region Command
        public RelayCommand ApplyCmd { get; }
        #endregion

        IBoltMapFilmCastingService boltMapFilmCastingService;
        public IInitParamService InitParam => initParamService;

        IBorderSearchService borderSearchService;
        IInitParamService initParamService;
        IFilmCastingProfileService filmCastingProfileService;
        public PgBoltMapVm()
        {
            ApplyCmd = new RelayCommand(Apply);
        }

        public void Init(
            IBoltMapFilmCastingService _boltMapFilmCastingService,
            IInitParamService _initParamService,
            IBorderSearchService _borderSearchService,
            IFilmCastingProfileService _filmCastingProfileService)
        {
            this.boltMapFilmCastingService = _boltMapFilmCastingService;
            this.initParamService = _initParamService;
            this.borderSearchService = _borderSearchService;
            this.filmCastingProfileService = _filmCastingProfileService;


            Misc.BindingOperations.SetBinding(boltMapFilmCastingService, nameof(IBoltMapFilmCastingService.IsReversed), this, nameof(IsReversed));
            Misc.BindingOperations.SetBinding(boltMapFilmCastingService, nameof(IBoltMapFilmCastingService.BoltWidth), this, nameof(BoltWidth));
            Misc.BindingOperations.SetBinding(boltMapFilmCastingService, nameof(IBoltMapFilmCastingService.BoltCnt), this, nameof(BoltCnt));
            Misc.BindingOperations.SetBinding(boltMapFilmCastingService, nameof(IBoltMapFilmCastingService.Smooth), this, nameof(Smooth));

            var param = this.filmCastingProfileService.Param;
            Misc.BindingOperations.SetBinding(param, nameof(FilmCastingProfileParam.LeftEmptyBolts), this, nameof(LeftEmptyBolts));
            Misc.BindingOperations.SetBinding(param, nameof(FilmCastingProfileParam.RightEmptyBolts), this, nameof(RightEmptyBolts));
            Misc.BindingOperations.SetBinding(param, nameof(FilmCastingProfileParam.UniformShrinkPercent), this, nameof(UniformShrinkPercent));
            Misc.BindingOperations.SetBinding(param, nameof(FilmCastingProfileParam.MidOffset), this, nameof(MidOffset));
            Misc.BindingOperations.SetBinding(param, nameof(FilmCastingProfileParam.PName), this, nameof(PName));

            Misc.BindingOperations.SetBinding(this, new string[] { nameof(BoltWidth), nameof(BoltCnt) }, () =>
            {
                DieLength = BoltWidth * BoltCnt;
            });

            Misc.BindingOperations.SetBinding(initParamService, new string[] { nameof(IInitParamService.PosLength), nameof(IInitParamService.Encoder1_mmpp) }, () =>
            {
                FrameLength = initParamService.PosLength * initParamService.Encoder1_mmpp;
            });
        }

        private void Apply()
        {
            if (!WdPassword.Authorize("Boltmap"))
                return;

            var param = (FilmCastingProfileParam)this.filmCastingProfileService.Param.Clone();
            param.LeftEmptyBolts = LeftEmptyBolts;
            param.RightEmptyBolts = RightEmptyBolts;
            param.UniformShrinkPercent = UniformShrinkPercent;
            param.MidOffset = MidOffset;
            this.filmCastingProfileService.ApplyParam(param);

            this.boltMapFilmCastingService.Smooth = Smooth;
            this.boltMapFilmCastingService.BoltWidth = BoltWidth;
            this.boltMapFilmCastingService.BoltCnt = BoltCnt;
            this.boltMapFilmCastingService.IsReversed = IsReversed;
            this.boltMapFilmCastingService.Apply();

            FLY.ControlLibrary.Window_Tip.Show("应用成功",
                null,
                TimeSpan.FromSeconds(2));
        }
    }
}
