EventBus框架的使用

参考文章:http://blog.csdn.net/yuanzeyao/article/details/38174537

EventBus源码以及jar的下载地址:https://github.com/greenrobot/EventBus/tree/V3.0.0  http://download.csdn.net/detail/yy1300326388/8727699

       在android 项目开发中,事件传递我们一般使用handler ,broadcast 和receiver等,但是这些东西东西多起来就会比较烦。比如handler 基本在每一个activity中都会有一个 ,而且还要将它写成静态(不然容易引起内存泄露),使得我们的项目看起来非常的不爽。于是EventBus开源框架就出来了。当我开始使用EventBus后,一个字爽,老子再也不要用什么startActivityforResult,handler,大量的广播等等一些操蛋东西了。吐槽完毕下面简单的介绍一下EventBus的四个订阅函数.

onEvent:如果使用onEvent作为订阅函数,那么该事件在哪个线程发布出来的,onEvent就会在这个线程中运行,也就是说发布事件和接收事件线程在同一个线程。使用这个方法时,在onEvent方法中不能执行耗时操作,如果执行耗时操作容易导致事件分发延迟。
onEventMainThread:如果使用onEventMainThread作为订阅函数,那么不论事件是在哪个线程中发布出来的onEventMainThread都会在UI线程中执行,接收事件就会在UI线程中运行,这个在Android中是非常有用的,因为在Android中只能在UI线程中跟新UI,所以在onEvnetMainThread方法中是不能执行耗时操作的。
onEvnetBackground:如果使用onEventBackgrond作为订阅函数,那么如果事件是在UI线程中发布出来的,那么onEventBackground就会在子线程中运行,如果事件本来就是子线程中发布出来的,那么onEventBackground函数直接在该子线程中执行。
onEventAsync:使用这个函数作为订阅函数,那么无论事件在哪个线程发布,都会创建新的子线程在执行onEventAsync.

简单介绍完EventBus咱们开始去学习EventBus的使用。

1.如果你想在所有的activity或者fragment中使用,建议写一个BaseActivity,下面是我写的一个简单的BaseActivity

package com.mao.activity;

import com.mao.event.FinishEvent;

import de.greenrobot.event.EventBus;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;

public class BaseActivity extends FragmentActivity{
	
	@Override
	protected void onCreate(Bundle arg0) {
		// TODO Auto-generated method stub
		super.onCreate(arg0);
		register();
	}
	
	public void register(){
		EventBus.getDefault().register(this);
	}
	@Override
	protected void onDestroy() {
		super.onDestroy();
		EventBus.getDefault().unregister(this);
	}
	public void onMainEventThread(FinishEvent finishEvent){
		finish();
	}
}
其中 register方法为注册观察者,在oncreate方法中调用,为什么要写成一个方法呢?因为注册有多种多样,比如延时注册,优先级等等。想要使用不同的注册方法,重写这个方法即可,和广播服务一样,注册了就得取消注册,咱们在ondestroy中取消注册。

在baseactivity中我还写了一个onMainEventThread方法,这就是上文所说的订阅函数。主要作用就是,我们想要退出整个app的时候发出一个退出消息即可。细心的朋友一定看到了onMainEventThread的参数,没错这个类就是相当于一个标记,比如你在某一个avtivity中发出了消息

EventBus.getDefault().post(new FinishEvent());
<pre name="code" class="java"><span style="font-size:18px;">发送消息有两种,一种是post(),另外一种是postSticky(),post发出消息不会保留,<span style="font-family: Arial, Helvetica, sans-serif;">postSticky会将消息保留到消息队列中,比如你的activity还没有被激活,使用post发消息,activity激活后是收不到消息的,而</span></span><pre name="code" class="java"><span style="font-size:18px;">postSticky能够收到消息。</span>

 
 
<pre name="code" class="java">
 
<span style="font-size:18px;">这时候订阅函数的参数只要是FinishEvent都会收到这消息,从而执行相应的操作,这里是关闭所有activity.FinishEvent如下:</span>
<pre name="code" class="java">package com.mao.event;

public class FinishEvent {

}


 
这里是一个空类,起到的作用仅仅是一个标记而已,这个类也可以加上各种各样的属性但是必须要有get set方法。 

2.使用EventBus实现handler,线程的功能。

有时候我们需要在子线程中做了某个操作之后,发出message告诉handler来更新UI,使用EventBus也能实现相应的功能,而且更方便,代码耦合更低。

下面我们使用EventBus实现这个简单的功能。

