eventBus ts封装

index.ts 文件

// @ts-nocheck
import { isDevEnv } from '@cxyx/foundation/utils/env'
import EventDesc from './event-desc'

type IEventType = new (...args: any[]) => EventDesc
type ISendEventListener = (eventName: string) => void
type ICommonFunc = (event: any) => void
type IListenerRef = { key: number; handler: ICommonFunc }
// 注册事件索引 | 注册事件回调 | 注册事件的描述类的实例
type ISubscribeRetVal = [number, ICommonFunc, IEventType]

export default class EventBus {
  // 存储注册事件
  private _eventListeners: Map<IEventType | EventDesc, Array<IListenerRef>> = new Map()
  // 当前注册事件索引,用于取消事件
  private _currentIndex: number = 0
  private onSendEvent?: ISendEventListener

  /**
   * 订阅 Event
   * @param {IEventType} event 消息类型
   * @param {(event: T) => void} handler 响应方法
   * @returns {ISubscribeRetVal | never} 注册事件索引 | 注册事件回调 | 注册事件的描述类的实例 | never
   */
  public subscribe(event: IEventType, handler: ICommonFunc): ISubscribeRetVal | never {
    if (isDevEnv && !handler) {
      throw new Error('invaild handler')
    }
    this._currentIndex++
    if (!this._eventListeners.has(event)) {
      this._eventListeners.set(event, [{ key: this._currentIndex, handler: handler }])
    } else {
      ;(this._eventListeners.get(event) as Array<IListenerRef>).push({ key: this._currentIndex, handler: handler })
    }

    return [this._currentIndex, handler, event]
  }

  /**
   * 设置发送 Event 的监听
   * @param {ISendEventListener} onSendEvent
   */
  public setSendEventListener(onSendEvent: ISendEventListener): void {
    this.onSendEvent = onSendEvent
  }

  /**
   * @param eventName: 触发事件的名称
   */
  public sendEvent<T extends EventDesc>(event: T): void {
    if (!event?.constructor) return
    const listenersList = this._eventListeners.get(event.constructor) as Array<IListenerRef>

    if (listenersList?.length) {
      listenersList.forEach((listener: IListenerRef) => {
        listener.handler(event)
      })
      if (this.onSendEvent) {
        this.onSendEvent(event.name)
      }
    }
  }

  /**
   * 取消订阅 Event
   * @param {[number, ICommonFunc]} unsubscribeParams
   */
  public unsubscribe(unsubscribeParams: ISubscribeRetVal): void {
    const currentSubscribePointIndex = unsubscribeParams[0]
    const currentSubscribePointEventRef = unsubscribeParams[2]

    if (this._eventListeners.has(currentSubscribePointEventRef)) {
      const listeners = this._eventListeners.get(currentSubscribePointEventRef)

      const reasonListener = listeners?.filter(listenerRef => listenerRef.key !== currentSubscribePointIndex) as Array<IListenerRef>

      this._eventListeners = this._eventListeners.set(currentSubscribePointEventRef, reasonListener)
    }
  }
}
const eventBus = new EventBus()
export { eventBus }

README.md

基于 RxJS 实现的 Event 总线,使用方式如下:

* step 1: 根据业务场景,在合适的时机生成 EventBus 实例, 如在页面初始化时。

const eventBus = new EventBus();

// 设置发送 Event 的回调
eventBus.setSendEventListener(( apiName: string )=>{ console.log(send ${apiName} event) });


* step 2: 继承 AbsEventDesc 定义一个Event。

class MyEventMsg extends AbsEventDesc {
public name = ‘MyEventMsg’;

// 根据需要自定义要传递的属性,属性修饰符为Public
public msg: string;

constructor(msg: string) {
    super();
    this.msg = msg;
}

}


* step 3:  在 Event 消费者处注册 Event 监听。

// 订阅消息
const subscription = eventBus.subscribe(MyEventMsg, (event: MyEventMsg) => {
// do something
});

// 取消订阅
eventBus.unsubscribe(subscription);


* step 4:  在 Event 生产者处发送 Event。

// 发送消息
eventBus.sendEvent(new MyEventMsg(‘hello’));


```

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值