using UnityEngine;
using UnityEditor;
using System.IO;

/// <summary>
/// Editor utility for creating enemy characters from EnemyCharacterData
/// Adds menu items under "RPG/Characters" for enemy creation workflow
/// </summary>
public class EnemyCharacterCreator : EditorWindow
{
    private EnemyCharacterData selectedEnemyData;
    private string outputPath = "Assets/Scripts/Characters/Enemies/Generated/";
    private Vector2 scrollPosition;

    [MenuItem("RPG/Characters/Enemy Creator Window")]
    public static void ShowWindow()
    {
        GetWindow<EnemyCharacterCreator>("Enemy Character Creator");
    }

    [MenuItem("Assets/RPG/Generate Enemy Character Script", true)]
    public static bool ValidateGenerateEnemyScript()
    {
        return Selection.activeObject is EnemyCharacterData;
    }

    [MenuItem("Assets/RPG/Generate Enemy Character Script")]
    public static void GenerateEnemyScriptFromSelected()
    {
        if (Selection.activeObject is EnemyCharacterData enemyData)
        {
            GenerateEnemyCharacterScript(enemyData);
        }
    }

    void OnGUI()
    {
        GUILayout.Label("Enemy Character Creator", EditorStyles.boldLabel);
        EditorGUILayout.Space();

        // Enemy data selection
        EditorGUILayout.LabelField("Select Enemy Data:", EditorStyles.boldLabel);
        selectedEnemyData = (EnemyCharacterData)EditorGUILayout.ObjectField(
            "Enemy Data", selectedEnemyData, typeof(EnemyCharacterData), false);

        EditorGUILayout.Space();

        // Output path
        EditorGUILayout.LabelField("Output Settings:", EditorStyles.boldLabel);
        outputPath = EditorGUILayout.TextField("Output Path:", outputPath);

        if (GUILayout.Button("Browse Output Folder"))
        {
            string selectedPath = EditorUtility.OpenFolderPanel("Select Output Folder", Application.dataPath, "");
            if (!string.IsNullOrEmpty(selectedPath))
            {
                outputPath = "Assets" + selectedPath.Substring(Application.dataPath.Length) + "/";
            }
        }

        EditorGUILayout.Space();

        // Preview
        if (selectedEnemyData != null)
        {
            EditorGUILayout.LabelField("Preview:", EditorStyles.boldLabel);

            using (var scrollScope = new EditorGUILayout.ScrollViewScope(scrollPosition, GUILayout.Height(200)))
            {
                scrollPosition = scrollScope.scrollPosition;

                EditorGUILayout.LabelField("Generated Class Name:",
                    selectedEnemyData.enemyName.Replace(" ", "") + "Character");
                EditorGUILayout.LabelField("Health:", selectedEnemyData.maxHealth.ToString());
                EditorGUILayout.LabelField("Attack:", selectedEnemyData.attack.ToString());
                EditorGUILayout.LabelField("Armor Class:", selectedEnemyData.armorClass.ToString());
                EditorGUILayout.LabelField("Weapon Type:", selectedEnemyData.preferredWeapon.weaponType.ToString());
                EditorGUILayout.LabelField("Threat Level:", selectedEnemyData.threatLevel.ToString());

                EditorGUILayout.Space();
                EditorGUILayout.LabelField("Special Abilities:");
                if (selectedEnemyData.canCastSpells) EditorGUILayout.LabelField("• Can Cast Spells");
                if (selectedEnemyData.hasRangedAttack) EditorGUILayout.LabelField("• Has Ranged Attack");
                if (selectedEnemyData.canFly) EditorGUILayout.LabelField("• Can Fly");
                if (selectedEnemyData.regeneratesHealth) EditorGUILayout.LabelField($"• Regenerates {selectedEnemyData.healthRegenPerTurn} HP per turn");
            }

            EditorGUILayout.Space();

            // Generate button
            GUI.enabled = selectedEnemyData != null;
            if (GUILayout.Button("Generate Enemy Character Script", GUILayout.Height(30)))
            {
                GenerateEnemyCharacterScript(selectedEnemyData);
            }
            GUI.enabled = true;
        }
        else
        {
            EditorGUILayout.HelpBox("Select an EnemyCharacterData asset to generate a character script.", MessageType.Info);
        }

        EditorGUILayout.Space();

        // Quick actions
        EditorGUILayout.LabelField("Quick Actions:", EditorStyles.boldLabel);

        if (GUILayout.Button("Create New Enemy Data Asset"))
        {
            CreateNewEnemyData();
        }

        if (GUILayout.Button("Open Generated Scripts Folder"))
        {
            EditorUtility.RevealInFinder(Path.Combine(Application.dataPath, "Scripts/Characters/Enemies/Generated"));
        }
    }

