2017年4月15日土曜日

【Android7.1】EventBusまとめ

  • 公開日:2017年04月15日

記事概要

EventBusの調査メモ。取り急ぎのまとめです。
プログラミングJava用にソースコード書いてgitにあげたり、動画撮ったり、英語にしてまとめるかは微妙です。純正ライブラリでないですし。アクセス数見て考えます。

環境

  • buildToolsVersion 25.0.2
  • EventBus 3.0.0
  • Android Studio 2.3.1

対象

pub, subの概念を理解している人。

git

ここのサイトから取得できます。

特徴(長所)

  • コンポーネント間の通信を簡素化
  • イベントの送信者と受信者を切り離す
  • アクティビティ、フラグメント、およびバックグラウンドスレッドで使える
  • 複雑でエラーを起こしやすい依存関係やライフサイクルの問題を避ける
  • コードをシンプルにする
  • 速い
  • 小さい(約50k)

特徴(欠点)

  • コードが直感的でない
  • Eventが増えるとコードのつながりがわかりにくくなる

Install

build.gradleファイルに以下の内容を記述します。

{project_folder}/build.gradle

dependencies {
  compile 'org.greenrobot:eventbus:3.0.0'
}

Android Studio Plugin

EventBusの欠点は、コードが直感的で無くなることです。
なので、Android Studio Pluginを導入して、コードリーディングの軽減を図るのは良い考えです。

ここのサイトから取得できます。
もしくはAndroid StudioのPluginでEventBus3で検索しましょう。

Hello EventBus

実際に実装してみましょう。
fragmentのButtonからActivityに通知してみます。

{project_folder}/MainActivity.java

  @Override
  public void onStart() {
      Log.d("MainActivity", "onStart");
      super.onStart();
      EventBus.getDefault().register(this);
  }

  @Override
  public void onStop() {
      Log.d("MainActivity", "onStop");
      super.onStop();
      EventBus.getDefault().unregister(this);
  }

  @Subscribe(threadMode = ThreadMode.MAIN)
  public void onMessageEvent(MainFragment.MessageEvent event) {
      Log.d("MainActivity", "onMessageEvent");
      Toast.makeText(getApplicationContext(), event.msg, Toast.LENGTH_SHORT).show();
  }

コードはSubscribeメソッドから記述します。メソッドには@Subscribeアノテーションを付加します。この時、@Subscribeメソッドの名前はなんでもOKです。

EventBus.getDefault().register(this);でSubscribeを登録します。registerを呼び出したクラスに@Subscribeアノテーションを追加したメソッドがないとエラーが発生します。

Error

super classes have no public methods with the @Subscribe annotation
Caused by: org.greenrobot.eventbus.EventBusException: Subscriber class com.example.xxxx.MainActivity and its super classes have no public methods with the @Subscribe annotation

また、複数回registerを呼び出すとクラッシュします。

Error

Caused by: org.greenrobot.eventbus.EventBusException: Subscriber class com.example.xxxx.MainActivity already registered to event class

以下の実装箇所で引っかかります。

Error

if (subscriptions.contains(newSubscription)) {
    throw new EventBusException("Subscriber " + subscriber.getClass() + " already registered to event " + eventType);
}

DialogやカスタムViewを使った場合も実装方法は同じです。

Configuration

不要だと思います。デフォルト設定で良いでしょう。

Sticky Events

複雑になるだけです。いりません。

Subscriber Index

EventBus version3から導入された新機能です。初期Subscribeの登録を高速化して最適化します。最高のパフォーマンスを得るために、使用が推奨されています。
まあ、使えってことです。

build.gradleファイルに以下の内容を記述します。

{project_folder}/build.gradle

android {
  defaultConfig {
    javaCompileOptions {
      annotationProcessorOptions {
        arguments = [ eventBusIndex : 'com.example.xxx.EventBusIndex' ]
      }
    }
  }
}

dependencies {
  compile 'org.greenrobot:eventbus:3.0.0'
  annotationProcessor 'org.greenrobot:eventbus-annotation-processor:3.0.1'
}

初期化してSubscribeを登録してindex化するので、Applicationクラスを使います。無い場合は作成します。

{project_folder}/MyApplication.java

public class MyApplication extends Application {
  @Override
  public void onCreate() {
      super.onCreate();
      EventBus.TAG = "MyApplication-EVENT";
      EventBus.builder().addIndex(new EventBusIndex()).installDefaultEventBus();
  }
}

新規作成の場合は、AndroidManifest.xmlも忘れないで設定します。

{project_folder}/AndroidManifest.xml

application
  android:name="com.example.xxx.MyApplication"

以上です。pub, subの処理は変わりません。なぜなら、EventBus.getDefault()メソッドでは、EventBus.builder().addIndex(new EventBusIndex()).installDefaultEventBus();で作成したEventBusのインスタンスを使い回すからです。
細かい動きが気になる人はコードを読んで見ると良いでしょう。

結論

EventBusは便利なライブラリです。とはいえ、コードが読みにくくなるので、階層の離れたviewからAcitivtyに伝えるなどのケース以外ではあんまり使いたくないですね。
やっぱりcallbackをなるべく使うべきな気がします。でも、RxJavaのPub, Subよりは使いやすいです。

以上です。

PICK UP

運営サイト


参照

この記事がお役にたちましたらシェアをお願いします

このエントリーをはてなブックマークに追加
Related Posts Plugin for WordPress, Blogger...