EventEmitter.ts 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596
  1. import { _decorator, Component, Node } from 'cc';
  2. import { Singleton } from '../manager/Singleton';
  3. const { ccclass, property } = _decorator;
  4. /*
  5. //注册事件
  6. EventEmitter.instance.register(this, "PLAYER_DEAD", (reason: string) => {
  7. console.log("~~:", reason);
  8. });
  9. //派发事件
  10. EventEmitter.instance.dispatch("PLAYER_DEAD", "被怪物击杀");
  11. //注销事件
  12. EventEmitter.instance.unregister(this, "PLAYER_DEAD");*/
  13. /**事件数据接口*/
  14. interface IEventData {
  15. func: Function; // 回调函数
  16. target: any; // 回调函数绑定的this对象
  17. }
  18. /**事件哈希表接口*/
  19. interface IEventHash {
  20. [eventType: string]: IEventData[]; //事件类型到事件数据数组的映射
  21. }
  22. @ccclass('EventEmitter')
  23. class EventEmitter extends Singleton {
  24. private eventHash: IEventHash = {};
  25. /**
  26. * 清空所有事件监听
  27. */
  28. public clearAll(): void {
  29. console.log("清空所有事件监听");
  30. this.eventHash = {};
  31. }
  32. /**
  33. * 注册事件监听
  34. * @param target 监听对象 (用于取消监听时识别)
  35. * @param type 事件类型
  36. * @param callback 回调函数
  37. */
  38. public register(target: any, type: string, callback: Function): void {
  39. if(!this.eventHash[type]) {
  40. this.eventHash[type] = [];
  41. }
  42. //检查是否已注册相同监听
  43. const exists = this.eventHash[type].some(
  44. event => event.func === callback && event.target === target
  45. );
  46. if(!exists) {
  47. this.eventHash[type].push({
  48. func: callback,
  49. target: target
  50. });
  51. }
  52. }
  53. /**
  54. * 注销事件监听
  55. * @param target 监听对象
  56. * @param type 事件类型
  57. */
  58. public unregister(target: any, type: string): void {
  59. const events = this.eventHash[type];
  60. if (events && events.length > 0) {
  61. for (let i = events.length - 1; i >= 0; i--) {
  62. if (events[i].target === target) {
  63. events.splice(i, 1);
  64. }
  65. }
  66. }
  67. }
  68. /**
  69. * 派发事件
  70. * @param type 事件类型
  71. * @param data 事件数据 (可变参数)
  72. */
  73. public dispatch(type: string, ...data: any[]): void {
  74. const events = this.eventHash[type];
  75. if (events && events.length > 0) {
  76. // 使用slice创建副本,防止在回调中修改数组影响遍历
  77. events.slice().forEach(event => {
  78. try {
  79. event.func.apply(event.target, data);
  80. } catch (error) {
  81. console.error(`事件[${type}]处理错误:`, error);
  82. }
  83. });
  84. }
  85. }
  86. }
  87. //单例
  88. export const eventEmitter = EventEmitter.ins();