gpt4 book ai didi

android - RxAndroidBle - 如何断开所有连接的设备?

转载 作者:行者123 更新时间:2023-11-29 19:02:51 25 4
gpt4 key购买 nike

我正在使用很棒的 rxandroidble 库进行 BLE 控制。
我保持 Activity 之间的联系。在开始扫描之前,我想先断开所有连接的设备。如果有很多连接,有时它不起作用。这是我正在使用的解决方案:

public void doScan() {

if (isScanning()) return;

// disconnect all connected devices first:
while(BleController.getDefault().getDisconnectTriggerSubject().hasObservers()){
BleController.getDefault().getDisconnectTriggerSubject().onNext(null);
}

scanSubscription = rxBleClient.scanBleDevices(
new ScanSettings.Builder()
.setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY)
.setCallbackType(ScanSettings.CALLBACK_TYPE_ALL_MATCHES)
.build(),
new ScanFilter.Builder()
// add custom filters if needed
.build()
)
.filter(rxBleScanResult -> !TextUtils.isEmpty(rxBleScanResult.getBleDevice().getName()))
.observeOn(AndroidSchedulers.mainThread())
.doOnUnsubscribe(this::clearSubscription)
.subscribe(resultsAdapter::addScanResult, this::onScanFailure);

updateButtonUIState();

}

BleController使用主应用程序的上下文进行初始化并保留 connectionObservable , disconnectTriggerSubject , rxBleClient .

什么是更好的解决方案?任何帮助将不胜感激!

最佳答案

从您的帖子中我可以看出您将 BLE 扫描/连接逻辑与 UI/Activity 逻辑混合在一起。这可能是正确管理连接的问题。

您可以做的是将所有 BLE 逻辑放入您的 BleController它已经有了一个好名字,但在你的情况下似乎是一个 BleObjectsContainer .

例如,您只能从 BleController 中公开只有以 Activities 的方式满足您的特定用例的可观察对象不需要处理。即你的 BleController可以处理扫描:

private final BehaviorRelay<Boolean> isScanningPublishRelay = BehaviorRelay.create(false); // a relay (that cannot emit an error) that emits when a scan is ongoing

private Observable<ScanResult> scanDevicesWithNonNullNameObs = rxBleClient.scanBleDevices(new ScanSettings.Builder().build())
.filter(scanResult -> !TextUtils.isEmpty(scanResult.getBleDevice().getName()))
.doOnSubscribe(() -> isScanningPublishRelay.call(true)) // when scan is subscribed/started emit true
.doOnUnsubscribe(() -> isScanningPublishRelay.call(false)) // when scan is stopped emit false
.subscribeOn(AndroidSchedulers.mainThread()) // the above emissions will happen on the same thread. should be serialized
.unsubscribeOn(AndroidSchedulers.mainThread()) // the above emissions will happen on the same thread. should be serialized
.share(); // share this observable so no matter how many places in the code will subscribe the scan is started once and `isScanningPublishRelay` is called once

public Observable<ScanResult> scanDevicesWithNonNullName() { // getter for the scan observable
return scanDevicesWithNonNullNameObs;
}

除了扫描之外,它还会处理每个 Activity 的特定用例。需要它:

class ScanInProgress extends Throwable {
// ...
}

public Observable<YourActivityUseCaseModel> doYourSpecificStuff(Observable<RxBleConnection> connectionObservable) {
return Observable.merge(
connectionObservable,
isScanningPublishRelay
.takeFirst(aBoolean -> aBoolean)
.flatMap(ignored -> Observable.error(new ScanInProgress())) // this will only emit an error when a scan is ongoing
)
.flatMap(...); // do the rest of your stuff
}

通过这种方式,在您的 Activity 中,您只需订阅他们需要的任何模型,并在一个专门用于它的地方处理 BLE (BleController)。

在上面的示例中,您需要提供 Observable<RxBleConnection>但它可以通过许多不同的方式实现,并且可以在 BleController 中进行管理也不会暴露在界面中。

关于android - RxAndroidBle - 如何断开所有连接的设备?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48272987/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com