package com.mao.activity;

import android.app.Activity;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteDatabase.CursorFactory;
import android.database.sqlite.SQLiteOpenHelper;
import android.os.Bundle;
import android.os.IBinder;
import android.os.RemoteException;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;

import com.example.unit11_test_3.R;
import com.iotek.service.aidl.IPerson;
import com.iotek.service.aidl.Person;
import com.mao.event.AsyncOnclickEvnet;
import com.mao.event.onClickEvent;

import de.greenrobot.event.EventBus;

public class MainActivity extends BaseActivity implements OnClickListener{
	Button btn_one_second,btn_two_second,btn_three_second;
	TextView tv;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		btn_one_second=(Button)findViewById(R.id.btn_one_second);
		btn_two_second=(Button)findViewById(R.id.btn_two_second);
		btn_three_second=(Button)findViewById(R.id.btn_three_second);
		tv=(TextView)findViewById(R.id.textView1);
		btn_one_second.setOnClickListener(this);
		btn_two_second.setOnClickListener(this);
		btn_three_second.setOnClickListener(this);
	}
	@Override
	public void onClick(View v) {
		switch (v.getId()) {
		case R.id.btn_one_second:
			EventBus.getDefault().post(new AsyncOnclickEvnet(1));
			break;
		case R.id.btn_two_second:
			EventBus.getDefault().post(new AsyncOnclickEvnet(2));
			break;
		case R.id.btn_three_second:
			EventBus.getDefault().post(new AsyncOnclickEvnet(3));
			break;
		default:
			break;
		}
	}
	public void OnEvnetMainThread(onClickEvent onClickEvent){
		switch (onClickEvent.getAction()) {
		case 1:
			tv.setText("1秒以後修改的");
			break;
		case 2:
			tv.setText("2秒以後修改的");
			break;
		case 3:
			tv.setText("3秒以後修改的");
			break;
		default:
			break;
		}
	}
	public void onEventAsync(AsyncOnclickEvnet asyncOnclickEvnet){
		switch (asyncOnclickEvnet.getAction()) {
		case 1:
			try {
				Thread.sleep(1000);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			EventBus.getDefault().post(new onClickEvent(1));
			break;
		case 2:
			try {
				Thread.sleep(2000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			EventBus.getDefault().post(new onClickEvent(2));
			break;
		case 3:
			try {
				Thread.sleep(3000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			EventBus.getDefault().post(new onClickEvent(3));
			break;
		default:
			break;
		}
	}
}


上面是我们MainActivity,主要实现功能就是点击按钮,一秒之后,两秒之后,三秒之后修改TextView的文本。

在Mainactivity中onMainEventThread()相当于我们的handler,onEventAsync相当子线程。传递消息的标记就是OnclickEvnet 和AsyncOnclickEvnet.OnclickEvnet 如下:

package com.mao.event;

public class onClickEvent {
	private int action;

	public int getAction() {
		return action;
	}

	public void setAction(int action) {
		this.action = action;
	}

	public onClickEvent(int action) {
		this.action=action;
	}
	public onClickEvent() {
	}
}
我添加了一个action属性,以便于知道是哪个按钮被点击了。当我们post一个消息,EventBus会通过反射将我们对象给订阅函数。然后我们通过判断action的值就可以知道是点击的哪个按钮,这里的OnclickEvnet 大家可以将他看成handler中的message,同样也可以传递Object对象。

例子讲完了,在上面我们只使用了两个订阅函数,但是其他的两个也是差不多的,只要掌握了这两个其他两个使用起来一样一样的。下面说几个我使用我过程中遇到的小问题。

1、注意我们传递参数的类一定要写成javaBean的形式,也就是必须要有get set方法。

2、一个注册了EventBus事件的类必须要有一个订阅函数,否则报的错误会让你怀疑人生。(我就因为写错了一个单词将onMainEventThread写成onMianEventThread,找了整整一个小时哭

3、同样的订阅函数可以有多个,只要参数不同即可,比如onMainEventThread你爱写多少个就可以写多少个只要Event不同微笑

4、注册之后一定要记得反注册,否则怎么死的都知道大哭

5、一定不要注册两次,否则会RuntimeException,这个运行的时候就会提示你。

到这里也就结束了,这是我第一个次写博客,有理解不恰当或者错误的地方望各位大牛指正微笑。想要更深层次的了解EventBus可以看这篇文章http://blog.csdn.net/yuanzeyao/article/details/38174537


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值