using System;
using System.ComponentModel;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Forms;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using SPC.Kiosk.Common;
using System.Threading.Tasks;
using SPC.Kiosk.PB.Model;
using SPC.Kiosk.PB.ViewModel;
using SPC.Kiosk.Popup.Model;
using System.Windows.Interop;
using System.Windows.Threading;

namespace SPC.Kiosk.PB
{
    /// <summary>
    /// MainWindow.xaml에 대한 상호 작용 논리
    /// </summary>
    public partial class PBWindow : Window
    {

        #region [ Members ]
        /// <summary>
        /// IcReadStart Event
        /// </summary>
        /// <param name="sender"></param>
        public delegate void IcReaderCheck(object sender);
        /// <summary>
        /// IcReadStart Event 반환용 
        /// </summary>
        public event IcReaderCheck ReaderCheck;
        /// <summary>
        /// PosRecipetRefund Event
        /// </summary>
        /// <param name="sender"></param>
        public delegate void PosRecipetRefund(object sender);
        /// <summary>
        /// PosRecipetRefund Event 반환용 
        /// </summary>
        public event PosRecipetRefund RecipetRefund;
        /// <summary>
        /// PosRecipetReprint Event
        /// </summary>
        /// <param name="sender"></param>
        public delegate void PosRecipetReprint(object sender);
        /// <summary>
        /// PosRecipetReprint Event 반환용 
        /// </summary>
        public event PosRecipetReprint RecipetReprint;
        private VmPBViewModel ViewModel { get; set; }
        private PBPageType ShowPage { get; set; }
        private int ScreenNo { get; set; } = 0;
        private DispatcherTimer BarcodeFocusing;
        #endregion Members

        #region [ Ctor/Etc ]
        /// <summary>
        /// Ctor
        /// </summary>
        public PBWindow()
        {
            StartInitialize();
        }
        /// <summary>
        /// Ctor
        /// </summary>
        /// <param name="_screenNo"></param>
        public PBWindow(int _screenNo)
        {
            ScreenNo = _screenNo;
            StartInitialize();
        }
        #endregion

        #region [ Methods ]

