Чтение шестнадцатеричного формата данных из порта

VISA, TCP/IP, USB, CAN, GPIB и подобные протоколы
Ответить
Владимир855
beginner
beginner
Сообщения: 11
Зарегистрирован: 16 сен 2017, 11:27
Версия LabVIEW: 2016
Откуда: Сочи
Контактная информация:

Чтение шестнадцатеричного формата данных из порта

Сообщение Владимир855 »

Подскажите как прочитать данные отправляемые с ардуинки в serial.
Я вижу что в буфере есть данные, но мне их надо декодировать. Это 6 чисел передаваемых в шестнадцатеричном формате.
Я не силён в программирование, и уже бьюсь над этим вопросом несколько дней.
А в общем схема представляет из себя ардуинку и гироскоп MPU6050. Задумка в том чтоб анализировать данные с гироскопа в Labview.
Вложения
1.jpg
1.jpg (34.43 КБ) 1784 просмотра
2.jpg
Rserial2.vi
(12.15 КБ) 58 скачиваний
Artem.spb

Activity Автор
professor
professor
Сообщения: 3394
Зарегистрирован: 31 июл 2011, 23:05
Награды: 2
Версия LabVIEW: 12-18
Благодарил (а): 49 раз
Поблагодарили: 172 раза
Контактная информация:

Re: Чтение шестнадцатеричного формата данных из порта

Сообщение Artem.spb »

Владимир855 писал(а): 04 фев 2022, 00:13 Это 6 чисел передаваемых в шестнадцатеричном формате.
Я насчитал 33 байта, на 6 не делится, так что "это" не 6 чисел.
Какой длины числа? Что значит "в шестнадцатеричном формате"? Строка отображается в обычном формате?
Если да, то
если числа однобайтные, то FE=254
если числа двухбайтные, то FEED = 65261 (или 60926, зависит от порядка байт).
hex.PNG
Владимир855
beginner
beginner
Сообщения: 11
Зарегистрирован: 16 сен 2017, 11:27
Версия LabVIEW: 2016
Откуда: Сочи
Контактная информация:

Re: Чтение шестнадцатеричного формата данных из порта

Сообщение Владимир855 »

Artem.spb писал(а): 04 фев 2022, 01:29
Владимир855 писал(а): 04 фев 2022, 00:13 Это 6 чисел передаваемых в шестнадцатеричном формате.
Я насчитал 33 байта, на 6 не делится, так что "это" не 6 чисел.
Какой длины числа? Что значит "в шестнадцатеричном формате"? Строка отображается в обычном формате?
Если да, то
если числа однобайтные, то FE=254
если числа двухбайтные, то FEED = 65261 (или 60926, зависит от порядка байт).
hex.PNG
Доброго времен суток Артём. Код в ардуино который записывает данные в порт выглядит следующим образом.

Код: Выделить всё

#ifdef OUTPUT_BINARY_ACCELGYRO
        Serial.write((uint8_t)(ax >> 8)); Serial.write((uint8_t)(ax & 0xFF));
        Serial.write((uint8_t)(ay >> 8)); Serial.write((uint8_t)(ay & 0xFF));
        Serial.write((uint8_t)(az >> 8)); Serial.write((uint8_t)(az & 0xFF));
        Serial.write((uint8_t)(gx >> 8)); Serial.write((uint8_t)(gx & 0xFF));
        Serial.write((uint8_t)(gy >> 8)); Serial.write((uint8_t)(gy & 0xFF));
        Serial.write((uint8_t)(gz >> 8)); Serial.write((uint8_t)(gz & 0xFF));
    #endif

Если отправлять обычным форматом данные то в порту будут значения как показаны в прикреплённом скриншоте.
Я попробовал Ваш пример. Он не работает в моём случае. Точнее он работает как отдельный элемент но данные приходящие, он отказывается читать.
На всякий случай выложу весь код залитый в ардуино.

Код: Выделить всё

#include "I2Cdev.h"
#include "MPU6050.h"
#if I2CDEV_IMPLEMENTATION == I2CDEV_ARDUINO_WIRE
#include "Wire.h"
#endif

// class default I2C address is 0x68
// specific I2C addresses may be passed as a parameter here
// AD0 low = 0x68 (default for InvenSense evaluation board)
// AD0 high = 0x69
MPU6050 accelgyro;
//MPU6050 accelgyro(0x69); // <-- use for AD0 high

int16_t ax, ay, az;
int16_t gx, gy, gz;

// uncomment "OUTPUT_READABLE_ACCELGYRO" if you want to see a tab-separated
// list of the accel X/Y/Z and then gyro X/Y/Z values in decimal. Easy to read,
// not so easy to parse, and slow(er) over UART.
#define OUTPUT_READABLE_ACCELGYRO

// uncomment "OUTPUT_BINARY_ACCELGYRO" to send all 6 axes of data as 16-bit
// binary, one right after the other. This is very fast (as fast as possible
// without compression or data loss), and easy to parse, but impossible to read
// for a human.
#define OUTPUT_BINARY_ACCELGYRO

#define LED_PIN 13
bool blinkState = false;

void setup() {
    // join I2C bus (I2Cdev library doesn't do this automatically)
    #if I2CDEV_IMPLEMENTATION == I2CDEV_ARDUINO_WIRE
        Wire.begin();
    #elif I2CDEV_IMPLEMENTATION == I2CDEV_BUILTIN_FASTWIRE
        Fastwire::setup(400, true);
    #endif

    // initialize serial communication
    // (38400 chosen because it works as well at 8MHz as it does at 16MHz, but
    // it's really up to you depending on your project)
     Serial.begin(300);
     accelgyro.initialize();
     pinMode(LED_PIN, OUTPUT);
}

