广播
在 Android 中实现广播功能主要有两种方式:标准广播和有序广播,同时需注意静态注册与动态注册的区别。以下是完整实现方案:
一、广播基础实现
1. 创建广播接收器(BroadcastReceiver)
// 自定义广播接收器
public class MyReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
// 获取广播传递的数据
String action = intent.getAction();
String message = intent.getStringExtra("message");
// 根据不同 action 处理逻辑
if (action.equals("com.example.MY_CUSTOM_ACTION")) {
Log.d("MyReceiver", "收到自定义广播: " + message);
}
}
}
2. 发送广播
// 发送标准广播(异步,无序接收)
Intent intent = new Intent("com.example.MY_CUSTOM_ACTION");
intent.putExtra("message", "这是一条广播消息");
sendBroadcast(intent);
// 发送有序广播(同步,按优先级接收)
sendOrderedBroadcast(intent, null);
3. 注册广播接收器
- 动态注册(推荐,避免内存泄漏):
public class MainActivity extends AppCompatActivity {
private MyReceiver receiver;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// 创建接收器实例
receiver = new MyReceiver();
// 动态注册
IntentFilter filter = new IntentFilter();
filter.addAction("com.example.MY_CUSTOM_ACTION");
registerReceiver(receiver, filter);
}
@Override
protected void onDestroy() {
super.onDestroy();
// 务必在 Activity 销毁时取消注册
unregisterReceiver(receiver);
}
} - 静态注册(适用于系统广播):
<!-- AndroidManifest.xml -->
<receiver android:name=".MyReceiver">
<intent-filter>
<action android:name="com.example.MY_CUSTOM_ACTION" />
</intent-filter>
</receiver>
二、系统广播示例(监听网络变化)
1. 创建网络状态接收器
public class NetworkChangeReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
ConnectivityManager cm = (ConnectivityManager)
context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = cm.getActiveNetworkInfo();
if (networkInfo != null && networkInfo.isConnected()) {
Log.d("NetworkReceiver", "网络已连接: " + networkInfo.getTypeName());
} else {
Log.d("NetworkReceiver", "网络已断开");
}
}
}
2. 注册系统广播
<!-- 需添加网络权限 -->
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<!-- 静态注册网络广播接收器 -->
<receiver android:name=".NetworkChangeReceiver">
<intent-filter>
<action android:name="android.net.conn.CONNECTIVITY_CHANGE" />
</intent-filter>
</receiver>
三、有序广播与结果传递
1. 设置广播优先级
// 动态注册时设置优先级(数值越大优先级越高)
IntentFilter filter = new IntentFilter("com.example.ORDERED_ACTION");
filter.setPriority(1000);
registerReceiver(receiver, filter);
2. 接收与传递结果
public class HighPriorityReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
// 获取前一个接收器的结果
String result = getResultData();
// 修改结果并传递给下一个接收器
setResultData(result + " -> 高优先级处理");
// 终止广播(后续接收器无法接收)
// abortBroadcast();
}
}
四、LocalBroadcastManager(本地广播)
1. 优势
- 仅在应用内传播,更安全高效。
- 无需担心其他应用监听或篡改广播内容。
2. 使用方式
// 注册本地广播接收器
LocalBroadcastManager manager = LocalBroadcastManager.getInstance(this);
manager.registerReceiver(receiver, new IntentFilter("com.example.LOCAL_ACTION"));
// 发送本地广播
Intent localIntent = new Intent("com.example.LOCAL_ACTION");
manager.sendBroadcast(localIntent);
五、Android 8.0+ 后台广播限制
1. 静态注册限制
- Android 8.0(API 26)及以上,大多数隐式广播(如
ACTION_BOOT_COMPLETED
)无法通过静态注册接收。 - 解决方案:改用动态注册或
JobScheduler
。
2. 示例(监听屏幕开关)
// 动态注册(Android 8.0+ 必须)
public class ScreenReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(Intent.ACTION_SCREEN_ON)) {
Log.d("ScreenReceiver", "屏幕已点亮");
} else if (intent.getAction().equals(Intent.ACTION_SCREEN_OFF)) {
Log.d("ScreenReceiver", "屏幕已关闭");
}
}
}
// 在 Activity 中动态注册
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ScreenReceiver receiver = new ScreenReceiver();
IntentFilter filter = new IntentFilter();
filter.addAction(Intent.ACTION_SCREEN_ON);
filter.addAction(Intent.ACTION_SCREEN_OFF);
registerReceiver(receiver, filter);
}
六、注意事项
- 内存泄漏:动态注册的广播必须在
onDestroy()
中取消注册。 - 性能影响:避免在
onReceive()
中执行耗时操作(如网络请求),可通过Handler
或Service
处理。 - 权限控制:发送自定义广播时可指定权限,确保安全性:
// 发送带权限的广播
sendBroadcast(intent, "com.example.MY_PERMISSION"); - 替代方案:复杂场景推荐使用 EventBus 或 LiveData 实现组件间通信,减少对广播的依赖。
总结
- 标准广播:异步、无序,适合一对多通知。
- 有序广播:同步、按优先级处理,支持结果传递与终止。
- 本地广播:应用内安全通信,性能更优。
- 系统广播:需注意 Android 8.0+ 的后台限制,优先使用动态注册。
根据具体场景选择合适的广播类型,并严格遵循生命周期管理,可确保广播功能稳定可靠。