Está en la página 1de 80

Sistemas Digitales

INGENIERÍA 2024-I

ARDUINO
Programación en Arduino

Introducción
Con el fin de poner a disposición al alumno una plataforma de prototipo de código abierto, como es
Arduino, el cual será pieza importante en el desarrollo de los trabajos destinado para este ciclo, se
ha propuesto una serie de laboratorios y seminarios en donde se verán a grandes rasgos lo que se
ha pensado son los conceptos y herramientas más importante que se deben tener en cuenta, y que
podrán ser aplicadas en la realización del trabajo.

En primer lugar, expondremos un marco teórico orientado a Arduino, donde definiremos los
conceptos más importantes que se deben saber al hablar del término Arduino, así como la estructura
que tiene el código y las principales funciones que se deben conocer del mismo.

Objetivos
Familiarizar al alumno con el uso de placas de Arduino y su programación en esta, además de tener
una visión diferente de los lenguajes de programación, así como su diferencia, además aprender
más sobre el lenguaje de programación C++ y su importancia.

Este seminario será realizado en tres partes, la primera es una pequeña introducción de lo que es
Arduino y el entorno en donde se programa, la segunda y tercera parte consiste en actividades que
se realizarán empleando protoboard, Arduino y los componentes necesarios para realizar lo que se
pide.

El alumno encontrará el uso de Arduino algo más práctico y mostrará interés por la programación
así como el correcto uso de los comandos a usarse.

Página 1 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

MARCO TEÓRICO ORIENTADO A ARDUINO

¿Qué es Arduino?
Arduino es una plataforma de prototipos electrónica de código abierto (open-source) basada en
hardware y software flexibles y fáciles de usar. Está pensado para artistas, diseñadores,
como hobby y para cualquiera interesado en crear objetos o entornos interactivos.
Arduino puede sentir el entorno mediante la recepción de entradas desde una variedad de sensores
y puede afectar a su alrededor mediante el control de luces, motores y otros artefactos.
El microcontrolador de la placa se programa usando el Arduino Programming Language (basado en
Wiring) y el Arduino Development Environment(basado en Processing). Los proyectos de Arduino
pueden ser autónomos o se pueden comunicar con software en ejecución en un ordenador. Las
placas se pueden ensamblar a mano o encargarlas pre-ensambladas; el software se
puede descargar gratuitamente. Los diseños de referencia del hardware (archivos CAD) están
disponibles bajo licencia open-source, por lo que eres libre de adaptarlas a tus necesidades.
Arduino recibió una mención honoríca en la sección Digital Communities del Ars Electronica Prix en
2006.

NOTA: Para los más curiosos la palabra “Arduino” es una palabra de origen germánico que significa
“el que ayuda a los amigos”.

¿Por qué Arduino?

Hay muchos otros microcontroladores y plataformas microcontroladoras disponibles para


computación física. Parallax Basic Stamp, Netmedia’s BX-24, Phidgets, MIT’s Handyboard, y
muchas otras ofertas de funcionalidad similar. Todas estas herramientas toman los desordenados
detalles de la programación de microcontrolador y la encierran en un paquete fácil de usar. Arduino
también simplifica el proceso de trabajo con microcontroladores, pero ofrece algunas ventajas
para profesores, estudiantes y a aficionados interesados sobre otros sistemas:

✓ Barato: Las placas Arduino son relativamente baratas comparadas con otras
plataformas microcontroladoras. La versión menos cara del módulo Arduino puede ser
ensamblada a mano, e incluso los módulos de Arduino pre-ensamblados cuestan menos de
50$.

✓ Multiplataforma: El software de Arduino se ejecuta en sistemas operativos Windows,


Macintosh OSX y GNU/Linux. La mayoría de los sistemas microcontroladores están
limitados a Windows.

✓ Entorno de programación simple y clara: El entorno de programación de Arduino es fácil


de usar para principiantes, pero suficientemente flexible para que usuarios avanzados
puedan aprovecharlo también. Para profesores, está convenientemente basado en el
entorno de programación Processing, de manera que estudiantes aprendiendo a programar
en ese entorno estarán familiarizados con el aspecto y la imagen de Arduino.

✓ Código abierto y software extensible: El software Arduino está publicado como


herramientas de código abierto, disponible para extensión por programadores
experimentados.

✓ El lenguaje puede ser expandido mediante librerías C++, y la gente que quiera entender los
detalles técnicos pueden hacer el salto desde Arduino a la programación en lenguaje AVR
C en el cual está basado. De forma similar, puedes añadir código AVR-C directamente en
tus programas Arduino si quieres.

✓ Código abierto y hardware extensible: El Arduino está basado en microcontroladores


ATMEGA8 y ATMEGA168 de Atmel. Los planos para los módulos están publicados bajo
licencia Creative Commons, por lo que diseñadores experimentados de circuitos pueden
hacer su propia versión del módulo, extendiéndolo y mejorándolo. Incluso usuarios

Página 2 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

relativamente inexpertos pueden construir la versión de la placa del módulo para entender
cómo funciona y ahorrar dinero.

Arduino Software (IDE):

El entorno de desarrollo integrado Arduino-o Arduino Software (IDE)-contiene un editor de texto


escribir código, un área de mensajes, una consola de texto, una barra de herramientas con botones
para funciones comunes y una serie de menús. Se conecta al Arduino y hardware Genuino para
cargar programas y comunicase con ellos.

Sketches
Los programas escritos utilizando Arduino Software (IDE) se llaman Sketches. Estos Sketches se
escriben en el editor de texto y se guardan con la extensión de archivo “.ino”. El editor tiene
funciones para cortar /pegar y para buscar /reemplazar texto. El área de mensajes proporciona
información mientras que se está guardando y exportando y también muestra los errores.

Estructura del programa


La estructura básica del lenguaje de programación de Arduino es bastante simple se compone de
al menos de dos partes. Estas dos partes necesarias, funciones, encierran bloques que contienen
declaraciones, estamentos o instrucciones.

void setup(){
estamentos;
}

void loop(){
estamentos;
}

En donde setup() es la aparte encargada de recoger la configuración y loop() es la que contienen


el programa que se ejecutara cíclicamente (de ahí el termino loop-bucle). Ambas funciones son
necesarias para que el programa trabaje.

La función setup():
La función setup() se invoca una sola vez cuando el programa empieza. Se utiliza para inicializar
los modos de trabajo de los pins, o el puerto serie. Debe ser incluido en un programa aunque no
haya declaración para ejecutar.

void setup(){
pinMode(pin, OUTPUT); // configura el 'pin' como salida
}

La función Loop():
Después de llamar a setup(),la función loop() hace precisamente lo que se sugiere su nombre, se
ejecutara de forma cíclica, lo que posibilita que el programa este respondiendo continuamente antes
los eventos que se produzcan en la tarjeta.

void loop(){
digitalWrite(pin, HIGH); // pone en uno (on, 5v) el ´pin´
delay(1000); // espera un segundo (1000 ms)
digitalWrite(pin, LOW); // pone en cero (off, 0v.) el ´pin´
delay(1000);
}

En cuanto a los modelos de tarjetas, han ido saliendo cada vez más nuevos modelos, uno de los
primeros fue el Arduino UNO el cual tiene el microcontrolador ATMEGA328, luego temenos distintas

Página 3 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

presentaciones de tarjetas que traen el mismo microcontrolador pero con distinto tipo de integrado
y otras tarjetas con otros modelos de microcontroladores, a continuación; mostraremos una tabla
de los distintos modelos de tarjetas así como sus principals características:

Figura 1 .- Tabla comparative de principals características

Página 4 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Materiales necesarios

✓ Una tarjeta Protoboard:

El protoboard o breadbord: Es una especie de tablero con orificios, en la cual se pueden


insertar componentes electrónicos y cables para armar circuitos. Como su nombre lo indica,
esta tableta sirve para experimentar con circuitos electrónicos, con lo que se asegura el buen
funcionamiento del mismo.

Figura 2.- Protoboard

✓ Cables para circuitos eléctronicos:

Los conductores son materiales que permiten que la electricidad fluya a través de ellos
fácilmente. Algunos de los componentes eléctricos, tales como las resistencias, que frenan
el flujo de corriente, y los condensadores, que almacenan energía eléctrica, también están
hechos de conductores. El cable de los circuitos está hecho de conductores, y se utiliza en
los circuitos para conectar los diferentes componentes eléctricos y demás conductores.

Figura 3.- Cables Dupont

✓ Placa Arduino

Las placas Arduino son pequeños ordenadores con los que puedes leer información de
diferentes sensores, así como controlar luces, motores y muchas otras cosas. La gran
mayoría de los sistemas que nos rodean son ordenadores de diferentes tamaños. Los
ordenadores no necesitan tener teclado ni pantalla. Hay ordenadores en el microondas de
la cocina, dentro de los ascensores para detectar qué botón pulsas y, en los coches. Hay
más de 70 ordenadores similares a Arduino, hay ordenadores por todas partes.

Página 5 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 4.- Placa de Arduino Mega 2560 ETH

Puesto que Arduino, a diferencia del ordenador que usas normalmente, no tiene pantalla ni
teclado, se necesita un programa externo ejecutado en otro ordenador para poder escribir
programas para la placa Arduino.

✓ Cable USB para Arduino

Las placas Arduino se conectan a tu ordenador utilizando un cable USB, al igual que
cualquier otro periférico, como la impresora, el teclado o incluso, un mando de videojuegos.
Arduino necesita estar conectado al ordenador a través del cable USB para cargar un
programa que realicemos previamente según lo que querramos hacer con la tarjeta. El cable
USB sirve también para suministrar energía a la placa, pero también puedes energizarla
usando una fuente de energía externa, como una batería o una fuente DC.

Figura 5.- Cable de comunicación USB

Página 6 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

MARCO TEÓRICO ORIENTADO AL SEMINARIO

El alumno deberá revisar ciertos conceptos puntuales que serán expuestos a continuación, se
recomienda hacer esto para un mejor entendimiento de lo que será expuesto en estos talleres.

Señales analógicas y digitales

Cuando un equipo electrónico nos muestra una información, puede hacerlo de forma analógica o
de forma digital.

Analógica quiere decir que la información, la señal, para pasar de un valor a otro pasa por todos los
valores intermedios, es continua.

La señal digital, en cambio, va “a saltos”, pasa de un valor al siguiente sin poder tomar valores
intermedios.

Figura 6.- Señal analógica y digital

Señales analógicas

La señal analógica es aquella que presenta una variación continua con el tiempo, es decir, que a
una variación suficientemente significativa del tiempo le corresponderá una variación igualmente
significativa del valor de la señal (la señal es continua).

Toda señal variable en el tiempo, por complicada que ésta sea, se representa en el ámbito de sus
valores (espectro) de frecuencia. De este modo, cualquier señal es susceptible de ser representada
descompuesta en su frecuencia fundamental y sus armónicos. El proceso matemático que permite
esta descomposición se denomina análisis de Fourier.

Un ejemplo de señal analógica es la generada por un usuario en el micrófono de su teléfono y que


después de sucesivos procesos, es recibida por otro abonado en el altavoz del suyo.

Figura 7.- Señal Analógica

Página 7 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Es preciso indicar que la señal analógica, es un sistema de comunicaciones de las mismas


características, mantiene dicho carácter y deberá ser reflejo de la generada por el usuario. Esta
necesaria circunstancia obliga a la utilización de canales lineales, es decir canales de comunicación
que no introduzcan deformación en la señal original.

Las señales analógicas predominan en nuestro entorno (variaciones de temperatura, presión,


velocidad, distancia, sonido etc.) y son transformadas en señales eléctricas, mediante el adecuado
transductor, para su tratamiento electrónico.

La utilización de señales analógicas en comunicaciones todavía se mantiene en la transmisión de


radio y televisión tanto privada como comercial. Los parámetros que definen un canal de
comunicaciones analógicas son el ancho de banda (diferencia entre la máxima y la mínima
frecuencia a transmitir) y su potencia media y de cresta.

Señales digitales

Una señal digital es aquella que presenta una variación discontinua con el tiempo y que sólo puede
tomar ciertos valores discretos. Su forma característica es ampliamente conocida: la señal básica
es una onda cuadrada (pulsos) y las representaciones se realizan en el dominio del tiempo.

Sus parámetros son:

✓ Altura de pulso (nivel eléctrico)


✓ Duración (ancho de pulso)
✓ Frecuencia de repetición (velocidad pulsos por segundo)

Las señales digitales no se producen en el mundo físico como tales, sino que son creadas por el
hombre y tiene una técnica particular de tratamiento, y como dijimos anteriormente, la señal básica
es una onda cuadrada, cuya representación se realiza necesariamente en el dominio del tiempo.

Figura 8.- Señal digital

La utilización de señales digitales para transmitir información se puede realizar de varios modos: el
primero, en función del número de estados distintos que pueda tener. Si son dos los estados
posibles, se dice que son binarias, si son tres, ternarias, si son cuatro, cuaternarias y así
sucesivamente. Los modos se representan por grupos de unos y de ceros, siendo, por tanto, lo que
se denomina el contenido lógico de información de la señal.

La segunda posibilidad es en cuanto a su naturaleza eléctrica. Una señal binaria se puede


representar como la variación de una amplitud (nivel eléctrico) respecto al tiempo (ancho del pulso).

Resumiendo, las señales digitales sólo pueden adquirir un número finito de estados diferentes, se
clasifican según el número de estados (binarias, ternarias, etc.) y según su naturaleza
eléctrica(unipolares y bipolares).

Página 8 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

PWM

Modulación por ancho de pulso, o PWM, es una técnica usada para obtener resultados análogos
con medios digitales. Control digital se utiliza para crear una onda cuadrada, una señal que conmuta
entre encendido y apagado. Este patrón de encendido y apagado puede simular tensiones entre
encendido (5 voltios) y apagado (0 Volts) cambiando la parte del tiempo que la señal está en ALTO
versus el tiempo que pasa la señal en BAJO. La duración de "señal en ALTO" se llama el “ancho
de pulso”. Para conseguir diferentes valores analógicos, se cambia o modula el ancho de pulso. Si
repite este patrón de encendido y apagado suficientemente rápido con un LED por ejemplo, el
resultado es como si la señal fuera una tensión constante entre 0 y 5v, controlando de esta manera
el brillo del LED.

