Sending serial data

Hi,

I'm sending values over ble. On the client side I opened an serial monitor. Everything seems fine. The values are received in the right way.

But when I try to read the serial port in python it says:

There is an random character, what isn't visible in the serial monitor(putty).

    sprintf(data_array, "%.2f", val0);
    uint16_t d_len = strlen(data_array);

    err_code = ble_nus_data_send(&m_nus, data_array, &d_len, m_conn_handle); 
    APP_ERROR_CHECK(err_code);

This is the way I'm sending my values. Am I missing something that I didn't see? Can someone help me out? 

Maybe it isn't a question to ask here, but maybe someone know the answer.

Kind regards,

JP 

Parents
  • I did watched the data on python.

    In the 2th, 3th etc it add an \x sequence. Is this something on the client side of my software?

    This is my python code:

    import serial
    import matplotlib.pyplot as plt
    
    plt.ion()
    fig=plt.figure()
    
    
    i=0
    x=list()
    y=list()
    i=0
    ser = serial.Serial('COM7',115200)
    ser.close()
    ser.open()
    while True:
    
        data = ser.readline()
        print(data.decode("utf-8"))
        #x.append(i)
        #y.append(data.decode())
    
        #plt.scatter(i, float(data.decode()))
        #i += 1
        #plt.show()
        #plt.pause(0.0001)  # Note this correction

  • Hi,

    I don't think you should need to convert the float value to a string. I mean, you could, but it will just add more overhead to your transfer if you are going to convert it back again anyway. Instead you can remove the sprintf() function and pass the value directly to your BLE send function.

    The python code may look something like this (not tested):

    value, = struct.unpack('<f', bytearray(<4 byte array received on UART>))
    
    printf(value)

    Best regards,

    Vidar

  • Hi Vidar,

    I tried that before, but I can’t pass a float value to ble_nus. It asks for an uint8. Therefore I used a string.

    Also tried to send an data_array over ble_nus, because I have 4 SAADC values. But it wouldn’t work for me. 

    Do you know how to send an array with my float values over ble?

    Kind regards,

    JP

Reply Children
  • Hi,

    You can use memcpy() to copy one or several float samples to your uint8_t array.

            memcpy(&array[offset],
                   &float_sample, sizeof(float_sample));

  • Hi Vidar,

    I processed your feedback. I don't know if I did it the right way. See my code:

    static void app_timer_handler(void * p_context)
    {
      if(m_conn_handle != BLE_CONN_HANDLE_INVALID)
      {
        uint8_t data_array[80];
    
        float val0;
        float val1;
        float val2;
        float val3;
    
        ret_code_t err_code;
    
        err_code = nrfx_saadc_sample_convert(0, &m_sample);
        APP_ERROR_CHECK(err_code);
    
        val0 = m_sample * 3.3 / 4096;
        memcpy(&data_array[0], &val0, sizeof(val0));
    
        err_code = nrfx_saadc_sample_convert(1, &m_sample);
        APP_ERROR_CHECK(err_code);
    
        val1 = m_sample * 3.3 / 4096;
        memcpy(&data_array[20], &val1, sizeof(val1));
    
        err_code = nrfx_saadc_sample_convert(2, &m_sample);
        APP_ERROR_CHECK(err_code);
    
        val2 = m_sample * 3.3 / 4096;
        memcpy(&data_array[40], &val2, sizeof(val2));
    
        err_code = nrfx_saadc_sample_convert(3, &m_sample);
        APP_ERROR_CHECK(err_code);
    
        val3 = m_sample * 3.3 / 4096;
        memcpy(&data_array[60], &val3, sizeof(val3));
      
        uint16_t d_len = sizeof(data_array)-1;
    
        err_code = ble_nus_data_send(&m_nus, data_array, &d_len, m_conn_handle); 
        APP_ERROR_CHECK(err_code);
      }
    }

    I was using an data_array[80] of 80, because I was using before an string in the array. Can I make it smaller and will it work right in this way?

    This is what I'm receiving now:

    b'\xcdL\x07=\xfc\x00\x00 \x00\x00\x00\x00\x98#\x00 \x01\x00\x00\x00\x00\x00\x04= \x01\x00 \x00\x10\x00@\x00\x00\x00\x00\x01\x00\x00\x00\x9a\x91\xaa?D\x85\x00@\x0c\x0c\x00 \x11\xc6\x01\x00$\x0c\x00 f\xe6.@\x00\x00\x00\x00\xe8\x1d\x00 \x00\x00\x00\x00\xdc\x00\x00\r\n'

    I tried this in python. 

    import serial
    import matplotlib.pyplot as plt
    import struct
    
    ser = serial.Serial('COM7',115200)
    ser.close()
    ser.open()
    while True:
    
        data = ser.readline(4)
        val = struct.unpack('<f', data)
        print(val)

    After this is what I get once then it stops.

        val = struct.unpack('<f', data)
    struct.error: unpack requires a buffer of 4 bytes
    (0.02980956993997097,)
    (1.0842347427221237e-19,)
    (0.0,)
    (1.0853798708826268e-19,)
    (1.401298464324817e-45,)
    (0.04672851413488388,)
    (1.0842393956130693e-19,)
    (2.0009765625,)
    (0.0,)
    (1.401298464324817e-45,)
    (1.372045874595642,)
    (2.008133888244629,)
    (1.0846007701431784e-19,)
    (1.6288833479158106e-40,)
    (1.0846038720704755e-19,)
    (2.7328124046325684,)
    (0.0,)
    (1.085191687293271e-19,)
    (0.0,)
    (3.944407969607931e-31,)
    
    Process finished with exit code 1

    I dont have much experience with python, therefore I don't know if I send wrong or reading it wrong.

    Kind regards,

    JP

Related