using System.Collections;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.Networking;
using UnityEngine.Video;
using TMPro;

/// <summary>
/// Gère la mise en page de la scène shooting selon les spécifications :
/// - Écran 1920x1080
/// - Image de fond chargée depuis URL (visible autour de la zone de jeu)
/// - Bandeau supérieur : 1480x160, à 40px du haut, coins arrondis 40px
/// - Zone de jeu : 1480x835, à 40px du bas (contient la vidéo avec coins arrondis)
/// </summary>
public class ShootingGameLayout : MonoBehaviour
{
    [Header("Layout Configuration")]
    [SerializeField] private string backdropUrl = "https://ujsa.studioplc.fr/datas/images/main_background.jpg"; // Image d'habillage à l'extérieur de la zone de jeu
    
    [Header("Layout Dimensions")]
    [SerializeField] private float screenWidth = 1920f;
    [SerializeField] private float screenHeight = 1080f;
    [SerializeField] private float contentWidth = 1480f;
    [SerializeField] private float headerHeight = 160f; // Sera écrasé par general-config.json
    [SerializeField] private float gameAreaHeight = 835f;
    [SerializeField] private float topMargin = 40f;
    [SerializeField] private float bottomMargin = 40f;
    [SerializeField] private float cornerRadius = 20f;         // Coins arrondis du bandeau
    [SerializeField] private float gameAreaCornerRadius = 20f; // Coins arrondis du cadre central
    
    [Header("Colors")]
    [SerializeField] private Color headerBackgroundColor = new Color(0.98f, 0.94f, 0.92f, 1f); // Sera écrasé par general-config.json
    
    // Shadow config
    private BandShadowConfig shadowConfig;
    
    [Header("Debug")]
    [SerializeField] private bool showDebugGizmos = false;
    
    // Références UI créées
    private RawImage backgroundImage;
    private GameObject headerPanel;
    private GameObject gameAreaPanel;
    private RawImage videoDisplay; // Pour afficher la vidéo dans la zone de jeu
    private Transform ledContainer;
    private TextMeshProUGUI questionText;
    
    // RenderTexture pour la vidéo
    private RenderTexture videoRenderTexture;
    
    // Références internes
    private Canvas mainCanvas;
    private CanvasScaler canvasScaler;
    private Texture2D loadedBackgroundTexture;
    private bool isInitialized = false;
    private bool backdropSetByApi = false; // Flag pour éviter d'écraser le backdrop de l'API
    private bool backdropLoadingComplete = false; // Flag pour indiquer que le backdrop est chargé
    
    // Propriétés publiques pour accès par le GameManager
    public GameObject HeaderPanel => headerPanel;
    public GameObject GameAreaPanel => gameAreaPanel;
    public TextMeshProUGUI QuestionText => questionText;
    public Transform LedContainer => ledContainer;
    public bool IsInitialized => isInitialized;
    public bool IsFullyLoaded => isInitialized && (backdropSetByApi || backdropLoadingComplete);
    public RectTransform GameAreaRect => gameAreaPanel?.GetComponent<RectTransform>();
    public RenderTexture VideoRenderTexture => videoRenderTexture;
    
    // Singleton pour accès facile
    public static ShootingGameLayout Instance { get; private set; }
    
    void Awake()
    {
        if (Instance == null)
        {
            Instance = this;
        }
        else
        {
            Destroy(gameObject);
            return;
        }
        
        SetupCanvas();
        
        // Charger les paramètres depuis general-config.json AVANT de créer le layout
        LoadConfigFromGeneralConfig();
        
        // Créer la RenderTexture pour la vidéo
        CreateVideoRenderTexture();
        
        // IMPORTANT: Créer le layout immédiatement dans Awake (synchrone)
        CreateLayoutImmediate();
    }
    