void loop() {
    // read raw accel/gyro measurements from device
    accelgyro.getMotion6(&ax, &ay, &az, &gx, &gy, &gz);
    // these methods (and a few others) are also available
    //accelgyro.getAcceleration(&ax, &ay, &az);
    accelgyro.getRotation(&gx, &gy, &gz);
   /*   
    *    
    #ifdef OUTPUT_READABLE_ACCELGYRO
// display tab-separated accel/gyro x/y/z values
  //   Serial.print("a/g:\t");
       Serial.print(ax); Serial.print("\t");
       Serial.print(ay); Serial.print("\t");
       Serial.print(az); Serial.print("\t");
       Serial.print(gx); Serial.print("\t");
       Serial.print(gy); Serial.print("\t");
       Serial.println(gz);
    #endif
 */
    
    #ifdef OUTPUT_BINARY_ACCELGYRO
        Serial.write((uint8_t)(ax >> 8)); Serial.write((uint8_t)(ax & 0xFF));
        Serial.write((uint8_t)(ay >> 8)); Serial.write((uint8_t)(ay & 0xFF));
        Serial.write((uint8_t)(az >> 8)); Serial.write((uint8_t)(az & 0xFF));
        Serial.write((uint8_t)(gx >> 8)); Serial.write((uint8_t)(gx & 0xFF));
        Serial.write((uint8_t)(gy >> 8)); Serial.write((uint8_t)(gy & 0xFF));
        Serial.write((uint8_t)(gz >> 8)); Serial.write((uint8_t)(gz & 0xFF));
    #endif

    // blink LED to indicate activity
    blinkState = !blinkState;
    digitalWrite(LED_PIN, blinkState);
}
Вложения
1.jpg
Владимир855
beginner
beginner
Сообщения: 11
Зарегистрирован: 16 сен 2017, 11:27
Версия LabVIEW: 2016
Откуда: Сочи
Контактная информация:

Re: Чтение шестнадцатеричного формата данных из порта

Сообщение Владимир855 »

Методом проб и ошибок что то стало получатся. теперь я не могу понять, куда делись знаки перед числами. Но и числа не соответствуют действительности, хотя уже получилось создать массив.
Вложения
1.jpg
Artem.spb

Activity Автор
professor
professor
Сообщения: 3394
Зарегистрирован: 31 июл 2011, 23:05
Награды: 2
Версия LabVIEW: 12-18
Благодарил (а): 49 раз
Поблагодарили: 172 раза
Контактная информация:

Re: Чтение шестнадцатеричного формата данных из порта

Сообщение Artem.spb »

Владимир855 писал(а): 04 фев 2022, 08:00 Если отправлять обычным форматом данные то в порту будут значения как показаны в прикреплённом скриншоте.
А чем вас это не устраивает?

Во-первых, судя по всему у вас двухбайтные числа, тогда почему вы читаете по 16 байт? 6*2 = 12. Ну разделитель, будет 13-14. Откуда ещё два байта?
Дальше, есть ли разделитель при "необычном" формате? Как программа должна понять, что "это" начало посылки. Судя по картинке в "обычном" формате разделителем служит перевод каретки.
Разбор посылки в этом случае может выглядеть так.
str.png
Знак у вас "пропал" потому что вы конвертируете строку в беззнаковые числа. Поставьте I16 (не u16) и будет нормально, но нужно найти границу между посылками
Владимир855
beginner
beginner
Сообщения: 11
Зарегистрирован: 16 сен 2017, 11:27
Версия LabVIEW: 2016
Откуда: Сочи
Контактная информация:

Re: Чтение шестнадцатеричного формата данных из порта

Сообщение Владимир855 »

Artem.spb писал(а): 04 фев 2022, 16:15
Владимир855 писал(а): 04 фев 2022, 08:00 Если отправлять обычным форматом данные то в порту будут значения как показаны в прикреплённом скриншоте.
Во-первых, судя по всему у вас двухбайтные числа, тогда почему вы читаете по 16 байт? 6*2 = 12. Ну разделитель, будет 13-14. Откуда ещё два байта?
Дальше, есть ли разделитель при "необычном" формате? Как программа должна понять, что "это" начало посылки. Судя по картинке в "обычном" формате разделителем служит перевод каретки.
Разбор посылки в этом случае может выглядеть так.
str.png
Знак у вас "пропал" потому что вы конвертируете строку в беззнаковые числа. Поставьте I16 (не u16) и будет нормально, но нужно найти границу между посылками
Огромное спасибо Вам за помощь. Получилось принять данные и теперь есть возможность их обработать.
Есть только один вопрос. При резких изменениях значения появляются нули в переменных и массиве. Как только значения стабилизировались, нули пропадают. Я заметил что если перед Scan From String Function добавить такую же функцию значения получаются без нулей. Без разницы как я настраиваю функцию Scan From String Function в DBL или I32.
А чем вас это не устраивает?
А что касаемо почему меня не устраивало вывод данных в читаемом формате, наверное меня смутило то, что в коде ардуино, автор написал комментарий который говорит что для более точных данных и высокой скорости обработки, лучше использовать HEX.
binary, one right after the other. This is very fast (as fast as possible without compression or data loss), and easy to parse, but impossible to read for a human.
Поэтому я и решил пробовать именно принимать данные в формате HEX.
И кстати, при установки константы byte count в функции VISA Read Function равной 32, получилось принять данные в правильном виде, точнее их записать в правильном порядке.
Вложения
1.jpg
2.jpg
Rserial2.vi
(23.2 КБ) 57 скачиваний
Ответить
  • Похожие темы
    Ответы
    Просмотры
    Последнее сообщение

Вернуться в «Коммуникация с приборами»