using UnityEngine;
using UnityEngine.UI;
using TMPro;
using UnityEngine.Video;

#if UNITY_EDITOR
using UnityEditor;
#endif

public class TrousSceneGenerator : ScriptableObject
{
    [Header("Configuration")]
    [SerializeField] private bool clearExisting = true;
    
    [Header("Canvas Settings")]
    [SerializeField] private Vector2 referenceResolution = new Vector2(1920, 1080);
    [SerializeField] private float matchWidthOrHeight = 0.5f;
    
    [Header("Background Settings")]
    [SerializeField] private bool createVideoBackground = true;
    [SerializeField] private bool createImageBackground = true;
    
    [Header("Text Panel Settings")]
    [SerializeField] private Vector2 textPanelPosition = new Vector2(100, -200);
    [SerializeField] private Vector2 textPanelSize = new Vector2(1720, 680);
    [SerializeField] private Color textPanelColor = new Color(0.96f, 0.93f, 0.9f, 0.8f);
    
    [Header("Font Settings")]
    [SerializeField] private TMP_FontAsset customFont;
    [SerializeField] private int defaultFontSize = 36;
    [SerializeField] private Color defaultTextColor = new Color(0.39f, 0.28f, 0.49f, 1f);
    
    [ContextMenu("Generate Trous Scene")]
    public void GenerateTrousScene()
    {
        Debug.Log("[TrousSceneGenerator] Génération de la scène Trous...");
        
        try
        {
            if (clearExisting)
            {
                Debug.Log("[TrousSceneGenerator] Nettoyage des objets existants...");
                ClearExistingObjects();
            }
            
            // 1. Créer le Canvas principal
            Debug.Log("[TrousSceneGenerator] Création du Canvas...");
            GameObject canvas = CreateMainCanvas();
            if (canvas == null)
            {
                Debug.LogError("[TrousSceneGenerator] Échec de création du Canvas");
                return;
            }
            
            // 2. Créer les composants de fond
            GameObject backgroundVideo = null;
            GameObject backgroundImage = null;
            
            if (createVideoBackground)
            {
                Debug.Log("[TrousSceneGenerator] Création du BackgroundVideo...");
                backgroundVideo = CreateBackgroundVideo(canvas);
            }
            
            if (createImageBackground)
            {
                Debug.Log("[TrousSceneGenerator] Création du BackgroundImage...");
                backgroundImage = CreateBackgroundImage(canvas);
            }
            
            // 3. Créer le panneau de texte
            Debug.Log("[TrousSceneGenerator] Création du TextPanel...");
            GameObject textPanel = CreateTextPanel(canvas);
            if (textPanel == null)
            {
                Debug.LogError("[TrousSceneGenerator] Échec de création du TextPanel");
                return;
            }
            
            // 4. Créer le conteneur des dropdowns
            Debug.Log("[TrousSceneGenerator] Création du DropdownContainer...");
            GameObject dropdownContainer = CreateDropdownContainer(canvas);
            
            // 5. Créer le panneau de feedback
            Debug.Log("[TrousSceneGenerator] Création du FeedbackPanel...");
            GameObject feedbackPanel = CreateFeedbackPanel(canvas);
            
            // 6. Créer l'AudioSource
            Debug.Log("[TrousSceneGenerator] Création de l'AudioSource...");
            GameObject audioSource = CreateAudioSource();
            
            // 7. Créer le TrousGameManager
            Debug.Log("[TrousSceneGenerator] Création du TrousGameManager...");
            GameObject trousManager = CreateTrousGameManager();
            if (trousManager == null)
            {
                Debug.LogError("[TrousSceneGenerator] Échec de création du TrousGameManager");
                return;
            }
            
            // 8. Configurer les références
            Debug.Log("[TrousSceneGenerator] Configuration des références...");
            ConfigureTrousGameManager(trousManager, textPanel, feedbackPanel, dropdownContainer, 
                                    backgroundVideo, backgroundImage, audioSource);
            
            // 9. Créer le prefab dropdown
            Debug.Log("[TrousSceneGenerator] Création du DropdownPrefab...");
            GameObject dropdownPrefab = CreateDropdownPrefab(canvas);
            
            // 10. Assigner le prefab au manager
            TrousGameManager manager = trousManager.GetComponent<TrousGameManager>();
            if (manager != null && dropdownPrefab != null)
            {
                manager.dropdownPrefab = dropdownPrefab;
                Debug.Log("[TrousSceneGenerator] Prefab assigné au manager");
            }
            
            // 11. Enregistrer tous les objets dans la scène
            #if UNITY_EDITOR
            Debug.Log("[TrousSceneGenerator] Enregistrement des objets dans la scène...");
            
            // Enregistrer tous les objets créés
            GameObject[] allObjects = { canvas, backgroundVideo, backgroundImage, textPanel, 
                                       dropdownContainer, feedbackPanel, audioSource, trousManager, dropdownPrefab };
            
            foreach (GameObject obj in allObjects)
            {
                if (obj != null)
                {
                    Undo.RegisterCreatedObjectUndo(obj, "Create Trous Scene Objects");
                    EditorUtility.SetDirty(obj);
                }
            }
            
            // Marquer la scène comme modifiée
            UnityEditor.SceneManagement.EditorSceneManager.MarkSceneDirty(UnityEditor.SceneManagement.EditorSceneManager.GetActiveScene());
            
            Debug.Log("[TrousSceneGenerator] Scène marquée comme modifiée - N'oubliez pas de sauvegarder avec Ctrl+S !");
            #endif
            
            Debug.Log("[TrousGameManager] ✅ Scène Trous générée avec succès !");
            Debug.Log("⚠️ IMPORTANT : Sauvegardez la scène avec Ctrl+S pour que les changements persistent !");
        }
        catch (System.Exception e)
        {
            Debug.LogError($"[TrousSceneGenerator] Erreur détaillée: {e.Message}\nStackTrace: {e.StackTrace}");
        }
    }
    
