关于BroadcastReceiver这一篇就够了

BroadcastReceiver简介

BroadcastReceiver 是 Android 中的一个核心组件,主要用于接收来自系统的广播消息。它可以用于监听各种系统事件,例如网络变化、电池状态、短信接收等。通过 BroadcastReceiver,应用程序可以在不需要启动自己的界面或者服务的情况下,响应这些事件并进行相应的操作123

如何使用BroadcastReceiver

静态注册

静态注册通常在 AndroidManifest.xml 文件中进行。首先,你需要创建一个继承自 BroadcastReceiver 的类,然后在 AndroidManifest.xml 文件中声明这个类,并为它配置一个 <intent-filter> 来指定它所关心的广播类型。例如,如果你想让你的 BroadcastReceiver 接收 android.intent.action.MY_BROADCAST 类型的广播,你可以这样配置:

<receiver android:name=".MyReceiver">
    <intent-filter>
        <action android:name="android.intent.action.MY_BROADCAST"/>
        <category android:name="android.intent.category.DEFAULT"/>
    </intent-filter>
</receiver>

静态注册的 BroadcastReceiver 在应用安装时会自动注册,即使应用未运行,只要有匹配的广播发送过来,BroadcastReceiver 就会被系统调用并运行2

动态注册

动态注册则是在代码中进行的。首先,你需要创建一个 BroadcastReceiver 的实例,然后创建一个 IntentFilter 来指定感兴趣的广播类型,并通过 Context 的 registerReceiver() 方法来注册 BroadcastReceiver。例如:

IntentFilter intentFilter = new IntentFilter();
intentFilter.addAction(android.net.conn.CONNECTIVITY_CHANGE);
registerReceiver(mBroadcastReceiver, intentFilter);

需要注意的是,动态注册的 BroadcastReceiver 需要在合适的时机注销,以避免内存泄漏。通常,你应该在 Activity 的 onPause() 方法中注销 BroadcastReceiver

@Override
protected void onPause() {
    super.onPause();
    unregisterReceiver(mBroadcastReceiver);
}

注意事项

无论是静态注册还是动态注册,都需要确保在不需要的时候注销 BroadcastReceiver,以避免内存泄漏。此外,由于 BroadcastReceiver 可能会在不同的线程中被调用,因此在 onReceive() 方法中应当避免进行耗时的操作,以免影响主线程的性能。

总结

BroadcastReceiver 是 Android 开发中非常重要的一个组件,它允许应用程序方便地接收和处理来自系统的广播消息。正确地使用 BroadcastReceiver 不仅可以提高程序的效率,还可以帮助应用程序更好地响应用户的操作和系统的变化。

广播类型

  1. 标准广播(Normal broadcasts):这是一种完全异步执行的广播,在广播发出之后,所有的广播接收器几乎都会在同一时刻接收到这条广播消息,因此它们之间没有任何先后顺序可言。这种广播的效率较高,但同时也意味着它是无法被截断的。
  1. 有序广播(Ordered broadcasts):这是一种同步执行的广播,在广播发出之后,同一时刻只会有一个广播接收器能够收到这条广播消息,当这个广播接收器中的逻辑执行完毕后,广播才会继续传递。所以此时的广播接收器是有先后顺序的,优先级高的广播接收器就可以先收到广播消息,并且前面的广播接收器还可以截断正在传递的广播,这样后面的广播接收器就无法收到广播消息了。
  1. 粘性广播(Sticky broadcasts):粘性广播也属于标准广播,在发送后就一直存在于系统的消息容器里面,等待对应的处理器去处理。如果暂时没有处理器处理这个消息则一直在消息容器里面处于等待状态,粘性广播的Receiver如果被销毁,那么下次重建时会自动接收到消息数据。
  1. 系统广播:Android 内置了很多系统级别的广播,我们可以在应用中通过监听这些广播来得到各种系统的状态信息。比如手机开机后会发送一条广播,电池的电量发生变化会发出一条广播,时间或时区发生改变也会发出一条广播等等。

每种广播类型都有自己的特点和适用场景,选择合适的广播类型可以使我们的应用更加高效和稳定。

使用场景

