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

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

過去の関連記事: 
[openFrameworks, serial通信, arduino, 1 byte, 2 bytes, multi-data](https://qiita.com/keitasumiya/items/44908da606c8da1a635c)

# 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)

```

```c: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)
```

```c: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)
```

```c: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)
```

```c: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)

```

```c
: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)

```

```c: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でシリアル通信](https://qiita.com/kosystem/items/0023cfee941fdf099087)
[Python 3 で16進数とバイト列の相互変換](https://qiita.com/masakielastic/items/21ba9f68ef6c4fd7692d)
[pySerial Short introduction](https://pythonhosted.org/pyserial/shortintro.html)
[python3ならintとbytesの変換が楽勝になる](https://blanktar.jp/blog/2014/10/python3-convert-int-bytes.html)
[python 組み込み型 int.to_bytes](https://docs.python.jp/3.3/library/stdtypes.html#int.to_bytes)
[C言語の演算子について](http://www.c-lang.org/operator.html)
[python ビット演算子](https://www.pythonweb.jp/tutorial/num/index4.html)
[How to check if all elements of a list matches a condition?](https://stackoverflow.com/questions/10666163/how-to-check-if-all-elements-of-a-list-matches-a-condition)
[python Built-in Functions all](https://docs.python.org/2/library/functions.html#all)