    private void ClearExistingObjects()
    {
        // Supprimer les objets existants avec les noms spécifiques
        string[] objectNames = {
            "Canvas", "BackgroundVideo", "BackgroundImage", "TextPanel", 
            "DropdownContainer", "FeedbackPanel", "AudioSource", "TrousGameManager", "DropdownPrefab"
        };
        
        foreach (string objectName in objectNames)
        {
            GameObject existing = GameObject.Find(objectName);
            if (existing != null)
            {
                DestroyImmediate(existing);
            }
        }
    }
    
    private GameObject CreateMainCanvas()
    {
        GameObject canvas = new GameObject("Canvas");
        Canvas canvasComponent = canvas.AddComponent<Canvas>();
        CanvasScaler scaler = canvas.AddComponent<CanvasScaler>();
        GraphicRaycaster raycaster = canvas.AddComponent<GraphicRaycaster>();
        
        // Configuration du Canvas
        canvasComponent.renderMode = RenderMode.ScreenSpaceOverlay;
        scaler.uiScaleMode = CanvasScaler.ScaleMode.ScaleWithScreenSize;
        scaler.referenceResolution = referenceResolution;
        scaler.screenMatchMode = CanvasScaler.ScreenMatchMode.MatchWidthOrHeight;
        scaler.matchWidthOrHeight = matchWidthOrHeight;
        
        return canvas;
    }
    
    private GameObject CreateBackgroundVideo(GameObject parent)
    {
        GameObject videoObj = new GameObject("BackgroundVideo");
        videoObj.transform.SetParent(parent.transform, false);
        
        // VideoPlayer
        VideoPlayer videoPlayer = videoObj.AddComponent<VideoPlayer>();
        videoPlayer.renderMode = VideoRenderMode.RenderTexture;
        videoPlayer.playOnAwake = false;
        videoPlayer.isLooping = true;
        
        // RawImage pour afficher la vidéo
        RawImage rawImage = videoObj.AddComponent<RawImage>();
        
        // RectTransform
        RectTransform rectTransform = videoObj.GetComponent<RectTransform>();
        rectTransform.anchorMin = Vector2.zero;
        rectTransform.anchorMax = Vector2.one;
        rectTransform.offsetMin = Vector2.zero;
        rectTransform.offsetMax = Vector2.zero;
        
        return videoObj;
    }
    