    public static void GenerateEnemyCharacterScript(EnemyCharacterData enemyData)
    {
        if (enemyData == null)
        {
            Debug.LogError("Enemy data is null!");
            return;
        }

        // Ensure output directory exists
        string fullOutputPath = Path.Combine(Application.dataPath, "Scripts/Characters/Enemies/Generated");
        if (!Directory.Exists(fullOutputPath))
        {
            Directory.CreateDirectory(fullOutputPath);
        }

        // Generate script content
        string scriptContent = enemyData.GenerateCharacterScript();
        string className = enemyData.enemyName.Replace(" ", "") + "Character";
        string fileName = className + ".cs";
        string fullPath = Path.Combine(fullOutputPath, fileName);

        // Write the file
        try
        {
            File.WriteAllText(fullPath, scriptContent);

            // Refresh asset database to show the new file
            AssetDatabase.Refresh();

            Debug.Log($"✅ Generated enemy character script: {fileName}");
            Debug.Log($"📁 Location: {fullPath}");

            // Select the generated file in the project window
            string assetPath = "Assets/Scripts/Characters/Enemies/Generated/" + fileName;
            Object asset = AssetDatabase.LoadAssetAtPath<Object>(assetPath);
            if (asset != null)
            {
                Selection.activeObject = asset;
                EditorGUIUtility.PingObject(asset);
            }

            EditorUtility.DisplayDialog("Success",
                $"Generated enemy character script: {className}\n\nThe script has been created at:\n{assetPath}",
                "OK");
        }
        catch (System.Exception e)
        {
            Debug.LogError($"Failed to generate enemy character script: {e.Message}");
            EditorUtility.DisplayDialog("Error",
                $"Failed to generate enemy character script:\n{e.Message}",
                "OK");
        }
    }

    private void CreateNewEnemyData()
    {
        string path = EditorUtility.SaveFilePanelInProject(
            "Create New Enemy Data",
            "NewEnemy",
            "asset",
            "Choose where to save the new enemy data asset");

        if (!string.IsNullOrEmpty(path))
        {
            EnemyCharacterData newEnemy = CreateInstance<EnemyCharacterData>();
            AssetDatabase.CreateAsset(newEnemy, path);
            AssetDatabase.SaveAssets();
            AssetDatabase.Refresh();

            Selection.activeObject = newEnemy;
            selectedEnemyData = newEnemy;

            Debug.Log($"✅ Created new enemy data asset: {path}");
        }
    }
}

/// <summary>
/// Additional menu items for RPG character creation
/// </summary>
public class RPGCharacterMenuItems
{
    [MenuItem("RPG/Characters/Create Enemy Data Asset")]
    public static void CreateEnemyDataAsset()
    {
        string path = EditorUtility.SaveFilePanelInProject(
            "Create Enemy Data Asset",
            "NewEnemy",
            "asset",
            "Choose location for the enemy data asset",
            "Assets/Scripts/Characters/Enemies");

        if (!string.IsNullOrEmpty(path))
        {
            EnemyCharacterData enemyData = ScriptableObject.CreateInstance<EnemyCharacterData>();
            AssetDatabase.CreateAsset(enemyData, path);
            AssetDatabase.SaveAssets();
            AssetDatabase.Refresh();

            Selection.activeObject = enemyData;
            EditorGUIUtility.PingObject(enemyData);

            Debug.Log($"✅ Created enemy data asset: {path}");
        }
    }

    [MenuItem("RPG/Characters/Batch Generate All Enemy Scripts")]
    public static void BatchGenerateEnemyScripts()
    {
        string[] guids = AssetDatabase.FindAssets("t:EnemyCharacterData");
        int count = 0;

        foreach (string guid in guids)
        {
            string path = AssetDatabase.GUIDToAssetPath(guid);
            EnemyCharacterData enemyData = AssetDatabase.LoadAssetAtPath<EnemyCharacterData>(path);

            if (enemyData != null)
            {
                EnemyCharacterCreator.GenerateEnemyCharacterScript(enemyData);
                count++;
            }
        }

        EditorUtility.DisplayDialog("Batch Generation Complete",
            $"Generated {count} enemy character scripts.", "OK");
    }

    [MenuItem("RPG/Characters/Open Enemy Scripts Folder")]
    public static void OpenEnemyScriptsFolder()
    {
        string folderPath = Path.Combine(Application.dataPath, "Scripts/Characters/Enemies");
        if (Directory.Exists(folderPath))
        {
            EditorUtility.RevealInFinder(folderPath);
        }
        else
        {
            Debug.LogWarning("Enemy scripts folder does not exist: " + folderPath);
        }
    }
}
