using CloudBuilder.AI.Entity;
using CloudBuilder.AI.Linkup;
using CloudBuilder.AI.Policy;
using CloudBuilder.AI.SearchCriteria;
using CloudBuilder.Core.Report;
using CloudBuilder.Core.Service;
using CloudBuilder.Gui;
using CloudBuilder.Request.AI;
using CloudBuilder.Security.Linkup;
using CloudBuilder.Security.Policy;
using Krypton.Toolkit;
using Microsoft.AspNetCore.Authorization;
using System.Data;


namespace CloudBuilder.AI.Gui
{
    public partial class AiBookEnquiryPage : AbstractPage
    {
        private AiBookEntity[] aiBooks = null!;
        private AiBookSearchCriteria searchCriteria = null!;
        private BindingContextAttributeProvider provider;
        private AiBookRequest aiBookRequest;
        private SecurityMessagePolicy securityMessagePolicy;

        //初始化Page，注入容器内，不要在此做任何事情
        public AiBookEnquiryPage()
        {
            InitializeComponent();
        }

        /// <summary>
        /// 第一次加载时执行，只执行一次
        /// </summary>
        public override void FunctionLoaded()
        {
            try
            {
                base.FunctionLoaded();
                //初始化容器-------------------------------------
                aiBookRequest = ServiceHelper.GetTypeService<AiBookRequest>();
                securityMessagePolicy = ServiceHelper.GetTypeService<SecurityMessagePolicy>()!;

                //界面初始化
                InitGui();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        /// <summary>
        /// 每次从别的界面进入时执行，不包括下面的界面切换，发生在FunctionLoaded之后
        /// 这个是有参数传入，常用于查询界面进入到操作界面发生
        /// </summary>
        /// <param name="param"></param>
        public override void FunctionActivated(object param)
        {
            base.FunctionActivated(param);
            titleTxt.Focus();
        }
        /// <summary>
        /// 当Page被选中时执行,用于Tab导航的切换，没有参数变化，跟FunctionActivated有区别
        /// </summary>
        public override void FunctionSelected()
        {
            this.ParentAbstractForm.AcceptButton = this.searchBut;
            if (!IsDialog)
                this.ParentAbstractForm.CancelButton = this.resetBut;
            else
                this.ParentAbstractForm.CancelButton = this.cancelBut;

            titleTxt.Focus();
        }
        /// <summary>
        /// 控件的初始化
        /// </summary>
        private void InitGui()
        {
            //DataGridView初始化不要自动生成列，且允许重排列名操作
            dataGv.InitColumn(true, true);
            //初始化绑定设置
            InitBindingContext();
            //设置显示模式
            SetDisplayMode(true);

            InitGridViewPagination();
        }
        /// <summary>
        /// DataGridView分页控件初始化
        /// </summary>
        private void InitGridViewPagination()
        {
            searchCriteria = new AiBookSearchCriteria();
            gridViewPagination.SetLimit(searchCriteria.limit);
            gridViewPagination.OnPaginationChanged += Search;
            gridViewPagination.OnPrint += Print;
        }

        /// <summary>
        /// 打印当前查询结果
        /// </summary>
        private void Print()
        {
            TemplateHeader[] headers = dataGv.GetTemplateHeaders();

            //打印Excel
            new DataToExcelHelper<AiBookEntity>(null).PrintExcel(this.Parent.Text, this.Parent.Text, null, headers, aiBooks);
        }

        /// <summary>
        /// 有特殊要求的UI控件初始化设置，使用guiOperateHelper管理
        /// </summary>
        private void InitBindingContext()
        {
            InitPermission();

            guiOperateHelper = new GuiOperateHelper();
        }

        private void InitPermission()
        {
            viewBut.Set(AIPermissionPolicy.AiBook, Operate.Find);
            createBut.Set(AIPermissionPolicy.AiBook, Operate.Insert);
            amendBut.Set(AIPermissionPolicy.AiBook, Operate.Update);
            deleteBut.Set(AIPermissionPolicy.AiBook, Operate.Delete);
        }

        private void SetDisplayMode(bool enable)
        {
            guiOperateHelper.EnableControls(true, this.searchPanel, this.bottomPanel);
            guiOperateHelper.EnableControls(false, dataGv);

            if (aiBooks != null)
                guiOperateHelper.EnableControls(enable, viewBut, amendBut, deleteBut);
            else
                guiOperateHelper.EnableControls(false, viewBut, amendBut, deleteBut);

            //如果是弹出的窗口，不显示
            createBut.Visible = !IsDialog;
            dialogPanel.Visible = IsDialog;
            operationPanel.Visible = !IsDialog;

            this.titleTxt.Focus();
        }

        private void searchBut_Click(object sender, EventArgs e)
        {
            try
            {
                Search();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        /// <summary>
        /// 与Web同步写法
        /// </summary>
        /// <returns></returns>
        private AiBookSearchCriteria PackSearchCriteria()
        {
            searchCriteria = new AiBookSearchCriteria();
            searchCriteria.limit = gridViewPagination.Limit;
            searchCriteria.page = gridViewPagination.CurrentPage;

            List<SearchFilter> filters = new List<SearchFilter>();

            SearchFilter filter = new SearchFilter();
            filter.Column = AiBookEntity.DB_TITLE;
            filter.Type = SearchFilterTypePolicy.TEXT;
            filter.Operator = SearchFilterOperatorPolicy.CN_CONTAIN;
            filter.Value = titleTxt.GetValue();
            filters.Add(filter);

            filter.Column = AiBookEntity.DB_AUTHOR;
            filter.Type = SearchFilterTypePolicy.TEXT;
            filter.Operator = SearchFilterOperatorPolicy.CN_CONTAIN;
            filter.Value = titleTxt.GetValue();
            filters.Add(filter);

            searchCriteria.Filter = filters.ToArray();

            return searchCriteria;
        }

        private void Search()
        {
            try
            {
                var data = aiBookRequest.FindBySearchCriteria(PackSearchCriteria());

                if (data != null) aiBooks = data.Datas;

                gridViewPagination.SetTotal(data.Total);

                if (aiBooks == null || aiBooks.Length == 0)
                {
                    ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                    guiOperateHelper.ResetControls(this.dataGv);
                    return;
                }

                dataGv.SetDataSource(aiBooks);

                SetDisplayMode(true);
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void resetBut_Click(object sender, EventArgs e)
        {
            guiOperateHelper.ResetControls(this.mainPanel);

            SetDisplayMode(false);

        }

        private void createBut_Click(object sender, EventArgs e)
        {
            DisplayPage(GuiDisplayMode.Create, null);
        }

        private void DisplayPage(GuiDisplayMode mode, string guid)
        {
            AiBookOperationLinkup linkupData = new AiBookOperationLinkup();
            linkupData.DisplayMode = Convert.ToInt32(mode);
            linkupData.Guid = guid;

            this.DisplayAbstractPage(typeof(AiBookOperationPage).Name, linkupData);
        }

        private void viewBut_Click(object sender, EventArgs e)
        {
            if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0)
            {
                ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                return;
            }

            AiBookEntity data = dataGv.GetRowData<AiBookEntity>(dataGv.SelectedCells[0].RowIndex);

            DisplayPage(GuiDisplayMode.View, data.Guid);
        }

        private void amendBut_Click(object sender, EventArgs e)
        {
            if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0)
            {
                ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                return;
            }

            AiBookEntity data = dataGv.GetRowData<AiBookEntity>(dataGv.SelectedCells[0].RowIndex);

            DisplayPage(GuiDisplayMode.Amend, data.Guid);
        }

        private void deleteBut_Click(object sender, EventArgs e)
        {
            try
            {
                Delete();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void Delete()
        {
            if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0)
            {
                ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_WS_RECORD_NOT_FOUND));
                return;
            }

            if (DialogResult.Yes != ShowMessageBox.ShowOption(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_CONFIRM_DEL_NULL), securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_DELETE))) return;

            AiBookEntity[] datas = dataGv.GetSelectedCellsData<AiBookEntity>();

            aiBookRequest.Deletes(datas.Select(x => x.Guid).ToArray());

            ShowMessageBox.ShowInfo(securityMessagePolicy.ComposeMessage(SecurityMessagePolicy.GUI_SUCCEED_DELETED_NULL));

            Search();
        }

        private void okBut_Click(object sender, EventArgs e)
        {
            try
            {
                if (dataGv.RowCount <= 0 || dataGv.SelectedCells.Count <= 0) return;
                AiBookEntity[] datas = dataGv.GetSelectedCellsData<AiBookEntity>();

                this.ParentAbstractForm.OutputData = datas;
                this.ParentAbstractForm.DialogResult = DialogResult.OK;
                this.ParentAbstractForm.Close();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void cancelBut_Click(object sender, EventArgs e)
        {
            try
            {
                this.ParentAbstractForm.DialogResult = DialogResult.Cancel;
                this.ParentAbstractForm.Close();
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }

        private void dataGv_CellDoubleClick(object sender, DataGridViewCellEventArgs e)
        {
            try
            {
                if (IsDialog)
                    okBut_Click(null, null);
                else
                    viewBut_Click(null, null);
            }
            catch (ValidatedException ex)
            {
                ShowMessageBox.ShowInfo(ex.Message);
            }
            catch (ServiceErrorException ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                ShowMessageBox.ShowError(ex.Message);
            }
        }
    }
}
