调用didDisconnectPeripheral后BLE仍显示已连接的问题排查
iOS BLE断开连接后系统设置仍显示已连接问题
尝试与Raspberry Pi3 BLE设备断开连接时,didDisconnectPeripheral代理方法已触发,代码中明确检测到外设处于断开状态,但系统设置应用里仍显示该设备处于连接状态。
实现代码及操作流程
页面初始化CBCentralManager
func setupBLE() { lblStatus.text = "Establising connection to the Scrubport" self.manager = CBCentralManager(delegate: self, queue: .main) }
处理CBCentralManager状态变更
func centralManagerDidUpdateState(_ central: CBCentralManager) { if central.state == .poweredOn { self.dismissAlert() self.showLoader() self.timer = Timer.scheduledTimer(withTimeInterval: 30, repeats: false, block: { _ in // No device found. Stop scanning. }) self.manager?.scanForPeripherals(withServices: [SERVICE_UUID]) return } else if central.state == .unauthorized { // Permission handlers here: return } // Handle all other cases. }
发现设备后连接
func centralManager(_ central: CBCentralManager, didDiscover peripheral: CBPeripheral, advertisementData: [String : Any], rssi RSSI: NSNumber) { self.peripheral = peripheral connect() }
func connect() { guard let peripheral = peripheral else { // Making sure we got the peripheral. return } lblStatus.text = "Connecting..." self.manager?.connect(peripheral) }
连接成功后发现服务
func centralManager(_ central: CBCentralManager, didConnect peripheral: CBPeripheral) { lblStatus.text = "Connected, preparing device for transfer..." self.timer.invalidate() central.stopScan() peripheral.delegate = self peripheral.discoverServices([SERVICE_UUID]) }
查找特征值
func peripheral(_ peripheral: CBPeripheral, didDiscoverServices error: Error?) { if let services = peripheral.services { for service in services { if service.uuid == SERVICE_UUID { peripheral.discoverCharacteristics([CHARACTERISTICS_UUID], for: service) } } } }
请求通知
func peripheral(_ peripheral: CBPeripheral, didDiscoverCharacteristicsFor service: CBService, error: Error?) { if let characteristics = service.characteristics { for characteristic in characteristics { if characteristic.uuid == self.CHARACTERISTICS_UUID { self.characteristic = characteristic peripheral.setNotifyValue(true, for: characteristic) } } } }
通知状态更新处理
func peripheral(_ peripheral: CBPeripheral, didUpdateNotificationStateFor characteristic: CBCharacteristic, error: Error?) { if characteristic.isNotifying { self.stopLoader() lblStatus.text = "Notifying now.." } else { print("Un-notified") print("Trying disconnection") manager?.cancelPeripheralConnection(peripheral) } }
断开连接的清理逻辑
fileprivate func cleanup() { print("CLEANING") guard let manager = manager else { return } print("Check scan.") if manager.isScanning { print("Stopping scan.") manager.stopScan() } // Don't do anything if we're not connected // self.discoveredPeripheral.isConnected is deprecated print("Checking peripheral connection") guard peripheral?.state == .connected else { print("No peripheral connected.") return } // See if we are subscribed to a characteristic on the peripheral print("Checking services") guard let services = peripheral?.services else { print("No services connection found.") cancelPeripheralConnection() return } print("Looping services") for service in services { print("Checking characteristics") guard let characteristics = service.characteristics else { print("No characteristics") continue } print("Looping characteristics") for characteristic in characteristics { print("Comparing characteristics UUID is notifying") if characteristic.uuid.isEqual(CHARACTERISTICS_UUID) && characteristic.isNotifying { print("Un-notifying") peripheral?.setNotifyValue(false, for: characteristic) } else { print("Nope not the one.", characteristic.isNotifying) } } } }
fileprivate func cancelPeripheralConnection() { print("Remove peripheral connection") guard let manager = manager, let peripheral = peripheral else { print("Manager or peripheral not found!") return } print("Cancelling peripheral connection.") // If we've got this far, we're connected, but we're not subscribed, so we just disconnect manager.cancelPeripheralConnection(peripheral) }
断开代理回调
func centralManager(_ central: CBCentralManager, didDisconnectPeripheral peripheral: CBPeripheral, error: Error?) { print("SERVICE INFO: didDisconnectPeripheral", peripheral.name ?? "Unknown") print("Was there an error?", error ?? "No error") self.peripheral = nil let peripherals = central.retrieveConnectedPeripherals(withServices: []) let _peri = central.retrievePeripherals(withIdentifiers: [peripheral.identifier]) _peri.forEach { per in print(per.state == .connected, "connected") print(per.state == .connecting, "connecting") print(per.state == .disconnected, "disconnected") print(per.state == .disconnecting, "disconnecting") } print(peripherals) }
cleanup()执行日志
CLEANING Check scan. Checking peripheral connection Checking services Looping services Checking characteristics Looping characteristics Comparing characteristics UUID is notifying Un-notifying Un-notified Trying disconnection SERVICE INFO: didDisconnectPeripheral raspberrypi-cm3 Was there an error? No error false connected false connecting true disconnected false disconnecting []
执行清理后,系统设置应用中仍显示该设备处于连接状态。
内容的提问来源于stack exchange,提问作者Mantiqh Technologies
相关产品推荐
相关产品推荐

