Android组件系列——BroadCastReceiver

BroadCast

进程间传输信息的机制,通过Intent携带书数据进行通信

无序、有序广播内部实现机制

1、自定义类继承BroadcastReceiver,并重写onReceiver()
2、通过Binder机制向AMS(Activity Manager Service)进行注册
3、通过Binder机制向AMS发送广播
4、AMS查找符合条件(IntentFilter/Permission等)的BroadcastReceiver,将广播发送到相应的BroadcastReceiver(一般情况下是Activity)的消息队列中
5、消息循环执行拿到此广播,回调BroadcastReceiver中的onReceiver()方法

无序广播(Normal BroadCast)

优点:完全异步,所有接收者均可同时接收,受优先级影响,越高,传递效率越高

弊端:接收者不能将内容传递给其他接收者,无法终止广播传递

发送

Intent intent = new Intent();		//定义一个意图
intent.setAction("com.hengtang.broadcast");		//设置意图action
intent.putExtra("data", "我是无序广播的数据");		//绑定数据
sendBroadcast(intent);			//发送无序广播

注册

<receiver android:name="com.hengtang.myreceiver.MyReceiver">
    <intent-filter >
        <action android:name="com.hengtang.broadcast"/>	//action相同的receiver才能接收到
     </intent-filter>
</receiver>

接收

自定义类BroadCastReceiver继承BroadcastReceiver,重写onReceive方法				
Intent.getStringExtra("data");	//获取到广播数据

有序广播(OrderedBroadCast)

受优先级影响,按照接收者声明的优先级高低,依次接收传递,在前面的接收者可修改广播内容或终止广播

发送

Intent intent = new Intent();
intent.setAction("com.hengtang.sendhongbao");
sendOrderedBroadcast(intent, null, new MyReceiver(), null, 1, "每人10块", null);
参数 类型 内容
1 Intent 意图
2 String receiverPermission,接收器需要的权限
3 BroadcastReceiver 自己定义的接收者作为最终接收者,获取传递到最后的数据,用于监听
4 Handler 用于执行接收器的回调,如果为null 则在主线程中执行
5 Int 结果代码的初始码
6 初始化参数
7 Bundle 额外的数据

注册

<receiver android:name="com.hengtang.ErNaiReceiver" >
	<intent-filter android:priority="1000">
		<action android:name="com.hengtang.sendhongbao" />
	</intent-filter>
</receiver>
<receiver android:name="com.hengtang.ErNaiReceiver" >
	<intent-filter android:priority="800">			//配置优先级,-1000 到1000
		<action android:name="com.hengtang.sendhongbao" />
	</intent-filter>
</receiver>

接收

public class ErNaiReceiver extends BroadcastReceiver {
	@Override
	public void onReceive(Context context, Intent intent) {
		String data = getResultData();
		setResultData("每人7块");		//重新设置广播信息
	}
}
public class SanNaiReceiver extends BroadcastReceiver {
	@Override
	public void onReceive(Context context, Intent intent) {
		String data = getResultData();			//通过输出getResultData()的值可以达到监听的目的
		setResultData("每人五块");	
 		abortBroadcast();  //终止广播 
	}
}

本地广播(LocalBroadCast)

//注册
 localBroadcastManager.registerReceiver(myBroadCast, intentFilter);
//发送
localBroadcastManager.sendBroadcast(Intent);

特点

​ 只在当前App内传播,更安全,比系统广播更有效
其他App不能对自己发送该广播,无需担心安全漏洞被利用
Receiver只允许动态注册,不允许在Manifest中注册
LocalBroadcastManager所发送的广播action,只能与注册到LocalBroadcastManager中BroadcastReceiver产生互动

内部实现机制

​ 内部通过Hanlder实现,发送广播其实是利用Hanlder发送一条Message。
内部协作通过mReceivers和mActions两个Map集合和一个mPendingBroadcasts(待接收的广播对象)的List集合完成
而系统广播通过Binder机制实现,因此更高效

两种注册方式

静态注册

​ 通过AndroidManifest.xml 注册

动态注册

​ 通过代码注册,在本文中前面使用到的BroadCastReceiver 全部都使用的是静态注册方式,其实也可以使用动态注册,但是对于锁屏解屏和电量变化的监听只能通过动态注册

区别

静态注册是当程序关闭后,如果有广播发过来,还能启动程序

动态注册的生命周期跟程序的生命周期是一样的,程序关闭后动态注册的广播是不能在接收到广播的

各自优点

动态注册的优点:在Android的广播机制中,动态注册的优先级高于静态注册的优先级,因此在必要情况下,我们需要动态注册广播接收器。当用来注册广播的Activity关闭后,广播也就失效了

静态注册的优点:无需担心广播接收器是否关闭,只要设备处于开启状态,广播接收器就能接收

动态注册案例

public class MainActivity extends Activity {	
	ScreenStatusReceiver receiver;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		//注册广播接受者
		receiver = new ScreenStatusReceiver();		
		IntentFilter filter = new IntentFilter();
		filter.addAction("android.intent.action.SCREEN_OFF");	//手机锁屏
		filter.addAction("android.intent.action.SCREEN_ON");	//手机亮屏
		registerReceiver(receiver, filter);
	}
	@Override
	protected void onDestroy() {	//当锁屏的时候调用,将activity销毁,如果不销毁,会造成内存泄漏
		// 取消注册广播接受者
		unregisterReceiver(receiver);	//在activity销毁的同时,应该取消注册广播接收者(反注册)
		receiver = null;				//将接收者对象置为空,让垃圾回收器更快的回收掉
		super.onDestroy();
	}
}

public class ScreenStatusReceiver extends BroadcastReceiver {
	@Override
	public void onReceive(Context context, Intent intent) {
		String action = intent.getAction();
		System.out.println("action:"+action);
	}
}

猜你喜欢

转载自blog.csdn.net/mLuoya/article/details/87927127