using Microsoft.WindowsAPICodePack.Dialogs;
using Panuon.WPF.UI;
using SWRIS.Dtos;
using SWRIS.Extensions;
using SWRIS.Models.ViewModel;
using SWRIS.Repository;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.IO;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;

namespace SWRIS.Pages
{
    /// <summary>
    /// RecordPage.xaml 的交互逻辑
    /// </summary>
    public partial class RecordPage : Page
    {
        private readonly IRecordRepository _recordRepository;
        public RecordViewModel ViewModel { get; set; } = new RecordViewModel();
        public RecordPage()
        {
            _recordRepository = new RecordRepository();
            InitializeComponent();
            BindTable();
            DataContext = this;
        }
        void BindTable()
        {
            var records = _recordRepository.GetRecords(ViewModel.SearchInput.RopeNumber,
                                                       ViewModel.SearchInput.StartTime,
                                                       ViewModel.SearchInput.EndTime,
                                                       ViewModel.SearchInput.RiskLevel,
                                                       ViewModel.SearchInput.Limit,
                                                       ViewModel.SearchInput.Offset,
                                                       true);
            ViewModel.IsAllSelected = false;
            ViewModel.Records = new ObservableCollection<RecordDto>(records);
        }
        private void Search_Click(object sender, RoutedEventArgs e)
        {
            BindTable();
        }
        private void Report_Click(object sender, RoutedEventArgs e)
        {
            if (sender is Button button && button.Tag is RecordDto record)
            {
                int reportedCount = Report(new List<RecordDto> { record });
                if (reportedCount > 0)
                {
                    NoticeBox.Show("报告生成成功", "通知", MessageBoxIcon.Success, true, 2000);
                }
                else if (reportedCount == 0)
                {
                    NoticeBox.Show("报告生成失败", "通知", MessageBoxIcon.Error, true, 5000);
                }
            }
        }
        private int Report(List<RecordDto> records)
        {
            string reportPath = SelectExportFolder();
            if (string.IsNullOrEmpty(reportPath))
            {
                return -1;
            }
            return ExportMultipleReports(records, reportPath);
        }
        private int Export(List<RecordDto> records)
        {
            string reportPath = SelectExportFolder(initialDirectory: "钢丝绳检测数据");
            if (string.IsNullOrEmpty(reportPath))
            {
                return -1;
            }
            return ExportMultipleRecords(records, reportPath);
        }
        private void Export_Click(object sender, RoutedEventArgs e)
        {
            if (sender is Button button && button.Tag is RecordDto record)
            {
                int exportedCount = Export(new List<RecordDto> { record });
                if (exportedCount > 0)
                {
                    NoticeBox.Show("记录导出成功", "通知", MessageBoxIcon.Success, true, 2000);
                }
                else if (exportedCount == 0)
                {
                    NoticeBox.Show("记录导出失败", "通知", MessageBoxIcon.Error, true, 5000);
                }
            }
        }

