標籤:
// 當發現了我們所需要的characteristic,我們最想做的就是查看下這個characteristic的value是多少。也就是說,我們需要一個接收資料的操作。
- (void)peripheral:(CBPeripheral *)peripheral didDiscoverCharacteristicsForService:(CBService *)service error:(NSError *)error
在CoreBluetooth中,提供了兩種方法:
1. [peripheral readValueForCharacteristic:characteristic];
peripheral是我們程式中的外設,characteristic是我們那個感興趣的characteristic當調用這個方法後,程式會回調一個方法:
- (void)peripheral:(CBPeripheral *)peripheral didUpdateValueForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error
上面的第二個參數:(CBCharacteristic *)characteristic -----我們直接用characteristic.value就擷取到了感興趣的characteristic的value,類型是NSData的,之後就可以對值進行操作了。
PS:回調的前提是要設定代理,不要忘了。這個方法比較直接,也符合我們的一般邏輯,下面介紹第二種方法
2. [peripheral setNotifyValue:YES forCharacteristic:characteristic]; Subscribe“訂閱”
第一個參數設定為YES,至於為啥,後面我說說我的理解。第二個參數同樣是我們感興趣的characteristic。
調用這個方法後,程式會回調一個方法:
- (void)peripheral:(CBPeripheral *)peripheral didUpdateNotificationStateForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error
這方法能做什嗎?我覺得主要是一些錯誤判斷,利用上面第三個參數error,如果出錯,系統把錯誤資訊放在error中,可以列印顯示。
之後在這個方法中調用[peripheral readValueForCharacteristic:characteristic]同樣會回調1中那個回調方法,
- (void)peripheral:(CBPeripheral *)peripheral didUpdateValueForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error
我們同樣在這裡處理資料,跟1中一樣。
跟1相比,多走了一步,多了一個參數notifyValue,這個參數我感覺就是一個標誌量,當為YES的時候,我要訂閱這個characteristic,之後每當這個characteristic的value發生變化時,都會回調
- (void)peripheral:(CBPeripheral *)peripheral didUpdateValueForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error
就好像我要訂閱這個雜誌(characteristic),每當有新版本的雜誌發行時(value值改變),你就要給我送一本(回調方法),為啥給我送?因為我訂閱了。
所以呢,這種方法在某些情況下是比1更高效的,就是我們需要操作的characteristic的value經常發生變化時。比如心率儀這些裝置的心率characteristic的value。
最後還有一個重要的補充,當我們已經找到了我們感興趣的characteristic後,他的value並不一定通過1方法或者2方法就可以接收的,就算可以接收,有時候只能用1,有時候只能用2。
這牽扯到characteristic的一個property:
typedef enum
{
CBCharacteristicPropertyBroadcast = 0x01,
CBCharacteristicPropertyRead = 0x02,
CBCharacteristicPropertyWriteWithoutResponse = 0x04,
CBCharacteristicPropertyWrite = 0x08,
CBCharacteristicPropertyNotify = 0x10,
CBCharacteristicPropertyIndicate = 0x20,
CBCharacteristicPropertyAuthenticatedSignedWrites = 0x40,
CBCharacteristicPropertyExtendedProperties = 0x80,
CBCharacteristicPropertyNotifyEncryptionRequired = 0x100,
CBCharacteristicPropertyIndicateEncryptionRequired = 0x200,
} CBCharacteristicProperties;
當為read(0x02)的時候,我們用1方法可以查看,用2就會出錯。當為notify(0x10)的時候我們就得用2方法。其他就不說明了,比如write就只能寫value······
所以當我們想查看value的時候,先瞭解一下這個characteristic的property,看是不是能讓我們讀的。
怎麼查看?找BLE外設的裝置廠商或者查看外設的說明書。
"<CBCharacteristic: 0x1565ee50, UUID = System ID, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x156806b0, UUID = Model Number String, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x1567f9e0, UUID = Serial Number String, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x1565a640, UUID = Firmware Revision String, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x15682f70, UUID = Hardware Revision String, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x1564bdf0, UUID = Software Revision String, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x1565a8c0, UUID = Manufacturer Name String, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x15683cd0, UUID = IEEE Regulatory Certification, properties = 0x2, value = (null), notifying = NO>",
"<CBCharacteristic: 0x15683bf0, UUID = PnP ID, properties = 0x2, value = (null), notifying = NO>"
推薦將value經常變化的characteristic的property設為notify(CBCharacteristicPropertyNotify)。
iOS 學習筆記 三 (2015.03.05)