BroadcastReceiver 的使用场景非常广泛,包括但不限于以下几点:

  1. 系统事件监听

    • 电池电量低(ACTION_BATTERY_LOW
    • 屏幕关闭与打开(ACTION_SCREEN_OFF 和 ACTION_SCREEN_ON
    • 网络变化(CONNECTIVITY_ACTION
    • 设备启动完成(BOOT_COMPLETED
    • 来电(TELEPHONY_CALL
    • 短信接收(SMS_RECEIVED
    • 等等。
  2. 应用内部事件

    • 自定义业务逻辑触发的事件
    • 服务绑定与断开(BIND_ADMIN 和 APP_PEER_MANAGED
    • 本地广播,用于应用不同组件间的通信
  3. 定时任务

    • 使用 AlarmManager 发送定时的广播,实现类似 cron 的定时任务

编程模型

Android 的 BroadcastReceiver 编程模型基于两种注册方式:静态注册和动态注册。

  • 静态注册是通过在 AndroidManifest.xml 文件中声明 <receiver> 元素,并在其中指定 <intent-filter> 来实现的。这种方式适用于那些在应用安装时就确定需要监听的系统广播。

  • 动态注册是在代码中使用 Context.registerReceiver() 方法注册。这种方式的好处是可以在应用运行时根据需要注册或注销,增加了灵活性。动态注册的 BroadcastReceiver 通常与某个 Activity 或 Service 的生命周期绑定,以避免不必要的资源消耗。

生命周期

BroadcastReceiver 的生命周期非常短暂,通常只在 onReceive(Context context, Intent intent) 方法被调用时存在。一旦该方法执行完成,BroadcastReceiver 就会自动卸载并销毁。因此,不建议在 onReceive()方法中执行耗时的操作,否则会严重影响用户体验和应用性能。

最佳实践

  • 尽量使用隐式 Intent 过滤器来注册 BroadcastReceiver,这样可以使应用更加模块化,也更容易维护。
  • 避免在 BroadcastReceiver 中执行耗时的操作。如果必须执行,请考虑使用 Service 来分担这些任务,并在合适的时候将结果通知给 BroadcastReceiver
  • 当使用动态注册时,始终记得在不需要 BroadcastReceiver 时注销它,以释放系统资源。
  • 对于敏感的操作(如发送短信、访问位置等),确保已经获得了必要的权限,并且在操作前进行检查,以避免应用崩溃或被系统强制停止。
  • 对于需要长期运行的后台任务,考虑使用 JobIntentServiceWorkManager 或 Foreground Service,而不是依赖 BroadcastReceiver

注意事项

从 Android 8.0(API 级别 26)开始,对于在后台隐式注册的 BroadcastReceiver,系统已经做了限制。除非这些 BroadcastReceiver 是显式地通过 startActivity() 启动 Activity 的一部分,否则它们将无法在应用处于后台时接收到事件。这一变化是为了提高设备的电池续航能力和性能。因此,在设计新的应用或更新现有应用时,需要特别注意这一点。

在 Android 开发中,BroadcastReceiver 的使用受到了一定的限制,特别是从 Android 8.0(API 级别 26)开始,谷歌引入了“后台执行限制”(Background Execution Limits),这直接影响了 BroadcastReceiver 的行为。

Android 8.0 及以上版本的限制

从 Android 8.0 开始,系统对后台服务和广播接收器施加了新的限制,以改善用户体验和节省电池。具体来说:

  1. 隐式广播限制

    • 应用不再能在后台接收其他应用发送的隐式广播。
    • 系统会将这些意图过滤,只有当应用在前台时才能接收到。
  2. 隐式广播白名单

    • 系统仍然会传递一些重要的隐式广播给应用,但数量极其有限。
    • 这些包括 BOOT_COMPLETEDPACKAGE_REMOVED 等,需要在 AndroidManifest.xml 中明确声明。
  3. 前台服务接收的广播

    • 如果应用有一个前台服务在运行,它仍然可以接收所有的广播,无论是隐式的还是显式的。
  4. 广播限制例外

    • 对于一些特定的系统广播,比如充电、低电量等,系统会提供例外,允许 BroadcastReceiver 在后台接收。

如何适应这些变化

为了适应这些变化,开发者需要采取新的策略:

  1. 使用 JobScheduler 或 WorkManager

    • 对于定期任务,可以使用 JobScheduler API 或者 FirebaseJobDispatcher,现在是 WorkManager
    • 这些API提供了一种在满足特定条件时运行作业的方式,即使应用没有在前台运行。
  2. 使用前台服务

    • 如果业务需求需要在后台接收广播,可以考虑使用前台服务。
    • 前台服务必须显示一个持久的通知,因此用户知道服务正在运行。
  3. 使用 LiveData 和 ViewModel

    • 对于前台组件(如 ActivityServiceFragment),可以使用 LiveData 和 ViewModel 来观察和处理生命周期感知的事件。
  4. 使用通知渠道

    • 对于需要通知用户的情况,使用 NotificationChannel 来创建通知渠道,这是 Android O 引入的一个新特性。
  5. 动态注册和注销

    • 对于在应用运行时需要接收的事件,可以在 Activity 或 Service 中动态注册 BroadcastReceiver
    • 记得在组件被销毁时注销 BroadcastReceiver,以避免内存泄漏。

总结

BroadcastReceiver 在 Android 中是一个强大的工具,但是从 Android 8.0 开始,它的使用受到了限制。开发者需要适应这些变化,通过使用 JobSchedulerWorkManagerLiveDataViewModel 和 NotificationChannel 等新的架构组件和API来实现后台任务的调度和通知。同时,对于确实需要在后台接收事件的情况,可以考虑使用前台服务,但要注意用户体验和电池消耗的问题。

在 Android 应用开发中,BroadcastReceiver的使用虽然受到限制,但在某些情况下仍然是必需的。下面是一些关于BroadcastReceiver的高级话题和最佳实践:

1. 使用 LocalBroadcastManager

LocalBroadcastManager是一个在应用进程内发送和接收意图(Intents)的组件。它不发送到其他应用,因此不会受到Android系统对后台服务和广播接收器的限制影响。这对于在应用内部不同组件之间通信非常有用,尤其是当你想要避免隐式广播的限制时。

2. 使用隐式广播的替代方案

  • 使用JobScheduler或AlarmManager:对于定期任务,可以使用JobSchedulerAlarmManager来代替。这些API允许你在特定的时间或条件下执行代码,即使应用没有在前台运行。
  • 使用前台服务:如果你需要在后台执行长时间运行的任务,可以考虑使用前台服务。前台服务必须显示一个持续的通知,这样用户就知道该服务正在运行。这可以避免系统杀死后台服务的风险,但要注意不要过度使用,以免影响用户体验。

3. 使用隐式广播的例外情况

尽管Android系统对隐式广播施加了限制,但还是有一些例外情况。例如,BOOT_COMPLETEDPACKAGE_REMOVEDPACKAGE_ADDED等系统广播仍然可以被任何应用接收。你可以在AndroidManifest.xml文件中注册这些广播,并在其中处理相应的逻辑。

4. 注意广播接收器的安全性

从 Android 8.0 开始,系统引入了一个名为“广播接收器自动注册禁用”的功能。该功能要求应用在注册接收器时必须明确其意图过滤器。这意味着应用不能再在代码中动态注册接收器来接收隐式广播。此外,对于需要接收敏感信息的广播(如短信、联系人等),系统可能会要求用户授予相应的权限。因此,在使用广播接收器时,一定要注意保护用户数据的安全。

5. 使用最新的架构组件

随着 Android 开发的不断演进,Google 引入了许多新的架构组件来帮助开发者更好地构建应用。例如,LiveDataViewModel提供了一种更好的方式来处理 UI 相关的数据,而RoomRetrofit等库则简化了数据访问和网络请求的代码。在使用BroadcastReceiver时,可以考虑结合使用这些新的架构组件来提高应用的可维护性和扩展性。

6. 考虑使用第三方推送通知服务

如果你的应用需要发送大量的推送通知,或者需要向不同平台(如 iOS、Web)的用户发送通知,那么可以考虑使用第三方推送通知服务,如 Firebase Cloud Messaging (FCM)。这些服务提供了丰富的功能和更好的可靠性,可以帮助你更轻松地实现推送通知的功能。

总之,BroadcastReceiver在 Android 开发中仍然是一个有用的工具,但在使用时需要注意其限制和最佳实践。通过合理地规划和使用BroadcastReceiver以及其他相关技术,你可以构建出更加高效、稳定和用户友好的 Android 应用。

  • 20
    点赞
  • 31
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值