        private void AiOpen(PBPageType _TargetPage)
        {
            //---------객체인식 화면 이동 시------------
            if (_TargetPage.Equals(PBPageType.Sensing))
            {

                this.Topmost = false;
                if (this.ViewModel.OptionValue812 == "0") { this.GMB_CallButton.Visibility = Visibility.Collapsed; }
                else { this.GMB_CallButton.Visibility = Visibility.Hidden; }
                this.GMB_LanguageButton.Visibility = Visibility.Hidden;
                this.GMB_PonitButton.Visibility = Visibility.Hidden;
                this.ViewModel.ToIntorTimerStop();
                AiScannerProcess.ExcuteAiScanner(new WindowInteropHelper(this).Handle);
            }
            else
            {
                this.Topmost = true;
                if (this.ViewModel.OptionValue812 == "0") { this.GMB_CallButton.Visibility = Visibility.Collapsed; }
                else { this.GMB_CallButton.Visibility = Visibility.Visible; }
                this.GMB_LanguageButton.Visibility = Visibility.Visible;
                this.GMB_PonitButton.Visibility = Visibility.Visible;
                //센싱 화면 종료 시 객체인식 프로세스 종료
                AiScannerProcess.StopAiScanner();
                this.ViewModel.ToIntorTimerStart();
            }
        }
        private void StartInitialize()
        {
            InitializeComponent();
            this.Left = Screen.AllScreens[ScreenNo].WorkingArea.Left;
            this.Top = Screen.AllScreens[ScreenNo].WorkingArea.Top;
            this.Width = Screen.AllScreens[ScreenNo].Bounds.Width;
            this.Height = Screen.AllScreens[ScreenNo].Bounds.Height;
            this.Loaded += PBWindow_Loaded;
        }
        private void GoRecipetReprint()
        {
            try
            {
                RecipetReprint(this);
            }
            catch
            {
            }
        }
        private void GoRecipetRefund()
        {
            try
            {
                RecipetRefund(this);
            }
            catch
            {
            }
        }
        private void GoReaderCheck()
        {
            try
            {
                ReaderCheck(this);
            }
            catch
            {
            }
        }
        private void SetPage(PBPageType _TargetPage)
        {
            switch (ShowPage)
            {
                case PBPageType.Intro:
                    switch (_TargetPage)
                    {
                        case PBPageType.Items:
                            ContentGrid.Visibility = Visibility.Visible;
                            FirstGrid.Visibility = Visibility.Hidden;
                            ItemGrid.Visibility = Visibility.Visible;
                            SenserGrid.Visibility = Visibility.Hidden;
                            ToggleGrid.Visibility = Visibility.Visible;
                            ContentGrid.RenderTransform = null;
                            ItemGrid.RenderTransform = null;
                            break;
                        case PBPageType.Sensing:
                            ContentGrid.Visibility = Visibility.Visible;
                            FirstGrid.Visibility = Visibility.Hidden;
                            ItemGrid.Visibility = Visibility.Hidden;
                            SenserGrid.Visibility = Visibility.Visible;
                            ToggleGrid.Visibility = Visibility.Visible;
                            SenserGrid.RenderTransform = null;

                            break;
                        case PBPageType.FirstSelect:                            
                            ContentGrid.Visibility = Visibility.Visible;
                            FirstGrid.Visibility = Visibility.Visible;
                            ItemGrid.Visibility = Visibility.Hidden;
                            SenserGrid.Visibility = Visibility.Hidden;
                            ToggleGrid.Visibility = Visibility.Hidden;
                            FirstGrid.RenderTransform = null;
                            break;
                    }
                    OpenAndClose(this.BaseGrid, this.TradeGrid, OpenCloseAnimationType.GotoLeft);
                    break;
                case PBPageType.FirstSelect:
                    switch (_TargetPage)
                    {
                        case PBPageType.Items:
                            SenserGrid.Visibility = Visibility.Hidden;
                            ItemGrid.Visibility = Visibility.Visible;
                            ToggleGrid.Visibility = Visibility.Visible;
                            ItemGrid.RenderTransform = new TranslateTransform(ItemGrid.Width, 0);
                            OpenAndClose(this.FirstGrid, this.ItemGrid, OpenCloseAnimationType.GotoLeft);
                            break;
                        case PBPageType.Sensing:
                            SenserGrid.Visibility = Visibility.Visible;
                            ItemGrid.Visibility = Visibility.Hidden;
                            ToggleGrid.Visibility = Visibility.Visible;
                            SenserGrid.RenderTransform = new TranslateTransform(SenserGrid.Width, 0);
                            OpenAndClose(this.FirstGrid, this.SenserGrid, OpenCloseAnimationType.GotoLeft);
                            break;
                        case PBPageType.Intro:
                            ItemGrid.Visibility = Visibility.Hidden;
                            SenserGrid.Visibility = Visibility.Hidden;
                            OpenAndClose(this.TradeGrid, this.BaseGrid, OpenCloseAnimationType.GotoRight);
                            break;
                    }
                    break;
                case PBPageType.Items:
                    switch (_TargetPage)
                    {
                        case PBPageType.Intro:
                            SenserGrid.Visibility = Visibility.Hidden;
                            FirstGrid.Visibility = Visibility.Hidden;
                            OpenAndClose(this.TradeGrid, this.BaseGrid, OpenCloseAnimationType.GotoRight);
                            break;
                        case PBPageType.Sensing:
                            SenserGrid.Visibility = Visibility.Visible;
                            SenserGrid.RenderTransform = new TranslateTransform(SenserGrid.Width, 0);
                            OpenAndClose(this.ItemGrid, this.SenserGrid, OpenCloseAnimationType.GotoRight);
                            break;
                        case PBPageType.FirstSelect:
                            FirstGrid.Visibility = Visibility.Visible;
                            ToggleGrid.Visibility = Visibility.Hidden;
                            FirstGrid.RenderTransform = new TranslateTransform(FirstGrid.Width, 0);
                            OpenAndClose(this.ItemGrid, this.FirstGrid, OpenCloseAnimationType.GotoRight);
                            break;
                    }
                    break;
                case PBPageType.Sensing:

                    ScanFirst.Visibility = Visibility.Visible;
                    ScanSecond.Visibility = Visibility.Hidden;
                    switch (_TargetPage)
                    {
                        case PBPageType.Intro:
                            ItemGrid.Visibility = Visibility.Hidden;
                            FirstGrid.Visibility = Visibility.Hidden;
                            OpenAndClose(this.TradeGrid, this.BaseGrid, OpenCloseAnimationType.GotoRight);
                            break;
                        case PBPageType.Items:
                            ItemGrid.Visibility = Visibility.Visible;
                            ItemGrid.RenderTransform = new TranslateTransform(ItemGrid.Width * -1, 0);
                            OpenAndClose(this.SenserGrid, this.ItemGrid, OpenCloseAnimationType.GotoLeft);
                            break;
                        case PBPageType.FirstSelect:
                            FirstGrid.Visibility = Visibility.Visible;
                            ToggleGrid.Visibility = Visibility.Hidden;
                            FirstGrid.RenderTransform = new TranslateTransform(FirstGrid.Width, 0);
                            OpenAndClose(this.SenserGrid, this.FirstGrid, OpenCloseAnimationType.GotoRight);
                            break;
                        case PBPageType.Sensing:
                            this.ViewModel.SensingSubPage = PBSensingSubPageType.SensingPage;
                            ChangeWindow();
                            break;
                    }
                    break;
            }
        }
        private void ChangeWindow()
        {
            //this.Dispatcher.Invoke((Action)(() =>
            //{
            try
            {
                var _target = this.SenserGrid;
                var targetAnimation = new Storyboard();
                var centerX = _target.ActualWidth / 2;
                var centerY = _target.ActualHeight / 2;
                _target.RenderTransform = new ScaleTransform(1, 1, centerX, centerY);
                var flipXAni = new DoubleAnimation(0, 1, new Duration(TimeSpan.FromSeconds(0.2)));
                Storyboard.SetTarget(flipXAni, _target);
                Storyboard.SetTargetProperty(flipXAni, new PropertyPath("RenderTransform.ScaleX"));
                targetAnimation.Children.Add(flipXAni);
                targetAnimation.Completed += TargetAnimation_Completed;
                targetAnimation.Begin();
            }
            catch (Exception ex)
            {
                CommonLog.ErrorLogWrite(this, "ChangeWindow()", "Fail !!", string.Format("{0}\n{1}", ex.Message, ex.StackTrace));
            }
            //}));
        }
        private void ScanBoxEnable()
        {
            if (!this.BarCode.IsEnabled) this.BarCode.IsEnabled = true;
            if (!this.BarCode.IsFocused) this.BarCode.Focus();
        }
        private void ScanBoxDisable()
        {
            BarcodeFocusing.Stop();
            this.BarCode.IsEnabled = false;
        }
        private void TargetAnimation_Completed(object sender, EventArgs e)
        {
            ScanBoxEnable();
        }
        private void GMBtoggle2Sensing()
        {
            var target = this.AiToggle;
            var toSensing = new Storyboard();
            target.RenderTransform = new TranslateTransform(0, 0);
            var toLeftAnimation = new DoubleAnimation(this.AiToggle.Width, 0, new Duration(TimeSpan.FromSeconds(0.2)));
            Storyboard.SetTarget(toLeftAnimation, target);
            Storyboard.SetTargetProperty(toLeftAnimation, new PropertyPath("RenderTransform.X"));
            toSensing.Children.Add(toLeftAnimation);
            toSensing.Completed += ToSensing_Completed;
            toSensing.Begin();
        }
        private void GMBtoggle2Order()
        {
            var target = this.AiToggle;
            var toOrder = new Storyboard();
            target.RenderTransform = new TranslateTransform(0, 0);
            var toLeftAnimation = new DoubleAnimation(0, this.AiToggle.Width, new Duration(TimeSpan.FromSeconds(0.2)));
            Storyboard.SetTarget(toLeftAnimation, target);
            Storyboard.SetTargetProperty(toLeftAnimation, new PropertyPath("RenderTransform.X"));
            toOrder.Children.Add(toLeftAnimation);
            toOrder.Completed += ToOrder_Completed;
            toOrder.Begin();

        }
        private void OpenBase()
        {
            this.TradeGrid.IsEnabled = false;
            this.TradeGrid.Visibility = Visibility.Hidden;
            var OpenAnimations = Animations.GetOpenAnimation(this.TopGrid, OpenCloseAnimationType.FullSizeUp, this.Width, 0.5);
            if (OpenAnimations != null)
            {
                OpenAnimations.Completed += OpenAnimations_Completed;
                OpenAnimations.Name = this.BaseGrid.Name;
                OpenAnimations.Begin();
            }
        }
        private void CloseBase()
        {
            var CloseAnimation = Animations.GetCloseAnimation(this.TopGrid, OpenCloseAnimationType.FullSizeDown, this.Width, 0.2);
            if (CloseAnimation != null)
            {
                CloseAnimation.Completed += CloseAnimation_Completed;
                CloseAnimation.Begin();
            }
        }
        private void OpenAndClose(Grid _closeGrid, Grid _openGrid, OpenCloseAnimationType _animationType)
        {
            var OpenAnimations = Animations.GetOpenAndCloseAnimation(_closeGrid, _openGrid, _animationType, _closeGrid.ActualWidth, 0.3);
            if (OpenAnimations != null)
            {
                OpenAnimations.Completed += OpenAnimations_Completed;
                OpenAnimations.Name = _openGrid.Name;
                OpenAnimations.Begin();
            }
        }
        private void OpenPaymentsWindow()
        {
            try
            {
                var newPBPayment = new PBPaymentsWindow(ViewModel.MiniBasketData
                                               , ViewModel.HappyPointReturn
                                               , ViewModel.OpenPBPaymentPage);
                this.ViewModel.ToIntorTimerStop();
                this.ViewModel.WaitWindowFrom.ShowWaitWindow();
                newPBPayment.ShowDialog();
                this.ViewModel.WaitWindowFrom.CloseWaitWindow();
                this.ViewModel.ToIntorTimerStart();
                if (newPBPayment.DataContext is PBPaymentsViewModel returnViewModel)
                {
                    ViewModel.ShowLanguageType = returnViewModel.ReturnValue.ReturnLanguage;
                    if (returnViewModel.ReturnValue.PopupArgs is List<M_BasketItem> returnBasket
                        && returnBasket.Count > 0)
                    {
                        ViewModel.MiniBasketData = new System.Collections.ObjectModel.ObservableCollection<M_BasketItem>(returnBasket);
                    }
                    else
                    {
                        ViewModel.DeledteAllBasket();
                    }
                    if (returnViewModel.ReturnValue.TimeOut
                     || returnViewModel.ReturnValue.OKAnswer) ViewModel.DefaultPage = PBPageType.Intro;
                }
                newPBPayment = null;

            }
            catch (Exception ex)
            {
                CommonLog.ErrorLogWrite(this, "OpenPaymentsWindow()", "Fail !!", string.Format("{0}\n{1}", ex.Message, ex.StackTrace));
            }
           
        }
        #endregion Methods

