Uno de los principales objetivos de la robótica es que el robot se mueva. Por eso, es muy común utilizar motores eléctricos y particularmente servomotores. En este artículo, programamos el Arduino para que pueda manejar un servomotor e iremos más allá en el uso de bibliotecas que incluyen Servo.h.
Prerrequisitos: Programa con Arduino
Material
- Ordenador
- Arduino UNO
- Cable USB
- Cable M/M x3
- Servomotor x1
Servomotor
Los servomotores son pequeños concentrados de tecnología que combinan mecánica y electrónica. Ampliamente utilizados en la creación de modelos, robótica y otras aplicaciones. Toman su nombre del hecho de que puede controlar a sí mismo su posición (o su velocidad).
Los servomotores se componen de un motor de CC, una caja de reducción y electrónica integrada para controlar la posición mediante una señal de modulación de ancho de pulso (en inglés: PWM – Pulse Width Modulation).
Diagrama de conexión
El servomotor se alimenta mediante el cable negro / marrón tierra (GND) y el cable rojo (+ 5V); y es impulsado por una señal PWM enviada por el cable amarillo / blanco (terminal 9). Dependiendo de la cantidad y la potencia del servomotor utilizado, puede ser alimentado por el terminal 5V del Arduino. Arduino puede ser alimentada por la computadora a través del puerto USB.
Si el servomotor excede la capacidad del microcontrolador, se debe utilizar una fuente de alimentación externa.
Código básico
Para controlar el servomotor en posición, debemos enviar una señal de modulación de ancho de pulso.
//Constants #define UPDATE_TIME 20 //Parameters int servoPin = 9; int pulse = 1500; void setup() { // Initialization pinMode(servoPin,OUTPUT); Serial.begin(9600); } void loop() { // main digitalWrite(servoPin,HIGH); delayMicroseconds(pulse); digitalWrite(servoPin,LOW); delay(UPDATE_TIME); }
Una forma más elegante de hacerlo es convertir la posición del servo en ancho de pulso. Para hacer eso, se requiere un poco de matemáticas.
- 5V durante 500µs (0,5ms) corresponden a 0 grados
- 5V durante 1500µs (1,5ms) corresponden a 90 grados
- 5V durante 2500µs (1,5ms) corresponden a 180 grados
Una vez que se establezca la fórmula, podemos implementar una función para convertir la posición en PWM.
//Constants #define UPDATE_TIME 20 //Parameters int servoPin = 9; int angle = 1500; void setup() { // Initialization pinMode(servoPin,OUTPUT); Serial.begin(9600); } void loop() { // main digitalWrite(servoPin,HIGH); delayMicroseconds(convertAngleToImp(angle)); digitalWrite(servoPin,LOW); delay(UPDATE_TIME); } // Declare function int convertAngleToImp(int ang){ float a = 2000/180; float b = 500; return int(a*ang+b); }
Se pueden escribir códigos más complejos en Arduino usando este conocimiento básico y algunas bibliotecas como la biblioteca Servo.h.
En este ejamplo, usamos la funcion digitalWrite() para mostrar el principio de la señal PWM. En la práctica, usamos analogWrite() para activar LEDs o servomotores.
//Déclaration des constantes #define UPDATE_TIME 20 //Déclaration des paramètres int servoPin = 9; void setup() { // Code d'initialisation pinMode(servoPin,OUTPUT); Serial.begin(9600); // Initialise la communication série PC/Arduino } void loop() { // Code principal for(int i=0;i<180;i++){ analogWrite(servoPin,convertirAngleEnPWM(i)); delay(UPDATE_TIME); } delay(200); for(int i=180;i>=0;i--){ analogWrite(servoPin,convertirAngleEnPWM(i)); delay(UPDATE_TIME); } delay(200); } // Déclaration d'un sous fonction int convertirAngleEnPWM(int ang){ float a = 255.0/180.0; return (a*ang); }
Servo control utilizando Servo.h
Vimos que se pueden crear funciones para reutilizar el código fácilmente en el mismo archivo. Esas funciones se pueden poner en la biblioteca, archivos externos, que también se pueden usar en cualquier aplicación. Se utilizan para organizar y aclarar el código y para evitar copiar y pegar. La biblioteca se puede usar agregando una línea de código simple (y leyendo la documentación para usarla correctamente) #include.
//Libraries #include <Servo.h> //Constants #define UPDATE_TIME 15 #define MAX_POS 180 #define MIN_POS 0 //Parameters int servoPin = 9; int pulse = 1500; //Variables Servo myServo; // create servo object int pos=0; // variable contenant la position du servomoteur void setup() { myServo.attach(servoPin); } void loop() { for (pos = MIN_POS; pos <= MAX_POS; pos += 1) { myServo.write(pos); delay(UPDATE_TIME); } for (pos = MAX_POS; pos >= MIN_POS; pos -= 1) { myServo.write(pos); delay(UPDATE_TIME); } }
Crea tu propia biblioteca ServoLib.h
La biblioteca se puede crear cuando se usa el mismo código para varias aplicaciones. Para crear una biblioteca, se deben escribir dos archivos en C (archivo .cpp y .h). El archivo .H, llamado header contiene declaraciones de clases, variables y de funciones. Esos archivos deben guardarse con el mismo nombre que la carpeta principal y colocarse en el directorio: .Documents/Arduino/libraries.
Archivo ServoLib.h
#ifndef ServoLib_h #define ServoLib_h //Constants #define UPDATE_TIME 15 #define MAX_POS 180 #define MIN_POS 0 #define MAX_PULSE_WIDTH 2500 #define MIN_PULSE_WIDTH 500 //Class class ServoLib { public: ServoLib(); //constructeur int servoPin; //broche du servomoteur void attach(int pin); void sendPosition(int value); int convertAngleToImp(int ang); void applyImp(int pulse); }; #endif
Archivo ServoLib.cpp
#include <ServoLib.h> ServoLib::ServoLib(){} void ServoLib::attach(int pin){ servoPin=pin; pinMode(servoPin,OUTPUT); } void ServoLib::sendPosition(int value){ int pulse=0; if (value<MIN_POS) value=MIN_POS; else if (value>MAX_POS) value=MAX_POS; value=map(value,MIN_POS,MAX_POS,MIN_PULSE_WIDTH,MAX_PULSE_WIDTH); pulse=this->convertAngleToImp(value); this->applyImp(pulse); } void ServoLib::applyImp(int pulse){ digitalWrite(servoPin,HIGH); delayMicroseconds(pulse); digitalWrite(servoPin,LOW); delay(UPDATE_TIME); } int ServoLib::convertAngleToImp(int ang){ float a = 2500/180; float b = 500; return int(a*ang+b); }
Puede anadir un archivo .txt que cambia el color de los variables o funciones en el IDE.
####################################### # Syntax Coloring Map ServoLib ####################################### ####################################### # Datatypes (KEYWORD1) ####################################### ServoLib KEYWORD1 ServoLib ####################################### # Methods and Functions (KEYWORD2) ####################################### attach KEYWORD2 sendPosition KEYWORD2 convertAngleToImp KEYWORD2 applyImp KEYWORDS2 ####################################### # Constants (LITERAL1) ####################################### UPDATE_TIME LITERAL1 MIN_POS LITERAL1 MAX_POS LITERAL1 MIN_PULSE_WIDTH LITERAL1 MAX_PULSE_WIDTH LITERAL1
Sin keywords.txt
Con keywords.txt
Cuando vuelve a cargar el software IDE, la biblioteca recién creada está disponible en Menú> Bosquejo> Incluir biblioteca
El código se puede simplificar de la siguiente manera:
//Library #include "ServoLib.h" //Parameters int servoPin = 9; //Variables ServoLib myServo; int pos=0; void setup() { myServo.attach(servoPin); } void loop() { for (pos = MIN_POS; pos <= MAX_POS; pos += 1) { myServo.sendPosition(pos); delay(UPDATE_TIME); } for (pos = MAX_POS; pos >= MIN_POS; pos -= 1) { myServo.sendPosition(pos); delay(UPDATE_TIME); } }
Próximas etapas
Funetes
- LA referencia https://www.arduino.cc/
- Especialmente para servos https://www.arduino.cc/en/Reference/Servo
- Para bibliotecas : https://arduino.cc/en/Guide/Libraries
- Programa con Arduino
Encuentre otros tutoriales y ejemplos en el generador de código automático
Arquitecto de Código