using System.Collections; using Data.ScriptableObjects; using FishNet.Object; using FishNet.Object.Synchronizing; using Managers.Item; using Types; using Types.Items; using Types.UI; using UnityEditor; using UnityEngine; namespace Managers { // Manages a INSTANCE of a single player. public class PlayerManager : NetworkBehaviour { [SerializeField] private InventoryManager inventoryManager; [SerializeField] private ToolbarManager toolbarManager; [SerializeField] private EquipmentManager equipmentManager; [SerializeField] private GameObject playerGo; [SerializeField] private Camera playerCamera; [SerializeField] private NetworkObject gameManagerPrefab; [SerializeField] private GameManager gameManager; private readonly SyncVar _playerData = new(new SyncTypeSettings(1f)); private void Awake() { _playerData.OnChange += playerData_OnChange; } public void playerData_OnChange(GamePlayer prev, GamePlayer next, bool asServer) { Debug.Log("PlayerData changed:"); if (prev != null) Debug.Log($"PlayerData changed PREV: {prev.ID} {prev.PlayerName} {asServer}"); if (next != null) Debug.Log($"PlayerData changed NEXT: {next.ID} {next.PlayerName} {asServer}"); } public override void OnStartServer() { base.OnStartServer(); if (gameManager == null) gameManager = FindObjectOfType(); if (gameManager == null) { Debug.Log("GameManager not found"); GameInit.Instance.InitializeGameManager(); gameManager = FindObjectOfType(); } } [ServerRpc] public void SpawnGameManager() { var gameManagerGo = Instantiate(gameManagerPrefab, transform.position, Quaternion.identity); Spawn(gameManagerGo); gameManager = gameManagerGo.GetComponent(); if (gameManager == null) Debug.LogError("GameManager not found"); } [ObserversRpc] public void SpawnGameManagerClient(GameManager gameManager) { this.gameManager = gameManager; } private IEnumerator WaitForClientActiveAndRegister() { while (!IsClientInitialized) { Debug.Log("Waiting for client to be initialized"); yield return null; } Debug.Log("Client is Ready to RegisterPlayer"); if (Owner == null) Debug.LogError("OwnerConnection not found"); if (gameManager == null) gameManager = FindObjectOfType(); Debug.Log("GameManager should be found"); GameManager.Instance.RegisterPlayerServerRpc(Owner, _playerData.Value); } public override void OnStartClient() { base.OnStartClient(); if (gameManager == null) { Debug.Log("Trying to find GameManager"); GameInit.Instance.InitializeGameManager(); gameManager = FindObjectOfType(); if (gameManager == null) { Debug.LogError("GameManager not found"); return; } if (gameManager) Debug.Log("GameManager found"); } if (IsOwner) { if (_playerData.Value == null) { Debug.LogWarning("PlayerData not found"); // load a scriptable objects default player data var playerData = AssetDatabase.LoadAssetAtPath("Assets/Resources/DefaultPlayer.asset"); _playerData.Value = new GamePlayer(playerData) { PlayerName = "Default Player" }; } InitializeManager(); Debug.Log("PlayerManager RegisterPlayer"); if (Owner == null) Debug.LogError("OwnerConnection not found"); StartCoroutine(WaitForClientActiveAndRegister()); // gameManager.RegisterPlayerServerRpc(Owner, this); // gameManager.AddPlayer(this); LocalPlayerManager.Instance = this; } else { // disables other peoples character controls. gameObject.GetComponent().enabled = false; gameObject.GetComponent().enabled = false; } } // should only run on the server, NOT clients [ServerRpc] public void InitializeManager() { inventoryManager = playerGo.AddComponent(); toolbarManager = playerGo.AddComponent(); equipmentManager = playerGo.AddComponent(); inventoryManager.Initialize(_playerData.Value); toolbarManager.Initialize(_playerData.Value); equipmentManager.Initialize(_playerData.Value); } // gets manager by slot type public IItemManager GetManagerBySlotType(SlotType slotType) { switch (slotType) { case SlotType.Inventory: Debug.Log("Getting Inventory Manager"); return inventoryManager; case SlotType.Toolbar: Debug.Log("Getting Toolbar Manager"); return toolbarManager; case SlotType.Equipment: Debug.Log("Getting Equipment Manager"); return equipmentManager; case SlotType.Box: Debug.Log("Getting Box Manager"); return BoxManager.Instance; case SlotType.Crafting: break; case SlotType.Shop: break; case SlotType.Quest: break; default: return null; } return null; } public GameSlot GetSlot(SlotType slotType, int slotId) { Debug.Log("Getting SlotType " + slotType + " / " + slotId); var manager = GetManagerBySlotType(slotType); if (manager == null) Debug.LogError("Manager not found"); return manager.GetSlot(slotId); } // Load save data public GameSlot GetActiveToolbarSlot() { return toolbarManager.GetActiveToolbarSlot(); } [Server] public void Initialize(GamePlayer data) { Debug.Log("Initializing PlayerManager"); _playerData.Value = data; inventoryManager.Initialize(data); toolbarManager.Initialize(data); equipmentManager.Initialize(data); } public InventoryManager GetInventoryManager() { if (inventoryManager != null) return inventoryManager; inventoryManager = playerGo.AddComponent(); inventoryManager.Initialize(_playerData.Value); return inventoryManager; } public ToolbarManager GetToolbarManager() { if (toolbarManager != null) return toolbarManager; return toolbarManager; } public EquipmentManager GetEquipmentManager() { if (equipmentManager != null) return equipmentManager; return equipmentManager; } public void AddItemToInventorySlot(GameItem item, int slotId) { // inventoryManager.AddItemToSlot(item, slotId); } [ServerRpc] public void AddItemToInventory(GameItem item) { // inventoryManager.AddItemToOpenSlot(item); } public GamePlayer GetPlayerData() { return _playerData.Value; } [ServerRpc] public void SetPlayerData(GamePlayer pd) { _playerData.Value = pd; } } }