LoginSignup
7
9

More than 5 years have passed since last update.

python--serial通信--arduino, 1byte, 2bytes, 複数データ

Last updated at Posted at 2018-06-29

pythonとarduinoとのserial通信まとめ
1byte, 2bytes, 複数データ *2
で6パターンあります.

過去の関連記事:
openFrameworks, serial通信, arduino, 1 byte, 2 bytes, multi-data

codes

1byte

python > arduino

write_1byte.py
import time
import serial
ser = serial.Serial('/dev/cu.usbmodem1421', 9600, timeout=0.1)
while True:
    val = 3
    valByte = val.to_bytes(1, 'big')
    # valByte = val.to_bytes(2, 'little')
    ser.write(valByte)
    print(val)
    time.sleep(1)

serial_read_1byte.ino
int readByte = 0;

void setup(){
  Serial.begin(9600);
}

void loop(){
  if (Serial.available() > 0) {
    readByte = Serial.read();
    Serial.println(readByte, DEC);
    //Serial.println(readByte);
  }
}

arduino > python

read_1byte.py
import serial
ser = serial.Serial('/dev/cu.usbmodem1421', 9600, timeout=0.1)
while True:
    c = ser.read()  # 1文字読み込み
    # val = int(c.hex(), 16)
    val = int.from_bytes(c, 'big')
    print(val)
serial_write_1byte.ino
void setup(){
  Serial.begin(9600);
}

void loop(){
  Serial.write(234);
}

2bytes

python > arduino

write_2bytes.py
import time
import serial
ser = serial.Serial('/dev/cu.usbmodem1421', 9600, timeout=0.1)
val = 500
while True:
    head = 128
    high = (val >> 7) & 127
    low  = val & 127
    headByte = head.to_bytes(1, 'big')
    highByte = high.to_bytes(1, 'big')
    lowByte = low.to_bytes(1, 'big')
    ser.write(headByte)
    ser.write(highByte)
    ser.write(lowByte)
    #print(val)
    time.sleep(1)
serial_read_2bytes.ino
int value = 0;
bool isValid = false;

void setup(){
  Serial.begin(9600);
}

void loop(){
  isValid = false;
  if (Serial.available() >= 3) {
    int head = Serial.read();
    if (head == 128) {
      int high = Serial.read();
      int low  = Serial.read();
      value = (high<<7) + low;
      Serial.println(value, DEC);
      if (0 <= value <= 1023) {
        isValid = true;
      }
    }
  }
}

arduino > python

read_2bytes.py
import serial
ser = serial.Serial('/dev/cu.usbmodem1421', 9600, timeout=0.1)
while True:
    isValid = False;
    headByte = ser.read()  # 1文字読み込み
    head = int.from_bytes(headByte, 'big')
    if head == 128:
        highByte = ser.read()  # 1文字読み込み
        lowByte = ser.read()  # 1文字読み込み
        high = int.from_bytes(highByte, 'big')
        low = int.from_bytes(lowByte, 'big')
        val = (high<<7) + low;
        if 0 <= val and val <= 1023 :
            #print("value is %d \n", val);
            isValid = True;

    if isValid:
        print(val)
serial_write_2bytes.ino
int value = 963;

void setup(){
  Serial.begin(9600);
}

void loop(){
  int low = value & 127;
  int high = (value >> 7) & 127;
  int head = 128;
  Serial.write(head);
  Serial.write(high);
  Serial.write(low);
}

複数データ 2bytes

python > arduino

write_multi-2bytes.py
import time
import serial

val_size = 3
values = [123, 456, 789]
ser = serial.Serial('/dev/cu.usbmodem1421', 9600, timeout=0.1)

while True:
    isValids = [False for x in range(val_size)]

    for i in range(val_size):
        head = 128+i
        high = (values[i] >> 7) & 127
        low  = values[i] & 127
        headByte = head.to_bytes(1, 'big')
        highByte = high.to_bytes(1, 'big')
        lowByte = low.to_bytes(1, 'big')
        ser.write(headByte)
        ser.write(highByte)
        ser.write(lowByte)

    print(values)

    time.sleep(3)

:serial_read_multi-2bytes.ino
const int val_size = 3;
int values[val_size] = {0, 0, 0};
bool isValids[val_size] = {false, false, false};

void setup(){
  Serial.begin(9600);
}

void loop(){
  if (Serial.available() >= 3*val_size+1) {
    int head = Serial.read();
    if (head == 128){
      bool isValids[val_size] = {false, false, false};
    }
    for (int i=0; i<val_size; i++){
      if (head == 128+i) {
        int high = Serial.read();
        int low  = Serial.read();
        values[i] = (high<<7) + low;
        Serial.print("[");
        Serial.print(i, DEC);
        Serial.print("]");
        if (0 <= values[i] <= 1023) {
          Serial.print("[");
          Serial.print(values[i], DEC);
          if (head == 128+val_size-1) {
            Serial.println("]");
          }else{
            Serial.print("] ");
          }
          isValids[i] = true;
        }
      }
    }
  }
}

arduino > python

read_multi-2bytes.py
import serial

val_size = 3;
values = [0 for x in range(val_size)]
isValids = [False for x in range(val_size)]
ser = serial.Serial('/dev/cu.usbmodem1421', 9600, timeout=0.1)

while True:
    headByte = ser.read()  # 1文字読み込み
    head = int.from_bytes(headByte, 'big')
    if head == 128:
        isValids = [False for x in range(val_size)]

    for i in range(val_size):
        if head == 128+i:
            highByte = ser.read()  # 1文字読み込み
            lowByte = ser.read()  # 1文字読み込み
            high = int.from_bytes(highByte, 'big')
            low = int.from_bytes(lowByte, 'big')
            values[i] = (high<<7) + low;
            if 0 <= values[i] and values[i] <= 1023 :
                isValids[i] = True;
                #print(values[i])

    if all(i == True for i in isValids):
        print(values)

serial_write_multi-2bytes.ino
const int val_size = 3;
int values[val_size] = {123, 456, 789};

void setup(){
  Serial.begin(9600);
}

void loop(){
  for (int i=0; i<val_size; i++){
    int high = (values[i] >> 7) & 127;
    int low  = values[i] & 127;
    Serial.write(128+i);
    Serial.write(high);
    Serial.write(low);
  }
}

ref

Pythonでシリアル通信
Python 3 で16進数とバイト列の相互変換
pySerial Short introduction
python3ならintとbytesの変換が楽勝になる
python 組み込み型 int.to_bytes
C言語の演算子について
python ビット演算子
How to check if all elements of a list matches a condition?
python Built-in Functions all

7
9
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
9