Hi, I was following along in this thread: http://forum.arduino.cc/index.php?topic=310054.45
I ran into some issues and thought I would make a new topic.
I’m trying to do some keyframe animation of servo movements for a robotic arm.
This is is the exact animation I’m hoping to achieve:
This is done in 3D Studio Max and I’m just translating the keyframes to milliseconds and for hte most part everything is working.
I have two servos, SHOULDER and SPIN. SHOULDER does a lifting rotation as though raising your arm from the shoulder, and the spin servo spins the arm. Both servos are HS-645MG from Hi-Tec
Here is my code:
#include <Servo.h>
Servo SPIN;
Servo SHOULDER;
int Val;
int SPINdefault = 99;
int SHOULDERdefault = 197;
struct ServoAction
{
unsigned long ActionTime; // Number of milliseconds after sequence starts to do this action
Servo ServoToAct; // Which servo is it?
bool ActionDone; // Is action done yet
int Degrees; // Number of degrees to send the designated servo to
};
ServoAction Actions[] = {
{1000, SHOULDER, false, 161},
{2000, SHOULDER, false, 197},
{3000, SPIN, false, 0},
{3500, SPIN, false, 99},
{4000, SPIN, false, 197},
{4500, SPIN, false, 99},
{5500, SHOULDER, false, 161},
{5500, SPIN, false, 0},
{6000, SPIN, false, 99},
{6500, SPIN, false, 197},
{7000, SPIN, false, 99},
{7500, SHOULDER, false, 197},
{7500, SPIN, false, 0},
{8000, SPIN, false, 99},
{8500, SPIN, false, 197},
{9000, SPIN, false, 99},
/* etc. etc. */
};
const byte NoActions = sizeof Actions / sizeof Actions[0];
unsigned long StartTime;
void setup()
{
Serial.begin(9600);
StartTime = millis();
SPIN.attach(9, 553, 2520); // attaches the servo on pin 9 to the servo object, the servo min/max pulse range is 553 to 2520 microseconds
SHOULDER.attach(10, 553, 2520);
SPIN.write(SPINdefault);
SHOULDER.write(SHOULDERdefault);
delay (2000);
}
void loop()
{
for(int i=0;i<NoActions;i++)
if(!Actions[i].ActionDone)
if(millis()-StartTime > Actions[i].ActionTime)
{
Actions[i].ActionDone=true;
Actions[i].ServoToAct.write(Actions[i].Degrees);
}
}
With that code I can achieve this:
There is one problem I am experiencing and a few things I’d like to add to the functionality if possible.
PROBLEM: If you look in my setup, when I attach the servos I change the pulse-rate range to match the specs of my servo per the manufacturer. Before I did this, I was only getting 0-180 degree rotation instead of 0-197. When I added in that pulse rate range it started working as it should. If you watch the video of the actual part, you can see during the setup function it does go to the proper spot (the arm being totally flat) but when it enters the loop function the arm immediately jumps up to about 180 range as if I never put those values in at all. It also never returns to full flat as it should at the end. Why are those pulse rate changes being ignored in the loop function?
As far as functionality, Is there a way I can add a parameter to ServoAction to slow down the speed of the servo, like add in a ‘delay’ between each step? In the CG animation the arms move slowly and are timed differently, the code seems to just make them move to their next point as fast as possible. I’m not sure how to add in a “speed control”
I plan on adding in the elbow servo which should work similarly to these, but I’m also hoping to control the claw at the end with a solenoid. The solenoid will be controlled by a cirucuit with a transistor. The transistor just needs a high/low signal from a digital pin. How can I add that into the ServoAction animation chain so I can incorporate it with the full animation?
I know it’s a lot that I am asking, but any help you can give would be amazing!
Thanks!