Android 9 原生设置关于蓝牙设置(四)

蓝牙打开后Setting界面变化及蓝牙搜索

参考:蓝牙扫描流程

  蓝牙打开后,BluetoothManagerService发出BluetoothAdapter.ACTION_STATE_CHANGED广播,Setting应用里面有很多地方注册接收该广播。其中settings/bluetooth/BluetoothEventManager.java里面有:
在这里插入图片描述
  LocalBluetoothAdapter.setBluetoothStateInt() -->LocalBluetoothProfileManager.setBluetoothStateOn()会判断Profile里面是否有已配对过的蓝牙设备,如果有,则进行自动配对。
  然后遍历、调用回调函数onBluetoothStateChanged(),DevicePickerFragment.java、CachedBluetoothDeviceManager.java、BluetoothSettings.java、DeviceListPreferenceFragment.java里面的onBluetoothStateChanged()会被调用。这里看BluetoothSettings.java的:
在这里插入图片描述
蓝牙打开后,界面如下:
在这里插入图片描述
下面分别解释“圈4”、“圈5”、“圈6”
  圈4:本机蓝牙设备的相关设置,包括本机蓝牙名称,蓝牙对附近可用设备的可见性,蓝牙对已经配对设备的可见性,当检测到蓝牙开启时会添加一个本机蓝牙信息的Preference,在方法updateContent中完成添加或者移除,添加代码如下:

在这里插入图片描述
preferencescreen添加或者移除的代码如下:

//添加一个种类的Preference
getPreferenceScreen().addPreference(mAvailableDevicesCategory);
.,....
//移除一个Preference
preferenceScreen.removePreference(mPairedDevicesCategory);
.....
//移除所有
Preference preferenceScreen.removeAll();

  圈5:已配对设备列表mPairedDevicesCategory,updateContent方法里面的代码:
在这里插入图片描述
圈6:附近可用设备列表mAvailableDevicesCategory
在这里插入图片描述
  updateContent方法最后的代码,分别判断已配对的蓝牙设备数量和扫描到的(可用的)设备数量,如果可用设备列表为空,则启动扫描。因为第一次打开蓝牙,还没有扫描记录,所以为空,且前面调用updateContent()传递下来的scanState=true,所以这里会进行扫描:
在这里插入图片描述
  另外,AndroidManifest.xml注册了DevicePickerActivity,该Activity用于蓝牙设置界面的蓝牙配置和管理,如果启动了这个Activity,在前面BluetoothEventManager.java处理BluetoothAdapter.ACTION_STATE_CHANGED广播时也会调用到DevicePickerFragment.java 的onBluetoothStateChanged(),这里也会进行startScanning。
  总之,上面调用的startScanning()最终都调用了LocalBluetoothAdapter.startScanning()
在这里插入图片描述
  如果参数force=false,则先判断是否扫描太频繁了(5分钟内扫描一次)、如果当前正使用A2DP播放音乐不进行扫描操作。
  下面会调到BluetoothAdapter.startDiscovery()>AdapterService.startDiscovery()> AS.startDiscoveryNative()>JNI里面的startDiscoveryNative()>再下面就到hw里面和bluetooth.start_discovery(void),这些暂时就不分析了,有兴趣的可以自行分析。

  Android 蓝牙应用开发,发现设备使用 startDiscovery()该进程为异步进程。该方法会立刻返回一个布尔值,指示是否已成功启动发现操作。发现进程通常包含约 12 秒的查询扫描,之后对发现的设备进行扫描,以检索其蓝牙设备的名字。
  蓝牙应用程序必须针对 BluetoothDevice.ACTION_FOUND Intent 注册一个 BroadcastReceiver,以便接受每台发现的设备的信息。针对每台设备,系统会广播 ACTION_FOUND Intent。这个 Intent 会携带额外的字段 EXTRA_DEVICE 和 EXTRA_CLASS。这两者分别包含 BluetoothDevice 和 BluetoothClass。
BluetoothEventManager.DeviceFoundHandler()
在这里插入图片描述
  根据底层传递过来的BluetoothDevice 和 BluetoothClass信息,构建一个CachedBluetoothDevice。CachedBluetoothDevice,缓存蓝牙设备,该类代表了一个远程设备,它包含了蓝牙设备的一些属性(例如蓝牙地址,名字,信号强度等)。可以通过这个类进行蓝牙设备的连接、配对、断开连接等功能,之所以命名为Cached,可能是因为它是临时存在的。
  之后调用dispatchDeviceAdded(),回调BluetoothSetting父类DeviceListPreferenceFragment.onDeviceAdded().
在这里插入图片描述
  创建一个BluetoothDevicePreference(继承Preference)并把它添加到mDeviceListGroup,mDeviceListGroup是PreferenceGroup类型,在DeviceListPreferenceFragment.onCreate()初始化:

mDeviceListGroup = (PreferenceCategory) findPreference(KEY_BT_DEVICE_LIST);

  当bluedroid扫描完成后,会告知Android上层扫描结束的广播,将回调package/apps/Bluetooth/src/com/android/bluetooth/btservice/JniCallbacks.java discoveryStateChangeCallback()–>AdapterProperties.discoveryStateChangeCallback()
在这里插入图片描述
  发送BluetoothAdapter.ACTION_DISCOVERY_FINISHED广播,最终被Setting软件的BluetoothEventManager.ScanningStateChangedHandler处理:
在这里插入图片描述
  有好几处地方注册了这个回调方法:
DevicePickerFragment.java
BluetoothPairingDetail.java
BluetoothSummaryUpdater.java
DeviceListPreferenceFragment.java,被BluetoothSettings.java重载
BluetoothDeviceUpdater.java
BluetoothSettings.java
  其中BluetoothSettings.java onScanningStateChanged()
在这里插入图片描述
  调用父类的onScanningStateChanged()
在这里插入图片描述
  代码很明显是为了更新UI。mDeviceListGroup已经在扫描过程中添加多个远程蓝牙设备的信息了,这里调用它的setProgress(),就是通知各个Preference刷新UI。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
你可以通过使用 Android 的 BluetoothAdapter 类提供的方法来监听蓝牙的状态。以下是一个示例代码: ``` import android.bluetooth.BluetoothAdapter; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.content.IntentFilter; public class BluetoothStateListener { private BluetoothAdapter bluetoothAdapter; private BluetoothStateReceiver bluetoothStateReceiver; public BluetoothStateListener(Context context) { bluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); bluetoothStateReceiver = new BluetoothStateReceiver(); IntentFilter filter = new IntentFilter(BluetoothAdapter.ACTION_STATE_CHANGED); context.registerReceiver(bluetoothStateReceiver, filter); } public void unregisterReceiver(Context context) { context.unregisterReceiver(bluetoothStateReceiver); } private class BluetoothStateReceiver extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { if (intent.getAction().equals(BluetoothAdapter.ACTION_STATE_CHANGED)) { int state = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, -1); switch (state) { case BluetoothAdapter.STATE_ON: // 蓝牙已打开 break; case BluetoothAdapter.STATE_OFF: // 蓝牙已关闭 break; } } } } } ``` 以上代码中,我们通过注册一个 BroadcastReceiver 来监听 BluetoothAdapter.ACTION_STATE_CHANGED 广播事件,当蓝牙状态发生变化时,会触发该广播事件,我们可以在 BroadcastReceiver 的 onReceive 方法中处理蓝牙状态的变化。在使用完后,记得调用 unregisterReceiver 方法来注销 BroadcastReceiver。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值