pyserial communication with arduino (for motor-control)

删除回忆录丶 提交于 2019-12-12 02:42:14

问题


I would like to send data from python do arduino in order to control motors via relays. Idea is to send a number, in order to identify a motor and a value, to finally move it. Unfortunately im struggling with some problems. Data is getting lost.

So, in this minimal example there is an identifier "n", to indicate that the received data is the variable "number" and an identifier "c" to identify that the received data is a counter. To find out what's wrong, I send the data back to Python and try to read it. This is setup is only working for the first to characters. All other data is getting lost.

Can someone give me a hint? Are those identifiers necessary? Do I have to put some delay(), or maybe another baut-rate?

I guess it's something about the second identifier. The setup is working fine, if I only work with the "counter" for example.

Thank you very much in advance!

Pyhton:

import serial
import time

Port = "/dev/cu.usbserial-A601FZBL"
ser = serial.Serial(Port,9600,timeout=1)

time.sleep(1)

counter = 0

def Test(counter):
    ser.write(b"n")
    ser.write(str(1).encode())
    print("number:", 1)

    get = ser.readline().decode()
    print("get:", get)    


    ser.write(b"c")
    ser.write(str(counter).encode())
    print("counter:", counter)

    get = ser.readline().decode()
    print("get:", get)
    print()


while True:
    Test(counter)
    counter += 1

Arduino:

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

int number;
int counter;

void loop() {
  if (Serial.available() > 0) {
    if (Serial.peek() == 'n') {
      Serial.read();
      number = Serial.parseInt();
      Serial.println(number);

      if (Serial.peek() == 'c') {
        Serial.read();
        counter = Serial.parseInt();
        Serial.println(counter);
      }

      while (Serial.available() > 0) {
        Serial.read();
      }
    }
  }
}

Sorry! Here is my sample-run: (I'm confused, why there are additional blank-lines, beside the print() in the output)

number: 1
get: 1


counter: 0
get: 

number: 1
get: 
counter: 1
get: 

number: 1
get: 
counter: 2
get: 

number: 1
get: 
counter: 3
get: 

number: 1
get: 
counter: 4
get: 

number: 1
get: 
counter: 5

回答1:


Thanks for the support. So, finally no data did get lost ;) The problem was: Arduino is creating a blank-line, when sending data back. so "ser.readline()[:-2].decode()" solved this issue. I run into another problem, when sending integers bigger than 9. In order to do so, one has to split the integer into separated chars and encode them. Here is my workaround:

Python:

import serial
import time

Port = "/dev/cu.usbserial-A601FZBL"
ser = serial.Serial(Port,9600,timeout=1)

time.sleep(1)

counter = 0

def Test(counter):
    data = [b"n", b"0", b"c"]
    value = list(str(counter))

    for char in value:
        data.append(char.encode())

    ser.write(data)
    print("write:", "0", counter)

    get_1 = ser.readline()[:-2].decode()
    get_2 = ser.readline()[:-2].decode()
    print("get:  ", get_1, get_2)
    print()

while True:
    Test(counter)
    counter += 1

Arduino:

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

int number;
int counter;

void loop() {
  while (Serial.available() > 0) {
    if (Serial.peek() == 'n') {
      Serial.read();
      number = Serial.parseInt();
      Serial.println(number);

      if (Serial.peek() == 'c') {
        Serial.read();
        counter = Serial.parseInt();
        Serial.println(counter);
      }

      while (Serial.available() > 0) {
        Serial.read();
      }
    }
  }
}

And the final output:

write: 0 0
get:   0 0

write: 0 1
get:   0 1

write: 0 2
get:   0 2

write: 0 3
get:   0 3

write: 0 4
get:   0 4

write: 0 5
get:   0 5

write: 0 6
get:   0 6

write: 0 7
get:   0 7

write: 0 8
get:   0 8

write: 0 9
get:   0 9

write: 0 10
get:   0 10

write: 0 11
get:   0 11


来源:https://stackoverflow.com/questions/40391672/pyserial-communication-with-arduino-for-motor-control

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!