DialogueEvent无法将DialogueEventListener注册到监听器列表问题求助
对话系统事件注册问题排查与解决
我正在开发带事件机制的对话系统,现有DialogueEvent和DialogueEventListener类代码如下。将DialogueEventListener挂载到GameObject后,其引用的DialogueEvent ScriptableObject(SO)未成功注册监听器,手动添加也无效,把注册逻辑移到Awake里同样没用。现在因为空引用错误(NRE)导致对话系统无法运行。
现有代码
DialogueEvent 类
using System.Collections; using System.Collections.Generic; using UnityEngine; namespace Assets.Scripts.Dialogue { [CreateAssetMenu(menuName = "ScriptableObjects/GameEvent/DialogueEvent")] public class DialogueEvent : ScriptableObject { public List<DialogueEventListener> listeners = new List<DialogueEventListener>(); // Raise event through different methods public void Raise(Component sender, object data) { for(int i = 0; i < listeners.Count; i++) { listeners[i].OnEventRaised(sender, data); } } // Manage Listeners public void RegisterListener(DialogueEventListener dialogueEventListener) { if(!listeners.Contains(dialogueEventListener)) { listeners.Add(dialogueEventListener); } } public void UnregisterListener(DialogueEventListener dialogueEventListener) { if(listeners.Contains(dialogueEventListener)) { listeners.Remove(dialogueEventListener); } } } }
DialogueEventListener 类
using System.Collections; using UnityEngine; using UnityEngine.Events; namespace Assets.Scripts.Dialogue { public class DialogueEventListener : MonoBehaviour { // EVENT VARIABLES [SerializeField] private DialogueEvent dialogueEvent; [SerializeField] private CustomDialogueEvent response; public DialogueEvent DialogueEvent { get => dialogueEvent; set => dialogueEvent = value; } public CustomDialogueEvent Response { get => response; set => response = value; } // FUNCTIONS private void OnEnable() { dialogueEvent.RegisterListener(this); } private void OnDisable() { dialogueEvent.UnregisterListener(this); } public void OnEventRaised(Component sender, object data) { response.Invoke(sender, data); } } }
解决步骤
- 检查SO引用有效性:在Inspector面板中确认
DialogueEventListener组件的dialogueEvent字段已正确拖入对应的DialogueEventScriptableObject实例,未留空。 - 添加空引用防护:修改
OnEnable和OnDisable方法,避免空引用错误中断注册流程:private void OnEnable() { if (dialogueEvent != null) { dialogueEvent.RegisterListener(this); } } private void OnDisable() { if (dialogueEvent != null) { dialogueEvent.UnregisterListener(this); } } - 验证注册逻辑:在
DialogueEvent的RegisterListener方法中添加日志,确认注册流程是否执行:public void RegisterListener(DialogueEventListener dialogueEventListener) { if (!listeners.Contains(dialogueEventListener)) { listeners.Add(dialogueEventListener); Debug.Log($"监听器 {dialogueEventListener.gameObject.name} 已注册到事件 {name}"); } else { Debug.Log($"监听器 {dialogueEventListener.gameObject.name} 已存在于事件 {name} 的监听列表中"); } } - 重新创建SO实例:若原
DialogueEventSO存在异常,尝试创建新的SO实例并重新赋值给DialogueEventListener。 - 检查响应事件引用:确认
DialogueEventListener的response字段(CustomDialogueEvent)也已正确赋值,避免后续触发事件时出现空引用。
内容的提问来源于stack exchange,提问作者Vivek Kilari
相关产品推荐
相关产品推荐