    private GameObject CreateBackgroundImage(GameObject parent)
    {
        GameObject imageObj = new GameObject("BackgroundImage");
        imageObj.transform.SetParent(parent.transform, false);
        
        // Image Component
        Image image = imageObj.AddComponent<Image>();
        image.type = Image.Type.Simple;
        image.preserveAspect = true;
        
        // RectTransform
        RectTransform rectTransform = imageObj.GetComponent<RectTransform>();
        rectTransform.anchorMin = Vector2.zero;
        rectTransform.anchorMax = Vector2.one;
        rectTransform.offsetMin = Vector2.zero;
        rectTransform.offsetMax = Vector2.zero;
        
        // Désactiver par défaut (sera activé selon la config)
        imageObj.SetActive(false);
        
        return imageObj;
    }
    
    private GameObject CreateTextPanel(GameObject parent)
    {
        GameObject textPanel = new GameObject("TextPanel");
        textPanel.transform.SetParent(parent.transform, false);
        
        // Image Component (fond)
        Image panelImage = textPanel.AddComponent<Image>();
        panelImage.color = textPanelColor;
        
        // RectTransform
        RectTransform rectTransform = textPanel.GetComponent<RectTransform>();
        rectTransform.anchorMin = new Vector2(0, 1);
        rectTransform.anchorMax = new Vector2(0, 1);
        rectTransform.anchoredPosition = textPanelPosition;
        rectTransform.sizeDelta = textPanelSize;
        
        // ScrollRect
        ScrollRect scrollRect = textPanel.AddComponent<ScrollRect>();
        scrollRect.horizontal = false;
        scrollRect.vertical = true;
        
        // Content pour le ScrollRect
        GameObject content = new GameObject("Content");
        content.transform.SetParent(textPanel.transform, false);
        
        RectTransform contentRect = content.AddComponent<RectTransform>();
        contentRect.anchorMin = Vector2.zero;
        contentRect.anchorMax = Vector2.one;
        contentRect.offsetMin = Vector2.zero;
        contentRect.offsetMax = Vector2.zero;
        
        // QuestionText
        GameObject questionText = new GameObject("QuestionText");
        questionText.transform.SetParent(content.transform, false);
        
        TextMeshProUGUI textComponent = questionText.AddComponent<TextMeshProUGUI>();
        textComponent.text = "Texte de la question avec des trous...";
        textComponent.fontSize = defaultFontSize;
        textComponent.color = defaultTextColor;
        textComponent.fontStyle = FontStyles.Bold;
        textComponent.alignment = TextAlignmentOptions.Left;
        textComponent.lineSpacing = 1.2f;
        
        if (customFont != null)
        {
            textComponent.font = customFont;
        }
        
        RectTransform textRect = questionText.GetComponent<RectTransform>();
        textRect.anchorMin = Vector2.zero;
        textRect.anchorMax = Vector2.one;
        textRect.offsetMin = new Vector2(30, 20);
        textRect.offsetMax = new Vector2(-30, -20);
        
        // Configurer le ScrollRect
        scrollRect.content = contentRect;
        scrollRect.viewport = rectTransform;
        
        return textPanel;
    }
    
    private GameObject CreateDropdownContainer(GameObject parent)
    {
        GameObject container = new GameObject("DropdownContainer");
        container.transform.SetParent(parent.transform, false);
        
        RectTransform rectTransform = container.AddComponent<RectTransform>();
        rectTransform.anchorMin = Vector2.zero;
        rectTransform.anchorMax = Vector2.one;
        rectTransform.offsetMin = Vector2.zero;
        rectTransform.offsetMax = Vector2.zero;
        
        return container;
    }
    
