Arduino + Python + 2 servos

Good morning,

My experience is minimal. Wired up Arduino Uno R3 with two servos this morning. Two servos, both on their own independent 6v power supplies then grounded into the board. One servo signal pin 9 the other pin 10. Installed Python shortly after and been at it since. (i cant take any credit for any of this code as i have copy and pasted from several forums to get this far)

Scenario:- Inwin 915 PC Case with Servos connected to the front and rear hinged panels. I ultimately wish for the panels to independently open up when the desired trigger happens (HWiNFO triggers script to run when CPU usage reaches x. e.g CPU at 60% front panel open (servo goes to angle 0). CPU usage goes to 100%, back panel opens up (rear servo goes to angle 0). CPU now drops back to 60% (rear servo goes to angle 150). CPU drops to 30%, front panel closes (front servo goes to angle 150).

Operation in the Arduino serial monitor is fine, but cant leave that open.
Have 4 python scripts for the trigger calls. left 50, left 150, right 50, right 150(just used 50 and 150 for diagnostic purposes).

When executing the python script, say left50 then left150, the servo moves to the desired angle AFTER going to 90degrees first.

I believe this happens as the Arduino board needs to reset.

Any suggestions/help would be appreciated.

Arduino Code:-

#include <Servo.h>
char buffer[11];
Servo servo1; // Create a servo object
Servo servo2; // Create a second servo object

void setup()
{
servo1.attach(9); // Attaches the servo on pin 5 to the servo1 object
servo2.attach(10); // Attaches the servo on pin 6 to the servo2 object
Serial.begin(115200);
while(Serial.available())
Serial.read();
// servo1.write(0); // Put servo1 at home position
// servo2.write(0); // Put servo2 at home postion
}
void loop()
{
if (Serial.available() > 0) { // Check if data has been entered
int index=0;
delay(100); // Let the buffer fill up
int numChar = Serial.available(); // Find the string length
if (numChar>10) {
numChar=10;
}
while (numChar--) {
// Fill the buffer with the string
buffer[index++] = Serial.read();
}
buffer[index]='\0';
splitString(buffer); // Run splitString function
}
}
void splitString(char* data) {
char* parameter;
parameter = strtok (data, " ,"); //String to token
while (parameter != NULL) { // If we haven't reached the end of the string...
setServo(parameter); // ...run the setServo function
parameter = strtok (NULL, " ,");
}
while(Serial.available())
Serial.read();
}
void setServo(char* data) {
if ((data[0] == 'L') || (data[0] == 'l')) {
int firstVal = strtol(data+1, NULL, 10); // String to long integer
firstVal = constrain(firstVal,0,150); // Constrain values
servo1.write(firstVal);
}
if ((data[0] == 'R') || (data[0] == 'r')) {
int secondVal = strtol(data+1, NULL, 10); // String to long integer
secondVal = constrain(secondVal,0,150); // Constrain the values
servo2.write(secondVal);
}
}

Python Code:-

import serial
import time
ser = serial.Serial('COM6', 115200)
time.sleep(3)
ser.write(b'L50')
time.sleep(3)
ser.close()

The comment is incorrect.
numChar will almost always just be one.

Edit: Sorry, I missed the delay. Nasty.

Research tells me...

Disable auto-reset on serial connection. This will eliminate the servo default position upon python script execution.

possibly store servo position in the eprom incase arduino loses power.

Can confirm breaking the trace between the two solder points for 'RESET-EN' works.

To upload Sketch:-
Press the reset after the binary sketch size is displayed (you have a couple of seconds to do this).

Servo no longer stops at its default angle upon executing the python scrips. Also adjusted the python script, 'time.sleep(3)' to 'time.sleep(0.1)', and the servos are more responsive.

Servos still default to 90ยบ when power is cut to the board as normal. I will be trying the EEPRON method to try work around this.

Small clip on all this working.

Final scripts below. Haven't played with EEPROM yet.

Arduino sketch. 2 servos attached. Moving slow. Controlled independently.

#include <Servo.h>
char buffer[11];
Servo servo1; // Create a servo object
Servo servo2; // Create a second servo object

// speed function

int s = 30; //pre-programmed speed.  higher is slower
int angle=0; // we will use this one later 

// All this function has to be declared before your main "void loop()"
void slow (int i) // speed function for servo1
        {
 
         if (i < 1){ i = 1;}// 1 is the lower limit for the servo 
        if (i > 179){ i = 179;} // 179 is the upper limit for the servo 
        angle =servo1.read(); //reads the actual angle for servo1
                    //Decides what direction to take 
                    if ( i >= angle) {
                      for (angle = angle; angle <= i; angle=angle +1)
                      {servo1.write(angle);                             
                      delay(s); } }
                   else 
                     { for (angle = angle; angle >= i; angle=angle- 1)
                        {servo1.write(angle);
                      delay(s); } }
                      
        }

void slow2 (int i) //speed function name for servo2
        {
 
         if (i < 1){ i = 1;}// 1 is the lower limit for the servo 
        if (i > 179){ i = 179;} // 179 is the upper limit for the servo 
        angle =servo2.read(); //reads the actual angle for servo2
                    //Decides what direction to take 
                    if ( i >= angle) {
                      for (angle = angle; angle <= i; angle=angle +1)
                      {servo2.write(angle);                             
                      delay(s); } }
                   else 
                     { for (angle = angle; angle >= i; angle=angle- 1)
                        {servo2.write(angle);
                      delay(s); } }
                      
        }


void setup()
{
servo1.attach(9); // Attaches the servo on pin 5 to the servo1 object
servo2.attach(10); // Attaches the servo on pin 6 to the servo2 object
Serial.begin(115200);
while(Serial.available())
Serial.read();
// servo1.write(0); // Put servo1 at home position
// servo2.write(0); // Put servo2 at home postion
}
void loop()
{
if (Serial.available() > 0) { // Check if data has been entered
int index=0;
delay(100); // Let the buffer fill up
int numChar = Serial.available(); // Find the string length
if (numChar>10) {
numChar=10;
}
while (numChar--) {
// Fill the buffer with the string
buffer[index++] = Serial.read();
}
buffer[index]='\0';
splitString(buffer); // Run splitString function
}
}
void splitString(char* data) {
char* parameter;
parameter = strtok (data, " ,"); //String to token
while (parameter != NULL) { // If we haven't reached the end of the string...
setServo(parameter); // ...run the setServo function
parameter = strtok (NULL, " ,");
}
while(Serial.available())
Serial.read();
}
void setServo(char* data) {
if ((data[0] == 'L') || (data[0] == 'l')) {
int firstVal = strtol(data+1, NULL, 10); // String to long integer
firstVal = constrain(firstVal,0,150); // Constrain values
// servo1.write(firstVal);
slow(firstVal); //speed function for servo1
}
if ((data[0] == 'R') || (data[0] == 'r')) {
int secondVal = strtol(data+1, NULL, 10); // String to long integer
secondVal = constrain(secondVal,0,150); // Constrain the values
// servo2.write(secondVal);
slow2(secondVal); // speed function for servo2
}
}

Python script to turn servo.

import serial
import time
ser = serial.Serial('COM6', 115200)
time.sleep(0.1)
ser.write(b'L150')
ser.close()