using System.Collections.Generic; using UnityEngine; namespace Architecture.Core { /// /// 运行时集合:替代 FindObjectsOfType / 单例列表,零单例开销地跟踪场景实体。 /// 实体在 OnEnable 注册、OnDisable 注销(见下方 RuntimeSetRegistrar)。 /// 资产实例是项目级资源,跨场景存活,可安全被任何系统读取。 /// public abstract class RuntimeSet : ScriptableObject { public List Items = new List(); public void Add(T item) { if (item != null && !Items.Contains(item)) Items.Add(item); } public void Remove(T item) { if (item != null && Items.Contains(item)) Items.Remove(item); } public int Count => Items.Count; public T this[int i] => Items[i]; } /// /// 通用 Transform 集合,作为"当前场景实体"的轻量注册表(玩家、敌人等)。 /// 领域专用集合(如 EnemyRuntimeSet : RuntimeSet<EnemyAI>)放在对应领域文件夹, /// 继承本类即可,无需改动核心。 /// [CreateAssetMenu(menuName = "Architecture/Runtime Sets/Transform Set", fileName = "NewTransformSet")] public class TransformRuntimeSet : RuntimeSet { } /// /// 挂载到任意预制体,使其自动注册进指定 RuntimeSet。 /// 这样系统只需遍历集合,永不需要 GameObject.Find / FindObjectsOfType。 /// public class RuntimeSetRegistrar : MonoBehaviour { [SerializeField] private TransformRuntimeSet _set; private void OnEnable() { if (_set != null) _set.Add(transform); } private void OnDisable() { if (_set != null) _set.Remove(transform); } } /// /// 泛型注册器:领域专用强类型集合(如 EnemyRuntimeSet : RuntimeSet<EnemyAI>)使用。 /// 自动 GetComponent<T>() 并加入对应集合,避免用 Transform 集合再手动转型。 /// 因 Unity 对泛型 MonoBehaviour 需具体闭包类型才能挂载,领域文件夹内写一行具体子类即可: /// public class EnemySetRegistrar : RuntimeSetRegistrar<EnemyAI> { } /// public class RuntimeSetRegistrar : MonoBehaviour where T : Component { [SerializeField] private RuntimeSet _set; private void OnEnable() { if (_set != null) _set.Add(GetComponent()); } private void OnDisable() { if (_set != null) _set.Remove(GetComponent()); } } }