Broadcast相关总结

来源:互联网 发布:便签的元数据已损坏 编辑:程序博客网 时间:2024/06/08 13:13

个人对广播使用得不多,在目前接触的项目开发中暂时没有使用到广播作为组件间交流工具,仅仅是在做应用复活的时候,接触过利用系统广播拉活的机制(现在已经不那么灵验了)。不过广播接收者作为Android四大组件之一,其重要性自然不言而喻 ,也是各类面试的常客,还是得好好总结一番。


定义

广播是一种广泛应用的在应用程序之间传输信息的机制,Android中我们要发送的广播内容是一个Intent,这个Intent中可以携带我们要传送的数据。


使用场景

A、同一个app不同组件之间的消息通信(可以同进程或者不同进程)。
B、不同的app之间的组件之间进行通信。


种类与使用方式

  1. 普通广播(Normal Broadcast)
  2. 系统广播(System Broadcast)
  3. 有序广播(Ordered Broadcast)
  4. 粘性广播(Sticky Boradcast),在Android 5.0即API 21已经被废弃
  5. 本地广播(Local Broadcast)

1. 普通广播

普通广播就是我们最常使用的一种广播,使用方法如下:
* 发送:我们在代码中通过创建Intent,设置action,再通过Context调用sendBroadcast(Intent)方法发送。
* 接收
* 自定义一个广播接收者类继承自BroadcastReceiver,重写里面的onReceive(…)方法。
* 通过静态或者动态方式注册广播接收者:
* 静态:
在AndroidManifest.xml文件中的application标签内注册
java
<receiver android:name=".MyBroadcastReceiver">
<intent-filter>
<action android:name="123"/>
</intent-filter>
</receiver>

* 动态:
“` java
@Override
protected void onResume() {
super.onResume();
mReceiver = new MyBroadcastReceiver();
IntentFilter intentFilter = new IntentFilter(“123”);
registerReceiver(mReceiver, intentFilter);
}

            @Override            protected void onPause() {                super.onPause();                unregisterReceiver(mReceiver);            }        ```        要注意的是通过动态注册时,一定要记得注销。Activity的声明周期是成对出现的,因此在onResume方法中注册,在onPause方法中注销。因为当Activity由于内存不足被回收时,只能保证onPause方法被调用,在onPause方法中进行注销从而能避免内存泄漏。

2. 系统广播

系统广播是Android系统内置的广播。当手机状态发生改变时,系统会发出相应的预设的广播。具体有哪些系统广播请随时搜索,不同版本谷歌会增删一些广播。要注意的是不要总是期望能接收到系统广播,一些国产ROM出于安全考虑可能会屏蔽掉某些系统广播。


3. 有序广播

有序广播与普通广播类似,差别只在于发送时调用的是sendOrderedBroadcast(Intent)方法。有序广播发出去后,会根据广播接收者的优先级,按序传递,优先级高的广播接收者先接收到广播,可以对广播进行修改后再传递给优先级较低的广播接收者。也可以通过abortBroadcast()方法将广播拦截,这样优先级较低的广播接收者将无法再接收到这条广播。
至于广播接收者的优先级,可以通过IntentFilter的setPriority(int)方法设置。


4. 粘性广播

在Android 5.0 / Api 21中已被废弃


5. 本地广播

为了解决其他应用通过注册与当前应用一致的IntentFilter来接收一些敏感的广播的安全问题,可以使用本地广播。顾名思义,本地广播是只发往同个应用内的广播,其他应用无法收到。发送本地广播需要使用LocalBroadcastManager来进行,使用方法如下:

public class MainActivity extends AppCompatActivity {    private final String TAG = getClass().getSimpleName();    private BroadcastReceiver mReceiver;    private LocalBroadcastManager mLbm;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);    }    public void onClick(View view) {        Intent intent = new Intent("123");        mLbm.sendBroadcast(intent);        sendBroadcast(intent);        Log.i(TAG, "发送广播了");    }    @Override    protected void onResume() {        super.onResume();        if (mReceiver == null) {            mReceiver = new MyBroadcastReceiver();        }        if (mLbm == null) {            IntentFilter intentFilter = new IntentFilter("123");            mLbm = LocalBroadcastManager.getInstance(this);            mLbm.registerReceiver(mReceiver, intentFilter);        }    }    @Override    protected void onPause() {        super.onPause();        if (mLbm != null && mReceiver != null) {            mLbm.unregisterReceiver(mReceiver);        }    }}

除了通过这种方法来保证广播的安全性之外,我们还可以在发送普通广播的时候,利用Intent指定接收的应用的包名,避免发送给其他应用,如下:

intent.setPackage(String packageName);

上面两种方式能保证我们发送的广播只被自身应用接收到。而要使应用内自定义的广播接收者不接受其他应用的广播,只需要在注册广播接收者的时候指定exported属性为false就可以了:

        <receiver android:name=".MyBroadcastReceiver"            android:exported="false">            <intent-filter>                <action android:name="123"/>            </intent-filter>        </receiver>

exported属性如果没有设置,默认有intent-filter时为true,否则为false

原创粉丝点击