Detailed explanation of the use of EventBus in the open source library

Introduction

EventBus is a publish/subscribe event bus for Android. Simplifies the communication between components, components and background threads in the application. It is often used to communicate and transfer data between Activity, Fragment and background Service.

GitHub address: https://github.com/greenrobot/EventBus

API

eventbus

As a message bus, there are three main components: event (Event), event subscriber (Subscriber), and event publisher (Publisher).

use

  • Add EventBus dependency in the module's build.gradle build script
dependencies {
    ...
   implementation 'org.greenrobot:eventbus:3.1.1'
}
  • Define the event, the event can be any ordinary Java object without any special requirements
public class MessageEvent {

    private String msg;

    public MessageEvent(String msg) {
        this.msg = msg;
    }

    public String getMsg() {
        return msg;
    }

    public void setMsg(String msg) {
        this.msg = msg;
    }
}
  • Subscribe to events
 @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_event_bus);
        //  注册订阅者
        EventBus.getDefault().register(this);
    }

    // 事件处理方法
    @Subscribe(threadMode = ThreadMode.MAIN)
    public void onMainEvent(MessageEvent event) {
        Log.e(TAG, "onMainEvent方法接收的数据---->" + event.getMsg());
    }

     // 注销订阅者
    @Override
    protected void onDestroy() {
        super.onDestroy();
        EventBus.getDefault().unregister(this);
    }
  • Publish events, publish events where needed, and all registered subscribers who have subscribed to this type of event will receive the event.
   EventBus.getDefault().post(new MessageEvent("main"));

Thread mode

Use thread mode to specify the thread of the subscriber method

  1. ThreadMode.POSTING

    The subscriber method will be called in the thread where the event is posted. This is the default thread mode. The delivery of events is synchronous. Once an event is published, all subscriber methods of this mode will be called. This threading mode means the least performance overhead, because it avoids thread switching. Therefore, this mode is recommended for simple tasks that do not require the main thread and take a short time. Subscriber methods using this pattern should return quickly to avoid blocking the thread that publishes the event, which may be the main thread.

  2. ThreadMode.MAIN

    The subscriber method will be called in the main thread (UI thread). Therefore, you can directly update the UI interface in the subscriber method of this mode. If the thread that publishes the event is the main thread, then the subscriber method of this mode will be called directly. Subscriber methods using this pattern must return quickly to avoid blocking the main thread.

  3. ThreadMode.MAIN_ORDERED

    The subscriber method will be called in the main thread (UI thread). Therefore, you can directly update the UI interface in the subscriber method of this mode. The event will enter the queue before being sent to the subscriber, so the call to publish the event will return immediately. This keeps the processing of events in a strict serial order. Subscriber methods using this mode must return quickly to avoid blocking the main thread

  4. ThreadMode.BACKGROUND

    The subscriber method will be called in a background thread. If the thread publishing the event is not the main thread, then the subscriber method will be called directly in that thread. If the thread that posted the event is the main thread, then a separate background thread will be used, which will send all events in sequence. Subscriber methods using this pattern should return quickly to avoid blocking background threads.

  5. ThreadMode.ASYNC

    The subscriber method will be called in a separate thread. Therefore, the call to publish the event will return immediately. If the execution of the subscriber method requires some time, such as network access, then this mode should be used. Avoid triggering a large number of long-running subscriber methods to limit the number of concurrent threads. EventBus uses a thread pool to effectively reuse threads that have finished calling subscriber methods.

Concrete example

  • ThreadMode.POSTING
// 在EventBusActivity 中进行注册订阅、处理订阅者方法、注销订阅
public class EventBusActivity extends AppCompatActivity {
    
    
  private static final String TAG = EventBusActivity.class.getSimpleName();
  @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_event_bus);
        //  注册订阅者
        EventBus.getDefault().register(this);
    }

    // 事件处理方法
    @Subscribe(threadMode = ThreadMode.POSTING)
    public void onPostingEvent(MessageEvent event) {
        Log.e(TAG, "onPostingEvent方法接收的数据---->" + event.getMsg()+ "---所在线程---->" + Thread.currentThread().getName());
    }

     // 注销订阅者
    @Override
    protected void onDestroy() {
        super.onDestroy();
        EventBus.getDefault().unregister(this);
    }
}


//  在EventSecondActivity 进行发送事件
public class EventSecondActivity extends AppCompatActivity implements View.OnClickListener {
    
    
    private static final String TAG = EventSecondActivity.class.getSimpleName();
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_event_second);

        Button btn = findViewById(R.id.btn);
        btn.setOnClickListener(this);
    }
    @Override
    public void onClick(View view) {
        switch (view.getId()) {
            case R.id.btn:
                // 在main 主线程调用
                EventBus.getDefault().post(new MessageEvent("posting"));
                break;
         }
    }
}