    /// <summary>
    /// Charge les paramètres du bandeau depuis general-config.json
    /// </summary>
    void LoadConfigFromGeneralConfig()
    {
        if (GeneralConfigManager.Instance == null)
        {
            Debug.LogWarning("[ShootingGameLayout] GeneralConfigManager non disponible, utilisation des valeurs par défaut");
            return;
        }
        
        // Attendre que la config soit chargée (synchrone dans Awake)
        if (!GeneralConfigManager.Instance.IsConfigLoaded())
        {
            Debug.LogWarning("[ShootingGameLayout] Config pas encore chargée, utilisation des valeurs par défaut");
            return;
        }
        
        var defaultUIConfig = GeneralConfigManager.Instance.GetDefaultUIConfig();
        if (defaultUIConfig?.bands != null)
        {
            // Hauteur du bandeau
            if (defaultUIConfig.bands.bandHeight > 0)
            {
                headerHeight = defaultUIConfig.bands.bandHeight;
                Debug.Log($"[ShootingGameLayout] ✅ Hauteur bandeau depuis config: {headerHeight}px");
            }
            
            // Couleur du bandeau
            if (!string.IsNullOrEmpty(defaultUIConfig.bands.bandColor))
            {
                if (ColorUtility.TryParseHtmlString(defaultUIConfig.bands.bandColor, out Color parsedColor))
                {
                    parsedColor.a = defaultUIConfig.bands.bandAlpha;
                    headerBackgroundColor = parsedColor;
                    Debug.Log($"[ShootingGameLayout] ✅ Couleur bandeau depuis config: {defaultUIConfig.bands.bandColor} (alpha: {defaultUIConfig.bands.bandAlpha})");
                }
            }
            
            // Corner radius (bandeau)
            if (defaultUIConfig.bands.cornerRadius > 0)
            {
                cornerRadius = defaultUIConfig.bands.cornerRadius;
                Debug.Log($"[ShootingGameLayout] ✅ Corner radius bandeau depuis config: {cornerRadius}px");
            }
            
            // Corner radius (cadre central / zone de jeu)
            if (defaultUIConfig.bands.gameAreaCornerRadius > 0)
            {
                gameAreaCornerRadius = defaultUIConfig.bands.gameAreaCornerRadius;
                Debug.Log($"[ShootingGameLayout] ✅ Corner radius zone de jeu depuis config: {gameAreaCornerRadius}px");
            }
            
            // Shadow config
            shadowConfig = defaultUIConfig.bands.shadow;
            if (shadowConfig != null && shadowConfig.enabled)
            {
                Debug.Log($"[ShootingGameLayout] ✅ Shadow configurée: {shadowConfig.color}, offset=({shadowConfig.offsetX}, {shadowConfig.offsetY})");
            }
            
            // Recalculer la hauteur de la zone de jeu en fonction de la nouvelle hauteur du bandeau
            // gameAreaHeight = screenHeight - topMargin - bottomMargin - headerHeight - espacement
            float spacing = 5f; // Espacement entre header et game area
            gameAreaHeight = screenHeight - topMargin - bottomMargin - headerHeight - spacing;
            Debug.Log($"[ShootingGameLayout] ✅ Zone de jeu recalculée: {gameAreaHeight}px");
        }
        else
        {
            Debug.Log("[ShootingGameLayout] Pas de config bands dans defaultUIConfig, utilisation des valeurs par défaut");
        }
    }
    
    void Start()
    {
        // Réappliquer le style de la question une fois que GeneralConfigManager est chargé
        if (questionText != null)
        {
            Debug.Log("[ShootingGameLayout] Start - Réapplication du style de la question");
            ApplyQuestionStyling();
            questionText.ForceMeshUpdate();
        }
        
        // Charger l'image du backdrop de manière asynchrone SEULEMENT si pas déjà défini par l'API
        if (!backdropSetByApi)
        {
            StartCoroutine(LoadBackdropImageAsync());
        }
        
        // Si la config n'était pas disponible dans Awake(), réessayer maintenant
        StartCoroutine(TryLoadConfigDelayed());
    }
    
    /// <summary>
    /// Essaie de charger la config après un court délai si elle n'était pas disponible dans Awake
    /// </summary>
    IEnumerator TryLoadConfigDelayed()
    {
        // Attendre que GeneralConfigManager soit disponible et chargé
        float timeout = 3f;
        float elapsed = 0f;
        
        while ((GeneralConfigManager.Instance == null || !GeneralConfigManager.Instance.IsConfigLoaded()) && elapsed < timeout)
        {
            yield return new WaitForSeconds(0.1f);
            elapsed += 0.1f;
        }
        
        if (GeneralConfigManager.Instance != null && GeneralConfigManager.Instance.IsConfigLoaded())
        {
            var defaultUIConfig = GeneralConfigManager.Instance.GetDefaultUIConfig();
            if (defaultUIConfig?.bands != null)
            {
                // Mettre à jour le corner radius du cadre central si nécessaire
                if (defaultUIConfig.bands.gameAreaCornerRadius > 0 && defaultUIConfig.bands.gameAreaCornerRadius != gameAreaCornerRadius)
                {
                    gameAreaCornerRadius = defaultUIConfig.bands.gameAreaCornerRadius;
                    Debug.Log($"[ShootingGameLayout] ✅ (Start) Corner radius zone de jeu mis à jour: {gameAreaCornerRadius}px");
                    
                    // Mettre à jour les coins arrondis du VideoMaskContainer
                    UpdateGameAreaCornerRadius();
                }
                
                // Mettre à jour le corner radius du bandeau si nécessaire
                if (defaultUIConfig.bands.cornerRadius > 0 && defaultUIConfig.bands.cornerRadius != cornerRadius)
                {
                    cornerRadius = defaultUIConfig.bands.cornerRadius;
                    Debug.Log($"[ShootingGameLayout] ✅ (Start) Corner radius bandeau mis à jour: {cornerRadius}px");
                    
                    // Mettre à jour les coins arrondis du header
                    if (headerPanel != null)
                    {
                        var roundedCorners = headerPanel.GetComponent<RoundedCornersImage>();
                        if (roundedCorners != null)
                        {
                            roundedCorners.cornerRadius = cornerRadius;
                        }
                    }
                }
            }
        }
    }
    
