Display float data in nRF Connect

Hi.

I transmit latitude and longitude data via bluetooth to my smartphone.

But in nRF Connect the data are displayed in HEX format (see screenshot), although in the terminal output the latitude and longitude are displayed correctly in float format (for example: 35.120275).

Please tell me how to display data correctly in nRF Connect.

Thank you. 

Parents
  • Hi,

    As far as I can see, nRF Connect for Mobile supports only HEX and ASCII (Text) as value field. If you want other data type, you need to write your own application or convert it manually on the phone.

    Best regards,
    Jørgen

  • backstreet.devisor said:
    Can you please tell me if it is possible to convert a floating point number to a string in the program and then transmit this string to the phone and display it in text format in nRF Connect?

    Yes, you can use C library function sprintf() with %f format to convert the float to a string and send the string. If you do not see the float being converted correctly, you might need to build the application with float support for printf. Note that the size of the string might exceed the size of the float once converted. 

    To change the display type in nRF Connect, long press the characteristic, press the "edit" button on the top (pencil), and select TEXT in the dialog that show up.

  • Hi.

    I tried to implement this task through the gcvt() function, but the result is not displayed correctly. 

    float x = 35.120275;
    char mybuf[8] = {0};
    
    gcvt(x, 8, mybuf);
    my_lbs_send_latitude_notify(mybuf);

    But when I try to send just a single character, it displays correctly.

    char x = 'A';
    my_lbs_send_latitude_notify(x);

    Can you please tell me where I am making a mistake?

    Thanks.

  • How is the function my_lbs_send_latitude_notify() implemented?

    The HEX data in nRF Connect looks suspiciously similar to a RAM address (0x20008308). Are you sure you are sending the data and not the address of the buffer?

  • Function my_lbs_send_latitude_notify():

    int my_lbs_send_latitude_notify(uint32_t latitude_value)
    {
    	if (!notify_latitude_enabled) {
    		return -EACCES;
    	}
    
    	return bt_gatt_notify(NULL, &my_lbs_svc.attrs[10], &latitude_value, sizeof(latitude_value));
    }

    Debug:

    In the code I wrote both options:
    1. my_lbs_send_latitude_notify(mybuf);
    2. my_lbs_send_latitude_notify(&mybuf);

    In text format both variants were printed incorrectly

  • This code must certainly generate warnings in your build, does it not?

    You are trying to pass a char array to a uint32_t parameter. "mybuf" will contain a pointer to the RAM location where the data is stored. In my_lbs_send_latitude_notify(), you have one input variable, which is not a pointer. The value assigned to this parameter will be stored in a new local variable inside the function, not a reference to the external data. When you pass the mybuf variable to this funtion, it will copy the RAM address where the buffer i stored into latitude_value, not the data stored in mybuf. When you try to pass the reference to latitude_value (&latitude_value) to bt_gatt_notify, this will be the address of the local variable. The sizeof function will also just report the size of an uint32_t, not the size of the buffer, since it is not aware that a buffer was passed to the variable.

    If you print the values, it should look something like this:

    mybuf=0x20005244
    &mybuf=0x20005244
    sizeof(mybuf)=8
    
    latitude_value=0x20005244
    &latitude_value=0x2000522c
    sizeof(latitude_value)=4

    You should modify the my_lbs_send_latitude_notify() function to take a pointer and buffer length as input, and pass this further to the bt_gatt_notify() function:

    int my_lbs_send_latitude_notify(uint32_t *latitude_value_string, uint32_t latitude_string_length)
    {
    	if (!notify_latitude_enabled) {
    		return -EACCES;
    	}
    
    	return bt_gatt_notify(NULL, &my_lbs_svc.attrs[10], latitude_value_string, latitude_string_length);
    }
    
    void send_data(void)
    {
        float x = 35.120275;
        char mybuf[8] = {0};
        
        gcvt(x, 8, mybuf);
        my_lbs_send_latitude_notify(mybuf, sizeof(mybuf));
    }

    Best regards,
    Jørgen

Reply
  • This code must certainly generate warnings in your build, does it not?

    You are trying to pass a char array to a uint32_t parameter. "mybuf" will contain a pointer to the RAM location where the data is stored. In my_lbs_send_latitude_notify(), you have one input variable, which is not a pointer. The value assigned to this parameter will be stored in a new local variable inside the function, not a reference to the external data. When you pass the mybuf variable to this funtion, it will copy the RAM address where the buffer i stored into latitude_value, not the data stored in mybuf. When you try to pass the reference to latitude_value (&latitude_value) to bt_gatt_notify, this will be the address of the local variable. The sizeof function will also just report the size of an uint32_t, not the size of the buffer, since it is not aware that a buffer was passed to the variable.

    If you print the values, it should look something like this:

    mybuf=0x20005244
    &mybuf=0x20005244
    sizeof(mybuf)=8
    
    latitude_value=0x20005244
    &latitude_value=0x2000522c
    sizeof(latitude_value)=4

    You should modify the my_lbs_send_latitude_notify() function to take a pointer and buffer length as input, and pass this further to the bt_gatt_notify() function:

    int my_lbs_send_latitude_notify(uint32_t *latitude_value_string, uint32_t latitude_string_length)
    {
    	if (!notify_latitude_enabled) {
    		return -EACCES;
    	}
    
    	return bt_gatt_notify(NULL, &my_lbs_svc.attrs[10], latitude_value_string, latitude_string_length);
    }
    
    void send_data(void)
    {
        float x = 35.120275;
        char mybuf[8] = {0};
        
        gcvt(x, 8, mybuf);
        my_lbs_send_latitude_notify(mybuf, sizeof(mybuf));
    }

    Best regards,
    Jørgen

Children
Related