using UnityEngine; using System.Collections.Generic; using System.Linq; namespace Core { public enum UILayer { Background, Normal, Popup, Top } /// /// 单例UI管理者,控制UI的层级关系,UI的开关 /// public class UIManager : MonoSingleton { public bool IsHasNonBackgroundUIActive { get { return openedUIs.Values.Any(ui => ui.gameObject.activeSelf && ui.transform.parent != layerRoots[UILayer.Background]); } } private Dictionary layerRoots = new Dictionary(); private Dictionary openedUIs = new Dictionary(); private IInputManager inputManager; public void RegisterInputManager(IInputManager inputMgr) { inputManager = inputMgr; } public void RegisterLayer(UILayer layer, Transform root) { if (!layerRoots.ContainsKey(layer)) { layerRoots[layer] = root; // 注册场景中已存在的UI // 遍历子对象 foreach (Transform child in root) { var uiName = child.gameObject.name; UIBase uiBase = child.GetComponent(); if (uiBase != null && !openedUIs.ContainsKey(uiName)) { openedUIs[uiName] = uiBase; uiBase.Hide(); // 默认关闭 if (uiBase.IsOpenOnFirstLoad) { uiBase.Show(); } } } } } public T OpenUI(UILayer layer = UILayer.Normal) where T : Component { string uiName = typeof(T).Name; if (openedUIs.ContainsKey(uiName)) { openedUIs[uiName].Show(); UpdateCursorState(); return openedUIs[uiName] as T; } // 加载UI预制体 GameObject prefab = Resources.Load("UI/" + uiName); // 从 Resources/UI 文件夹加载UI预制体 if (prefab == null) { Debug.LogError("UI Prefab not found: " + uiName); return null; } GameObject uiObj = Instantiate(prefab, layerRoots[layer]); // 实例化并设置父对象 UIBase uiBase = uiObj.GetComponent(); // 获取UIBase组件 openedUIs[uiName] = uiBase; // 注册到字典中 uiBase.Show(); // 显示UI UpdateCursorState(); // 更新鼠标状态 return uiBase as T; } public void CloseUI() where T : Component { string uiName = typeof(T).Name; if (openedUIs.ContainsKey(uiName)) { openedUIs[uiName].Hide(); UpdateCursorState(); } } // 来回切换UI状态,按同一个键实现UI的开关 public void SwitchUI(UILayer layer = UILayer.Normal) where T : Component { string uiName = typeof(T).Name; if (openedUIs.ContainsKey(uiName) && openedUIs[uiName].gameObject.activeSelf) { CloseUI(); } else { OpenUI(layer); } } public Dictionary> GetExistingUIsByLayer() { var result = new Dictionary>(); foreach (var kvp in layerRoots) { var layer = kvp.Key; var root = kvp.Value; var uiList = new List(); foreach (Transform child in root) { UIBase uiBase = child.GetComponent(); if (uiBase != null) uiList.Add(uiBase.gameObject); } result[layer] = uiList; } return result; } private void UpdateCursorState() { if(inputManager == null) return; bool shouldLockCursor = !IsHasNonBackgroundUIActive; //&& !isInMainMenu; // 仅在没有非Background UI且不在主菜单时锁定鼠标 if (shouldLockCursor) { inputManager.SetCursorState(false, CursorLockMode.Locked); } else { inputManager.SetCursorState(true, CursorLockMode.None); } inputManager.SetInputForLook(shouldLockCursor); inputManager.SetInputForMove(shouldLockCursor); } } }