    /// <summary>
    /// Met à jour les coins arrondis de la zone de jeu
    /// </summary>
    void UpdateGameAreaCornerRadius()
    {
        // Trouver le VideoMaskContainer et mettre à jour ses coins arrondis
        Transform maskContainer = mainCanvas?.transform.Find("VideoMaskContainer");
        if (maskContainer != null)
        {
            var roundedCorners = maskContainer.GetComponent<RoundedCornersImage>();
            if (roundedCorners != null)
            {
                roundedCorners.cornerRadius = gameAreaCornerRadius;
                Debug.Log($"[ShootingGameLayout] ✅ VideoMaskContainer coins arrondis mis à jour: {gameAreaCornerRadius}px");
            }
            else
            {
                // Ajouter le composant si absent
                roundedCorners = maskContainer.gameObject.AddComponent<RoundedCornersImage>();
                roundedCorners.cornerRadius = gameAreaCornerRadius;
                Debug.Log($"[ShootingGameLayout] ✅ RoundedCornersImage ajouté à VideoMaskContainer: {gameAreaCornerRadius}px");
            }
        }
        else
        {
            Debug.LogWarning("[ShootingGameLayout] VideoMaskContainer non trouvé pour mise à jour des coins arrondis");
        }
    }
    
    void SetupCanvas()
    {
        mainCanvas = GetComponentInParent<Canvas>();
        if (mainCanvas == null)
        {
            mainCanvas = FindFirstObjectByType<Canvas>();
        }
        
        if (mainCanvas != null)
        {
            canvasScaler = mainCanvas.GetComponent<CanvasScaler>();
            if (canvasScaler != null)
            {
                canvasScaler.uiScaleMode = CanvasScaler.ScaleMode.ScaleWithScreenSize;
                canvasScaler.referenceResolution = new Vector2(screenWidth, screenHeight);
                canvasScaler.matchWidthOrHeight = 0.5f;
            }
        }
    }
    
    void CreateVideoRenderTexture()
    {
        // Créer une RenderTexture pour la vidéo avec la taille de la zone de jeu
        int width = Mathf.RoundToInt(contentWidth);
        int height = Mathf.RoundToInt(gameAreaHeight);
        
        videoRenderTexture = new RenderTexture(width, height, 0, RenderTextureFormat.ARGB32);
        videoRenderTexture.name = "VideoRenderTexture";
        videoRenderTexture.Create();
        
        Debug.Log($"[ShootingGameLayout] RenderTexture créée: {width}x{height}");
    }
    
    void CreateLayoutImmediate()
    {
        Debug.Log("[ShootingGameLayout] Création immédiate du layout...");
        
        // 1. Créer l'image de fond (couvre tout l'écran)
        CreateBackgroundImage();
        
        // 2. Créer le bandeau supérieur
        CreateHeaderPanel();
        
        // 3. Créer la zone de jeu avec la vidéo
        CreateGameAreaPanel();
        
        isInitialized = true;
        Debug.Log("[ShootingGameLayout] Layout créé et prêt !");
    }
    
    void CreateBackgroundImage()
    {
        GameObject bgObj = new GameObject("MainBackgroundImage");
        bgObj.transform.SetParent(mainCanvas.transform, false);
        bgObj.transform.SetAsFirstSibling(); // Tout au fond
        
        RectTransform bgRect = bgObj.AddComponent<RectTransform>();
        bgRect.anchorMin = Vector2.zero;
        bgRect.anchorMax = Vector2.one;
        bgRect.offsetMin = Vector2.zero;
        bgRect.offsetMax = Vector2.zero;
        
        backgroundImage = bgObj.AddComponent<RawImage>();
        backgroundImage.raycastTarget = false;
        backgroundImage.color = new Color(0.2f, 0.3f, 0.25f, 1f); // Couleur temporaire avant chargement
        
        // Canvas avec sorting order très bas pour être vraiment en arrière
        Canvas bgCanvas = bgObj.AddComponent<Canvas>();
        bgCanvas.overrideSorting = true;
        bgCanvas.sortingOrder = -10; // En dessous de tout
        
        Debug.Log("[ShootingGameLayout] Image de fond créée (sortingOrder=-10)");
    }
    
