Seperating serial data

I want to control two servos with an Arduino and some Python code on my computer. The Python program sends the angles (int between 0-180) for the Servos to the Arduino, encoded as bytes, with PySerial. The Arduino Code for just one Servo:

#include <Servo.h>

Servo servo1;

void setup() {
 Serial.begin(9600);
 servo.attach(9);
}

void loop() {
 while (Serial.available() > 0)
 {
   static unsigned int message_pos = 0;

   char inByte = Serial.read();

   if ( inByte != '\n' )
   {
     message[message_pos] = inByte;
     message_pos++;
   }
   else
   {
     message[message_pos] = '\0';

     int number = atoi(message);
     servo.write1(number); 

And the python code for one servo (not the actual one, just very simplified):

port = serial.Serial('COM9', 9600)
val =  str(val) + '\n'
port.write(val)

Now, I want to control two servos at the same time, so I'd have to seperate the incoming serial data so that the arduino knows which servo to move to which position. I think using another termiantion charakter might work, right? But how do I do that?

See the serial input basics tutorial. Your answer lies therein.

1 Like

There are several possibilities to solve your task.

  • Send always both values separated by a delimiter like a comma, colon or similar (first value servo1, second servo2) -> e.g. "99,50" or "180,10"

Just separate the data at the delimiter.

  • Send servo position separatly, each position marked by a header like "S1:" and "S2:" -> e.g. "S2:099" and "S1:000".

First you separate the header (example: "S1" and "S2") and the value ( example 99 and 0) then allocate the value in accordance with the header to servo1 or servo2.

For separating you can collect the incoming serial characters into a C string and use the C-string functions or use the String class and its methods.

1 Like

Read the Evils of Arduino Strings before using the String class.

1 Like

consider using Serial.readBytesUntil() and strtok()

1 Like

You could also consider using an RPC library (shameless plug).

In that case, your can add the following line to your loop() function

  interface(Serial,
    pack(&servo1, &Servo::write), "servo1: Write to servo 1. @val: Value.",
    pack(&servo2, &Servo::write), "servo2: Write to servo 2. @val: Value.");

and from Python, you can call these functions as follows.

interface.servo1(20)
1 Like

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.