1 Broadcast是Android中的四大组件之一,他的用途很大,比如系统的一些广播:电量低、开机、锁屏等一些操作都会发送一个广播。
2 广播被分为两种不同的类型:“普通广播(Normalbroadcasts)”和“有序广播(Ordered broadcasts)”.普通广播是完全异步的,可以在同一时刻(逻辑上)被所有广播接收者接收到,消息传递的效率比较高,但缺点是:接收者不能将处理结果传递给下一个接收者,并且无法终止广播Intent的传播;然后有序广播是按照接收者声明的优先级别(声明在intent-filter元素的android:priority)属性中,数越大优先级别越高,取值范围:-1000到1000。也可以调用IntentFilter对象的setPriority()进行设置),被接收者依次接收广播。如:A的级别高于B,B的级别高于C,那么,广播先传A,在传给B,最后传给C,A得到广播后,可以往广播里存入数据,当广播传给B时,B可以从广播中得到A存入的数据。
Context.sendBroadcast()
发送的是普通广播,所有订阅者都有机会获得并进行处理。
Context.sendOrderedBroadcast()
发送的是有序广播,系统会根据接收者声明的优先级按顺序逐个执行接收者,前面的接收者有权终止广播(通过调用BroadcastReceiver.abortBroadcast()),如果广播被前面的接收者终止,后面的接收者就再也无法获取到广播。对于有序广播,前面的接收者可以将处理结果存进广播Intent,然后传给下一个接收者。
编写以下案例:
3 编写Android清单文件
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.itheima.broadcasttest"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="19" />
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme" >
<activity
android:name="com.itheima.broadcasttest.MainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<receiver android:name="com.itheima.broadcasttest.Level1Receiver" >
<intent-filter android:priority="1000" >
<action android:name="com.itheima.broadcasttest.songwennuan" />
</intent-filter>
</receiver>
<receiver android:name="com.itheima.broadcasttest.Level2Receiver" >
<intent-filter android:priority="500" >
<action android:name="com.itheima.broadcasttest.songwennuan" />
</intent-filter>
</receiver>
<receiver android:name="com.itheima.broadcasttest.Level3Receiver" >
<intent-filter android:priority="100" >
<action android:name="com.itheima.broadcasttest.songwennuan" />
</intent-filter>
</receiver>
<receiver android:name="com.itheima.broadcasttest.FinalReceiver" >
<intent-filter android:priority="0" >
<action android:name="com.itheima.broadcasttest.songwennuan" />
</intent-filter>
</receiver>
</application>
</manifest>
4 编写布局文件activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity" >
<Button
android:onClick="send1"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="发送无序广播" />
<Button
android:onClick="send2"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="发送有序广播" />
</LinearLayout>
5 编写一下广播接收者
Level1Receiver
package com.itheima.broadcasttest;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
public class Level1Receiver extends BroadcastReceiver {
private static final String TAG = "Broadcasttest";
@Override
public void onReceive(Context context, Intent intent) {
String message = getResultData();
Log.i(TAG,"省级部门得到中央的消息:" + message);
abortBroadcast(); //这里是终止了消息,可以关闭或者取消这里查看LogCat中打印的效果。
setResultData("给农民兄弟发5000块钱");
}
}
Level2Receiver
package com.itheima.broadcasttest;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
public class Level2Receiver extends BroadcastReceiver {
private static final String TAG = "Broadcasttest";
@Override
public void onReceive(Context context, Intent intent) {
String message = getResultData();
Log.i(TAG,"市级部门得到省级的消息" + message);
setResultData("给农民兄弟发2000块钱");
}
}
Level3Receiver
package com.itheima.broadcasttest;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
public class Level3Receiver extends BroadcastReceiver {
private static final String TAG = "Broadcasttest";
@Override
public void onReceive(Context context, Intent intent) {
String message = getResultData();
Log.i(TAG, "乡级部门得到市的消息:" + message);
setResultData("给农民兄弟发两大大米");
}
}
FinalReceiver
package com.itheima.broadcasttest;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
public class FinalReceiver extends BroadcastReceiver {
private static final String TAG = "Broadcasttest";
@Override
public void onReceive(Context context, Intent intent) {
String message = getResultData();
Log.i(TAG, "农民兄弟得到乡的消息:" + message);
}
}
6 MainActivity的内容如下:
package com.itheima.broadcasttest;
import android.content.Intent;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.view.View;
public class MainActivity extends ActionBarActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
/**
* 发送无序广播
* @param view
*/
public void send1(View view) {
Intent intent = new Intent();
intent.setAction("com.itheima.broadcasttest.songwennuan");
intent.putExtra("msg", "发1万块");
//无序广播,不可被拦截,不可终止
sendBroadcast(intent);
}
public void send2(View view) {
Intent intent = new Intent();
intent.setAction("com.itheima.broadcasttest.songwennuan");
//有序广播,可被拦截,可终止,可以修改数据
sendOrderedBroadcast(intent, null,new FinalReceiver(),null,0,"给农民兄弟发10000块钱",null);
}
}
运行:
点击”发送无序广播”按钮,在LogCat中打印出的内容如下:
点击” 发送有序广播”按钮,在LogCat中打印出的内容如下:
之所以在Level1Receiver执行了abortBroadcast()后还显示下面一条,是因为指定了之中广播:
//有序广播,可被拦截,可终止,可以修改数据
sendOrderedBroadcast(intent, null,new FinalReceiver(),null,0,"给农民兄弟发10000块钱",null);
若把Level1Receiver改成如下时:
package com.itheima.broadcasttest;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
public class Level1Receiver extends BroadcastReceiver {
private static final String TAG = "Broadcasttest";
@Override
public void onReceive(Context context, Intent intent) {
String message = getResultData();
Log.i(TAG,"省级部门得到中央的消息:" + message);
//abortBroadcast(); //这里是终止了消息,可以关闭或者取消这里查看LogCat中打印的效果。
setResultData("给农民兄弟发5000块钱");
}
}
点击”发送有序广播”后显示的内容如下:
==========================================================================
关于有序广播的另外的一个案例:
1、编写第一个广播MyOrderBroadcastReciver
package com.demoorderbroadcast;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
public class MyOrderBroadcastReciver extends BroadcastReceiver {
private static final String TAG = "BroadCast";
@Override
public void onReceive(Context context, Intent intent) {
String strMsg = intent.getStringExtra("msg");
Log.i(TAG, "第一个:" + strMsg);
//通过Bundle传递参数
Bundle extras = new Bundle();
extras.putString("msg", "第一个界面传过来的" + strMsg);
setResultExtras(extras);//继续向下传
}
}
2 编写第二个广播MyOrderBroadcastReciverTwo
package com.demoorderbroadcast;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
public class MyOrderBroadcastReciverTwo extends BroadcastReceiver {
private static final String TAG = "BroadCast";
@Override
public void onReceive(Context context, Intent intent) {
//abortBroadcast(); //开启此处,可以截断广播,不让它传到third中
String strMsg = intent.getStringExtra("msg"); //获取广播的原始数据
Log.i(TAG, "第二个界面传过来的" + strMsg);
Bundle extras = new Bundle();
extras.putString("msg", "第二个界面传过来的" + strMsg);
setResultExtras(extras); //继续向下传
//"第二个:"+strMsg这是two中新的数据,传递到third中,
//在third中是用getResultData来获得setResultData("")中的数据
setResultData("第二个:" + strMsg);
}
}
3 编写第三个广播MyOrderBroadcastReciverThird
package com.demoorderbroadcast;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
public class MyOrderBroadcastReciverThird extends BroadcastReceiver {
private static final String TAG = "BroadCast";
@Override
public void onReceive(Context context, Intent intent) {
//获得two中setResultData中的数据
String resultData = getResultData();
//获取two中setResultExtras中的数据
Bundle bundle = getResultExtras(true);
//获取广播的原始数据
String bundleData = bundle.getString("msg");
//获取广播的原始数据
String strMsg = intent.getStringExtra("msg");
Log.i(TAG, "第三个:" + strMsg);
Log.i(TAG,"two中传递到third新的数据:" + resultData);
Log.i(TAG, "two中setResultExtras(extras)传到third新的数据:" + bundleData);
}
}
4 编写MainActivity,代码如下:
package com.demoorderbroadcast;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
public class MainActivity extends Activity {
private Button btnSendOrderBroadCast;
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();
}
private void initView() {
btnSendOrderBroadCast = (Button) this.findViewById(R.id.btn);
btnSendOrderBroadCast.setOnClickListener(new MyOnclickListener());
}
private class MyOnclickListener implements OnClickListener {
public void onClick(View v) {
if (btnSendOrderBroadCast==v) {
sendOrderBroadCast();
}
}
}
public void sendOrderBroadCast() {
Intent intent = new Intent("com.pzf.mybroadcast");
intent.putExtra("msg", "toto ni hao");
sendOrderedBroadcast(intent, "com.pzf.permission");
}
}
5 编写Android的清单文件AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.demoorderbroadcast"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="19" />
<permission android:name="com.pzf.permission" android:protectionLevel="normal"></permission>
<uses-permission android:name="com.pzf.permission"/>
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme" >
<activity
android:name="com.demoorderbroadcast.MainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<receiver android:name="com.demoorderbroadcast.MyOrderBroadcastReciver">
<intent-filter android:priority="1000">
<action android:name="com.pzf.mybroadcast"></action>
</intent-filter>
</receiver>
<receiver android:name="com.demoorderbroadcast.MyOrderBroadcastReciverTwo">
<intent-filter android:priority="900">
<action android:name="com.pzf.mybroadcast"></action>
</intent-filter>
</receiver>
<receiver android:name="com.demoorderbroadcast.MyOrderBroadcastReciverThird">
<intent-filter android:priority="800">
<action android:name="com.pzf.mybroadcast"></action>
</intent-filter>
</receiver>
</application>
</manifest>
当点击“发送有序广播”时,LogCat中打印的内容如下: