不仅仅局限于Activity和Fragment,在任何地方都可用,方便快捷,废话不多说:
EventBusManager 对 EventBus 进行了封装,使得其可以再任何地方订阅接收消息,对于粘性消息和非粘性消息进行了区分处理,由于框架的封装,post的事件类型统一为EventData.class类型,而默认单个EventBus实例内部对于粘性事件是由事件类型进行区分,也就导致在极端场景下同一个EventBus发送了相同类型的粘性消息,只有最后一条消息才会响应的问题,因此发送粘性消息的时候会单独创建一个EventBus实例处理每一类型的粘性消息事件,普通消息则采用默认的EventBus.default实例。
public class EventBusManager {
/**
* 保存黏性事件的EventBus对象
* 解决默认 EventBus.getDefault() 连续发送黏性事件只有最后一个会生效
*/
private static final Hashtable<EventKey, EventBus> customEventBusMap = new Hashtable<>();
private static EventBus getDefaultEventBus() {
return EventBus.getDefault();
}
private static EventBus getCustomEventBus() {
return new EventBus();
}
/**
* 黏性事件 {@link BaseStickySubscriber}
* 普通事件 {@link BaseSubscriber}
*/
public static <T> void register(BaseSubscriber<T> subscriber) {
if (subscriber instanceof BaseStickySubscriber) {
EventBus eventBus = getStickyEventBus(subscriber.key);
if (!eventBus.isRegistered(subscriber)) {
eventBus.register(subscriber);
}
} else {
if (!getDefaultEventBus().isRegistered(subscriber))
getDefaultEventBus().register(subscriber);
}
}
/**
* 取消注册
*/
public static void unregister(BaseSubscriber<?> subscriber) {
if (subscriber == null)
return;
if (subscriber instanceof BaseStickySubscriber) {
EventBus eventBus = customEventBusMap.get(subscriber.key);
if (eventBus != null)
eventBus.unregister(subscriber);
} else {
getDefaultEventBus().unregister(subscriber);
}
}
/**
* 发送普通事件
*/
public static <T> void post(EventData<T> eventData) {
getDefaultEventBus().post(eventData);
}
/**
* 发送黏性事件
*/
public static <T> void postSticky(EventData<T> eventData) {
getStickyEventBus(eventData.getKey()).postSticky(eventData);
}
private static EventBus getStickyEventBus(EventKey key){
EventBus eventBus = customEventBusMap.get(key);
if (eventBus == null) {
eventBus = getCustomEventBus();
customEventBusMap.put(key, eventBus);
}
return eventBus;
}
}
BaseSubscriber类为订阅者的基础类,满足接收基本的非粘性消息事件分发,构造函数要求开发者传入对应的事件 KEY 作为标识,用于接受消息事件区分消息来源;onSubscribeEvent方法为EventBus订阅的方法,有Subscribe 注解,如果有特殊需要定制具体Subscribe 参数的需求,继承此类重写即可,该方法接收一个消息事件类型为EventData,EventData内容为为key-value 形式,key即为消息订阅时的key,value为具体数据;接收消息后,通过比对消息的key来确定来源分发给指定订阅者,详情看如下代码:
public abstract class BaseSubscriber<T> {
protected EventKey key;
public BaseSubscriber(EventKey key) {
this.key = key;
}
/**
* 默认 threadMode = ThreadMode.POSTING ,非粘性事件
* 有需要特殊 Subscribe 的情况, 子类直接覆盖按需实现
*/
@Subscribe(threadMode = ThreadMode.POSTING)
public void onSubscribeEvent(EventData<T> eventData) {
if (eventData != null && eventData.getKey() == key) {
notifyDataChanged(eventData.getValue());
// Log.e("testBus","事件 key-> "+key+" eventData key->"+
// eventData.getKey() +" 是否相等->"+(key==eventData.getKey()));
}
}
/**
* -- Subscribe 代理方法 --
* onSubscribeEvent 匹配到对应事件 下发通知
* 避免到处写 Subscribe注解
* --- 如有特殊情况,特殊处理 ---
*
* @param value 自定义类型数据
*/
protected abstract void notifyDataChanged(T value);
BaseStickySubscriber类为订阅者的基础类,满足接收基本的粘性消息事件分发,用法参照BaseSubscriber的基本用法,代码如下:
public abstract class BaseStickySubscriber<T> extends BaseSubscriber<T>{
public BaseStickySubscriber(EventKey key) {
super(key);
}
@Subscribe(threadMode = ThreadMode.POSTING,sticky = true)
@Override
public void onSubscribeEvent(EventData<T> eventData) {
//Log.e("testBus","黏性事件 key-> "+key+" eventData key->"+eventData.getKey() +" 是否相等->"+(key==eventData.getKey()));
super.onSubscribeEvent(eventData);
}
}
/**
* 传递的数据 统一格式
* @param <T> 数据类型
*/
public class EventData<T> {
private EventKey key;
private T value;
public EventData(EventKey key, T value) {
this.key = key;
this.value = value;
}
public EventKey getKey() {
return key;
}
public T getValue() {
return value;
}
}
/**
* 业务 标识 key
*/
public enum EventKey {
KEY,
KEY1,
KEY2
}
基本用法:
// 发送事件消息,默认非粘性消息
EventBusManager.post(new EventData<>(EventKey.KEY,"value test"));
// 消息订阅者,默认接收非粘性消息
BaseSubscriber<String> subscriber = new BaseSubscriber<String>(EventKey.KEY) {
@Override
protected void notifyDataChanged(String value) {
Log.e("testBus", value);
}
};
// 发送事件消息,粘性消息
EventBusManager.postSticky(new EventData<>(EventKey.KEY1,"Sticky value test"));
// 消息订阅者,接收粘性消息
BaseStickySubscriber<String> stickySubscriber = new BaseStickySubscriber<String>(EventKey.KEY1) {
@Override
protected void notifyDataChanged(String value) {
Log.e("testBus", value);
}
};
// 消息注册反注册,通用
EventBusManager.register(subscriber);
EventBusManager.unregister(subscriber);
EventBusManager.post(new EventData<>(EventKey.KEY,"value test"));
EventBusManager.postSticky(new EventData<>(EventKey.KEY1,"Sticky value test"));
BaseSubscriber<String> subscriber = new BaseSubscriber<String>(EventKey.KEY) {
@Override
protected void notifyDataChanged(String value) {
Log.e("testBus", value);
}
};
EventBusManager.register(subscriber);
EventBusManager.unregister(subscriber);
BaseStickySubscriber<String> stickySubscriber = new BaseStickySubscriber<String>(EventKey.KEY1) {
@Override
protected void notifyDataChanged(String value) {
Log.e("testBus", value);
}
};
EventBusManager.register(stickySubscriber);
EventBusManager.unregister(stickySubscriber);