        #region [ Event Handlers ]
        private void PBWindow_Loaded(object sender, RoutedEventArgs e)
        {
            if (this.DataContext is VmPBViewModel viewModel)
            {
                ViewModel = viewModel;
                viewModel.PropertyChanged += ViewModel_PropertyChanged;
                ViewModel.IsTimeoutPopup = true;
            }
            this.BarCode.PreviewKeyDown += BarCode_PreviewKeyDown;
            BarcodeFocusing = new DispatcherTimer
            {
                Interval = TimeSpan.FromMilliseconds(100d),
            };
            BarcodeFocusing.Tick += BarcodeFocusing_Tick;
            OpenBase();
        }

        private void BarcodeFocusing_Tick(object sender, EventArgs e)
        {
            try
            {
                if (this.ViewModel is VmPBViewModel)
                {
                    if (ViewModel.DefaultPage.Equals(PBPageType.Sensing))
                    {
                        ScanBoxEnable();
                    }
                }

            }
            catch 
            {
            }
        }

        private void BarCode_PreviewKeyDown(object sender, System.Windows.Input.KeyEventArgs e)
        {
            if (sender is System.Windows.Controls.TextBox textBox
                && (e.Key.Equals(Key.Enter) || e.Key.Equals(Key.Return))
                && !string.IsNullOrEmpty(textBox.Text))
            {
                this.ViewModel.ReadBarCode = textBox.Text.Trim();
                textBox.Text = string.Empty;
            }
        }
        private void ViewModel_PropertyChanged(object sender, PropertyChangedEventArgs e)
        {
            switch (e.PropertyName)
            {
                case "DefaultPage":
                    SetPage(ViewModel.DefaultPage);
                    if (this.ViewModel.OptionValue810 == "0" 
                        && this.ViewModel.OptionValue811 == "1")
                    { }
                    else
                    {
                        AiOpen(ViewModel.DefaultPage);
                    }
                    
                    break;
                case "GmbReaderCheckOpen":
                    if (ViewModel.GmbReaderCheckOpen)
                    {
                        AiScannerProcess.StopAiScanner();
                        this.ViewModel.ToIntorTimerStop();
                        this.AdminGrid.Visibility = Visibility.Visible;
                        ViewModel.ReaderCheckClickCount = 0;
                    }
                    break;
                case "OrderHistoryView":
                    if (this.ViewModel.OrderHistoryView
                        && this.ViewModel.DefaultPage.Equals(PBPageType.Items))
                    {
                        this.OrderHisoty.Visibility = Visibility.Visible;
                        var OrderHisotyOpenAnimation = Animations.GetOpenAnimation(this.OrderHisotyItems, OpenCloseAnimationType.GotoUp, this.OrderHisotyItems.Height, 0.2);
                        if (OrderHisotyOpenAnimation != null)
                        {
                            OrderHisotyOpenAnimation.Completed += OrderHisotyOpenAnimation_Completed;
                            OrderHisotyOpenAnimation.Begin();
                        }
                    }
                    else
                    {
                        var OrderHisotyCloseAnimation = Animations.GetCloseAnimation(this.OrderHisotyItems, OpenCloseAnimationType.GotoDown, this.OrderHisotyItems.Height, 0.2);
                        if (OrderHisotyCloseAnimation != null)
                        {
                            OrderHisotyCloseAnimation.Completed += OrderHisotyCloseAnimation_Completed;
                            OrderHisotyCloseAnimation.Begin();
                        }
                    }
                    break;
                case "SensingSubPage":
                    if (this.ViewModel.SensingSubPage.Equals(PBSensingSubPageType.BarcordPage))
                    {
                        ScanFirst.Visibility = Visibility.Hidden;
                        ScanSecond.Visibility = Visibility.Visible;
                        ChangeWindow();
                    }
                    break;
                case "OpenPBPaymentPage":
                    OpenPaymentsWindow();
                    break;
                case "CanWindowClose":
                    CloseBase();
                    break;
                default:
                    break;
            }
        }

