BroadcastReceiver组件的基础认识

来源:互联网 发布:everything软件ftp 编辑:程序博客网 时间:2024/05/18 01:35


广播接收器简介


在Android中,有一些操作完成以后,会发送广播,比如说发出一条短信,或打出一个电话,如果某个程序接收了这个广播,就会做相应的处理。它只负责“说”而不管你“听不听”,也就是不管你接收方如何处理。另外,广播可以被不只一个应用程序所接收,当然也可能不被任何应用程序所接收。

四大组件之中的广播接收器(BroadcastReceiver)也是我比较常用但是却用得较为迷糊的一个组件。一直以为广播是四大组件之一,其实,它的接收器((BroadcastReceive)才是。现在就为自己总结一下

既然是安卓组件,那就少不了要在AndroidManifest.xml中进行注册使用。其中manifest单词的意思是货单、清单。但是,相比于Activity和Service组件而言,
广播接收器的注册方式不仅限于静态的在AndroidMainfest中注册,还可以调用ContextWrapper的registerReceiver()方法进行动态注册,但是动态注册的话,需要在退出程序的时候解除注册,否则会报错提醒没有进行解除注册,所以谨记解除注册。
关于动态注册。
在谷歌官方API中有这么一句话:
Note:    If registering a receiver in your Activity.onResume() implementation, you should unregister it in Activity.onPause(). 
这只是一句提醒而已,但是网上有人建议在onResume()中进行动态注册,然后在onPause()中解除注册,说这样能够减轻系统的负载和内存消耗,不用一直接受广播。
但是不排除有些时候在熄屏的时候需要用到广播。
所以我觉得是网上的同学们一句善意的提醒。怎么用还是按国情需要见仁见智具体分析啦。


应用广播实例

本案例为:
发送广播---->接收器响应---->另外APP中的接收器响应(该APP启动和没有启动都没有关系)


实现广播接收器的接口

package zy.zh.broadcastdemo;public class DemoReceiver extends BroadcastReceiver {private int count = 0;/** * 因为特殊的10秒生命周期,每次接收广播都会实例化一次 */public DemoReceiver() {super();count++;Log.i(getClass().getSimpleName(),"DemoReceiverServe Construct count = " + count);}@Overridepublic void onReceive(Context context, Intent intent) {Toast.makeText(context,"同进程接收广播onReceiver, Msg=" + intent.getExtras().getString("Msg"),Toast.LENGTH_LONG).show();Log.i(getClass().getSimpleName(), "同进程接收广播called onReceive");}}
注册接收器组件(动态和静态都可以):

AndroidManifest.xml中静态注册:

<receiver    android:name="zy.zh.broadcastdemo.SecondReceiver"    android:exported="true" >    <intent-filter><action android:name="zh_demo_filter" />    </intent-filter></receiver>


代码中动态注册:
public class App extends Application {@Overridepublic void onCreate() {super.onCreate();IntentFilter filter = new IntentFilter();filter.addAction("zh_demo_filter");registerReceiver(new DemoReceiver(), filter);registerReceiver(new SecondReceiver(), filter);}}

发送广播:

button1.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {Intent intent = new Intent();intent.setAction("zh_demo_filter");intent.putExtra("Msg", "hello BroadCast");sendBroadcast(intent);}});

以上是在同一个应用中进行的。下面要跨进程的在另外一个应用中监听该广播:

实现接收器接口:

public class ClientReceiver extends BroadcastReceiver {@Overridepublic void onReceive(Context context, Intent intent) {String reuslt = "跨进程客户端 onReceiver, Msg=" + intent.getExtras().getString("Msg");Toast.makeText(context,reuslt,Toast.LENGTH_LONG).show();Log.i(getClass().getSimpleName(),getClass().getSimpleName()+reuslt);}}
静态注册:因为静态注册方式的特点:不管该应用程序是否处于活动状态,都会进行监听。

 <receiver    android:name="zy.zh.broadcastclient.ClientReceiver"    android:exported="true" >    <intent-filter><action android:name="zh_demo_filter" />    </intent-filter></receiver>

运行程序:





可怜的生命周期

BroadcastReceiver本质上是一个系统级的监听器,它专门负责监听各个程序所发出来的Broadcast,
每次系统Broadcast事件发生后,系统就会创建对应的BroadcastReceiver的实例,并且自动触发它的onReceive()方法,onReceive()方法执行完后,BroadcastReceiver的实例就会被销毁。
我亲手试验了,可以接收不同程序的广播,就算是BroadcastReceiver所在的App没有启动(刚开机),可完全可以接收都其他APP发出来的广播。
所以,4大组件之间的关系,都是在不同进程中进行的,特别是BroadcastReceiver,尤为特别,不过我喜欢,因为他居然可以监听到系统开机的广播,干的漂亮。
这已经是明显的IPC了这个组件。
与Activity组件更加给力的地方是,当系统通过Intent启动指定的Activity组件时,如果系统找不到合适的Activity组件,会导致程序异常终止,。但是系统通过Intent激发BroadcastReceiver时,找不到合适的BroadcastReceiver组件,应用没有任何问题一切照旧。
每次系统Broadcast事件发生后,系统就会创建对应的BroadcastReceiver的实例,并自动触发它的onReive()方法,onRceive()方法执行完后,BroadcastReceiver的实例就会被销毁。所谓的对应的BroadcastReceiver的实例,就是所以APP的AndroidManifestt配置文件中注册到的接收器都会被实例化,然后销毁,下次还有广播,再重新实例化一个新的,然后触发它的onReive()。
如果BroadcastReceive的onReceive()方法不能在10秒内执行完成,Android会认为该程序无响应。所以不要在onReceive()方法里执行一些耗时的操作,否则就会弹出ANR(Application No Response)的对话框。
如果这样,有耗时操作的话,请联系Service。


关于广播方式

普通广播:sendBroadcast(intent);

有序广播:sendOrderedBroadcast(intent,null);

粘性广播:sendStickyBroadcast(intent);

后续了解,to be continue........

手写总结,转载请注明出处http://blog.csdn.net/dreamintheworld/article/details/38532119



0 0
原创粉丝点击