Bluetooth a basso consumo energetico/Mbed 2 deprecato BLE_GATT_Example
Questa è una dimostrazione di come creare un servizio e una caratteristica GATT.
Dipendenze: API_BLE mbed nRF51822
Forchetta di BLE_EvothingsEsempio_GATTdi Austin Pietranera
- Casa
- Storia
- Grafico
- Documentazione dell'API
- Wiki
- Richieste pull
Introduzione
Questo codice mostra come utilizzare BLE_API per creare un servizio GATT e una caratteristica per attivare/disattivare un LED.
Panoramica
Questo codice è una dimostrazione di come creare un servizio personalizzato (UUID=0xA0000) con due caratteristiche, una caratteristica di sola lettura (UUID=0xA001) e una caratteristica di scrittura (UUID=0xA002). Ciò che viene scritto nella caratteristica di scrittura verrà copiato nella caratteristica di lettura e trasmesso. Se viene scritto un singolo byte, verrà utilizzato per attivare/disattivare il LED di bordo, se viene scritto più di 1 byte, i dati verranno scritti sul terminale. La dimensione massima predefinita è 10 byte.
video
Questo è un video su come utilizzare questo esempio. Si noti che in questo video viene utilizzato Android per leggere/scrivere le caratteristiche. Questo potrebbe essere fatto altrettanto facilmente con l'app Evothings elencata di seguito o un'app iOS equivalente. Potrebbe essere stata utilizzata qualsiasi app in grado di leggere/scrivere caratteristiche.
Dettagli
gli UUID caratteristici e di servizio vengono inizializzati qui
UUID
uint16_t customServiceUUID = 0xA000;uint16_t readCharUUID = 0xA001;uint16_t writeCharUUID = 0xA002;
Impostiamo qui l'elenco degli UUID disponibili che verranno pubblicizzati come parte del pacchetto pubblicitario GAP. (è buona norma fare in modo che corrisponda ai servizi che stai effettivamente pubblicizzando, quindi in questo caso dovremmo impostarlo su 0xA000, ma stiamo scegliendo di impostarlo su 0xFFFF in modo che sia più facile distinguerlo sull'app di scansione)
Set_ServiceID
static const uint16_t uuid16_list[] = {0xFFFF};...ble.accumulateAdvertisingPayload(GapAdvertisingData::COMPLETE_LIST_16BIT_SERVICE_IDS, (uint8_t *)uuid16_list, sizeof(uuid16_list)); // Trasmissione dell'UUID nel pacchetto pubblicitario
Successivamente impostiamo le caratteristiche e poi le mettiamo insieme in un servizio. Si noti che ogni caratteristica ha un massimo di 10 byte di spazio valore, questo può essere espanso fino a 512B.
Setup_Servizio_&_Caratteristiche
// Imposta le caratteristiche personalizzate uint8_t readValue[10] = {0};ReadOnlyArrayGattCharacteristicreadChar(readCharUUID, readValue); static uint8_t writeValue[10] = {0};WriteOnlyArrayGattCharacteristic writeChar(writeCharUUID, writeValue); // Imposta il servizio personalizzatoGattCharacteristic *characteristics[] = {&readChar, &writeChar};GattService customService(customServiceUUID, caratteristiche, sizeof(characteristics) / sizeof(GattCharacteristic *));
Successivamente impostiamo la funzione writeCharCallback() che verrà chiamata quando viene attivato un evento BLE onDataWritten (quando qualcuno scrive su una caratteristica sul dispositivo). Questa funzione controllerà per vedere quale caratteristica viene scritta e quindi la gestirà in modo appropriato. In questo caso c'è solo una caratteristica scrivibile quindi la sua forma ridondante, ma buona per combinazioni servizio/caratteristica più complesse.
On_Characteristic_write_to_callback
void writeCharCallback(const GattCharacteristicWriteCBParams *params){ // controlla per vedere quale caratteristica è stata scritta, dall'handle if(params->charHandle == writeChar.getValueHandle()) { // attiva/disattiva il LED se viene scritto solo 1 byte if(params- >len == 1) { led = parametri->dati[0]; ...} // stampa i dati se è scritto più di 1 byte else { printf("\n\r Dati ricevuti: lunghezza = %d, dati = 0x",params->len); ...} // aggiorna readChar con il valore di writeChar ble.updateCharacteristicValue(readChar.getValueHandle(),params->data,params->len); }}...// registra la funzione di callbackble.onDataWritten(writeCharCallback);...
L'ultima cosa da fare è registrare il servizio con l'oggetto BLE in modo che sia disponibile.
Add_Service_to_BLE_Object
... // aggiungi il nostro servizio personalizzato ble.addService(customService);...
Visualizzazione dei dati
Puoi usare sia ilAzzurroapp su iOS o ilPannello di controllo principale nRFapplicazione su Android per visualizzare i dati pubblicitari. In alternativa puoi utilizzare aApp GATT Evothings personalizzataper visualizzare i dati.
Evoluzioni?
Evoluzioniè un ambiente di prototipazione rapida che utilizza cordova per consentirti di sviluppare rapidamente applicazioni per smartphone in Javascript. Si prega di scaricare ilBanco da lavoro Evothingssul tuo computer e il client Evothings sul tuo smartphone. Il workbench Evothings verrà fornito con un programma chiamato "mbed Evothings GATT", questo programma per smartphone Evothings è pensato per essere utilizzato con il codice mbed incorporato. Per istruzioni su come utilizzare evothings, consultare la sezione di riferimento di seguito.
Riferimento
- file
- revisioni
- annotare
- diff
- crudo
CustomService.h
- Commitante:
- Ciao Austin
- Data:
- 2015-03-09
- Revisione:
- 7: f6814152873c
- Genitore:
- 1:94152e7d8b5c
Contenuto del file dalla revisione 7:f6814152873c:
/* mbed Microcontroller Library * Copyright (c) 2006-2013 ARM Limited * * Licenza Apache, versione 2.0 (la "Licenza"); * non puoi utilizzare questo file se non in conformità con la Licenza. * È possibile ottenere una copia della Licenza all'indirizzo * * http://www.apache.org/licenses/LICENSE-2.0 * * A meno che non sia richiesto dalla legge applicabile o concordato per iscritto, il software * distribuito sotto la Licenza è distribuito su un "COSÌ COM'È", * SENZA GARANZIE O CONDIZIONI DI ALCUN TIPO, espresse o implicite. * Vedere la Licenza per la lingua specifica che regola le autorizzazioni e * le limitazioni previste dalla Licenza. */ #ifndef __BLE_HEART_RATE_SERVICE_H__#define __BLE_HEART_RATE_SERVICE_H__ #include "BLEDevice.h" /*** @class HeartRateService* @brief Servizio BLE per HeartRate. Questo servizio BLE contiene la posizione del sensore, la frequenza cardiaca in battiti al minuto.
* Servizio: https://developer.bluetooth.org/gatt/services/Pages/ServiceViewer.aspx?u=org.bluetooth.service.heart_rate.xml
* Carattere HRM: https://developer. bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.heart_rate_measurement.xml
* Posizione: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx ?u=org.bluetooth.characteristic.body_sensor_location.xml*/class HeartRateService {public: /** * @enum SensorLocation * @brief Posizione del sensore di frequenza cardiaca sul corpo. */ enum { LOCATION_OTHER = 0, /*!< Altra posizione */ LOCATION_CHEST, /*!< Petto */ LOCATION_WRIST, /*!< Polso */ LOCATION_FINGER, /*!< Dito */ LOCATION_HAND, /*!< Mano */ LOCATION_EAR_LOBE, /*!< Lobo dell'orecchio */ LOCATION_FOOT, /*!< Piede */ }; public: /** * @brief Costruttore con valore del contatore HRM a 8 bit. * * @param[ref] _ble * Riferimento al BLEDevice sottostante. * @param[in] hrmCounter (8-bit) * valore iniziale per il contatore hrm. * @param[in] location * Posizione del sensore. */ HeartRateService(BLEDevice &_ble, uint8_t hrmCounter, uint8_t location) : ble(_ble), valueBytes(hrmCounter), hrmRate(GattCharacteristic::UUID_HEART_RATE_MEASUREMENT_CHAR, valueBytes.getPointer(), valueBytes.getNumValueBytes(), HeartRateValueBytes::MAX_VALUE_BYTES, Gatt Caratteristico: :BLE_GATT_CHAR_PROPERTIES_NOTIFY), hrmLocation(GattCharacteristic::UUID_BODY_SENSOR_LOCATION_CHAR, &posizione), controlPoint(GattCharacteristic::UUID_HEART_RATE_CONTROL_POINT_CHAR, &controlPointValue) { setupService(); } /** * @brief Costruttore con un valore contatore HRM a 16 bit. * * @param[in] _ble * Riferimento al BLEDevice sottostante. * @param[in] hrmCounter (8-bit) * valore iniziale per il contatore hrm. * @param[in] location * Posizione del sensore. */ HeartRateService(BLEDevice &_ble, uint16_t hrmCounter, uint8_t location) : ble(_ble), valueBytes(hrmCounter), hrmRate(GattCharacteristic::UUID_HEART_RATE_MEASUREMENT_CHAR, valueBytes.getPointer(), valueBytes.getNumValueBytes(), HeartRateValueBytes::MAX_VALUE_BYTES, G attCaratteristica: :BLE_GATT_CHAR_PROPERTIES_NOTIFY), hrmLocation(GattCharacteristic::UUID_BODY_SENSOR_LOCATION_CHAR, &posizione), controlPoint(GattCharacteristic::UUID_HEART_RATE_CONTROL_POINT_CHAR, &controlPointValue) { setupService(); } /** * @brief Imposta un nuovo valore a 8 bit per la frequenza cardiaca. * * @param[in] hrmCounter * Frequenza cardiaca in bpm. */ void updateHeartRate(uint8_t hrmCounter) { valueBytes.updateHeartRate(hrmCounter); ble.updateCharacteristicValue(hrmRate.getValueAttribute().getHandle(), valueBytes.getPointer(), valueBytes.getNumValueBytes()); } /** * Imposta un nuovo valore a 16 bit per la frequenza cardiaca. * * @param[in] hrmCounter * Frequenza cardiaca in bpm. */ void updateHeartRate(uint16_t hrmCounter) { valueBytes.updateHeartRate(hrmCounter); ble.updateCharacteristicValue(hrmRate.getValueAttribute().getHandle(), valueBytes.getPointer(), valueBytes.getNumValueBytes()); } /** * Questa richiamata consente a HeartRateService di ricevere aggiornamenti alla * caratteristica controlPoint. * * @param[in] params * Informazioni sulla caratteristica in fase di aggiornamento. */ virtual void onDataWritten(const GattCharacteristicWriteCBParams *params) { if (params->charHandle == controlPoint.getValueAttribute().getHandle()) { /* Fai qualcosa qui se il nuovo valore è 1; altrimenti puoi sovrascrivere questo metodo * estendendo questa classe. * @NOTA: se stai estendendo questa classe, assicurati di chiamare anche * ble.onDataWritten(this, &ExtendedHRService::onDataWritten); in * il tuo costruttore. */ } } private: void setupService(void) { static bool serviceAdded = false; /* Dovremmo aggiungere il servizio di frequenza cardiaca solo una volta. */ if (servizio aggiunto) { return; } GattCharacteristic *charTable[] = {&hrmRate, &hrmLocation, &controlPoint}; GattService hrmService(GattService::UUID_HEART_RATE_SERVICE, charTable, sizeof(charTable) / sizeof(GattCharacteristic *)); ble.addService(hrmService); servizioAggiunto = vero; ble.onDataWritten(this, &HeartRateService::onDataWritten); } private: /* Rappresentazione interna privata per i byte utilizzati per lavorare con il valore della caratteristica della frequenza cardiaca. */ struct HeartRateValueBytes { static const unsigned MAX_VALUE_BYTES = 3; /* FLAGS + fino a due byte per la frequenza cardiaca */ static const unsigned FLAGS_BYTE_INDEX = 0; const statico senza segno VALUE_FORMAT_BITNUM = 0; const statico uint8_t VALUE_FORMAT_FLAG = (1 << VALUE_FORMAT_BITNUM); HeartRateValueBytes(uint8_t hrmCounter) : valueBytes() { updateHeartRate(hrmCounter); } HeartRateValueBytes(uint16_t hrmCounter) : valueBytes() { updateHeartRate(hrmCounter); } void updateHeartRate(uint8_t hrmCounter) { valueBytes[FLAGS_BYTE_INDEX] &= ~VALUE_FORMAT_FLAG; valoreBytes[FLAGS_BYTE_INDEX + 1] = hrmCounter; } void updateHeartRate(uint16_t hrmCounter) { valueBytes[FLAGS_BYTE_INDEX] |= VALUE_FORMAT_FLAG; valoreBytes[FLAGS_BYTE_INDEX + 1] = (uint8_t)(hrmCounter & 0xFF); valoreBytes[FLAGS_BYTE_INDEX + 2] = (uint8_t)(hrmCounter >> 8); } uint8_t *getPointer(void) { return valueBytes; } const uint8_t *getPointer(void) const { return valueBytes; } unsigned getNumValueBytes(void) const { return 1 + ((valueBytes[FLAGS_BYTE_INDEX] & VALUE_FORMAT_FLAG) ? sizeof(uint16_t) : sizeof(uint8_t)); } private: /* Primo byte = valori a 8 bit, nessuna informazione aggiuntiva, Secondo byte = uint8_t Valore HRM */ /* Vedi --> https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx ?u=org.bluetooth.characteristic.heart_rate_measurement.xml */ uint8_t valueBytes[MAX_VALUE_BYTES]; }; privato: BLEDevice &ble; HeartRateValueBytes valoreBytes; uint8_t controlPointValue; GattCaratteristiche hrmRate; ReadOnlyGattCharacteristichrmLocation; WriteOnlyGattCharacteristic controlPoint;}; #endif /* #ifndef __BLE_HEART_RATE_SERVICE_H__*/