Я изо всех сил пытаюсь прочитать структуру двоичных данных с помощью Python3, отправляемого последовательно от Arduino Mega 2560.
Код Arduino:
char userInput;
bool ledState = false;
typedef struct
{
unsigned long logTimeStart;
unsigned long frequencyOne;
unsigned long frequencyTwo;
unsigned long frequencyThree;
unsigned long frequencyFour;
unsigned short int revPowerOne;
unsigned short int revPowerTwo;
unsigned short int revPowerThree;
unsigned short int revPowerFour;
unsigned short int tempSensor;
} SDLogger;
SDLogger dataLog;
void setup()
{
Serial.begin(9600);
bitWrite(DDRB, 7, HIGH); // Set LED DDR high on port B, pin 7
dataLog.logTimeStart = millis();
dataLog.frequencyOne = 4000000000; // PREDEFINED VALUES FOR TESTING
dataLog.frequencyTwo = 4000000000;
dataLog.frequencyThree = 4000000000;
dataLog.frequencyFour = 4000000000;
dataLog.revPowerOne = 65000; // PREDEFINED VALUES FOR TESTING
dataLog.revPowerTwo = 65000;
dataLog.revPowerThree = 65000;
dataLog.revPowerFour = 65000;
dataLog.tempSensor = 65000;
Serial.println("<Arduino is ready>");
}
void loop()
{
checkForSerialMessage();
delay(1000);
}
void checkForSerialMessage()
{
Serial.println("checking serial...");
if (Serial.available() > 0)
{
userInput = Serial.read();
if (userInput == 'a')
{
ledState = !ledState;
bitWrite(PORTB, 7, ledState);
Serial.println("led");
}
if (userInput == 'b')
{
Serial.write((byte*)&dataLog, sizeof(dataLog));
}
}
}
Я считаю, что размер структуры составляет 30 байтов. Моя цель состоит в том, чтобы Arduino периодически проверял буфер на наличие определенного c символа. Когда этот символ получен, Arduino отправляет определенную структуру данных моему интерфейсу python, который затем распаковывается и декодируется во что-то читаемое людьми. Я написал альтернативную команду, которая включает встроенный светодиод Arduino. Это было сделано, чтобы понять простое последовательное взаимодействие между программным обеспечением. Кажется, что светодиодный переключатель работает должным образом, но не команды struct.
Python Код
from tkinter import *
from struct import *
import serial
import time
ser = serial.Serial('COM5', baudrate=9600, timeout=1)
root = Tk() # root widget, this has to be first before any other widgets.
BINARY_STRFORMAT = "LLLLLHHHHH" # Format to match arduino struct
print(calcsize(BINARY_STRFORMAT)) # RESULT IS 30
def toggleLED():
ser.write(b'a')
arduinoData = ser.readline().decode('ascii') # readline functions will read until it sees a newline \n
# .decode('ascii')
print(arduinoData)
def toggleSerial():
ser.write(b'b')
arduinoData = ser.readline()
print(arduinoData)
unpacked = unpack(BINARY_STRFORMAT, arduinoData)
# in tkinter, everything is a widget:
header = Label(root, text="Read data from Arduino")
led_on = Button(root, text="led on", command=toggleLED)
read_serial = Button(root, text="enable data stream", command=toggleSerial)
# showing Label widget onto screen
header.pack()
led_on.pack()
read_serial.pack()
root.mainloop()
Когда я запускаю код python, я могу использовать свой элементарный tkinter GUI для переключения светодиода Arduino. Но когда я пытаюсь запросить структуру данных, я получаю структурную ошибку:
struct.error: unpack requires a buffer of 30 bytes
Я попытался прочитать документацию pySerial, чтобы посмотреть, смогу ли я улучшить способ получения моих последовательных данных, но не смог найти структурные ссылки. Я не понимаю, как структура отправляется / принимается и как ее следует читать в python.
Я относительно новичок в разработке программного обеспечения и последовательной связи, поэтому, пожалуйста, дайте мне знать, если мне нужно чтобы уточнить что-нибудь здесь.