EventBus 3.0 使用介绍
来源:互联网 发布:网游明星知乎 编辑:程序博客网 时间:2024/05/16 08:21
EventBus3.0(greenrobot),它是一款针对Android的发布/订阅事件总线。它可以很方便的让我们在各个组件之间,组件和线程之间进行通信,并具有很好的解耦特性。
Publisher 就是发布者、Subscriber 就是订阅者 ,它的大致流程就是:发布者发布事件给EventBus,EventBus将事件转发给注册了的订阅者。
它的优点如下:
- simplifies the communication between components
- decouples event senders and receivers
- performs well with Activities, Fragments, and background threads
- avoids complex and error-prone dependencies and life cycle issues
- makes your code simpler
- is fast
- is tiny (~50k jar)
- is proven in practice by apps with 100,000,000+ installs
- has advanced features like delivery threads, subscriber priorities, etc.
一般的使用步骤如下:
1.使用android studio,在你项目的app目录下的build.gradle中添加对EventBus的应用
dependencies { compile 'org.greenrobot:eventbus:3.0.0'}
2.创建自定义的event对象,这个event就是我们发布者传递给订阅者的对象,订阅者拿到这个对象后可以做一些具体的操作,这个event需要是个POJO对象:Plain Old Java Object 是指那些没有从任何类继承、也没有实现任何接口,更没有被其它框架侵入的java对象
public class MessageEvent { public final String message; public MessageEvent(String message) { this.message = message; }}
3.准备订阅者,这里包含两个步骤
第一、向EventBus注册订阅者,这里使用默认的EventBus
@Overridepublic void onStart() { super.onStart(); EventBus.getDefault().register(this); //注册,将感兴趣的订阅者传入,可以是activity,fragment等等}@Overridepublic void onStop() { EventBus.getDefault().unregister(this); //反注册 super.onStop();}
第二、定义订阅者的回调函数
// This method will be called when a MessageEvent is posted (in the UI thread for Toast)@Subscribe(threadMode = ThreadMode.MAIN)public void onMessageEvent(MessageEvent event) { //接收MessageEvent 类型的事件,事件监听方法必须是public修饰的,如果你写成private了,则收不到消息,如果你所有的事件监听方法都不用public修饰(包括父类),则会直接报错 Toast.makeText(getActivity(), event.message, Toast.LENGTH_SHORT).show();}// This method will be called when a SomeOtherEvent is posted@Subscribepublic void handleSomethingElse(SomeOtherEvent event) { //接收SomeOtherEvent 类型的事件 doSomethingWith(event);}
4.发送事件
EventBus.getDefault().post(new MessageEvent("Hello everyone!"));//这里post是MessageEvent事件
其它须知:
one:
ThreadMode线程模式,即订阅者回调方法上面的注解,这个是3.0的新特性,通过这个线程模式可以指定回调函数是否跑在新线程@Subscribe(threadMode = ThreadMode.MAIN),默认情况下是ThreadMode: POSTING模式。
ThreadMode: POSTING:发布者post时是那个线程,那么订阅者的回调函数就在那个线程执行,因为不切换线程所以资源消耗最小
ThreadMode: MAIN:即订阅者不管发布者在哪个线程post,订阅者的回调函数都在UI 线程执行,即不能做耗时操作,容易引起ANR
ThreadMode: BACKGROUND : 如果是在UI 线程post,那么订eventbus会另起一个后台线程运行回调函数,并按顺序分发事件,只能有一个后台线程,注意不要堵塞后台线程
ThreadMode: ASYNC:不管post是在哪个线程,eventbus 都会新建一个线程执行回调函数,此时回调函数里可以做一些耗时操作,比如:网络访问,下载等,但是避免大量长时间使用异步线程
two:
配置一些特殊的EventBus对象:
前面的例子我们都是使用EventBus.getDefault()来获得一个默认的EventBus对象,然后做一些register、post这些操作,其实我们可以通过EventBusBuilder 这个类来配置一些特别的EventBus对象,比如:
正常情况下,默认的EventBus如果没有订阅者我们post事件出去时会有错误提示,但是我们可以定义一个特别的EventBus让它不提示这个错误信息,我们这样做:
EventBus eventBus = EventBus.builder().logNoSubscriberMessages(false) .sendNoSubscriberEvent(false).build();//创建一个eventbus对象并且不提示没有订阅者的错误信息
我们也可以通过installDefaultEventBus方法,将我们的特殊配置设置到默认的EventBus里面,这样即使我们通过EventBus.getDefault()获得的对象,也具有相应的特殊性质,但是,这个设置必须在第一次使用eventbus之前配置好,不然会报异常
EventBus.builder().throwSubscriberException(BuildConfig.DEBUG).installDefaultEventBus();
three:
粘沾性事件:Sticky Events 以sticky的形式post的最后一个事件,会保存在缓存中,待有对此事件感兴趣的订阅者时,订阅者会收到这个事件(即延迟接收)
EventBus.getDefault().postSticky(new MessageEvent("Hello everyone!"));//发送sticky事件 @Override public void onStart() { super.onStart(); EventBus.getDefault().register(this); } @Subscribe(sticky = true, threadMode = ThreadMode.MAIN)//订阅者需要指明sticky属性才能接收 public void onEvent(MessageEvent event) { // UI updates must run on MainThread textField.setText(event.message); } @Override public void onStop() { EventBus.getDefault().unregister(this); super.onStop(); }
我们还可以手动管理sticky事件
//第一种MessageEvent stickyEvent = EventBus.getDefault().getStickyEvent(MessageEvent.class);//获得sticky事件// Better check that an event was actually posted beforeif(stickyEvent != null) { // "Consume" the sticky event EventBus.getDefault().removeStickyEvent(stickyEvent); //处理事件后手动移除 // Now do something with it}//第二种MessageEvent stickyEvent = EventBus.getDefault().removeStickyEvent(MessageEvent.class);//获得sticky事件// Better check that an event was actually posted beforeif(stickyEvent != null) { // Now do something with it}
four:
Priorities and Event Cancellation:优先级和取消事件,即同一个线程模式下,如果有多个订阅者订阅同一个event,那么我就可以指定订阅者收到event的优先权,即priority 其值越大优先级越高,默认为0,我们还可以在高优先级中取消事件继续向低优先级分发。
// Called in the same thread (default)@Subscribe(priority = 1); //指定优先级为1public void onEvent(MessageEvent event) {EventBus.getDefault().cancelEventDelivery(event) ; //取消事件继续向低优先级发送}
five:
Subscriber Index :订阅者索引,通过apt(Annotation Processing Tool)的方式来代替java反射找到订阅者的回调函数,大大的提升了eventbus的执行效率,具体操作如下:
//在project的build.gradle添加如下信息buildscript { dependencies { classpath 'com.neenbedankt.gradle.plugins:android-apt:1.8' }}//在app的build.gradle添加如下信息apply plugin: 'com.neenbedankt.android-apt'dependencies { compile 'org.greenrobot:eventbus:3.0.0' apt 'org.greenrobot:eventbus-annotation-processor:3.0.1'}apt { arguments { eventBusIndex "com.example.admin.myeventbus.MyEventMessageindex" //这里的路径和MainActivity路径相同,MyEventBusIndex是我们自己定义的名字, }}
配置完成后rebuild一下项目,然后会在项目的一下目录生成一个以MyEventBusIndex命名的java文件,build\generated\source\apt\debug\com\example\admin\myeventbus\MyEventMessageindex.java
MyEventBusIndex文件生成后我们就可以在项目中是用了,使用方法如下:
EventBus eventBus = EventBus.builder().addIndex(new MyEventBusIndex()).build();//给项目中的eventbus添加MyEventBusIndex对象//或者将其添加到默认的eventbus中EventBus.builder().addIndex(new MyEventBusIndex()).installDefaultEventBus();// Now the default instance uses the given index. Use it like this:EventBus eventBus = EventBus.getDefault();//或者你可以添加多个索引类,这样可以实现更复杂的逻辑EventBus eventBus = EventBus.builder() .addIndex(new MyEventBusAppIndex()) .addIndex(new MyEventBusLibIndex()).build();
six:
ProGuard:代码混淆,在AS中我们使用android自带的Proguard来混淆我们的代码,写在我们项目的app/build.gradle 文件中,一般配置如下:
buildTypes { release { //只有release版本才会混淆代码 // 是否进行混淆 以前使用的是runProguard true命令 minifyEnabled false // 混淆文件的位置,其中proguard-android.txt为默认的配置文件,在SDK中,proguard-rules.pro为AS创建项目时自动生成的配置文件,我们自定义的混淆配置需要写在这个问题件中 proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } }
前提需要我们的sdk中包含Proguard,路径为:sdk安装目录/tools/proguard/proguard-android.txt
因为我们EventBus中订阅者的方法是回调函数,没有直接调用,所以,当我们做代码混淆时会把这些方法给删除,为了保证混淆后程序能够正常运行,我们需要配置混淆文件,让其不删除EventBus中的部分代码,配置如下,修改proguard-rules.pro文件:
-keepattributes *Annotation* //保护Annotation属性-keepclassmembers class ** { //保护指定类的成员 @org.greenrobot.eventbus.Subscribe <methods>;}-keep enum org.greenrobot.eventbus.ThreadMode { *; } //保护指定的类文件和类的成员# Only required if you use AsyncExecutor-keepclassmembers class * extends org.greenrobot.eventbus.util.ThrowableFailureEvent { <init>(java.lang.Throwable);}
http://greenrobot.org/eventbus/
https://github.com/greenrobot/EventBus
- EventBus 3.0 使用介绍
- EventBus 使用介绍
- EventBus 使用介绍
- EventBus 使用介绍
- EventBus使用介绍
- EventBus介绍与使用
- EventBus的初级使用介绍
- EventBus使用的简单介绍
- Android--EventBus的使用介绍
- EventBus 3.0 使用详解
- Eventbus 3.0 使用
- EventBus 3.0使用详解
- EventBus 3.0使用基础
- EventBus 3.0使用详情
- EventBus 3.0 使用
- EventBus 3.0 的使用
- EventBus 3.0的使用
- EventBus 3.0 简单使用
- MX、SPF记录查询的方法
- Ubuntu server 14.04下安装hadoop-2.6.4 集群机
- git简单操作
- 实训第三天--数字迷宫
- POJ 3281 Dining(最大流)
- EventBus 3.0 使用介绍
- LeetCode 100. Same Tree
- 渲染路径-实时渲染中常用的几种Rendering Path
- Elastic cache
- 串(String)--基本概念
- CXF和spring整合实现webservice实例(二)
- MyEclipse8.5 环境中配置Tomcat7.X
- Java运算符
- 自己认为好的博客(java+Android)