    IEnumerator LoadBackdropImageAsync()
    {
        if (string.IsNullOrEmpty(backdropUrl) || backgroundImage == null)
        {
            backdropLoadingComplete = true;
            yield break;
        }
        
        Debug.Log($"[ShootingGameLayout] 🖼️ Chargement du backdrop (habillage): {backdropUrl}");
        
        // 🚀 NOUVEAU : Vérifier d'abord le cache de GameDataManager
        if (GameDataManager.Instance != null)
        {
            Texture2D cachedTexture = GameDataManager.Instance.GetCachedTexture("backdrop");
            if (cachedTexture != null)
            {
                Debug.Log($"[ShootingGameLayout] ⚡ Backdrop chargé instantanément depuis le cache !");
                loadedBackgroundTexture = cachedTexture;
                backgroundImage.texture = cachedTexture;
                backgroundImage.color = Color.white;
                backdropLoadingComplete = true;
                yield break;
            }
        }
        
        using (UnityWebRequest www = UnityWebRequestTexture.GetTexture(backdropUrl))
        {
            yield return www.SendWebRequest();
            
            if (www.result == UnityWebRequest.Result.Success)
            {
                loadedBackgroundTexture = ((DownloadHandlerTexture)www.downloadHandler).texture;
                backgroundImage.texture = loadedBackgroundTexture;
                backgroundImage.color = Color.white;
                Debug.Log("[ShootingGameLayout] ✅ Backdrop chargé avec succès");
            }
            else
            {
                Debug.LogError($"[ShootingGameLayout] ❌ Erreur chargement backdrop: {www.error}");
            }
            
            backdropLoadingComplete = true;
            Debug.Log("[ShootingGameLayout] ✅ Chargement du backdrop terminé");
        }
    }
    
    void CreateHeaderPanel()
    {
        headerPanel = new GameObject("HeaderPanel_Layout");
        headerPanel.transform.SetParent(mainCanvas.transform, false);
        
        RectTransform headerRect = headerPanel.AddComponent<RectTransform>();
        
        // Positionner : centré horizontalement, à 40px du haut
        headerRect.anchorMin = new Vector2(0.5f, 1f);
        headerRect.anchorMax = new Vector2(0.5f, 1f);
        headerRect.pivot = new Vector2(0.5f, 1f);
        headerRect.sizeDelta = new Vector2(contentWidth, headerHeight);
        headerRect.anchoredPosition = new Vector2(0, -topMargin);
        
        // Fond avec couleur
        Image headerBg = headerPanel.AddComponent<Image>();
        headerBg.color = headerBackgroundColor;
        headerBg.raycastTarget = false;
        
        // Coins arrondis
        AddRoundedCorners(headerPanel, cornerRadius);
        
        // Ajouter l'ombre si configurée
        if (shadowConfig != null && shadowConfig.enabled)
        {
            Shadow shadow = headerPanel.AddComponent<Shadow>();
            
            Color shadowColor = new Color(0, 0, 0, 0.25f);
            if (ColorUtility.TryParseHtmlString(shadowConfig.color, out Color parsedShadowColor))
            {
                shadowColor = parsedShadowColor;
            }
            
            shadow.effectColor = shadowColor;
            // Pour le bandeau du haut, l'ombre va vers le bas
            shadow.effectDistance = new Vector2(shadowConfig.offsetX, -shadowConfig.offsetY);
            
            Debug.Log($"[ShootingGameLayout] ✅ Shadow ajoutée au header: {shadowConfig.color}");
        }
        
        // Canvas pour sorting order élevé
        Canvas headerCanvas = headerPanel.AddComponent<Canvas>();
        headerCanvas.overrideSorting = true;
        headerCanvas.sortingOrder = 100;
        headerPanel.AddComponent<GraphicRaycaster>();
        
        // Créer le contenu
        CreateHeaderContent();
        
        Debug.Log($"[ShootingGameLayout] Header créé: {contentWidth}x{headerHeight}, couleur: {headerBackgroundColor}");
    }
    
    void CreateHeaderContent()
    {
        // === CONTENEUR POUR LES LEDs (à gauche) ===
        GameObject ledContainerObj = new GameObject("LEDContainer");
        ledContainerObj.transform.SetParent(headerPanel.transform, false);
        
        RectTransform ledRect = ledContainerObj.AddComponent<RectTransform>();
        ledRect.anchorMin = new Vector2(0f, 0f);
        ledRect.anchorMax = new Vector2(0f, 1f);
        ledRect.pivot = new Vector2(0f, 0.5f);
        ledRect.sizeDelta = new Vector2(400f, 0f);
        ledRect.anchoredPosition = new Vector2(20f, 0f);
        
        ledContainer = ledContainerObj.transform;
        
        // === ZONE DE TEXTE POUR LA QUESTION ===
        GameObject questionObj = new GameObject("QuestionText");
        questionObj.transform.SetParent(headerPanel.transform, false);
        
        RectTransform questionRect = questionObj.AddComponent<RectTransform>();
        questionRect.anchorMin = new Vector2(0f, 0f);
        questionRect.anchorMax = new Vector2(1f, 1f);
        
        // Appliquer les marges depuis la configuration
        var defaultUIConfig = GeneralConfigManager.Instance?.GetDefaultUIConfig();
        float marginLeft = 300f; // Valeur par défaut DEPUIS LE JSON
        float marginRight = 50f; // Valeur par défaut DEPUIS LE JSON
        float marginTop = 20f; // Valeur par défaut DEPUIS LE JSON
        
        if (defaultUIConfig?.questionDisplay != null)
        {
            marginLeft = defaultUIConfig.questionDisplay.marginLeft;
            marginRight = defaultUIConfig.questionDisplay.marginRight;
            marginTop = defaultUIConfig.questionDisplay.marginTop;
            Debug.Log($"[ShootingGameLayout] ✅ Marges chargées depuis config: left={marginLeft}, right={marginRight}, top={marginTop}");
        }
        else
        {
            Debug.LogWarning($"[ShootingGameLayout] ⚠️ Config non disponible, utilisation des fallback: left={marginLeft}, right={marginRight}, top={marginTop}");
        }
        
        questionRect.offsetMin = new Vector2(marginLeft, marginTop);
        questionRect.offsetMax = new Vector2(-marginRight, -marginTop);
        
        questionText = questionObj.AddComponent<TextMeshProUGUI>();
        questionText.text = "Chargement de la question...";
        
        // Appliquer strictement la configuration depuis general-config.json
        ApplyQuestionStyling();
        
        // Forcer la mise à jour pour s'assurer que la couleur est appliquée
        questionText.ForceMeshUpdate();
        
        Debug.Log($"[ShootingGameLayout] Contenu header créé - couleur actuelle: {questionText.color}");
    }
    
