The program listed below moves my servos to the desired position, however, the movement is very jerky and happens too fast. Is their anyway to slow down/smooth out the servos motion? Once in the position the servos are fine and their is no twitching.
I looked at the examples of moving servos, however, I was not able to find one which showed smooth motion of 4 servos at the same time.
I tried at the "sweep" example and I loved the smooth motion however I could not figure out how to sweep all the servos at the same time. In the program I'm using now the servos all appear to start moving at the same time which is what I want. Is it possible to modify the sweep example so that all the servos move smoothly and at about the same time?
// Sweep
// by BARRAGAN <http://barraganstudio.com>
// This example code is in the public domain.
#include <Servo.h>
Servo myservo; // create servo object to control a servo
// a maximum of eight servo objects can be created
int pos = 0; // variable to store the servo position
void setup()
{
myservo.attach(9); // attaches the servo on pin 9 to the servo object
}
void loop()
{
for(pos = 0; pos < 180; pos += 1) // goes from 0 degrees to 180 degrees
{ // in steps of 1 degree
myservo.write(pos); // tell servo to go to position in variable 'pos'
delay(15); // waits 15ms for the servo to reach the position
}
for(pos = 180; pos>=1; pos-=1) // goes from 180 degrees to 0 degrees
{
myservo.write(pos); // tell servo to go to position in variable 'pos'
delay(15); // waits 15ms for the servo to reach the position
}
}
In the servo sweep sketch where it says " myservo.write(pos); " if you add three more lines immediately following (and all before the delay()) - so you have a line for each servo - I think it should work as you want.
// Sweep
// by BARRAGAN <http://barraganstudio.com>
// This example code is in the public domain.
#include <Servo.h>
Servo myservo2; // create servo object to control servo 2
Servo myservo3; // create servo object to control servo 3
Servo myservo4; // create servo object to control servo 4
Servo myservo5; // create servo object to control servo 5
int pos = 0; // variable to store the servo position
void setup()
{
myservo2.attach(2); // attaches the servo on pin 2 to the servo object
myservo3.attach(3); // attaches the servo on pin 3 to the servo object
myservo4.attach(4); // attaches the servo on pin 4 to the servo object
myservo5.attach(5); // attaches the servo on pin 5 to the servo object
}
void loop()
{
for(pos = 0; pos < 180; pos += 1) // goes from 0 degrees to 180 degrees
{ // in steps of 1 degree
myservo(2).write(pos); // tell servo to go to position in variable 'pos'
myservo(3).write(pos);
myservo(4).write(pos);
myservo(5).write(pos);
delay(15); // waits 15ms for the servo to reach the position
}
for(pos = 180; pos>=1; pos-=1) // goes from 180 degrees to 0 degrees
{
myservo(2).write(pos); // tell servo to go to position in variable 'pos'
myservo(3).write(pos);
myservo(4).write(pos);
myservo(5).write(pos);
delay(15); // waits 15ms for the servo to reach the position
}
}
I need the servos to go to different positions (like in the first program i posted) but I want them to move to those positions with the smoothness of the sweep example. I also need them to arrive in their positions at about the same time. In the code you posted I think all the servos will end up in the same position.
In the first code I posted (which I wrote) the servos start at a desired position wait a few seconds and move to an other position. In my code the servos move at ruffly the same time. The problem with my code is that the servos move straight to the position with no steps in-between, making the movement jerky. In the sweep example the servo moves in steps which makes the movement smooth.
I would like to modify my code so that each servo moves in steps but all the servos finish their steps at about the same time. I don't want one servo moving to position then the other. The servos should all be moving thought their steps at the same time. They will need to go to different positions wait a few seconds and then go back. For example one might go from 0 to 90 and another from 100 to 160.
You'll need to figure out some common factor in the angles that the servos are to move (90, 30, 9, and 90). Clearly, a for loop that iterates 90 times will work.
On each iteration, increment (or decrement) the position for each servo 1/90th of total range of motion for that servo (1 degree, 1/3 of a degree, 1/10 of a degree, 1 degree). Write that position to the servo. For the two smaller sweeps, the angle value will increment less than a degree, so you can see that ints won't work. The Servo library will truncate the value to an int, but that's OK. It just means that 9 out of 10 passes through the for loop, one of the servos will do nothing. On 1 of three passes, another will do nothing. On each pass, 2 of the servos will move every time.
Keep in mind that the for loop index does not HAVE to be used in the body of the for loop.
I made a program that uses steps to move the servos and it works perfect. Thanks for all the help!
Also is their anyway to shorten it?
Edit: I have found one problem. When moving to a new position the servo starts at a really low number which does not work in my design with some servos. If the arm is traveling to 180 degrees is their anyway that I can start the travel off at say 100 degrees?
[quote author=Drew Davis link=topic=170233.msg1266226#msg1266226 date=1370378671]
I made a program that uses steps to move the servos and it works perfect. Thanks for all the help!
Also is their anyway to shorten it? [/quote]
Try:
void smove(pos1, pos2, pos3)
{
pos1 = pos1/12;
pos2 = pos2/12;
pos3 = pos3/12;
for (int x =1;x<13;x++){ //do the following 12 times
pos3b+ = pos3; //does the same as pos3b = pos3b + pos3
pos2b+ = pos2;
pos1b+ = pos1;
myservo2.write(pos1b);
myservo3.write(pos2b);
myservo4.write(pos3b);
delay(75);
}
pos3b = 0; //reset variables for next call to function but,
//if you need to retain where the servos are, remove these lines
pos2b = 0;
pos1b = 0;
}
Hey Drew,
Here is a code example of sine wave smooth servo movement from two different positions.
The code seems complex but it just uses the more detailed writemicroseconds() command spread out in a bunch of for loops to handle start pause, and alterations in beginning and ending speed.
You are basically able to pick the beginning and end range of the servo, then pick positions between that you want the servo to travel to.
The motion between will be a sine wave smooth with a selectable start and end speed.
I usually have two sets of variables in arrays (or a struct in a single array - whatever) which contains the desired and current position of each servo on the system. Then, at pre-defined intervals, either through the use of millis() or on a timer, I update the contents of that array so that the "current" variable is set to half way between its current value and that of the "target" value. Then I write that new current value to the servo. It makes for a nice fast start to the movement, but it comes to a nice gentle stop at the right position. The overall speed is set by the delay between updates.