        private void RecordDataGrid_MouseDoubleClick(object sender, MouseButtonEventArgs e)
        {
            if (e.ChangedButton == MouseButton.Left && sender is DataGrid dataGrid && dataGrid.SelectedItem != null)
            {
                var selectedItem = dataGrid.SelectedItem as RecordDto; // 获取当前选中行的数据
                (Application.Current.MainWindow as MainWindow).NavigatePage(new Uri($"Pages/DamagesPage.xaml?id=" + selectedItem.Id, uriKind: UriKind.Relative));
            }
        }
        private void Delete_Click(object sender, RoutedEventArgs e)
        {
            if (sender is Button button)
            {
                int id = (int)button.Tag;
                var result = MessageBoxX.Show(Application.Current.MainWindow,
                                              "此操作不可恢复，是否确认删除记录？",
                                              "警告",
                                              MessageBoxButton.YesNo,
                                              MessageBoxIcon.Warning,
                                              DefaultButton.YesOK);
                if (result == MessageBoxResult.Yes)
                {
                    var effect = _recordRepository.DeleteRecord(id);
                    if (effect)
                    {
                        var deletedRecord = ViewModel.Records.FirstOrDefault(x => x.Id == id);
                        if (deletedRecord != null)
                        {
                            ViewModel.Records.Remove(deletedRecord);
                            DatFileHandler.DeleteDatFile(deletedRecord.DataFilePath);
                        }
                        NoticeBox.Show("记录删除成功", "通知", MessageBoxIcon.Success, true, 5000);
                    }
                    else
                    {
                        NoticeBox.Show("记录删除失败", "通知", MessageBoxIcon.Error, true, 5000);
                    }
                }
            }
        }
        private int Delete(int[] recordIds)
        {
            var result = MessageBoxX.Show(Application.Current.MainWindow,
                                              "此操作不可恢复，是否确认删除记录？",
                                              "警告",
                                              MessageBoxButton.YesNo,
                                              MessageBoxIcon.Warning,
                                              DefaultButton.YesOK);

            if (result == MessageBoxResult.Yes)
            {
                return _recordRepository.DeleteRecords(recordIds);
            }
            return 0;
        }
        private void Batch_Report(object sender, RoutedEventArgs e)
        {
            var records = ViewModel.Records.Where(c => c.IsSelected).ToList();
            if (records.Any())
            {
                int reportCount = Report(records);
                if (reportCount > 0)
                {
                    Application.Current.Dispatcher.Invoke(() =>
                    {
                        NoticeBox.Show($"检测报告文件{(reportCount > 1 ? $"({reportCount})条" : "")}已生成成功", "通知", MessageBoxIcon.Success, true, 5000);
                    });
                }
            }
            else
            {
                MessageBoxX.Show(Application.Current.MainWindow, "请选择要生成报告的检测记录", "通知", MessageBoxButton.OK,
                                 MessageBoxIcon.Info, DefaultButton.YesOK);
            }
        }

        private void Batch_Delete(object sender, RoutedEventArgs e)
        {
            var records = ViewModel.Records.Where(c => c.IsSelected).ToList();
            if (records.Any())
            {
                int[] recordIds = records.Select(x => (int)x.Id).ToArray();
                int deletedCount = Delete(recordIds);
                if (deletedCount > 0)
                {
                    foreach (var record in records)
                    {
                        ViewModel.Records.Remove(record);
                        DatFileHandler.DeleteDatFile(record.DataFilePath);
                    }
                    Application.Current.Dispatcher.Invoke(() =>
                    {
                        NoticeBox.Show($"检测记录{(recordIds.Length > 1 ? $"({recordIds.Length}条)" : "")}已成功删除", "通知", MessageBoxIcon.Success, true, 5000);
                    });
                }
            }
            else
            {
                MessageBoxX.Show(Application.Current.MainWindow, "请选择要删除的检测记录", "提醒", MessageBoxButton.OK,
                                 MessageBoxIcon.Info, DefaultButton.YesOK);
            }
        }

        private void Batch_Export(object sender, RoutedEventArgs e)
        {
            var records = ViewModel.Records.Where(c => c.IsSelected).ToList();
            if (records.Any())
            {
                int exportCount = Export(records);
                if (exportCount > 0)
                {
                    Application.Current.Dispatcher.Invoke(() =>
                    {
                        NoticeBox.Show($"检测数据文件{(exportCount > 1 ? $"({exportCount})条" : "")}已成功导出", "通知", MessageBoxIcon.Success, true, 5000);
                    });
                }
            }
            else
            {
                MessageBoxX.Show(Application.Current.MainWindow, "请选择要导出的检测记录", "通知", MessageBoxButton.OK,
                                 MessageBoxIcon.Info, DefaultButton.YesOK);
            }
        }