    /// <summary>
    /// Applique le style de la question depuis la configuration general-config.json
    /// </summary>
    void ApplyQuestionStyling()
    {
        if (questionText == null) return;
        
        Debug.Log($"[ShootingGameLayout] ApplyQuestionStyling - GeneralConfigManager.Instance: {GeneralConfigManager.Instance != null}");
        
        var defaultUIConfig = GeneralConfigManager.Instance?.GetDefaultUIConfig();
        Debug.Log($"[ShootingGameLayout] ApplyQuestionStyling - defaultUIConfig: {defaultUIConfig != null}");
        Debug.Log($"[ShootingGameLayout] ApplyQuestionStyling - questionDisplay: {defaultUIConfig?.questionDisplay != null}");
        
        if (defaultUIConfig?.questionDisplay != null)
        {
            var questionConfig = defaultUIConfig.questionDisplay;
            
            // Taille de police
            questionText.fontSize = questionConfig.fontSize;
            
            // Couleur
            string colorString = questionConfig.fontColor;
            if (!colorString.StartsWith("#"))
            {
                colorString = "#" + colorString;
            }
            if (ColorUtility.TryParseHtmlString(colorString, out Color textColor))
            {
                questionText.color = textColor;
                questionText.faceColor = textColor; // Forcer aussi la couleur de face
                Debug.Log($"[ShootingGameLayout] ✅ Couleur appliquée: {colorString} -> color: {textColor}, faceColor: {questionText.faceColor}");
            }
            else
            {
                Debug.LogWarning($"[ShootingGameLayout] ⚠️ Impossible de parser la couleur: {colorString}");
            }
            
            // S'assurer qu'il n'y a pas de gradient qui écrase la couleur
            questionText.enableVertexGradient = false;
            
            // Gras
            questionText.fontStyle = questionConfig.fontBold ? FontStyles.Bold : FontStyles.Normal;
            
            // Alignement
            if (questionConfig.alignment == "Center")
            {
                questionText.alignment = TextAlignmentOptions.Center;
            }
            else if (questionConfig.alignment == "Left")
            {
                questionText.alignment = TextAlignmentOptions.Left;
            }
            else if (questionConfig.alignment == "Right")
            {
                questionText.alignment = TextAlignmentOptions.Right;
            }
            
            // Auto-sizing si activé
            if (questionConfig.adaptToScreenSize)
            {
                questionText.enableAutoSizing = true;
                questionText.fontSizeMin = questionConfig.minFontSize;
                questionText.fontSizeMax = questionConfig.maxFontSize;
            }
            else
            {
                questionText.enableAutoSizing = false;
            }
            
            // Configuration du wrapping
            questionText.textWrappingMode = TextWrappingModes.Normal;
            questionText.overflowMode = TextOverflowModes.Overflow;
            
            Debug.Log($"[ShootingGameLayout] ✅ Style question appliqué depuis config - fontSize:{questionConfig.fontSize}, color:{questionConfig.fontColor}, alignment:{questionConfig.alignment}");
        }
        else
        {
            Debug.LogWarning("[ShootingGameLayout] ⚠️ Aucune configuration questionDisplay trouvée dans general-config.json - Application des valeurs par défaut");
            
            // FALLBACK: Appliquer directement les valeurs du JSON en dur pour éviter le texte blanc
            questionText.fontSize = 30f;
            
            // FORCER la couleur avec plusieurs méthodes
            Color targetColor = new Color(0.486f, 0.420f, 0.388f, 1f); // #7c6b63
            questionText.color = targetColor;
            questionText.faceColor = targetColor; // Forcer aussi la couleur de face
            
            questionText.fontStyle = FontStyles.Normal;
            questionText.alignment = TextAlignmentOptions.Center;
            questionText.enableAutoSizing = true;
            questionText.fontSizeMin = 24f;
            questionText.fontSizeMax = 42f;
            questionText.textWrappingMode = TextWrappingModes.Normal;
            questionText.overflowMode = TextOverflowModes.Overflow;
            
            // S'assurer qu'il n'y a pas de gradient ou outline qui écrase la couleur
            questionText.enableVertexGradient = false;
            
            Debug.Log($"[ShootingGameLayout] ✅ Fallback appliqué - color: {questionText.color}, faceColor: {questionText.faceColor}");
        }
    }
    
