using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Input;

using FasdDesktopUi.Basics.Models;
using FasdDesktopUi.Basics.UiActions;

namespace FasdDesktopUi.Basics.UserControls
{
    public partial class DetailedData : UserControl
    {

        #region Properties

        #region ListViewDataSource

        #region ListViewHeaders

        public List<object> ListViewHeaders
        {
            get
            {
                if (DetailedInformationData.FullDetailedData?.Count > 0)
                {
                    var _retVal = DetailedInformationData.FullDetailedData[0];
                    var _ret = _retVal as List<object>;
                    return _ret;
                }

                return new List<object>();
            }
        }

        #endregion

        #region ListViewData

        internal static readonly DependencyPropertyKey ListViewDataKey = DependencyProperty.RegisterReadOnly("ListViewData", typeof(List<object>), typeof(DetailedData), new PropertyMetadata(new List<object>()));

        public static readonly DependencyProperty ListViewDataProperty = ListViewDataKey.DependencyProperty;

        public List<object> ListViewData => (List<object>)GetValue(ListViewDataProperty);

        #endregion

        #endregion

        #region DetailedData

        private static void DetailedDataChangedCallback(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            if (!(d is DetailedData _me))
                return;


            if (_me.DetailedInformationData == null)
                return;

            int _skip = _me.DetailedInformationData.HasColumnHeaders? 1 : 0;

            if (_me.DetailedInformationData.FullDetailedData.Count < _skip)
                return;

            var listViewDataKeyValue = _me.DetailedInformationData.FullDetailedData.Count > _skip ? _me.DetailedInformationData.FullDetailedData.Skip(_skip).ToList() : new List<object>();
            _me.SetValue(ListViewDataKey, listViewDataKeyValue);
            _me.UpdateListView();
        }

        public static readonly DependencyProperty DetailedInformationDataProperty =
            DependencyProperty.Register("DetailedInformationData", typeof(cDetailedDataModel), typeof(DetailedData), new PropertyMetadata(new cDetailedDataModel(), new PropertyChangedCallback(DetailedDataChangedCallback)));

        public cDetailedDataModel DetailedInformationData
        {
            get { return (cDetailedDataModel)GetValue(DetailedInformationDataProperty); }
            set { SetValue(DetailedInformationDataProperty, value); }
        }

        #endregion

        #region IsCloseButtonVisible

        public static readonly DependencyProperty IsCloseButtonVisibleProperty =
            DependencyProperty.Register("IsCloseButtonVisible", typeof(bool), typeof(DetailedData), new PropertyMetadata(false));

        public bool IsCloseButtonVisible
        {
            get { return (bool)GetValue(IsCloseButtonVisibleProperty); }
            set { SetValue(IsCloseButtonVisibleProperty, value); }
        }

        #endregion

        public Action CloseButtonClickedAction { get; set; }

        #endregion

        public DetailedData()
        {
            InitializeComponent();
        }

        private void UpdateListView()
        {
            DetailedDataListView.ClearValue(ListView.ViewProperty);

            if (ListViewHeaders.Count < 0)
                return;

            GridView newGridView = new GridView() { AllowsColumnReorder = false };

            // set the header style (header present or not)
            var _data = DetailedInformationData;
            if (!_data.HasColumnHeaders)
            {
                object _objStyle = this.FindResource("NoColumnHeaderStyle");
                if (_objStyle is Style _style)
                    if (!DetailedDataListView.Resources.Contains(typeof(GridViewColumnHeader)))
                        DetailedDataListView.Resources.Add(typeof(GridViewColumnHeader), _style);
            }
            else
            {
                if (DetailedDataListView.Resources.Contains(typeof(GridViewColumnHeader)))
                        DetailedDataListView.Resources.Remove(typeof(GridViewColumnHeader));
            }

            // create the header columns
            for (int i = 0; i < ListViewHeaders.Count; i++)
                {
                    BindingBase bindingBase = new Binding($"[{i}]");
                    object _header = null;
                    if (_data.HasColumnHeaders)
                        _header = ListViewHeaders[i];
                    var _gvColumn = new GridViewColumn() { Header = _header, DisplayMemberBinding = bindingBase };
                    newGridView.Columns.Add(_gvColumn);
                }

            DetailedDataListView.View = newGridView;
        }

        private void ListView_PreviewMouseWheel(object sender, MouseWheelEventArgs e)
        {
            if (sender is ListView && !e.Handled)
            {
                e.Handled = true;
                var eventArg = new MouseWheelEventArgs(e.MouseDevice, e.Timestamp, e.Delta)
                {
                    RoutedEvent = MouseWheelEvent,
                    Source = sender
                };
                var parent = ((Control)sender).Parent as UIElement;
                parent.RaiseEvent(eventArg);
            }
        }

        #region CloseButton_Click

        private void CloseButton_Click()
        {
            if (CloseButtonClickedAction != null)
                CloseButtonClickedAction.Invoke();
        }

        private void CloseButton_MouseUp(object sender, MouseButtonEventArgs e)
        {
            CloseButton_Click();
        }

        private void CloseButton_TouchDown(object sender, TouchEventArgs e)
        {
            CloseButton_Click();
        }

        #endregion

        #region CopyButton_Click

        private async Task CopyButton_ClickAsync()
        {
            var uiAction = new cUiCopyDetailsTableContent(DetailedInformationData);
            cUiActionBase.RaiseEvent(uiAction, this, this);

            await cUtility.ChangeIconToCheckAsync(CopyButton);

        }

        private async void CopyButton_MouseUp(object sender, MouseButtonEventArgs e)
        {
            await CopyButton_ClickAsync();
        }

        private async void CopyButton_TouchDown(object sender, TouchEventArgs e)
        {
            await CopyButton_ClickAsync();
        }

        #endregion

        #region DownloadButton_Click

        private void DownloadButton_Click()
        {
            var uiAction = new cUiSaveDetailsTableContent(DetailedInformationData);
            cUiActionBase.RaiseEvent(uiAction, this, this);
        }

        private void DownloadButton_MouseUp(object sender, MouseButtonEventArgs e)
        {
            DownloadButton_Click();
        }

        private void DownloadButton_TouchDown(object sender, TouchEventArgs e)
        {
            DownloadButton_Click();
        }

        #endregion
    }
}
