在连接到一个 BLE 设备时继续扫描其他 BLE 设备

Continue scanning for other BLE devices while connecting to one

我希望我的应用程序连续扫描最多 3 个不同的 BLE 外围设备(由 MAC 地址标识)。当找到一台设备时,我会停止扫描并连接到它。代码:

static Observable<ScanResult> bleSharedScanner = MyApplication
        .getRxBleClient()
        .scanBleDevices(new ScanSettings.Builder()
                .setScanMode(SCAN_MODE)
                .build())
        .share();

static Observable<ScanResult> device1Scanner = bleSharedScanner
        .filter(scanResult -> scanResult.getBleDevice().getMacAddress().equalsIgnoreCase( device1MacAddress ) 
        );

Device2 和Device3 的代码相同。最初我订阅了所有这 3 个设备扫描仪;当我找到其中一个设备时,我 unsubscribe 该订阅 - 同时继续扫描其他两个。

到目前为止,这似乎对我的测试有效 Android phone。但我注意到您对 a previous question 的回复:“......在尝试连接之前停止 scanSubscription——Android 有时不能同时处理好扫描和连接。”

这是一个常见问题吗?有好的解决方法吗?我需要在与找到的设备交互的同时继续扫描其他设备。

我的经验表明,至少有一些华为设备在使用两个不同的外围设备进行扫描时连接到外围设备时出现问题(我在 P8 Lite 和 P9 上确认过)。

当扫描正在进行时,我收到 COMMAND_DISALLOWED 命令的 LE_CREATE_CONNECTION。主机和 BLE 芯片之间的通信是从 HCI Snoop Log 中提取的。唯一对我有用的解决方法是在建立连接期间停止扫描。

不幸的是,我们没有任何统计数据可以证明这一点。

"correct" 方法是简单地连接到每个设备并将自动连接标志设置为真。然后你可以有多个连接挂起,并且与扫描时相比,连接尝试永远不会超时。

唯一的问题是设备必须绑定或自最近一次蓝牙重启后至少被扫描一次才能正确地使堆栈学习设备的地址类型(public 或随机)。

反正99%的Android常用设备都有蓝牙芯片,可以同时扫描和启动。华为 P8 lite 和便宜的华硕平板电脑是目前我发现的唯一无法做到这一点的例外。