Please fill the info fields, it helps to get you faster support ;)
Board: ESP32 Dev Module
Core Installation/update date: 11/JAN/2018
IDE name: Arduino IDE
Flash Frequency: 40Mhz
Upload Speed: 115200
I'm trying to create BLE server that set values and notify changes
all my values are floats but setValue function is not clear what optio can be used to set a float
do i need to convert double values or floats values to unint ?
any help would be great
#include <Wire.h>
#include "MutichannelGasSensor.h"
#include <SPI.h>
#include <BLE2902.h>
#include <BLEDevice.h>
#include <BLEUtils.h>
#include <BLEServer.h>
#include "Adafruit_HDC1000.h"
#include <math.h>
#include "EmonLib.h"
Adafruit_HDC1000 hdc = Adafruit_HDC1000();
EnergyMonitor emon1;
#define LED_PIN 5
#define PRE_HEAT_TIME 1
const float reference_vol = 0.500;
unsigned char clear_num = 0; //when use lcd to display
float R = 0;
float voltage = 0;
// See the following for generating UUIDs:
//#define aqService "CCC0"
//#define allCharacteristic "CCC1"
//#define nh3Characteristic "CCCa"
//#define coCharacteristic "CCC2"
//#define no2Characteristic "CCC3"
//#define c3h8Characteristic "CCC4"
//#define c4h10Characteristic "CCC5"
//#define ch4Characteristic "CCC6"
//#define h2Characteristic "CCC6"
//
//#define aqService2 "DDD0"
//#define c2h5ohCharacteristic "DDD1"
//#define tempCharacteristic "DDD2"
//#define humCharacteristic "DDD3"
//
//#define aqService3 "EEE0"
//#define power1Characteristic "EEE1"
//#define power2Characteristic "EEE2"
//
//#define getService "19b10000e8f2537e4f6cd104768a1214"
//#define switchCharacteristic "19b10001e8f2537e4f6cd104768a1214"
//#define calibCharacteristic "19b10001e8f2537e4f6cd104768a1215"
BLEDescriptor allDescriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor nh3Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor coDescriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor no2Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor c3h8Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor c4h10Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor ch4Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor h2Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor c2h5ohDescriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor tempDescriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor humDescriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor power1Descriptor(BLEUUID((uint16_t)0x2901));
BLEDescriptor power2Descriptor(BLEUUID((uint16_t)0x2901));
BLECharacteristic allCharacteristic("CCC1", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic nh3Characteristic("CCCa", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic coCharacteristic("CCC2", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic no2Characteristic("CCC3", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic c3h8Characteristic("CCC4", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic c4h10Characteristic("CCC5", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic ch4Characteristic("CCC6", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic h2Characteristic("CCC7", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic c2h5ohCharacteristic("DDD1", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic tempCharacteristic("DDD2", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic humCharacteristic("DDD3", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic power1Characteristic("EEE1", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic power2Characteristic("EEE2", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_NOTIFY);
BLECharacteristic switchCharacteristic("19b10001e8f2537e4f6cd104768a1214", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_WRITE);
BLECharacteristic calibCharacteristic("19b10001e8f2537e4f6cd104768a1215", BLECharacteristic::PROPERTY_READ | BLECharacteristic::PROPERTY_WRITE);
volatile bool readFromSensor = false;
volatile bool readFromSensor2 = false;
volatile bool readFromSensor3 = false;
volatile bool readFromSensor4 = false;
float lastTempReading;
float lastHumidityReading;
void setup() {
Serial.begin(115200);
pinMode(LED_PIN, OUTPUT);
digitalWrite(LED_PIN, HIGH);
Serial.println("Starting BLE work!");
BLEDevice::init("AirQuality");
// Create the BLE Server
BLEServer *pServer = BLEDevice::createServer();
// Create the BLE Service
BLEService *pService = pServer->createService(BLEUUID((uint16_t)0xCCC0));
allDescriptor.setValue("All");
nh3Descriptor.setValue("NH3");
coDescriptor.setValue("CO");
no2Descriptor.setValue("NO2");
c3h8Descriptor.setValue("C3H8");
c4h10Descriptor.setValue("C4H10");
ch4Descriptor.setValue("CH4");
h2Descriptor.setValue("H2");
c2h5ohDescriptor.setValue("C2H5OH");
tempDescriptor.setValue("temp");
humCharacteristic.setValue("hum");
power1Descriptor.setValue("current");
power2Descriptor.setValue("power");
allCharacteristic.addDescriptor(&allDescriptor);
nh3Characteristic.addDescriptor(&nh3Descriptor);
coCharacteristic.addDescriptor(&coDescriptor);
no2Characteristic.addDescriptor(&no2Descriptor);
c3h8Characteristic.addDescriptor(&c3h8Descriptor);
c4h10Characteristic.addDescriptor(&c4h10Descriptor);
ch4Characteristic.addDescriptor(&ch4Descriptor);
h2Characteristic.addDescriptor(&h2Descriptor);
c2h5ohCharacteristic.addDescriptor(&c2h5ohDescriptor);
tempCharacteristic.addDescriptor(&tempDescriptor);
humCharacteristic.addDescriptor(&humDescriptor);
power1Characteristic.addDescriptor(&power1Descriptor);
power2Characteristic.addDescriptor(&power2Descriptor);
// https://www.bluetooth.com/specifications/gatt/viewer?attributeXmlFile=org.bluetooth.descriptor.gatt.client_characteristic_configuration.xml
// Create a BLE Descriptor
allCharacteristic.addDescriptor(new BLE2902());
nh3Characteristic.addDescriptor(new BLE2902());
coCharacteristic.addDescriptor(new BLE2902());
no2Characteristic.addDescriptor(new BLE2902());
c3h8Characteristic.addDescriptor(new BLE2902());
c4h10Characteristic.addDescriptor(new BLE2902());
ch4Characteristic.addDescriptor(new BLE2902());
h2Characteristic.addDescriptor(new BLE2902());
c2h5ohCharacteristic.addDescriptor(new BLE2902());
tempCharacteristic.addDescriptor(new BLE2902());
humCharacteristic.addDescriptor(new BLE2902());
power1Characteristic.addDescriptor(new BLE2902());
power2Characteristic.addDescriptor(new BLE2902());
switchCharacteristic.addDescriptor(new BLE2902());
calibCharacteristic.addDescriptor(new BLE2902());
pService->addCharacteristic(&allCharacteristic);
pService->addCharacteristic(&nh3Characteristic);
pService->addCharacteristic(&coCharacteristic);
pService->addCharacteristic(&no2Characteristic);
pService->addCharacteristic(&c3h8Characteristic);
pService->addCharacteristic(&c4h10Characteristic);
pService->addCharacteristic(&ch4Characteristic);
pService->addCharacteristic(&h2Characteristic);
pService->addCharacteristic(&c2h5ohCharacteristic);
pService->addCharacteristic(&tempCharacteristic);
pService->addCharacteristic(&humCharacteristic);
pService->addCharacteristic(&power1Characteristic);
pService->addCharacteristic(&power2Characteristic);
pService->addCharacteristic(&switchCharacteristic);
pService->addCharacteristic(&calibCharacteristic);
pService->start();
// Start advertising
pServer->getAdvertising()->start();
Serial.println(F("BLE AirQ Sensor"));
Serial.println("power on!");
digitalWrite(LED_PIN, LOW);
Serial.println("power on, and pre-heat");
gas.begin(0x04);//the default I2C address of the slave is 0x04
gas.powerOn();
delay(60);
hdc.begin();
}
void getallVal() {
float t;
float h;
float a;
String r;
t = hdc.readTemperature();
r += String(t) + ",";
h = hdc.readHumidity();
r += String(h) + ",";
a = gas.measure_NH3();
r += String(a) + ",";
a = gas.measure_CO();
r += String(a) + ",";
a = gas.measure_NO2();
r += String(a) + ",";
a = gas.measure_C3H8();
r += String(a) + ",";
a = gas.measure_C4H10();
r += String(a) + ",";
a = gas.measure_CH4();
r += String(a) + ",";
a = gas.measure_H2();
r += String(a) + ",";
a = gas.measure_C2H5OH();
r += String(a) + ",";
Serial.print(r);
// char *b ;
// b = string2char(r);
// allCharacteristic.setValue(b);
// char b[20] ;
// r.toCharArray(b, 20);
// allCharacteristic.setValue((unsigned char*)b);
}
void calibrate() {
for (int i = 60 * PRE_HEAT_TIME; i >= 0; i--)
{
Serial.print(i / 60);
Serial.print(":");
Serial.println(i % 60);
delay(1000);
}
Serial.println("Begin to calibrate...");
gas.doCalibrate();
Serial.println("Calibration ok");
delay(60);
}
void setPowerVal() {
double Irms = emon1.calcIrms(1480); // Calculate Irms only
double Power = Irms * 230.0 / 1000;
power1Characteristic.setValue(Irms);
power2Characteristic.setValue(Power);
power1Characteristic.notify();
power2Characteristic.notify();
Serial.print(F("I: ")); Serial.print(Irms); Serial.println();
Serial.print(F("P: ")); Serial.print(Power); Serial.println();
//emon1.calcVI(20,2000); // Calculate all. No.of wavelengths, time-out
//emon1.serialprint(); // Print out all variables
}
void setTempHumVal() {
float t;
float h;
t = hdc.readTemperature();
h = hdc.readHumidity();
tempCharacteristic.setValue(t);
humCharacteristic.setValue(h);
tempCharacteristic.notify();
humCharacteristic.notify();
Serial.print(F("T: ")); Serial.print(t); Serial.println();
Serial.print(F("H: ")); Serial.print(h); Serial.println();
}
void setNH3CharacteristicValue() {
float a;
a = gas.measure_NH3();
nh3Characteristic.setValue(a);
nh3Characteristic.notify();
Serial.print(F("NH3: ")); Serial.print(a); Serial.println();
}
void setCOCharacteristicValue() {
float a;
a = gas.measure_CO();
coCharacteristic.setValue(a);
coCharacteristic.notify();
Serial.print(F("CO: ")); Serial.print(a); Serial.println();
}
void setNO2CharacteristicValue() {
float a;
a = gas.measure_NO2();
no2Characteristic.setValue(a,);
no2Characteristic.notify();
Serial.print(F("NO2: ")); Serial.print(a); Serial.println();
}
void setC3H8CharacteristicValue() {
float a;
a = gas.measure_C3H8();
c3h8Characteristic.setValue(a);
c3h8Characteristic.notify();
Serial.print(F("C3H8: ")); Serial.print(a); Serial.println();
}
void setC4H10CharacteristicValue() {
float a;
a = gas.measure_C4H10();
c4h10Characteristic.setValue(a);
c4h10Characteristic.notify();
Serial.print(F("C4H10: ")); Serial.print(a); Serial.println();
}
void setCH4CharacteristicValue() {
float a;
a = gas.measure_CH4();
ch4Characteristic.setValue(a);
ch4Characteristic.notify();
Serial.print(F("CH4: ")); Serial.print(a); Serial.println();
}
void setH2CharacteristicValue() {
float a;
a = gas.measure_H2();
h2Characteristic.setValue(a);
h2Characteristic.notify();
Serial.print(F("H2: ")); Serial.print(a); Serial.println();
}
void setC2H5OHCharacteristicValue() {
float a;
a = gas.measure_C2H5OH();
c2h5ohCharacteristic.setValue(a);
c2h5ohCharacteristic.notify();
Serial.print(F("C2H5OH: ")); Serial.print(a); Serial.println();
}
void setEMPTYCharacteristicValue() {
float a;
a = gas.measure_C2H5OH();
c2h5ohCharacteristic.setValue(a);
c2h5ohCharacteristic.notify();
Serial.print(F("C2H5OH: ")); Serial.print(a); Serial.println();
}
boolean significantChange(float val1, float val2, float threshold) {
return (abs(val1 - val2) >= threshold);
}
void loop() {
// put your main code here, to run repeatedly:
if (readFromSensor) {
//getallVal();
digitalWrite(LED_PIN, HIGH);
setNH3CharacteristicValue();
setCOCharacteristicValue();
setNO2CharacteristicValue();
setC3H8CharacteristicValue();
setC4H10CharacteristicValue();
readFromSensor = false;
delay(10000);
digitalWrite(LED_PIN, LOW);
}
if (readFromSensor2) {
digitalWrite(LED_PIN, HIGH);
setCH4CharacteristicValue();
setH2CharacteristicValue();
setC2H5OHCharacteristicValue();
setTempHumVal();
readFromSensor2 = false;
delay(10000);
digitalWrite(LED_PIN, LOW);
}
if (readFromSensor3) {
digitalWrite(LED_PIN, HIGH);
setPowerVal();
readFromSensor3 = false;
digitalWrite(LED_PIN, LOW);
}
if (readFromSensor4) {
calibCharacteristic.setValue(0);
digitalWrite(LED_PIN, HIGH);
calibrate();
readFromSensor4 = false;
digitalWrite(LED_PIN, LOW);
calibCharacteristic.setValue(1);
}
}
void switchCharacteristicWritten() {
// central wrote new value to characteristic, update LED
Serial.print(F("Characteristic event, writen: "));
Serial.print(switchCharacteristic.getValue());
if ( switchCharacteristic.getValue() == "1" ) {
timerHandler();
}
if ( switchCharacteristic.getValue() == "2" ) {
timer2Handler();
}
if ( switchCharacteristic.getValue() == "3" ) {
timer3Handler();
}
if ( switchCharacteristic.getValue() == "4" ) {
timer4Handler();
}
}
void timerHandler() {
readFromSensor = true;
}
void timer2Handler() {
readFromSensor2 = true;
}
void timer3Handler() {
readFromSensor3 = true;
}
void timer4Handler() {
readFromSensor4 = true;
}
char* string2char(String command) {
if (command.length() != 0) {
char *p = const_cast<char*>(command.c_str());
return p;
}
}
Arduino/BLE_server_esp32/BLE_server_esp32.ino: In function 'void setPowerVal()':
BLE_server_esp32:247: error: no matching function for call to 'BLECharacteristic::setValue(double&)'
power1Characteristic.setValue(Irms);
^
In file included from /Documents/Arduino/hardware/espressif/esp32/libraries/BLE/src/BLEDescriptor.h:14:0,
from /Documents/Arduino/hardware/espressif/esp32/libraries/BLE/src/BLE2902.h:13,
from /Documents/Arduino/BLE_server_esp32/BLE_server_esp32.ino:8:
/Documents/Arduino/hardware/espressif/esp32/libraries/BLE/src/BLECharacteristic.h:75:7: note: candidate: void BLECharacteristic::setValue(uint8_t*, size_t)
void setValue(uint8_t* data, size_t size);
@gesaleh a BLE value is either an array of bytes or a String.
If you look at BLE characteristic Temperature
Temperature
Information:
Unit is in degrees Celsius with a resolution of 0.01 degrees Celsius
Unit:
org.bluetooth.unit.thermodynamic_temperature.degree_celsius
Exponent:聽Decimal,聽-2
and BLE characteristic Humidty
Humidity
Information:
Unit is in percent with a resolution of 0.01 percent
Unit:
org.bluetooth.unit.percentage
Exponent:聽Decimal,聽-2
you can see that both temperature and humidity are uint16 values. Temperature and humidity are both defined with 2 digits after the decimal point (the mantissa). The uint16 values are transferred in the sequence LSB first, MSB last.
_Of course you can disregard the BLE definitions and transfer your temperature and humidity values with a higher precision. But you have to convert the float value into an array of bytes still._
Here is my code that I use to convert temperature and humidity into values conform with the BLE specifications for temperature and humidity:
// get float values from DHT sensor
float temperature = dht.getTemperature();
float humidity = dht.getHumidity();
// convert float value into 16 bit integer value (LSB first MSB last)
uint8_t tempData[2];
uint16_t tempValue;
// multiply by 100 to get 2 digits mantissa and convert into uint16_t
tempValue = (uint16_t)(temperature *100);
// set LSB of characteristic
tempData[0] = tempValue;
// set MSB of characteristic
tempData[1] = tempValue>>8;
// set characteristic value
pCharacteristicTemp->setValue(tempData, 2);
// convert float value into 16 bit integer value (LSB first MSB last)
// multiply by 100 to get 2 digits mantissa and convert into uint16_t
tempValue = (uint16_t)(humidity *100);
// set LSB of characteristic
tempData[0] = tempValue;
// set MSB of characteristic
tempData[1] = tempValue>>8;
// set characteristic value
pCharacteristicHumid->setValue(tempData, 2);
// notify client about new temperature value
pCharacteristicTemp->notify();
// notify client about new humidity value
pCharacteristicHumid->notify();
I use this in my ESP32 Weatherstation application
Most helpful comment
@gesaleh a BLE value is either an array of bytes or a String.
If you look at BLE characteristic Temperature
and BLE characteristic Humidty
you can see that both temperature and humidity are uint16 values. Temperature and humidity are both defined with 2 digits after the decimal point (the mantissa). The uint16 values are transferred in the sequence LSB first, MSB last.
_Of course you can disregard the BLE definitions and transfer your temperature and humidity values with a higher precision. But you have to convert the float value into an array of bytes still._
Here is my code that I use to convert temperature and humidity into values conform with the BLE specifications for temperature and humidity:
I use this in my ESP32 Weatherstation application