BLE 后台重新连接

2023-11-22

我想在设备被用户或系统移出/终止/在后台模式下重新启动后重新连接到 BLE 设备。

我知道这是可能的:-请参阅此问题及其描述

问题 - 我该如何设置centralManager如果应用程序终止,是否会在后台模式下自动重新连接到外围设备?有人可以逐步描述如何完成吗?

关于当前实施的几句话:

我使用以下选项创建centralManager:

self.centralManager = [[CBCentralManager alloc] initWithDelegate:self queue:nil  options:@{
                                                                                               CBCentralManagerOptionRestoreIdentifierKey: @"myCentralManagerIdentifier",
                                                                                               CBCentralManagerRestoredStatePeripheralsKey : @YES,
                                                                                               CBCentralManagerRestoredStateScanServicesKey : @YES,
                                                                                               CBCentralManagerRestoredStateScanOptionsKey : @YES
                                                                                               }];

之后我开始扫描 BLE 设备

[self.centralManager scanForPeripheralsWithServices:[self discoverableCharacteristics] options:nil];

in - (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary *)advertisementData RSSI:(NSNumber *)RSSI我连接到外围设备:

    NSString *localName = [advertisementData objectForKey:CBAdvertisementDataLocalNameKey];
    [self.centralManager stopScan];
    peripheral.delegate = self;
    [self.centralManager connectPeripheral:peripheral options: @{
                                                                CBConnectPeripheralOptionNotifyOnNotificationKey : @YES
                                                                }];

之后我可以发现服务和特征 - 一切看起来都不错。当我发现特征并读/写数据时我cancelPeripheralConnection

在 didDisconnect 中我重新连接到设备

- (void)centralManager:(CBCentralManager *)central didDisconnectPeripheral:(CBPeripheral *)peripheral error:(nullable NSError *)error
{
    [central connectPeripheral:peripheral options:nil];
}

我也实施centralManager:willRestoreState: like:

NSArray *peripherals = dict[CBCentralManagerRestoredStatePeripheralsKey];
for  (CBPeripheral *peripheral in peripherals) {
    [central connectPeripheral:peripheral options:nil];
    peripheral.delegate = nil;
}

在 plist 中。添加了所需的密钥App communicates using CoreBluetooth.

目前,如果我连接到设备并终止它 - 它会自动重新启动并连接到设备 - 一切都好,但如果它再次终止 - 什么也不会发生。

另外,如果我从外围设备移出并回来-什么也没有发生。


Update

关于第 5 点 - 我的跌倒 - 应该使用这个键connectPeripheral

in WillRestoreState:

NSArray *peripherals = dict[CBCentralManagerRestoredStatePeripheralsKey];
if (!peripherals.count) {
    peripherals = [central retrievePeripheralsWithIdentifiers:[self discoverableCharacteristics]];
}

if (peripherals.count) {
    for  (CBPeripheral *peripheral in peripherals) {
        [central connectPeripheral:peripheral options:@{
                                                        CBCentralManagerRestoredStatePeripheralsKey : @YES,
                                                        CBCentralManagerRestoredStateScanServicesKey : @YES,
                                                        CBCentralManagerRestoredStateScanOptionsKey : @YES
                                                        }];
         }
} else {
    [self startScanning];
}

当前结果 - 如果应用程序未从托盘中滑出,则应用程序将重新启动。我使用我的 mac 作为外围设备,所以有时当我不启动充当外围设备中心角色的应用程序时,可以连接到 mac 本身而不是所需的服务。

另一个问题 - 在失去连接时重新连接到外围设备以保持连接是一个不错的选择,例如:

- (void)centralManager:(CBCentralManager *)central didDisconnectPeripheral:(CBPeripheral *)peripheral error:(nullable NSError *)error
{
    [central connectPeripheral:peripheral options:@{
                                                CBCentralManagerRestoredStatePeripheralsKey : @YES,
                                                CBCentralManagerRestoredStateScanServicesKey : @YES,
                                                CBCentralManagerRestoredStateScanOptionsKey : @YES
                                                }];
}

还尝试更改外设上的通知特征并在设备上读取它。如果一切都在前台完成 - 一切都完美,但如果连接有时在后台完成didUpdateValueForCharacteristic根本没有被调用,但是didUpdateNotificationStateForCharacteristic被调用时没有错误 - 这意味着(我认为)我这边做错了什么。也许你可以建议问题出在哪里

