EventBus源碼解析(對應3.2.0版本)

1. 註冊EventBus: register(Object subscriber)

  1. 獲取該subscriber的SubscribeMethod列表;List<SubscriberMethod> subscriberMethods
    1. 執行subscriberMethodFinder.findSubscriberMethods(subscriberClass)獲取List<SubscriberMethod>;
    2. 執行findUsingReflectionInSingleClass()反射獲取subscriber中所有methods,Subscribe註解的Method會記錄在SubscriberMethodFinder.FindState.subscriberMethods()
  2. 遍歷SubscribeMethod列表執行subscribe(subscriber, subscriberMethod)
    1. 更新Map<Class<?>, CopyOnWriteArrayList<Subscription>> subscriptionsByEventType,該字段表示:某個Event對應哪些@Subscribe註解的方法;
    2. 更新Map<Object, List<Class<?>>> typesBySubscriber,該字段表示:register過的類接收哪些Event;該字段的作用:1> 判斷是否註冊過; 2>註銷時輔助subscriptionsByEventType刪除對應event的Subscription;
  3. 對於sticky的subscription,註冊時檢查stickyEvents中是否包含subscriberMethod.eventType的最近事件,如果有立即發出postToSubscription()
  4. unregister(Object subscriber) 相對簡單,從subscriptionsByEventType和typesBySubscriber中刪除相應subscriber;
  5. 重複register()會crash,重複unregister()則不會;

2. 發送、接收Event:post(Object event)

  1. post(Object event)ThreadLocal<PostingThreadState> 類型變量currentPostingThreadState的eventQueue列表會接收event;Event依次從eventQueue取出,執行postSingleEvent()

  2. postSingleEvent(Object event, PostingTHreadState postingState) 中獲取Event Class列表:lookupAllEventTypes(eventClass), 該列表包含eventClass、遞歸父類class直到Object;遍歷列表,執行postSingleEventForEventType()方法;

  3. postSingleEventForEventType(Event, PostingThreadState, eventClass)根據eventClass,從subscriptionsByEventType獲取Subscriptions列表, 遍歷執行postToSubscription()

  4. postToSubscription(Subscription subscription, Object event, boolean isMainThread)根據subscription.subscriberMethod.threadMode 和 isMainThread 判斷,決定event發送線程;

  5. 最終都是反射構造出註冊的方法(@Subscribe註解的方法),將event傳入;invokeSubscriber(Subscription subscription, Object event)

    subscription.subscriberMethod.method.invoke(subscription.subscriber, event);
    

3. EventBus中的ThreadMode

Mode 說明
POSTING 默認Mode; 在發送Event的線程接收Event;
MAIN 在主線程接收Event;如果主線程發送要阻塞主線程,需要儘快返回;
MAIN_ORDERED 在主線程接收Event;但是不會阻塞主線程,而是加入Handler中,按序發送;
BACKGROUND 在主線程發送Event,則加入隊列在後臺線程排序,不可執行耗時任務;如果在非主線程執行,則在該線程執行任務;
ASYNC subscriber執行不阻塞發送線程;使用線程池管理線程;
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章