9.管理器基类和GameRoot

管理器基类和GameRoot

管理器基类

为管理器创建基类和管理器单例。

    public abstract class ManagerBase : MonoBehaviour
    {
        public virtual void Init() { }
    }

    public abstract class ManagerBase<T> : ManagerBase where T : ManagerBase<T>
    {
        public static T Instance;

        /// <summary>
        /// 管理器的初始化
        /// </summary>
        public override void Init()
        {
            Instance = this as T;
        }
    }

这里可以发现在ManagerBase单例类上又包了一层ManagerBase,其目的就在与对不同的管理器单例进行一层包装,这样统一方便在GameRoot中用数组进行统一存储(不必关系具体T是哪一类管理器),ManagerBase实际是所有管理器类的爷爷类。

              ManagerBase[] managers = GetComponents<ManagerBase>();

这种思想在事件系统中也有类似体现,对不同参数个数的事件类进行一层接口封装,方便Dictionary进行存储,稍有区别在于事件系统中事件类型只存数据可以使用接口进行封装,而管理器由于需要继承Mono所以用抽象类进行封装(接口不能继承Mono类,也可以爷爷接口,父亲继承Mono)。 alt

GameRoot

使用GameRoot控制管理器的初始化顺序。

         protected override void Awake()
        {
            if (Instance != null)
            {
                Destroy(gameObject);
                return;
            }
            base.Awake();
            DontDestroyOnLoad(gameObject);

            // 初始化所有管理器
            InitManager();
        }

        private void InitManager()
        {
            ManagerBase[] managers = GetComponents<ManagerBase>();
            for (int i = 0; i < managers.Length; i++)
            {
                managers[i].Init();
            }
        }

对于GameRoot游戏根节点,其作为游戏运行的核心,挂载了许多功能脚本,应该是全局唯一且跨场景不销毁的,所以首先要判断当前是否存在GameRoot单例,存在那说明自己是多余的,把自己销毁并return,如果当前没有GameRoot单例(进入游戏第一个场景),需要调用父类的Awake方法完成单例实例化,再去调用InitManager对所有管理器类进行初始化,这样确保GameRoot第一个被加载且可以在这里自定义控制管理器类初始化顺序。

Unity独立游戏开发

全部评论

相关推荐

2024-12-11 11:40
海南大学 Java
点赞 评论 收藏
分享
2024-12-07 21:21
东北大学 Java
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客企业服务