我是Android BLE的新手,所以我的问题在某种程度上可能是不正确的或天真的。如果是这种情况,请向我解释我错在哪里,并告诉我管理这种情况的正确方法。
场景如下:我的Android应用与BLE设备通信,使用BLE特性发送命令并从设备获取答案。
顺序是:
onConnectionStateChange
方法)writeCharacteristic
将命令放在value
参数中)。 onCharacteristicChanged
方法,value
参数包含答案)唤醒应用程序后,在通过writeCharacteristic
发送命令之前,设备不会执行任何操作。设备接受不同的命令。
到目前为止一切都很好,但最近我开发了第二个不同的应用程序来与同一设备进行通信。
当我在同一个Android手机上运行这两个应用时,一个应用会向设备发送命令,并且两个应用都会收到响应!当然,未发送命令的应用程序会收到意外的答案并进入意外状态。
好的,知道问题我可以修改我的应用程序来处理这种情况,但问题是:当同一设备中的两个应用程序与同一个BLE设备通信时,这种行为是否正常?
应用程序是否有办法与BLE设备建立通信通道,以避免将特定命令的答案发送给除发送请求的应用程序之外的任何其他应用程序?
我的猜测是writeCharacteristic
和onNotificationChanged
不适合进行此类沟通,但在这种情况下哪些是替代方案?
答案 0 :(得分:6)
如果两个应用程序都与同一设备建立GATT连接,则蓝牙标准本身并未定义多个应用程序的行为方式。在标准中,只有一个" GATT客户端"。
现在iOS和Android都朝着可能看起来不直观的方式迈出了一步。多个应用程序可以通过同一个GATT客户端连接到设备,而不是一次只允许一个应用程序进行通信。 OS"多路复用"来自/到应用程序的通信。行为是对读取和写入请求的响应只能由发出请求的应用程序看到。所以如果你只读readCharacteristic应用程序将获得onCharacteristicRead回调。然而,通知将被发送到onCharacteristicChanged回调的两个应用程序,因为将通知仅发送给一个是没有任何意义的。
当你说"回复"写入请求是通知,这在GATT术语方面是不正确的。每个规范(或错误)对写请求的响应始终为空。如果您的外围设备发出通知,那么在您的情况下可能是"答案"根据您自己的逻辑,但它不是响应或与GATT规范的写请求相关的任何方式。这就是为什么Android无法(并且不应该)只向一个设备发送通知的原因。
我建议您只是忽略您不期望的通知。如果你想关联一个"答案"对于写入请求,您可以更改协议以在两个数据包中包含事务ID,以便匹配它们。
当我写" app"上面,我的意思是BluetoothGatt对象。你可以在同一个应用程序中使用同一个远程设备调用connectGatt两次,这与从两个不同的应用程序连接时的行为相同。