This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Send a float

I want to send a float as a value of a characteristic.

As I know is this all what I have to change to send a float...

float temperature;

uint16_t len = 20;

attr_char_value.init_len  = 4;
attr_char_value.init_offs = 0;
attr_char_value.max_len   = 4;
attr_char_value.p_value   = (uint8_t*)&temperature;

hvx_params.offset = 0;
hvx_params.p_len = &len;
hvx_params.p_data = (uint8_t*)&temperature;

But it doesnt work. I wont recieve any data.

  • If I choose the way with sd_ble_gatts_value_set(). How can I send a float with 2 dots after the comma? I mean do I have to split the value in Bytes or will the sd_ble_gatts_value_set function do that for me. It doesnt have to be exatcly 2 dots after the comma. It can be also the hole float. But 2 dots after the comma are minimum.

  • You need to choose the format to send depending on the max value. Either send float and don't do any conversion in nRF51 but you may need to do the conversion on host side. Or convert your float to integer. for example 13.273 will become 1327, then you just /100 on the host to display result. You can also choose to send string "13.273" if you want. In that case nRF51 will do sprintf and host will just display the string. In any case sd_ble_gatts_value_set will set new array of bytes in characteristic, it is up to you how to represent data and number of bytes you will use in the end.

  • My first idea was to convert the float to an integer. And then do divide by 100 on the side of the host. But send the value as string is also a good solution! If the temp has the value 18.53°C. This would be 1853 as integer. So I would need 3 Bytes. But I need reserve for higher temperature so that would be 4 Bytes. Is my calculation right? How many Bytes would I have to send for 18.53 as string?

  • 1853 only requires 2 bytes, not 3. 2 bytes gives you everything from 0 - 65535. 18.53 as a string would be 5 bytes, one for each character (if you didn't send the final \0 which you don't really need).

    But all of that requires converting things on the nrf51822 chip to float, then 'printing' it to a string, all of which it can do but it's lots of library code, lots of floating point emulation and all on the low power device. Why don't you just send the raw value you read from the sensor, which is probably a 16 or 32 bit integer and do all the work on the receiving end? Your code will be smaller, will run quicker and use less power.

  • @RK Now I do like you suggest. I will send the raw value as integer. My temperature has the value 0x00000A38 = 26.16°C. But on the Master Control Panel I will recieve Value:38-00. Why is the A missing? It looks like the value is <<2. But I dont know why it should be shifted...

Related