    private GameObject CreateFeedbackPanel(GameObject parent)
    {
        GameObject feedbackPanel = new GameObject("FeedbackPanel");
        feedbackPanel.transform.SetParent(parent.transform, false);
        
        // Image Component (fond)
        Image panelImage = feedbackPanel.AddComponent<Image>();
        panelImage.color = new Color(0, 0, 0, 0.8f);
        
        // RectTransform
        RectTransform rectTransform = feedbackPanel.GetComponent<RectTransform>();
        rectTransform.anchorMin = new Vector2(0.5f, 0.5f);
        rectTransform.anchorMax = new Vector2(0.5f, 0.5f);
        rectTransform.anchoredPosition = Vector2.zero;
        rectTransform.sizeDelta = new Vector2(1024, 635);
        
        // FeedbackText
        GameObject feedbackText = new GameObject("FeedbackText");
        feedbackText.transform.SetParent(feedbackPanel.transform, false);
        
        TextMeshProUGUI textComponent = feedbackText.AddComponent<TextMeshProUGUI>();
        textComponent.text = "Feedback du jeu...";
        textComponent.fontSize = 42;
        textComponent.color = Color.white;
        textComponent.fontStyle = FontStyles.Bold;
        textComponent.alignment = TextAlignmentOptions.Center;
        
        if (customFont != null)
        {
            textComponent.font = customFont;
        }
        
        RectTransform textRect = feedbackText.GetComponent<RectTransform>();
        textRect.anchorMin = Vector2.zero;
        textRect.anchorMax = Vector2.one;
        textRect.offsetMin = Vector2.zero;
        textRect.offsetMax = Vector2.zero;
        
        // FeedbackBackgroundImage
        GameObject feedbackBgImage = new GameObject("FeedbackBackgroundImage");
        feedbackBgImage.transform.SetParent(feedbackPanel.transform, false);
        
        Image bgImage = feedbackBgImage.AddComponent<Image>();
        bgImage.color = Color.clear;
        
        RectTransform bgRect = feedbackBgImage.GetComponent<RectTransform>();
        bgRect.anchorMin = Vector2.zero;
        bgRect.anchorMax = Vector2.one;
        bgRect.offsetMin = Vector2.zero;
        bgRect.offsetMax = Vector2.zero;
        
        // Désactiver par défaut
        feedbackPanel.SetActive(false);
        
        return feedbackPanel;
    }
    
    private GameObject CreateAudioSource()
    {
        GameObject audioObj = new GameObject("AudioSource");
        AudioSource audioSource = audioObj.AddComponent<AudioSource>();
        audioSource.playOnAwake = false;
        audioSource.volume = 0.7f;
        
        return audioObj;
    }
    
    private GameObject CreateTrousGameManager()
    {
        GameObject manager = new GameObject("TrousGameManager");
        TrousGameManager trousManager = manager.AddComponent<TrousGameManager>();
        
        return manager;
    }
    
    private void ConfigureTrousGameManager(GameObject manager, GameObject textPanel, GameObject feedbackPanel, 
                                         GameObject dropdownContainer, GameObject backgroundVideo, 
                                         GameObject backgroundImage, GameObject audioSource)
    {
        if (manager == null)
        {
            Debug.LogError("[TrousSceneGenerator] Manager est null");
            return;
        }
        
        TrousGameManager trousManager = manager.GetComponent<TrousGameManager>();
        if (trousManager == null)
        {
            Debug.LogError("[TrousSceneGenerator] TrousGameManager component est null");
            return;
        }
        
        // Configurer les références avec vérifications
        if (textPanel != null)
        {
            trousManager.questionText = textPanel.GetComponentInChildren<TextMeshProUGUI>();
            trousManager.textPanel = textPanel;
            trousManager.textScrollRect = textPanel.GetComponent<ScrollRect>();
        }
        
        if (feedbackPanel != null)
        {
            trousManager.feedbackPanel = feedbackPanel;
            trousManager.feedbackText = feedbackPanel.GetComponentInChildren<TextMeshProUGUI>();
        }
        
        if (dropdownContainer != null)
        {
            trousManager.textContainer = dropdownContainer.transform;
        }
        
        if (audioSource != null)
        {
            trousManager.audioSource = audioSource.GetComponent<AudioSource>();
        }
        
        // Trouver la caméra principale
        Camera mainCam = Camera.main;
        if (mainCam == null)
        {
            mainCam = FindFirstObjectByType<Camera>();
        }
        trousManager.mainCamera = mainCam;
        
        trousManager.customFont = customFont;
        
        if (backgroundVideo != null)
        {
            trousManager.backgroundVideo = backgroundVideo.GetComponent<VideoPlayer>();
        }
        
        if (backgroundImage != null)
        {
            trousManager.backgroundImage = backgroundImage.GetComponent<Image>();
        }
        
        Debug.Log("[TrousSceneGenerator] Références configurées avec succès");
    }
    