还有一个问题 - 将数据写入特征是否有一些限制?因为在苹果示例中它被设置为 20 字节。


首先,我想说,我已经使用 CoreBluetooth 大约两年了,据我所知,CoreBluetooth 状态保存和恢复根本无法可靠地工作。你可以让它“正常”工作,但你永远不会让它可靠地重新连接,除非有一天苹果修复它。

话虽如此,我想注意一下您的设置的一些事项。

1) In centralManager:willRestoreState:您只能检索在应用程序终止时进行过任何通信的外围设备。这意味着您还应该实施centralManagerDidUpdateState:如果状态是CBCentralManagerStatePoweredOn那么你可以使用retrievePeripheralsWithIdentifiers:方法来检索其他外设并重置其委托。这当然意味着您必须将外围设备标识符存储在应用程序中的某个位置。还要记住在这里重置挂起的连接。

2)您将委托设置为nilcentralManager:willRestoreState:!所以即使它确实连接了,你也不会知道它 i:P

3) 只有当应用程序被系统终止时,您的应用程序才会重新启动。如果您从应用程序列表中手动删除它,它将不会重新启动。不幸的是,如果设备重新启动,它也不会重新启动。

4) The CBConnectPeripheralOptionNotifyOnConnectionKey使用蓝牙中央背景模式时没有必要,而且对用户来说很烦人,所以我不会使用它。

5) CBCentralManagerRestoredStatePeripheralsKey, CBCentralManagerRestoredStateScanServicesKey, CBCentralManagerRestoredStateScanOptionsKey不是有效的初始化选项,所以我不明白你为什么使用这些..

5) 如果蓝牙在应用程序终止时切换状态,则所有挂起的连接都将丢失,并且您将不会重新启动来了解这一情况。这本身就意味着国家恢复是相当无用的。

无论如何,我很遗憾地说,但如果您正在开发一个必须依赖于在后台重新连接外围设备的应用程序,那么我不建议这样做。你会感到沮丧。我可能可以写一篇关于苹果不想修复的核心蓝牙中所有错误的文章。更可怕的是,您可以很容易地通过一个应用程序破坏设备上的全局蓝牙连接,这样在设备重新启动之前没有应用程序可以使用蓝牙。这是非常糟糕的,因为它违背了苹果自己的沙盒原则。

如果您需要更多帮助,请告诉我!

/A

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

