using UnityEngine;
using UnityEngine.UI;
using UnityEngine.InputSystem;
using RR.Game2D.Core.Managers;
namespace RR.Common.UI
{
///
/// Меню паузы. Наследуется от Modal для автоматического управления фокусом.
/// Открывается/закрывается через GameManager.PauseStateChanged.
///
public class PauseMenu : Modal
{
[Header("Управление паузой")]
[SerializeField] private InputActionReference pauseToggle;
[Header("Кнопки меню")]
[SerializeField] private Button resumeButton;
[SerializeField] private Button quitButton;
[Header("Связь с другими элементами")]
[SerializeField] private GameEndUIController bannerController;
///
/// Флаг активности меню. Деактивируется когда показан баннер проигрыша/победы.
///
public bool IsActive { get; private set; } = true;
protected override void Awake()
{
// Настраиваем обработчики кнопок
if (resumeButton) resumeButton.onClick.AddListener(OnResumeClicked);
if (quitButton) quitButton.onClick.AddListener(OnQuitClicked);
if (pauseToggle) pauseToggle.action.performed += OnPauseToggle;
// Устанавливаем первый выбранный элемент
SetFirstSelected(resumeButton);
if (GameManager.Instance != null)
GameManager.Instance.PauseStateChanged += HandlePauseChanged;
if (bannerController)
{
bannerController.WinBannerShown += _ => { IsActive = false; };
bannerController.LoseBannerShown += _ => { IsActive = false; };
bannerController.BannerDismissed += () => { IsActive = true; };
}
// Изначально скрыто - не вызываем base.Awake(), делаем это вручную
gameObject.SetActive(false);
}
private void OnPauseToggle(InputAction.CallbackContext ctx)
{
// Блокируем паузу если меню неактивно (например, показан баннер проигрыша/победы)
if (!IsActive) return;
// Блокируем паузу если открыто любое другое модальное окно
if (!_isOpen && IsAnyOtherModalOpen()) return;
GameManager.Instance.TogglePause();
}
private void OnDestroy()
{
if (pauseToggle) pauseToggle.action.performed -= OnPauseToggle;
if (GameManager.Instance != null)
GameManager.Instance.PauseStateChanged -= HandlePauseChanged;
}
///
/// Обработка события паузы от GameManager.
///
private void HandlePauseChanged(bool paused)
{
if (!IsActive) return;
// Не показываем меню паузы, если открыто другое модальное окно
if (paused && IsAnyOtherModalOpen()) return;
if (paused)
Open();
else
Close();
}
///
/// Проверяет, открыто ли какое-либо модальное окно, кроме самого PauseMenu.
///
private bool IsAnyOtherModalOpen()
{
var mm = ModalManager.Instance;
if (mm == null) return false;
// Если открытых окон нет — точно нет других
if (!mm.HasOpenModals) return false;
// Если текущее окно — мы сами, значит других нет
if (mm.CurrentModal == this) return false;
return true;
}
///
/// Переопределяем Close, чтобы при закрытии также снимать паузу.
///
public override void Close()
{
// Блокируем закрытие если меню неактивно (показан баннер)
if (!IsActive) return;
base.Close();
// Если игра ещё на паузе, снимаем её
if (GameManager.Instance != null && GameManager.Instance.IsPaused)
{
GameManager.Instance.SetPause(false);
}
}
///
/// Метод для возобновления игры.
///
public static void OnResumeClicked()
{
// Блокируем если меню неактивно (показан баннер)
var pauseMenu = FindFirstObjectByType();
if (pauseMenu != null && !pauseMenu.IsActive) return;
GameManager.Instance.TogglePause();
}
///
/// Метод для выхода в главное меню.
///
public void OnQuitClicked()
{
GameManager.Instance.SetPause(false);
GameManager.Instance.LoadScene("MainMenu", false);
}
}
}