    void CreateGameAreaPanel()
    {
        // Créer un conteneur vide pour le GameAreaPanel (pour les références)
        gameAreaPanel = new GameObject("GameAreaPanel_Layout");
        gameAreaPanel.transform.SetParent(mainCanvas.transform, false);
        
        RectTransform gameRect = gameAreaPanel.AddComponent<RectTransform>();
        
        // Positionner : centré horizontalement, à 40px du bas
        gameRect.anchorMin = new Vector2(0.5f, 0f);
        gameRect.anchorMax = new Vector2(0.5f, 0f);
        gameRect.pivot = new Vector2(0.5f, 0f);
        gameRect.sizeDelta = new Vector2(contentWidth, gameAreaHeight);
        gameRect.anchoredPosition = new Vector2(0, bottomMargin);
        
        // Créer la RawImage pour afficher la vidéo - DIRECTEMENT DANS LE MAIN CANVAS
        // pour éviter les problèmes de hiérarchie
        CreateVideoDisplay();
        
        Debug.Log($"[ShootingGameLayout] Game Area créée: {contentWidth}x{gameAreaHeight}");
    }
    
    void CreateVideoDisplay()
    {
        // === CONTENEUR PRINCIPAL AVEC COINS ARRONDIS (zone de jeu) ===
        // Même logique que CalculatorGameLayout qui fonctionne
        GameObject gameAreaPanel = new GameObject("VideoMaskContainer");
        gameAreaPanel.transform.SetParent(mainCanvas.transform, false);
        
        RectTransform containerRect = gameAreaPanel.AddComponent<RectTransform>();
        containerRect.anchorMin = new Vector2(0.5f, 0f);
        containerRect.anchorMax = new Vector2(0.5f, 0f);
        containerRect.pivot = new Vector2(0.5f, 0f);
        containerRect.sizeDelta = new Vector2(contentWidth, gameAreaHeight);
        containerRect.anchoredPosition = new Vector2(0, bottomMargin);
        
        // Canvas avec sortingOrder pour contrôler l'ordre d'affichage
        Canvas videoCanvas = gameAreaPanel.AddComponent<Canvas>();
        videoCanvas.overrideSorting = true;
        videoCanvas.sortingOrder = 10; // Entre le fond (-10) et le header (100)
        gameAreaPanel.AddComponent<GraphicRaycaster>();
        
        // Image de fond du conteneur (couleur de fallback visible si vidéo ne couvre pas)
        Image containerBg = gameAreaPanel.AddComponent<Image>();
        containerBg.color = new Color(0.15f, 0.15f, 0.2f, 1f); // Bleu-gris foncé comme fallback
        containerBg.raycastTarget = true;
        
        // IMPORTANT: Ajouter les coins arrondis AVANT le Mask
        AddRoundedCorners(gameAreaPanel, gameAreaCornerRadius);
        
        // Masque pour découper le contenu aux coins arrondis
        // showMaskGraphic = true pour que l'image avec coins arrondis soit visible !
        Mask containerMask = gameAreaPanel.AddComponent<Mask>();
        containerMask.showMaskGraphic = true;
        
        // === VIDEO DISPLAY (enfant du masque, remplit tout) ===
        GameObject videoObj = new GameObject("VideoDisplay");
        videoObj.transform.SetParent(gameAreaPanel.transform, false);
        
        RectTransform videoRect = videoObj.AddComponent<RectTransform>();
        // Remplir tout le conteneur
        videoRect.anchorMin = Vector2.zero;
        videoRect.anchorMax = Vector2.one;
        videoRect.sizeDelta = Vector2.zero;
        videoRect.anchoredPosition = Vector2.zero;
        
        // Créer la RawImage pour afficher la RenderTexture
        videoDisplay = videoObj.AddComponent<RawImage>();
        videoDisplay.texture = videoRenderTexture;
        videoDisplay.raycastTarget = true;
        videoDisplay.color = Color.white;
        
        Debug.Log($"[ShootingGameLayout] ✅ VideoDisplay créé avec coins arrondis ({gameAreaCornerRadius}px):");
        Debug.Log($"  - RenderTexture: {(videoRenderTexture != null ? $"{videoRenderTexture.width}x{videoRenderTexture.height}" : "NULL")}");
        Debug.Log($"  - Taille: {contentWidth}x{gameAreaHeight}");
        Debug.Log($"  - Position: centre, {bottomMargin}px du bas");
    }
    
