Avanzando con Arduino
Avanzando para aprender a programar Arduino.
Abriendo el primer ejemplo
El primer paso para comprobar que todo lo que hemos hecho hasta ahora está bien y familiarizarnos con el interfaz de desarrollo, es abrir uno de los ejemplos. Se recomienda abrir el ejemplo “led_blink”. Para ello debemos acceder a través del menú File --> Sketchbook --> Examples --> led_blink
Subiendo el programa de ejemplo a la placa arduino
El ejemplo “led_blink” lo único que hace es parpadear un LED que esté colocado en el pin número 13 de la placa. Vamos a ver qué hay que hacer para subir el programa a la placa Arduino.
Primero comprobamos que el código fuente es el correcto. Para ello pulsamos el botón de verificación de código que tiene forma de triángulo inclinado 90 grados.
Si todo va bien deberá aparecer un mensaje en la parte inferior de la interfaz indicando “Done compiling”.
Una vez que el código ha sido verificado procederemos a cargarlo en la placa. Para ello tenemos que pulsar el botón de reset de la placa e inmediatamante después pulsar el botón que comienza la carga.
Subiendo el programa a la placa
Durante la carga del programa, en la placa USB, se encenderán los LED que indican que se están enviando y recibiendo información por el puerto serie: TX/RX.
Subiendo el programa
Si todo se ha realizado correctamente debe aparecer un mensaje como el que se muestra a continuación:
El programa se ha cargado correctamente en la placa
Ahora tan sólo queda esperar unos 8 segundos aproximadamente para comprobar que todo ha salido bien. Si el led colocado en el pin 13 de la placa se enciende y se apaga cada segundo entonces todo ha ido bien. Por fin tenemos todo listo para empezar a trabajar con la placa Arduino.
Cómo programar Arduino
Estructuras
void setup()
La función setup() es llamada justo en el momento en que el programa comienza. Se utiliza para inicializar variables, definir los modos de entrada o salida de los pines, indicar librerías, etc.
Ejemplo
int buttonPin = 3;
void setup() //Sección Setup de la estructura de programa
{
beginSerial(9600); pinMode(buttonPin, INPUT);
}
void loop() //Sección loop de la estructura de programa
{
if (digitalRead(buttonPin) == HIGH)
serialWrite('H');
else
serialWrite('L');
delay(1000);}
void loop()
Después de crear la sección setup(), que inicializa y asigna los valores iniciales, la sección loop() hace precisamente lo que su nombre indica en inglés(bucle), y se repite continuamente, permitiendo que tu programa mute y responda. Se usa para controlar de forma activa la tarjeta Arduino.
El tiempo del bucle, varía según el número de instrucciones que contenga. Y se puede conocer y controlar con las funciones de temporización (millis(), delay(), etc).
Ejemplo
int buttonPin = 3;
// setup inicializa la comunicación serie y el modo del
//pin conectado al pulsador,como entrada
void setup() {
beginSerial(9600); pinMode(buttonPin, INPUT);
}
// loop chequea el pin de entrada conectado al pulsador continuamente,
// dependiendo si es pulsado o no,enviará un valor diferente vía comunicación serie
void loop() {
if (digitalRead(buttonPin) == HIGH)
serialWrite('H');
else
serialWrite('L');
delay(1000);
}
Declaración de Variables
Las variables son expresiones que almacenan valores, como las capturas o lecturas de los valores de entrada de un pin analógico o sensor. (Para más información sobre asignación de modos de entrada (input) o salida (output) a los pines referirse la función pinMode ).
Inicializas o das valor a una variable, haciéndola igual al valor que quieres almacenar. En el siguiente código se declara una variable "inputVariable", y entonces se inicializa con el valor capturado desde el pin analógico número #2:
int inputVariable = 0; # Declara la variable; sólo necesario una vez.
inputVariable = analogRead(2); # le asiga a la variable el valor de entrada del pin analógico #2
"inputVariable" es la variable. La primera línea es para indicar que contendrá un dato de tipo "int" (entero corto). La segunda línea le asigna a la variable el valor capturado del pin analógico número #2. Lo que hace que se pueda acceder al valor del pin #2 desde cualquier parte del código.
Una vez que a la variable le ha sido asignado un valor (o reasignado), se puede comprobar su valor para saber si cumple ciertas condiciones, o se puede usar su valor directamente. Por ejemplo, el siguiente código comprueba si la variable "inputVariable" es menor que 100, y realizará una pausa basada en el valor de dicha variable, la cual tendrá siempre como mínimo un valor de 100ms:
if (inputVariable < 100) { inputVariable = 100 }
delay(inputVariable)
Declaración de funciones
Las funciones te permiten crear piezas modulares de código, de forma que se puedan realizar ciertas rutinas y retornar al área de código desde donde se realizó la llamada a la función. A continuación mostramos un ejemplo de la llamada a una función:
displayNumber(value);
Cuando Arduino ejecuta esta línea, busca la declaración de dicha función en algún lugar del código, y le pasa el valor de la variable "value" como un argumento (contenido entre los paréntesis) a la función. A continuación se muestra un ejemplo de como podría ser la declaración de la función:
void displayNumber(int incomingValue){
printInteger(incomingValue); // otro código dentro de la función
}
De forma que una función se define por el tipo de valor que devuelve (enlace a declaración de variables), por su nombre, por la lista de argumentos o parámetros que le son pasados (expresión entre paréntesis) y el bloque de código que se ejecuta cuando se realiza la llamada.
El tipo "void" del ejemplo, significa nada e indica que la función no va a devolver ningún valor.
Los parámetros o argumentos pueden ser pasados por dos métodos o mecanismos: "por valor" o "por referencia".
Cuando son pasados "por valor", significa que sólo se aplica una simple operación de asignación o copiado (=) entre las varibles externas a la función y las variables locales a la función. Como en el ejemplo anterior, el parámetro o argumento "num" va obteniendo sus valores del contexto de la llamada a la función. Dicha asignación se realiza justo antes de que la función empiece a ejecutarse.
El otro método, paso de parámetros "por referencia", se utiliza en el caso de que el parámetro sea de tipo estructura, como por ejemplo un vector.
Prototipado
En lenguaje de programación C, cualquier función que se cree en el código, debe llevar asociada una declaración de prototipado de la función, al comienzo de tu código y antes de la sección o bloque setup(). Dicha declaración es similar a la declaración que se realiza con una variable, y básicamente es la primera línea de la declaración de tu función, finalizada por el punto y coma. En otras palabras, se da su nombre y sus argumentos, pero no su código.
void displayNumber(int incomingValue);
Con ello se prepara al programa para que pueda saber que tipo de función se va a ejecutar y que argumentos se le pasarán.
Estructuras de control
if (condición)
La estructura If comprueba si la condición contenida entre paréntesis () se ha cumplido, como por ejemplo si una entrada supera un cierto número. El formato de la comprobación que se realiza en el if es:
if (algunaVariable > 50) {
// hacer algo aquí
}
El programa comprueba si la variable "algunaVariable" es más grande que 50. Si es así, el programa realiza una acción particular. Dicho de otra manera, si la declaración entre paréntesis es verdadera, el código dentro de los paréntesis se ejecuta. Si no, el código no se ejecuta o se salta el código.
Las condiciones que van a ser comprobadas o evaluadas, dentro de los paréntesis requieren el uso de uno o más operadores:
Operadores:(Enlace a operadores relacionales)
- x == y (x es igual a y)
- x != y (x no es igual a y)
- x < y (x es menor que y)
- x > y (x es mayor que y)
- x <= y (x es menor que o igual a y)
- x >= y (x es mayor que o igual a y)
if /else
La estructura if/else da un mayor control sobre el flujo o secuenciación del código que la estructura de control básica if, permitiendo agrupar múltiples comprobaciones juntas.
Por ejemplo, si quieres comprobar una entrada analógica, y hacer una cosa si su valor fue menor que 500, y otra cosa si su valor fue 500 o mayor, se debería de escribir de la siguiente forma:
if (pinFiveInput < 500)
{
//hacer cosa A
}
else
{
//hacer cosa B
}
else también puede ser precedido por otra comprobación if, así que se podrían ejecutarse al mismo tiempo múltiples comprobaciones y mutuamente excluyentes.
for (init; test; update)
Realiza el control sobre una secuencia de repetición. Se compone de tres partes: init (inicializado de la variable local), test (condición) , y update (actualización del valor la variable local), cada parte debe ser separada por punto y coma ";". El bucle continua hasta que la condición establecida se cumple (es verdad) o no (falsa). Es útil cuando se usa en combinación con vectores y operar sobre grupo de datos/pines.
Cuando se ejcuta el for, ocurre la siguiente secuencia de eventos:
- Se ejecuta la parte init (inicializado de la variable local) de la declaración.
- Se evalúa la condición, si se cumple (es verdad) o no (falsa).
- Si se cumple la condición (es verdad), salta al paso 4. Si no se cumple la condición (es falsa), salta al paso 6.
- Ejecuta las sentencias o el código que está dentro del bloque.
- Ejecuta la parte de update (actualización de la variable local) y salta al paso 2.
- Sale del bucle.
Nota Importante: En lenguaje de programación C no necesitas inicializar la variable local. Puedes hacerlo directamente dentro de la declaración for. Es una diferencia con respecto a otros lenguajes, lenguajes basados en java.
Parámetros
for(init; test; update) {
statements (sentencias o código)
}
Switch Case
Como la estructura de control "If", la estructura de control "switch case" ayuda en el control del flujo o secuenciación de los programas. Permite hacer una lista de "casos" posibles dentro de un bloque delimitado por paréntesis, en el cual arduino encontrará el caso más idóneo y lo ejecutará.
Parámetros
var - variable a validar con cada uno de los casos declarados.
default - si no se dá ninguno de los casos, se ejecutará la parte definida en el default
break - importante, sin "break", la estructura de control continúa realizando la comprobación con el caso siguiente. Si también se cumple, se ejecuta de igual modo, lo que podría no ser tu intención. "Break" le indica a la estructura que pare de buscar en el resto de los casos, y finalice la función.
Ejemplo
switch (var) {
case 1:
//hacer algo cuando var == 1
break;
case 2:
//hacer algo cuando when var == 2
break;
default:
// si ninguna de las anteriores, hacer la parte de default
}
While (expresión)
Realiza un bucle de forma continuada hasta que la expresión contenida dentro de los paréntesis () deja de ser verdadera. Es útil para crear bucles propios, pero asegurando el seguimiento de alguna de las variable usadas para parar o salir del bucle, si esa es la intención.
Ejemplo
var = 0; while(var < 200){
//hacer que algo se repita 200 veces var++;
}
Más sintaxis:
- ; (punto y coma)
- , (coma)
- . (punto)
- {} (paréntesis)
- [] (corchetes)
- // (comentarios de línea)
- /* */ (comentarios de multi-línea)
- * Puntero (vector)
- = (asignación)
- #define
Un define es un componente útil en el lenguaje de progración C, que permite dar un nombre a un valor antes de que el programa sea compilado.
Puedes definir números en Arduino, para que no ocupen espacio de memoria de programa en el chip. La definición en Arduino tiene la misma sintaxis que la definición en C:
#define constantName value
- #include
Para utilizarlas, sólo es necesario añadir la correspondiente declaración #include al comienzo de tu código o proyecto.
Variables:
- char (caracter)
- int (entero corto)
- long (entero largo)
- boolean (lógica)
- Byte (Tipo de datos)
- Array (vector)
- string (Cadena de carácteres)
Constantes
- HIGH | LOW
- INPUT | OUTPUT
- true | false
Pines digitales
- pinMode(pin, mode)
Configura el pin especificado para que se comporte como una entrada (input) o una salida (output).
Ejemplo
int ledPin = 13; // LED conectado a pin digital 13
void setup() {
pinMode(ledPin, OUTPUT); // asigna al pin digital como salida
}
void loop() {
digitalWrite(ledPin, HIGH); // enciende el LED delay(1000); // espera un segundo digitalWrite(ledPin, LOW); // apaga el LED delay(1000); // espera un segundo
}
configura el pin número 13 para que funcione como un pin de salida (output).
- digitalWrite(pin, value)
Asigna el valor de salida HIGH o LOW al pin especificado.
Ejemplo
int ledPin = 13; // LED conectado a pin digital 13
void setup() {
pinMode(ledPin, OUTPUT); // asigna al pin digital como modo pin de salida
}
void loop() {
digitalWrite(ledPin, HIGH); // enciende LED delay(1000); // espera un segundo digitalWrite(ledPin, LOW); // apaga el LED delay(1000); // espera un segundo
}
Asigna HIGH al pin 13, realiza un retardo de un segundo, y vuelve a asignar LOW al pin.
- int digitalRead(pin)
Lee o captura el valor de entrada del pin especificado, dará valores HIGH o LOW. Devuelve un valor de tipo entero HIGH(1) o LOW (0).
Ejemplo
int ledPin = 13; //
int inPin = 7; // pulsador conectado a pin digital 7
int val = 0; // variable para almacenar el valor de captura o lectura
void setup() {
pinMode(ledPin, OUTPUT); // asigna al pin digital 13 como modo pin de salida pinMode(inPin, INPUT); // asigna al pin digital 7 como modo pin de entrada
}
void loop() {
val = digitalRead(inPin); // lee o captura el valor de entrada del pulsador digitalWrite(ledPin, val); // asigna el valor capturado al LED
}
Asigna al pin 13 (salida), el mismo valor capturado en el pin 7 (entrada).
- unsigned long pulseIn(pin)
Lee un pulso (en estado HIGH (1) o LOW(0)) sobre un pin. Por ejemplo, si el valor es HIGH, pulseIn() espera hasta que el pin esté en estado HIGH, entonces empieza a temporizar, y cuando el pin vuelve al estado LOW, se para el temporizador. De este modo, se devuelve el ancho del pulso en microsegundos. Devuelve el ancho del pulso(en microsegundos).
Ejemplo:
int pin = 7; unsigned long duration;
void setup() {
pinMode(pin, INPUT);
}
void loop() {
duration = pulseIn(pin, HIGH);
}
Pines analógicos
- int analogRead(pin)
Lee o captura el valor de entrada del especificado pin analógico, la tarjeta Arduino realiza una conversión analógica a digital de 10 bits. Esto quiere decir que mapeará los valores de voltage de entrada, entre 0 y 5 voltios, a valores enteros comprendidos entre 0 y 1024.
Los pines analógicos, al contrario que los pines digitales, no necesitan ser declarados como modo INPUT (entrada) o OUTPUT (salida). Devuelve un valor entero comprendido en el rango de 0 a 1024.
Ejemplo
int ledPin = 13; // LED conectado a pin digital 13
int analogPin = 3; // potentiómetro conectado a pin analógico 3
int val = 0; // variable para almacenar el valor capturado
int threshold = 512; // valor de disparo o umbral (1024/2)
void setup() {
pinMode(ledPin, OUTPUT); // asigna modo salida el pin digital 13
}
void loop() {
val = analogRead(analogPin); // captura el pin de entrada
if (val >= threshold) {
digitalWrite(ledPin, HIGH); // enciende el LED
} else {
digitalWrite(ledPin, LOW); // apaga el LED
}
}
Asigna el valor HIGH(1) o LOW(0) al pin 13, dependiendo de que si el valor de entrada al pin analógico es mayor que un cierto valor de disparo o umbral.
- analogWrite(pin, value)- PWM
Escribe o asigna un valor analógico (señal PWM) a pines 9,10 y 11 ¿?. Se puede usar para encender un Led e ir variando la intensidad de su brillo o impulsar un motor a distintas velocidades. Después de invocar o realizar una llamada a la función analogWrite, el pin generará una señal estable hasta la próxima invocación o llamada de la función analogWrite (o una llamada a digitalRead o digitalWrite sobre el mismo pin). No devuelve nada.
Ejemplo
int ledPin = 9; // LED conectado al pin digital 9
int analogPin = 3; // potenciómetro conectado al pin analógico 3
int val = 0; // variable para almacenar el valor de captura o lectura
void setup() {
pinMode(ledPin, OUTPUT); // asigna el pin como modo salida
}
void loop() {
val = analogRead(analogPin); // lee o captura el pin de entrada
analogWrite(ledPin, val / 4);
// los valores de analogRead van desde 0 a 1023, los valores de analogWrite desde 0 a 255
}
Asigna a la salida que va al LED el valor proporcional capturado desde el potentiómetro.











