using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using UnityEditor;
using UnityEngine;

namespace Gyvr.Mythril2D
{
    public class GameFlagDebugWindow : EditorWindow
    {
        private Vector2 m_scrollPosition;
        private string m_searchFilter = "";
        private string m_newFlagName = "";
        private List<string> m_allFlags = new List<string>();
        private bool m_autoRefresh = true;
        private double m_lastRefreshTime;

        [MenuItem("Mythril2D/Debug/Game Flags Viewer")]
        public static void ShowWindow()
        {
            GameFlagDebugWindow window = GetWindow<GameFlagDebugWindow>("Game Flags");
            window.minSize = new Vector2(400, 300);
            window.Show();
        }

        private void OnEnable()
        {
            RefreshFlags();
        }

        private void OnInspectorUpdate()
        {
            if (m_autoRefresh && EditorApplication.isPlaying)
            {
                if (EditorApplication.timeSinceStartup - m_lastRefreshTime > 0.5)
                {
                    RefreshFlags();
                    m_lastRefreshTime = EditorApplication.timeSinceStartup;
                    Repaint();
                }
            }
        }

        private void RefreshFlags()
        {
            if (!EditorApplication.isPlaying || GameManager.Instance == null)
            {
                m_allFlags.Clear();
                return;
            }
            var gameFlagSystem = GameManager.GameFlagSystem;
            if (gameFlagSystem != null)
            {
                var fieldInfo = gameFlagSystem.GetType().GetField("m_flags", BindingFlags.NonPublic | BindingFlags.Instance);
                if (fieldInfo != null)
                {
                    var flags = fieldInfo.GetValue(gameFlagSystem) as HashSet<string>;
                    if (flags != null)
                    {
                        m_allFlags = flags.OrderBy(f => f).ToList();
                    }
                }
            }
        }

        private void OnGUI()
        {
            EditorGUILayout.BeginVertical();

            EditorGUILayout.Space(10);
            EditorGUILayout.LabelField("Game Flags Debug Viewer", EditorStyles.boldLabel);
            EditorGUILayout.Space(5);

            if (!EditorApplication.isPlaying)
            {
                EditorGUILayout.HelpBox("Enter Play Mode to view and modify game flags.", MessageType.Info);
                EditorGUILayout.EndVertical();
                return;
            }

            EditorGUILayout.BeginHorizontal();
            m_autoRefresh = EditorGUILayout.Toggle("Auto Refresh", m_autoRefresh, GUILayout.Width(150));
            GUILayout.FlexibleSpace();
            if (GUILayout.Button("Manual Refresh", GUILayout.Width(120)))
            {
                RefreshFlags();
            }
            EditorGUILayout.EndHorizontal();

            EditorGUILayout.Space(5);

            EditorGUILayout.BeginHorizontal();
            EditorGUILayout.LabelField($"Total Flags: {m_allFlags.Count}", EditorStyles.miniLabel);
            GUILayout.FlexibleSpace();
            EditorGUILayout.EndHorizontal();

            EditorGUILayout.Space(5);

            EditorGUILayout.BeginHorizontal();
            EditorGUILayout.LabelField("Search:", GUILayout.Width(50));
            m_searchFilter = EditorGUILayout.TextField(m_searchFilter);
            if (GUILayout.Button("Clear", GUILayout.Width(50)))
            {
                m_searchFilter = "";
                GUI.FocusControl(null);
            }
            EditorGUILayout.EndHorizontal();

            EditorGUILayout.Space(5);

            EditorGUILayout.BeginVertical("box");
            EditorGUILayout.LabelField("Add New Flag", EditorStyles.boldLabel);
            EditorGUILayout.BeginHorizontal();
            m_newFlagName = EditorGUILayout.TextField(m_newFlagName);
            GUI.enabled = !string.IsNullOrWhiteSpace(m_newFlagName);
            if (GUILayout.Button("Add", GUILayout.Width(60)))
            {
                GameManager.GameFlagSystem.Set(m_newFlagName.Trim(), true);
                m_newFlagName = "";
                RefreshFlags();
                GUI.FocusControl(null);
            }
            GUI.enabled = true;
            EditorGUILayout.EndHorizontal();
            EditorGUILayout.EndVertical();

            EditorGUILayout.Space(5);

            var filteredFlags = string.IsNullOrWhiteSpace(m_searchFilter)
                ? m_allFlags
                : m_allFlags.Where(f => f.ToLower().Contains(m_searchFilter.ToLower())).ToList();

            EditorGUILayout.LabelField($"Active Flags ({filteredFlags.Count}):", EditorStyles.boldLabel);

            if (filteredFlags.Count == 0)
            {
                EditorGUILayout.HelpBox(
                    string.IsNullOrWhiteSpace(m_searchFilter) 
                        ? "No flags are currently set." 
                        : "No flags match your search.", 
                    MessageType.Info);
            }
            else
            {
                m_scrollPosition = EditorGUILayout.BeginScrollView(m_scrollPosition);

                foreach (var flag in filteredFlags)
                {
                    EditorGUILayout.BeginHorizontal("box");
                    
                    EditorGUILayout.LabelField(new GUIContent(" " + flag, EditorGUIUtility.IconContent("d_animationvisibilitytoggleon").image), GUILayout.ExpandWidth(true));
                    
                    if (GUILayout.Button(new GUIContent("Copy", "Copy flag name to clipboard"), GUILayout.Width(50)))
                    {
                        EditorGUIUtility.systemCopyBuffer = flag;
                        Debug.Log($"Copied flag to clipboard: {flag}");
                    }

                    GUI.backgroundColor = new Color(1f, 0.6f, 0.6f);
                    if (GUILayout.Button(new GUIContent("Remove", "Remove this flag"), GUILayout.Width(70)))
                    {
                        if (EditorUtility.DisplayDialog("Remove Flag", 
                            $"Are you sure you want to remove the flag:\n\n{flag}", 
                            "Remove", "Cancel"))
                        {
                            GameManager.GameFlagSystem.Set(flag, false);
                            RefreshFlags();
                        }
                    }
                    GUI.backgroundColor = Color.white;

                    EditorGUILayout.EndHorizontal();
                }

                EditorGUILayout.EndScrollView();
            }

            EditorGUILayout.Space(5);

            EditorGUILayout.BeginHorizontal();
            GUILayout.FlexibleSpace();
            GUI.backgroundColor = new Color(1f, 0.5f, 0.5f);
            GUI.enabled = m_allFlags.Count > 0;
            if (GUILayout.Button("Clear All Flags", GUILayout.Width(150), GUILayout.Height(25)))
            {
                if (EditorUtility.DisplayDialog("Clear All Flags", 
                    $"Are you sure you want to remove ALL {m_allFlags.Count} flags?\n\nThis cannot be undone!", 
                    "Clear All", "Cancel"))
                {
                    foreach (var flag in m_allFlags.ToList())
                    {
                        GameManager.GameFlagSystem.Set(flag, false);
                    }
                    RefreshFlags();
                }
            }
            GUI.enabled = true;
            GUI.backgroundColor = Color.white;
            EditorGUILayout.EndHorizontal();

            EditorGUILayout.Space(10);
            EditorGUILayout.EndVertical();
        }
    }
}