    void AddRoundedCorners(GameObject target, float radius)
    {
        RoundedCornersImage roundedCorners = target.GetComponent<RoundedCornersImage>();
        if (roundedCorners == null)
        {
            roundedCorners = target.AddComponent<RoundedCornersImage>();
        }
        roundedCorners.cornerRadius = radius;
    }
    
    /// <summary>
    /// Configure le VideoPlayer pour utiliser la RenderTexture du layout
    /// </summary>
    public void ConfigureVideoPlayer(VideoPlayer videoPlayer)
    {
        if (videoPlayer == null || videoRenderTexture == null)
        {
            Debug.LogError("[ShootingGameLayout] VideoPlayer ou RenderTexture null!");
            return;
        }
        
        // IMPORTANT: Forcer le mode RenderTexture et désactiver tout autre mode
        videoPlayer.renderMode = VideoRenderMode.RenderTexture;
        videoPlayer.targetTexture = videoRenderTexture;
        videoPlayer.targetCamera = null; // Pas de rendu caméra
        videoPlayer.targetCameraAlpha = 0f;
        
        // IMPORTANT: Étirer la vidéo pour remplir toute la zone (évite les bandes noires)
        videoPlayer.aspectRatio = VideoAspectRatio.Stretch;
        
        // Désactiver tout Renderer qui pourrait afficher la vidéo sur un mesh
        Renderer videoRenderer = videoPlayer.GetComponent<Renderer>();
        if (videoRenderer != null)
        {
            videoRenderer.enabled = false;
            Debug.Log("[ShootingGameLayout] ⚠️ Renderer du VideoPlayer désactivé");
        }
        
        // Désactiver aussi les Renderers enfants
        Renderer[] childRenderers = videoPlayer.GetComponentsInChildren<Renderer>();
        foreach (Renderer r in childRenderers)
        {
            r.enabled = false;
        }
        
        Debug.Log($"[ShootingGameLayout] VideoPlayer configuré pour RenderTexture: {videoRenderTexture.width}x{videoRenderTexture.height}");
    }
    
    public void SetQuestionText(string text)
    {
        if (questionText != null)
        {
            questionText.text = text;
            // Réappliquer le style pour s'assurer que la couleur est correcte
            ApplyQuestionStyling();
            questionText.ForceMeshUpdate();
            Debug.Log($"[ShootingGameLayout] SetQuestionText - couleur: {questionText.color}");
        }
    }
    
    /// <summary>
    /// Définit l'URL du backdrop (image d'habillage à l'extérieur de la zone de jeu)
    /// </summary>
    /// <param name="url">URL du backdrop</param>
    /// <param name="fromApi">True si appelé depuis l'API (prioritaire)</param>
    public void SetBackdropUrl(string url, bool fromApi = false)
    {
        // Si le backdrop a déjà été défini par l'API, ignorer les autres sources
        if (backdropSetByApi && !fromApi)
        {
            Debug.Log($"[ShootingGameLayout] ⏭️ Backdrop ignoré (déjà défini par l'API): {url}");
            return;
        }
        
        if (fromApi)
        {
            backdropSetByApi = true;
            Debug.Log($"[ShootingGameLayout] 🎯 Backdrop défini par l'API: {url}");
        }
        
        // Si URL vide, considérer comme chargé
        if (string.IsNullOrEmpty(url))
        {
            backdropLoadingComplete = true;
            if (fromApi) backdropSetByApi = true;
            return;
        }
        
        backdropUrl = url;
        if (gameObject.activeInHierarchy && !string.IsNullOrEmpty(url))
        {
            StartCoroutine(LoadBackdropImageAsync());
        }
    }
    
    /// <summary>
    /// Alias pour compatibilité avec l'ancien code
    /// </summary>
    public void SetBackgroundImageUrl(string url)
    {
        SetBackdropUrl(url);
    }
    
    public Vector2 GetGameAreaSize()
    {
        return new Vector2(contentWidth, gameAreaHeight);
    }
    
    public Vector2 GetHeaderSize()
    {
        return new Vector2(contentWidth, headerHeight);
    }
    
    /// <summary>
    /// Obtient les limites de la zone de jeu en coordonnées ÉCRAN (pixels, origine bas-gauche)
    /// </summary>
    public Rect GetGameAreaScreenBounds()
    {
        // Ratio entre l'écran réel et la résolution de référence
        float screenScaleX = Screen.width / screenWidth;
        float screenScaleY = Screen.height / screenHeight;
        
        // Position et taille en pixels écran
        float x = ((screenWidth - contentWidth) / 2f) * screenScaleX;
        float y = bottomMargin * screenScaleY;
        float width = contentWidth * screenScaleX;
        float height = gameAreaHeight * screenScaleY;
        
        return new Rect(x, y, width, height);
    }
    
