using FirstVillain.Singleton; using System; using System.Collections.Generic; using UnityEngine.Events; namespace FirstVillain.EventBus { public class EventBus : UnitySingleton { private readonly Dictionary _delegateDict = new Dictionary(); private readonly Dictionary _delegateLookupDict = new Dictionary(); public delegate void EventDelegate(T myEvent) where T : EventBase; private delegate void EventDelegate(EventBase myEvent); public void Subscribe(EventDelegate callback) where T : EventBase { EventDelegate newDelegate = e => callback(e as T); _delegateLookupDict[callback] = newDelegate; var type = typeof(T); if (!_delegateDict.TryGetValue(type, out EventDelegate tempDeletage)) { _delegateDict[type] = tempDeletage; } _delegateDict[type] += newDelegate; } public void Unsubscribe(EventDelegate callback) where T : EventBase { if (_delegateLookupDict.TryGetValue(callback, out EventDelegate targetDelegate)) { var type = typeof(T); if (_delegateDict.TryGetValue(type, out EventDelegate tempDelegate)) { tempDelegate -= targetDelegate; if (tempDelegate == null) { _delegateDict.Remove(type); } else { _delegateDict[type] = tempDelegate; } } _delegateLookupDict.Remove(callback); } } public void Publish(EventBase eventType) { if (_delegateDict.TryGetValue(eventType.GetType(), out EventDelegate callback)) { callback.Invoke(eventType); } } public void Clear() { _delegateDict.Clear(); _delegateLookupDict.Clear(); } } public class EventBase { private int _errorCode; public int ErrorCode { get { return _errorCode; } set { _errorCode = value; } } } }