using Nox.Core;
using Nox.Game;
using Jovian.SaveSystem;
using UnityEngine;
using UnityEngine.AddressableAssets;
using UnityEngine.ResourceManagement.AsyncOperations;
using PlayMode = Nox.Core.PlayMode;

namespace Nox.UI {
    /// <summary>
    /// Main menu interface class which is responsible for creating the main menu view and handling the main menu events
    /// </summary>
    public class MainMenuView : IGameLifecycle {
        private readonly MenuPrefabsContainer menuPrefabsContainer;
        private readonly MenuGameStateData menuGameStateData;
        private readonly ISaveSystem saveSystem;
        private MainMenuReference mainMenuReference;
        private CharacterCreationReference characterCreationReference;
        private CharacterCreationView characterCreationView;
        private AsyncOperationHandle<GameObject> charCreationHandle;

        public MainMenuView(MenuPrefabsContainer menuPrefabsContainer, MenuGameStateData menuGameStateData, ISaveSystem saveSystem) {
            this.menuPrefabsContainer = menuPrefabsContainer;
            this.menuGameStateData = menuGameStateData;
            this.saveSystem = saveSystem;
        }
        public void Initialize() {
            if(mainMenuReference == null) {
                mainMenuReference = Addressables.InstantiateAsync(menuPrefabsContainer.mainMenuReference).WaitForCompletion().GetComponent<MainMenuReference>();
            }
            mainMenuReference.exitButton.onClick.AddListener(Application.Quit);
            mainMenuReference.optionsButton.onClick.AddListener(() => {/* options logic here */});
            mainMenuReference.newGameButton.onClick.AddListener(InitializeCharacterCreation);

            bool hasSave = saveSystem.HasAnySaves();
            mainMenuReference.continueButton.gameObject.SetActive(hasSave);
            if(hasSave) {
                mainMenuReference.continueButton.onClick.AddListener(() => menuGameStateData.continueGameRequest.Invoke());
            }
        }

        public void InitializeCharacterCreation() {
            charCreationHandle = Addressables.InstantiateAsync(menuPrefabsContainer.characterCreationReference);
            charCreationHandle.Task.ContinueWith(t => {
                if(t.IsFaulted) {
                    Debug.LogError(t.Exception);
                }
                characterCreationReference =t.Result.GetComponent<CharacterCreationReference>();
                characterCreationView = new CharacterCreationView(characterCreationReference, menuGameStateData);
                characterCreationView.Show();
            });
        }

        public void Tick() {
            characterCreationView?.Tick();
        }

        public void Dispose() {
            characterCreationView?.Dispose();
            Object.Destroy(characterCreationReference.gameObject);
            charCreationHandle.Release();
        }
    }
}
