using Check.Main.Camera;
using Check.Main.Common;
using Check.Main.UI;
using HslCommunication;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using WeifenLuo.WinFormsUI.Docking;
namespace Check.Main
{
    public partial class FrmMain : Form
    {
        // private FrmCamConfig _formCameraConfig;
        public static ModbusTcpService PlcClient;//定义全局PLC对象 --- 10.10添加①
        private FrmConfig _frmConfig;
        private FrmLog _formLog;
        private ThemeBase _theme = new VS2015BlueTheme(); // 外观主题
        public DockPanel MainDockPanel => this.dockPanel1;
        private FormControlPanel _formControlPanel;
        private FormStatistics _formStatistics;
        private readonly string _layoutConfigFile = Path.Combine(Application.StartupPath, "layout.xml");
        //用于反序列化时创建窗体的委托
        private DeserializeDockContent _deserializeDockContent;
        public FrmMain()
        {
            InitializeComponent();
            dockPanel1.Theme = _theme;
            IsMdiContainer = true;
            _deserializeDockContent = new DeserializeDockContent(GetContentFromPersistString);
        }
        //添加 PLC 初始化方法 --- 10.10添加②
        private async Task InitPlcConnection()
        {
            try
            {
                PlcClient = new ModbusTcpService("192.168.1.88", 502); 
               // await PlcClient.ConnectAsync();
                ThreadSafeLogger.Log("[PLC] 已成功连接到汇川PLC");
            }
            catch (Exception ex)
            {
                ThreadSafeLogger.Log($"[PLC] 连接失败: {ex.Message}");
            }
        }
        private async void FrmMain_Load(object sender, EventArgs e)//添加了一个async,原来是private void FrmMain_Load-----10.10修改
        {
            // 初始化PLC连接-----10.10添加
            await InitPlcConnection();
            ModbusTcpService easyPlcClient = new ModbusTcpService("192.168.1.88", 502, 1);
            //easyPlcClient.ConnectAsync();
            _frmConfig = new FrmConfig { Text = "主程序配置" };
            _formLog = new FrmLog { Text = "运行日志" };
            _formStatistics = new FormStatistics { Text = "生产统计" };
            _formControlPanel = new FormControlPanel { Text = "控制面板" };
            // 为每个子窗体订阅 FormClosing 事件
            _frmConfig.FormClosing += DockContent_FormClosing;
            _formLog.FormClosing += DockContent_FormClosing;
            _formStatistics.FormClosing += DockContent_FormClosing;
            _formControlPanel.FormClosing += DockContent_FormClosing;
            ThreadSafeLogger.Initialize();
            ThreadSafeLogger.OnLogMessage += (msg) => { _formLog.AddLog(msg); };
            // 2. 尝试加载布局文件
            if (File.Exists(_layoutConfigFile))
            {
                try
                {
                    // 使用委托加载布局
                    dockPanel1.LoadFromXml(_layoutConfigFile, _deserializeDockContent);
                    ThreadSafeLogger.Log("成功加载用户布局。");
                }
                catch (Exception ex)
                {
                    ThreadSafeLogger.Log($"加载布局失败: {ex.Message}。将使用默认布局。");
                    // 如果加载失败,则使用默认布局
                    ShowDefaultLayout();
                }
            }
            else
            {
                // 3. 如果布局文件不存在,则显示默认布局
                ThreadSafeLogger.Log("未找到布局文件,使用默认布局。");
                ShowDefaultLayout();
            }
        }
        /// 
        /// 将相机名称添加到状态栏
        /// 
        public void AddCameraToStatusStrip(string name)
        {
            if (statusStrip1.InvokeRequired)
            {
                statusStrip1.Invoke(new Action(() => AddCameraToStatusStrip(name)));
                return;
            }
            var label = new ToolStripStatusLabel(name)
            {
                Name = "status_" + name,
                BorderSides = ToolStripStatusLabelBorderSides.All,
                Spring = false,
            };
            label.Click += StatusLabel_Click;
            statusStrip1.Items.Add(label);
        }
        private void 控制面板ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            if (_formControlPanel == null || _formControlPanel.IsDisposed)
            {
                _formControlPanel = new FormControlPanel { Text = "控制面板" };
                _formControlPanel.FormClosing += DockContent_FormClosing;
            }
            _formControlPanel.Show(this.dockPanel1);
        }
        /// 
        /// 清空状态栏中的相机名称
        /// 
        public void ClearStatusStrip()
        {
            if (statusStrip1.InvokeRequired)
            {
                statusStrip1.Invoke(new Action(ClearStatusStrip));
                return;
            }
            // 从后往前删,避免索引问题
            for (int i = statusStrip1.Items.Count - 1; i >= 0; i--)
            {
                if (statusStrip1.Items[i] is ToolStripStatusLabel && statusStrip1.Items[i].Name.StartsWith("status_"))
                {
                    statusStrip1.Items.RemoveAt(i);
                }
            }
        }
        private void StatusLabel_Click(object sender, EventArgs e)
        {
            if (sender is ToolStripStatusLabel label)
            {
                string cameraName = label.Text;
                ThreadSafeLogger.Log($"用户点击状态栏标签: {cameraName}");
                bool foundOriginal = false;
                bool foundResult = false;
                // 1. 尝试重新显示“原图”窗口
                if (CameraManager.OriginalImageDisplays.TryGetValue(cameraName, out var originalDisplayForm))
                {
                    // 使用 Show() 方法来重新激活或显示隐藏的窗口
                    // 传入 DockPanel 确保它知道在哪里显示
                    originalDisplayForm.Show(this.dockPanel1);
                    originalDisplayForm.Activate(); // 调用 Activate() 确保它成为当前焦点窗口
                    foundOriginal = true;
                }
                // 2. 尝试重新显示“结果”窗口
                if (CameraManager.ResultImageDisplays.TryGetValue(cameraName, out var resultDisplayForm))
                {
                    resultDisplayForm.Show(this.dockPanel1);
                    resultDisplayForm.Activate();
                    foundResult = true;
                }
                // 3. 提供反馈
                if (foundOriginal || foundResult)
                {
                    ThreadSafeLogger.Log($"已重新激活相机 '{cameraName}' 的显示窗口。");
                }
                else
                {
                    ThreadSafeLogger.Log($"[警告] 未能找到相机 '{cameraName}' 对应的活动显示窗口。可能设备已关闭。");
                }
            }
        }
        /// 
        /// 根据持久化字符串创建或返回对应的窗体实例。
        /// 这是DockPanel Suite反序列化布局时需要的回调方法。
        /// 
        /// 在XML中代表一个窗体的唯一字符串(通常是其类型名)。
        /// 对应的窗体实例。
        private IDockContent GetContentFromPersistString(string persistString)
        {
            if (persistString == typeof(FormControlPanel).ToString())
                return _formControlPanel;
            if (persistString == typeof(FrmConfig).ToString())
                return _frmConfig;
            if (persistString == typeof(FrmLog).ToString())
                return _formLog;
            if (persistString == typeof(FormStatistics).ToString())
                return _formStatistics;
            // 对于图像显示窗口,由于它们是动态创建的,情况会更复杂。
            // 在当前设计中,我们不保存图像窗口的布局,它们会在应用相机配置时重新创建。
            // 如果需要保存它们,需要在CameraManager中管理它们的持久化字符串。
            // 目前的设计下,返回null是安全的。
            return null;
        }
        /// 
        /// 显示程序的默认窗口布局。
        /// 
        private void ShowDefaultLayout()
        {
            // 确保所有窗体都未被意外关闭
            if (_formControlPanel.IsDisposed) _formControlPanel = new FormControlPanel();
            if (_frmConfig.IsDisposed) _frmConfig = new FrmConfig();
            if (_formLog.IsDisposed) _formLog = new FrmLog();
            if (_formStatistics.IsDisposed) _formStatistics = new FormStatistics();
            // 显示默认窗口
            _frmConfig.Show(dockPanel1, DockState.DockLeft);
            _formLog.Show(dockPanel1, DockState.DockBottom);
            _formControlPanel.Show(dockPanel1, DockState.DockRight);
            _formStatistics.Show(dockPanel1, DockState.DockTop);
        }
        /// 
        /// 【新增】保存当前窗口布局到XML文件。
        /// 
        private void SaveLayout()
        {
            try
            {
                // 将当前DockPanel的布局保存到指定文件
                dockPanel1.SaveAsXml(_layoutConfigFile);
                ThreadSafeLogger.Log("布局已成功保存!");
                //MessageBox.Show("布局已成功保存!", "提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
            }
            catch (Exception ex)
            {
                ThreadSafeLogger.Log("保存布局失败: " + ex.Message);
                //MessageBox.Show("保存布局失败: " + ex.Message, "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }
        private void FrmMain_FormClosing(object sender, FormClosingEventArgs e)
        {
            if (_formStatistics != null && !_formStatistics.IsDisposed)
            {
                StatisticsExporter.ExportToExcel(_formStatistics.CurrentStatistics, "Shutdown");
            }
            CameraManager.Shutdown();
            ThreadSafeLogger.Shutdown();
        }
        private void ToolStripMenuSaveLayou_Click(object sender, EventArgs e)
        {
            SaveLayout();
        }
        private void 配置ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //_frmConfig.Show();
            // 如果窗体因意外被销毁,则重新创建它
            if (_frmConfig == null || _frmConfig.IsDisposed)
            {
                _frmConfig = new FrmConfig() { Text = "主程序配置" };
                _frmConfig.FormClosing += DockContent_FormClosing;
            }
            // 调用 Show() 会自动处理隐藏和显示逻辑
            _frmConfig.Show(this.dockPanel1);
        }
        private void 日志ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            if (_formLog == null || _formLog.IsDisposed)
            {
                _formLog = new FrmLog { Text = "运行日志" };
                _formLog.FormClosing += DockContent_FormClosing;
            }
            _formLog.Show(this.dockPanel1);
        }
        /// 
        /// 处理所有可停靠子窗体关闭事件的通用方法。
        /// 通过取消关闭并隐藏窗口,来实现“假关闭”,以便后续能重新显示。
        /// 
        private void DockContent_FormClosing(object sender, FormClosingEventArgs e)
        {
            // 检查关闭原因是否为用户点击了关闭按钮
            if (e.CloseReason == CloseReason.UserClosing)
            {
                // 1. 取消真正的关闭(Dispose)操作,防止窗体被销毁
                e.Cancel = true;
                // 2. 将窗口隐藏起来
                // 我们需要将 sender 转换为 DockContent 类型来访问 Hide() 方法
                if (sender is DockContent dockContent)
                {
                    if (dockContent is FormImageDisplay imageDisplay)
                    {
                        ThreadSafeLogger.Log($"用户关闭了窗口 '{imageDisplay.Text}',已将其隐藏。");
                    }
                    dockContent.Hide();
                }
            }
        }
       
    }
}