        private void OrderHisotyOpenAnimation_Completed(object sender, EventArgs e)
        {
            this.OrderHisotyItems.IsEnabled = true;
        }

        private void OrderHisotyCloseAnimation_Completed(object sender, EventArgs e)
        {
            this.OrderHisoty.Visibility = Visibility.Collapsed; 
        }

        private void ToSensing_Completed(object sender, EventArgs e)
        {
            var senderStoryboard = (sender as ClockGroup).Timeline as Storyboard;
            senderStoryboard = null;
            this.SenserGrid.IsEnabled = true;
            this.GMB_ic_order.Enabled = true;
            BarcodeFocusing.Start();
        }


        private void ToOrder_Completed(object sender, EventArgs e)
        {
            var senderStoryboard = (sender as ClockGroup).Timeline as Storyboard;
            senderStoryboard = null;
            this.ItemGrid.IsEnabled = true;
            this.GMB_ai_order.Enabled = true;
        }

        


        private void OpenAnimations_Completed(object sender, EventArgs e)
        {
            var senderStoryboard = (sender as ClockGroup).Timeline as Storyboard;
            var getName = senderStoryboard.Name;
            ScanBoxDisable();
            switch (senderStoryboard.Name)
            {

                case "BaseGrid":
                    this.ShowPage = PBPageType.Intro;
                    break;
                case "SenserGrid":
                    this.ShowPage = PBPageType.Sensing;
                    this.ContentGrid.IsEnabled = true;
                    GMBtoggle2Sensing();
                    ScanBoxEnable();
                    break;
                case "ItemGrid":
                    this.ShowPage = PBPageType.Items;
                    this.ContentGrid.IsEnabled = true;
                    GMBtoggle2Order();
                    break;
                case "ContentGrid":
                    this.ShowPage = ViewModel.DefaultPage;
                    switch (ViewModel.DefaultPage)
                    {
                        case PBPageType.Items:
                            GMBtoggle2Order();
                            break;
                        case PBPageType.Sensing:
                            GMBtoggle2Sensing();
                            break;
                    }
                    break;
                case "FirstGrid":
                    this.ShowPage = ViewModel.DefaultPage;
                    break;
                case "TradeGrid":
                    if (ShowPage.Equals(PBPageType.Intro))
                    {

                        this.ShowPage = ViewModel.DefaultPage;
                        switch (ViewModel.DefaultPage)
                        {
                            case PBPageType.Items:
                                GMBtoggle2Order();
                                break;
                            case PBPageType.Sensing:
                                GMBtoggle2Sensing();
                                break;
                            case PBPageType.FirstSelect:
                                FirstGrid.IsEnabled = true;
                                break;
                        }
                    }
                    else
                    {
                        switch (ViewModel.DefaultPage)
                        {
                            case PBPageType.Items:
                                ItemGrid.Visibility = Visibility.Visible;
                                ItemGrid.RenderTransform = new TranslateTransform(ItemGrid.Width * -1, 0); ;
                                OpenAndClose(this.SenserGrid, this.ItemGrid, OpenCloseAnimationType.GotoLeft);
                                break;
                            case PBPageType.Sensing:
                                SenserGrid.Visibility = Visibility.Visible;
                                SenserGrid.RenderTransform = new TranslateTransform(ItemGrid.Width, 0); ;
                                OpenAndClose(this.ItemGrid, this.SenserGrid, OpenCloseAnimationType.GotoRight);
                                
                                break;
                        }
                    }
                    break;
            }
            if (this.FindName(getName) is Grid findGrid) findGrid.IsEnabled = true;
            senderStoryboard = null;

        }
        private void CloseAnimation_Completed(object sender, EventArgs e)
        {
            AiScannerProcess.StopAiScanner();
            if (BarcodeFocusing != null)
            {
                BarcodeFocusing.Stop();
                BarcodeFocusing.Tick -= BarcodeFocusing_Tick;
                BarcodeFocusing = null;
            }
            this.BarCode.PreviewKeyDown -= BarCode_PreviewKeyDown;
            this.ViewModel.Dispose();
            this.Close();
        }
        private void IcReaderCheckButton_MouseClicked(object sender, RoutedEventArgs e)
        {
            GoReaderCheck();
        }
        private void RecipetRefundButton_MouseClicked(object sender, RoutedEventArgs e)
        {
            GoRecipetRefund();
        }
        private void RecipetReprintButton_MouseClicked(object sender, RoutedEventArgs e)
        {
            GoRecipetReprint();
        }
        private void ExitWindow_MouseClicked(object sender, RoutedEventArgs e)
        {
            CloseBase();
        }
        private void CloseWindow_MouseClicked(object sender, RoutedEventArgs e)
        {
            ViewModel.GmbReaderCheckOpen = false;
            this.AdminGrid.Visibility = Visibility.Collapsed;
            this.ViewModel.ToIntorTimerStart();
        }

        #endregion Event Handlers

    }
}