result:
Write picture description here

  • ThreadMode.MAIN
// EventBusActivity 代码
......

 @Subscribe(threadMode = ThreadMode.MAIN)
    public void onMainEvent(MessageEvent event) {

        Log.e(TAG, "onMainEvent方法接收的数据---->" + event.getMsg() + "---所在线程---->" + Thread.currentThread().getName());
    }

.......

// EventSecondActivity 进行发送事件
.......

EventBus.getDefault().post(new MessageEvent("main"));
  • ThreadMode.BACKGROUND
// EventBusActivity 代码
   @Subscribe(threadMode = ThreadMode.BACKGROUND)
    public void onBackgroundEvent(MessageEvent event) {
        Log.e(TAG, "onBackgroundEvent方法接收的数据---->" + event.getMsg() + "---所在线程---->" + Thread.currentThread().getName());
    }

 // EventSecondActivity 进行发送事件
 new Thread(new Runnable() {
     @Override
     public void run() {
      EventBus.getDefault().post(new MessageEvent("background"));
         Log.e(TAG, "---所在线程为--->" + Thread.currentThread().getName());
      }
 }).start();

result:
Write picture description here

  • ThreadMode.ASYNC
// EventBusActivity 代码
 @Subscribe(threadMode = ThreadMode.ASYNC)
    public void onAsyncEvent(MessageEvent event) {
        Log.e(TAG, "onAsyncEvent 方法接收的数据---->" + event.getMsg() + "---所在线程---->" + Thread.currentThread().getName());
    }
// EventSecondActivity 进行发送事件
 EventBus.getDefault().post(new MessageEvent("async"));

result:
Write picture description here

Event priority

EventBus supports specifying the priority of event delivery when defining subscriber methods. By default, the event delivery priority of the subscriber method is 0. The larger the value, the higher the priority. In the same thread mode, higher priority subscriber methods will receive events first

// EventBusActivity 代码
@Subscribe(threadMode = ThreadMode.MAIN, priority = 1)
    public void onMainEvent(MessageEvent event) {

        Log.e(TAG, "onMainEvent方法接收的数据---->" + event.getMsg() + "---所在线程---->" + Thread.currentThread().getName());
    }

    @Subscribe(threadMode = ThreadMode.MAIN, priority = 2)
    public void onMainEvent_2(MessageEvent event) {
        Log.e(TAG, "onMainEvent_2方法接收的数据---->" + event.getMsg() + "---所在线程---->" + Thread.currentThread().getName());
    }

    @Subscribe(threadMode = ThreadMode.MAIN, priority = 3)
    public void onMainEvent_3(MessageEvent event) {

        Log.e(TAG, "onMainEvent_3方法接收的数据---->" + event.getMsg() + "---所在线程---->" + Thread.currentThread().getName());
    }

Note: Priority is only valid in the same thread mode.
result:
Write picture description here

Sticky event

If the event is published first, and then a subscriber subscribes to the event, the subscriber will never receive the event unless the event is published again. At this point, sticky events can be used. After posting a sticky event, EventBus will cache the sticky event in memory. When a subscriber subscribes to the sticky event, the subscriber will receive the event

Example:

// EventBusActivity 代码
TextView tv_sticky = findViewById(R.id.tv_sticky);
tv_sticky.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                EventBus.getDefault().postSticky(new MessageEvent("sticky"));
            }
  });

 Button btn = findViewById(R.id.btn);
 btn.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
       Intent intent = new Intent(EventBusActivity.this, EventSecondActivity.class);
       startActivity(intent);
    }
 });

// EventSecondActivity
 @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_event_second);
        EventBus.getDefault().register(this);
  }

  @Subscribe(threadMode = ThreadMode.MAIN, sticky = true)
    public void onStickyEvent(MessageEvent event) {
        Log.e(TAG,"onStickyEvent 粘性事件接收---------->"+event.getMsg());
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        EventBus.getDefault().unregister(this);

    }

result:
Write picture description here

Related API:

  • removeStickyEvent(Object event)
    removes the specified sticky event
  • removeStickyEvent(Class eventType);
    remove the specified type of sticky event
  • removeAllStickyEvents();
    remove all sticky events

EventBus plugin

The project uses EventBus, and various events in it are chaotic. This plug-in is very easy to use for events in the project.

  • 在AndroidStudio Setting——–>Plugins
    Write picture description here
  • Click the small post event icon, it will directly list all the received places
    Write picture description here
  • Clicking on the icon of receiving events will directly list all the places that sent events:
    Write picture description here

Guess you like

Origin blog.csdn.net/xufei5789651/article/details/82667995