BLE 后台重新连接 的相关文章

  • 如何在iOS中将底部安全区域设置为XIB?

    我想打开自定义弹出视图 在 XIB 中设计 它从底部显示 但现在在 iPhoneX 模拟器中 它从屏幕底部显示 我想在安全区域打开弹出窗口 iPhone X 的结果 并且 XIB 布局有约束 简单来说解决方案 使用超级视图删除底部约束并将其
  • 裁剪图像和中心

    在 Swift 中如何裁剪图像并将其放在中心 我已经裁剪了图像 但想将其放在中间 ImgView image OrigImage var masklayer CAShapeLayer masklayer frame ImgView fram
  • 用于 iOS 搜索的 Facebook Graph API

    我尝试使用以下代码从 Graph API 中搜索地点 但没有成功 有人可以启发我的道路吗 如果我尝试发布链接 消息 照片 它会按预期工作 但是当尝试获取位置时 它总是失败并给我 The operation couldn t be compl
  • AVAudioSessionManager availableInputs“未知为端口 iPhone 麦克风选择的数据源”

    我在控制台日志中注意到这个错误已经有一段时间了 虽然它不影响我的应用程序的执行 但我觉得它真的很烦人 于是 我开始追查这个错误是从哪里来的 事实证明 当我调用 availableInputs 时 NSArray inputs AVAudio
  • WGS84 iOS 上外部 GPS 数据的大地水准面高度高度偏移

    对于我正在编写的应用程序 我们将 IOS 设备与外部传感器连接起来 该传感器通过本地 WiFi 网络输出 GPS 数据 该数据以相对于海拔高度的 原始 格式出现 一般来说 所有 GPS 高度都需要应用与基于当前位置的 WGS84 大地水准面
  • iOS Facebook SDK 通过图搜索来搜索用户

    我是图形搜索新手 我想搜索具有电子邮件地址的用户 那可能吗 现在 我只知道如何使用他们的名字进行搜索 如下所示 https graph facebook com search q chandler de angelis type user
  • 以编程方式获取 iOS 应用程序中的内存使用情况实时/脏字节(不是驻留/真实字节)

    根据我到目前为止所读到的内容 实际 驻留字节表示分配给应用程序的字节数 包括应用程序不再使用但尚未被操作系统回收的字节数 活动 脏字节是应用程序实际使用且操作系统无法回收的字节 我认为 XCode 调试导航器中显示的数字是 Live Byt
  • 向 UIImageView 添加反射的最有效方法是什么

    我只想要最简单的方法在易于管理的 UIImageView 下进行反射 只需使用iPhone SDK 库中的示例代码 http developer apple com library ios samplecode Reflection Int
  • Facebook SDK:openActiveSessionWithPermissionscompletionHandler 未调用

    使用我已经实现的 Facebook 代码 BOOL openSessionWithAllowLoginUI BOOL allowLoginUI NSArray permissions NSArray alloc initWithObject
  • UIStackView - 拖动以重新排序排列的子视图?

    我试图获得一些关于如何实现在 a 上发现的相同类型的 拖动重新排序 行为的建议 UITableView但在一个UIStackView 到目前为止 这就是我的想法 为每个按钮添加一个长按手势识别器arrangedSubviews 长按时 添加
  • 从 UIImageView 的中心对 UIImageView 进行动画处理

    我有一个UIImageView应该从动画size 0 0 gt 93 75 我有以下内容 UIView animateWithDuration 0 5 delay 0 options UIViewAnimationOptionTransit
  • 如何使 TextField 右对齐(尾随)

    我正在努力拥有一个价值文本域以尾随对齐方式显示 正如你所看到的价值34 3以前导对齐方式显示 我确信我错过了一些明显的东西 但我不知道是什么 有任何想法吗 State private var endwert 34 3 var numberF
  • 设置视图控制器根视图的外观代理

    使用 UIAppearance 时是否可以仅针对视图控制器的根视图 我想从我的应用程序委托中为所有控制器设置背景颜色 但只想定位视图控制器上的直接视图 谢谢 详细来说 每个 UIViewController 子类都有自己的 UIView 对
  • 在 swift 中实现自定义markerInfoWindow不起作用

    我一直在使用下面发布的方法来显示自定义信息窗口 但是每当我运行它时 只显示默认窗口 带有标题 片段 我已经为以下方法创建了 xib 和 swift 文件 并且我尝试使用标准函数表示法 即 mapView mapView markerInfo
  • 使用文本编辑器避免在 SwiftUI 中使用键盘

    我正在尝试重新创建 iOS 笔记应用程序的简单版本 请注意 我是一个十足的 Swift 新手 我当前的问题是我希望我的视图在键盘出现时向上移动 我已经实现了一些代码does这样做 但它有一些讨厌的错误 它首先将视图移动得太高 然后当您开始打
  • 禁用应用程序的启动图像

    我想从我的应用程序禁用启动图像 我已经有一个启动屏幕 因此在应用程序启动时首先显示启动图像 然后显示启动屏幕 我想禁用启动图像并仅在应用程序启动时显示启动屏幕 请帮忙 提前致谢 你不能 因为它会一直保持到你的程序被加载并从applicati
  • 如何将文本从文本字段发送到另一个视图控制器

    我正在制作一个应用程序 其行为类似于 iPhone 中的默认 Messages app 用户可以在其中编写短信UITextField点击 发送 按钮后 该值UITextField in ComposeViewController将被转移到表
  • 如何在 Cocoa 中将 NSString 转换为 unsigned int?

    我的申请收到了NSString含有一个unsigned int NSString 没有 myString unsignedIntegerValue 方法 我希望能够从字符串中取出值而不破坏它 然后将其放入NSNumber 我正在尝试这样做
  • Ionic 3 Deeplinking - 从 URL 启动应用程序

    我正在使用 Ionic 开发一个跨平台应用程序 当尝试实现深度链接时 我安装了一个名为 Ionic Native 插件深层链接 我运行了这些命令 ionic cordova plugin add ionic plugin deeplinks
  • NSTimer 在后台的行为(addTimer:, beginBackgroundTaskWithExpirationHandler:)

    Xcode 6 3 1 ARC 启用 适用于 iOS 8 3 我需要帮助理解我在应用程序进入后台后尝试在应用程序中维护单例共享计时器时遇到的奇怪行为 以前我不关心这个 NSTimer 因为它是使用后台位置服务在后台更新用户位置的 但是 我想

随机推荐