1. 程式人生 > >60.android 簡單的EventBus傳值,簡單好用

60.android 簡單的EventBus傳值,簡單好用

//第一步 匯入依賴

implementation 'org.greenrobot:eventbus:3.0.0'

//第二步 MainActivity裡傳送事件

 //就寫了個簡單的Button按鈕,點選跳轉,傳值到Main2Activity

public class MainActivity extends AppCompatActivity implements View.OnClickListener {

    private Button mEventBus;
    private String name="曹二少";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        initView();
    }

    private void initView() {
        mEventBus = (Button) findViewById(R.id.mEventBus);

        mEventBus.setOnClickListener(this);
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.mEventBus:
                //釋出事件 activity和activity傳值要用粘性事件
                // 何為黏性事件呢?簡單講,就是在傳送事件之後再訂閱該事件也能收到該事件
                //我在MainActivity裡是先發布了這個事件,傳遞了值,但是我Main2Activity裡的onStart()方法裡註冊,
                //也就是說我釋出完了,跳過去頁面2,它才註冊,並不是一開始就已經註冊的,所以要用到粘性事件
                EventBus.getDefault().postSticky(new EvBean(name));
                startActivity(new Intent(this,Main2Activity.class));
                break;
        }
    }
}

//我寫了個Bean類傳值,你要是不寫Bean類也行,隨便傳個String或者int 隨便型別,因為方法是Objiect型別的。

public class EvBean {
    private String name;

    public EvBean(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

//第三步 Main2Activity裡註冊,接收值,銷燬

 //這個MainActivity的佈局就寫了個Button按鈕,給它賦值。

public class Main2Activity extends AppCompatActivity  {

    private Button mButton;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main2);
        initView();
    }

    private void initView() {
        mButton = (Button) findViewById(R.id.mButton);
    }

    @Override
    protected void onStart() {
        super.onStart();
        //訂閱這個EventBus
        EventBus.getDefault().register(this);
    }

    //3.0以後這個方法自己隨便寫,不過要加@Subscribe這個註解
    @Subscribe(threadMode = ThreadMode.POSTING,sticky = true)//true 就是允許接收粘性事件
    public void onEvent(EvBean evBean){
        String name = evBean.getName();
        mButton.setText(name);
    }

    //及時銷燬
    @Override
    protected void onDestroy() {
        super.onDestroy();
        //取消訂閱
        EventBus.getDefault().unregister(this);
    }
}

//-------------------------------------------------------------傳值就已經完成了-----------------------------------------------------------------------

//以下是一些 引數的理解

//------------------------------------------以下是原始碼中的意思-----------------------------------------------
//POSTING
//    訂閱者將在釋出事件的同一執行緒中被呼叫。這是預設設定。事件傳遞
//*意味著開銷最小,因為它完全避免了執行緒切換。因此,這是的推薦模式
//*已知完成的簡單任務非常短,不需要主執行緒。事件處理程式
//*使用此模式必須快速返回,以避免阻塞可能是主執行緒的釋出執行緒。



//MAIN
//    訂閱者將在Android的主執行緒中被呼叫(有時稱為UI執行緒)。如果張貼線索是
//*主執行緒、事件處理程式方法將被直接呼叫。使用此模式的事件處理程式必須返回
//*快速避免堵塞主執行緒。


//BACKGROUND
//    訂戶將在後臺執行緒中被呼叫。如果釋出執行緒不是主執行緒,事件處理程式方法
//*將直接在釋出執行緒中呼叫。如果釋出執行緒是主執行緒,event bus使用單個執行緒
//*後臺執行緒,將依次傳遞其所有事件。使用此模式的事件處理程式應嘗試
//*快速返回以避免阻塞後臺執行緒。


//ASYNC
//    在單獨的執行緒中呼叫事件處理程式方法。這總是獨立於釋出執行緒和
//*主線。釋出事件從不等待使用此模式的事件處理程式方法。事件處理程式方法應該
//*如果執行這些命令可能需要一些時間,例如網路訪問,請使用此模式。避免觸發大量
//*同時使用長時間執行的非同步處理程式方法來限制併發執行緒的數量。事件匯流排
//*使用執行緒池有效地重用已完成的非同步事件處理程式通知中的執行緒。





//----------------------------------------以下是通俗理解---------------------------------------------
//    PostThread:如果使用事件處理函式指定了執行緒模型為PostThread,
// 那麼該事件在哪個執行緒釋出出來的,事件處理函式就會在這個執行緒中執行,
// 也就是說釋出事件和接收事件在同一個執行緒。
// 線上程模型為PostThread的事件處理函式中儘量避免執行耗時操作,
// 因為它會阻塞事件的傳遞,甚至有可能會引起ANR。

//    MainThread:如果使用事件處理函式指定了執行緒模型為MainThread,
// 那麼不論事件是在哪個執行緒中釋出出來的,該事件處理函式都會在UI執行緒中執行。
// 該方法可以用來更新UI,但是不能處理耗時操作。

//    BackgroundThread:如果使用事件處理函式指定了執行緒模型為BackgroundThread,
// 那麼如果事件是在UI執行緒中釋出出來的,那麼該事件處理函式就會在新的執行緒中執行,
// 如果事件本來就是子執行緒中釋出出來的,那麼該事件處理函式直接在釋出事件的執行緒中執行。
// 在此事件處理函式中禁止進行UI更新操作。

//    Async:如果使用事件處理函式指定了執行緒模型為Async,
// 那麼無論事件在哪個執行緒釋出,該事件處理函式都會在新建的子執行緒中執行。
// 同樣,此事件處理函式中禁止進行UI更新操作。

//注意一個異常

//發現一個異常,當你這個訂閱要是在onStart()方法裡的話,點選這個訂閱的介面,再跳轉一個頁面,當你按返回鍵返回上一個介面的時候,會丟擲異常,會丟擲一個事件匯流排的異常,解決辦法,在OnCreate()方法裡訂閱。

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main2);
    initView();
    //訂閱這個EventBus
    EventBus.getDefault().register(this);
}

//----------------------------------------------------------------------完---------------------------------------------------------------------------