Magren

Magren

Idealist & Garbage maker 🛸
twitter
jike

Android的EventBus使用

這兩天在網上想着找 Android 系統學習的路線,然後發現了阿里雲上的阿里巴巴 Android 開發手冊,雖然網上已經有免費下載的地方了,不過憑著不能白嫖的感覺,我還是花錢支持了下,其實就賣一塊錢,而且還有一份考試證書的資格,總的來說還是很舒服的。

網址在下面:

阿里巴巴 Android 開發手冊

估摸是我接觸的太少的緣故,在一開始的第一條我就懵掉了

  1. 【強制】Activity 間的數據通信,對於數據量比較大的,避免使用 Intent + Parcelable 的方式,可以考慮 EventBus 等替代方案,以免造成 TransactionTooLargeException。

這個EventBus…… 是啥???

EventBus 概述#

EventBus 是一個 Android 事件發布 / 訂閱框架,通過解耦發布者和訂閱者簡化 Android 事件傳遞,這裡的事件可以理解為消息。事件傳遞既可以用於 Android 四大組件間通訊,也可以用於異步線程和主線程間通訊等。傳統的事件傳遞方式包括:Handler、BroadcastReceiver、Interface 回調,相比之下 EventBus 的優點是代碼簡潔,使用簡單,並將事件發布和訂閱充分解耦。

在這裡面,又有三個對象:

  • 事件 Event:就是消息,分為一般事件和 Sticky(黏性)事件,Sticky 事件的特殊在於,當事件發布後,再有訂閱者訂閱該類型事件,依然能收到該類型事件的最近的一個 Sticky 事件
  • 訂閱者 Subscriber:訂閱事件的對象,當發布者發布事件時,EventBus 會執行訂閱者的事件響應函數。訂閱者通過 register 接口訂閱某個事件類型,unregister 接口退訂
  • 發布者:發布事件的對象,通過 post 接口發布事件,黏性事件通過 postSticky

Github 地址:EventBus

使用#

道理我都懂,但是我得知道它是怎麼用的,不然日後複製起來粘貼在哪都不知道,於是我在網上找到了它的使用方法。

一般事件#

自定義一個事件類
public class Event {

    String message;


    public Event(String message){
        this.message = message;
    }

    public String getMessage() {
        return message;
    }
}
在需要接收消息的頁面註冊
EventBus.getDefault().register(this);
接收消息的方法
@Subscribe(threadMode = ThreadMode.MAIN)
   public void getEvent(Event event) {
       msg = event.getMessage();
       tv.setText(msg);
   }
發送事件
@OnClick(R.id.bt_return)
    public void renturnActivity(){
        //發送事件
        EventBus.getDefault().post(new Event("Magren"));
        finish();
    }
在註冊的頁面銷毀的時候反註冊
@Override
    protected void onDestroy() {
        super.onDestroy();
        //反註冊
        EventBus.getDefault().unregister(this);
    }

通過上面的方法,實現了在 MainActivity 中註冊 EventBus 事件,然後寫好響應事件的方法,當跳轉到另一個 Activity,點擊按鈕向 MainActivity 發送 Event 事件,同時我們回到 MainActivity 的時候發現我們的事件已經接收到並且呈現了出來。

MainActivity:
eventMain1.png

SendMainActivity:
eventSend.png

返回 MainActivity:
eventMain2.png

這是一般事件的使用方法,但是我想的傳遞數據是在當前 Activity 向下一個 Activity 傳遞數據並且在下一個 Activity 使用,但是我用上面的方法去實現的時候發現並不能派上用場,後面我才清楚了這裡得用上我們的黏性事件。

Sticky 事件#

自定義一個事件類
public class Event {

    String message;


    public Event(String message){
        this.message = message;
    }

    public String getMessage() {
        return message;
    }
}
在需要接收消息的頁面註冊
EventBus.getDefault().register(this);
接收消息的方法

此時多了 sticky = true

@Subscribe(sticky = true,threadMode = ThreadMode.MAIN)
    public void getEvent(Event event) {
        msg = event.getMessage();
        tv.setText(msg);
    }
發送事件

先發送消息後進行 Activity 的跳轉,注意這裡是 postSticky,發送黏性事件

@OnClick(R.id.bt_return)
   public void renturnActivity(){
       //發送事件
       EventBus.getDefault().postSticky(new Event("Magren"));
       Intent intent = new Intent(this,MainActivity.class);
       startActivity(intent);

   }
在註冊的頁面銷毀的時候反註冊
@Override
    protected void onDestroy() {
        super.onDestroy();
        //反註冊
        EventBus.getDefault().unregister(this);
    }

這時候我們就可以實現直接向下一個 Activity 發送事件並且在裡面獲取並使用了。

1.SendActivity

2.MainActivity

EventBus 處理事件的線程#

上面我們的註解 @Subscribe (threadMode = ThreadMode.MAIN) 裡面用了 ThreadMode.MAIN 這個模式,其實表示的是這個函數在主線程裡面進行,EventBus 給我們提供了總共有 4 中線程模式

  • ThreadMode.MAIN:表示無論事件是在哪個線程發布出來的,該事件訂閱方法 onEvent 都會在 UI 線程中執行,這個在 Android 中是非常有用的,因為在 Android 中只能在 UI 線程中更新 UI,所有在此模式下的方法是不能執行耗時操作的。
  • ThreadMode.POSTING:表示事件在哪個線程中發布出來的,事件訂閱函數 onEvent 就會在這個線程中運行,也就是說發布事件和接收事件在同一個線程。使用這個方法時,在 onEvent 方法中不能執行耗時操作,如果執行耗時操作容易導致事件分發延遲。
  • ThreadMode.BACKGROUND:表示如果事件在 UI 線程中發布出來的,那麼訂閱函數 onEvent 就會在子線程中運行,如果事件本來就是在子線程中發布出來的,那麼訂閱函數直接在該子線程中執行。
  • ThreadMode.AYSNC:使用這個模式的訂閱函數,那麼無論事件在哪個線程發布,都会創建新的子線程來執行訂閱函數

注意點#

  • 註冊一般寫在 onCreate 或者 onStart 中,盡量不要寫在 onResume,可能出現多次註冊,多次註冊會出現報錯以及 APP 閃退
  • 取消註冊一定寫在 onDestory, 寫在 onStop 可能會引發異常,同時檢查或許會導致頁面退出的情況,及時取消註冊
  • 註冊前可以先判斷是否已經註冊
if (!EventBus.getDefault().isRegistered(this)) {
    EventBus.getDefault().register(this);
}
  • 未聲明 threadMode 的時候默認線程模式是 ThreadMode.POSTING

以上就是我從網上總結的部分 EventBus 的使用以及自己的實操,每次隨便逛逛都可以發現我不懂的知識點,任重道遠

載入中......
此文章數據所有權由區塊鏈加密技術和智能合約保障僅歸創作者所有。