Что именно могут делать приложения CoreBluetooth в фоновом режиме?
Субъект говорит все, правда. Документация, поскольку она вообще существует, предполагает, что приложения, написанные для платформы CoreBluetooth, работающей на устройствах iOS, могут добавлять "bluetooth-central" в свой фоновый список привилегий и, таким образом, обрабатывать какие-то события Bluetooth, пока они неактивны, но какие именно события делают и не доставляется?
Например:
- Могу ли я поддерживать связь с устройством, с которым я уже установил соединение?
- Могу ли я периодически отправлять запросы на обнаружение, чтобы найти устройства, которые находятся вне диапазона / я никогда раньше не видел? (Например, если бы я хотел иметь возможность доставить уведомление при обнаружении нового интересного устройства)
- Что если устройство выходит за пределы диапазона, а затем возвращается? Получу ли я отключенные и подключенные события без вмешательства пользователя, или мне нужно быть предвзятым и попросить пользователя явно запросить переподключение?
4 ответа
Казалось, никто не знал, поэтому я купил аккаунт разработчика iOS и провел несколько экспериментов. Вот что я нашел:
При работе на переднем плане вы можете запустить сканирование, используя CBCentralManager::scanForPeripheralsWithServices. Ваше сканирование может быть ограничено устройствами, рекламирующими определенную услугу, или неограниченно (передайте ноль для параметра этого вызова). Это может также разрешить или запретить дубликаты; в первом случае вы получите обратный вызов didDiscoverPeripheral каждый раз, когда iPhone получает рекламные пакеты; в последнем случае вы получите только один обратный вызов на каждое найденное устройство.
Когда вы вводите фон, правила выглядят следующим образом:
- Если вы выполняли неограниченное сканирование, оно будет автоматически отменено. Вы не получите никаких обратных вызовов didDiscover.
- Если сканирование было ограничено (т. Е. Вы указали один или несколько UUID службы, которые вы искали), сканирование продолжится, но флаг разрешения дубликатов будет игнорироваться. Это означает, что теперь вы будете получать только обратные вызовы didDiscoverPeripheral для новых устройств. Если все устройства были замечены в то время как на переднем плане, вы не получите никаких обратных вызовов вообще.
- Запуск и остановка сканирования не сбрасывает, какие устройства считаются новыми. Если присутствует одно устройство, вы получите только один обратный вызов, даже при нескольких сканированиях, если только...
- Если вы подключаетесь к устройству, затем отключаетесь, а затем сканируете снова, устройство будет перечисляться снова (т.е. вы получите еще один вызов didDiscoverPeripheral). Я предполагаю, что iOS считает, что это "проявило интерес" к устройству.
Я не знаю, достаточно ли хороши попытки подключения к неподключаемым устройствам (например, рекламодателям BLE, например, реализующим профиль близости), так как мои примеры устройств подключаемы. Однако, по крайней мере, для подключаемых устройств этой процедуры сканирования / подключения / отключения / сканирования достаточно для опроса на наличие устройства в фоновом режиме.
Вышеуказанные результаты были получены с помощью iPhone 4S под управлением iOS 5.0.1.
В дополнение к ответу Криса:
- Если ваше приложение имеет "bluetooth-центральный" фоновый режим и подключено к периферийному устройству, вы можете получать уведомления (
peripheral:didUpdateValueForCharacteristic:error:
) из периферийного в фоновом режиме, даже через 10 минут.
Поэтому, если вы хотите непрерывно работать в фоновом режиме, у вас есть 2 варианта:
- Запустите цикл "подключить, отключить, снова сканировать"
- Сделать периферию отправлять уведомления
Позже должна появиться "Фоновая обработка событий" из основных видео на Bluetooth WWDC 2012 https://developer.apple.com/videos/wwdc/2012/ Но первое выглядит как хак, я не хочу на это полагаться.
Я проверял это на iPhone5, iOS6.1.4
Apple, наконец, выпустила Руководство по программированию Core Bluetooth, и вот официальная заметка о
Также хорошо отметить поведение фонового режима и CoreBluetooth, связанного с iBeacons, хотя Apple нравится думать об этом как о функциональности CoreLocation:
Когда уведомления для региона iBeacon включены, они будут уведомлять пользователя о входе или выходе из региона. Эти уведомления могут быть сделаны в зависимости от того, включен дисплей или выключен. Эти уведомления будут работать, даже если приложение, запрашивающее уведомления, находится в фоновом режиме. (Это очень ясно видно в документации).
Не так очевидно: если вы используете API ранжирования iBeacon, то ваше приложение должно быть на переднем плане. Это прямо не сказано об этом в документации - на самом деле, можно ввести в заблуждение, полагая, что ранжирование должно работать в фоновом режиме из документации. Тем не менее, инженер Apple разъясняет это в посте, похороненном где-то в длинной ветке на форуме разработчиков Apple, и я тоже видел, что это не удалось. Ранжирование будет работать только на переднем плане.
Можно обнаружить другие сервисы, рекламируемые периферийной рекламой iBeacons. Но это будет работать только на переднем плане. Поэтому, если вы хотите, чтобы центральный узел получал уведомление о близости с помощью iBeacons, а затем выполнял некоторые другие транзакции с использованием других служб на основе BLE, это будет работать, но только на переднем плане. Это не будет работать в фоновом режиме. Для транзакций с BLE-сервисами в фоновом режиме реклама должна быть обычной рекламой BLE, а не iBeacon. Вы не можете использовать рекламу iBeacon, чтобы помочь процессу обнаружения в фоновом режиме, а затем переключиться на использование BLE-сервисов в фоновом режиме. (Мне бы очень понравилось, чтобы это работало, но не играло в кости).
Я только что изучил фоновый режим для устройств BLE на iOS8.3 и 8.4 и обнаружил некоторые отличия сверху:
если я начну
[centralManager scanForPeripheralsWithServices:@[[CBUUID UUIDWithString:kServiceUUID]] параметры:@{CBCentralManagerScanOptionAllowDuplicatesKey: @YES }];
от
- (void)applicationDidEnterBackground:(UIApplication *)application
Я обнаружил, что перечисление возвращает одно и то же устройство при каждом вызове с разными RSSI, поэтому CBCentralManagerScanOptionAllowDuplicatesKey не игнорируется.
- Если приложение находится на переднем плане, оно обнаруживает устройство BLE 50 раз в секунду. Если приложение работает в фоновом режиме, но экран телефона активен, приложение обнаруживает устройства BLE 6 раз в секунду. Если экран телефона заблокирован, приложение обнаруживает устройства BLE 1 раз в сек.