0

Я надеюсь передать некоторые из моего кода CoreBluetooth с iOS на OS X. Я настроил общий набор оберток CoreBluetooth, которые потребляются как приложение iOS, так и приложение OS X точно так же с теми же устройствами BLE.CBPeripheral advertisingData отличается при обнаружении периферийных устройств в OSX vs iOS (GAP/GATT)

Сканирование для периферийных устройств:

override init() { 
    super.init() 
    let queue = DispatchQueue.global(qos: .background) 
    centralManager = CBCentralManager(delegate: self, queue: queue) 
} 

func startScanning() { 
    let options: [String: Any] = [CBCentralManagerScanOptionAllowDuplicatesKey: true] 
    let deviceUUID = CBUUID(string: Project.Service.Device) 
    let recoveryUUID = CBUUID(string: Project.Service.DFURecovery) 
    centralManager?.scanForPeripherals(withServices: [deviceUUID, recoveryUUID], options: options) 
} 

func centralManager(_ central: CBCentralManager, didDiscover peripheral: CBPeripheral, advertisementData: [String : Any], rssi RSSI: NSNumber){ 
    // Inspect advertisementData here to decipher what kind of device 
} 

На мое приложение IOS, didDiscoverPeripheral обжигают. Затем, когда я проверить данные рекламы я получаю все ключи/значения, которые я ожидаю:

{ 
    kCBAdvDataIsConnectable = 1; 
    kCBAdvDataLocalName = "My Device"; 
    kCBAdvDataManufacturerData = <34045254 5877f283 43fdd12d ff530978 45000000 000050c2 6500>; 
    kCBAdvDataServiceData =  { 
     Battery = <64>; 
    }; 
    kCBAdvDataServiceUUIDs =  (
     "My Inforamtion" 
    ); 
} 

Однако, когда этот же код запуска (сканирование для одних и тех же устройств) из X приложения OS, данные реклама Отсутствуют некоторые поля.

{ 
    kCBAdvDataIsConnectable = 1; 
    kCBAdvDataManufacturerData = <34045254 5877f36e 43fdd12d ff530978 45000000 000050c2 6500>; 
} 

Следующие пары ключей/значений отсутствуют в рекламируемых данных.

kCBAdvDataLocalName 
kCBAdvDataServiceData 
kCBAdvDataServiceUUIDs 

Я попытался добавить эти ключи к scanForPeripherals называют так:

let options: [String: Any] = [CBCentralManagerScanOptionAllowDuplicatesKey: true, 
            CBAdvertisementDataLocalNameKey: true, 
            CBAdvertisementDataServiceDataKey: true, 
            CBAdvertisementDataServiceUUIDsKey: true] 
    let deviceUUID = CBUUID(string: Nightlight.Service.Device) 
    let recoveryUUID = CBUUID(string: Nightlight.Service.DFURecovery) 
    centralManager?.scanForPeripherals(withServices: [deviceUUID, recoveryUUID], options: options) 

При отсутствии эффекта.

ответ

0

OSX может вызвать didDiscoverPeripheral несколько раз для каждого устройства, каждый вызов с различными объявлениями. Решение, которое я придумал, - это написать кеш.

импорта Фонд импорта CoreBluetooth

class AdvertisementDataCache { 

    fileprivate var map = [UUID: [String: Any]]() 

    func append(peripheral: CBPeripheral, advertisementData: [String: Any]) -> [String: Any] { 
     var ad = (map[peripheral.identifier]) ?? [String: Any]() 
     for (key, value) in advertisementData { 
      ad[key] = value 
     } 
     map[peripheral.identifier] = ad 
     return ad 
    } 

    func clear() { 
     map.removeAll() 
    } 
} 

А потом в didDiscoverPeripheral:

var advertisementDataCache = AdvertisementDataCache() 

func centralManager(_ central: CBCentralManager, didDiscover peripheral: CBPeripheral, advertisementData: [String : Any], rssi RSSI: NSNumber){ 
    let advertisementDataCache = self.advertisementDataCache.append(peripheral: peripheral, advertisementData: advertisementDataCache) 
    // cache may contain all 5 of the advertisements, depending on how may have been delivered 
    if let device = AdvertisementData.isTheDeviceIAmLookingFor(peripheral: peripheral, advertisementData: cache) { 
     // Do stuff with device 
    } 
} 

 Смежные вопросы

  • Нет связанных вопросов^_^