    /// <summary>
    /// Obtient les limites de la zone de jeu en coordonnées Canvas (référence 1920x1080, bas-gauche)
    /// </summary>
    public Rect GetGameAreaBoundsInCanvas()
    {
        float x = (screenWidth - contentWidth) / 2f; // = 220
        float y = bottomMargin; // = 40
        return new Rect(x, y, contentWidth, gameAreaHeight);
    }
    
    /// <summary>
    /// Convertit des coordonnées JSON (0-1920, 0-1080, origine HAUT-GAUCHE) 
    /// vers des coordonnées Canvas (origine BAS-GAUCHE) dans la zone de jeu
    /// </summary>
    public Vector2 ConvertJsonToCanvasPosition(float jsonX, float jsonY)
    {
        // Ratio de conversion JSON (1920x1080) vers zone de jeu (1480x835)
        float scaleX = contentWidth / screenWidth;    // 1480/1920 = 0.7708
        float scaleY = gameAreaHeight / screenHeight; // 835/1080 = 0.7731
        
        // Convertir vers coordonnées zone de jeu
        float gameAreaX = jsonX * scaleX;
        float gameAreaY = jsonY * scaleY;
        
        // Inverser Y (JSON: haut-gauche, Canvas: bas-gauche) et ajouter offset de la zone de jeu
        float canvasX = (screenWidth - contentWidth) / 2f + gameAreaX;
        float canvasY = bottomMargin + (gameAreaHeight - gameAreaY);
        
        return new Vector2(canvasX, canvasY);
    }
    
    /// <summary>
    /// Convertit une taille JSON vers une taille dans la zone de jeu
    /// </summary>
    public Vector2 ConvertJsonToCanvasSize(float jsonWidth, float jsonHeight)
    {
        float scaleX = contentWidth / screenWidth;
        float scaleY = gameAreaHeight / screenHeight;
        return new Vector2(jsonWidth * scaleX, jsonHeight * scaleY);
    }
    
    /// <summary>
    /// Convertit des coordonnées Canvas (bas-gauche) vers des coordonnées JSON (haut-gauche)
    /// Retourne (-1, -1) si le point est hors de la zone de jeu
    /// </summary>
    public Vector2 ConvertCanvasToJsonPosition(float canvasX, float canvasY)
    {
        Rect gameArea = GetGameAreaBoundsInCanvas();
        
        // Vérifier si le point est dans la zone de jeu
        if (canvasX < gameArea.x || canvasX > gameArea.x + gameArea.width ||
            canvasY < gameArea.y || canvasY > gameArea.y + gameArea.height)
        {
            return new Vector2(-1, -1); // Hors zone
        }
        
        // Convertir vers coordonnées relatives à la zone de jeu
        float relativeX = canvasX - gameArea.x;
        float relativeY = canvasY - gameArea.y;
        
        // Ratio de conversion zone de jeu (1480x835) vers JSON (1920x1080)
        float scaleX = screenWidth / contentWidth;
        float scaleY = screenHeight / gameAreaHeight;
        
        // Convertir et inverser Y
        float jsonX = relativeX * scaleX;
        float jsonY = (gameAreaHeight - relativeY) * scaleY;
        
        return new Vector2(jsonX, jsonY);
    }
    
    /// <summary>
    /// Dimensions de référence de la zone de jeu
    /// </summary>
    public float GameAreaWidth => contentWidth;  // 1480
    public float GameAreaHeight => gameAreaHeight; // 835
    public float ScreenWidth => screenWidth;     // 1920
    public float ScreenHeight => screenHeight;   // 1080
    
    /// <summary>
    /// Convertit des coordonnées JSON (0-1920, 0-1080) vers les coordonnées de la zone de jeu (0-1480, 0-835)
    /// </summary>
    public Vector2 ConvertJsonToGameAreaCoordinates(Vector2 jsonCoords, int jsonWidth = 1920, int jsonHeight = 1080)
    {
        // Les coordonnées JSON sont relatives à l'écran complet
        // On doit les convertir pour être relatives à la zone de jeu
        
        // Ratio de conversion
        float scaleX = contentWidth / (float)jsonWidth;
        float scaleY = gameAreaHeight / (float)jsonHeight;
        
        // Convertir (les coordonnées JSON ont l'origine en haut-gauche, on les convertit en bas-gauche)
        float gameAreaX = jsonCoords.x * scaleX;
        float gameAreaY = (jsonHeight - jsonCoords.y) * scaleY; // Inverser Y
        
        return new Vector2(gameAreaX, gameAreaY);
    }
    
    void OnDestroy()
    {
        if (Instance == this)
        {
            Instance = null;
        }
        
        if (loadedBackgroundTexture != null)
        {
            Destroy(loadedBackgroundTexture);
        }
        
        if (videoRenderTexture != null)
        {
            videoRenderTexture.Release();
            Destroy(videoRenderTexture);
        }
    }
}
