This example controls a servomotor. It moves a servomotor based on the value of an analog input. Thanks to Casey Reas for cleaning up the code. Thanks to Henryk Marstrander for the formula.
/* Servo control from an analog input The minimum (minPulse) and maxiumum (maxPuluse) values will be different depending on your specific servo motor. Ideally, it should be between 1 and 2 milliseconds, but in practice, 0.5 - 2.5 milliseconds works well for me. Try different values to see what numbers are best for you. This program uses the millis() function to keep track of when the servo was last pulsed. millis() produces an overflow error (i.e. generates a number that's too big to fit in a long variable) after about 5 days. if you're making a program that has to run for more than 5 days, you may need to account for this. by Tom Igoe additions by Carlyn Maw Created 28 Jan. 2006 Updated 7 Jun. 2006 */ int servoPin = 2; // Control pin for servo motor int minPulse = 500; // Minimum servo position int maxPulse = 2500; // Maximum servo position int pulse = 0; // Amount to pulse the servo int lastPulse = 0; // the time in milliseconds of the last pulse int refreshTime = 20; // the time needed in between pulses int analogValue = 0; // the value returned from the analog sensor int analogPin = 0; // the analog pin that the sensor's on void setup() { pinMode(servoPin, OUTPUT); // Set servo pin as an output pin pulse = minPulse; // Set the motor position value to the minimum Serial.begin(9600); } void loop() { analogValue = analogRead(analogPin); // read the analog input pulse = (analogValue / 10) * 19 + 500; // convert the analog value // to a range between minPulse // and maxPulse. // pulse the servo again if rhe refresh time (20 ms) have passed: if (millis() - lastPulse >= refreshTime) { digitalWrite(servoPin, HIGH); // Turn the motor on delayMicroseconds(pulse); // Length of the pulse sets the motor position digitalWrite(servoPin, LOW); // Turn the motor off lastPulse = millis(); // save the time of the last pulse } }
Here’s a version that controls two servos. Note that you have to reduce the refresh time to compensate for the pulse times of the servos as you add more servos. Thanks to Carlyn Maw for the update.
/* Two-servo control from an analog input Moves two servos based on the value of one analog sensor, in opposite directions. The minimum (minPulse) and maxiumum (maxPuluse) values will be different depending on your specific servo motor. Ideally, it should be between 1 and 2 milliseconds, but in practice, 0.5 - 2.5 milliseconds works well for me. Try different values to see what numbers are best for you. by Tom Igoe Created 28 Jan. 2006 Repurposed for Dual Servos by Carlyn Maw 24 Mar. 2006 */ int servoPinL = 2; // Control pin for servo motor - L int servoPinR = 3; // Control pin for servo motor - R int minPulse = 500; // Minimum servo position int maxPulse = 2500; // Maximum servo position long adjustedAV = 0; // Analog value adjusted for determining pulse values int pulseL = 0; // Amount to pulse the servoL int pulseR = 0; // Amount to pulse the servoR int delayValueMax = 20000; // the 20 microsecond maxiumum pulse range for the servo int delayValue = 20000; // the actual value the code should wait, determined later int analogValue = 0; // the value returned from the analog sensor int analogPin = 0; // the analog pin that the sensor's on void setup() { pinMode(servoPinL, OUTPUT); // Set servo pins as an output pins pinMode(servoPinR, OUTPUT); pulseL = minPulse; // Set the motor position values to the minimum pulseR = maxPulse; } void loop() { analogValue = analogRead(analogPin); // read the analog input (0-1024) adjustedAV = (analogValue / 10) * 19; // convert the analog value to a number // between 0-2000 (difference between min and max) pulseL = adjustedAV + minPulse; // set value for left motor pulseR = maxPulse - adjustedAV; // and the inverse for the right digitalWrite(servoPinL, HIGH); // Turn the L motor on delayMicroseconds(pulseL); // Length of the pulse sets the motor position digitalWrite(servoPinL, LOW); // Turn the L motor off digitalWrite(servoPinR, HIGH); // Turn the R motor on delayMicroseconds(pulseR); // Length of the pulse sets the motor position digitalWrite(servoPinR, LOW); // Turn the R motor off delayValue = (delayValueMax - pulseL) - pulseR; // determine how much time you have before the 20 ms is over... delayMicroseconds(delayValue); // 20 millisecond delay is needed between pulses // to keep the servos in sync }