7

Specyfikacja Low Energy Bluetooth nie mówi zbyt wiele o tym, czy urządzenia peryferyjne mogą łączyć się z więcej niż jednym centralnym urządzeniem naraz, ale moje testowanie doświadczenia mówi mi, że nie mogą.Ciągłe skanowanie centralnego menedżera iOS CoreBluetooth?

Ponieważ moja aplikacja wymaga niewiążącej relacji z urządzeniami peryferyjnymi (tj. Bez połączeń, które blokowałyby inne) i musi stale aktualizować ich wartości RSSI, szukam sposobu na ciągłe skanowanie urządzeń peryferyjnych i przechwytywanie ich wartości RSSI .

Metoda scanForPeripheralsWithServices wydaje się skanować przez pewien okres, a następnie zatrzymuje się. Uważam, że najlepiej jest skanować przez 3 sekundy naraz, stopScan, odczekać (kilka sekund), a następnie ponownie zainicjować skanowanie. Powtarzać.

Czy ktoś może wskazać lepszy sposób na zrobienie tego? Na przykład, konfigurowanie urządzenia peryferyjnego do połączenia z więcej niż jednym centralnym systemem?

Odpowiedz

7

Urządzenie peryferyjne nie może połączyć się z więcej niż jednym centralnym. Ale jeśli potrzebujesz po prostu przechwycić RSSI, nie potrzebujesz nawet połączenia. Skanowanie w poszukiwaniu urządzeń można pobrać RSSI przy użyciu tej funkcji:

- (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary *)advertisementData RSSI:(NSNumber *)RSSI 
+2

Tak, ale muszę nieustannie uzyskać zaktualizowany RSSI. Moje wnioski są takie, że gdy Centralny Menedżer odkrył i ponownie odkrył urządzenie peryferyjne kilka razy, przestał je wykrywać (wydaje się, że trwało to około 3 sekundy), nawet jeśli skanowanie jest kontynuowane. Pozostaje mi potrzeba ponownego zainicjowania skanowania, aby uzyskać zaktualizowane wartości RSSI. – Jonathan

+3

Tak, możesz ponownie zainicjować skanowanie wewnątrz funkcji didDiscoverPerirectal, przez co otrzymasz RSSI szybko na zawsze. – Aboelseoud

+1

Dzięki. To działa. W celu oszczędzania energii faktycznie zatrzymuję skanowanie po 100 ms, a następnie wykonuję 100ms serii co sekundę. Działa świetnie. – Jonathan

5

Co do poprzedniej odpowiedzi, jeśli jesteś zainteresowany tylko w RSSI można po prostu dostać się do metody Delegat:

- (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary *)advertisementData RSSI:(NSNumber *)RSSI 

BTW, domyślnie CBCentralManager wywoła tę metodę tylko raz. Jeśli potrzebujesz tej funkcji zwrotnej na miano każdym razem CBCentralManager odbiera pakiet reklamowy trzeba zainicjować skanowanie z opcją CBCentralManagerScanOptionAllowDuplicatesKey zestaw do YES:

NSDictionary *scanningOptions = @{CBCentralManagerScanOptionAllowDuplicatesKey: @YES}; 
[centralManager scanForPeripheralsWithServices:nil options:scanningOptions]; 

Strzeż się, że Apple zniechęcać korzystanie z tej opcji, jeśli nie jest to bezwzględnie konieczną .

Patrz: iOS Developer Library -Best Practices for Interacting with a Remote Peripheral Device

1

I rozwiązać tego typu problemu z tym kodem, w zasadzie tylko ponowne uruchomienie skanując każdy razem, gdy reklama jest przetwarzany. Miałem do czynienia z tym samym problemem, w którym instancja CBCentralManager przestałaby słuchać urządzenia peryferyjnego.

(. Ustawianie CBCentralManagerScanOptionAllowDuplicatesKey do @YES nie w pełni rozwiązać ten problem dla mnie)

Zakładając, że klasa implementuje CBCentralManagerDelegate:

- (id) init { 
    self.central = [[CBCentralManager alloc]initWithDelegate:self queue:nil]; 
    [self initScan]; 
} 

- (void) initScan { 
    [self.central stopScan]; 
    [self.central scanForPeripheralsWithServices:nil 
             options:[NSDictionary dictionaryWithObjectsAndKeys:@NO, CBCentralManagerScanOptionAllowDuplicatesKey, nil]]; 
} 

- (void) centralManager:(CBCentralManager*)central didDiscoverPeripheral:(CBPeripheral*)peripheral advertisementData:(NSDictionary*)advertisementData RSSI:(NSNumber*)RSSI { 

    // 
    // Do stuff here 
    // 

    [self initScan]; 
} 
Powiązane problemy