En el siguiente gráfico, las líneas verdes representan un período de tiempo regular. Esta duración
o período es la inversa de la frecuencia PWM. En otras palabras, con frecuencia PWM de Arduino
en alrededor de 500 Hz, las líneas verdes medirían 2 milisegundos cada uno. Una llamada
a analogWrite () es en una escala de 0 a 255, de tal manera que analogWrite (255) solicita un ciclo
de trabajo del 100% (siempre encendido), y analogWrite (127) es un ciclo de trabajo del 50% (en la
mitad del tiempo) por ejemplo.

Figura 9.- Modulación por ancho de pulso.

Ejemplo de introducción: “Blink”

Antes de realizar las actividades propuestas, se comenzara exponiendo un pequeño ejemplo


improductivo al tema E/S analógicas y digitales, este simple ejemplo se pude encontrar en el mismo
Arduino IDE, así que simplemente lo que haremos es abrir el ejemplo, el cual tiene que siguiente
código.

// La función setup que solo se ejecutara una sola vez


void setup() {
// Declaramos el pin digital 13 como una salida

Página 9 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

pinMode(13, OUTPUT);
}
//La función loop se ejecutara de manera cíclica una y otra vez.
void loop() {
digitalWrite(13, HIGH); // Encendemos el LED (HIGH es el máximo nivel de
voltaje)
delay(1000); // Se mantendrá prendido por 1 segundo.
digitalWrite(13, LOW); // Apagamos el LED escribiendo en el pin LOW(mínimo
voltaje)
delay(1000); // Se mantendrá apagado por un segundo.
}

Actividad - Fading con un potenciómetro

Al leer el sensor, que en este caso es el potenciómetro, que estará conectada a la entrada análoga
A0, se obtiene un valor entre 0 a 1023, el cual variará conforme se esté girando la perilla. Este valor
será leído y normalizado hasta el máximo de 255 que es que el valor máximo que le podemos
escribir de forma analógica al LED, esto con la función analogWrite().

Nota: Los Pines que me ofrecen una salida PWM (modulación por ancho de pulso) tienen una
resolución de 8 bits (valores de 0 a 255) mediante la función analogWrite().

De la misma manera cada una de las entradas analógicas proporciona una resolución de 10 bits
(valores de 0 a 1023).

Materiales
En principio son los mismos que se usaron en la anterior ejercicio, agregando al circuito es un
potenciómetro.

✓ Led de cualquier color:

El LED (Light-Emitting Diode: Diodo Emisor de Luz), es un dispositivo semiconductor que


emite luz incoherente de espectro reducido cuando se polariza de forma directa la unión PN
en la cual circula por él una corriente eléctrica . Este fenómeno es una forma de
electroluminiscencia, el LED es un tipo especial de diodo que trabaja como un diodo común,
pero que al ser atravesado por la corriente eléctrica, emite luz. El voltaje de operación va
desde 1,8 hasta 3,8 voltios aproximadamente y la gama de intensidades que debe circular
por él varía según su aplicación.

Figura 10.- Diodo Led

Página 10 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

✓ Un potenciómetro

Un potenciómetro es un dispositivo que permite variar su resistencia de forma manual, entre


un valor mínimo Rmin, (normalmente 0 ohminos) y un valor máximo Rmax. Valores
habituales de Rmax son 5k, 10k o 20k ohmios.

Internamente un potenciómetro está constituido por un contacto móvil que se desplaza a lo


largo de una pista resistiva. De esta forma, al mover el potenciómetro movemos el contacto
a lo largo de la pista, y variando la longitud del tramo de pista con el que estamos en contacto,
y por tanto variando su resistencia.

Normalmente un potenciómetro tiene tres terminales. Los dos extremos están unidos a
ambos lados de la pista, por lo que siempre registrarán la resistencia máximo Rmax. El
terminal restante corresponde con el contacto móvil. Este terminal varía su resistencia
respecto a los otros dos terminales a medida que accionamos el potenciómetro, siendo la
suma de la resistencia a los otros terminales igual a Rmax.

Figura 11.- Terminales de un potenciómetro.

Respecto a la geometría, podemos encontrar potenciómetros de tipo lineal o rotativo.

Figura 12.- Geometría de un potenciómetro.

Por último, en cuanto a la relación entre posición y resistencia, encontramos potenciómetros de tipo
lineal, parabólico o exponencial. Los lineales presentan una proporcionalidad entre resistencia y
desplazamiento, lo cual significa un comportamiento más intuitivo. Mientras, los exponenciales
permiten mayor precisión en valores de resistencia bajos, por lo que resultan adecuados cuando
hace falta un ajuste fino en un amplio rango.

Página 11 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 13.- Grafico posición vs resistencia.

Se procede a conectar un LED a nuestra protoboard, tal como se puede apreciar en la figura 14.

Conectamos el catado del led al pin digital 9 de nuestro Arduino (es vital que sea conectado
únicamente al pin 9), no sin antes colarse una resistencia entre 220-470Ω tal como se puede
apreciar en la figura.

Seguidamente el ánodo del LED, será conectado a la tierra de nuestra placa Arduino (GND).

Ahora es momento de conectar nuestro potenciómetro de la manera en que se muestra en la figura.

Viendo el potenciómetro tal y como se encuentra dispuesto en la imagen, conectamos el extremo


izquierdo a los 5V de cual dispone nuestra placa Arduino, de la misma manera el extremo derecho
lo conectamos a la tierra (GND) de la misma.

Por último, lo que se procede a realizar es cargar nuestro código, el cual será detallado a
continuación.

Aclaración: Es importante que sea el pin 9 ya que es una salida analógica, aunque el Arduino Nano
cuenta con otros pines analógicos aparte del 3, estos son el 5, 6,9, 10 y 11, todos ellos proporcionar
una salida PWM de 8 bits con el comando analogWrite ().

Página 12 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 14.- Imagen del circuito a montar en el laboratorio.

Código

const int led = 9; //Cátodo del led conectado al pin digital 9.


int control = A0; //Potenciómetro conectado al pin digital analógico 0.
int poten;//Variable que guardara los valores del potenciómetro(0 a 1023).
int brillo = 0; //Variable para guardar los valores de brillo.

