9

la scansione per la mia periferica come questa:Corebluetooth centrale responsabile di richiamata due volte didDiscoverPeripheral

NSDictionary *scanOptions = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:NO] 
                  forKey:CBCentralManagerScanOptionAllowDuplicatesKey]; 
     // Scan for peripherals with given UUID 
     [cm scanForPeripheralsWithServices:[NSArray arrayWithObject:HeliController.serviceUUID] options:scanOptions] 

Nessun problema, trovo la periferica e sono in grado di connettersi ad esso. Come potete vedere, gli do CBCentralManagerScanOptionAllowDuplicatesKey con bool NO per non consentire più di una periferica, ma a volte il callback didDiscoverPeripheral si attiva due volte.

- (void) centralManager:(CBCentralManager *)central 
    didDiscoverPeripheral:(CBPeripheral *)peripheral 
    advertisementData:(NSDictionary *)advertisementData 
       RSSI:(NSNumber *)RSSI 
{   
if(!discovered){ 
    discovered = YES; 
    NSLog(@"Discovered"); 

    [cm stopScan]; 

    [scanButton setTitle:@"Connect" forState:UIControlStateNormal]; 
} 
else if(discovered){ 
    discovered = YES 
    NSLog(@"Already discovered"); 
} 
} 

Alcune volte ottengo

Discovered 
Already discovered 

come output nella mia console, e il più delle volte solo il messaggio Discovered vede.

Nel mio delegato periferico ho scoprire servizi, che poi chiamano [peripheral discoverCharacteristics e il callback si verifica sempre:

- (void) peripheral:(CBPeripheral *)peripheral didDiscoverCharacteristicsForService:(CBService *)service error:(NSError *)error{ 

NSLog(@"Did discover characteristic for service %@", [service.peripheral UUID]); 

for(CBCharacteristic *c in [service characteristics]){ 
    // We never get here when peripheral is discovered twice 
    if([[c UUID] isEqual:myCharacteristicUUID]){ 

     NSLog(@"Found characteristic"); 

     self.throttleCharacteristic = c; 

    } 
} 

Quando didDiscoverPeripheral si verificano due volte, service diventa nil in questo metodo, anche se peripheral non è (UUID, il nome è ancora corretto).

Il riavvio del telefono o il ripristino delle impostazioni di rete risolvono il problema temporaneamente.

Ho davvero bisogno di farlo riparare! Grazie

+0

Qual è stato il parametro "non più di un dispositivo" che hai fornito? – yuklai

+0

false su CBCentralManagerScanOptionAllowDuplicatesKey – chwi

+0

La mia ipotesi è che venga chiamata due volte quando la potenza del segnale è scarsa. –

risposta

9

I dispositivi possono restituire dati aggiuntivi durante la pubblicità. Questi possono arrivare in pacchetti separati, arrivando in momenti diversi. In questo caso, didDiscoverPeripheral viene chiamato per primo quando il dispositivo viene inizialmente visto, e quindi di nuovo quando diventano disponibili informazioni aggiuntive.

CBCentralManagerScanOptionAllowDuplicatesKey è diverso. Indica a CoreBluetooth se desideri ricevere risultati duplicati quando il dispositivo si pubblicizza di nuovo. Non impedisce più chiamate a didDiscoverPeripheral per la stessa sequenza di scoperta; lo impedisce per sequenze di scoperte ripetute.

Fonte: http://lists.apple.com/archives/bluetooth-dev/2012/Apr/msg00047.html (il rappresentante Apple su bluetooth-dev).

+0

Grazie. Hai qualche idea su come risolvere questo? – chwi

+0

@Wilhelmsen: che cosa deve essere risolto? Ti basta monitorare gli UUID che hai già visto. –

+0

Ho provato la risposta di @ Mike, non tiene traccia degli UUID? Sono abbastanza nuovo in questo, quindi se avete ulteriori suggerimenti su come raggiungere questo obiettivo, sarei davvero grato! In ogni caso, grazie mille per le tue informazioni – chwi

6

Non penso che questo parametro faccia quello che pensi che faccia. La mia comprensione di come viene utilizzata in campioni Apple come Health Thermometer è che l'attivazione di questo flag consente di rilevare più periferiche diverse con lo stesso UUID. Ad esempio, se si desidera scrivere un'applicazione che guarda quattro diversi termometri nella stessa stanza e li trova tutti, è necessario il parametro in modo che la scansione non si fermi dopo aver trovato il primo.

Nel loro codice, Apple evita duplicati simili:

NSMutableArray *peripherals = [self mutableArrayValueForKey:@"thermometers"]; 
if(![self.thermometers containsObject:peripheral]) 
    [peripherals addObject:peripheral]; 

Se il dispositivo è già presente nella matrice, non viene aggiunto un secondo tempo.

Sarebbe bello se la documentazione fosse più chiara su questo punto. Ammetto che sto indovinando in base a come il parametro viene utilizzato nel contesto.

+0

Grazie! questo dovrebbe andare nel mio metodo didDiscoverPeripheral? – chwi

+0

Sì, è lì che Apple ha messo, comunque. Vedi http://developer.apple.com/library/mac/#samplecode/HealthThermometer/Listings/HealthThermometerClient_HealthThermometerClientAppDelegate_m.html#//apple_ref/doc/uid/DTS40011370-HealthThermometerClient_HealthThermometerClientAppDelegate_m-DontLinkElementID_4 per l'origine completa. – Mike

+0

In realtà penso che l'abbia risolto. Non sono stato in grado di replicarlo in alcun modo: D inserirò una risposta sulla mia domanda solo per chiarire. Grazie mille – chwi