greenrobot EventBus post event in Android

ronie picture ronie · Jan 10, 2013 · Viewed 17.5k times · Source

By using EventBus, I need to post an event(MyEvent) in an Activity and receive the event in another Activity in Android. I tried the greenrobot EventBus performance test project but could not get how to do it.

I tried in ActivitySubscriber

MyEvent event = new MyEvent();
EventBus.getDefault().post(event);

and tried to receive the event in ActivityReceiver as

EventBus.getDefault().register(this);

public void onEvent(MyEvent event){
....
}

but I am unable to receive the event. Can anyone let me know where am I doing wrong?

Answer

Dimitar Genov picture Dimitar Genov · Feb 4, 2013

Since they are two activities, ActivitySubscriber posts the event while ActivityReceiver is still not created, or is in stall mode (onStop()). You need to use sticky events, i.e.

  • ActivitySubscriber.postSticky(...)

And for ActivityReceiver you have two options:

  • EventBus.getDefault().register(this) and somewhere after that EventBus.getDefault().getStickyEvent()
  • EventBus.getDefault().registerSticky() and then using regular EventBus.getDefault().onEvent(...)

Updated: EventBus 3.0 changes the way to subscribe.

There is no need of method names which end up with specific suffixes but rather annotations.

How to use version 3:

//// in your build.gradle
compile 'de.greenrobot:eventbus:3.0.0-beta1'
// alternatively you can target latest whatever currently
// compile 'de.greenrobot:eventbus:+'

//// from a class which needs to dispatch an event
// posting an event is as before, no changes
// here we dispatch a sticky event
EventBus.getDefault().postSticky(myStickyEvent);

//// from your class which needs to listen
// method name can be any name
// any of subscribe params is optional, i.e. can use just @Subscribe
@Subscribe(threadMode = ThreadMode.MainThread, sticky = true, priority = 1)
public void onEventBusEvent(@Nullable final StickyEvent stickyEvent) {
    if (stickyEvent != null) {
      ...
      // optionally you can clean your sticky event in different ways
      EventBus.getDefault().removeAllStickyEvents();
      // EventBus.getDefault().removeStickyEvent(stickyEvent);
      // EventBus.getDefault().removeStickyEvent(StickyEvent.class);
    }
}

For more details and comparison of version 3:

Some details extracted from the sources:

  • ThreadMode.PostThread

    Subscriber will be called in the same thread, which is posting the event. This is the default. Event delivery implies the least overhead because it avoids thread switching completely. Thus this is the recommended mode for simple tasks that are known to complete is a very short time without requiring the main thread. Event handlers using this mode must return quickly to avoid blocking the posting thread, which may be the main thread.

  • ThreadMode.MainThread

    Subscriber will be called in Android's main thread (sometimes referred to as UI thread). If the posting thread is the main thread, event handler methods will be called directly. Event handlers using this mode must return quickly to avoid blocking the main thread.

  • ThreadMode.BackgroundThread

    Subscriber will be called in a background thread. If posting thread is not the main thread, event handler methods will be called directly in the posting thread. If the posting thread is the main thread, EventBus uses a single background thread, that will deliver all its events sequentially. Event handlers using this mode should try to return quickly to avoid blocking the background thread.

  • ThreadMode.Async

    Event handler methods are called in a separate thread. This is always independent from the posting thread and the main thread. Posting events never wait for event handler methods using this mode. Event handler methods should use this mode if their execution might take some time, e.g. for network access. Avoid triggering a large number of long running asynchronous handler methods at the same time to limit the number of concurrent threads. EventBus uses a thread pool to efficiently reuse threads from completed asynchronous event handler notifications.

  • default values for @Subscribe
    • threadMode = ThreadMode.PostThread
    • sticky = false - If true, delivers the most recent sticky event (posted with de.greenrobot.event.EventBus.postSticky(Object) to this subscriber (if event available)
    • priority = 0 - Subscriber priority to influence the order of event delivery. Within the same delivery thread, higher priority subscribers will receive events before others with a lower priority. The default priority is 0. Note: the priority does NOT affect the order of delivery among subscribers with different thread modes.

Edit 2

There is a dedicated site now for any Greenrobot EventBus questions from the creator of the lib:

http://greenrobot.org/eventbus/