    private GameObject CreateDropdownPrefab(GameObject parent)
    {
        GameObject prefab = new GameObject("DropdownPrefab");
        prefab.transform.SetParent(parent.transform, false);
        
        // Button Component
        Button button = prefab.AddComponent<Button>();
        Image buttonImage = prefab.AddComponent<Image>();
        buttonImage.color = Color.white;
        
        // RectTransform
        RectTransform rectTransform = prefab.GetComponent<RectTransform>();
        rectTransform.sizeDelta = new Vector2(200, 40);
        
        // ButtonText
        GameObject buttonText = new GameObject("ButtonText");
        buttonText.transform.SetParent(prefab.transform, false);
        
        TextMeshProUGUI textComponent = buttonText.AddComponent<TextMeshProUGUI>();
        textComponent.text = "Choisir...";
        textComponent.fontSize = 32;
        textComponent.color = new Color(0.17f, 0.24f, 0.31f, 1f);
        textComponent.alignment = TextAlignmentOptions.Center;
        
        if (customFont != null)
        {
            textComponent.font = customFont;
        }
        
        RectTransform textRect = buttonText.GetComponent<RectTransform>();
        textRect.anchorMin = Vector2.zero;
        textRect.anchorMax = Vector2.one;
        textRect.offsetMin = Vector2.zero;
        textRect.offsetMax = Vector2.zero;
        
        // DropdownPanel
        GameObject dropdownPanel = new GameObject("DropdownPanel");
        dropdownPanel.transform.SetParent(prefab.transform, false);
        
        Image panelImage = dropdownPanel.AddComponent<Image>();
        panelImage.color = Color.white;
        
        Outline outline = dropdownPanel.AddComponent<Outline>();
        outline.effectColor = new Color(0.39f, 0.28f, 0.49f, 1f);
        outline.effectDistance = new Vector2(2, 2);
        
        RectTransform panelRect = dropdownPanel.GetComponent<RectTransform>();
        panelRect.anchorMin = new Vector2(0, 1);
        panelRect.anchorMax = new Vector2(0, 1);
        panelRect.anchoredPosition = Vector2.zero;
        panelRect.sizeDelta = new Vector2(200, 200);
        
        // Désactiver par défaut
        dropdownPanel.SetActive(false);
        
        // TrousDropdown Script
        TrousDropdown trousDropdown = prefab.AddComponent<TrousDropdown>();
        
        return prefab;
    }
    
    #if UNITY_EDITOR
    [MenuItem("Tools/Trous Scene/Generate Scene")]
    public static void GenerateSceneFromMenu()
    {
        try
        {
            // Créer une instance temporaire sans GameObject
            TrousSceneGenerator generator = ScriptableObject.CreateInstance<TrousSceneGenerator>();
            
            // Configurer les paramètres par défaut
            generator.referenceResolution = new Vector2(1920, 1080);
            generator.matchWidthOrHeight = 0.5f;
            generator.createVideoBackground = true;
            generator.createImageBackground = true;
            generator.textPanelPosition = new Vector2(100, -200);
            generator.textPanelSize = new Vector2(1720, 680);
            generator.textPanelColor = new Color(0.96f, 0.93f, 0.9f, 0.8f);
            generator.defaultFontSize = 36;
            generator.defaultTextColor = new Color(0.39f, 0.28f, 0.49f, 1f);
            generator.clearExisting = true;
            
            Debug.Log("[TrousSceneGenerator] Générateur créé, début de la génération...");
            
            generator.GenerateTrousScene();
            
            Debug.Log("[TrousSceneGenerator] Scène générée avec succès depuis le menu !");
            
            // Nettoyer l'instance temporaire
            ScriptableObject.DestroyImmediate(generator);
        }
        catch (System.Exception e)
        {
            Debug.LogError($"[TrousSceneGenerator] Erreur lors de la génération: {e.Message}\nStackTrace: {e.StackTrace}");
        }
    }
    
    [MenuItem("Tools/Trous Scene/Clear Scene")]
    public static void ClearSceneFromMenu()
    {
        try
        {
            TrousSceneGenerator generator = ScriptableObject.CreateInstance<TrousSceneGenerator>();
            generator.ClearExistingObjects();
            Debug.Log("[TrousSceneGenerator] Scène nettoyée avec succès !");
            ScriptableObject.DestroyImmediate(generator);
        }
        catch (System.Exception e)
        {
            Debug.LogError($"[TrousSceneGenerator] Erreur lors du nettoyage: {e.Message}");
        }
    }
    #endif
}