        private string SelectExportFolder(string title = "选择文件夹", string initialDirectory = "钢丝绳检测报告")
        {
            using (var dialog = new CommonOpenFileDialog())
            {
                dialog.Title = title;
                dialog.IsFolderPicker = true;
                dialog.EnsurePathExists = true;
                dialog.InitialDirectory = GetDefaultExportDirectory(initialDirectory);

                if (dialog.ShowDialog() == CommonFileDialogResult.Ok)
                {
                    return dialog.FileName;
                }
            }
            return null;
        }

        private int ExportMultipleReports(List<RecordDto> records, string folderPath)
        {
            int savedCount = 0;
            string craneName = App.Config.Crane;
            // 按钢丝绳编号分组处理
            var groupedRecords = records.OrderBy(r => r.RopeNumber).GroupBy(r => r.RopeNumber);
            foreach (var group in groupedRecords)
            {
                var equipment = App.Config.Equipments
                    .FirstOrDefault(c => c.RopeNumber == group.Key);

                foreach (var record in group)
                {
                    string fileName = GenerateReportFileName(record);
                    string filePath = Path.Combine(folderPath, fileName);
                    var export = new ReportPdfExporter(craneName, record, equipment);
                    if (export.SavePdf(filePath))
                    {
                        savedCount++;
                        _recordRepository.AddRecordExportCount(record.Id.Value);
                    }
                }
            }
            return savedCount;
        }
        private int ExportMultipleRecords(List<RecordDto> records, string folderPath)
        {
            int exportedCount = 0;
            string craneName = App.Config.Crane;
            foreach (var record in records)
            {
                if (record != null && record.DataFilePath != null)
                {
                    var damageData = DatFileHandler.ReadDatFile(record.DataFilePath);
                    if ((damageData?.Length ?? 0) > 0)
                    {
                        string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(record.DataFilePath);
                        string directroyName = Path.Combine(folderPath, fileNameWithoutExtension);
                        Directory.CreateDirectory(directroyName);
                        string datFileName = Path.Combine(directroyName, "data.dat");
                        File.WriteAllBytes(datFileName, damageData);
                        string txtFileName = Path.Combine(directroyName, "info.txt");
                        File.WriteAllText(txtFileName, $"钢丝绳：{record.RopeName}\r\n" +
                            $"起始位置：{record.StartPoint}\r\n" +
                            $"结束位置：{record.EndPoint}\r\n" +
                            $"检测长度：{record.DetectionLength}\r\n" +
                            $"损伤数量：{record.DamageCount}处\r\n" +
                            $"-------------------------------------------\r\n" +
                            $"{string.Join("", record.Damages.Select(c => $"位置：{c.DamagePoint},损伤值：{c.DamageValue}\r\n"))}", Encoding.UTF8);

                        exportedCount++;
                    }
                }
            }
            return exportedCount;
        }
        private string GetDefaultExportDirectory(string folderName = "钢丝绳检测报告")
        {
            string docsPath = Path.Combine(
                Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments),
                folderName,
                DateTime.Now.ToString("yyyy-MM"));

            // 确保目录存在
            try
            {
                Directory.CreateDirectory(docsPath);
                return docsPath;
            }
            catch
            {
                // 失败时返回桌面
                return Environment.GetFolderPath(Environment.SpecialFolder.Desktop);
            }
        }

        private string GenerateReportFileName(RecordDto record)
        {
            // 清理文件名中的非法字符
            string ropeName = CleanFileName(record.RopeName);
            string time = record.EndTime.ToString("yyyyMMdd_HHmmss");

            return $"{ropeName}_{time}_检测报告.pdf";
        }

        private string CleanFileName(string fileName)
        {
            if (string.IsNullOrEmpty(fileName))
                return "未知";

            // 移除非法字符
            char[] invalidChars = Path.GetInvalidFileNameChars();
            foreach (char c in invalidChars)
            {
                fileName = fileName.Replace(c, '_');
            }

            // 限制长度
            if (fileName.Length > 50)
            {
                fileName = fileName.Substring(0, 50);
            }

            return fileName.Trim();
        }
    }
}
