// Assets/_Project/Scripts/UI/FloatingTextSpawner.cs
using UnityEngine;

namespace TD.UI
{
    /// <summary>
    /// Scene singleton that spawns <see cref="FloatingText"/> instances above
    /// world positions for gold-reward and life-loss feedback.
    /// </summary>
    /// <remarks>
    /// <b>Why a singleton:</b> the spawner is shared by every caller (kills, leaks,
    /// future status pop-ups) and holds inspector-tunable colors and a prefab
    /// reference. Plain <c>MonoBehaviour</c> — visual-only, no networking required.
    ///
    /// <b>Who calls this:</b> <see cref="TD.Gameplay.WaveManager"/> invokes
    /// <see cref="SpawnGoldReward"/> and <see cref="SpawnLifeLoss"/> via ClientRpc
    /// so every peer shows the popup locally.
    ///
    /// <b>Inspector setup:</b> drop this on any scene GameObject (e.g. a
    /// <c>FloatingTextSpawner</c> empty), assign the floating-text prefab, tune
    /// colors to match the HUD.
    /// </remarks>
    public class FloatingTextSpawner : MonoBehaviour
    {
        // ----- Singleton --------------------------------------------------

        public static FloatingTextSpawner Instance { get; private set; }

        // ----- Inspector --------------------------------------------------

        [Tooltip("Prefab to instantiate for each pop-up. Must have a FloatingText " +
                 "component and a TextMeshPro renderer.")]
        [SerializeField] private FloatingText prefab;

        [Tooltip("Color used for kill-reward gold pop-ups. Tune to match the HUD's " +
                 "gold label color.")]
        [SerializeField] private Color goldColor = new Color(1f, 0.84f, 0.2f);

        [Tooltip("Color used for life-loss pop-ups (enemies reaching the goal).")]
        [SerializeField] private Color livesColor = new Color(0.95f, 0.25f, 0.25f);

        [Tooltip("Default vertical offset above the source position. Tunes how high " +
                 "above the enemy the text starts.")]
        [SerializeField] private float verticalOffset = 2.0f;

        [Tooltip("Maximum random horizontal jitter applied to the spawn position so " +
                 "consecutive pop-ups don't stack visually.")]
        [SerializeField] private float positionJitter = 0.4f;

        [Tooltip("Maximum random vertical jitter applied on top of verticalOffset.")]
        [SerializeField] private float verticalJitter = 0.2f;

        // ----- Lifecycle --------------------------------------------------

        private void Awake()
        {
            if (Instance != null && Instance != this)
            {
                Debug.LogWarning("[FloatingTextSpawner] Duplicate instance detected. " +
                                 "Only one should exist per scene.");
                return;
            }
            Instance = this;
        }

        private void OnDestroy()
        {
            if (Instance == this) Instance = null;
        }

        // ----- Public API -------------------------------------------------

        /// <summary>Spawns a gold-reward popup (e.g. "+10") at the given world position.</summary>
        public void SpawnGoldReward(Vector3 worldPos, int amount)
            => SpawnInternal(worldPos, $"+{amount}", goldColor);

        /// <summary>Spawns a life-loss popup (e.g. "-1") at the given world position.</summary>
        public void SpawnLifeLoss(Vector3 worldPos, int amount)
            => SpawnInternal(worldPos, $"-{amount}", livesColor);

        /// <summary>Lower-level overload: arbitrary content and color.</summary>
        public void SpawnCustom(Vector3 worldPos, string text, Color color)
            => SpawnInternal(worldPos, text, color);

        // ----- Internal ---------------------------------------------------

        private void SpawnInternal(Vector3 worldPos, string text, Color color)
        {
            if (prefab == null)
            {
                Debug.LogWarning("[FloatingTextSpawner] No prefab assigned. " +
                                 "Pop-up will not be shown.");
                return;
            }

            Vector3 jitter = new Vector3(
                Random.Range(-positionJitter, positionJitter),
                Random.Range(0f, verticalJitter),
                Random.Range(-positionJitter, positionJitter));

            Vector3 spawnPos = worldPos + Vector3.up * verticalOffset + jitter;

            var instance = Instantiate(prefab, spawnPos, Quaternion.identity);
            instance.Init(text, color);
        }
    }
}
