我正在将纯 Android BLE 库转换为使用 RxAndroidBle,但遇到了一些障碍。
该库当前打开连接,读取特征,并检查它是否已加密。如果是,则继续读取接下来的几个特征。但是,如果它没有加密,它会向客户端发出一个回调,告诉他们传入一个加密密钥(客户端负责生成这个密钥或从服务器获取它)。传入密钥后,库会将其写入设备,然后像加密设备一样继续操作。
目前在 RxAndroidBle 中,我正在建立连接,读取特征,然后关闭连接。然后,如果它是加密的,则再次建立连接并读取其他特征。如果没有,则触发回调,然后在客户端回复后建立连接。
public void connect() {
connectionDisposable = bleDevice.establishConnection(false)
.flatMapSingle(rxBleConnection -> rxBleConnection.readCharacteristic(ENCRYPT_CHARACTERISTIC_UUID))
.subscribe(bytes -> {
if(isEncrypted(bytes))
encryptedConnect();
else
listener.onKeyNeeded();
}, this::onError);
}
public void setKey(byte[] key) {
unencryptedConnect();
}
private void encryptedConnect() {
connectionDisposable = bleDevice.establishConnection(false)
.flatMapSingle(rxBleConnection -> Single.zip(
rxBleConnection.readCharacteristic(A_CHARACTERISTIC_UUID),
rxBleConnection.readCharacteristic(B_CHARACTERISTIC_UUID),
rxBleConnection.readCharacteristic(C_CHARACTERISTIC_UUID),
DataModel::new))
.subscribe(this::processData, this::onError);
}
private void unencryptedConnect() {
connectionDisposable = bleDevice.establishConnection(false)
.flatMap(rxBleConnection -> rxBleConnection.writeCharacteristic(ENCRYPT_CHARACTERISTIC_UUID)
.flatMapSingle(bytes -> Single.zip(
rxBleConnection.readCharacteristic(A_CHARACTERISTIC_UUID),
rxBleConnection.readCharacteristic(B_CHARACTERISTIC_UUID),
rxBleConnection.readCharacteristic(C_CHARACTERISTIC_UUID),
DataModel::new))
)
.subscribe(this::processData, this::onError);
}
我对 RxJava 完全陌生,但是这种连接和重新连接的方法似乎错过了反应式设计的全部要点。有没有人能够指出我如何正确利用 Rx 来处理这个用例的正确方向。即,如何在一个流中等待不同的 observable 发出(客户端对回调的回复),以及如何根据上游结果更改流的路由(根据加密状态更改下一个操作)。理想情况下,无需更改客户端代码,因为该库已部署在一些 3rd 方应用程序中。
谢谢。
首先,我没有看到您通过处理connectionDisposable
. 连接将持续,直到您执行此操作或设备断开连接。
您想要的也许可以通过将您的第一个连接保存在类型为 的变量中来实现RxBleConnection
。在 之前.flatMapSingle()
,插入.doOnNext( connection -> savedConnection = connection )
。然后savedConnection
用于后续操作,而不是建立一个新的操作。
完成后不要忘记处理。也应该为 nullsavedConnection
以避免尝试使用死连接。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句