以编程方式启用/禁用Broadcastreceiver

vol*_*nde 7 android

我们有一个扫描蓝牙设备的应用程序.负责扫描的代码只应在启用蓝牙时运行.此外,我们希望在任何时间点禁用/启用此功能.

我们选择实现一个注册BluetoothAdapter.ACTION_STATE_CHANGED广播的BroadcastReceiver.

这里遇到的一些问题:

以编程方式启用BroadcastReceiver:

public void registerForBroadcasts(Context context) {
    IntentFilter bluetooth = new IntentFilter(BluetoothAdapter.ACTION_STATE_CHANGED);
    context.registerReceiver(this, bluetooth);
}
Run Code Online (Sandbox Code Playgroud)
  1. 当应用程序被杀死时,BroadcastReceiver也不再处于活动状态.因此,如果用户多任务 - 将应用程序刷死,则不会再次被唤醒.
  2. 我们完全控制,何时启动BroadcastReceiver.

在Manifest中声明BroadcastReceiver

<receiver android:name="com.mypackage.BroadcastReceiver">
    <intent-filter>
        <action android:name="android.bluetooth.adapter.action.STATE_CHANGED"/>
    </intent-filter>
</receiver>
Run Code Online (Sandbox Code Playgroud)
  1. 应用程序启动后,BroadcastReceiver处于活动状态.
  2. 无法禁用BroadcastReceiver.

将Manifest中的BroadcastReceiver声明为disabled并以编程方式启用它

<receiver android:name="com.mypackage.BroadcastReceiver"
          android:enabled="false" >
    <intent-filter>
        <action android:name="android.bluetooth.adapter.action.STATE_CHANGED"/>
    </intent-filter>
</receiver>
Run Code Online (Sandbox Code Playgroud)

然后在需要时启用组件.

public void registerForBroadcasts(Context context) {
    ComponentName component = new ComponentName(context, BroadcastReceiver.class);
    PackageManager pm = context.getPackageManager();
    pm.setComponentEnabledSetting(
                component,
                PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
                PackageManager.DONT_KILL_APP);
}
Run Code Online (Sandbox Code Playgroud)

我的测试显示,状态是系统持久化的,因此BroadcastReceiver将保持启用状态.它结合了两种方法的优点.

  1. 可以禁用BroadcastReceiver
  2. 默认情况下,BroadcastReceiver可以打开或关闭
  3. 即使应用程序已禁用且手机重新启动,BroadcastReceiver仍会保持激活状态.

我错过了什么,这种方法看起来合法吗?

Kum*_*r M 8

可以以编程方式启用/禁用接收器.

以编程方式启用

PackageManager pm  = Re_editActivity.this.getPackageManager();
ComponentName componentName = new ComponentName(currentActivity.this, name_of_your_receiver.class);        
pm.setComponentEnabledSetting(componentName,PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
                                PackageManager.DONT_KILL_APP);
Run Code Online (Sandbox Code Playgroud)

以编程方式禁用

PackageManager pm  = Re_editActivity.this.getPackageManager();
ComponentName componentName = new ComponentName(currentActivity.this, name_of_your_receiver.class);
pm.setComponentEnabledSetting(componentName,PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
                            PackageManager.DONT_KILL_APP);
Run Code Online (Sandbox Code Playgroud)

显示接收器

<receiver android:name="name_of_your_receiver" android:enabled="false">
        <intent-filter >                
            <action android:name="android.intent.action.BOOT_COMPLETED"/>                
        </intent-filter>
    </receiver>
Run Code Online (Sandbox Code Playgroud)


Com*_*are 6

无法禁用BroadcastReceiver.

当然可以.使用PackageManagersetComponentEnabledSetting(),就像在第三个场景中一样.

我错过了什么,这种方法看起来合法吗?

这是非常合法的,至少在管理方面BroadcastReceiver.我不知道是否有任何蓝牙特定的打嗝,但我会怀疑.此技术用于各种广播,例如仅ACTION_BOOT_COMPLETED在您确实需要在启动时完成某些操作时进行监听.