void setup() {
pinMode(led, OUTPUT); //Declaramos la variable led como una salida.

void loop() {
poten = analogRead(control); /*Leemos los valores que nos da el potenciómetro
al hacerlo variar.*/

brillo = map(poten, 0, 1023, 0, 255); /*Normalizamos los valores que recogemos


del potenciómetro que van desde 0 hasta 1023,a valores que van de 0 a 255,ya que
es el rango de valores que pueden ser escritos en una salida digital PWM*/

analogWrite(led, brillo); /*Escribimos en el led los valores ya normalizados


que estamos recogiendo del potenciómetro*/
}

Página 13 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Funciones

Una función es un conjunto ordenado de código que tiene un nombre y una determinada cantidad
de instrucciones que son ejecutadas cuando se llama a la función. Son funciones setup() y loop()
de las que ya se ha hablado.

Las funciones de usuario pueden ser escritas para realizar tareas repetitivas y para reducir el
tamaño de un programa. Segmentar el código en funciones permite crear piezas de código que
hacen una determinada tarea y volver al área del código desde la que han sido llamadas.

Las funciones se declaran asociadas a un tipo de valor. Este valor será el que devolverá la función,
por ejemplo ‘int’ se utilizará cuando la función devuelva un dato numérico de tipo entero. Si la función
no devuelve ningún valor entonces se colocará delante la palabra “void”, que significa “función
vacía”

Sintaxis:

tipo nombreFunción (parámetros) {

instrucciones;

Figura 15.- Estructura de una función

Para llamar a una función, simplemente colocaremos el nombre de la función y entre parentesis los
parámetros.

nombreFunción(parámetros);

En una función que devuelve un valor siempre debe tener la instrucción Return, este termina una
función y devuelve un valor a quien ha llamado a la función: http://arduino.cc/en/Reference/Return

Página 14 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Ventajas del uso de funciones:

✓ Ayuda a tener organizado el código.


✓ Una función codifica una tarea en un lugar de nuestro sketch, así que la función solo debe
ser pensada una sola vez.
✓ Reduce la probabilidad de errores al modificar el código.
✓ Hacen que el tamaño del sketch sea menor porque el código de la función es reutilizado.
✓ Facilita la lectura del código.
✓ Hace más sencillo reutilizar código en otros sketches.

Nombres de funciones

Generalmente los nombres de las funciones deben ser en minúscula, con las palabras separadas
por un guión bajo, aplicándose éstos tanto como sea necesario para mejorar la legibilidad.

“mixedCase” (primera palabra en minúscula) es aceptado únicamente en contextos en donde éste


es el estilo predominante con el objetivo de mantener la compatibilidad con versiones anteriores.

En el caso de las clases, los nombres deben utilizar la convención “CapWords” (palabras que
comienzan con mayúsculas).

Las funciones en Arduino pueden estar dentro del mismo fichero .ino o en otro fichero con extensión
.ino dentro del directorio del sketch.

Paso por Valor y Paso por Referencia

Hasta ahora siempre hemos declarado los parámetros de nuestras funciones del mismo modo. Sin
embargo, éste no es el único modo que existe para pasar parámetros.

La forma en que hemos declarado y pasado los parámetros de las funciones hasta ahora es la que
normalmente se conoce como «por valor». Esto quiere decir que cuando el control pasa a la función,
los valores de los parámetros en la llamada se copian a «objetos» locales de la función, estos
«objetos» son de hecho los propios parámetros.

int funcion(int n, int m) {


n = n + 2;
m = m - 5;
return n+m;
}

int a = 10;
int b = 20;
Serial.println(funcion(a,b));
Serial.println(funcion(10,20));

Empezamos haciendo a = 10 y b = 20, después llamamos a la función «funcion» con los objetos a
y b como parámetros. Dentro de «funcion» esos parámetros se llaman n y m, y sus valores son
modificados. Sin embargo al retornar al programa que lo llama, a y b conservan sus valores
originales. Lo que pasamos no son los objetos a y b, sino que copiamos sus valores a los objetos n
y m. Es lo mismo que hacer funcion(10,20), cuando llamamos a la función con parámetros
constantes. Si los parámetros por valor no funcionasen así, no sería posible llamar a una función
con valores constantes o literales.

Las referencias sirven para definir «alias» o nombres alternativos para un mismo objeto. Para ello
se usa el operador de referencia (&).

Página 15 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Por ejemplo:

int a;
int &r = a;
a = 10;
Serial.println(r);

En este ejemplo los identificadores a y r se refieren al mismo objeto, cualquier cambio en una de
ellos se produce en el otro, ya que son, de hecho, el mismo objeto. El compilador mantiene una
tabla en la que se hace corresponder una dirección de memoria para cada identificador de objeto.
A cada nuevo objeto declarado se le reserva un espacio de memoria y se almacena su dirección.
En el caso de las referencias, se omite ese paso, y se asigna la dirección de otro objeto que ya
existía previamente. De ese modo, podemos tener varios identificadores que hacen referencia al
mismo objeto, pero sin usar punteros.

Si queremos que los cambios realizados en los parámetros dentro de la función se conserven al
retornar de la llamada, deberemos pasarlos por referencia. Esto se hace declarando los parámetros
de la función como referencias a objetos. Por ejemplo:

int funcion(int &n, int &m) {


n = n + 2;
m = m - 5;
return n+m;
}

int a = 10;
int b = 20;

Serial.println(funcion(a,b));
Serial.println("a = " + String(a) + " b = " + String(b));
//es ilegal pasar constantes como parámetros cuando estos son referencias
Serial.println(funcion(10,20));

En este caso, los objetos «a» y «b» tendrán valores distintos después de llamar a la función.
Cualquier cambio de valor que realicemos en los parámetros dentro de la función, se hará también
en los objetos referenciadas. Esto quiere decir que no podremos llamar a la función con parámetros
constantes, ya que aunque es posible definir referencias a constantes, en este ejemplo, la función
tiene como parámetros referencias a objetos variables. Y si bien es posible hacer un casting implícito
de un objeto variable a uno constante, no es posible hacerlo en el sentido inverso. Un objeto
constante no puede tratarse como objeto variable.

Una const reference es una referencia que no permite cambiar la variable a través de esa referencia.
Por ejemplo const int &r = a; en r tengo el valor de a pero no puedo cambiar el valor de a usando r.

No confundir este concepto con el modificador de variable static, que es utilizado para crear
variables que solo son visibles dentro de una función, sin embargo, al contrario que las variables
locales que se crean y destruyen cada vez que se llama a la función, las variables estáticas
mantienen sus valores entre las llamadas a las funciones.

Página 16 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Librerías
Se emplea el término librería para referirse a una biblioteca, por la similitud con el original inglés
library. Ambos términos, biblioteca y librería, son correctos según las definiciones de la RAE, aunque
en términos formales, la acepción correcta es biblioteca, porque es la traducción correcta de library.

Independientemente de lo anterior comentado, una biblioteca es un Kit de herramientas software


pequeño y autónomo que ofrece una funcionalidad muy específica al usuario. Normalmente se usa
junto con otras librerías y herramientas para hacer una aplicación completa, ya que por lo general
las bibliotecas no son ejecutables, pero sí pueden ser usadas por ejecutables que las necesiten
para poder funcionar.

Imaginemos que estamos haciendo programas de ordenador, nos damos cuenta que algunas partes
del código se utilizan en muchos de ellos. Por ejemplo, podemos tener varios programas que utilizan
números complejos y las funciones de suma, resta, etc son comunes. También es posible, por
ejemplo, que nos guste hacer juegos, y nos damos cuenta que estamos repitiendo una y otra vez el
código para mover una imagen por la pantalla. Sería estupendo poder meter esas funciones en un
directorio separado de los programas concretos y tenerlas ya compiladas, de forma que podamos
usarlas siempre que queramos.

Las ventajas enormes de esto son:

✓ No tener que volver a escribir el código (o hacer copy-paste).


✓ Nos ahorraremos el tiempo de compilar cada vez ese código que ya está compilado.
Además, ya sabemos que mientras hacemos un programa, probamos y corregimos, hay
que compilar entre muchas y "más muchas" veces.
✓ El código ya compilado estará probado y será fiable. No las primeras veces, pero sí
cuando ya lo hayamos usado en 200 programas distintos y le hayamos ido corrigiendo
los errores.

La forma de hacer esto es hacer librerías. Ya que hemos quedado que una librería son una o más
funciones que tenemos ya compiladas y preparadas para ser utilizadas en cualquier programa que
hagamos.

Existen dos tipos de librerías:

✓ Librerías estáticas: Es una librería que "se copia" en nuestro programa cuando lo
compilamos. Una vez que tenemos el ejecutable de nuestro programa, la librería no sirve
para nada (es un decir, sirve para otros futuros proyectos). Podríamos borrarla y nuestro
programa seguiría funcionando, ya que tiene copia de todo lo que necesita. Sólo se copia
aquella parte de la librería que se necesite. Por ejemplo, si la librería tiene dos funciones y
nuestro programa sólo llama a una, sólo se copia esa función.

✓ Librerías dinámica: No se copia en nuestro programa al compilarlo. Cuando tengamos


nuestro ejecutable y lo estemos ejecutando, cada vez que el código necesite algo de la
librería, irá a buscarlo a ésta. Si borramos la librería, nuestro programa dará un error de que
no la encuentra. Windows está construido sobre una gran cantidad de DLL's, y es que
Windows guarda sus librerías de enlace dinámico en archivos que tienen extensión DLL.

Toda librería ofrecerá un Interfaz de programación de aplicaciones (API) que es el conjunto de


métodos que ofrece cierta biblioteca para ser utilizado por otro software como una capa de
abstracción.

Página 17 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Actividad – Nuestra Librería

¿Cómo escribir una librería para Arduino?

Se comienza con un programa que realiza, mediante el encendido y apagado de un led, el código
morse y se explica cómo convertir este en una función de librería. Esto permite a otras personas
utilizar fácilmente el código que has escrito cargándolo de una forma sencilla.

Se comienza con el programa de un sencillo código Morse: La palabra a generar es SOS (. . . - - - .


. . ).

// Genera SOS en código Morse luminoso

int pin = 13;

void setup()
{
pinMode(pin, OUTPUT);
}

void loop() //Programa principal que genera '. . .', '- - -' y '. . .'
{
dot(); dot(); dot(); //Genera la S (. . .)
dash(); dash(); dash(); // Genera la O (- - -)
dot(); dot(); dot(); // Genera la S (. . .)
delay(3000); //Espera un tiempo
}

void dot() //Procedimiento para generar un punto


{
digitalWrite(pin, HIGH);
delay(250);
digitalWrite(pin, LOW);
delay(250);
}

void dash() //Procedimiento para generar una raya


{
digitalWrite(pin, HIGH);
delay(1000);
digitalWrite(pin, LOW);
delay(250);
}

Si se ejecuta este programa, se ejecuta el código SOS (llamada de solicitud de auxilio) en el pin 13.
El programa tiene distintas partes que tendremos que poner en nuestra librería. En primer lugar, por
supuesto, tenemos las funciones dot() (punto) y dash() (raya) que se encargar de que el led
parpadee de manera corta o larga respectivamente. En segundo lugar, tenemos la línea ledPin que
utilizamos para determinar el pin a utilizar. Por último, está la llamada a la función pinMode() que
inicializa el pin como salida.

Vamos a empezar a convertir el programa en una librería.

Necesitas por lo menos dos archivos en una librería: un archivo de cabecera (con la extensión ".h")
y el archivo fuente (con la extensión ".cpp"). El fichero de cabecera tiene definiciones para la librería:
básicamente una lista de todo lo que contiene, mientras que el archivo fuente tiene el código real.
Vamos a llamar a nuestra biblioteca "Morse", por lo que nuestro fichero de cabecera se llamará

Página 18 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Morse.h. Echemos un vistazo a lo que sucede en ella. Puede parecer un poco extraño al principio,
pero lo entenderá una vez que vea el archivo de origen que va con ella.
El núcleo del archivo de cabecera consiste en una línea para cada función en la biblioteca, envuelto
en una clase junto con las variables que usted necesita:

class Morse
{
public: Morse(int pin);
void dot();
void dash();
private:
int _pin;
};

Una clase es simplemente una colección de funciones y variables que se mantienen unidos todos
en un solo lugar. Estas funciones y variables pueden ser públicos, lo que significa que puede ser
utilizadas por quienes utilizan la librería, o privadas, lo que significa que sólo se puede acceder
desde dentro de la propia clase. Cada clase tiene una función especial conocida como
un constructor, que se utiliza para crear una instancia de la clase. El constructor tiene el mismo
nombre que la clase, y no devuelve nada.
Usted necesita dos cosas más en el fichero de cabecera. Uno de ellos es un #include, declaración
que le da acceso a los tipos estándar y las constantes del lenguaje de Arduino (esto se añade
automáticamente en todos los programas que hacemos con Arduino, pero no a las librerías), por lo
que debemos incluirlas (poniéndolas por encima de la definición de clase dada anteriormente):

#include <Arduino.h> //Permite utilizar los comandos de Arduino

Por último, se colocará delante del código la cabecera siguiente:

#ifndef Morse_h
#define Morse_h
// el estamento #include y el resto del código va aquí
#endif

Básicamente, esto evita problemas si alguien accidentalmente pone #include en la librería dos
veces.

Por último, por lo general, se pone un comentario en la parte superior de la librería con su nombre,
una breve descripción de lo que hace, quien la escribió, la fecha y la licencia.

Echemos un vistazo a la cabecera completa y disposición del fichero de cabecera h:

Fichero Morse.h

#ifndef Morse_h
#define Morse_h
#include <Arduino.h> //Permite utilizar los comandos de Arduino

class Morse
{
public: Morse(int pin); void dot();
void dash();
private:
int _pin;
};

#endif

Página 19 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Ahora vamos a escribir las diversas partes del archivo fuente de la librería, Morse.cpp.
Primero se ponen un par de declaraciones mediante #include. Estas incluyen el resto del código de
acceso a las funciones estándar de Arduino, ya que en las definiciones figuran en el archivo de
cabecera:

#include <Arduino.h> //Permite utilizar los comandos de Arduino


#include "Morse.h"

Luego viene el constructor. Ahora se indicará lo que debería suceder cuando alguien crea una
instancia a la clase. En este caso, el usuario especifica el pin que les gustaría utilizar. Configuramos
el pin como salida guardarlo en una variable privada para su uso en las otras funciones:

Morse::Morse(int pin)
{
pinMode(pin, OUTPUT);
_pin = pin;
}

Hay un par de cosas extrañas en este código. El primero es el Morse:: antes del nombre de la
función. Esto indica que la función es parte de la clase Morse. Verá este de nuevo en las otras
funciones en la clase. La segunda cosa inusual es el guión bajo en el nombre de nuestra variable
privada, _pin. Esta variable puede tener cualquier nombre que desee, siempre y cuando coincida
con la definición que figura en el fichero de cabecera. La adición de un guión bajo al comienzo del
nombre es una convención para dejar claro que las variables son privadas, y también a distinguir el
nombre de la del argumento a la función (pin en este caso).
Después viene el código del programa que queremos convertir en una función (¡por fin!). Parece
casi igual, excepto con Morse:: delante de los nombres de las funciones, y _pin en lugar de pin:

void Morse::dot()
{
digitalWrite(_pin, HIGH); delay(250);
digitalWrite(_pin, LOW); delay(250);
}

void Morse::dash()
{
digitalWrite(_pin, HIGH); delay(1000);
digitalWrite(_pin, LOW); delay(250);
}

Por último, es típico incluir el comentario de cabecera en la parte superior de la fuente así como el
archivo. Vamos a ver el fichero completo:
6

Fichero Morse.cpp
/*
Morse.cpp - Library for flashing Morse code. Created by David A. Mellis,
November 2, 2007. Released into the public domain.
*/

#include <Arduino.h> //Permite utilizar los comandos de Arduino


#include "Morse.h"

Página 20 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Morse::Morse(int pin)
{
pinMode(pin, OUTPUT);
_pin = pin;
}

void Morse::dot()
{
digitalWrite(_pin, HIGH); delay(250);
digitalWrite(_pin, LOW); delay(250);
}

void Morse::dash()
{
digitalWrite(_pin, HIGH); delay(1000);
digitalWrite(_pin, LOW); delay(250);
}

Y eso es todo lo que necesita (hay algunas otras cosas opcionales, pero vamos a hablar de eso
más adelante).

Ahora vamos a ver cómo se utiliza la librería.

En primer lugar, debemos crear una carpeta llamada Morse dentro del subdirectorio libraries de la
aplicación Arduino. Copiar o mover los archivos Morse.h y Morse.cpp en esa carpeta. Ahora lanzar
la aplicación Arduino. Si abres el menú Sketch> Import Library, deberás ver el objeto Morse. Si
realizas alguna modificación en la librería, deberás reiniciar el entorno de Arduino para así
recompilarla. Si aparece algún fallo relacionado con la compilación de la biblioteca, asegúrese de
que están realmente los archivos .cpp y .h (sin extensión adicional .pde o .txt, por ejemplo).
Veamos cómo podemos escribir nuestro nuevo programa SOS haciendo uso de la nueva librería:

Programa para Arduino

#include <Morse.h>

Morse morse(13);

void setup() {}

void loop()
{
morse.dot(); morse.dot(); morse.dot();
morse.dash(); morse.dash(); morse.dash();
morse.dot(); morse.dot(); morse.dot();
delay(3000);
}

Hay algunas diferencias con respecto al antiguo programa (además del hecho de que algunos de
los códigos se han incorporado a la librería).

En primer lugar, hemos añadido un estamento #include en la parte superior del programa. Esto
hace que la librería Morse quede a disposición del programa y la incluya en el código. Esto significa
que ya no necesitan una librería en el programa, usted debe borrar el # include para ahorrar espacio.
En segundo lugar, nosotros ahora podemos crear una instancia de la clase Morse llamado morse:
Morse morse(13);

Página 21 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Cuando esta línea se ejecuta (que en realidad sucede antes incluso de setup()), el constructor de
la clase Morse será invocado y le pasara el argumento que se ha dado aquí (en este caso, sólo 13).
Tenga en cuenta que nuestra parte setup() del programa está vacía, porque la llamada a
pinMode() se lleva a cabo en el interior de la librería (cuando la instancia se construye).
Por último, para llamar a las funciones punto dot() y raya dash(), es necesario colocar el
prefijo morse delante de la instancia que queremos usar. Podríamos tener varias instancias de la
clase Morse, cada uno en su propio pin almacenados en la variable privada_pin de esa instancia.
Al llamar a una función en un caso particular, especificaremos qué variables del ejemplo debe
utilizarse durante esa llamada a una función. Es decir, si hemos escrito:

Morse morse(13);
Morse morse2(12);

Entonces dentro de una llamada a morse2.dot(), _pin sería 12.

Si ha escrito el nuevo programa, probablemente se habrá dado cuenta de que ninguna de nuestras
funciones de la librería fue reconocida por el entorno de Arduino destacando su color. Por desgracia,
el software de Arduino no puede averiguar automáticamente lo que se ha definido en su librería (a
pesar de que sería una característica interesante), por lo que tiene que darle un poco de ayuda.
Para hacer esto, cree un archivo llamado keywords.txt en el directorio Morse. Debe tener este
aspecto:

Morse KEYWORD1
Dash KEYWORD2
Dot KEYWORD2

Cada línea tiene el nombre de la palabra clave, seguida de un tabulador (sin espacios), seguido por
el tipo de palabra clave. Las clases deben ser KEYWORD1 y son de color naranja; las funciones
deben ser KEYWORD2 y serán de color marrón. Tendrás que reiniciar el entorno Arduino para
conseguir reconocer las nuevas palabras clave.

Es interesante que quienes utilicen la librería Morse tengan algún ejemplo guardado y que aparezca
en el IDE de Arduino cuando seleccionamos dentro de la carpeta ejemplos (Sketch). Para hacer
esto, se crea una carpeta de ejemplos dentro de la carpeta que contiene la librería Morse. A
continuación, movemos o copiamos el directorio que contiene el programa (lo llamaremos SOS)
que hemos escrito anteriormente en el directorio de ejemplos. Si reiniciamos el entorno de Arduino
veremos un elemento Library_Morse dentro del menú Archivo → Ejemplo que contiene su
ejemplo. Es posible que desee añadir algunos comentarios que explicar mejor cómo utilizar la
biblioteca.

Página 22 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Comunicación Serial

Un puerto Serial es un modulo de comunicación digital para un sistema embebido. Es decir, permite
la comunicación entre dos dispositivos digitales. Cuenta con dos conexiones, RX y TX. Lo que nos
indica los modos de comunicación que puede manejar, Full-duplex, Duplex y Simplex. Además
podemos considerar como su principal ventaja a la sencillez de su protocolo de comunicación. Sin
embargo también tiene desventajas como que sólo se puede comunicar a un puerto dos
dispositivos.

Full duplex. Significa que puede recibir y enviar información digital simultáneamente.

Duplex o Half-duplex. Es cuando sólo podemos transmitir o recibir información, una cosa a la vez.

Simplex. Cuando sólo podemos ya sea recibir o transmitir.

La función principal de un puerto serial, es la de empacar y des-empacar paquetes de datos binarios


seriales. Como resultado, la serialización significa convertir un dato paralelo (byte) a un conjunto de
pulsos seriales que puedan ser recibidos y enviados por una línea de transmisión. En primer lugar,
el protocolo serial opera mediante tres condiciones digitales básicas: inicio de transmisión (IT),
paridad (P) y fin de transmisión (FT). Estas condiciones son sincronizadas mediante un oscilador
interno. El generador permite controlar la velocidad del puerto serial. Por lo tanto, la velocidad se
mide en BAUD ‘s. Al modulo serial también se le conoce como UART ó USART o EUSART.

▪ UART – Universal Asyncronos Receiver and Transmitter que en español se traduciría como
Transceptor Asíncrono.
▪ USART – Universal Syncronos and Asyncronos Receiver and Transmitter, que significa en
español Transceptor Síncrono y Asíncrono.
▪ EUART – Enhanced Universal Asyncronos Receiver and Transmitter ó
Transceptor Asíncrono Universal Mejorado.

Para configurar al modulo se requiere indicar la velocidad de operación. Los BAUDios que es una
medida de cuantos bits por segundo se van a transmitir, se configuran mediante un registro de
propósito específico. Dependiendo del lenguaje de programación la configuración puede ser
relativamente sencilla. En el caso de Arduino se haría con la instrucción Serial.begin(9600).
También es necesario configurar cuantos bits de parada y si habrá o no bit de paridad. Una de las
configuraciones más usadas para un puerto serial es:

▪ 8 bits de datos
▪ 1 bit de parada
▪ Sin bit de paridad
▪ 1 bit de inicio
▪ Velocidad de 9600 BAUD

Para que pueda haber una sincronización de los datos enviados, se requiere que ambos dispositivos
que usen el mismo puerto serial, tengan la misma configuración.

Funciones de Arduino para el puerto Serial

▪ Función Serial print


▪ Serial read

Página 23 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

▪ Para iniciarlizar Serial begin

Modos de comunicación en el puerto serial

El modo de comunicación para un puerto serial,se refiere a la forma en la que se envían y reciben
los paquetes de información. De acuerdo al tipo de conexión, una UART tiene separadas las lineas
de transmisión y recepción. Esta característica le permite poder operar los tres modos de
comunicación asíncrona que existen. Los modos de comunicación son los siguientes:

▪ Full-duplex. Significa que puede transmitir y recibir simultáneamente.


▪ Half-duplex. O sólo transmite o sólo recibe.
▪ Simplex. Sólo se dedica a transmitir información binaria.

Cuando se diseña una aplicación que requiere comunicación serial, al inicio, se suelen cometer
algunos errores básicos. Dentro de los esquemas de comunicación se utiliza al dispositivo serial en
modo simplex, sólo enviando información. Lo recomendable es usar el esquema de comunicación
Half-duplex, en donde, solo se envíe información si así lo pide uno de los elementos en la
comunicación.

Tipos de conexiones o arreglos del puerto serial

Cuando un puerto serial, opera o trabaja a un voltaje lógico distinto del de nuestro sistema embebido
se requieren hacer ciertas modificaciones al circuito. La figura 16, muestra tres tipos de conexiones
para un puerto de comunicación digital. En el elemento 1, estaríamos comunicando a dos sistemas
con el mismo voltaje lógico. Mientras que para el elemento 2 se considera que uno de los
dispositivos trabaja a un voltaje distinto, por lo que requiere de una etapa intermedia que ajuste a
los voltajes lógicos. Esta etapa intermedia puede ser un elevador de voltaje o level shiffter. En el
caso 3, de la figura 16 se observa como sería la comunicación serial con una computadora.

Las computadoras, tanto de escritorio como laptops, ya no cuenta con puertos de comunicación
serial. Para lograr comunicar un sistema embebido serial con una computadora, se requiere de un
elemento adicional. Este elemento electrónico se le conoce como convertidor USB-TTL. El
convertidor esta programado para convertir el protocolo de comunicación serial al protocolo de
comunicación USB. En este caso la computadora reconoce a dicho circuito como un puerto Serial
Virtual. Por lo tanto, para los sistemas operativos de Windows se le asigna un nombre que comienza
con la palabra COM seguida de un numero. Mientras tanto, Linux se utilizan las letras TTYACM#
o TTYUSB# donde el # es un numero que se va asignando consecutivamente a la conexión de los
dispositivos.

Página 24 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 16.- Tipos de conexiones seriales

En la figura 16 se puede apreciar los tipos de conexiones seriales. 1 – Dos dispositivos seriales con
el mismo voltaje lógico. 2 – Distintos voltajes lógicos. 3 – Comunicación serial con una computadora
mediante una tarjeta de conversión de protocolo serial a protocolo USB.

Protocolo Serial y sus tramas de comunicación

El protocolo serial se refiere a la forma o a la cantidad de bits que forma un paquete de datos. En
este caso el “dato” es la información que queremos transmitir por el puerto serial. Como resultado,
la trama de datos o bits digitales necesarios para transmitir un byte de información pueden variar.
Esencialmente se tienen que agregar tres tipos de bits al byte de información. Un bit de inicio, un
bit de paridad y uno o dos bits de parada. Por ejemplo, se configura el puerto serial a una velocidad
de 9600 BAUD, 8 bits de datos, 1 bit de parada y sin bit de paridad. Para este ejemplo la trama de
datos seria:

Paquete de datos = Bit de inicio + 8 bits de datos + 1 bit de parada

Es decir, que esta configuración envía 10 bits para cada 8 que se quieran transmitir. Si la velocidad
es 9600 bits/s, da como resultado una tasa real de 960Bytes por segundo, dado que cada byte tiene
agregados dos bits por parte del protocolo serial.

Todas las tarjetas arduino se programan empleando este puerto de comunicación, modelos como
el UNO, Nano y Leonardo solo tienen un puerto de comunicación serial que es el mismo que se

Página 25 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

emplean para subirle el código, es importante tener en cuenta esto en caso se requiera usar este
puerto para comunicar la terjeta Arduino con algún otro dispositivo empleando este protocolo de
comunicación, si queremos hacer esto debemos energizar la tarjeta por los pines o el jack de
alimentación de la tarjeta y desconectar el cable de programación, esto debido a que la
comunicación serial es punto a punto como ya se ha mencionado previamente y de este modo
evitamos posibles pérdidas de datos o errores en la transmisión de información. Otras tarjetas
cuentan con más de un puerto de comunicación serial, por lo que podríamos conectar varios
dispotivos que empleen comunicación serial dependiendo del número del número de puertos
disponibles por harwdare de la tarjeta; cabe mencionar que podemos implementar por software en
pines digitales el protocolo de comunicación serial empleando la librería SoftwareSerial, esta librería
viene por defecto en el software de Arduino por lo que no es necesario descargar ninguna librería
adicional, incluso hay dos ejemplos empleando esta librería que podemos usar de guía, para poder
verlos nos dirigimos a Archivo →Ejemplos → SoftwareSerial.

Figura 17.- IDE arduino en donde encontramos los ejemlos

Hay modelos más compactos como el arduino Promini que esta oriendato para aplicaciones en
donde no se cuenta con mucho espacio, y por tal motivo su diseño con la finalidad de ser más
compacto no trae el chip encargado de la comunicación serial por lo cual si deseamos cargarle el
código debemos emplear un grabador o módulo de comunicación serial, a continuación semuestran
algunos modelos de estos módulos.

Página 26 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 18.- Modelos de Módulos USB-Serial-TTL

Para configurar el puerto serial debemos iniciarlizar el respectivo módulo en el setup como se
muestra a continuación:

void setup() {
Serial.begin(9600);
}

Luego si deseamos imprimir un texto fijo lo hacemos con el comando print y entre comillas dobles
el texto que deseamos mostrar, en caso queramos imprimir una variable simplemente la colocamos
dentro de los paréntesis.
void loop(){
Serial.print("Hello");
}

En cuanto a la lectura se emplea el comando read, en el ejemplo que se muestra a continuación se


guarda el dato en una variable del tipo char.
void loop(){
char a = Serial.read();

Página 27 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Es una buena practica imprimir por el puerto serial valores de variables o textos en determinadas
partes del código para poder ir monitoreando el funcionamiento del programa y poder corregir
errores de ser necesarios, ya que el mismo software de proteus incorpora un monitor serial mediante
el cual podemos enviar y leer los datos de nuestra tarjeta dependiendo del código de programación
subido o grabado previamente, para acceder a este debemos ir a Herramientas → Monitor Serie
como se muestra a continuación:

Figura 19.- Forma de abrir el Monitor Serie

Luego debemos seleccionar la velocidad con la que hayamos inicializado el puerto de comunicación
principal de la tarjeta con la estemos trabajando.

Figura 20.- Monitor Serie

Página 28 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Motores

El motor eléctrico es un dispositivo que transforma la energía eléctrica en energía mecánica por
medio de la acción de los campos magnéticos generados en sus bobinas. Son máquinas eléctricas
rotatorias compuestas por un estator y un rotor.

Motores de corriente continúa

El motor de corriente continua (denominado también motor de corriente directa, motor CC o motor
DC) es una máquina que convierte la energía eléctrica en mecánica, provocando un movimiento
rotatorio, gracias a la acción que se genera del campo magnético.

Una máquina de corriente continua (generador o motor) se compone principalmente de dos partes:

✓ El estator o parte inmóvil que por regla general incluye o bien imanes potentes fijos o
generan un campo variable mediante corriente alterna (Lo que nos llevaría a construir un
motor de corriente alterna claro), además da soporte mecánico al aparato y contiene los
devanados principales de la máquina, conocidos también con el nombre de polos, que
pueden ser de imanes permanentes o devanados con hilo de cobre sobre un núcleo de
hierro.

✓ El rotor, en el que disponemos espiras o arrollamientos de hilos de cobre alrededor de un


núcleo, para que la fuerza que se ejerce sobre el rotor se multiplique proporcionalmente a
este número, es generalmente de forma cilíndrica, alimentado con corriente directa
mediante escobillas (conocidas también como carbones).

Hay una relación muy estrecha entre la corriente eléctrica y los campos que definen las ecuaciones
de Maxwell y resulta que cuando hacemos circular una corriente por un conductor que está inmerso
en un campo magnético, este se ve sometido a una fuerza mecánica, que llamamos electromotriz
y que podemos usar como principio básico de funcionamiento de un motor eléctrico.

Figura 20.- Rotor de motor de corriente continua.

Página 29 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 21. Partes de un motor de corriente continua.

Actividad

Para esta actividad lo que haremos es controlar la velocidad de motor de corriente continua, para
esto haremos uso de un potenciómetro que hará la vez de control de velocidad del motor, aunque
es un ejercicio sencillo y que luego podrán relacionar con salida PWM, podría tener un papel
fundamental en algún proyecto.

Materiales

Motor de corriente continúa

Figura 22.- Motor de corriente continua.

Especificaciones:

✓ Conmutación de modelo: RF-300F-12350

✓ Corriente continua: 22mA

✓ Características protegidas: Totalmente Cerrados.

✓ Construcción: Imán Permanente

✓ Velocidad: 3500 r/min

✓ Voltaje: 5.9 V

Página 30 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Se procede hacer el montado de nuestro circuito teniendo de referencia la figura 23.

Recordamos conectar el potenciómetro siguiendo la imagen, el pin del lado derecho será conectado
a tierra, el pin de lado derecho a 5V y el pin de en medio lo conectamos al pin analógico A0 de
nuestra placa Arduino.

Con respecto al motor conectamos el ánodo a la tierra de nuestro Arduino y el cátodo será
conectado a la pin digital 9, la cual recordemos es un pin que me ofrece una salida PWM.

Figura 23. Montado del circuito para la actividad 1.

Código

const int motor=9;/*Declaramos la variable motor, conectamos el cátodo del


motor al pin digital 9*/
int control=A0;/*Declaramos la variable control, conectamos el pin del
medio del potenciómetro al pin analógico 0*/
int velocidad;//Declaramos la variable velocidad
int v;//Declaramos la variable velocidad

void setup()
{
pinMode(motor,OUTPUT);//Declaramos en pin 9 como salida.
}

void loop()
{
v=analogRead(control);//Leemos los valores del potenciómetro.
velocidad=map(v,0,1023,30 ,255);
analogWrite(motor,velocidad);

Para esta segunda parte, haremos algo similar que en el anterior, pero esta vez ya no se trata del
control de un motor de DC, esta vez se trabajara con un servomotor. Para esto, desarrollaremos un
marco teórico de un servomotor.

Página 31 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

¿Qué es un servomotor?

Normalmente los motores habituales lo que hacen es transformar la energía eléctrica (o química)
en un giro continuo que podemos usar para desarrollar trabajo mecánico.
Los servos son también motores de corriente continua, pero en lugar de diseñarse para obtener un
giro continuo que podamos aprovechar (para mover una rueda por ejemplo), se diseñan para que
se muevan un ángulo fijo en respuesta a una señal de control, y se mantengan fijos en esa posición.
Imaginemos por ejemplo un timón de un avión o barco. No queremos un giro continuo, sino un motor
al que le pueda indicar el ángulo que deseamos en grados y que mantenga esa orientación hasta
que le demos una orden en contrario.
Estos servos o servomotores son empleados frecuentemente en aeromodelismo y en robótica, por
la capacidad que presentan para moverse a un ángulo concreto y mantenerse allí. De hecho se
suelen diseñar para que giren un ángulo proporcional a una señal PWM, de forma que su control
es muy preciso. Un servo suele estar formado por:

✓ Una reductora. Un circuito de control.


✓ Un motor de CC.
✓ Un circuito de control

Figura 24.- Equivalencia de un servomotor.

En la práctica se comporta como un bloque funcional que posiciona su eje en un ángulo preciso en
función de la señal de control.
Habitualmente los servos tiene un margen de operación, es decir, pueden moverse entre 0º y ángulo
dado, que suele ser de 180º, pero existen modelos comerciales de todas la características
imaginables (incluyendo servos de 360º).
Normalmente estos pequeños servos funcionan sobre 5V y el control se realiza mediante una señal
de control PWM, en la que el ancho de pulso indica el ángulo que deseamos adopte el eje.
Un servo tiene un conector de 3 hilos, 5V (rojo), GND (negro o marrón) y el otro Control (amarillo o
blanco).
Nosotros podemos escribir un pequeño programa en Arduino que controle estos pulsos y los
relacione con el ángulo buscado, pero no hay porque alarmarse, los servos (y otras cosas) son tan
comunes, que hay personas que ya han escrito estos tipos de programas
y los han puesto a nuestra disposición.
De este modo podemos manejar un servo sin preocuparnos para nada de cómo realizar el control
de las señales, o de la operación interna, basta con usar las librería del mismo.
La ventaja de trabajar con una plataforma tan bien establecida como Arduino, es que hay cantidad

Página 32 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

de gente en el mundo desarrollando librerías, casi para cualquier cosa que puedas imaginar.

Se procede a realizar el montado del circuito tal como se aprecia en la figura 25.

Con respecto a nuestro servo, este tiene a disposición tres cables expuesto al usuario, el cable
negro se conectara a tierra, cable rojo se conectara a 5V y por último el amarillo se conectara al pin
digital D9 de nuestra placa Arduino.

Finalmente procedemos a cargar nuestras líneas de código, el cual será expuesto a continuación.

Figura 25.- Rotor de motor de corriente continua.

Código

#include<Servo.h>
Servo servo1;
int angulo = 0;

void setup()
{
servo1.attach(9);
}

void loop()
{
servo1.write(0);
delay(1000);
servo1.write(30);
delay(1000);
servo1.write(60);
delay(1000);
servo1.write(90);
delay(1000);

Página 33 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Para el siguiente ejercicio nos guiaremos del circuito tal como se aprecia en Fig.26

Recordemos que el pin izquierdo del potenciómetro se conecta a 5V, el pin derecho se conecta a
tierra, y por último el pin del centro se conecta al pin analógico A0 de nuestra placa Arduino.

Con respecto a nuestro servo, este tiene a disposición tres cables expuesto al usuario, el cable
negro se conectara a tierra, cable rojo se conectara a 5V y por último el amarillo se conectara al pin
digital D9 de nuestra placa Arduino.

Finalmente procedemos a cargar nuestras líneas de código, el cual será expuesto a continuación.

Figura 26.- Montado del circuito

Código

#include<Servo.h>
Servo servo1;
int angulo = 0;
int poten = 0;
int grados = 0;

void setup()
{
servo1.attach(9);
}

void loop()
{
poten = analogRead(A0);
grados = map(poten, 0, 1023, 0, 180);
servo1.write(grados);
}

Página 34 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Pantallas LCD1602

Los LCD’s tienen una interfaz paralela, lo que significa que el microcontrolador tiene que manipular
varios pines de interfaz a la vez para controlar la visualización. La interfaz consta de los siguientes
pines:

RS: Selección de Registro.


0 lógico: Registro de comandos (escritura),
1 lógico: Registro de datos (escritura, lectura)

R/W:
0 lógico: Escritura del LCD.
1 Lógico: Lectura del LCD.

Enable: El famoso Enable de casi todos los componentes de la electrónica digital. Un 1 lógico
señala el inicio de escritura o lectura del LCD, un 0 lógico, desactiva todas las funciones.

D0/D7: Pines correspondientes al bus de datos.

Ánodo de la retroiluminación : R + 5V.


Cátodo de la retroiluminación: GND.

También hay un pin para el contraste de la pantalla, pines de alimentación (+5V y


GND) y retroiluminación LED ( A y K ) pines que se puede utilizar para alimentar la pantalla LCD,
controlar el contraste de la pantalla, y encender y apagar el LED luz de fondo, respectivamente.

El proceso de control de la pantalla consiste en colocar los datos que forman la imagen de lo que
desea mostrar en los registros de datos, a continuación, poniendo instrucciones en el registro de
instrucción. La Biblioteca LiquidCrystal simplifica esto para usted para que usted no necesita saber
las instrucciones de bajo nivel.

Los compatibles-Hitachi LCD’s pueden ser controlados en dos modos: 4 bits o 8 bits. El modo de 4
bits requiere siete pines E / S desde el Arduino, mientras que el modo de 8 bits requiere 11
pines. Para mostrar texto en la pantalla, se puede hacer casi todo en el modo de 4 bits, de modo
ejemplo muestra cómo controlar un LCD de 2x16 en el modo de 4 bits.

Figura 27.- Salida del boceto en una pantalla LCD de 2x16

Página 35 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

✓ Se procede con el armado del circuito, siguiendo como guía la figura 28

✓ Seguidamente se procede a cargar el código, es cual será expuesto a continuación.

Figura 28.- Montado del circuito para el ejemplo introductorio

Código

// Incluimos la librería "LiquidCrystal777”:/


#include <LiquidCrystal.h>

// Inicializamos la biblioteca con los números de los pines de interfaz.


LiquidCrystal lcd (12, 11, 5, 4, 3, 2);

void setup() {
// Establecemos el número de columnas y filas que posee nuestra pantalla.
lcd.begin(16, 2);
// Imprimimos un mensaje a la pantalla LCD.
lcd.print("hello, world!");
}

void loop() {
// Establecemos el cursor a la columna 0, la línea 1.
// (Nota: la línea 1 es la segunda fila, ya que el recuento comienza con 0):
lcd.setCursor(0, 1);
// Imprimimos el número de segundo desde reinicio.
lcd.print(millis() / 1000);
}

Página 36 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Existen módulos de comunicación I2C que se pueden acoplar a este tipo de pantallas para
controlarlas emplenado este bus de datos, los pines de comunicación del I2C que veremos más
adelante se encuentran en lo siguientes pines como se muestra en la siguiente imagen:

Figura 29.- Disposición de pines y conexión de móludo I2C con pantalla L01602 y arduino

De este modo podemos ahorrar pines de nuestra tarjeta para pode conectar algún otro módulo,
sensor o lo que deseemos.

El propio sofware de Arduino cuenta con una librería para poder controlar este tipo de pantallas
conectadas a éstos módulos, permitiendo tanto una fácil conexíon y programación lo cual se
explicará en el desarrollo de los talleres de programación; para ello nos dirigimos a Archivo
→ejemplos →LiquisCrystalI2C y luego nos mostrará 3 ejemplos disponibles que podemos probar
con nuestras pantallas con comunicación I2C, de este modo podemos ahorrar tiempo y pines que
nos pueden ser útiles para conectar algún otro módulo de entrada o salida según como lo
configuremos respectivamente según nuestros requerimientos.

Página 37 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Interrupciones

Tienes tu módulo conectado a tu Arduino y quieres activar algún motor o modificar una variable
cuando suceda algo (haya ruido, entre alguien…) pero claro ¿Si no sabes cuándo va a suceder ese
evento cómo haces el código? ¿Te pasas todo el día monitorizando ese pin? ¿Y si justo
sucede cuando la instrucción que se está ejecutando es un delay()? ¿Y si es un sonido impulsivo
(como un golpe) y no lo detectas con el código? Todos estos problemas encuentran su solución en
el uso de las interrupciones. Las interrupciones en Arduino te permiten detectar eventos de forma
asíncrona con independencia de las líneas de código que se estén ejecutando en ese momento en
tu microcontrolador.

¿Qué es una Interrupción?

Una interrupción consiste básicamente en detectar un evento y realizar algo en consecuencia. A un


nivel básico, una interrupción es una señal que interrumpe la actividad normal de nuestro
microprocesador y salta para atenderla. Arduino tiene una serie de pines a los que puedes asociar
un módulo (un segmento de código) de modo que este se ejecute cuando en ese pin cambie de un
estado a otro que tú previamente has establecido.

Cuando utilizas instrucciones del tipo millis() estás utilizando interrupciones. ¿Te suena eso de que
la función millis() vuelve a 0 tras 50 días con tu Arduino conectado? ¡Exacto! Eso también se hace
con interrupciones.

Hay tres eventos que pueden disparar una interrupción:

✓ Un evento hardware, previamente definido.


✓ Un evento programado, o Timer
✓ Una llamada por software.

Cuando un evento dispara una interrupción, la ejecución normal del micro se suspende
(ordenadamente para poder volver) y salta a ejecutar una función especial que llamamos Interrupt
Service Handler o ISH (Servicio de gestión de interrupción). Cuando el ISH finaliza, el procesador
vuelve tranquilamente al punto donde lo dejó y sigue con lo que estaba como si no hubiese pasado
nada.

El concepto de interrupción nace de la necesidad imperiosa de reaccionar de forma inmediata en


respuesta a un acontecimiento electrónico fulgurante, que no admite demora. Bien sea por la
urgencia del suceso o porque algo se podría perder de forma irrecuperable sino reaccionamos con
suficiente presteza.

Por otro lado las interrupciones nos ofrecen una ventaja enorme a la hora de organizar nuestro
programa. Se define la función que se ejecutará al recibir una interrupción dada y se ejecuta
limpiamente cuando ocurre, no hay que comprobar si se da o no una situación.

Página 38 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

¿Para qué sirven las interrupciones de arduino?

Como todos los códigos, sirve para lo que tú lo quieras usar en tu proyecto. No te ha ayudado mucho
¿Verdad? Bueno, para que te hagas un poco la idea de para qué puedes usar las interrupciones te
pongo unos cuantos ejemplos:

✓ Para detectar cambios como un pulsador que ha sido presionado.

✓ Para determinar cuándo se ha terminado de gestionar la memoria EEPROM o Flash de tu


Arduino.

✓ A modo de despertador del controlador. Esta es una interesantísima funcionalidad de tu


placa que te permite mantener el consumo al mínimo dejando tu Arduino en standby hasta
que suceda algún evento. Con ello podrás hacer que tus baterías duren mucho más.
✓ Como el complemento ideal a los módulos digitales de sonido, temperatura… que disponen
de un potenciómetro que regula cuándo se activa la salida digital. Así puedes, por ejemplo,
realizar un montaje simple en el que ocurra alguna acción cuando se supere un cierto umbral
de sonido o una cierta distancia.

Modos De Activar Las Interrupciones

Ahora que sabes a qué pines se pueden asociar las interrupciones en Arduino, te falta conocer
cómo activarlas, es decir, qué tiene que suceder en ese pin para que la interrupción se ejecute.
Estos modos de activación los determinas tú cuando programas la interrupción y las posibilidades
son las siguientes:

LOW: La interrupción se activa cuando el valor de voltaje del pin elegido es bajo, esto es, 0V.
CHANGE: La interrupción se activa cuando el pin cambia de valor, es decir, cuando pasa de LOW
a HIGH o de HIGH a LOW.
RISING: Se activa únicamente cuando el valor del pin pasa de LOW a HIGH.
FALLING: Es el caso opuesto al modo RISING. Se activa la interrupción cuando el valor pasa de
HIGH a LOW.
HIGH: Este modo solo está disponible en la placa DUE y funciona de manera opuesta al modo
LOW, es decir, se activa cuando el valor de voltaje del pin es alto.

Tienes aquí una serie de conceptos y tips importantes:

✓ Se debe implementar los módulos de tus interrupciones lo más cortos y eficientes que te sea
posible.
✓ Sólo se puede ejecutar una instrucción de cada vez, esto es, si se está ejecutando una
interrupción y se activa una segunda, no tendrá efecto hasta que la primera termine.
✓ No es posible utilizar la función delay() conjuntamente con las interrupciones.
✓ La función millis() no incrementa su valor durante el transcurso de una interrupción.
✓ A pesar de que las funciones delay() y millis() no funcionan correctamente cuando hay
activadas interrupciones, sí que puedes utilizar la función delayMicroseconds().
✓ Si se está transmitiendo o recibiendo datos (Serial. Begin()) cuando se activa una
interrupción, es posible que los pierdas.
✓ Si se quieres utilizar la variable que es modificada por tu interrupción (estado_actual) fuera

Página 39 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

de ese módulo, debes crearla de tipo volatile.


✓ Se puede deshabilitar las interrupciones en cualquier momento utilizando la instrucción
detachInterrupt().

Para esta actividad montaremos un circuito de tal manera que haciendo uso de las correctas líneas
de código podremos visualizar el número de veces que está siendo presionado el pulsador, además
mientras no se presione, se mostrará una secuencia de puntos, que indican la continuidad del
código, esto nos ayudara a ejemplificar un proceso que es interrumpido, finalmente esto se podrá
visualizar en nuestro monitor serial.

Materiales

Pulsador:

El pulsador es simplemente un interruptor momentáneo: dejará pasar la corriente únicamente


mientras se mantenga pulsado, aunque se puede utilizar un truco para que se comporte como un
interruptor permanente.
Aunque existen también de dos patillas, lo más normal será que los pulsadores tengan 4 patillas. El
motivo de que sea así, no se tiene muy claro, aunque una razón para esto, puede ser para poder
ser fijadas más fácilmente en las placas de circuitos. Sea como sea, físicamente son 4 patillas pero
realmente son 2, porque están unidas internamente en parejas.

En la siguiente imagen se marca las hacen pareja, de tal forma que al presionar el pulsador se
cerrara el circuito entre una pareja y otra.

Figura 30.- Pulsador: Disposicion de los pines

Procedemos a realizar el montado del circuito tal y como se muestra en la Fig.31 , recordar que
físicamente son 4 patillas pero realmente son 2, porque están unidas internamente en parejas.

Seguidamente conectamos nuestro Arduino a nuestro ordenador y cargamos el código que a


continuación se muestra.

Figura 31.- Montado del circuito

Página 40 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

La idea consiste en que al presionar el pulsador cuente la interrupción, además mientras no se


presione, se muestre una secuencia de puntos, que indican la continuidad del código, para
ejemplificar un proceso que es interrumpido.

Código

int interrupcion = 0;
// Interrupt.0 se encuentra en el pin digital 2
// Interrupt.1 se encuentra en el pin digital 3

/* Creamos la variable con el calificador volatile


para asegurar que la variable será accesible desde el
flujo normal del programa y desde la interrupcion.
*/

volatile int numInterrupt = 0;

void setup() {

Serial.begin(9600);

// Sintaxis interrupciones:
// attachInterrupt(numero_interrupt,función_a_ejecutar,modo);
// Modos LOW,CHANGE,RISING,FALLING

attachInterrupt(interrupcion, funcionInterrupcion,FALLING);
}

void loop() {
/*Simulamos una tarea que requiera tiempo.
Utilizamos While(true) ya que siempre se cumplirá la
condición y nunca dejará de ejecutar el código incluido.
*/
while(true){
Serial.println(".");
delay(250);
}
}

void funcionInterrupcion() {
Serial.print("Interrupt numero ");
Serial.println(numInterrupt);
numInterrupt++; // Aumentamos el número almacenado en numInterrupt en una
unidad.
}

Página 41 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Sensor de Ultrasonido
Un complemento imprescindible para muchos de robots o vehículos controlados a distancia es un
sensor que nos permita saber la distancia libre de obstáculos para movernos. Si las distancias van
a ser pequeñas podemos emplear sensores de infrarrojos, pero si queremos movernos en áreas
grandes y poder medir distancias en un rango de varios metros el complemento perfecto es
un sensor de ultrasonidos.

Funciona exactamente igual que un radar, de hecho es un pequeño radar.

El sensor de ultrasonidos se enmarca dentro de los sensores para medir distancias o superar
obstáculos, entre otras posibles funciones.
En este caso vamos a utilizarlo para la medición de distancias. Esto lo consigue enviando un
ultrasonido (inaudible para el oído humano por su alta frecuencia) a través de uno de la pareja de
cilindros que compone el sensor (un transductor) y espera a que dicho sonido ,rebote sobre un
objeto y vuelva, retorno captado por el otro cilindro.

Este sensor en concreto tiene un rango de distancias sensible entre 3cm y 3m con una precisión de
3mm.

Figura 32.- Sensor HC-SR04

¿Qué recibimos en el sensor?

El tiempo que transcurre entre el envío y la recepción del ultrasonido.

¿Cómo vamos a traducir dicho tiempo en distancia?

Aprovechando que la velocidad de dicho ultrasonido en el aire es de valor 340 m/s, o 0,034
cm/microsegundos (ya que trabajaremos con centímetros y microsegundos). Para calcular la
distancia, recordaremos que v=d/t (definición de velocidad: distancia recorrida en un determinado
tiempo). De la fórmula anterior despejamos d, obteniendo d=v·t, siendo v la constante anteriormente
citada y t el valor devuelto por el sensor a la placa Arduino.

También habrá que dividir el resultado entre 2 dado que el tiempo recibido es el tiempo de ida y
vuelta.

Se procede con el armado del circuito, siguiendo como guía la figura 33.

Seguidamente se procede a cargar el código, es cual será expuesto a continuación.

Página 42 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 33.- Montado del circuito para la actividad Nº1

Código

#include <LiquidCrystal.h>//Incluimos la librería para pantalla.


LiquidCrystal lcd(12, 11, 5, 4, 3, 2);// Inicializamos la biblioteca con los
números de los pines de interfaz.
long distancia;//Declaramos una variable que almacenera el valor de distancia.
long tiempo;//Declaramos una variable que almacenara el valor del tiempo.
const int trig = 6; //Pin de Arduino conectado a la patilla Trigger,en el sensor
del ultrasonido.
const int echo = 7; //Pin de Arduino conectado a la patilla Echo, en el sensor
del ultrasonido.

void setup() {
lcd.begin(16, 2);
//Declaramos a trig y led como salidas, echo será declarada como entrada.
pinMode(trig, OUTPUT);
pinMode(echo, INPUT);
//Inicializamos la comunicación serial.
Serial.begin(9600);
}

void loop() {
//Escribimos en la parte superior de la pantalla Distancia.
lcd.setCursor(0, 0);
lcd.print("Distancia");
digitalWrite(trig, LOW); //Por cuestión de estabilización del sensor.
delayMicroseconds(5);
digitalWrite(trig, HIGH); // envío del pulso ultrasónico.
delayMicroseconds(10);
tiempo = pulseIn(echo, HIGH);/* Función para medir la longitud del pulso
entrante. Mide el tiempo que transcurrido entre el envío
del pulso ultrasónico y cuando el sensor recibe el rebote, es decir: desde que
el pin 7 empieza a recibir el rebote, HIGH, hasta que deja de hacerlo, LOW, la
longitud del pulso entrante*/
distancia = int(0.017 * tiempo); /*fórmula para calcular la distancia
obteniendo un valor entero*/
/*Líneas de código para visualizar en nuestras pantallas la distancia a la que
se encuentra un cuerpo con respecto a nuestro sensor */

Página 43 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

lcd.clear();
lcd.setCursor(0, 0);
lcd.print("Distancia");
lcd.setCursor(0, 1);
lcd.print(distancia);
lcd.setCursor(4, 4);
lcd.print("cm");
/*Para que en el monitor serial muestre la distancia a la que se encuentra el
sensor*/
Serial.println("Distancia");
Serial.print(distancia);
Serial.println("cm");
delay(500);
}

Actividad: Alarma de proximidad

Para esta actividad le daremos una pequeña aplicación al uso del sensor de ultrasonido y la pantalla
LCD 16x2, lo que haremos es una alarma, conformada por un led que se activará cuando el sensor
detecte a un cierta distancia un obstáculo, el mismo aumentara la velocidad de parpadeo a medida
que la distancia de alarma se vaya acortando, señal de que el obstáculo está cada vez más cerca.

Se procede con el armado del circuito, siguiendo como guía la figura 34.

Lo que ahora hay que agregarle a nuestro circuito es el LED, procedemos a conectar el catado del
led al pin digital 8 de nuestro Arduino, no sin antes colarse una resistencia de 220Ω tal como se
puede apreciar en la figura, y por ultimo no olvidar conectar la tierra como también se aprecia.

Por último, lo que se procede a realizar es cargar nuestro código, el cual será detallado a
continuación.

Figura 34.- Montado del circuito para la actividad a realizar.

Página 44 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Código

#include <LiquidCrystal.h>//Incluimos la librería para pantalla.


LiquidCrystal lcd(12, 11, 5, 4, 3, 2);// Inicializamos la biblioteca con los
números de los pines de interfaz.

long distancia;//Declaramos una variable que almacenera el valor de distancia.


long tiempo;//Declaramos una variable que almacenara el valor del tiempo.
const int trig = 6; //Pin de Arduino conectado a la patilla Trigger,en el sensor
del ultrasonido.
const int echo = 7; //Pin de Arduino conectado a la patilla Echo, en el sensor
del ultrasonido.
const int led = 8; //Pin conectado al led que indicara la alarma.

void setup() {
lcd.begin(16, 2);
//Declaramos a trig y led como salidas, echo será declarada como entrada.
pinMode(trig, OUTPUT);
pinMode(echo, INPUT);
pinMode(led, OUTPUT);
//Inicializamos la comunicación serial.
Serial.begin(9600);
}

void loop() {
//Escribimos en la parte superior de la pantalla Distancia.
lcd.setCursor(0, 0);
lcd.print("Distancia");
digitalWrite(trig, LOW); //Por cuestión de estabilización del sensor.
delayMicroseconds(5);
digitalWrite(trig, HIGH); // envío del pulso ultrasónico.
delayMicroseconds(10);

tiempo = pulseIn(echo, HIGH); /* Función para medir la longitud del pulso


entrante. Mide el tiempo que transcurrido entre el envío del pulso ultrasónico y
cuando el sensor recibe el rebote, es decir: desde que el pin 50 empieza a
recibir el rebote, HIGH, hasta que deja de hacerlo, LOW, la longitud del pulso
entrante*/
distancia = int(0.017 * tiempo); /*fórmula para calcular la distancia
obteniendo un valor entero*/
/*Monitorización en centímetros por el monitor serial*/
/*Condiciones lo cual se activara la alarma y lectura en todo momento de la
distancia a la que
se encuentra el sensor*/
if (distancia < 350) {
/*Si cumple con las condiciones asignadas de alarma en la pantalla me
mostrara un mensaje de alarma*/
lcd.clear();
lcd.setCursor(0, 0);
lcd.print("Alarma");
lcd.setCursor(0, 1);
lcd.print(distancia);
lcd.setCursor(4, 4);
lcd.print("cm");
digitalWrite(led, HIGH);
delay(distancia * 10);
digitalWrite(led, LOW);
delay(distancia * 10);
}

Página 45 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

/*Si no se cumple con la condiciones de alarma la pantalla seguirá mostrando


la distancia a la que se encuentra el sensor*/
else {
lcd.setCursor(0, 1);
lcd.print(distancia);
lcd.setCursor(4, 4);
lcd.print("cm");
digitalWrite(led, LOW);
delay(1000);
}
/*Para que en el monitor serial muestre la distancia a la que se encuentra el
sensor*/
Serial.println("Distancia:");
Serial.print(distancia);
Serial.println(" cm");
}

Página 46 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

STRING

Este tipo de varible es muy útil debido a que cuenta con varias propiedades las cuales son muy
útiles para el procesamiento de información como se da en los protocolos de comunicación, nos
permitirá armar nuestras estructuras de dados y procesar los mismos, convertir datos de variables
númericas a texto para poder transmitirlos de manera más sencilla emplenado algún puerto de
comunicación en esta ocación de los que nos proporcionan nustras tarjetas Arduino, vale mencionar
que cuentan con puertos de comunicación Serial que ya hemos visto, puerto de comunicacón SPI
e I2C que veremos en la siguiente sesión.

Una variable String, cuando no se inicializa y no contiene ningún valor, se le asigna un espacio de
16 bytes en la memoria RAM. Recordemos que en realidad sólo se usarían 15 bytes, dado que un
string DEBE de terminar en el carácter nulo \0. Por el contrario, si se inicializa con un valor que
supera el valor anterior, se le asignara un valor que considere el byte nulo.

Entonces es muy importante resaltar que cuando se usan variables del tipo String se hará un uso
excesivo de la memoria de Arduino.

El IDE de Arduino nos ofrece una clase llamada String que facilita el uso de de las cadenas de
caracteres con unos métodos muy sencillos de usar y poder usar los operadores que conocemos
para los Strings.

Se trata de una clase que permite usar y manipular cadenas de texto de una forma más sencilla
que los strings. Puedes concatenar, añadir, buscar, etc… usando los métodos/funciones que ofrece
esta clase.

Los Strings tienen un uso intensivo de memoria, pero son muy útiles y se van a utilizar mucho en el
apartado de comunicación, por ese motivo es importante aprender a manejar los Strings.

Tener en cuenta que al no ser un tipo de dato propiamente dicho sino una clase, tienes unas
funciones asociadas (métodos), operadores y unas propiedades. Es una abstracción del dato y para
aprender a usarlo hay que leerse la documentación correspondiente.

En el transcurso de la sesión se explicarán algunos de los ejemplos que nos proporciona el IDE de
Arduino los cuales serán muy útiles para trabajar con los puertos de comunicación de nuestras
tarjetas lo cual nos permitirá conectar con algún otro dispositivo ( tarjeta, sensor, equipo, etc)
mediante algún protocolo de comunicación dispinible en nuestras tarjetas Arduino.

Ejemplos de como declarar un String

String str1 = "hola";


String str2 = "hola mundo";
String str3 = "1234";
String str4 = "hola IME 12345";
String str5 = "*/-+";
String str6 = "hola mundo ++**53245**++";

Podemos encontrar ejemplos en donde se emplean estos métodos empleando este tipo de
variables, para ello nos dirigimos a Archivo → Ejemplos → Strings como se muestra en la imagen:

Página 47 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 35.- Ejemplos de clase String del IDE de Arduino

Página 48 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Comuniocación I2C
¿Qué es I2C?

Abreviatura de inter-IC (inter integrated circuits); un tipo de bus diseñado por Phillis Semiconductors
a principios de 80s, que se emplea para conectar circuitos integrados.

Este protocolo de comunicación entre microcontroladores, memorias y otros dispositivos con cierto
nivel de “inteligencia” solo requiere de 2 señales y una línea común y permite el intercambio de
información entre muchos dispositivos a una velocidad aceptable, de unos 100Kbits por segundo,
aunque hay casos especiales en los que el reloj llega hasta los 3.4 MHz.

Señales empleadas:
✓ SCL (System Clock) es la línea de los pulsos de reloj que sincronizan el sistema.
✓ SDA (System Data) es la línea por la que se mueven los datos entre los dispositivos.
✓ GND (Masa) común de la interconexión entre todos los dispositivos «enganchados» al bus

Funcionamiento del protocolo I2C


Para poder realizar la comunicación empleando el protocolo I2C se emplea una trama de datos (el
formato de los datos enviados) amplia. La comunicación costa de:
✓ 7 bits a la dirección del dispositivo esclavo con el que queremos comunicar.
✓ Un bit restante indica si queremos enviar o recibir información.
✓ Un bit de validación
✓ Uno o más bytes son los datos enviados o recibidos del esclavo.
✓ Un bit de validación

Figura 36.- Señales del protocolo de Comunicación I2C

Con estos 7 bits de dirección es posible acceder a 112 dispositivos en un mismo bus (16 direcciones
de las 128 direcciones posibles se reservan para usos especiales)

Página 49 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Este incremento de los datos enviados (18bits por cada 8bits de datos) supone que, en general, la
velocidad del bus I2C es reducida. La velocidad estándar de transmisión es de 100khz, con un modo
de alta velocidad de 400khz.

Ventajas

✓ Requiere pocos cables


✓ Dispone de mecanismos para verificar que la señal hay llegado

Desventajes

✓ Su velocidad es media-baja
✓ No es full duplex
✓ No hay verificación de que el contenido del mensaje es correcto

Arduino dispone de soporte I2C por hardware vinculado físicamente a ciertos pines. También es
posible emplear cualquier otro grupo de pines como bus I2C a través de software, pero en ese caso
la velocidad será mucho menor.

Los pines a los que está asociado varían de un modelo a otro. La siguiente tabla muestra la
disposición en alguno de los principales modelos. Para otros modelos, consultar el esquema de
patillaje correspondiente.

Figura 37.- Distribusción de pines de I2C en principales tarjetas Arduino

Para usar el bus I2C en Arduino, el IDE Standard proporciona la librería "Wire.h", que contiene las
funciones necesarias para controlar el hardware integrado.

Página 50 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Comandos principales de I2C de la librería “Wire.h”

Wire.begin() // Inicializa el hardware del bus


Wire.beginTransmission(address); //Comienza la transmisión
Wire.endTransmission(); // Finaliza la transmisión
Wire.requestFrom(address,nBytes); //solicita un numero de bytes al esclavo en la dirección
address
Wire.available(); // Detecta si hay datos pendientes por ser leídos
Wire.write(); // Envía un byte
Wire.read(); // Recibe un byte

Wire.onReceive(handler); // Registra una función de callback al recibir un dato


Wire.onRequest(handler); // Registra una función de callback al solicitar un dato

Ejercicios a desarrollar

Primero resolveremos unos ejercicios sencillos y poco a poco iremos viendo unos más complejos
Se debe programar tanto el maestro como los dispositivos esclavos a emplear, cada elemento debe
tener configurado un número de maestro o esclavo. La comunicación funciona la inicia el maestro
y transmite a todos sus esclavos una determinada trama de datos la cuál lleva una determinada
dirección que es la dirección del esclavo con el que quiere entablar comunicación; a continuación,
todos los esclavos recibirán la trama y la evaluarán al ver que no coincide con su dirección la
descartarán y caso contrario recibirá la información para su respectivo procesamiento.

El propio IDE de Arduino nos proporciona ejemplos básicos para realizar pruebas de este protocolo
de comunicación, para acceder a estos desde el IDE de Arduino nos dirigimos a Archivo → Ejemplos
→ Wire como se muestra en la siguiente imagen:

Figura 38.- Ejemplos de I2C en IDE Arduino

Página 51 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Primero analizaremos algunos de estos ejemplos:

I2c_scanner:

#include <Wire.h>

void setup() {
Wire.begin();

Serial.begin(9600);
while (!Serial); // Leonardo: wait for serial monitor
Serial.println("\nI2C Scanner");
}

void loop() {
int nDevices = 0;

Serial.println("Scanning...");

for (byte address = 1; address < 127; ++address) {


// The i2c_scanner uses the return value of
// the Write.endTransmisstion to see if
// a device did acknowledge to the address.
Wire.beginTransmission(address);
byte error = Wire.endTransmission();

if (error == 0) {
Serial.print("I2C device found at address 0x");
if (address < 16) {
Serial.print("0");
}
Serial.print(address, HEX);
Serial.println(" !");

++nDevices;
} else if (error == 4) {
Serial.print("Unknown error at address 0x");
if (address < 16) {
Serial.print("0");
}
Serial.println(address, HEX);
}
}
if (nDevices == 0) {
Serial.println("No I2C devices found\n");
} else {
Serial.println("done\n");
}
delay(5000); // Wait 5 seconds for next scan
}

Este ejemplo sirve para escanear dispositivos que tengamos conectados al puerto de comunicación
I2C de los cuales no sabemos su dirección, empleando este código podremos ver mediante el
puerto de comunicación serial la dirección que tiene asignado de fabrica para poder trabajar sin
ningún problema.

Master_reader:
#include <Wire.h>

void setup() {
Wire.begin(); // join i2c bus (address optional for master)

Página 52 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Serial.begin(9600); // start serial for output


}

void loop() {
Wire.requestFrom(8, 6); // request 6 bytes from slave device #8

while (Wire.available()) { // slave may send less than requested


char c = Wire.read(); // receive a byte as character
Serial.print(c); // print the character
}

delay(500);
}

Master_writer:

#include <Wire.h>

void setup() {
Wire.begin(); // join i2c bus (address optional for master)
}

byte x = 0;

void loop() {
Wire.beginTransmission(8); // transmit to device #8
Wire.write("x is "); // sends five bytes
Wire.write(x); // sends one byte
Wire.endTransmission(); // stop transmitting

x++;
delay(500);
}

Slave_receiver:

#include <Wire.h>

void setup() {
Wire.begin(8); // join i2c bus with address #8
Wire.onReceive(receiveEvent); // register event
Serial.begin(9600); // start serial for output
}

void loop() {
delay(100);
}

// function that executes whenever data is received from master


// this function is registered as an event, see setup()
void receiveEvent(int howMany) {
while (1 < Wire.available()) { // loop through all but the last
char c = Wire.read(); // receive byte as a character
Serial.print(c); // print the character
}
int x = Wire.read(); // receive byte as an integer
Serial.println(x); // print the integer
}

Página 53 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Slave_sender:
#include <Wire.h>

void setup() {
Wire.begin(8); // join i2c bus with address #8
Wire.onRequest(requestEvent); // register event
}

void loop() {
delay(100);
}

// function that executes whenever data is requested by master


// this function is registered as an event, see setup()
void requestEvent() {
Wire.write("hello "); // respond with message of 6 bytes
// as expected by master
}

Como podrán apreciar estos 4 ejemplos nos sirve para enviar/recibir un solo dato a la vez, en caso
queramos realizar el envío de una mayor cantidad de datos en la misma trama de datos se tendrá
que realizar o armar un formato o nueva trama de datos para poder enviar/recibir datos desde/hacia
el maestro/esclavo respectivamente según la lógica que se configure a la tarjeta de Arduino a
emplear; a continuación se explicará como realizar este proceso para poder enviar varios datos sin
tener inconvenientes.

En el siguiente código a estudiar veremos el tipo y cantidades de variables a emplear para una
correcta transmisión/recepción de datos entre varios dispositivos empleando el protocolo I2C.

#include <Wire.h>

int s1 = 0;
char datain[14];
char enviar[14];
String dataenviada = "";
String datarecibida = "";
float x = 2.24;

void setup() {
Wire.begin(); // join i2c bus (address optional for master)
Serial.begin(9600); // start serial for output
pinMode(2, INPUT);
}
void muestra(String texto) {
int inicio, coma, fin, s2;//Varibles de separadores
float s1;//Variable de dato a enviar/recibir
String sensor1, sensor2;//Variable para almacenar dato de sensores
Serial.println(texto);//Se imprime todo lo que recibe
inicio = texto.indexOf("@");//Ubicamos la posición del caracter especial "@"
coma = texto.indexOf(",");//Ubicamos la posición del caracter especial ","
fin = texto.indexOf("a");//Ubicamos la posición del caracter especial "a"

sensor1 = texto.substring(inicio + 1, coma);//aplicamos substring para tomar


parte de la cadena colocando las posicines previamente obtenidas
sensor2 = texto.substring(coma + 1, fin);//
s1 = (texto.substring(inicio + 1, coma)).toFloat();//Convertimos en float el
valor para poder realizar operaciones matemáticas.
s2 = (texto.substring(coma + 1, fin)).toInt();//Convertimos en int el valor
para poder realizar operaciones matemáticas.

Página 54 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Serial.print("Sensor1:" ); Serial.print(sensor1); Serial.print("


");//Imprimimos por el puerto serial los datos obtenidos de los sensores
Serial.print("Sensor2:" ); Serial.println(sensor2);

datarecibida = "";//Limpiamos la variable que almacena la data;


}

void loop() {

int a1 = analogRead(A0);//Lectura del pinanalócigo A0


if (digitalRead(2) == LOW) {//Condicional para iniciar envio
dataenviada = "#"+String(a1) + "," + String(x)+"/";
dataenviada.toCharArray(enviar, 14);
m_transmisor();
dataenviada="";
}
if (digitalRead(2) == HIGH) {//Condicional para inicar recepción
m_receptor();
}
delay(500);
}

void verifica(int dato) {


String datoverificado;
if (dato < 100) {
//Agregagar 1 caracter delante
datoverificado = "0" + String(x);
if (dato < 10) {
//Agregar 2 caracteres delante
}
}
else {
datoverificado = dato;
}
}

void m_receptor() {//Funcion de inicio de recepción


Wire.requestFrom(8, 14); // se envía solicitud de 14 bytes del esclavo #8

while (Wire.available()) {// slave may send less than requested


char c = Wire.read(); // receive a byte as character
Serial.print(c); // print the character
datarecibida = datarecibida + c;//ALmacenamos la data recibida en la
variable datarecibida
if (c == 'a') {//Condicional para proceder a porcesar la data recibida.
muestra(datarecibida);//llamamos a la funcion muestra
Serial.println(); //Imprimios un salto de línea
}
}
}

void m_transmisor() {//Funcion para iniciar transmision de datos


Serial.print("enviando: ");
Wire.beginTransmission(8); // transmit to device #8
Wire.write(enviar);
Serial.println(enviar); // imprimimos por el puerto serial los datos mejor
Wire.endTransmission(); // stop transmitting
}

Procedemos a subir los respectivos códigos según lo explicado en cada tarjeta respectivamente.

Subiremos el Código del maestro sólo a una tarjeta y para los esclavos sus respectivos códigos

Página 55 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

que básicamente es el mismo con la única diferencia de la dirección que se le asigna a cada una
para poder entablar comunicación con el maestro.

Podemos emplear las librerías del simlación de Arduino para Proteus para realizar pruebas o en
físico; realizamos el siguiente esquemático en el software el cual también tomaremos de
referencia

Figura 39.- Simulación de comunicación I2C

En este esquema le asignaremos el código del maestro al arduino de la izquierda y el de la derecha


le colocaremos el código del esclavo respectivamente para poder realizar la respectiva simulación.

Luego de realizado esto procedemos a correr la simulación y emplearemos los dispositos virtuales
para comunicación I2C para poder monitoriar los datos de manera visual.

Como podemos apreciar el modo de lectura/escritura dependerá del estado de la entrada digital en
donde tenemos conectado el pulsador, en pocas palabras dependiendo del estado del pulsador el
maestro enviará datos de escrituta o solicitud de datos al esclavo.

Página 56 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

IoT con ArduinoCloud

Con el fin de poner a disposición al alumno una plataforma de prototipo de código abierto, como es
Arduino, el cual será pieza importante en el desarrollo de los trabajos destinado para este ciclo, se
ha propuesto una serie de laboratorios en donde se verán a grandes rasgos lo que se ha pensado
son los conceptos y herramientas más importante que se deben tener en cuenta, y que podrán ser
aplicadas en la realización de los trabajos.

Con la teoría vista en los talleres previos continuaremos en este laboratorio de Arduino orientado a
IoT empleando librerías que nos ofrece Arduino, así como la herramienta llamada ArduinoCloud.

Para el ejemplo se empleo una tarjeta NodeMcu la cual nos permite conectarnos inalambricamente
a una red WIFI

Figura 40.-Módulo ethernet w5500

Procedemos a conectar nuestra tarjeta Arduino con el módulo ethernet w5500, el cual trae los pines
impresos en la parte posterior como se puede apreciar en la imagen:

Figura 41.-Lado posterior de módulo ethernet w550

Los pines a conectar son 7 son y los siguientes:

Módulo ethernetw5500 Arduino MEGA


5V 5V
GND GND
MOSI MOSI
MISO MISO
CLK SCK
CSN SS
RST RST

Página 57 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 42.- Diagrama de pines del módulo w5500

Figura 43.- Pines de comunicación SPI del Arduino MEGA2560

Página 58 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Procedimiento

Para esta primera actividad, realizaremos la configuración de nuestro dispositivo desde el IDE de
Arduino; nos dirigimos a programas incluir librerías administrar bibliotecas, y en la ventana de
búsqueda tipiaremos el nombre del módulo a emplear que es en este caso el módulo ethernet
w5500 como se puede apreciar en la siguiente figura.

Figura 44.- Gestor de librerías de Arduino

Luego podemos dirigirnos a archivos → ejemplos → ethernet2 en donde podremos ver un listado
de los distintos ejemplos que vienen precargados con la librería como se muestra a continuación:

Figura 45.- Ejemplos de librería Ethernet2

Página 59 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Realizaremos la carga del ejemplo web server que se muestra a continuación:

#include <SPI.h>
#include <Ethernet2.h>

// Enter a MAC address and IP address for your controller below.


// The IP address will be dependent on your local network:
byte mac[] = {
0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED
};
IPAddress ip(192, 168, 17, 177);

// Initialize the Ethernet server library


// with the IP address and port you want to use
// (port 80 is default for HTTP):
EthernetServer server(80);

void setup() {
// Open serial communications and wait for port to open:
Serial.begin(9600);
while (!Serial) {
; // wait for serial port to connect. Needed for Leonardo only
}

// start the Ethernet connection and the server:


Ethernet.begin(mac, ip);
server.begin();
Serial.print("server is at ");
Serial.println(Ethernet.localIP());
}

void loop() {
// listen for incoming clients
EthernetClient client = server.available();
if (client) {
Serial.println("new client");
// an http request ends with a blank line
boolean currentLineIsBlank = true;
while (client.connected()) {
if (client.available()) {
char c = client.read();
Serial.write(c);
// if you've gotten to the end of the line (received a newline
// character) and the line is blank, the http request has ended,
// so you can send a reply
if (c == '\n' && currentLineIsBlank) {
// send a standard http response header
client.println("HTTP/1.1 200 OK");
client.println("Content-Type: text/html");
client.println("Connection: close"); // the connection will be closed
after completion of the response
client.println("Refresh: 5"); // refresh the page automatically every
5 sec
client.println();
client.println("<!DOCTYPE HTML>");
client.println("<html>");
// output the value of each analog input pin
for (int analogChannel = 0; analogChannel < 6; analogChannel++) {
int sensorReading = analogRead(analogChannel);
client.print("analog input ");

Página 60 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

client.print(analogChannel);
client.print(" is ");
client.print(sensorReading);
client.println("<br />");
}
client.println("</html>");
break;
}
if (c == '\n') {
// you're starting a new line
currentLineIsBlank = true;
}
else if (c != '\r') {
// you've gotten a character on the current line
currentLineIsBlank = false;
}
}
}
// give the web browser time to receive the data
delay(1);
// close the connection:
client.stop();
Serial.println("client disconnected");
}
}

Lo único vamos a comprobar es el IP empleando que esté disponible en nuestra red, luego
procedemos a cargar el código, una vez realizado esto podemos dirigirnos a nuestro navegador
web y tipiar en la barra de búsqueda el IP asignado y nos mostrará la lectura de los puertos
analógicos de nuestro Arduino como se muestra a continuación:

Figura 46.- Vista desde navedador de datos analógicos

Ahora realizaremos la configuración de nuestro dispositivo empleando otro método para lo cual
debemos realizar es registrarnos en la plataforma de ArduinoCloud para poder tener acceso a sus
herramientas gráficas y poder hacer uso de esta fantástica plataforma, podemos dirigirnos al
siguiente link oficial arduino y seguir los siguientes pasos:

https://www.arduino.cc/

Luego de ingresaremos al apartado que dice CLOUD como se muestra en la imagen:

Página 61 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 47.- Página oficial de arduino

Luego deberemos crear una cuenta nueva, para ello deberemos dar click en la opción que dice
GET STARTED:

Figura 48.- Página oficial de arduino

Luego de dar click en esta opción se abrirá una nueva pesña en donde le daremos click Create one
y crearemos una cuenta

Figura 49.- Página oficial de arduino

Página 62 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Luego de creada la cuenta nos dirigiremos al siguiente apartado (Things) en donde crearemos las
variables, para eso le daremos click en el botón CREATE THING como se muestra en la imagen:

Figura 50.- Vista de arduino Cloud

Aquí nos aparecerá una ventana en donde podremos ediatar el nombre del proyecto y también
podemos ir agreganado las varibles dando click en ADD VARIABLE ; también podemos vincular el
dispositivo a emplear como se puede apreciar en la imagen:

Figura 51.- Creación de variables en plataforma

Página 63 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Luego de dar click en ADD variable y nos mostrará una nueva ventana en la cual ocnfiguraremos
dicha varible como se puede apreciar a continución en la imagen:

Figura 52.- Configuración de variables en plataforma

Para cada variable que deseemos agregar simplemente debemos repetir este paso con los datos
respectivos de la variable a crear.

Luego de crear todas las variables procedemos a vincular un dispositivo, en caso no encuentre
ningún dispositivo le podemos dar a la opción que dice SET UP NEW DEVICE como se puede
apreciar a continuación y luego selecionamos el modelo de la tarjeta que vamos emplear, el cual
obviamente debe estar dentro de la lista de tarjetas compatibles con la plataforma, en esta ocación
se empleará un nodeMCU.

Figura 53.- Conexión de nuevo dispositivo

Página 64 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Después de dar click en la opción antes mencionada nos mostrará las siguientes opciones:

Figura 54.- Ventada para elegir el tipo de tarjeta a conectar

Aquí seleccionaré la opción Third party device, dependiedo del tipo de tarjeta con el que se vaya a
trabajar se seleccionará la opción respectiva:

Figura 55.- NodeMCU(izquierda) Selección de tarjeta a conectar(derecha)

En este caso se selecionó la tarjeta con la que se trabajará, como se muestra a en la imagen

Página 65 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

anterior, posteriormente aparecerá una ventana nueva en la cual podremos editar el nombre de la
tarjeta en la plataforma como se puede apreciar acontinuación:

Figura 56.- Ventana para asignación de un nombre al dispositivo

A continuación nos mostrará unos datos que debemos guardar que nos servirán para poder
configurar nuestro dispositivo al momento de programarlo para poder conectarnos al servidor

Figura 57.- Datos del dispositivo

Finalmente nos aparecerá un mensaje de que se creo nuestro dispositivo, no queda más que
programarlo y configurar el dashboard para poder apreciar de manera gráfica y sencilla los datos

Página 66 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

del dispositivo a conectar como se puede apreciar en la figura siguiente:

Figura 58.- Vista de ceración satisfactoria del dispositivo

El paso siguiente es configurar el apartado de Networks, en donde deberemos colocar los datos o
credenciales de la red a la que nos conectaremos con nuestro dispositivo asi como el key de nuestro
dispositvo

Figura 59.- Configuración de red a emplear

Página 67 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Nos aparecerá una nueva ventana en donde llenaremos los respectivos datos como se muestra a
continuación en la siguiente imagen:

Figura 60.- Vista para ingresar datos de conexión y dispositivo

Luego nos dirigiremos a la pestaña de sketch para seleccionar el puerto y modelo de tarjeta al que
le cargaremos el código respectivo, el cual deberemos editar según nuestra aplicación, hay una
opción de full editor que nos ofrece la platarforma que es más completa como se pueden apreciar
en las imágenes a continuación:

Figura 61.- Código base para subir al dispositivo

Si es la primera vez que empleamos la plataforma nos pedirá instalar unos drivers, luego de inslarlos
la plataforma detectará los dispositivos conectados, para lo cual deberemos seleccionar el puerto y
modelo de tarjeta al cual le cargaremos el código respectivo como se puede aprecia a continuación
en la imagen:

Página 68 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 62.- Selección de puerto y tarjeta a emplear

El siguiente paso es editar el código empleando las variables creadas para que se puedan reflejar
en el dashboard que explicaremos a continuación como crear; nos dirigiamos a la pestaña que dice
dashboard y luego le daremos en build dashboard como se muestra en la imagen:

Figura 63.- Pesataña para la creación del dashboard

Luego nos aparecerá una hoja en blanco en donde iremos agregando los elementos, para estos
nos dirigimos a ADD le adremos click y se nos desplegara todas las opciones disponibles las cuales
iremos agregando y configurando respectivamente como se puede apreciar en la imagen:

Página 69 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 64.- Ventana de edición del dashboard

Para esto deberemos agregar algún elemento y luego nos mostrará las propiedades a editar, como
el nombre y la lista de variables disponibles y compatibles que se crearon previamente las cuales
deberemos vincular como se muestra en la siguiente imagen:

Figura 65.- Vinculación de varianbes con elementos del dahsboard

Finalmente arrastraremos los elementos creadosen el orden que deseemos, luego podemos
editarlos o eliminarlos sin ningún inconveniente

Figura 66.- Visualización de dashboard conectado a nuestra tarjeta nodeMCU

Página 70 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Ahora realizaremos la configuración de nuestro dispositivo empleando otro método para lo cual
debemos realizar es registrarnos en la plataforma de Cayenne para poder tener acceso a sus
herramientas gráficas y poder hacer uso de esta fantástica plataforma, podemos dirigirnos al
siguiente link para empezar con la creación de nuestra cuenta en Cayenne:

https://cayenne.mydevices.com

Resaltar que esta plataforma es de pago, igualmente se explican los pasos para emplearla para
conocimiento del alumno:

Luego de registrarnos podemos dirigirnos al apartado donde dice dispositivos para seleccionar la
tarjeta a emplear en este caso Arduino Mega tal como se muestra en la siguiente imagen:

Figura 67.- Plataforma web de Cayenne

Luego de realizar esto nos aparecerá una serie de pasos que debemos realizar para poder conectar
nuestro dispositivo con la plataforma como se muestra a continuación:

Página 71 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 68.- Pasos para configurar dispositivo con cayenne

El primer paso nos indica que necesitamos una tarjeta para poder conectarnos a la red, en nuestro
caso emplearemos uh ethernet shied, el segundo requisito es tener instalado el software de Arduino
el cual ya lo hemos instalado en el laboratorio anterior; el cuarto requisito es descargar la librería de
cayenne para el Arduino desde el software del mismo nombre dirigiendonos a Programas → Incuir
librería → Administrar bibliotecas selecionamos esta opción y se nos abrirá una ventana como se
muestra en la siguiente imagen en donde tipiaremos cayenne, luego selecionamos la respectia
librería como se muestra a continuación y finalmente en el botón de instalar y esperamos que se
descarge en instale .

Figura 69.- Gestor de librerías

Página 72 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Como se puede apreciar aparecerá una lista de librerías disponibles, en esta ocación instalaraemos
la librería llamada CayenneMQTT by myDevices como se muestra en la imagen.

Figura 70.- instalación de librería cayenne

Luego de terminar de realizar estos pasos seleccionamos el puerto en donde tenemos conectado
nuestra tarjeta de Arduino así como el modelo de la placa que estamos usando, en nuestro caso el
Arduino Mega 2560.

Después de realizar los pasos anteriores procedemos a dar click en el boton NEXT de la plataforma
web de cayenne para seguir con la configuración respectiva; a continuación nos mostrará una lista
con todos los modelos de Arduino así como las tarjetas y shields para conexión wifi y ethernet de la
cual selecionaresmos Arduino uno y la shield ethernet W5500 que es con la que trabajaremos así
como se muestra en la figura 71.

Página 73 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figurar 71.- Interfaz web para selección de modelo Arduino y módulo ethernet

Después de seleccionar nuestra respectiva tarjeta y shield ethernet nos aparecerá una ventana con
el código de prueba que debemos copiar en nuestro scketch de Arduino para realizar una primera
prueba, luego lo podemos editar según lo que deseemos editar lo cual se expliacará más adelante

Página 74 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 72.- Código de prueba para arduino con cayenne

Luego de cagar el código de prueba del Arduino podemos abrir el monitor serial de nuestro Arduino
y nos mostrará la dirección MAC de nuestro dispositivo, la dirección IP asignada y el puerto por el
cual se a conectado como se muestra en la imagen:

Página 75 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 73.- Monitor serial.

Por otro lado, en la interfaz web nos mostrará un cuadro que nos indica un valor analógico del canal
analógico 0 que en este caso es virtual según el ejemplo de prueba, lo siguiente a realizar es
conectar un sensor analógico y realizar el respectivo código para mostrarlo en nuestra interfaz
gráfica.

Figura 74.- Interfaz web de Cayenne conIOT

A continuación, se muestra el código del ejemplo que nos proporciona Cayenne y se realizará una
pequeña prueba

/*
This example shows how to connect to Cayenne using an Ethernet W5100
shield and send/receive sample data.

The CayenneMQTT Library is required to run this sketch. If you have not
already done so you can install it from the Arduino IDE Library Manager.

Steps:
1. Set the Cayenne authentication info to match the authentication info
from the Dashboard.

Página 76 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

2. Compile and upload the sketch.


3. A temporary widget will be automatically generated in the Cayenne
Dashboard. To make the widget permanent click the plus sign on the
widget.
*/

//#define CAYENNE_DEBUG // Uncomment to show debug messages


#define CAYENNE_PRINT Serial // Comment this out to disable prints and
save space
#include <CayenneMQTTEthernetW5500.h>

// Cayenne authentication info. This should be obtained from the Cayenne


Dashboard.
char username[] = "82c420b0-7591-11e9-94e9-493d67fd755e";
char password[] = "f7a86e5c8a63c2eb8d4edb182d46b5681da844ab";
char clientID[] = "6a263420-8d66-11e9-9636-f9904f7b864b";

void setup() {
Serial.begin(9600);
Cayenne.begin(username, password, clientID);
}

void loop() {
Cayenne.loop();
}

// Default function for sending sensor data at intervals to Cayenne.


// You can also use functions for specific channels, e.g CAYENNE_OUT(1)
for sending channel 1 data.
CAYENNE_OUT_DEFAULT()
{
// Write data to Cayenne here. This example just sends the current
uptime in milliseconds on virtual channel 0.
Cayenne.virtualWrite(0, millis());
// Some examples of other functions you can use to send data.
//Cayenne.celsiusWrite(1, 22.0);
//Cayenne.luxWrite(2, 700);
//Cayenne.virtualWrite(3, 50, TYPE_PROXIMITY, UNIT_CENTIMETER);
}

// Default function for processing actuator commands from the Cayenne


Dashboard.
// You can also use functions for specific channels, e.g CAYENNE_IN(1)
for channel 1 commands.
CAYENNE_IN_DEFAULT()
{
CAYENNE_LOG("Channel %u, value %s", request.channel,
getValue.asString());
//Process message here. If there is an error set an error message
using getValue.setError(), e.g getValue.setError("Error message");
}

Luego de realizar estas conexiones ya tendremos conectado nuestra tarjeta de Arduino a internet
de manera sencilla gracias a Cayenne; lo siguiente a realizar es realizar la conexión de dispositivos
como ya se ha realizado en laboratorios anteriores pero esta vez empleando la herramienta de
Cayenne como se explicará a continuación.

Página 77 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Agregando dispositivos a nuestra tarjeta Arduino:

Figura 75.- Agregar dispositivos en la Interfaz web de Cayenne.

A continuación nos dirigimos a Custom Widgets y buscamos la opción Slider como se muestra en
la siguiente imagen:

Figura 76.- Interfaz web de Cayenne después de agregar dispositivos.

Luego nos mostrará un cuadro para ingresar las configuraciones como el nombre, a que dispositivo
se conectará, en nuestro caso selecionaremos el Arduino Mega que hemos agregado previamente
y otros parámetros los cuales se pueden apreciar en la figura:

Página 78 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

Figura 77.- Interfaz web de Cayenne.

A continuación se muestra un código en el cual se controlará una salida digital, una salida analógica
PWM y un servomotor, el código

#define CAYENNE_PRINT Serial


#include <CayenneMQTTEthernet.h>
#include <Servo.h>
char username[] = "82c420b0-7591-11e9-94e9-493d67fd755e";
char password[] = "f7a86e5c8a63c2eb8d4edb182d46b5681da844ab";
char clientID[] = "02097060-b7fe-11e9-809b-df5a1171d82f";

#define VIRTUAL_CHANNEL 1
#define VIRTUAL_CHANNEL2 2
#define VIRTUAL_CHANNEL3 3
#define ACTUATOR_PIN 13
#define ACTUATOR_PIN2 6
#define ACTUATOR_PIN3 8

Servo s1;

void setup()
{
Serial.begin(9600);
pinMode(ACTUATOR_PIN, OUTPUT);
pinMode(ACTUATOR_PIN2, OUTPUT);
Cayenne.begin(username, password, clientID);
s1.attach(ACTUATOR_PIN3);
}

void loop()

Página 79 de 80 Programación en Arduino


Universidad de Piura Sistemas Digitales
Sistemas Digitales

{
Cayenne.loop();
}

CAYENNE_IN(VIRTUAL_CHANNEL)
{
int value = getValue.asInt();
CAYENNE_LOG("Channel %d, pin %d, value %d", VIRTUAL_CHANNEL, ACTUATOR_PIN,
value);
digitalWrite(ACTUATOR_PIN, value);
}

CAYENNE_IN(VIRTUAL_CHANNEL2)
{
int value2 = getValue.asInt();
CAYENNE_LOG("Channel %d, pin %d, value2 %d", VIRTUAL_CHANNEL2, ACTUATOR_PIN2,
value2);
analogWrite(ACTUATOR_PIN2, value2);
}

CAYENNE_IN(VIRTUAL_CHANNEL3)
{
int position = getValue.asDouble();
s1.write(position);
}

Agregamos los siguientes widgets para controlar las cargas como se muestran en la siguiente
imagen:

Figura 78.- Ejemplos de widgets

Página 80 de 80 Programación en Arduino

También podría gustarte