using UnityEngine;

/// <summary>
/// Central game manager that controls game state, timer, score, and puck in play status.
/// </summary>
public class GameManager : MonoBehaviour
{
    public static GameManager Instance { get; private set; }

    [Header("Game Settings")]
    [SerializeField] private float periodDuration = 1200f; // 20:00 in seconds
    [SerializeField] private int totalPeriods = 3;

    [Header("Game State")]
    private int homeScore = 0;
    private int awayScore = 0;
    private int currentPeriod = 1;
    private float timeRemaining = 1200f; // Start at 20:00
    private bool isPuckInPlay = false;
    private bool isGameRunning = false;

    public bool IsPuckInPlay => isPuckInPlay;
    public bool IsGameRunning => isGameRunning;
    public int HomeScore => homeScore;
    public int AwayScore => awayScore;
    public int CurrentPeriod => currentPeriod;
    public float TimeRemaining => timeRemaining;

    // Events for UI updates
    public delegate void ScoreChangedHandler(int homeScore, int awayScore);
    public event ScoreChangedHandler OnScoreChanged;

    public delegate void TimeChangedHandler(float timeRemaining);
    public event TimeChangedHandler OnTimeChanged;

    public delegate void PeriodChangedHandler(int period);
    public event PeriodChangedHandler OnPeriodChanged;

    public delegate void PuckInPlayChangedHandler(bool inPlay);
    public event PuckInPlayChangedHandler OnPuckInPlayChanged;

    void Awake()
    {
        // Singleton pattern
        if (Instance == null)
        {
            Instance = this;
        }
        else
        {
            Destroy(gameObject);
            return;
        }
    }

    void Start()
    {
        timeRemaining = periodDuration;
        StartGame();
        
        Debug.Log("Game started. All players frozen by default. Press F to start faceoff.");
    }

    void Update()
    {
        if (isGameRunning && isPuckInPlay && timeRemaining > 0)
        {
            timeRemaining -= Time.deltaTime;
            
            if (timeRemaining <= 0)
            {
                timeRemaining = 0;
                EndPeriod();
            }

            OnTimeChanged?.Invoke(timeRemaining);
        }
    }

    public void StartGame()
    {
        isGameRunning = true;
        currentPeriod = 1;
        timeRemaining = periodDuration;
        homeScore = 0;
        awayScore = 0;
        
        OnScoreChanged?.Invoke(homeScore, awayScore);
        OnTimeChanged?.Invoke(timeRemaining);
        OnPeriodChanged?.Invoke(currentPeriod);
        
        Debug.Log("Game Started!");
    }

    public void SetPuckInPlay(bool inPlay)
    {
        if (isPuckInPlay != inPlay)
        {
            isPuckInPlay = inPlay;
            OnPuckInPlayChanged?.Invoke(isPuckInPlay);
            Debug.Log($"Puck in play: {isPuckInPlay}");
        }
    }

    public void AddHomeScore(int points = 1)
    {
        homeScore += points;
        OnScoreChanged?.Invoke(homeScore, awayScore);
        Debug.Log($"Home Team scores! {homeScore} - {awayScore}");
        
        // Stop play after goal
        SetPuckInPlay(false);
    }

    public void AddAwayScore(int points = 1)
    {
        awayScore += points;
        OnScoreChanged?.Invoke(homeScore, awayScore);
        Debug.Log($"Away Team scores! {homeScore} - {awayScore}");
        
        // Stop play after goal
        SetPuckInPlay(false);
    }

    private void EndPeriod()
    {
        SetPuckInPlay(false);
        isGameRunning = false;
        
        Debug.Log($"End of Period {currentPeriod}");

        if (currentPeriod < totalPeriods)
        {
            // Start next period
            currentPeriod++;
            timeRemaining = periodDuration;
            OnPeriodChanged?.Invoke(currentPeriod);
            OnTimeChanged?.Invoke(timeRemaining);
            
            // Game will resume after faceoff
            isGameRunning = true;
        }
        else
        {
            EndGame();
        }
    }

    private void EndGame()
    {
        Debug.Log($"Game Over! Final Score: {homeScore} - {awayScore}");
        
        if (homeScore > awayScore)
        {
            Debug.Log("Home Team Wins!");
        }
        else if (awayScore > homeScore)
        {
            Debug.Log("Away Team Wins!");
        }
        else
        {
            Debug.Log("Game is tied!");
        }
    }

    public void PauseGame()
    {
        isGameRunning = false;
    }

    public void ResumeGame()
    {
        isGameRunning = true;
    }

    public string GetFormattedTime()
    {
        int minutes = Mathf.FloorToInt(timeRemaining / 60f);
        int seconds = Mathf.FloorToInt(timeRemaining % 60f);
        return $"{minutes:00}:{seconds:00}";
    }
}
