一、广播(broadcast receiver):属于Android四大组件之一,是一个全局的监听器。你的应用可以使用它对外部事件进行过滤,只对感兴趣的外部事件(如当电话呼入时,或数据网络可用是),进行接收并做出响应。广播接收区没有用户界面。然而,它可以启动一个Service或者Activity来响应他们接收的信息,或者NotificationManager来通知用户。通知可以用很多种方式来吸引用户的注意力,列如闪动背灯、震动,播放声音等,一般来说是在状态栏上放一个持久的图标,用户可以打开它并获取信息。
1、 分类: Android广播分为两个角色:广播发送者和广播接受者。
2、 作用:监听/接收应用App发出的广播消息,并做出响应。
3、应用场景:Android不同组件的通信(含:应用内/不同应用之间)
多线程通信
与Android系统在特定情况下的通信,如:电话呼入时,网络可用时。
4、实现原理:
(1)、采用的模型
Android中的广播使用了设计模式中的观察者模式/基于消息的发布/订阅事件模型,因此,Android将广播的发送者和接收者解耦,使得系统方便集成,更易扩展。
(2)、模型讲解
模型中有三个角色
消息订阅者(广播接受者:BroadcastReceiver ),
消息发送者(广播发送者:Context.sendBroadcast()),
消息中心(AMS:即Activity Manager Service)。
(3)、原理:
原理示意图原理描述:
a、广播接收者,通过Binder机制在AMS注册。
b、广播发送者,通过Binder机制想AMS发送发送广播。
c、AMS根据广播发送者要求,在已注册列表中,寻找合适的广播接收者。(寻找依据:intentFilter/Permission)。
d、AMS将广播发送到合适的广播接收者相应的消息循环队列中。
e、广播接收者通过消息循环拿到此广播,并回调 onReceiver()。
特别注意:广播发送者和广播接收者的执行都是异步的,即广播发送者不会关心有无接收者接收,也不确定接收者何时才能接收到。
5、广播的注册方式:静态注册和动态注册
(1)、静态注册:清单文件注册
注册方式:在AndroidManifest.xml里通过<receiver>标签声明。
区 别:静态注册无需担忧广播接收器是否被关闭,只要设备是开启状态,广播接收器也是打开着的,也就是说哪怕app本身未启动,该app订阅的广播在触发时也会对他起作用。
代 码:
静态注册示例代码(2)、动态注册:代码中注册
注册方式:在代码中调用Context.registerReceiver()方法
区 别:动态注册广播接收器的特点是当用来注册的Activity关闭后,广播也就失效了。
代 码:
动态注册是示例代码特别注意:动态广播最后在Activity的onResum()注册,onPause()注销。原因:
1、对于动态广播,有注册就必然有注销,否则会导致内存泄漏。重复注册,重复注销也不被允许。
2、在onResum()注册、onPause()注销是因为onPause()在App死亡前一定会被执行,从而保证广播在App死亡前一定会被注销,从而防止内存泄漏。不在onCreate()&onDestory()或onStart()&onStop()注册、注销,是因为:当系统因为内存不足(优先级更高的应用需要内存)要回收Activity占用的资源时,Activity在执行完onPause()方法后就会被销毁,有些生命周期方法onStop()、onDestory()就不会在执行,当再回到此Activity时,是从onCreate()开始执行。
3、假设我们将广播的注销放在onStop(),onDestory()方法里面,有可能在Activity被销毁后还未执行onStop(),onDestory()方法,即广播任还未注销,从而导致内存泄漏。但是onPause()一定会被执行,从而保证了广播在App死亡前一定会被注销,从而防止内存泄漏。
5、广播接收者和广播发送者。
(1)、广播接收者:简单的说,就是接受广播意图的java类,此java类继承BroadcastReceiver类,重写public void onReceive(Context context,Intent intent),其中intent可以获得传递的数据;
广播意图是通过Context.sendBroadcast(Intent intent)或Contetxt.sendOrderedBroadcast(Intent intent)发送的意图,通过这个语句,能够广播给所以满足条件的组件,比如intent设置了action="com.xiazdong"则所有在AndroidManifest.xml中设置过<action android:name="com.xiazdong"/>的广播接收者都能够接收到广播;
注:onReceive方法必须在10秒内完成,如果没有完成,则抛“Application No Response”当广播接收者onReceive方法需要执行很长时间时,最好将此耗时工作通过Intent发送给Service,由Service完成,并且不能使用子线程解决,因为BroadcastReceiver是接收到广播后才创建的,并且生命周期很短,因此子线程可能在没有执行完就已经被杀死了。
(2)、广播发送者:
通常广播发送方就是调用Context.sendBroadcast()的程序,而广播接收者就是继承BroadcastReceiver的程序;
通常广播发送方都是通过隐式意图,这样才能发送给多人;
广播发送方分为普通广播和有序广播;
同步广播:发送方发出后,几乎同时到达多个广播接收者处,某个接收者不能接收到广播后进行一番处理后传给下一个接收者,并且无法终止广播继续传播;Context.sendBroadcast(intent);
有序广播:广播接收者需要提前设置优先级,优先级高的先接收到广播,优先级数值为-1000~1000,在AndroidManifest.xml的设置;比如存在3个广播接收者A、B、C,优先级A>B>C,因此A最先收到广播,当A收到广播后,可以向广播中添加一些数据给下一个接收者(intent.putExtra()),或者终止广播(abortBroadcast());Context.sendOrderedBroadcast(intent);
相关文章阅读
网友评论