Automatismo y Robotica Con Arduino
Automatismo y Robotica Con Arduino
Vivimos en un mundo dominado por la energía eléctrica. Tenemos a nuestra disposición otras
energías, los combustibles, gaseosos o líquidos, pero suelen tener usos muy concretos como la
calefacción, los fogones y el coche, mientras que la energía eléctrica da vida a todo tipo de
aparatos que nos rodean. Por otra parte, elementos como puertas. válvulas de agua, sistemas de
filtrado, etc, pueden ser fácilmente gestionados con la inclusión de equipos eléctricos
especializados en su control y protección.
Desde el radio despertador con el que amanecemos, hasta la luz que apagamos al dormir, toda
nuestra vida está rodeada de aparatos eléctricos, incluso cuando el aparato utiliza como fuente
principal otra clase de energía, por ejemplo, el gas natural de calefacción, su uso está regulado por
la electricidad, ósea, la corriente eléctrica quien regula el consumo de esos combustibles.
Por ello si tenemos un medio de controlar los circuitos eléctricos tenemos un medio de controlar el
mundo que nos rodea. Eso es lo que permite el conocimiento de Arduino
Qué es Arduino
Arduino es una tarjeta, como la que se ve en la imagen, que contiene un microcontrolador que a
través de sencillos programas de software hechos en un PC, permite captar información del
entorno, con todo tipo de sensores, tanto digitales como analógicos, como relojes, medidores de
temperatura, de ruido, de luz, pulsación en botones, inerciómetros, altímetros, GPS, micrófonos,
etc. y con la información captada y elaborada en el procesador generar la respuesta adecuada sobre
cómo deben actuar los circuitos eléctricos que alimentan luces, motores, altavoces, y cualquier
aparato eléctrico diseñado para realizar cualquier tipo de acción.
Arduino puede actuar como el cerebro de cualquier proyecto que puedan imaginar, tanto por
aficionados, como por diseñadores profesional interesado en crear objetos que interactúan con el
entorno, como sistemas de alarma, domótica, robótica, etc. Algo que no es nada nuevo, pero que
por primera vez está específicamente diseñado para el manejo de particulares y aficionados, y no
precisar para su uso, ni de conocimientos especializados, ni de talleres ni herramientas
especializados, ni de grandes dispendios económicos.
Software de Arduino
Hardware de Arduino
Tarjeta Arduino – Hay muchas tarjetas compatible Windows y constantemente aparecen más en
el mercado las más conocidas son la UNO, Duemile, Leonardo, Pro, Mini, cada uno con ventajas y
posibilidades específicas. Para un principiante yo aconsejo la UNO, por ser suficiente para los
proyectos con los que se puede enfrentar de momento y que con la compra de baratas tarjetas de
expansión, como comunicación wifia, tarjeta de relés, controladores de motores etc.
Cable USB – Para conectar el Pc con la tarjeta, un extremo es el terminal macho estándar plano
más conocido, el otro extremo suele ser un terminal macho estándar pero menos conocido,
habitualmente uno de sección cuadrado, si es para la tarjeta Arduino UNO, pero dependiendo de la
tarjeta puede ser otro.
Cables de conexión – Son cables de un solo hilo conductor recubierto de un plástico de colores,
utilizados para conectar entre sí los orificios del protoboard, Conviene tener de varios colores,
rojo, azul, verde, amarillo y blanco, cuantos más colores mejor, para poder seguir con mas
facilidad los circuitos eléctricos de los montajes que hagamos en la protoboard. Pueden hacerse a
partir un cable que se venden por metros, (un metro de cada color da para muchos cables), sin
embargo, aconsejo comprar unos montados con una terminal de un alambre más rígido que un
cable eléctrico pues se manejan con más comodidad,
Leds, de colores –. Para el semáforo necesitaremos varios leds de colores rojo, verde, naranja y
blanco, cada led y necesitamos mínimo dos de cada color
Potenciómetros – Son resistencias variables, los que necesitamos basta que cubran el espectro de 0
a10 kohms. Con un tres tenemos suficientes.
Pulsadores – Son interruptores de corriente que funcionan como los timbres cierran un circuito
cuando se oprimen, pero normalmente el circuito está desconectado. necesitamos otro par de ellos.
Mi consejo por ello es que compres online un kit de iniciación que tiene un poco de todo como
punto de partida, por ejemplo yo creo muy
util el kit de iniciación que vende Deal
Extreme llamado Y1204 ATmega328 UNO
Kits de desarrollo de la Junta para
principiantes.
1 x Arduino UNO
1 x USB cable (57cm)
2 x Breadboards
25 x Breadboard cables de puente
30 x Carbono resistentes a la 100R
30 x Carbono resistentes a la 1K
30 x Carbono resistentes a la 4.7K
30 x Carbono resistentes a la 10K
30 x Carbono resistentes a la 47K
30 x Carbono resistentes a la 100K
30 x carbono resistentes a la 1M
2 potenciómetros 10K x Monovuelta
2 x potenciómetros turm 100K Individual
3 x F5 LED blanco verde
3 x F5 LED blanco rojo
3 x F5 LED blanco amarillo
3 x F5 LED blanco
6 x Tact switches
3 x interruptores de tacto redondo (azul)
3 x interruptores de tacto redondo (rojo)
3 x interruptores de tacto redondo (blanco)
3 x interruptores de tacto Cuadrados (blanco)
3 x interruptores de tacto Cuadrados (verde)
2 x conectores pin header
Para comprender de lo que es capaz de hacer Arduino voy a describir que partes componen la
placa y cuál es su uso. No te preocupes demasiado pues en post sucesivos y a medida que
utilicemos cada uno de estos componentes explicaremos en detalle su utilidad y como se usan al
detalle, hoy solo damos una descripción genera a vista de pájaro.
Uno de los problemas tradicionales de los aparatos construidos bajo licencia open hardware, es
que viene sin documentación técnica, pues así se reduce gastos y se espera que tú la encuentres
en Internet, pues con seguridad, ahí sí que está la documentación. El segundo problema es que no
hay un único modelo de placa de Arduino, sino que existen varias, pues al ser un
producto OPEN SOURCE, y no estar protegido por patentas, cualquiera, (que tenga los
suficientes conocimientos y un amplio taller de electrónica), puede fabricar la placa y
comercializarla.
Por lo tanto las placas que hay en el mercado serán parecidas, pero no necesariamente iguales,
pues para tener una ventaja competitiva en este duro mercado, cada cual la hace con una
característica que las diferencia de las demás, bien en tamaño, o en prestaciones, o similar pero
utilizando componentes de bajo precio etc. por lo que incluso las que son parecidas pueden no
serlo y otras no serán ni parecidas pues buscan solucionar problemas específicos o tiene
capacidades muy superiores a las placas originales.
Cuando mezclas ambos problema, resultara que no estarás nunca seguro que las especificaciones
que encuentras en Internet sean las que correspondan exactamente con las de tu modelo y serie de
fabricación, o son de otra parecida pero no igual. Esto es así y nos guste o no hay que vivir con
ello, pero cierto es, que, a pesar de ser un problema, la sangre no llega al rio y de una forma u otra
todos los aficionados a Arduino vamos resolviendo el problema.
Por ejemplo Alonsojpd, persona que con sus escritos me enseñó mucho y yo, utilizamos la placa
modelo Arduino UNO R3, la mía es la que se ve al inicio del post y tiene ligera diferencias con la
de Alonsojpd cuya foto he sacado de su página web
Si se
fijan el botón de Reset (pequeño botón rojo que vuelve a iniciar el programa que hay cargado en la
placa desde el principio), en mi placa está situado en la esquina superior izquierda, (un puntito
rojo), mientras que en la placa que se muestra en la web está situado a la mitad de la tarjeta y en el
lado derecho junto a unos pinchos de para mi y por ahora, utilidad desconocida, (quizá sea un
puerto serie), mientras que donde en mi tarjeta está el botón de Reset se ve un texto que dice
MADE IN ITALY, ello indica que la tarjeta de Alonsojpd es muy probablemente una tarjeta
fabricada por los inventores de Arduino y la mía casi seguro una copia más o menos clónica, (y
más barata), que es legal, pues una copia de Arduino no puede ser ilegal nunca, pero no es
“original”, aunque tiene un funcionamiento semejante a la original, (aunque probablemente con
componentes más baratos y de menor duración), y muy posiblemente suficiente para el trote
moderado a que yo le someto y le vamos a dar nosotros.
Incluyo otra imagen de Arduino UNO “original “con el esquema de los componentes que son
importante en ella (desde el punto de vista del usuario).
Ya explicaremos en su momento esto con más detalle, de momento quédense con la copla de que
pese a parecer todos los pines iguales, hay dos tipos de pines digitales unos modulados y otros no.
Lógicamente esto solo ocurre si hemos utilizado esos pines como OUPUT, pues como detectores
de energía todos funcionan igual
Pues lo que acabo de decir también es falso hay dos pines el 2 y el 3 que funcionando en OUPUT
tiene un funcionamiento diferente al resto de los pines de E/S. Tiene la propiedad de detectar
interrupciones. De ello hablaremos con detalle en su momento, pero en general un Pin utilizado
como OUPUT, en un momento determinado del programa preguntamos si tiene o no voltaje. Esto
se muy útil cuando el proceso lo controlamos nosotros por programa, por ejemplo, si un motor
acaba en un pin de OUPUT, podremos saber si anda o no está parado estudiando si este pin recibe
energía (porque el motor funciona) o no, porque se ha interrumpido el suministro.
Para una acción que tenemos prevista, por ejemplo, cundo ha dado tres vueltas completas,
paramos el motor y en otra parte del programa consultamos periódicamente si está parado y si lo
está, cambiamos el sentido de giro del motor y lo volvemos a arrancar. Habremos hecho un
aparato que funciona en va y ven cada tres vueltas del motor. Perfecto, pero, y si el evento que va
a ocurrir es imprevisible saber cuándo ocurrirá y hay que detectarlo nada más ocurre, ¿cómo lo
controlamos? Por ejemplo queremos para un robot que limpia gallineros cundo entre una gallina
para no asustarla, podemos poner un detector de paso de gallinas en la entrada, pero ¿Cuándo
preguntamos si ha pasado la gallina, si l0 hacemos periódicamente, por ejemplo cada tres minutos,
sabremos que ha entrado la gallina tarde, pero si constantemente estamos comprobando si llega
una gallina, ¿cuándo hacemos las cosas que necesitamos hacer con el robot? – La solución es
encargar de detect0r al pin 2 o al 3 puse ellos lanzan una función de detección del robot cundo
detecten el paso de la gallina independientemente de en qué ciclo del programa esté, haciendo en
este momento. mientras no ocurra la incidencia el programa transcurrirá normalmente, cundo
ocurra se prioriza hacer la función que lanza la interrupción
También el Pin 13 tiene algo que le diferencia del resto y es tener asociado un pequeño Led
amarillo marcado con una “L” que en la imagen se ve a la altura del Pin 13, pero inmediatamente
debajo del óvalo pintado de azul. Cuando por el pin 13 pasa corriente el Led se enciende teniendo
de este modo una comprobación visual de lo que está ocurriendo.
Botón de Reset
2. En el centro derecha Botón “Reset” (reiniciar)de la tarjeta (Del que ya hemos hablado y
permite el reinicio de la misma, es decir volver a leer el programa desde la primera sentencia. El
efecto es semejante al apagar y volver a empezar que tan feliz nos hace a los informáticos, que con
ello resolvemos el 90% de los problemas que no sabemos cómo arreglar. (Situado junto a la salida
USB en muchas placas (entre otra en la mía)
Entradas/salidas analógicas
Línea de Alimentación
4. En el centro de la parte inferior Línea de alimentación. En estos pines podemos encontrar:
Vin, (Proporciona el mismo voltaje que se introduce en la tarjeta, si recibe 9 volts ese pin da 9
volts, y si recibe 7 da 7 es como un enchufe directo al cable de entrada,
Tierra (GND)
Hay dos pines marcados como Tierra (GND =Ground), pon eso el lugar que siempre está a cero
voltios. y valen de sumidero de la corriente continua,
Cinco voltios 5V
Proporciona 5 voltios independientemente del voltaje que reciba la tarjeta e pero la energía que
puede dar está limitada a 40 miliamperioos, suficiente para muchas cosas, pero no suficientes para
trabajos de consumo de energía por ejemplo mover motores o calentar, algo que tendremos que
hacer con fuentes auxiliares de energía utilizando Arduino para regularlas y controlarlas por eso se
llama la a tarjeta una controladora.
Proporciona 3,3 voltios independientemente del voltaje que reciba en condiciones similares al
anterior
Reset
El pin Reset tampoco lo sé utilizar de momento, supongo que al recibir una corriente reinicia el
programa como si apretáramos el botón rojo.
[Link] la parte inferior izquierda Plug de alimentación (enchufe) de la tarjeta, para voltajes
entre 7 a 12 volts. La tarjeta se puede alimentar de corriente por dos sistemas por el cable USB
que le cede corriente del ordenador, o por otra fuente generalmente baterías o un transformador de
corriente alterna a corriente continua, (tipo cargador de teléfonos móviles), en cualquier caso el
voltaje e entrada a de estar dentro del rango comprendido entre 7 y 12 voltios, pues es ese rango
donde la tarjeta es capaz de cambiar el voltaje internamente a 5 voltios que es el voltaje con que
trabajan los componentes electrónicos que tiene. La posibilidad de trabajar con baterías permite
hacer aparatos que actúan de forma autónoma aun que estén desenchufados del ordenador, Por
ejemplo, si queremos poner un sistema de vigilancia en el chalet, puede funcionar con energía de
una pila o de la electricidad del chalet sin tener en el un ordenador.
6. Regulador de voltaje.
En el centro de la parte derecha Regulación del Voltaje. No se aun como funciona, pero creo
que el voltaje se regula automáticamente y no tenemos que hacer nosotros nada, es quien
independiente que alimentemos la tarjeta con 7 o 12 voltios genera 5 voltios para su consumo
interno.
7. Conector USB.
En la esquina superior derecha conector USB Enchufe del cable que le une físicamente la
Tarjeta Arduino al PC. Por ese cable pasan las siguientes cosas:
Electricidad a 5 voltios para alimentación de Arduino, Como indicamos más arriba la tarjeta
puede recibir corriente eléctrica de dos fuentes del PC, por el cable USB, o por la otra entrada
corrinte entre 7 y 12 voltios procedente de una fuente exterior (bateria o transformador), que
permite a Arduino trabajar de forma autónoma separada del PC. al tener puesto el cable USB la
tarjeta” come” de la fuente de alimentación del PC.
Transferir programas También el cable vale para transferir el programa del PC una vez
compilado, (traducido automáticamente a lenguaje maquina) al procesador de Arduino
Procesador de Arduino
8. En el centro de la placa está el procesador, un chip rectangular de gran tamaño y múltiples
patas, ese es el procesador de Arduino, (su cerebro). Cuando escribimos en nuestro PC un
programa, (sketch) y lo compilamos, es decir lo traducimos automáticamente del “lenguaje de
programación”, (literal, aunque de sintaxis obligatoria y muy concreta), en el que le hemos escrito
el programa, a “lenguaje máquina” muy complejo y abstracto para los humanos, pero el único que
entiende el procesador ) y una vez compilado lo transferimos una copia de ese programa
compilado del PC al procesador donde queda grabado de forma permanente, (aunque lo
desenchufemos), y solo cambia cuando un nuevo sketch se va a escribir sobre el anterior. Este
comienza a leer las instrucciones que programamos en orden tal como las grabamos y a ejecutarlas
de forma secuencial (una de tras de otra), mandando voltajes a los pies utilizados de salida
(OUPUT) y leyendo el voltaje de los pines utilizados de entrada (INPUT) (a su vez va recorriendo
las sentencias siguiendo las pautas que nosotros hayamos escrito.
Aunque no nos parezca posible el procesador nunca comete errores sin embargo los humanos
tenemos tendencia a pasar muchas cosas por alto por qué no meditamos de cero, sino aunque nos
pese, vivimos de prejuicios, de presuponer que as cosas ocurren siempre de determinada forma,
aunque todos sabemos que no hay regla sin excepción, Si por ejemplo decidimos has esto si el
valor es menor que cinco y esto otro cuando sea mayor, todo funcionará perfectamente hasta que
eso tome exactamente el valor 5 y el programa no sepa que hacer porque no lo hemos programado.
Led RX t TX
9. Existen dos pequeños Led marcados con las siglas TX y RX situados un poco por debajo del
Led del Pin 13, que parpadean cuando (TX) transmiten información de la tarjeta al PC, o cuando
(RX) reciben instrucciones del PC a la controladora. Los veremos por ejemplo parpadear cuando
se cargue el programa del PC en el controlador y cuando enviemos datos síncronos en un sentido o
en otro durante el procesamiento del programa
Descripción de las principales Tarjetas controladoras de la familia Arduino
Enseña las placas controladoras de la familia Arduino más conocidas sin ninguna intención de
pretender cubrir todas las existentes sino tan solo las más conocidas. Lo que enseño no llegará ni
al % de lo que existe, pero espero que os valga para daros cuenta de la riqueza que hay en el
mundo de Arduino y que si bien lo podemos considerar un juguetee y un hobby es mucho más que
eso.
Arduino UNO R3
Esla más representativa de la familia Arduino, la más popular y en consecuencia de las de menor
precio su aspecto se asemeja a las que he mostrado en el post aunque las hay de otros colores por
ejmplo esta llamada Zduino UNO Posée un Micro controlador: ATmega328, voltaje de
funcionamiento: 5V, voltaje de entrada (recomendado) 7-12V, voltaje de entrada (límites): 6-20V,
I / O Pins digitales: 14 (de los cuales 6 proporcionan PWM), clavijas de entrada analógica: 6, DC
Corriente por I / O Pin: 40 mA, CC para Pin 3.3V Corriente: 50 mA Memoria Flash: 32 KB
(ATmega328) de los cuales 0,5 KB usados por bootloader, SRAM: 2 KB (ATmega328)
EEPROM: 1 KB (ATmega328), Velocidad de reloj: 16 MHz
Arduino DUE Con un Core (nucleo de procesado) de 32 bits permite operaciones en 4 bytes de
datos y reloj en 84Mhz, 96KB de SRAM, 512 KB de memoria flash para el código. Arduino Due
se basa en la de 32 bits del procesador Atmel SAM3X8E ARM Cortex-M3 MCU y mejora todas
las funcionalidades estándar de Arduino y añade muchas nuevas características, el Arduino Due
ofrece 54 pines de entrada / salida digitales, 12 entradas analógicas, 4 UART , dos salidas DAC,
un oscilador de cristal de 84MHz, dos CII, conexión OTG USB, un conector de alimentación, un
header ICSP, una cabecera SPI, un botón de reinicio y el botón de borrar. La tensión máxima que
los pines de E / S pueden proporcionar o tolerar es 3.3V. La placa tiene dos conectores USB micro
– uno
para
fines
de
depuración y otro capaz de actuar como un host USB, lo que permite periféricos externos USB
como ratones, teclados, teléfonos inteligentes, etc para ser conectados a la placa Arduino Due. La
placa contiene todo lo necesario para apoyar el microcontrolador, basta con conectarlo a un
ordenador con un cable USB o el poder con un adaptador AC-DC o batería para empezar. El
duque es compatible con todos los escudos de Arduino que trabajan a 3,3 V y son compatibles con
el pinout Arduino 1.0.1) ArduinoDUE (procesador ATSAM3X8E ARM Cortex-M3 corriendo a
84 Mhz de 32 bits).
ArduinoGalileo
Desarrollado por Arduino con Texas Instruments e Intel, es 100% compatible, placas mucho más
potentes, comparables a una Raspberry Pi, pero con un Arduino completo integrado en la
placa. Incorpora un Intel Quark SoC X1000 Application Processor, de 32 bit, perteneciente a la
familia Pentium con lo que su arquitectura es x86 con una velocidad de 400MHz. Dispone de
512Kb de RAM, 256MB de Almacenamiento Ethernet 10/100, conector PCI, Reloj de tiempo real
RTC USB HOST2.0 USB de programación Tarjeta micros
Arduino
Leonardo El
Leonardo es una placa electrónica basada en el [Link] de 20 pines de entrada /
salida digital (de los cuales 7 se puede utilizar como salidas PWM y 12 como entradas analógicas),
un oscilador de 16MHz, una conexión micro USB, un conector de alimentación, una cabecera
ICSP, y un botón de reinicio. Contiene todo lo necesario para apoyar el microcontrolador, basta
con conectarlo a un ordenador con un cable USB o el poder con un adaptador AC-DC o batería
para empezar; El Leonardo difiere de todas las tablas anteriores, en que la ATMEGA32U4 ha
incorporado en comunicación USB, eliminando la necesidad de un procesador secundario. Esto
permite que el Leonardo que aparezca a un ordenador conectado como un ratón y un teclado,
además de un puerto serie / COM virtual (CDC).
Arduin0 Nano 3.0 Microcontroladores: Atmel ATMEGA328P-AU; Tensión de servicio: DC 5V
~ 12V; Digital – I / O Pins: 12 (D2 ~ D13, de las cuales 6 proporcionar una salida PWM), pin de
entrada analógica: 8 (A0 ~ A7) Ideal por su reducido tamaño para todo tipo de bricolage
Arduino Lily pad USB Arduino diseñado para ser cosido a tejidos y hacer con la ropa interactiva.
que reacción ante la temperatura, la lluvia la presencia de conocidos o cosas por el estilo.
microcontrolador, ATmega32u4, opera a 3,3 voltios, 9 pins digitales cuatro de ellos PW 32 K de
memoria, 2,5 SRAM, Reloj a 8 MH
Identificar en la Tarjeta
Controladora Arduino que
realmente tienes la situacion de
cada una de las partes indicadas eb
el post.
Sin embargo, la escritura del programa ha de hacerse de acuerdo con unas estrictas normas
sintácicas, debido a que el procesador solo entiende sentencias que contengan mandatos dados con
un formato predeterminado. Y que puedan ser cumplidos con una lógica sencilla, pero que aparta
al “lenguaje de programación”, del “lenguaje natural” que constantemente alude a un entorno
conocido.
Si dices (mandas) a alguien, “tráeme un vaso de agua”, estas dando por supuesto que esperas que
te traigan el recipiente llamado “vaso de agua”, pero aunque no lo hayas especificado, que te lo
traigan lleno de agua y no tienes que indicar donde esta el vaso de agua, ni le grifo, ni como se
abre el grifo, pero si una orden semejante se da a un procesador, de momento,y por muchos años,
este aparato carece de esos conocimientos del entorno, por lo que una orden similar dada a un
robot, es muchísimo mas compleja que dada a un humano.
Así por ejemplo si queremos restar el valor que en determinado momento del programa tienen dos
variables que vamos a llamar, “variable1” y “variable2” y queremos dejar el resultado de la resta
en la variable “diferencia”, escribiríamos una sentencia tal como:
Puede ocurrir que variable1 es menor que variable2, deberemos definir “diferencia” como variable
numérica con signo, puesto que puede alcanzar valores negativos y por último, es necesario
indicar el final de esta sentencia con un punto y coma “;” para que la máquina “se entere”, que
hemos acabado la sentencia y comenzamos otra nueva, sino lo que escribimos, aunque esté en otra
línea, entenderá que son elementos de la fórmula matemática que estamos definiendo, y al no
encontrar el símbolo de operación entre ello dará un error.
Por ejemplo, muchas veces se nos olvidará poner el caracter punto y como “;” al final de una
sentencia, o tecleas mal y pones dos puntos “:” o simplemente coma “,”. La máquina siempre
piensa que el error no es ese, sino que deseas incorporar a la sentencia el contenido de la siguiente
fila, dando así lugar a textos de error tan vaiados e inútiles.
Afortunadamente, no siempre ocurre eso y a veces el mensaje de error es más o menos certero y
nos facilita arreglar los errores que cometemos, por ejemplo, si escribo “varable1” en vez
“variable1” dira algo así como “varable1 not defined”, pues no sabe que he cometido un error de
ortografía, sino simplemente, que “varable1” no esta definida como variable de ningúno de los
diferentes tipos de los posibles. Sin ser perfecto el mensaje, en este caso nos orienta hacia que ese
nombre es incorrecto, bien por no haberle definido previamente, lo que también ocurre
frecuentemente, pues a medio programa podemos necesitar una nueva variable y se no olvida darla
de alta, o bien, porque lo hemos escrito mal.
A veces los confusos mensajes y la limitación disléxica, que a muchos nos impide leer
pausadamente que realmente hay escrito, y no leer lo que quisimos escribir, hace que nos
volvamos algo locos a la hora de poner a punto un programa
Una vez pasada la validación podremos pasar al siguiente punto compilar (traducir al “lenguaje
máquina”) el programam (sketch), o y trasladarlo a la tarjeta controlador Arduino
3- Compilación y traspasar el
programa,
¿Qué es compilar?
Una vez cambiado todo el programa a instrucciones de lenguaje máquina se carga también
automáticamente ese programa en la Tarjeta controladora en concreto en el procesador que es el
chip más grande y con más patas de la tarjeta, lo que podremos observar pues hay dos leds
marcados como RX y TX que parpadean mientras el programa se trasfiere a la tarjeta. Al cargar
un nuevo progrma se destruye el que hubiera anteriormente y esta es la forma de destruir un
programa de la tarjeta controladora, por que sino, con solo dar energía a la tarjeta el programa que
tenga grabado internamente se pone en marcha.
Esos aparatos que físicamente forman parte del PC no dan problemas pues ya están debidamente
conectados de fábrica. Hay otras salidas más conflictivas y varias suelen ser salidas USB. Por ello
se conectan los aparatos habituales, como un pendriver, un disco duro o una impresora, las
cámaras fotográficas, etc.
Los ordenadores modernos suelen estar preparados (aunque no siempre) para reconocerlos y una
vez detectados automáticamente reciben/envían los datos como los necesitan esos aparatos, no
entran igual los aparatos de un scanner que de un disco duro, pero el PC internamente asimila los
cambios que hay que dar a la informacion para que los datos sean útiles a ambos lados del cable.
A veces pasa que una determinada máquina no es reconocida de fábrica, (algo cada vez más raro),
entonces es necesario cargar un “driver” (conductor) que es un programa intermedio que
transforma el formato de los datos que salen/ entran en el procesador, tal como los necesita el
aparato que d se conecta.
Entre estos equipos no habituales está la Tarjeta Arduino, por eso hay que cargar un “driver”
dentro del PC que preparan los datos tal como conviene a ambas máquinas, para ello “engaña” al
ordenador haciéndole creer que esta unida a un “puerto com” y cambia la información que
circularía en ese punto a una salida USB, mucho más sencilla de manejar por un no experto pues
basta con enchufar y desenchufar.
Pero como oficialmente las cosas entran por un determinado “puerto com”, tendremos que
asegurarnos que los programas que enviamos a Arduino manden la información como si fuera a
ese determinado “puerto com” que se asigna a Arduino, por lo que antes de compilar indicamos el
“puerto com” que hemos de utilizar para que así quede grabado en el programa en lenguaje
máquina. Si no tenemos bien elegido el “[Link]” tendremos que indicarlo seleccionandolo
manualmente y repitiendo la compilación.
La satisfacción total nos llega cuando hemos conseguido finalizar el programa sin que la
validación detecte un error, hemos compilado el programa y transferido con éxito a Arduino el
programa, algo que físicamente observaremos al ver parpadear unos leds marcados como RX y
TX. Sin embargo, solo hemos pasado la primera barrera, que consiste en la depuración de errores.
Otra fase, que consiste en eliminar los errores de lógica. Incluso en programas sencillos, se nos
escapan posibles estados que quedan fuera de control y que hacen que el aparato que hemos
diseñado funcione, pero no como habíamos previsto, sino de una forma aleatoria o que se meta en
un callejón sin salida.
Para llegar a esto será necesario cargar en nuestro PC los programas de edición, validación,
compilación y carga de los programas en la tarjeta así, como el “driver” que permita
reconocer la tarjeta controladora Arduino
Los “sketch” o programas de Arduino están sujeto a un esquema fijo e invariable, El programa en
su conjunto está formado por dos partes:
La primera se recorre una única vez y nunca más vuelve a pasar por ella, (salvo que se reinicie el
programa, haciendo eso que nos gusta tanto a los informáticos de apagando el aparato y volverlo a
encender, o el equivalente que es apretando el botón “Reset” o posiblemente mandando tensión al
pin “reset” de la tarjeta)
Pero ¿como el “PROCESO” puede mandar cosas tan diversas si no hace mas que dar vueltas? – La
cosa tiene un pequeño truco, lo que llamamos “PROCESO” es en realidad, un conjunto de cajas
que contienen instruciones diferentes dentro, estas cajas se abren y se hace lo que dice en el
interior o no se abren y se pasa a la siguiente de acuerdo con algo que ocurre que esta
preestablecido en el programa.
Programar es pues dividir de un proceso complejo en procesos simples, proceso que podemos
descomponer en otros aún más sencillos, de modo que pasemos de lo complejo a lo sencillo. Al fin
y al cabo, la tarjeta Aarduino, solo va a encender y apagar circuitos y a mirar el voltaje de otros
circuitos, por tanto, podemos descomponer cualquier proceso en miles de instrucciones simples
hasta llegar a la instrucción de encender y apagar.
La virtud está en el término medio, descomponer una tarea, que no tenemos ni idea como podemos
programarla, en otras más simples que sí sepamos programar con las funciones básicas que viene
en la librería de nuestro lenguaje de programación y dejar que eso que han inventado otros sea lo
que encienda y apague los circuitos.
Volviendo a los “sketch”, (esquema) de Arduino, estos tiene dos partes en la primera se definen
las variables y parámetros que vamos a utilizar en el programa y a continuación entra la función
“setup()”, (configurar) que define como que parte de la tarjeta va a funcionar y cómo lo va a
hacer, que pines estarán activos, por cuales se va a poder enviar energía, (OUTPUT) o por cuales
se recibirá energía de fuera, (INPUT.). si vamos a utilizar comunicaciones síncronas o no y con
que velocidad se van a mandar los impulsos que marcan si se mando un 0 o un 1 y poco más.
A continuación, comienza la función “loop( )” (bucle) que como hemos indicado se ejecuta en su
totalidad indefinidamente, aunque en cada vuelta puede que lo haga de forma diferente en función
de valores que al cambiar hagan que unas sentencias se ejecuten y otras se salten en ese bucle.
Indicar donde se encuentra y como se descarga de la Red todo el software que necesitamos
instalar en nuestro PC para programar la tarjeta controladora Arduino e instalar los controladores
que permiten al PC reconocer a la tarjeta Arduino cuando se le conecta a través de un puerto
USB.
Material necesario
Tarjeta Arduino y su cable de USB de conexión, adquiere un kit, tarjeta de relés, control de
motores, motores eléctricos y algunos sensores, tendrás material para muchos capítulos de este
Curso de Arduino. Mucho del material necesario, como cables, interruptores, leds, motores, etc.,
pueden obtenerse de electrodomésticos y juguetes viejos y rotos. La afición a Arduino es
realmente económica.
Para manejar Arduino necesitamos una serie de programas que nos permitan escribiren nuestro
PC los programas que manejaran la tarjeta Arduino y una vez compilados (hechos comprensibles a
las máquinas), cargarlos posteriormente en la tarjeta Arduino. Esto es lo que se llama instalar un
entorno de desarrollo en nuestro PC (Software IDE de desarrollo), y también necesitamos
instalar los controladores de Arduino, (device drivers), software que informa a tu PC, el tipo de
aparato que se le conecta por USB y que le explica cómo tiene que manejarlo, pues por el USB, se
puede poner cualquier cosa, de un scanner, a un ratón, o esta tarjeta y el PC, tiene que identificar
que es, para saber, como tiene que mandar los datos al aparato y que tipo tienen los datos que
puede esperar recibir por ese puerto USB.
Los aparatos normales y los comerciales, teclados, pantallas, cámaras fotográficas etc.
generalmente pagan a Microsoft, para que tenga los programas de reconocimientos, (drivers),
incluidos de serie en su software por lo tanto no hay que instalarlos, o bien hacen un programa de
auto instalación, que los introducen casi automáticamente. Ests última opcion es la que ha puesto
en marcha hace poco Arduino, en vez de dar dinero a Microsoft, se ha hecho un programa de auto
instalación que solo tienes que dar varios “Intros” para instalarlo y otra buena noticia, todos esos
programas son ABSOLUTAMENTE GRATUITOS, no tienen publicidad y no piden datos
nuestros.
Los programas son de una organización que los desarrolla en un ambiente universitario y la gente
que los hace son mayoritaria, entes estudiantes de postgrado con becas de estudios, por tanto, su
trabajo o es voluntario, o pagado con dinero público, por ello es gratuito para el público
particular, aunque como es lógico y natural, no desprecian las donaciones que voluntariamente
quiera hacer cada cual que ayudan a depender menos del dinero público.
Licencia Copyleft
Los programas de Arduino tienen la licencia COPYLEFT, esta licencia a diferencia de la habitual
COPYRIGHT, permite expresamente que puedas copiar, vender o modificar los programas
originales hechos por otros siempre y cuando tus programas sean a su vez COPYLEFT. Estas
licencias tienden a crear un “ecosistema” que crece con el tiempo, pero se conserva gratuito. Cada
vez es mas grande. valioso y poderoso, al ir acumulando el trabajo de más personas, y a su vez
crea una masa critica de usuarios suficientemente grande como para que trabajar para este grupo
sea rentable aun obteniendo por cada objeto un reducido beneficio.
Por ello, no solo puedes bajarte los programas compilado, sino las fuentes.
Estos programas fuentes, si puede ser con ciertos conocimientos ser manejados y entendidos por
un técnico de nivel medio y, por tanto, son susceptibles de ser copiados y modificados dando lugar
a procesos mas perfectos o mas poderosos. Se bajaran solo los programas compilados que son los
que vas a utilizar si no tu si tu ordenador y tu tarjeta, pero si en un futuro lejano, aprendes tanto,
que deseas modificar estos programas para algún invento tuyo, debes saber que están disponibles y
tienes legalmente derecho de utilizarlos, con la sola condición de que entregues los programas
fuentes que generes a partir de estos y que queden cubierto con el mismo tipo de licencia con que
se te cedieron, es decir que cualquiera pueda a su vez gratuitamente tomarlos, utilizarlos, y
modificarlos.
Como este trabajo se hace una única vez en cada ordenador, mi consejo es no romperte la cabeza
y seguir al pie de la letra, (en la medida que lo permita tu sistema operativo), las instrucciones que
doy. Veamos los distintos pasos que componen el proceso
1º.- Buscar la página donde está el Software
2º Ir a la página de descargas
Si tu no eres geek con seguridad tu sistema operativo es uno de los dos primeros si tu equipo es
Apple es Mac OS X y si no es Apple es Windows.
Si sospechas que es Windows puedes confirmarlo pinchando la siguiente dirección que te lleva
a una página de Windows que analiza el sistema Windows que tienes instalado y te dice cual es
exactamente. En mi caso como se ve en la imagen es el Windowa 8.1
De las dos opciones la primera le va a ha hacer automáticamente una instalación estándar, creando
las carpetas que contendrán los ficheros de programas con nombres predeterminados y colgado de
sitios predeterminados, mientras que la segunda opción permite que personalices la instalación.
Salvo que sepas mucho del tema y seas un poco maniático de tu propio sistema de orden te
aconsejo la primera opción.
4º Contribución económica
En la opción Windows installer, se pasa a otra página donde solicitan una donación voluntaria.
No es mi intención desanimarte
de que cedas dinero si te parece
oportuno, pero si te informo que
el hacerlo, no te da ningún tipo de
ventaja, (salvo la moral), sobre no
hacerlo si pinchas en la opción
CONTRIBUITES DOWLOAD,
contribuyes al mantenimiento de
los pequeños gastos que tiene el
mantenimiento de este servicio.
5º Descargar
Si pinchas en JUST DOWLOAD (Sólo descargar) veras que en la parte inferior de la pantalla
aparece una nueva opción de seguridad que te pregunta
Si das a Ejecutar, posiblemente te aparezca una pantalla que te solicita permiso para cambiar
automáticamente cosas en tu sistema operativo que no ha podido capturar. Di que das
permisopuedo asegurarte que de donde bajas el software es un lugar absolutamente seguro que no
te meterá basura en tu PC.
7º Licencia C0pyleft
8º Opciones de Instalción
A estas alturas, salvo que no tengas más tiempo o padezcas un ataque de ansiedad, no tiene sentido
Cancelar. Retroceder a la pantalla anterior tampoco tiene sentido, pues lo único que podemos
cambiar es la licencia que hemos firmado, así que aconsejo firmemente pinchar en NEXT
(Siguiente) que da paso a la siguiente Pantalla de Instalación de una carpeta que contendrá todo lo
que bajemos de Internet.
12 Finalizar
Acabado de instalar hemos acabado todos los procesos lo que nos permite que en la pantalla
anterior podamos dar a la tecla CLOSE (cerrar) y dar por finalizado el trabajo.
Nuevo Icono en el escritorio.- En el escritorio se le habrá instalado un icono mas con este aspecto
Que quizá la primera vez que lo apretemos nos haga que aparezca una
pantalla pidiendo autorización para su uso, Di que si lo autorizas y por
fin entrarás en el llamado Menú de Inicio de Arduino , aunque durante
unos instantes y se carga todo aparecerá esta otra pantalla
Material necesario
Llamar al
Menú de
Inicio de Arduino
void loop() {
// put your main code here, to run repetedly:
void setup () {
// ponga su código de configuración aquí, para ejecutar una vez:
}
void loop () {
// ponga su código principal aquí, para ejecutar repetidamente:
}
Eso si, lo hace muy rápido, pero solo hace eso y con eso, es capaz lo mismo de mandar un robot a
Marte que mandar un washApp a un amigo, algo muy sencillo, es capaz de realizar cosas muy
complicadas y diferentes.
Arduino, que no es mas que un aparato digital, y solo hace dos cosas y las hace bien y de hace
de fabrica, es decir no tienes, ni puedes programarlas tu, Hacer una vez lo que le mande la
función “setup” (preparar) y a continuación repetir una y otra vez lo que le mande la
función “loop” (bucle).
Nada mas encender Arduino, (Power Up Arduino), se inicia la función “setup” que se ejecuta
una sola vez, para inmediatamente iniciarse la función “loop” que cuando se acaba se repite una y
otra vez hasta que cortemos el suministro eléctrico. Es decir, si permanece siempre encendido, se
quedará repitiendo “loop” una y otra vez.
“void” quiere decir vacio,
¿Que es “void”? - “void” es una palabra reservada, sólo se puede utilizarse para cosas muy
determinadas y precisas y la función que viene a continuación no devuelve ningún valor,
cuadrado
anda tres pasos
gira 90 º a la derecha
anda tres pasos
gira 90 º a la derecha
anda tres pasos
gira 90 º a la derecha
anda tres pasos
gira 90 º a la derecha
Cada vez que el procesador del robot recorra la función “cuadrado··, el robot andará una ruta que
es un cuadrado de lado 3. Hemos definido un módulo o función llamado “cuadrado” que contiene
las instrucciones para hacer andar al robot un cuadrado. Podíamos definir acciones como
“triangulo” “rectangulo” o “dodecágono” que obligaran al robot a seguir determinadas figuras
geométricas. Funcion”, agrupacion de instrucciones para realizar un accion determinada.
Sin embargo, si el cuadrado que tenemos que hacer en vez de tres unidades fuera de cuatro,
tendríamos que volver a escribir todo el proceso. Una forma de generalizar el sistema es utilizar
“parámetros de entrada”.
cuadrado (n)
anda “n” pasos
gira 90 º a la derecha
anda “n” pasos
gira 90 º a la derecha
anda “n” pasos
gira 90 º a la derecha
anda “n” pasos
gira 90 º a la derecha
Hay un procedimiento para generalizar la acción de una función, que consiste en introducir
parámetros desde el encabezamiento de la función al interior de la función de modo que el
efecto realizado cambie acción a realizar de acuerdo con el valor de los “parámtros de entrada”.
En el ejemplo del cuadrado, basta mandar un sólo parámetro, el valor del lado del cuadrado, pero
en otros casos, como, por ejemplo, si quisiéramos que el robot andase paralelogramos, habría que
pasar dos parámetros, pues habría que indicar el valor del lado mayor y el del menor.
Parámetros de salida.
Claro está, que estas funciones que hemos hablado hacen una actividad y finalizan su trabajo, pero
hay otras funciones, que ademas realizan una actividad, en la que tienen que devolver un valor al
finalizar. Por ejemplo, en nuestro caso, podíamos necesitar saber lo que ha andado el robot, por lo
que la función seria algo asi:
camino cuadrado(n)
anda n pasos
gira 90 º a la derecha
anda n pasos
gira 90 º a la derecha
anda n pasos
gira 90 º a la derecha
anda n pasos
gira 90 º a la derecha
camino = 4 n
Retorna camino
Una función es algo muy cómodo, porque costará mas o menos escribirla, pero una vez escrita y
probada, se puede guardar en una “librería de funciones” y cuando en cualquier programa se
necesite realizar la misma acción, la buscamos en la “librería” y la volvemos a utilizar, con la
ventaja de que sabemos que está ya probada y funciona.
Con ello programamos mucho màs rápido y seguro y ademas, nos podemos aprovechar de lo
que otro ha escrito, copiando sus “librerías”. Te alegrara saber que a parte de una librería
estándar de funciones que vienen con Arduino, hay muchas librerías que te puedes bajar
gratuitamente, que contienen funciones especializadas en áreas concretas, como pueden ser, las
telecomunicación, funciones trigonometricas o logaritmicas, funciones para generar musica, o de
manejo de imágenes.
resultado nombrefuncion(parametros_entrada)
pero esta sintaxis corresponde a la forma mas general de escribir una función, que abarca
también a aquellas funciones que como la primera que vimos, no necesita parámetros de entrada.
En cuyo caso tendrán la forma reducida, donde los dos parentesis “()” indican que no hay
parámetros de entrada
resultado nombrefuncion()
ye incluso habrá casos que ni tiene parámetros de entrada, ni de respuesta de salida lo que
avisamos poniendo como respuesta “void” (vacio), es decir que no devuelve nada.
void nombrefuncion()
Asi pues, ya estamos en condiciones de entender lo que inicialmente nos parecía críptico y sin
sentido, Arduino llama de fábrica consecutivamente a dos funciones una que se llama “setup”
(preparar) que la llama un sola vez y otra función que llama repetidas veces que se llama “loop”
(bucle) y ambas funciones ni precisan que se las introduzcan parámetros por eso se pone “()” ni
devuelven ningún valor por eso las antecede “void”
Aun queda por explicar alguna cosa, como es que en Arduino se indica que el contenido que
componen las instrucciones que tiene la función, marcando cuando empieza y cuando acaba con
“corchetes”, comienza con un corchete de apertura “{“ y acaba con un corchete de cierre “}“
Estos corchetes se encuentran en el lado derecho del teclado de la linea de teclas que contiena a la
izquierda “a”y “s”, en los mismos caracteres que “´´” y “ç” y para escribirlos, igual que ocurre
con el carácter “@” hay que tener pulsada la tecla “Alt Gr” a la vez que se da ala tecla
correspondiente.
Bien, ya casi somos capaces de comprender lo que dice eso que aparece en la pantalla
void setup(){
// put your setuo code here , to run once:
Esta clarisimo funcion “setup” que no tiene paranetros de entrada, “()”· y ni devuelve ningún
valor, “void” que contine la siguiente instrucciones
la doble barra “//” (7 mayuscula) avisa a la maquina que lo que bien a continuación es un
“comentario”, un texto que no esta escrito para la máquina, sino para que los humanos se enteren.
Por ello, sea lo que sea lo que haya escrito después de “//” al compilar la función, (crear el fichero
objeto, que es el que entiende la máquina). se elimina y no se compila, lo que tiene un ventaja,
podemos documentar profusamente nuestras funciones sin que ello ocupe espacio en el fichero
final por que el compilador lo va a eliminar.
Bien volvamos a nuestra inicial criptica funcion y ademas como igual da lo que pone a la derecha
de la doble barra, lo ponemos en español para que quede mas claro.
void setup () {
// ponga su código de configuración aquí, para ejecutar una vez:
void loop () {
// ponga su código principal aquí, para ejecutar repetidamente:
¿Lo entiende ahora perfectamente? – Pues pasemos a hacer lo que amablemente nos piden.
O sea, con la funcion “setup”, construimos físicamente a tarjeta Arduino de acuerdo a nuestras
necesidades, igual que si cableáramos a mano la tarjeta como nos conviene. Claro está, ESO SE
HACE lo primero de todo, antes de empezar realmente a ejecutar el programa y (al menos por
ahora) UNA SOLA VEZ. Iniciado el funcionaniento de la tarjeta, queda configurada como
queramos, pero durante la ejecución del programa, no se puede cambiar, (salvo contadas
excepciones que iremos viendo).
De fabrica todos los pines operativos vienen pensados para medir voltajes, porque es la forma
que mejor se protege a la tarjeta de descargas eléctricas accidentales, puesto que está por defecto
demodo que queda preparada para medir voltajes es decir recibir descargas, pero por programa se
puede hacer que esos pines, actúen como lugares de salida de corriente eléctrica. Eso es lo
principal que se hace en la función “setup·, pero algunos pines pueden hacer más cosas, como
veremos en su momento y aquí es donde se avida a la Tarjeta Arduino que utilizaremos esas
posibilidades..
Utilizaremos el pin13. Este pin es diferente a los demás, porque tiene un pequeño led marcado
como L en la propia tarjeta Arduino, de modo que cuando mandemos salir corriente por el pin13
se encenderá el led y cuando no salga el led se mantent¡eme apagado. Asi. que sin mayores
complicaciones, podemos observar lo que pasa por el pin13
Definiremos pues el pin13 como de salida. Para ello tendremos que decir a Arduino que se
prepare (setup) para sacar engergía por el PIN13 y luego en el bucle le mandaremos
“encender “, esperar, “apagar”, esperar y volver a repetir (loop). De esta forma el led que esta
en la tarjeta se enciende y se apague intermiténtemente.
Veremos que en el interior de las cajas que representan las funciones han aparecido una serie de
lineas que seguinos sin entender demasiado bien. pero que aun así, sabemos lo que van a hacer, en
la funcion “setup” un mandato “pinMode” preparar un pin para sacar energía (OUTPUT) y en la
funcion “loop” un mandato “digitaWrite” encender o poner voltaje en alto (HIGH) el pin que
hemos preparado en “setup” como de salida o OUTPUT, otro mandato “delay” para un tiempo
(1000 milisegundos) el proceso, para luego poner el voltaje en bajo en el mismo pin (LOW) y
esperar otros 1000 milisegundos.
void setup() {
// código de configuración, PIN13 como SALIDA, para ejecutar una vez
pinMode(13, OUTPUT);
}
void loop() {
// código principal, encender, esperar, apagar, esperar
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
delay(1000);
}
Dentro de cada uno de las funciones que recorre Arduino de forma automática hemos puesto unas
funciones estandard que nos han dado en la libreria de software estandard de Arduino que nos
bajamos de al red.
Función “pinMode”
Untilizamos la funcion “pinMode” que prepara un pin digital como se le mande, que puede ser de
dos formas, de salida (OUPUT) o entrada (INPUT ). Como “OUPUT” queda preparado para
dejar salir corriente continua eléctrica a 5 Voltios cuando se lo mandan y no enviarla cuando se lo
pidamos. Como “INPUT”, puede medir si por otro circuito pasa corriente , (si por ese circuito
pasa electricidad o no), e informar de ello a la tarjeta, (pero eso lo veremos en otro capítulo).
La funcion “pinMode” (que puede traducirse como, “tipo_de_ pin”), tiene la siguiente sintaxis
pinMode(pin,mode)
Esta funcion no devuelve ningun valor al sistema por lotanto en principio deberia venir
encabezada por la palabra “void”, pero (una incongruencia) la funciones standard de Arduino
cuando no devuelven nada no ponen nada delante.
Por último cuando acabamos de escribir una función, se lo indicamos a la máquina escribiendo
puinto y como “:” como separador, un error muy corriente es que se nos olvide ponerlo en cuyo
caso la máquina entiende que hay detrás mas cosas, se lía y da un error.
En este ejemplo ya no tenemos que preparar más, por tanto hemos acabado con la función “setup
“. Asi pues la funcion “setup” completa ya es puramente comprensible (espero)
void setup() {
// código de configuración, PIN13 como SALIDA, para ejecutar una vez
pinMode(13, OUTPUT);
}
Utilizamos por dos vees dos funciones diferentes, la función “digitalWrite” y la función “delay”.
Función “digitalWrite”
“digitalWrite” actúa igual que lo hace un interruptor de la luz eléctrica, podemos permitir el paso
de la corriente o podemos cortar la luz.
digitalWrite(pin, value)
Función “delay”
“delay” paraliza el avance del programa, (puede traducirse como, “retrasar”), tiene la siguiente
sintaxis
delay(ms)
Aunque Arduino dista de ser una maquina rápida comparada con un PC, es aun muy rápida para
el hombre, con el “delay”· podemos hacer pausas que nos permitan percibir por ejemplo que una
luz se enciende y se apaga, porque si lo hiciéramos así la frecuencia de parpadeo sería tan rápida
que no llegaríamos a percibirla.
La función utiliza un solo parámetro, pero a diferencia de los anteriores /excepto el número de
pin), que eran solo palabras reservadas del sistema como, “INPUT” y “OUPUT”, o “HIGH” y
“LOW”. Aquí podemos utilizar cualquier numero entero y indicará el tiempo en milisegundos
(“ms”) que queremos dejar parado el sistema, en nuestro caso pararemos un segundo, (1000 ms),
después de encender la luz y otro segundo después de apagarl0, pero podiamos haber puesto
cualquier otra cantidad entera como 1200 milisegundos o 732 nilisegundos, lo que nos viniera
mejor en nuestro caso.
Como siempre cuando acabamos de escribir una función, se lo indicamos a la máquina escribiendo
punto y como “:” como separador.
Ya podemos escribir la función “loop“. Asi pues la funcion “loop” completa ya es puramente
comprensible (espero)
void loop() {
// código principal, encender, esperar, apagar, esperar
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
delay(1000);
}
Bien esto es el programa completo o Sketch que tenemos que escribir en el Menú de inicio de
Arduino.
Lo más cómodo y evita errores es que haga “copiar y pegar”, sobre la función completa y lo
traslades totalmente a tu pantalla del Menú de Arduino sustituyendo lo que hay,Para facilitartelo.
La reescribo a continuacion al completo. Tienes que tener en cuenta de copiar dede la primera
palabra “void” de la funcion “setup”, al último signo que es la llave de cierre de la función
“loop” o sea el símbolo “}”–
void setup() {
// código de configuración, PIN13 como SALIDA, para ejecutar una vez
pinMode(13, OUTPUT);
}
void loop() {
// código principal, encender, esperar, apagar, esperar
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
delay(1000);
}
De modo que la pantalla de su Menu Princuipal de Arduino tendrá ahora un aspecto Más o menos
como este.
Observarán como palabras reservadas del sistema como “void” “OUTPUT” “HIGH” y “LOW”
aparecen en azul los nombres de las funciones de Arduino “pinMode” “digitalWriter” “delay”
aparecen en marrón y los textos libres tanto comentarios como los parámetros “13” y “1000”
aparecen en negro. Esto es porque la pantalla del menu donde escribinos inicia un proceso de
identificación del texto que vamos escribiendo.
Sketch de Ardunino
Bien, esto que ven aquí. es un programa o Sketch, muy sencillo pero completo, obligatoriamente
tiene una función “setup” y una funcion “loop”. Sin embrago este es un “programa fuente” algo
que entiende con poca dificultad cualquier humano que trabaje con Arduino, pero que para la
máquina es indescifrable, porque la máquina solo entiende de ceros y unos y direcciones de
memoria.
Si pinchamos en la barra de menu superir ahí donde dice “Archivo”. Se despliega un submenú
que indica todo lo que podemos hacer con el archivo:
Nosotros lo primero que vamos a hacer es guardar el sketch que hemos escrito. Por tanto elegimos
la opción “Salvar” que nos lleva automáticamente y por defecto a la carpeta Arduino que
hicimos para bajar los programas de Arduino, (que aconsejo utilizar), donde podremos guardar el
fichero que aconsejo previamente titular, (como yo he hecho), como “Sketch 1 Intermitente”
para que más adelante sepamos encontrarlo y luego aprietas a la tecla “Guardar”
Si vuelve a repetir el proceso de inchar en “Archivos” vera que se ha producido un cambio sutil
Programa Objeto
Como dije, este “Programa fuente”, es solo para que los lean y escriban los humanos, las
máquinas y algunos superespecialistas, son los que leen programas formados por ceros y unos
direcciones de memoria. Afortunadamente el trabajo de generar un “programa objeto” a partir de
un “programa fuente” se hace automáticamente por un proceso que se llama “compilación”, que
principalmente consiste en sustituir las funciones estándar de Arduino por complejas
instrucciones de ceros y unos que hacen digitalmente lo que indican las funciones y eliminar los
comentarios, porque la máquina para nada los necesita.
Si pinchas en la barra de menú en la opcion “Programa” se despliega otro submenú que tiene
Para que vean lo que les digo es cierto, en la primera versión del programa que he hecho, se me
escapó en la linea que aparece en fondo rosa poner dos puntos “:” en vez de punto y como “;” y el
programa al de verificación al llegar a esa línea la ha marcado en rojo y en la parte de abajo indica
claramente:
expecte ‘;’ before ‘:’ token (esperaba ‘;’ antes del simblo ‘:’ )
Como ven el mensaje ideal seria, “Se ha confundido y ha puesto ‘:’ en lugar de ‘;’ “ y más aun
puesto que es obvio que la misma máquina sustituyera loa “:” por el “;”, pero esto es lo que hay (al
menos de momento).
Como corregí el error, si has copiado íntegramente el texto, incluida la última llave de cierre de
“loop” “}” , lo razonable es que llegues a una pantalla como esta
“El Sketch usa 1.030 bytes (3%) del espacio de almacenamiento de programa. El máximo es
32.256 bytes. Las variables Globales usan 9 bytes (0%) de la memoria dinámica,”
O sea que todo ha ido bien y que el programa solo ocupa un 3% del espacio pasible, es decir
que sketch muchísimo mas complicados que el presennte caben en tu tarjeta Arduino, solo que, (al
menos de momento), la tarjeta Arduino, a diferencia de lo que ocurre en el PC donde podemos
guardar muchos sketch , sólo admite un programa en su memoria. Si hay uno y se introduce otro,
el primero se borra, desaparece y queda el segundo sustituyendo al que había,otro como veremos
en otros capítulos.
Subirlo a la Tarjeta.
Conviene que la tarjeta esté físicamente conectada al PC antes de llamar al Menu principal de
Arduino. La razón es que si no es así, podemos tener problemas de identificación del puerto
serie o puerto com que nos adjudica el PC.
La forma más sencilla de hacer que los controladores están instalados correctamente, es
llamar al Menú de inicio con la placa Arduino previamente conectado al ordenador. Por ello,
pido que conectes tu tarjeta al pc y cierres la pantalla del Menú de Arduino, (como has
guardado el programa no se perderá) y la vuelvas a abrir nuevamente, o sea, la tradicional
chapuza informática de, “apaga y vuelve a empezar”, porque es en la instalación del Menú y
teniendo enchufada la Tarjeta Ardunino a un puerto USB, es cuando todo se instala
correctamente. Asi que vamos a hacerlo ahora para evitar tener problemas a la hora de “subir” el
“programa Objeto” a la tarjeta
Conectar la Tarjeta
Con la tarjeta nos han debido dar un cable con dos terminales
macho USB algo diferentes, uno más plano que es el que se conecta al ordenador y otro más
cuadrado que se conecta a la tarjeta, tal como se ve eb esta fotografía.
El cable USB tiene por dentro cuatro hilos diferentes, dos de ellos son los que proporcionan
corriente continua a la tarjeta uno de ida a 5Voltios y la “tierra” a cero voltios para el
retormo. Los otros dos hilos son los que permiten comunicarse al PC con la tarjeta, uno, (TX)
es para transmitir los datos y otro (RV) para recibirlos. Por lógico el extremo TX de un lado,
acaba en el extremo RX del otro, pues si uno transmite, el otro recibe, el cable ya esta montad de
forma que internamente se cruzan los hilos como conviene, por tanto es algo que no nos tenemos
que preocupar. Sólo saber que por esos dos hilos, es por los que dialogan automáticamente el
Ordenador y la Tarjeta, y es por donde va a pasar el “fichero objeto” que creamos en el
ordenador a la tarjeta.
Conecta Arduino
Ahora enchufe físicamente la Tarjeta Arduino al PC, observara que se produce el ruidito típico
de haber detectado el PC que se le ha unido un dispositivo USB. Hay un piloto en Tarjeta
Arduino, situado en la parte inferior de la imagen, cerca de una de las perforaciones que se usan
para sujetar la tarjeta a un soporte, que viene marcado como “ON” Al euchufar la tarjeta al PC, lo
primero que hace es recibir energía a 5 voltios y el piloto ON lo indica brillando (en mi caso), una
luz de color verde.
Vuelva a llamar al programa Menú de Inicio de Arduino
Con la tarjeta enchufada vuelva a cargar el Menü de Inicio de Ardunio, verás que aparece una
pantalla intermedia, que informa que esta cargargando el programa Menú y además selecciona
correctamente el puerto com.
Ahora despliega el submenu “Archivo” y elige la opción “Abrir Reciente” que le debe llevar a
otro submenú donde encontrara el programa que guardó “Sketch_1_Intermitente”
Aparecerá una nueva pantalla con el contenido del “programa fuente” que previamente
guardamos. Compile primeramente el “programa fuente” como le indicamos antes, es decir
seleccionando en el submenú “Programa” la opción “Verificar/Compilar” y vera que nuevamente
se le genera el “Programa Objeto” sin problemas, si una vez lo hizo y no ha cambiado nada, tiene
que poderse hacer otra vez.
Las luces TX y RX se encienden cuando se están enviando datos por el cable y si todo va bien,
han de parpadear cuando nuestro programa esté siendo transferido al ordenador. La otra luz
marcada L es un pequeño piloto asociado al pin13, algo que solo tiene este pin, que luce siempre
que se mande salir energía por ese pin.
Ha de estar atento porque la cosa solo dura unos segundos. Cuando seleccione ahora en el
submenu “Programas”, la opcion “Subir” enviaras automáticamente el “Programa Objeto” por
los cables de comunicación Tx y RX y los ledes correspondientes a las comunicaciones
parapadearán debido al diálogo automático que se establece entre el PC y la Tarjeta para instalar el
programa objeto dentro del procesador de la Tarjeta
Posiblementee tendrás que verla varias veces porque todo resulta muy rápido. Inicialmente todas
l0s led están apagados excepto el led ON que es de color verde y se encuentra a la derecha de la
imagen que permanecerá permanentmente enciendido por que indica que la Tarjeta esta recibiendo
corriente eléctrica.
Pasado el primer segundo se encienden los dos led el RX y TX que indican que el programa se
está transfiriendo a la tarjeta. Poco después se apagan y comienza a parpadear el led L, lo que
indica que nuestro programa gha sido un éxito, eso es lo que pretendíaamos
¿Y eso es todo?
Si, eso es todo, pero no es más que el comienzo. He querido demostrate que serias u capaz de
escribir un programa y hacer que funcionara convenientemente en la tarjeta. Te aseguro que tan
solo en el siguiente capítulo te quedarasasombrado de lo que ya eres capaz de hacer y de lo rápido
que progresas.
Si alguno de los conceptos que indicom no lo tienes suficientemente claro, repasa la parte del texto
correspondiente, porque en el próximo capítulo vas a tenerlos que utilizar con mucha frecuencia y
ahi ya no los voy a explicar con el detalle que lo hago aqui.
Félix Maocho
7/6/2016
Material mecesarrio
Para las prácticas de este capítulo no se necesita la tarjeta controladora Arduino pues todo se
simula mediante software..
Todavía no lo he probado. Por lo que hablo aun de oídas, espero adquirir pronto experiencia e iré
indicando mis avances con la herramienta, así como las dificultades y limitaciones que encuentre.
Simula en el Pc una placa Arduino Uno y muchos de los dispositivos de entrada y salida mas
normales, resistencias, leds, motores de corriente continua, servomotores, comunicaciones,
pulsadores, potenciómetros deslizantes, e incluso un osciloscopio para visualizar las señales
analógica y digitales de salida. Por supuesto. los componentes tiene una icono que representa su
aspecto, pero lo importante es que también su simula su actividad eléctrica
La ventaja de esta simulación es que puedes ejecutar tus sketch, ademas en simulación de
ejecución continua, como paso a paso, o bien poner puntos de parada (breakpoints), y
averiguar en cada parada el valor que van adquiriendo las variables, por lo que puedes con
bastante facilidad analizar los motivos por el cual el sketch no funciona de forma esperada.
Por ello considero, que es sumamente útil tanto para principiantes como para medianamente
avanzados, pues además de tener una potente herramienta de depuración de programas,
conseguimos separar totalmente el software del hardware, de forma, que cuando un programa
funcione en el simulador, si posteriormente no funciona en real, sera única y exclusivamente por
errores en la construcción del hardware.
El programa es totalmente portable y no necesita ningún tipo de instalación, por lo que permite,
quizá junto con otra e herramienta fundamental el programa Fritzing, también portable, y todos
nuestros programas y ficheros que creemos, meterlos en un pendriver no muy grande y llevar
todo lo necesario a donde quiera que vayamos y poder trabajar en cualquier ordenador Windows
para poner a punto los sketch, sin necesidad de trasladar los “triquilis” digitales y una vez probado
y marchando casi sobre seguro, montar ya en tu “laboratorio”, el aparato físico en cuestión. Algo
muy interesante por ejemplo para el verano, donde no es cosa de trasladar toda la cacharrería
que tenemos en casa.
Por supuesto, otra gran ventaja es que UnoArduSim, como casi todo lo relacionado con Arduino,
es absolutamente GRATUITO y de libre uso. El único inconveniente, como viene siendo habitual
en todo el mundo Arduino, es que el Manual de Uso y Guía Rápida está únicamente en dos .pdf
en inglés que puede llevarse al traductor de Google y conseguir una versión (mas o menos) en
castellano.
Pero además en este caso, encontramos un video tutorial en español de cinco vídeos realizado
por Agustín Borrego Colomer, profesor de Técnicas y procesos de montaje y mantenimiento
de equipos electrónicos en un Instituto de Alicante, que explican detalladamente lo necesarios
para utilizar y sacar todo el partido al programa.
He estado viendo los dos primeros videos del Tutorial de Agustín Borrego Colomer y me
parecen muy bien hechos, de lenguaje muy claro y muy didácticos, como era de esperar de
alguien que es profesor de tecnología de un Instituto. Aconsejo que los veas en paralelo a las
practicas en la utilización de UnoAduSim, Les dejo más abajo los link a los videos
Tendrás que utilizar un des compresor zip para desplegar los ficheros que te bajes. El capítulo uno
del tutorial indica como se hace y que contiene.
Los video en castellano del tutorial del programa son los encontrareis en esta dirección
Félix Maocho
12/6/2016
Hoy es mi primer día de contacto con el programa UnoArdSim. Iré contando las dificultades que
me he encontrado y como las he resuelto, con el fin de que los que me sigan se encuentren con
menos dificultades en el [Link] este prograna de simulacion de la tarjeta Arduino les
hablé en “UnoArduSim programa simulador de la tarjeta Arduino, para experimentar sin
el Hardware”
Descargar el programa
De la pagina oficial de descargas llamada “Simulator Download” (Descarga del simulador) elijo
la última versión que apare en la parte inferior de la página, que se denomina
[Link] con 1147k firmada por el Prof Simmons de fecha May 17, 2016. Al
pinchar en la pequeña flecha hacia abajo que esta a la derecha, sorprende la rapidez con que baja
el fichero zip.
C:\Users\Usuario\Downloads\UnoArduSimV1.5 (1).zip\UnoArduSimV1.5
En el fichero del usuario para descargas, (Downloads), que tiene de forma estándar Windows, se
sitúa el fichero bajado UnoArduSimV1.5 (1).zip que al desplegarse, creó la carpeta llamada
UnoArduSimV1.5 a la que fueron a parar todos los ficheros descomprimidos que fueron los
siguientes:
Por lógica comenzamos leyendo el fichero READMEV1.5, pues tradicionalmente los fichero
REDME han tenido las instrucciones necesarias para instalar la aplicación. En este caso el fichero
dice lo siguiente:
UnoArduSimV1.5 README
When you first run [Link], you will see a default set of I/O devices (one of each of eight
of the “big” I/O devices, and several of each of the “small” I/O devices), and a dummy
“[Link]” default program which you can immediately run.
You can use the Configure menu to adjust the set of I/O devices, and from the provided dialog
“Save” that configuration for next time (as a named text file). That file name will be automatically
added to the [Link] file that gets loaded at the next program startup — to go back to the
default startup configuration, delete the IODevs line in the [Link] file (or just delete that
entire file).
When ready, you can load and try out the provided [Link] demonstration program —
that program needs to have a particular set of I/O devices attached, so use “Configure->IO
Devices” and “Load” the myUnoDevs_DemoProg1.txt file. That will load the devices (with pre-
set pin connections (and settings and values) that are needed by the [Link] program.
Run it to see the IO devices and program in action.
You can then try out a more complex (and fun) program [Link] that has musical
playback and IO devices moving to the music (my acknowledgment to the animated TV program,
the Simpsons, for that one). This second demo program also shows that you can split your code
(and included data) between multiple files for better viewing and navigation.
Que vamo a traducir de forma automática con el traductor de Google , que sin dar una traducción
perfecta. Suele dar una traducción con la suficiente calidad para poder entender lo que dice
README UnoArduSimV1.5
Cuando se ejecuta por primera vez [Link], verá un conjunto predeterminado de los
dispositivos de E / S (uno de cada uno de los ocho de los “grandes” los dispositivos de E / S, y
varios de cada uno de los “pequeños” los dispositivos de E / S), y un “[Link]” programa
predeterminado ficticia que puede ejecutar inmediatamente.
A continuación, puede probar un más complejo (y divertido) [Link] programa que tiene
la reproducción musical y dispositivos IO en movimiento a la música (mi reconocimiento al
programa de televisión animada, los Simpson, para que uno). Este segundo programa de
demostración también demuestra que se puede dividir su código (y datos incluidos) entre varios
archivos para una mejor visualización y navegación.
Así pues hagamos lo que nos dice, ejecutar por primera vez [Link], y ver que pasa.
Pinchamos sobre el fichero [Link] y al cabo de un instante aparece la siguiente
pantalla
La pantalla del ordenador aparece dividida en tres secciones, la de la esquina superior izquierda,
destinada a tener el sketch que vamos a probar, a de la esquina inferior izquierda que es la que nos
va a dar el valor de las variables cada vez que se produzca una parada en la ejecución del
programa y la de la derecha que es el simulador de la tarjeta Arduino
Si pinchamos dos veces en cualquier punto de donde aparece el sketch, (secciones la de la esquina
superior izquierda), se abre un editor de textos que nos permite escribir el programa y hacer los
cambios que queramos en el texto como si de un editor corriente y vulgar se tratara.
Por probar, he metido el programa más sencillo que conozco, que es el que vimos en este Curso
de Arduino , en el capítulo ·”Principales opciones del Menú de Inicio de Arduino,” que si
recuerdan, no hace más que parpadear el led que hay en la Tarjeta Arduino asociado al Pin
13. La ventaja de este programa, es que no se necesita conectar nada a la tarjeta, por lo que
podemos probarle en nuestro simulador con las mínimas complicaciones posibles. Poco a poco
iremos complicando la cosa.
void setup() {
// código de configuración, PIN13 como SALIDA, para ejecutar una vez
pinMode(13, OUTPUT);
}
void loop() {
// código principal, encender, esperar, apagar, esperar
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
delay(1000);
}
Que con un COPY/PASTE vamos a introducir íntegramente en nuestra ventana del editor de
textos. Con lo que la pantalla del editor quedará con un aspecto similar al siguiente:
Y cuando hacenos “Save” (Salvar), clicando en el botón de la derecha, se traspasa a la secciones
del sketch en la esquina superior izquierda, aunque antes, sale una pantalla solicitando la
confirmación de que deseamos el cambio, para evitar errores por despiste. Pero al hacerlo verán,
que debajo del texto introducido,, han aparecido unas lineas de programa que no hemos escrito..
Les amplio esta zona a continuación:
Han aparecido dos lineas de comentario y una función para nosotros desconocida que se llama
“int main()” que dentro de las instrucciones que contiene, llama a la función “setup” y a la
función “loop”.
Con saber que la crea el simulador, que se añade automáticamente sin que nosotros hagamos nada,
y que no la tenemos, (ni podemos), tocar, estamos del otro lado. Estas lineas no aparecen en la
ventana del editor de textos, por tanto no hay posibilidad de poder cambiarlas.
Supongamos que comentemos un error de sintaxis en alguna línea de sketch, ¿que pasará?. Por
ejemplo vamos a borrar un punto y como “;” de final de una línea, lo que indica al procesador que
la sentencia se ha acabado, por ejemplo, el punto y coma ”:” situado en la línea donde
encendemos el led (HIGH).
Al traspasar el texto del sketch, automáticamente se pone azul la linea con el error y en el pie de la
pantalla aparece un mensaje, (en inglés), que intenta aclararla razón del error. En nuestro caso sale
PARSE ERROR (ERROR DE ANALISIS), que seamos honestos, mucho no aclara, pero lo que
si aclara bastante es que la línea azul, nos marque en que sentencia está el error.
Corregimos el error y todo vuelve como estaba antes, la linea azul fuera de nuestro texto nos
indica que al menos sintácticamente el programa está bien escrito, es una simulación equivalente a
que el programa se compile cuando probamos en real.
Observarán que en este caso, la esquina inferior derecha, donde deberían aparecer las variables, no
aparece nada, porque este programa, excepcionalmente, es tan sencillo que no utiliza ningún
parámetro ni variable, algo rarísimo. En otros ejemplos, veremos que aquí aparecen esas variables,
con los valores como los hayamos inicializado y que van cambiando a medida que el programa
avanza, para resaltarlo se señalara con una raya azul la variable que haya cambiado de valor con la
ejecución de la línea.
Por otra parte observarán que el pin 13 se encuentra en color azul, en vez de gris, lo que indica
que ese pin ha sido activado como pin de OUPUT lo que confirma que encima de el hay una “O”
en vez de una “I” pues los pines por defecto están en INPUT y encima vemos un “0” sobre fondo
azul lo que indica que en este momento no está saliendo corriente eléctrica por ese pin, a
diferencia del pin 0 que esta en OUTPUT “O”, que se utiliza también como receptor “Rx” en
comunicaciones asíncronas, que si esta recibiendo electricidad y por ello esta a “1” y en color rojo,
(pues la tarjeta se supone que está conectada al Pc) .
La franja del menú, contiene una serie de opciones que al desplegarlos se abre dejando una serie
de subopciones que más o menos son las mismas que se utilizan en todos los sitios, Poco a poco
ya las iremos utilizando y contando para que valen. Hoy nos vanos a centrar en las opciones de
“Execute” (Ejecutar), que permiten lo que pretendemos en este momento, que es simplemente
simular la ejecución del sketch.
Para ello vamos a ver algunas de las subopciones que tiene la opción del menú
“Execute”(Ejecutar),
Si despegamos este submenú veremos que tiene una amplia variedad de subopciones
Reset (Reiniciar)
Hacer “Reset” (Reiniciar), es equivalente a clisar en el botón rojo de la Tarjeta
Arduino , (algo que también se puede), o lo que es lo mismo, dejar todo como está al principio del
programa. Podemos conseguir hacerlo, clicando en el botón rojo de la tarjeta, en esta subopción,
y además en uno de los iconos que hay en la barra de herramientas, como el icono negro que
mostramos situado bajo la opción “VarUpdates”.
Si tuviéramos variables, veríamos que estas adquieren los valores con que las hemos inicializado y
la barra azul que indica qué mandato se está ejecutando se sitúa sobre la función “main” que es la
que controla el proceso de simulación.
Halt (Detener)
“Halt” para o detiene la ejecución ahí donde se encuentre el programa en ese momento.
Es útil tanto para finalizar la ejecución del sketch, como para estudiar con calma los valores de las
variables en ese momento, pues a diferencia de “Reset”, deja las variables con sus valores en el
momento de pararse y no las inicializa.
Hay un icono rojo como el que se muestra que esta a la izquierda de “Reset” que realiza la misma
acción. Que habitualmente esta rojo y que se pone gris cuando para.
Run (Correr)
Si lo clikan, verán que en nuestro caso. el cuadradito amarillo que simula el led asociado al pin 13
se pone a parpadear y así se mantiene por tiempo indefinido, hasta que apretemos “Reset” o
“Halt”. Si hemos apretado “Halt” y volvemos a clicar “Run”, el programa continua desde ese
punto de parada. Puede ser una buena forma de estudiar los valores que toman las variables en un
determinado momento, lo difícil a velocidad normal va a ser acertar con el momento de parada.
Por ello esta opción, por si sola suele ser poco útil, si no tenemos idea de donde estamos en la
ejecución del programa, casi siempre se suele utilizarse conjuntamente con las subopciones
“Animate” (Animar) y “Slow Motión” (Cámara lenta)que veremos a continuación
Animate (Animar)
Nos permite seguir la linea que se está ejecutando. porque aparece una barra azul, que se sitúa
encima de la línea que se esta ejecutando en cada momento. El poner en marcha esta opción.
reduce la velocidad de ejecución del programa lo suficiente, para que nos de tiempo de ver a la
barra. Por tanto, la velocidad de ejecución, deja de simular la que tendría la tarjeta Arduino UNO,
para ser más lenta, sin embargo sigue siendo aun muy rápida, si no para el ojo humano, si para
nuestra velocidad de reacción y comprensión de lo que ocurre, por lo que podemos añadir la
opción “Slow Motión” (Cámara lenta) que expiaremos a continuación como su nombre indica
relentiza la acción
Slow Motión (Cámara lenta)
Mejore que “Entrar en” hubiera sido traducirlo por “Paso a paso”, pues cada vez que
cliquemos en esta subopción el programa avanzará una línea, En este caso que presenta,os, que es
extrordinariamente sencillo, podemos permitirnos ese lujo de correr todo el programa paso a paso,
pues ademas tenemos un icono amarillo, como el que mostramos, situado a la izquierda del icono
“Run” verde que permite fácilmente clicarlo.
Si tuviéramos variables, veríamos los valores que estas tendrían después de parar en cada una
de las líneas de programa, lo que nos permite fácilmente depurar el programa, cuando tenemos un
punto con especial complejidad. Sin embargo, lo habitual es combinar esta acción con otra que te
pare el programa un poco antes del punto conflictivo, pues no es cosa de correr un programa de
500 lineas de una en una. Eso es lo que hace la subopción siguiente.
Esta subopción permite parar el programa allí donde indiquemos. Para ello hay que
efectuar dos acciones, la primera con el sketch parado marcamos con el ratón en que línea
queremos que pare, para ello basta clicar sobre la linea que queremos parar, (vemos que la
linea azul se desplaza a ese punto) y luego clicar en “Run to”(Correr hacia) o bien en el icono
rojo similar al que indicamos.
Por ejemplo una vez parado el sketch en esa línea podemos recorrer el programa línea a línea
clicando en el icono amarillo de “Step into” con lo que será fácil recorrer la parte más conflictiva
de nuestro sketch olvidándonos del resto del programa.
Con esto doy por finalizado por hoy el aprendizaje del manejo de esta simulación. Quiero resaltar
la poderosa herramienta que tenemos para poner a punto los sketch, pues nos permiten un control
total linea por linea del sketch, con un escaneo de los diversos valores que van adquiriendo las
variables en el transcurso de la ejecución. Como veremos en artículos posteriores esto facilita
mucho el poner a punto los programas, por tanto siempre que sea posible pondré a punto los
programas en la simulación antes de construir el Hardware y probarlos en real. En ejemplos más
complicados y con hardware que pongamos en el futuro, podremos probar la utilidad de poder
observar estos valores.
Comfigurar el hardware
Aun nos falta hacer una cosa. Si nuestro software no utiliza ningún componente electrónico,
¿por qué aparece la Tarjeta rodeada de componentes no utilizados? ¿Podemos eliminarlos?
Por supuesto que si hay una opción en el menú “Configure” (Configuración) que al desplegarse
presenta el submenú “I/O Devices” (E/S Dispositivos), que vale para seleccionar los dispositivos
que deseamos manejar (simunladamente) con la tarjeta Arduno.
Si clicamos en ese submenú nos aparece una pantalla con todos los dispositivos que podemos
utilizar con nuestra tarjeta y al lado un número que indica cuantos utilizamos en muestra
configuración.
En nuestro caso aparecen como componentes ligeros, de los cuales puede tener como máximo 16
componentes:
1 Servo Motors
1 DC Motors (Motores de Corriente continua)
0 Sreppers Motor (Motores paso a aso)
1 Digital Pulsers (Pulsos digitales)
1 Funtion Generators (Generador de funciones)
1 Soft Serial Ports (Puertos Series ligeros)
1 SPI Slaves ( Bus de comunicaciones Serial Periferical Interface Esclavos)
0 Shift-reg Slaves (Bus de comunicaciones de cambio de registro esclavos)
1 12C Slaves (bus de comunicaciones 12C esclavos)
Aparte podemos o no ten seleccionado
USB Serial (comunicación serial USB)
SDCARD (Tarjeta de datos SD)
De momento como en nuestro caso no necesitamos montar ningún componente los vamos a borrar
todos poniendo un cero en las casillas correspondientes.
Una vez que demos al “OK” a la nueva configuración, modificaremos la configuración de
hardwara asociada al programa. Con ello conseguimos que muestra tarjeta parezca ahora sola en la
sección gráfica de la simulación.
Ahora sólo nos resta, aprender a guardar lo realizado, tamto en lo referente al sketch que hemos
escrito como a la configuración que hemos elegido. El , medio de hacerlo es similar al que se
utiliza en cualquier programa de Windows. Desplegando la primera opción de menú llamada
“File” (Fichero) que mas o menos tiene los habituales submenús
Al opción “Save as” (Salvar como), permite salvar el trabajo realizado con el nombre que
prefiramos y en la carpeta que queramos, yo lo he salvado en la carpeta donde tengo todo lo
referente a este programa llamada UnoArdSinV1.5 con el nombre “Blink” que es el tradicional
que se da a este fichero
Si comparan el estado actual del directorio de esa carpeta, con el inicial, observarán, que en la
primera línea de ficheros hay un fichero que antes no estaba llamado “Blink” precedido del
logotipo de Arduino que contiene todo lo que hemos hecho.
Lo explicado se corresponde más o menos, con lo que explican los tres piremos vídeos del
Tutorial de Agustín Borrego, que aconsejo ver, como complemento para obtener un perfecto
aprendizaje de la herramienta.
Material necesario
Uso de la opciones básicas del Menú de inicio de Arduino, que perrnitan escribir, compilar y subir
un sketch a la tarjeta Arduino
Uso de las funciones del sistema “pinMode”, “digitalWrite” y “delay”
Conocer los parámetros estandariza “void”, “OUTPUT”, “INPUT”, “HIGH” y “LOW”
Manejar las lineas de comentario (“//”)
Todos estos conocimientos se explican en detalle en el capitulo “Principales opciones del Menú
de Inicio de Arduino”
Pines digitales
Los pines digitales son salidas de corriente programables, de forma que a través de un programa
podemos hacer que dejar salir una corriente continua de 5 V. o bien pueden impedir tal salida. En
la Tarjeta Arduino Uno tal como se ve en la figura inicial se encuentran situadas en la parte
izquierda de la arista superior y viene marcadas como “Digital In/Out Pins” y tiene escritos con
unos numero que van del 0 a 13, o sea que hay previstas 14 salidas programables digitales
En el capítulo anterior hicimos nuestro primer programa que enciende y apaga un led L
insertado en la propia tarjeta, que está asociado a lo que ocurre en el Pin13, si por ese pin sale
corriente se enciende el led y si no sale se apaga. Si creamos un circuito exterior que nazca en ese
pin que contenga un led, también se iluminará y apagará sincrónicamente con el led L.
Lo primero hay que tener en cuenta, es que, aun desenchufada la Tarjeta Arduino, se conserva
grabado en su memoria el último sketch que se le introdujo, o como se dice en el argot del gremio
se le “subió”. Por tanto, al volver a enchufar la tarjeta a un puerto USB y recibir la corriente
eléctrica, el programa que tiene grabado, se reinicia automáticamente desde el principio y vuelve a
hacer lo mismo que hacia, en nuestro caso hacer parpadear el pin13.
Si del pin13 sacamos un circuito eléctrico con un led por donde pueda pasar la corriente, este led
se encenderá y apagará a la vez que el led L de la tarjeta, pues por ambos lugares, pasa, o deja de
pasar la electricidad a la vez. ¿Quiere verlo?
Voy a poner un esquema de lo que he montado para que lo pueda ver mas claramente y en mi
opinión, debes construir también este circuito, porque solo experimentando, (y cometiendo
errores), se aprende de verdad.
Observen. De el Pin13 parte un cable verde que termina en un punto situado en la misma línea
que una de las patas del led blanco, mientras que la segunda pata del led, está pinchada en la línea
paralela de la izquierda, que un poco más abajo tiene insertada una pata de una resistencia de 220
Ω mientras que la otra pata acaba en otra linea paralela en la que acaba un cable la blanco que
parte de un pin que bien marcado como GND.
Tarjeta Protoboard
Para empezar, hay que saber que es la tarjeta de prototipado o tarjeta protoboard. Es una
tarjeta viene plagada de perforaciones donde se pueden enchufar fácilmente los cables y
componentes electrónicos sin necesidad de molestas soldaduras, lo que permite armar y modificar
fácilmente los proyectos, así como desarmarlos, reciclando sin problemas todos los componentes,
lo que a la larga supone un ahorro apreciable de tiempo y dinero, por lo que todos, aficionados y
profesionales, montamos en estas tarjetas protoboard, nuestros proyecto y sólamente una vez
probados, se trasladan a los equipos definitivos que se están proyectando.
Por tanto, a través de estas conexiones internas tenemos un circuito que partiendo un cable verde
del Pin 13, enlaza con la pata del led blanco a través de una de las lineas de conexión vertical
paralela.
Por su parte la otra pata del led blanco conecta a través de una linea de conexión paralela a la
anterior con una de las patas de una resistencia de 220Ω que con la otra pata y a través de un linea
de conexión vertical conecta con un cable blanco que finaliza en el pin GMD, apócope de
“Ground” (tierra).
O lo que es lo mismo, hemos cerrado un circuito, que parte de un punto capaz de suministrar
energía a 5V y acaba en un punto de tierra o 0V.
Resistencia
¿Por qué tenemos que poner una resistencia? – La razón es que el led tiene una resistencia
mínima. Si no pusiéramos la resistencia, ocurriría como cuando dos cables eléctricos se conectan
sin tener nada por medio, se produce un cortocircuito.
V=R I
El led tiene algo de resistencia, como lo tienen absolutamente todos los cables y componentes
eléctricos, que en mayor o menor medida dificultan el paso de la corriente, pero su resistencia no
es suficiente para evitar un cortocircuito que pudiera dañar la tarjeta, por ello recordar, “Todo
circuito que salga de un pin que produzca 5 voltios y muera en la tarjeta en un pin GMD tiene que
tener componentes electrónicos que en conjunto tenga al menos 220Ω para evitar dañar la tarjeta”.
El orden como se pongan las resistencia es indiferente porque las resistencias puestas en serie,
(unas detrás de otras), suman su resistencias y ya sabemos, que el orden de los factores no cambia
la suma igual da 4 +1 que 1 + 4.
Independientemente del orden en que enlacemos estas resistencias el valor de la resistencia total
equivalente será 1846 Ω
Suele asemejarse la electricidad a la corriente de agua. donde la diferencia de potencial viene dada
por la diferencia de nivel, a mayor nivel, el agua puede realizar un mayor trabajo o tiene mas
energía potencial y la resistencia seria el tubo por el que tiene que circular el agua, la resistencia
que se oponeg al paso del agua, por ejemplo un tubo mas fino, Indudablemente este tubo frena la
energía del agua, si solo deja pasar un fino chorrito, podrá hacer menos trabajo que si deja pasar el
doble de caudal.
Aunque varían de forma, el aspecto tradicional de una resistencia es como muestra la siguiente
imagen y el símbolo convencional que se utiliza en los esquemas eléctricos es una linea quebrada
Para saber de cuantos homios, (Ω) tiene una resistencia, hay que conocer el código de colores con
el que se marcan. Los códigos de colores son como siguen:
Lo primero tenemos que saber colocar de derecha a izquierda correctamente la resistencia para
leer las bandas de color en el orden correcto. Hay una serie de bandas de color igualmente
distanciadas y otra un poco mas separada, (en ocasiones son dos). La separada debe quedar a la
derecha.
Hecho esto las líneas del lado izquierdo que son tres o cuatro, las primeras por la izquierda son
cifras de acuerdo con el código de colores y la última por la derecha de la serie es el número de
ceros que siguen.
Por ejemplo la resistencia de la imagen que pusimos mas arriba tiene las, siguientes, lineas,
marrón, negro rojo y dorado que significa
marrón = 1
negro = 0
rojo = 00
dorado = 0,5%
o sea es de 1000 Ω con una tolerancia del 0,5% es decir fluctúa entre 995 Ω y 1005 Ω
La que vamos buscando son de 220 homios (aprox.), que son las suficientes en nuestro caso para
rebajar los cinco voltios a tres, que son los que necesitamos. O por tanto tendrá´las siguientes
bandas de color:
2 = rojo
2 = rojo
negro = Un solo 0 o sea 220 homios
y una tolerancia que puede variar según la calidad de la resistencia pero que en este caso nos es
indiferente. Como ven la cosa es un poco confusa, por eso quizá más practico, al menos en nuestra
etapa de principiantes , sea asegurarse que es la correcta midiendo con el polarímetro los homios
que tiene, pero como de momento no tiene polarímetro se tendrá que valer de este sistema.
Yo habitualmente como reciclo todas las resistencias las suelo marcar con una etiqueta auto
adhesiva tipo APLI que corto al tamaño adecuado, que indica la el valor de la resistencia en
homios. no se si se aprecia en el video pero tiene unas banderolas de papel que pone que son de
220 (se sobrentiende Ω).
El polarímetro será de las cosas que entraran en la próxima lista de la compra que hagamos, pero
antes de gastar más dinero, conviene saber si realmente nos entra la afición a Arduino, pues no es
cuestión de comprar cosa para que terminen en un cajón, así que no se apresure a comprarlo lo
dejamos en la lista de la compra pendiente y ya le indicare yo el momento adecuado para comprar
mas cosas con que seguir explorando este mundo de la robótica o abandona el estudio porque no le
va.
Lo más cómodo una vez identificado el valor de la resistencia es marcarla de forma más visible
Yo suelo ponerlas una etiqueta autoadhesiva tipo APLI que venden en las secciones de papelería
en la que claramente escribo los homios que tiene la resistencia.
Diodo
Led son las sigla de la expresión inglesa light-emitting diode, ‘diodo emisor de luz’, o sea un
diodo que emite luz. Pero ¿qué es un diodo?
Pues una válvula que permite el paso de la corriente en un sentido, pero no en el otro. Algo
parecido pero en digital, a la válvula de la las ruedas, permiten que el aire del compresor al interior
de la rueda, pero no en dirección contraria, impidiendo con ello que el aire de la rueda se escape
nuevamente.
Y ese es el uso que se suele dar en los circuitos eléctricos, permitir el paso de la corriente en una
determinada dirección, pero no en la contraria. Por ejemplo, el Pin13 de nuestro ejemplo esta
preparado para emitir electricidad, pero no esta preparado para recibirlo, pues le hemos puesto
como OUPUT (salida) y no INPUT (entrada), si hubiera el riesgo de que por el cable que va al
pin 13 pudiera circular corriente en dirección contraria, colocaríamos un diodo para evitar que
pasara. Es algo muy corriente, porque en este tipo de circuitos, se generan corrientes parásitas que
corren por donde pueden a poco que te descuides incluso a contramano.
Los diodos mas comunes en la actualidad, son un semiconductor conectada a dos terminales
eléctricos. De forma simplificada, si el voltaje esta por debajo de cierta cantidad en una dirección
se comporta como si fuera aislante (no deja pasar la corriente), y en la otra como una resistencia
eléctrica muy pequeña que permite el paso de la corriente sin dificultad.
Debido a este comportamiento, se les suele denominar rectificadores, ya que son dispositivos
capaces de suprimir lo que pudiéramos denominar el “retroceso” de la energía.
En esencia un diodo esta formado por dos partes en contacto de materiales diferentes, uno es de
tipo P, con abundantes electrones libres en la capa externa y otra de tipo N, deficitaria de
electrones libres y que por lo tanto tiende a capturarlos.
En la frontera entre los dos materiales llamada “Región de Agotamiento” se acumulan los
electrones libres atraídos por los huecos existentes en el otro material, por lo cual, a los efectos el
material tiene ausencia de electrones portadores por lo que el aparato en conjunto actuaría como
un material mal conductor de la corriente.
Por tanto de un diodo debemos tener en cuenta las siguientes características que debe indicar el
fabricante:
El voltaje máximo aplicable al componente, tanto para impedir el paso de corriente, (si se aplica
mas voltaje, el diodo colapsa y deja pasar la corriente en ambas direcciones) y el voltaje de
trabajo en la dirección favorable al paso de la corriente (VRRR máx y VR máx). que ha de ser
tres veces mayor, como mínimo, que el máximo voltaje que se espera que soporte en neutro
circuito.
La Intensidad de la corriente máxima tanto en sentido directo como en el contrario, que puede
atravesar al componente, (IFRM máx e IF máx), que ha de ser como el doble de la máxima
intensidad de corriente que se espera que soporte en neutro circuito.
Por tanto queda claro que los diodos hay que colocarlos en un sentido determinado en nuestros
circuitos y superar holgadamente las perores condiciones de trabo que puedan esperarse. La
corriente ha de fluir del ánodo (+) al cátodo (-). Es decir el ánodo (+) debe “mirar” en la
dirección que tiene el voltaje más alto y el cátodo(-) hacia la tierra (GMD)
Por esta razón en los esquemas, su icono tiene una punta de flecha que indica la dirección en que
dejan pasar la corriente, pero además tenemos que poder distinguir, como veremos que ocurre en
los LED, que patilla del diodo hay que orientar hacia la corriente de 5 Voltios y cual hay que
orientar hacia tierra. Para distinguirlo, los diodos suelen tener impresa una banda blanca o
negra pintada en el cátodo (-) o extremo que debe apuntar a tierra (GRD) ,
Los diodos no tienen formas tan específicas como las resistencias, pongo unas imágenes de las
formas más representativas que suelen tener.
Leds
Retomamos la definición de led. Led son las sigla de la expresión inglesa light-emitting diode,
‘diodo emisor de luz’, o sea un diodo que emite luz
Como indicamos, un diodo siempre supone una cierta resistencia, o lo que es lo mimo que partee
de la energía eléctrica se disipa en otra forma de energía. Los diodos habituales lo hacen en forma
de calor, o sea radiaciones del espectro por debajo de las radiaciones luminosas, pero hay unos
diodos específicos, los leds, que esa disipación de energía se trasforma en una radiación de una
determinada longitud de onda visible característica de laa substancias con que está fabricado.
Según sea las longitudes de onda que emitan la luz emitida será de un color o de otro y está a su
vez dependerá de la sustancia química que componen las partes P y N del Led. Lógicamente, para
que la luz pueda escapar del led, este viene encapsulado en una sustancia transparente a la luz,
generalmente de plástico, pues al emitir radiaciones luminosas, pero no infrarroja, el led es un
elemento esencialmente frío y no funde el plástico.
Con frecuencia, los leds se encapsulan en
plásticos coloridos con el color que emiten, con lo que es fácil distinguir un led blanco,
(transparente), rojo , verde, naranja, …. como se ve en esta foto.
El plástico coloreado, filtra el paso de la luz solar, impide el paso de diferentes longitudes de onda,
dejando pasar únicamente determinada frecuencias, con ello el plástico se ilumina de color, pero
esto no es necesario en un led, porque el led únicamente produce determinadas radiaciones, por lo
que su luz a diferencia de la del sol, que envía todas las longitudes de ondas que en conjunto lucen
blanco, solo emite unas pocas radiaciones, las que corresponden a los materiales con los que se ha
construido, por lo que ya nacen coloreadas, por eso, muchas veces, y mas aun en los led baratos,
el encapsulamiento es transparente, (no filtra a luz), y cuando están apagados no hay forma de
descubrir el color del led, hasta que este no comienza a emitir luz.
Los led como diodos que son, sólo dejan pasar la corriente continua en una determinada
dirección del ánodo (+) al cátodo (-). En este caso no pintan una banda en el cátodo, (que seria lo
razonable), sino que dejan el ánodo , ligeramente mas largo que el cátodo.
Cuando los led transparentes, yo los suelo pegar en la pata más larga, a semejanza de lo que
hago con las resistencias, una pequeña banderola, hecha con una etiqueta autoadhesiva en el
que escribo el color que emite, así, no solo sé cual es el color que emiten, sino la pata que tengo
que poner mirando a los 5 voltios y la parta que mirara a tierra (GMD).
Cada led genera un color muy definido que es el generado por las diferentes radiaciones de onda
que despiden la sustancia con la que están creados, el primero que se invento. emitía luz roja y
por ejemplo, le solemos encontrar en el sensor de movimiento de los ratones ópticos, pero ha
sido tan difícil conseguir encontrar leds que emitan longitudes de onda diferente, que nada
menos tres físicos, fueron galardonados en el 2014 con el Nobel, por descubrir el led azul, que
era uno de los que mas se resistieron.
Descubierta esta sustancia, solo fue cuestión de tiempo conseguir mezclas adecuadas en los leds
que emitieran en la debida proporción los colores fundamentales, para que obtener lo largamente
perseguido, leds de luz blanca, que han supuesto una revolución en el mundo de la iluminación.
En el siguiente vídeo, verán cuatro leds, aparentemente iguales cuando están apagados, sin
embargo los de los extremos emiten luz roja, mientras que los dos del centro emiten luz azul, algo
que se pone en evidencia, tan pronto como la corriente eléctrica pasa por su interior
En el esquemas el led se representa como lo que es un diodo al que se le añaden dos flechillas que
asemejan la luz que desprende
No me resisto a poner una esquema de las partes que componen un led para que comprendas la
complejidad que tiene su fabricación y lo asombros que es este mundo de lo digital, que pese a
ello permite su coste no supera habitualmente los 0,3 cents de euro.
Ejercicio
A continuación les explico el programa que hace que los leds se enciendan y apaguen como se ha
visto en la película. Concretamente lo que hacem las luces es lo siguiente:
* 1º Encender las luces de un extremo al otro y volver, secuencia leduno, leddos, ledtresl
ledcuatro, ledtres, leddos, leduno, en colores rojo, azul, azul, rojo, azul, azul, rojo,
* 2º Encender de los extremos y luego los del centro y repetir tres veces.
* 3º Encender todos los leds uno tras otra y apagarlas en el mismo orden.
Hardware necesario
Como ven en la imagen es el mismo montaje repetido cuatro veces que vimos al inicio del
programa. De los pines 6, 7, 8 y 9 parten unos cables, que van a parar a la pata más larga, (cátodo
+), de un led que a su vez conecta con una resistencia de 220 Ω cuya otra pata atraviesa el centro
de la protoboard, para unirse del otro lado mediante un cable al bus qye esta unido a tierra
(GMD).
Se observa que cualquiera de los pin digitales marcados de o a 13 puede ser utilizado como
fuente de una corriente de 5 Voltios y como cada pin se puede por programa activar o apagar,
resulta sencillo tener el control de los componentes situados en el circuito que parte de estos pines.
En este caso hemos utilizado como pines de salida los pines marcados como 6, 7, 8 y 9 que
alimentan respectivamente dos leds rojos colocados en los extreemos y dos azules colocados en el
centro.
Observen también que en este caso se pueden hacer terminar todos los circuitos unidos en un
mismo pin GND, por el sencillo procedimiento de hacer acabar los diferentes circuitos en uno de
los buses de la protoboard y unire este bus a un pin GND. Pudiera ser que por estos cables
amarillos circulen corrientes parásitas pues cuando un led esta encendido se conecta a través del
bus con los demás circuitos , pero como los leds son diodos, no dejarán pasar estas corrientes con
lo que los pines abierto como OUPUT están a salvo de recibir descargas.
Software
El programa que hace lucir de esa forma los leds resulta ser tan largo que no cabe en la pantalla
del Menú de Inicio de Arduino, así que lo presentaos en cuatro pantallas consecutivas, pero en la
realidad está todo escrito en una única pantalla y el “ascensor” que está a la derecha de la pantalla
hace “subir” el texto que queda oculto.
Lo primero que vemos es un programa mucho más largo que el anterior, pero, puedo asegurar que
esto, no es nada comparado con lo que puede llegar a ser un programa de cierta complejidad, Por
eso conviene ser sumamente ordenado, Pese a que parezca que perdemos el tiempo haciendo bien
las cosas desde el principio nos ahorramos mucho esfuerzo.
Mírenlo sólo por encima. Quizá aun no sepan entender la mayor parte de lo que dice, porque
hemos aplicado algunos cambios, que son lo que diferencian un buen programador de un
chapucero. Procedamos por partes para que vaya entendiendo todo lo que pone.
Comentario de cabecera
Si quieren, vean nuevamente el video que les puse al principio y verán que el programa enciende y
apaga los led de tres forma diferentes de forma consecutiva y vuelve a repetir el proceso. Por tanto
lo que pretende este programa es controlar el encendido y apagados de los leds, cada uno
conectado a un pin diferente, de modo que se haga de tres formas diferentes
1º Encender las luces de un extremo al otro y volver hacia el otro lado de la misma forma
2º Encender de los extremos y luego los del centro y repetir tres veces
3º Encender todos los leds uno tras otra y apagarlas en el mismo orden
Repetir el ciclo
Esto es un comentario para que lo entiendan quienes hacen los programas, los humanos y explica
lo más extractado que se pueda lo que hace el programa.
Hasta ahora, habíamos visto los comentarios que se escriben con dos barra inclinadas (//), estos
comentarios son para una sola línea, pero si queremos escribir un párrafo, se utiliza otro juego de
caracteres para que el compilador salte lo que hay escrito ese párrafo Los juegos de caracteres en
lugar de las dos barras (//) son (/*) al inicia el párrafo y (*/) para acabar.
Dentro de estos dos juegos de caracteres, se puede escribir lo que quieras sin que la máquina lo
tenga en cuenta. El que cada fila comience por un asterisco (*) no es obligatorio, pues lo que hay
entre (/*) y (*/) le es indiferente al programa, (i siquiera lo compila y l pasa a la tarjeta), pero se
suele hacer para resaltar mas y el texto del comentario.
Lo normal es como mínimo, lo que hacemos en este caso, escribir el titulo del sketch y una
pequeña descripción de lo que hace. Con frecuencia añaden otros datos que ayudan a mantener
cierto orden, como el número de la versión o la fecha de la última modificación, que puedan
ayudar a saber cual de las distintas versiones que tienes guardadas es la más moderna.
¿Y que son parámetros y variables? – Son nombres simbólicos que adquieren valores que
posteriormente se utilizan en el programa.
Parámetros
De los parámetros he hablado en el capítulo anterior al explicar lo que era una función. El
parámetro era un valor que que se utilizaba en una función que hacia que esta actuar de forma
diferente de acuerdo con el valor del parámetro.
Hasta ahora hemos utilizado funciones que utilizaban parámetros estándar como “HIGH” o
“OUTPUT”, que no hay que explicar al sistema los que son e indican, porque son propios del
sistema y números como el “13” para indicar el pin que queremos utilizar, o “1000” para indicar a
la función “delay” que retarde el proceso 1000 milsegundos, pero también podíamos haber
introducido un parámetro para traspasar estos valores, con tal que el parámetro tome valor antes de
utilizarlo en la función.
siempre que previamente hubiéramos informado al sistema que “pinconluz” es un numero entero
al que en algún momento le asignamos el valor 13
Función “int”
Donde “int” (integer =entero) es el nombre de la función estándar que informa que el parámetro
que vamos a definir es un numero entero, (otras funciones estándar similares informan de los
parámetros que son de otra naturaleza como textos, (por ejemplo “apellido) o números decimales
como los números pi, e), y además ese entero se encuentra comprendido entre –32,768 y 32,767, o
sea entre –2^15 y (2^15) – 1.
“nombre” es el elegido por el programador para dar a ese parámetro. Puede ser cualquier nombre
pero aconsejo que siempre se utilicen minúsculas y sea fácilmente relacionarle para el uso que
se le va a dar.
“valor” es un numero entre cualquiera -32,768 y 32,767 que decidimos que va a tomar el
parámetro
Variables
Variables, son exactamente igual que los parámetros, Su única diferencia es que mientras los
parámetros conservan invariable su valor durante todo el programa, las variables, como su
nombre indica, pueden variar de valor a lo largo del programa. Supongamos que un sensor toma
la temperatura de un vaso con agua y la guarda en la variable “temperatura” y la introduce en el
sistema para regular un termostato. Indudablemente, el valor de la variable “temperatura” puede
variar y tomar cualquier valor entre los que pueda fluctuar la temperatura del agua, Para que el
sistema lo comprenda definiremos la variable igual que si fuera un parámetros, y la daremos
cualquier valor de inicio, pues el programa ya se ocupará de cambiarlo. (esto lo veremos mas
adelante así que ahora no me complico más).
int temperatura = 0
Como ven exactamente igual que si fuera un parámetro, sólo que el valor inicial que le damos,
puede ser cualquiera, generalmente el valor que deba tener la primera vez que se utilice, porque el
que vaya a tener se lo adjudicará el sensor de temperatura, (o termómetro), cuando mandemos al
sistema leerla.
La pregunta obligada es, ¿Porque hay esos límites tan absurdos de –32,768 y 32,767? –
Como saben, la maquinas digitales solo funcionan con bits que pueden tener solo el valor 0 o
1, (realmente cargado o no cargado), por tanto, se acude a un truco para escribir números mas
grandes que es descomponerlos en potencias de 2,
Cada numero solo tiene una descomposición posible. Se entiende que un O quiere decir que ese
número en su descomposición, no utiliza esa potencia y un uno que si la utiliza. Pongamos un
ejemplo, el numero 36, es igual a (0x1)+(0x2)+(1×4)+(0x8)+(0x16)+(1×32) o sea que solo utiliza
las potencias (2^2) y (2^5) por tanto se escribirá (de derecha a izquierda, como lo árabes , y
utilizamos 16 bits (o lo que es lo mismo 2 bytes u octetos) Así que el 36 se escribirá
1000000000010010
el 1 del extremo izquierdo indica que es positivo, si fuera negativo sería un 0. Así que hay dos
formas de escribir el cero, pues valen lo mismo -0 que +0
00000000000000 ó 100000000000000
Igualmente los número mas bajo y el más alto que podemos escribir son:
01111111111111111 y 11111111111111111
Y que hacemos cuando queremos escribir números como 47,623 pues utilizar otra función que no
es int que utiliza para guardar los números 32 bits (4 bytes) y que por lo tanto puede guardar
números entre –2,147.483.648 y [Link]
Claro esta también se pueden guardar un entero y muchos decimales multiplicado por cualquier
potencia de 10 con lo cual no podemos directamente guardar un numero inmenso pero si una
aproximación con 16 dígitos representativos.
Todo esto viene de antes cuando la memoria era muy cara y se escatimaba, hoy carece de sentido
en un ordenador normal, pero la tarjeta Arduino no es un ordenador normal solo tiene
32k (32000 bits)de memoria frente a Gigas y Teras que tenes en cualquier PC por lo que aquí si
conviene ahorrar de lo que se pueda. Con todo es provisional pues por ejemplo el Arduino Due,
guarda por defecto todo a 32-bit (4-byte) por tanto ahí un parámetro definido con “int” soporta
núneros en el rango de -2,147,483,648 a 2,147,483,647.
Todo esto lo anticipo a modo de “cultura digital” lo único que es importante es que te quedes con
que en Arduino UNO, (y por “si acaso” en cualquier Arduino), “int” solo vale para parámetros
que van a contener números enteros positivos o negativos menores de 30.000, lo cual por otra
parte, en la mayoría de los casos es más que suficiente, (pero en una minoría de casos no lo es)
Bien, visto esto ya estamos en condiciones de entender todo el contenido del “Área de definición
de variables y parámetros”. Recordemos lo que ponía
Hemos definido una serie de parámetros de nombre “leduno”, “leddos”, “ledtres” y “ledcuatro”
con valores 6, 7, 8, y 9 que claramente apuntan a utilizar los pines de esos números para encender
los led con el color indicado y ademas dos parámetros llamados “tiempo1” y “tiempo2” que
según el comentario que acompaña a la función son la separación de tiempo entre dos luces
consecutivas y el intervalo entre cada juego de luces. Por ejemplo para el parámetro de parada si
puede hacer falta valores mayores de 30.000, pues una hora son 60x60x1000=1.600.000
claramente superior a 30.000. en este caso necesitaríamos declarar un parámetro de doble
precisión que otro día veremos como se hace.
Y puede que te hagas otra pregunta para que voy a definir la función “delay” así;
pues aunque no te lo parezca, para ahorrar tiempo y evitar errores. Te pongo este caso, veras
que en “loop” se utilizan repetidas veces tanto la función “delay(tiempo1)” como la función
“delay(tiempo2)” Imaginate que acabamos el programa y al probarlo descubrimos que las luces
van demasiado rápidas o demasiado lentas, o que la separación entre juegos de luces es confusa,
basta entra en el programa y en el “Área de definición de variables y parámetros” y cambiar los
valores que había por otros más pequeños o más grandes para que automáticamente la función
acelere o ralentice el encendido y apagado de las luces.
Cuando tienes un programa, medianamente complicado, buscar todos los posibles sitios donde se
utiliza un parámetro, no es sencillo, incluso en este programa “tiempo1” se utiliza repetidas veces,
aun siendo fácil de localizar, es mas sencillo cambiar el valor en UN SOLO PUNTO que en
media docena, eliminamos con ello la causa de errores y en cualquier caso, una perdida de tiempo,
ten en cuanta que a la hora de ajustar definitivamente el programa puede que hagas seis o siete
pruebas diferentes hasta dar con la velocidad de cambio de luces que te satisface.
Igual pasa con los pines, puede que sobre el papel todo vaya muy claro pero a la hora de la verdad
al montar el aparato los cables se entrecruzan y conviene mas que lo que habíamos dicho que
controlara el pin 6, lo haga el 12, y viceversa, pues lo montas como te viene bien y en el
programa cambias en “Área de definición de variables y parámetros· el 6 por 12 y el 12 por el 6 y
todo seguirá marchando tan bien como antes.
Sólo falta una cosa no olvidar el final de línea (;) detrás de cada una de las lineas que hemos
creado. Y otra incongruencia aquí el área no se delimita con llaves ({ … }), como en el caso de las
funciones. porque aquí no hay una función general que agrupe la definición de parámetros y
variables.
Función “setup”
// Función setup
void setup() {
// Pines abiertos como OUTPUT
pinMode(leduno, OUTPUT);
pinMode(leddos, OUTPUT);
pinMode(ledtres, OUTPUT);
pinMode(ledcuatro, OUTPUT);
}
Simplemente hemos indicado al sistema que utilizaremos los pines que se corresponden con el
valor de los parámetros “leduno”, “leddos”, “ledtres” y “ledcuatro” de “OUTPUT” (Salida)
por lo que los pines físicos que indiquen los valores de esos parámetros, (en nuestro caso 6, 7, 8 y
9), quedan capacitados para emitir energía a 5 voltios
Función loop
La función loop resulta muy larga pero es muy sencilla y deberias estar ya en condiciones de
comprenderla, porque solo utilizo las funciones ya conocidas “digitalWrite” y “delay” salvo que
las utilizo con parámetros que adquiriron valor en el Área de definición de variables y
parámetros :
Para estudiarla mejor la vamos a dividir en tres trozos según el juego de luces que se realizado
Hace que se enciendan y se apaguen las luces de un extremo a otro segu la secuencia roja, azul,
verde y blanca y en sentido contrario
Esta parte no presenta ningún secreto, enciende y apaga cada uno de los leds del leduno a
ledcuatro y vuelve encendiendo consrcutivamte los led hasta lacabr en el led uno . Cada e led se
entiene encendido un tiempo “tiempo1” ante de apagarse ydar paso al encendido del siguiente,
(casi), simultáne y finalizado el proceso hace la pausa de separacion entre juegos de luches que
dura “tiempo2”
2 Juego de luces
// Función loop
void loop() {
// 1º hace ir desplazándose la luz cada timpo1 de un
// extremo al otro ida y vuelta y para después timpo2
digitalWrite(leduno, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(leddos, HIGH);
delay(tiempo1);
digitalWrite(leddos, LOW);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(ledtres, LOW);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
// vuelta
digitalWrite(ledcuatro, LOW);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(ledtres, LOW);
digitalWrite(leddos, HIGH);
delay(tiempo1);
digitalWrite(leddos, LOW);
digitalWrite(leduno, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
delay(tiempo2);
// 2º enciende de los extremos hacia ay centro y vuelta
// y repite tres veces el cambio
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
digitalWrite(leddos, HIGH);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(leddos, LOW);
digitalWrite(ledtres, LOW);
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
delay(tiempo1);
// segunda vez hace lo mismo
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
digitalWrite(leddos, HIGH);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
;digitalWrite(leddos, LOW);
digitalWrite(ledtres, LOW);
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
delay(tiempo1);
// Repite la tercera vez igual
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
digitalWrite(leddos, HIGH);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
;digitalWrite(leddos, LOW);
digitalWrite(ledtres, LOW);
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
delay(tiempo2); // tiempo2 para separar los juegos de luces
// 3º Se encienden todas una detrás de otra
// y luego se apagan una detrás de otra
digitalWrite(leduno, HIGH);
delay(tiempo1);
digitalWrite(leddos, HIGH);
delay(tiempo1);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
delay(tiempo1);
digitalWrite(leddos, LOW);
delay(tiempo1);
digitalWrite(ledtres, LOW);
delay(tiempo1);
digitalWrite(ledcuatro, LOW);
delay(tiempo2);
}
// Función loop
void loop() {
// 1º hace ir desplazándose la luz cada timpo1 de un
// extremo al otro ida y vuelta y para después timpo2
digitalWrite(leduno, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(leddos, HIGH);
delay(tiempo1);
digitalWrite(leddos, LOW);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(ledtres, LOW);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
// vuelta
digitalWrite(ledcuatro, LOW);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(ledtres, LOW);
digitalWrite(leddos, HIGH);
delay(tiempo1);
digitalWrite(leddos, LOW);
digitalWrite(leduno, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
delay(tiempo2
Lo que hace es encender primero la luz roja y¡un tiempo corto, tiempo1, luego la apaga y
simultáneamente enciende la luz azul, y así sigue hasta finalizar las cauro luces, comenzando la
vuelta apagando el extremo y encendiendo a contigua hasta finalizar. Acabado espera y un tiempo
mayor tiempo2.
Nada hasta el momento que no supiera hacer, pero que da idea de la flexibilidad del sistema para
poner en marcha y parar cualquier tipo de actuador, o aparato capaz de actuar, como luces,
sonidos, motores, resistencias, etc. , de ahí el nombre de tarjeta controladora, desde ella se puede
centralizar el funcionamiento de muchos aparatos.
Enciende a la vez los dos leds de los extremos, luego los apaga y enciende las dos del centro,
Repite la misma acción tres veces.
// **********************************************
// 2º enciende de los extremos hacia ay centro y vuelta
// y repite tres veces el cambio
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
digitalWrite(leddos, HIGH);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(leddos, LOW);
digitalWrite(ledtres, LOW);
// ****** segunda vez hace lo mismo
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
digitalWrite(leddos, HIGH);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
;digitalWrite(leddos, LOW);
digitalWrite(ledtres, LOW);
// ***** Repite la tercera vez igual
digitalWrite(leduno, HIGH);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
digitalWrite(ledcuatro, LOW);
digitalWrite(leddos, HIGH);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
;digitalWrite(leddos, LOW);
digitalWrite(ledtres, LOW);
delay(tiempo2); // tiempo2 para separar los juegos de luces
No presenta ninguna dificultad solo quería resaltar que varios pins se pueden abrir y cerra (casi)
simultáneamente. Y añado nuevamente casi, porque cada pin se enciende en un ciclo diferente del
reloj interno que controla el procesador, por tanto, si formalmente no podemos decir que el
encendido es simultáneo , prácticmente somos incapaces de apreciar la diferencia de tiempo
transcurrido entre dos encendidos consecutivos.
Este juego es muy parecido al primero pero ahora dejando encendidos dos leds. He puesto este
juego para que vean las posibilidades que tiene el sistema, limitado mucho más por nuestra
limitación de concebir usos, que por lo que realmente no puede hacer.
La tarjeta Arduino UNO es limitada, las hay más potentes, pero centrándonos en este modelo las
especificaciones dicen que la tensión máxima que puede entregar cada pin es de 40mA, pero
esto solo vale para momentos puntuales, por ejemplo para lanzar una señal de emergencia al
máximo volumen, en trabajos habituales la intensidad recomendado es de 20mA, No es
conveniente forzar los límites de potencia de forma prolongada, la placa podría calentarse y
dañarse.
El límite de 20 mA por salida significa que, para un voltaje de 5V, la resistencia del dispositivo
que queramos alimentar no debe ser inferior a 200 Ω, yo , (porque así lo he visto en todas partes)
si hay un led que tiene más o menos Ω de resistencia le acompaño de una resistencia de 220 Ω
Por otra parte hay una limitación en cuanto a la suma total de toda la energía entregada por
todo tipo de salidas de la tarjeta que debe ser inferior a 300 mA.
De aquí se deducen dos limitaciones no podemos utilizar mas de 15 pines como salida a la vez, o
sea los 14 digital de OUTPUT y el 5V o 3V como máximo y por otra parte un solo pin tiene
potencia más que suficiente para iluminar un led, hacer funcionar un motor mínimo como un
servomotor de 9g, o encender alimentar algún sensor, pero no es suficiente para alimentar cargas
mayores.
En los experimentos que he hecho, si pones ademas una resistencia de 220 Ωm solo puedes
conseguir que luzcan dos leds en un mismo circuito, pero podrías poner muchos mas si reduces la
resistencia. He estado mirando y los led, en la dirección que dejan pasar la corriente tiene entre 3 y
5 homios, por tanto si pones una resistencia de 170 Ω puedes utilizas los 50 Ω que te has
liberado para poner 10 leds en linea.
Cuando tengas el polarimetro, que te he dicho que dejamos para la siguiente lista de la compra,
pones los leds que quieras en serie y una vez colocados miras con el polarímetro la resistencia
que todos ellos suponen, lo que falte para 220 Ω lo complementas con una resistencia de ese valor
y arreglado.
Tu próximo abeto de Navidad, va a poder tener con un mínimo desembolso en leds y cables y tu
tarjeta de Arduino, 14 circuitos de leds de colores que van a hacer todo tipo de virguerias,
iluminar al árbol de arriba a abajo y de abajo arriba luego en el sentido de las agujas del reloj y
luego en el contrario, primero con luces todas azules y luego rojas, ¡ Lo que se te ocurra !
En la imagen ven un relé de cuatro canales, es decir que mediante ´él podemos controlar hasta
cuatro circuitos que se alimenten de forma autónoma, en este caso con corrientes continuas hasta
12 voltios o con corriente alterna domñestica de 220 voltios,
Arduino tiene suficiente energía para poner hacer que el relé sea capaz de abrir y cerrar
cualquier circuito eléctrico, desde corrientes continuas de seis voltios, producidas por cuatro
baterías de 1,5V, como las que alimentan la mayoría de los juguetes y pequeños
electrodomésticos, pasando por las corrientes a 12 voltios, que por ejemplo tiene una batería de
automóvil, capaz de poner en marcha el motores de gasóleo, a circuitos eléctricos domésticos a
220 voltios de corriente alterna, que alimentan todos nuestros electrodomésticos e incluso con
reles especializados corrientes trifásicas como las que mueven un ascensor o un motor industrial.
Por ello, Arduino puede fácilmente manejar, nuestra nevera, cocina, aire acondicionado,
calefacción, lavadora, lamparas, radios, etc., etc., y en general cualquier aparato eléctrico, con
solo dejarlos enchufados a la corriente y controlar el paso de corriente mediante un relé conectado
Arduino. Todo esto tendrás ocasión de probarlo antes de lo que esperas. Otra de las cosas que irán
en esa lista de compras que estamos elaborando es un juego de relés.
¿Como se hace la misma cosa tres veces no podíamos hacer algo para evitar escribirlo tres
veces?
Me anticipo aquí como me he anticipado al explicar la existencia de los relés, ¡Si! existe un medio
sencillo de indicar que un conjunto de funciones se repita un numero determinado de veces con la
función condicional “for” que hace repetir tantas veces como queramos un conjunto de funciones
comprendidas entre los corchetes ( {… } ), mientras se cumpla un condición determinada. Para no
mezclar conceptos, dejo su explicación para más adelante, conformándome con dejar aquí
infoormacion de su existencia con un ejemplo.
Esta única funcionescrita en tres lineas, imprmiría los números del 1 al 100, pero como digo dejo
para otro dia la explicacion detallada de esta función.
¡Ojo! Observa que cada linea acaba con el carácter punto y coma (;), es imprescindible para que
Arduino sepa que acaba la línea. Perdona que sea tan pesado, pero es que es uno de los errores
que sigo cometiendo yo pese al tiempo que llevo con esto
Por último se van encendiendo todas las luces una detrás de otra, se las apaga en el orden inverso
// **********************************************
// 3º Se encienden todas una detrás de otra
// y luego se apagan una detrás de otra
digitalWrite(leduno, HIGH);
delay(tiempo1);
digitalWrite(leddos, HIGH);
delay(tiempo1);
digitalWrite(ledtres, HIGH);
delay(tiempo1);
digitalWrite(ledcuatro, HIGH);
delay(tiempo1);
digitalWrite(leduno, LOW);
delay(tiempo1);
digitalWrite(leddos, LOW);
delay(tiempo1);
digitalWrite(ledtres, LOW);
delay(tiempo1);
digitalWrite(ledcuatro, LOW);
delay(tiempo2);
No creo que sea necesario explicar nada, si no entiendes lo que hace, yo creo que deberías
empezar por leer el post anterior y luego volver a este. Si lo entiendes perfectamente la lección de
hoy se ha acabado.
Por supuesto al finalizar la función “loop” hay que poner un “}” que indique el fin de la función.
Probar y ensayar
Nunca me cansaré a decir que hagas pruebas y ensayos, solo así y sobre todo tratando de
corregir los errores que cometas es como aprendes de verdad. Para facilitarte el trabajo te pongo
el programa completo de modo que lo puedas Copiar/pegar sin esfuerzo en tu Menú de Inicio de
Arduino. Aun que no lo creas, pese a toda mi experiencia para llegar a que este programa
funcione, ha tenido que corregir muchos errores de pequeña importancia, faltas de ortografía,
olvido de parentesis y cosas por el estilo que son inevitables,
Aconsejo que copies/pegues porque escribir todo el programa y corregir todo ese tipo de errores
no te va a aportar denasiado en tu aprendizaje, tiempo tendrás de aprender a depurar programas, A
cambio te pido que experimentes y ensayes.
Haz cambios en el programa, los que te parezca bien, por ejemplo que se enciendan tres y se
pague la del medio, o que duren mas las de los extremos que la del medio. Todo tipo de pequeñas
variaciones que te haga llegar comprender por el uso la utilidad de cada parámetro y cada función
que utilizamos, solo así llegaras a dominar Arduino.
Te dejo todo junto preparado para el Copia/pega sin más dificultad. Una vez que lo hagas cambia
los pines de salida, cambia los tiempos de parada inventa nuevos juegos de luces, practica,
practica, practica…
Repaso
El objetivo del era familiarizarlos con el manejo de los pines digitales en OUPUT, adicionalmente
hhan apredido
Si ha llegado a este punto con razonable aprovechamiento deberá saber resolver estos dos
ejercicios que le propongo
Para una maqueta nos proponemos hacer un faro que luzca con la misma cadencia del faro
existente en la Ria de Ribadeo
Datos
En la página de Protección civil encontrara los destellos características de cada faro. Viene en la
última columna y hay que saber interpretarlo Según el tipo de juego que proporcione la señal,
podremos encontrar Grupos de destellos (GpD), que agrupa varios destellos y ocultaciones a un
ritmo determinado entre sí, el Destello único (D), que se repite en todo el ciclo), Ocultaciones
(Oc) y Grupo de ocultaciones (GpOc), donde los períodos de oscuridad son más frecuentes o
duraderos que los de luz), o, simplemente, Luz fija (F). Luego viene un letra que es el color del
faro generalmente “blanca” (B) pero a veces “verde” (V) o “roja” (R) y por último la duración
del ciclo en segundos seguido de una s (20s)
Nos proponemos simular el faro situado de la Ria de Ribadeo, que tiene el siguiente ciclo
1º.- En un extremos se acaba de poner la luz en verde mientras que en el otro extremo está en
rojo. Así se mantiene 25 segundos.
2º.- Para estimular el paso de los últimos coches, el verde se pone parpadeante cinco veces con
periodos de encendido y apagados de un segundo. o sea esta así 10 segundos más, mientras que
el otro extremo esta en rojo
3º.- El semáforo se pone en rojo en un extremo, pero para dar tiempo a que salgan los coches que
estuvieran dentro del túnel el otro extremo también continua en rojo durante otros 10 segundos
Se repite el proceso, pero en este caso el es otro extremo el que se pone en verde y el inicial
continúa en rojo.
En mi opinión debe saber resolver estos dos problemas sin ninguna dificultad pues no mecesitan
para ello conocimientos o trucos que no hayamos aplicado exahustivamente en el ejenplo que
aparece en este capítulo por lo que creo que debe tratar de resolverlo pos si nismo.
Estos dos ejemplos los presentaré resueltos próximamente. Posiblemente mi solución sea
diferente a la tuya, porque hay muchas formas de hacer lo mismo. Si la tuya funciona de
acuerdo con las especificaciones que he dado, tu respuesta es válida. No obstante, hay siempre
una solución que es más elegante que las otras, y posiblemente esa sea la mía, porque tengo más
experiencia, pero no es seguro, puede que haya quien encuentre una solución mejor.
La economía de medios.- La solución más corta, que menos y mas pobres medios utiliza de la
tarjeta
La claridad. La que es mas clara y está mejor documentada
Tenga en cuenta que lo que yo escriba, tu tienes que entenderlo, es fundamental ser claro, porque
programar suele ser labor de equipo y el equipo, tiene que comunicarse perfectamente.
Con mucho gusto recibiré en mi buzón sus soluciones, mándame el texto completo de tu sketch
(haga copia /pega en su email) y si es posible mandame una filmación del resultado de la prueba.
Aquí tiene mi dirección e mail faocho@[Link].
Igualmentee recibiré con gusto nuevas propuestas de otros ejercicios y con vuestro permiso si creo
que aportan algo al aprendizaje les añadiré a esta [Link]én agradecerá que le manden ideas
para ejercicios que se puedan resolver con estee nivel de conocimientos para desarrollarla y con
vuetro permiso, añadirla a este Curso.
Por último. ¿Creería posible que con solo dos lecciones y conociendo únicamente cuatro
funciones pudiera simular cualquier faro del mundo y hacer un semáforo que funciona? ¿Se
da cuenta a que velocidad se aprende en Arduino?
Material necesario
Para una maqueta nos proponemos hacer un faro que luzca con la misma cadencia del faro
existente en la Ria de Ribadeo cuyo ciclo de funcionamiento es como se indica a continuación:
Hardware
Tan solo necesitamos encender y apagar un led refractante lo mismo que hicimos en el capitulo
llamado “Principales opciones del Menú de Inicio de Arduino”, por lo que podemos “reciclar”
el mismo hardware que utilizamos allí y que ampliamos en el capítulo “Uso de los pines digitales
como salida”. Les pongo el esquema .aquí:
Lo que estamos realizando es algo muy típico de los objetos digitales. que consiste en aprovechar
un hardware existente, para sin modificaciones físicas en el hardware, sólidamente cambiando el
software “construir” un aparato, que realiza cosas absolutamente diferentes de lo que hacía cuando
se proyectó.
Software
Puesto que es un derivado del Sketch 2 vamos a llamarle Sketch E5.1, (E de ejercicio 5 del
capítulo 5 y 1 por ser el primero. Añadiremos una línea que nos indique que es una versión de un
ejemplo anterior y lo que hará es lo indicado en el enunciado
// Función setup
void setup() {
// Pines abiertos como OUTPUT
pinMode(pinblanco, OUTPUT); // Pin 13
}
// Función loop
void loop() {
// 1º Tres destellos de 5 décimas de segundos (500 ms) seguidos de
// un apagado 3 décimas de segundo (300 ms) ******************
digitalWrite(pinblanco, HIGH);
delay(tiempo1);
digitalWrite(pinblanco, LOW);
delay(tiempo2);
// ***** Repetir ********************************************
digitalWrite(pinblanco, HIGH);
delay(tiempo1);
digitalWrite(pinblanco, LOW);
delay(tiempo2);
// ***** Repetir ********************************************
digitalWrite(pinblanco, HIGH);
delay(tiempo1);
digitalWrite(pinblanco, LOW);
delay(tiempo2);
// finalizados los terse destellos
// 2º Mantener apagado 6 décimas de segundo (600 ms) ******
delay(tiempo3);
// 3º Destello de 10 décimas de segundos (1000 ms) **********
digitalWrite(pinblanco, HIGH);
delay(tiempo4);
// 4º Apagado 16 segundo (16000 ms) **********************
digitalWrite(pinblanco, LOW);
delay(tiempo4);
// Repetir el ciclo *******************************************
}
Resultado
Observaciones
De forma similar a como se ha programado la simulación de este faro se podría simular cualquier
otro del mundo. con solo comocer los el ciclo de destellos que le caracterizan
Puntuación
Agradeceré ideas de ejercicios que se puedan hacer con estee nivel de conocimientos, sean solo la
idea o su confeccion concreta.
Félix Maocho
11/5/2016
.
Para realizar este ejercicio tal como aquí se resuelve solo se necesitan los conocimientos que se
han ido explicando hasta el capítulo dedicado al “Uso de los pines digitales como salida” que
podemos resumir en los siguientes puntos:
Para una maqueta deseamos simular un semáforo que regule el paso a través de un corto túnel que
no permite el cruce de dos trenes. Para que evitar que un tren arranque mientras que el otro no ha
terminado de pasar, antes de poner un semáforo en verde se dejara que pasen los dos semáforos en
rojo, tanto si hay o no trenes en el interior del túnel. Por tanto el funcionamiento será como sigue:
1º.- En un extremos se acaba de poner la luz en verde mientras que en el otro extremo está en rojo.
Así se mantiene 25 segundos.
2º.- Para estimular el paso de los últimos coches, el verde se pone parpadeante cinco veces con
periodos de encendido y apagados de un segundo. o sea esta así 10 segundos más, mientras que
el otro extremo esta en rojo, el resto no cambian
3º.- El semáforo se pone en rojo en un extremo, pero para dar tiempo a que salgan los coches que
estuvieran dentro del túnel el otro extremo también continua en rojo durante otros 10 segundos
Se repite el proceso, pero en este caso el es otro extremo el que se pone en verde
Hardware
Tenemos que colocar cuatro leds, uno rojo y uno verde en un extremos que llamaremos “Derecha”
(D) y uno rojo y otro verde en el extremo que llamamos “Izquierda” (I)
La duda que se nos presenta es si necesitamos necesariamente cuatro pines para controlarlos, pues
en principio parece que si un led esta rojo en un extremo está verde en el contrario por tanto un
solo circuito que diera corriente a los dos led sería suficiente.
¿Lo es así en nuestro caso?. – No, porque en la condición 2ª hay que poner intermitente el verde
mientras que en el otro extremo esta fijo el rojo y en la 3ºº se exige poner los dos extremos en rojo
mientras que los verdes están apagados
Así pues necesitamos utilizar cuatro pines digitales que vamos a llamar:
El nombre que le damos es Sketch E5.2, (E de ejercicio 5 del capítulo 5 y 2 por ser el segundo.
Puntuación
Si ha realizado el mismo ejercio compara sus resultados con este y proceda a autopuntuarse
Si has conseguido que tu ejercicio funcione como este tienes 5 puntos
Si alguien que no lo ha hecho lo entiende con facilidad un punto mas
Si se entiende con más facilidad otro punto mas
Si tiene menos lineas de código que este un punto mas y otro punto por cada 19% de diferencia
Si utiliza recursos de la tarjeta de menos importancia otro punto más
Si quieres mandame el programa en un email y (si tengo tiempo) te lo comento. Agradeceré ideas
de ejercicios que se puedan hacer con ester nivel de conocimientos, sean solo la idea o su
confección concreta.
Total 6 puntos, aprobado alto, podría mejorar la nota reduciendo el número de lineas pero para
ello necesito utilizar conocimientos que aun no he explicado. Cambien podría mejorar utilizando
recursos de menos valor de la tarjeta, pero como en el caso anterior necesitamos para ello utilizar
conocimientos que aun no he explicado.
Cabria añadir más complicación a este ejercicio poniendo en cada semáforo un led naranja y
utilizando dos pines digitales más, pero opino, que esa complejidad no añade mas enseñanza, Si lo
desea como ejerció adicional puede hacerlo así como cambiar los tiempos de encendido y apagado
o cualquiera de las especificaciones de funcionamiento.
Observaciones
Como observaran las luces que deberían ser verdes son azules porque no he encontrado los led
verdes, eso no cambia el ejercicio en absoluto.
Otro cambio ha sido el de las duraciones previstas inicialmente. Pues la experiencia indica que los
tiempos inicialmente propuestos no eran poco adecuados a la hora de experimentar por ser muy
largos por lo que he decidido cambiarlos a los siguientes, tiempo de circulación (tiempo1, 4s,
tiempo de parpadeo (tiempo2), 0, 4s y tiempo de circulación interrumpida (tiempo3) 2s. Si en un
trabajo real hubiera que poner finalmente los tiempos indicados inicialmente, una vez acabadas las
pruebas se cambiaría en “Área de definición de variables y parámetros “ los tiempos y con una
prueba final estaríamos seguros que el programa cumple al pie de la letra las especificaciones que
se hicieron.
Observen con que facilidad cualquier sencillo enunciado se trasforma en un programa complejo,
sin embago complejo no es equivalente a complicado, Este programa es muy sencillo de
comprender aunque resulte complejo y laborioso de poner a punto.
Como al final de medio ciclo se apaga una luz roja, que se enciende en el comienzo del otro
medio, podemos eliminar esas dos funciones. En principio igual se podría hacer al fin del loop y
comienzo del nuevo loop, sin embargo, en el primer loop si hay que encender el led rojo, porque la
primera vez viene apagado. Por ello En los siguientes ciclos encenderemos algo que ya está
encendido, pero no pasa nada con ello.
He dejado estas líneas insertando “//” como comentario para que resalten. Realmente podríamos
borrarlas, así el programa conseguiría un punto más de valoración, pues tendría menos líneas
haciendo lo mismo, sin que se complique su compresión.
Es muy frecuente que la primera vez haya que hacer cosas que en los siguientes loop ya no es
necesario hacer, en muchos programas habrá que saber dir ferenciar si se está ejecutando el
primer loop o los sucesivos. Ya aprederemos a diferenciarlo. .
A mi, personalmente, me ha costado bastante poner a punto este programa, porque en su sencillez,
tiene un juego de encendido y apagado de leds que es posible que inicialmente confunda mucho.
La forma de poner a punto un programa y cualquier asunto en informática se basa en la vieja
máxima de “Divide y vencerás”. Es decir, separar un problema un un conjunto de problemas
más sencillos que puedan resolverse por separado y a su vez dividir estos problemas en otros aun
mas sencillos, hasta que no veamos posible y sin complejidad resolver esos puntos
independientemente de lo que tenga que hacer las otras partes. Lo importante para poner a punto
un programa es ir poniendo a punto cada una de sus partes, poco a poco y no tratar de resolverlo
del todo, sino cada parte por separado
En nuestro caso hemos hecho lo siguiente:
Análisis funcional
Generalmente si el enunciado del ejercicio esta bien redactado, en él debe quedar especificado en
que condiciones ha de funcionar el programa, esto es en suma el Análisis Funcional. En nuestro
caso fue le siguiente:
Para una maqueta deseamos simular un semáforo que regule el paso a través de un corto túnel que
no permite el cruce de dos trenes. Para que evitar que un tren arranque mientras que el otro no ha
terminado de pasar, antes de poner un semáforo en verde se dejara que pasen los dos semáforos en
rojo, tanto si hay o no trenes en el interior del túnel.
Análisis Orgánico
Del estudio del Análisis Funcional se debe poder definir el Análisis Orgánico o que es lo que debe
hacer nuestro programa para cumplir los requerimientos del Análisis Funcional. Aquí comienza el
trabajo de dividir algo complejo en partes más sencillas.
1º.- En un extremos se acaba de poner la luz en verde mientras que en el otro extremo está en rojo.
Así se mantiene 25 segundos.
2º.- Para estimular el paso de los últimos coches, el verde se pone parpadeante cinco veces con
periodos de encendido y apagados de un segundo. o sea esta así 10 segundos más, mientras que el
otro extremo está en rojo
3º.- El semáforo se pone en rojo en un extremo, pero para dar tiempo a que salgan los coches que
estuvieran dentro del túnel el otro extremo también continua en rojo durante otros 10 segundos
4º Se repite todo el proceso, pero en se cambian los extremos se pone en verde y rojo
Cambien se puede definir el Hardware que en neutro caso serán dos semáforo de dos led cada
uno que necesitan cuatro pines digitales de salida para funcionar. Como se ve en el esquema que
puse al principio.
Con todo esto, estamos en principio en condiciones de intentar iniciar programarlo. Por lo pronto
ya tenemos el encabezamiento, un extracto del Análisis Orgánico, También podemos escribir el
“Área de definición de variables y parámetros” y la Función “setup” pues se deduce en parte del
Análisis Orgánico, (las diferentes valores de los tiempos) y del hardware que hemos diseñado, (los
pin que se van a utilizar como OUPUT).
Todo provisional y dispuesto a cambios si algún paso posterior exige hacer un cambio en lo ya
redactado. Pero cuando demos un paso más lo anterior debe funcionar perfectamente según lo
previsto y no contener errores.
Lo más peligroso y lo que hemos de tratr de evitar
No nos puede pasar nada peor que dos o mas errores se solean a la vez, pues al tratar de corregir
uno no apreciaremos arreglo y fácilmente tratemos de buscar la solucion volviendo a cambiar en
ese punto con otra solución ,que tampoco puede arreglar nada, porque la solución pasa por arreglar
también simultáneamente otro lado. Por ello es muy importante, que en la medidas de lo posible,
los errores se produzcan sólo en lo que añadimos a la prueba, porque lo anterior lo dejamos
funcionando correctamente.
Observen primero de todo algo que es una tontería, pero facilita mucho la vida, sujeto la tarjeta
Arduino a la “protoboard” con una anilla elástica de goma. Esto mantiene solidarias ambas
tarjetas y evitan, que al manipularlas, se tire sin querer de los cables y se suelten. Por otra parte, al
montar los circuitos se tiene las dos manos libres para manipular y resulta mas sencillo. En mi
opinión siempre que sea factible conviene mantener solidarias por un sistema o por otro, la tarjeta
y la protoboard, y en general todos los componentes que se utilicen. En programas con poca
complicación basta utilizar anillas elásticas para hacer de todo un solo objeto.
tes que nada, conviene probar dos cosas, si lo que hemos escrito del programa está bien escrito
o tiene errores ortográficos, como unos de mayúsculas en lugar de minúsculas o faltas de “:” al
final de lineas. Algo que nos indicará la compilación que detecta fácilmente este tipo de errores.
Por ello mada más terminar la función “loop” probaremos si puede compilarse. Cuando hayamos
terminado de compilar y se cargue el programa en la Tarjeta no hará nada, porque todavía
tenemos vacía la función “loop”, pero al menos habremos depurado algún error que otro. Y si el
montaje que hemos realizado en la protoboard no contiene errores de montaje
Probamos y compilamos esta parte y vamos detectando y corrigiendo los errores que hayamos
cometido hasta que el programa se compile y se cargue en la tarjeta de Arduino. Con esto
habremos resuelto muchos errores que aun siendo menores pueden dar muchos quebraderos de
cabeza
Por otra partee teniendo compilado y cargado el programa ningún circuito de los que salen de los
pines debe tener energía, pero podemos probar si los hemos montado bien dándoles energía con un
cable provisional que salga de V5, así comprobaremos que el hardware esta bien montado (los
leds “pinchados” en la dirección correcta, por ejemplo)
Vean en la primera foto un cable naranja que parte del pin 3V, (situado all lado izquierdo de la
tarjeta), y que anda suelto. Ese cable le iremos introduciendo sucesivamente en la misma fila
donde mueren los cables que parten de los pines digitales, (situados al lado derecho de la tarjeta).
Si hemos hecho el montaje de los componentes correctamente, (sobre todo si los leds se han
conectado de la forma correcta, pataa larga hacia donde viene la corriente) y conectan en los
origicios de la “protoboard” previstos, de forma que los circuitos estén internamente conectados,
lo que deba ocurrir cuando pase energía por el circuito ocurriraá (en este caso que se enciende el
led)
Uno por uno iremos probando todos los circuitos para cerciorarnos que funcionan según lo previst.
Acabado esto ya podemos empezar a ir depurando el programa.
Iniciar el programa
Ya estamos en condiciones de escribir el primer trozo del programa que en este caso es
sumamente sencillo. encender una luz verde en un extremo y una roja en otro. Pese a todo
conviene probarlo por separado del resto del programa. añadimos al programa entre los dos
corchetes “,{…. ]“, las siguientes instrucciones
Esto debe encienden un led verde en el extremo izquierdo y rojo en el derecho y al final del ciclo
las volvemos a apagar pues se espera que el siguiente ciclo comience tal como salió de “setap”,
con todo apagado, también añadimos una pausa al final de todo para poder diferenciar los
diferentes loops y tener tiempo de asimilar si lo que ha pasado se corresponde con lo previsto.
Corregimos los errores que hubiéramos cometido y observamos que todo va bien pero los tiempos
son muy largos para las pruebas, por lo que opto para reducirlos en el futuro a 4000 tiempo1 y
1000 la pausa final
Segundo módulo del programa Hacer parpadear la luz verde
Este punto lo haremos en dos veces, la primera hacerla parpadear una vez y la segunda copiando
cuatro ves mas las mismas instrucciones.
A continuacion de encender las luces, añadimos primeramente las instrucciones para que
parpadee una vez, el final no hay que cambiarlo pues en este trozo no se encienden nuevoa leds.
Como signe al final los mismos led encendidos no tenemos que cambiar el final-
// 2º.- Circonio I >> D (IV) parpadea 5 veces (tiempo2) resto no cambian ****
// 1º Vez ***************************************************
digitalWrite(piniv, LOW);
delay(tiempo2);
digitalWrite(piniv, HIGH);
delay(tiempo2);
Probado que funciona el parpadeo hacemos copy/paste de esas íines cuatro veces mas haciendo los
cambios mímimos en los comentarios.
// 2º Vez ***************************************************
digitalWrite(piniv, LOW);
delay(tiempo2);
digitalWrite(piniv, HIGH);
delay(tiempo2);
// 3º Vez ***************************************************
digitalWrite(piniv, LOW);
delay(tiempo2);
digitalWrite(piniv, HIGH);
delay(tiempo2);
// 4º Vez ***************************************************
digitalWrite(piniv, LOW);
delay(tiempo2);
digitalWrite(piniv, HIGH);
delay(tiempo2);
//5º Vez ***************************************************
digitalWrite(piniv, LOW);
delay(tiempo2);
digitalWrite(piniv, HIGH);
delay(tiempo2);
Falta añadir tan solo la pausa donde los dos lads están en rojo, apagamos el estreno verde y le
ponemos en rojo. Como en este nódulo si cambiamos las luces que quedan encendidas al final del
loos cambiado los pins que apagamos al final pues dejar todo apagado como cuando empezó.
Finalizado de poner a punto este módulo, hamos hecho todo lo reg fernte al paso de la circulacion
de Izquierda a Derecha ahora hara que hacer lo mimo paraa que pase la circulacion de derecha a
Izquierda. Observemos como está el programa hasta ahora
Bata ahora hacer copy/pate de cada uno de los módulos cambiando izquierda por derecha es decir
donde ponga “iv” poner “dv” y donde ponga “Ir” poner “Dr” y viceversa,
Aprender a utilizar los pines digitales como detectores del paso de corriente por otros circuitos.
Familiarizarse con la funciones que ya hemos aprendido y aprender algunas nuevas relacionadas
con el uso de los pines como entrada.
Material necesario
Todos estos conocimientos se explican en detalle en los capítulos anteriores del “Uso de los pines
digitales como salida (OUTPUT)“ y “Interruptores, pulsadores, conmutadores y relés
utilizados en electrónica”
En el capítulo “Uso de los pines digitales como salida (OUTPUT)“ practicamos el uso de los pin
digitales como puntos de control de la salida de corrientes de 5V y manejamos el más sencillo de
los actuadores, el led, que luce cuando se permite el paso de la corriente y permanece apagado
cuando no pasa corriente. En estese capitulo, vamos a aprender a manejar sensores, que son los
aparatos que “avisan” a Arduino, de los cambios ocurrido en su entorno, para que en función de
esos cambios, “decida” que acción ha de ejecutar y en función de ello, ponga en marcha los
“actuadores” necesarios para llevarla a cabo.
Con ello entramos en un nuevo mundo, el de la automática y la robótica, donde los objetos que
creemos, dejen de ser meros autómatas que repiten incansablemente aquello que les hayamos
programado, como ocurría en los ejemplos del faro y el semáforo que vimos en capítulos
anteriores, para entrar en la confección de objetos que “reaccionan” a los cambios de su
entorno, actuando de forma diferente, de acuerdo a lo que “deducen“ de los cambios
observados.
El más sencillo de los “sensores”, el equivalente al led en los actuadores, es el pulsador, botón,
o “push button”, que por todos estos nombres se conoce, habitualmente lo llamaré pulsador, pero
si hay que buscar en Internet. utilice la palabra “push button” pues es como localizará mas
fácilmente toda la información que hay (generalmente en inglés), sobre el tema.
De los interruptores, de los que el pulsador es uno de los tipos
hablamos en el capítulo anterior. Quedamos en que había varios tipos de pulsadores que se
pueden agrupar en dos grandes familias los “pulsadores NO”, o normalmente abiertos (Open),
cuyo esquema se corresponde a la imagen inferior y los “pulsadores NC” o normalmente
cerrados (Closed), cuyo esquema se corresponde a la imagen superior. Los primeros cuando no se
los pulsa no dejan pasar la corriente (normalmente abiertos) y los segundos si (normalmente
cerrados), cambiando de fase al oprimir el pulsador.
,
Por ello lo primero sera estudiar que tipo de pulsadores manejamos. Como indiqué lo más sencillo
es hacer unos circuitos que partiendo de el pin 5V (5 voltios) pasa por una conector del pulsador y
sacar un cable de otro conector y después de pasar por el led y una resistencia de 220 Ω mere en el
pin de tierra GRD, Así de esta forma se prueban como funcionan los contactos del pulsador y que
ocurre cuando se oprime el botón. Les dejo el esquema del pulsador mas complejo que se pueden
encontrar pues es a la vez NO y NC según se conecten sus bornes.
Y el esquema del circuito para probarlo rápidamente cambiando simplemente de posición los
cables azules
En mi caso concreto encontré que siempre actuaba como un pulsador NO, (normalmente abierto),
y que las dos patas de cada uno de los lado estaban conectadas entre si, por lo que era indiferente a
que bornes nos conectáramos siempre que los cables se conectaran en lados opuestos
No lo he hecho, pero muy posiblemente si abrimos el pulsador, nos encontramos con algo muy
semejante al esquema que les muestro Dos cables en U que forman las cuatro patas del pulsador y
sobre ellos un circulo de metal pegado a una esponja de goma, que es el muelle que separa el
circulo de metal de los dos cables cuando dejamos de oprimir como indica este esquema. Por ello
el esquema mas claro par este tipo de pulsadores es el que sigue:
Conociendo ya como es nuestro pulsador, podemos pasar a estudiar como le podemos utilizar.
Indudablemente como ocurre en este ejemplo que hemos montado, un uso del pulsador es poder
abrir y cerrar un circuito con un LED, zumbador o un motor, a voluntad, de forma que el aparato
funcione o no según apretemos el botón. Posiblemente en algún montaje queramos tener
controlado un aparato por un botón, no obstante, este uso será minoritario y raro, pues teniendo
una placa especializada en abrir y cerrar circuitos, resulta claramente innecesario el uso de un
pulsador manual, que por otra parte si es NO, nos obliga a estar oprimiendo el botón durante todo
el tiempo que deseemos tener el circuito cerrado.
Para ese trabajo es más eficaz el conmutador, como las llaves de la luz que un pulsador. De hecho
en la vida real se utilizan de esa forma muy poco los pulsadores, que y recuerde, en los timbres,
las minipimer y los taladros, en la inmensa mayoría de los aparatos, se instala un conmutadores
del tipo i/O que en una posición permite de forma continuada el paso de la electricidad y en ella
otra posición impide el paso, como por ejemplo pasa en los conmutadores de las lámparas.
Mas o menos, la gráfica del voltajes que se alcanzan en los momentos posteriores a interrumpir o
dar la corriente eléctrica es como indica esta imagen
La fluctuación dura poco tiempo. del orden de unos milisegundos, algo que en principio parece
que no nos debiera importar, pero tenemos que tener en cuenta la alta velocidad de procesamiento
de Arduino. Pudiera ser que en ese tiempo se dieran varias vueltas a la función “loop”. por lo que
Arduino. pudiera interpretar los diferentes voltajes leídos en cada vuelta, como que activemos y
desactivemos la corriente y “deducir” de ello. que hemos encendido y apagado diferentes veces el
interruptor, o en el caso del pulsador, que lo hemos presionado diferentes veces.
Por ello, debemos poner alguna medida que elimine este problema. La mas sencilla, (hay otras
muchas), es anteponer un pequeño “delay” a la lectura del voltaje, de modo que garantice que
leemos el voltaje una vez estabilizado. Suele ser suficiente que esta interrupción dure 100 mili
segundos, una fracción de tiempo ,que pasa desapercibida en el funcionamiento del programa,
pero que evita el riesgo de producir diferentes lecturas en el periodo de rebotes del interruptor
(En este enlace Mariano del Campo explica otra solución más profesional).
Aunque no lo parezca, el pulsador se utiliza mucho más, como la forma de indicar a un aparato
que realice una tarea que ya tiene programada, pesemos por ejemplo en las botoneras de un
ascensor, en el pulsador de la luz de la escalera, y los cien botones de un telemando. Un
pulsador se utiliza habitualmente como elemento comunicador con las máquinas de lo que
deseamos hacer, es por ello un sencillo sensor de la maquina, mediante el interruptor la máquina
siente la presión que se ejecuta.
Un uso lógico del interruptor es utilizarlo para indicar a la tarjeta, cuando queremos iniciar
o finalizar una acción determinada. Por ejemplo, cuando queremos encender una luz y cuando
la queremos apagar. Si conseguimos que la tarjeta detecte cuando hemos oprimido el pulsador,
podemos hacer que si el LED esté apagado, se encienda, y si esta encendido, se apague, sin
necesidad que durante todo el rato que esté encendido estemos apretando el botón del pulsador. En
resumen podemos utilizar el/los, pulsador/es para indicar a la máquina cuando deber modificar su
forma de funcionamiento.
En este uso, el interruptor como hardware tiene que venir acompañado en el software de un
mandato condicional del tipo “Si oprimió el botón, haz tal cosa”: Entonces lo primero que
tenemos que saber es como se entera la tarjeta que hemos oprimido el botón.
Que hace un pin como INPUT
Esa función hace que el pin actúe como un VOLTIMETRO es decir como un aparato que mide
la intensidad de la corriente que pasa por un punto, Y, ¿Para qué queremos tal cosa? – Si
conseguimos que al apretear un boton cambie un circuito de estar a ov a pasar a 5V, (o viceversa),
habremos construido un “sensor de presión”. Por este sistema la ´tarjeta Arduino, se puede
“enterar” cuando alguien ha pulsado un botón e iniciar lo que esté previsto hacer cuando eso
ocurra.e
El método que se utiliza es el siguiente, cuando se lo mande el programa, se lee el voltaje del cable
que se introduce en el pin y si el voltaje es superior a 3,5 voltios avisa que hay “voltaje alto” (>3,5
V) y la funcion devuelve el valor “1”, si el voltaje es “bajo” (<3,5V) informa “0”, pues como es un
pin digital solo tiene capacidad de decir si o no, en forna de 1 y 0.
Hemos modificado un poco el último esquema sacando un cable verde que conecta también con la
salida del pulsador y termina en el PIN4 que abriremos como “INPUT” y un led que parte del
PIN3 que abriremos como OUPUT.
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee pulsador
}
// Función loop
void loop() {
// 1º Leer el pin4 y deposita el resultado en “valor”
// Repetir el ciclo
Creo que ya debe ser sencillo entender este sketch pues gran parte de las cosas ya las conocen,
además que por si mismo es muy sencillo.
Obvio explicar nada del encabezamiento pues a estas alturas deben saber todo sobre los
comentarios, así pues paso directamente al “Área de definición de variables y parámetros” que
como única novedad creo que por primera vez definimos una variable “Valor” que dentro del
programa tomará el valor de la lectura del voltaje que haga el pin 4, solo puede tomar dos valores
posibles o y uno por lo que podemos definiría como entero “int” pero es que así es como espera
encontrarse la variable la función de lectura de la tensión.
Pasamos a la función “setup” que ha configurado el pin 3 como “OUPUT” y el pin 4 como
“INPUT”. Podíamos no haber configurado el PIN4 como “INPUT” porque de fabrica todos los
pines están configurados como INPUT por lo que realmente solo hace falta configurar los
OUPUT. (aconsejo que lo compruebe, sólo así se aprende), sin embargo aconsejo escribirlo pues
es solamente una linea más por Pin que haya que configurar como INPUT y añade mucha
claridad al programa, pues resalta la función de cada pin algo que no queda claro en los esquemas.
La función que se utiliza para configurar un pin como INPUT es “pinMode”, exactamente la
misma que se utiliza para abrirlos como OUPUT, pero claro esta cambiando el parámetro de
salida con la siguiente sintaxis
pinMode(numpin, INPUT)
Entramos en la función “loop” que platea un poco mas de novedades en primer lugar esta la
forma de hacer la lectura de la tensión del cable que penetra en el pin la función “digitalRead”,
que cuando el sketch se la encuentre leerá el voltaje de cable que penetra en el pin indicado, que
previamente ha de ser configurado como “INPUT” y si encuentra que la tensión es menor que
3,5V (en una tarjeta que funcione a 5V como la Arduino UNO) devuelve un “0” y si es mayor
devuelve un “1”, Su sintaxis es como sigue
val = DigitalRead(PinInput)
“val” es una variable que puede tener cualquier nombre, (en nuestro caso se llama “valor”), que
previamente ha sido definida como variable numérica y entera y que solo puede recibir de la
función “DigitalRead” los valores “0” y “1” según la tensión de cable que entra en el pin sea
menor o mayor que 3,5V.
“DigitalRead” es una función del sistema que lee el voltaje de un pin. Se escribe exactamente así
con las mayúsculas que se indica
“PinInput” numero o una variable con un valor correspondiente al pin digital que se quiere leer el
voltaje que soporta que previamente se ha configurado como “OUPUT”
Función condicional if
Utilizamos también una nueva función que pertenece al grupo de la funciones condicionales, lo
que quiere decir que los comandos que abarcan esta función y que quedan entre dos corchetes
*{….}” solo se ejecutan si se cumple una condición especificada La función se llama “if” (si) y su
sintaxis es como sigue ;
“if” es una función del sistema del tipo condicional, es decir que solo se ejecuta si se cumple la
condición especificada entre los paréntesis (….) que vienen a continuación
“var” una variable definida previamente que tiene un cierto valor, (en nuestro caso ha adquirido el
valor que devuelva la función “DigitalRead”
“comp” es la comparación que hay que cumplir. Las condiciones aceptadas son
En nuestro caso utilizamos la igualdad (==). Observe que son dos signos igual (=) seguidos
¿Que quiere decir eso? – Que el valor de la expresión que está a la derecha si sustituye el valor
que tuviera hasta ese momento las variable que está a la izquierda
Por ejemplo
var = 3 ;
Indica que la variable “var”, (que habremos definido en “setup” muy posiblemente con un valor
inicial, adquiere el valor 3, desde el momento que en la función “loop” se ejecute esta línea, si
posteriormente encontramos una expresión que dice
Observe que esta última expresión, es una “expresión informática”. pero no “expresión
matemática”. donde esta linea seria en matemáticas un claro error, o en caso de aparecer en una
hipótesis, la demostración al absurdo, porque “valor = valor +1” “matemática” se simplificaría
quedando solo “0 = 1”, lo cual es imposible.
Realmente lo más correcto seria utilizar en vez del caracter “=” haber utilizado el caracter “←”
que sería mucho más adecuado, ¿Por qué no se usa?.- Habria que remontarse a la historia del PC a
los Amstrand y Spectrun, esos ordenadores tnían muchas limitaciones gráficas y solo utilizaban
un teclado similar al de la máquina de escribir antiguas en ellos no existian caracteres como el
“Ω” o el “←” y los programadores se tenían que apañar con lo que tenían, sasi que echarn mano
del signo de igualdad o identidad para expresar la transferencia de valores
Por eso una linea del tipo “variable1 = variable2 + variable3” tiene sentido en una expresión
informática, independientemente del valor que para entonces tenga “variable1”, en cambio la linea
inversa “variable2 + variable3 = variable1” no tiene “sentido informático” aunque lo pueda
tener “matemático” pues el programa intentara traspasar el valor de “variable1” al otro lado de
el símbolo “igual” pero no sabrá como repartirlo entre las dos variables
Si se cumple la condición impuesta ( en ingles if), entonces se ejecutan las líneas incluidas entre
los dos corchetes ({…. }), cualquiera que sea el contenido incluido entre los corchetes, pero si la
condición no se cumple, entonces el programa se salta todas esas líneas de programa y continúa
en la siguiente línea que venga a continuación de el último corchete de cierre “}” . Por eso es una
función condicional, solo se ejecuta si se cumple la condición. Estas c funciones condicionales
son las que permiten que la programación sea muy elástica, tanto como lo desee el programar,
pues siempre puede mandar hacer cosas sólo “si ocurre tal cosa”.
Aunque aquí no se haga, ni se lo pongo para no complicar más la cosa, simplemente como
información, añadiré que una función “if” puede tener en las lineas que controla cualquier cosa,
como indicamos, incluso otra función “if”, esto se llama tener “anidada” otra función condicional
que se ejecutarán o no las funciones comprendidas entre los correspondientes corchetes ({…})
según se cumple la condición que contiene la segunda función “if”. Por esta razón los corchetes
siempre vienen por parejas y de estar anidados, los más interiores son los que forman un bloque y
los mas exteriores son los que forman el bloque de funciones que contiene al “If” anidada.
Como ven, es un poco lioso. así que de momento pasamos de explicarlo con detalle simple mente
pondré un ejemplo literal para que se entienda el concepto.
Imaginemos que estamos un “Robot Machista” es decir un robot grosero que siempre que se crece
con una mujer de mas de 170 cm y sea rubia diga ·TIA BUENA”, El esquema de la programación
seria algo parecido a los siguiente los sensores detectarian la presencia de personas a su alrededor
su tamaño, sexo y color del pelo y en un momento el programa haría algo parecido a esto
if(“sexo” == hembra) {
if ¨(pelo == rubio)
Solamente si se cumplen todas las condiciones el robot diría ¡¡¡ TIA BUENA !!! No es un
ejemplo muy fino lo reconozco pero pero espero que valga para entender el concepto de Funciones
condicionales anidadas,
También de momento, a modo de anticipo, les informo que la función “if”(si) puede asociarse a
otra función llamada “else”(en otro caso). En este caso habrá por un lado un conjunto de
instrucciones comprendidas entre los corchetes ({…}) del “if” y a continuación el otro conjunto
situado entre lo corchetes ({…}) del “else” y o se ejecuta el primero, si se cumpla la condición
exigida o se ejecuta el segundo si no se cumple, pero siempre se ejecuta uno de los dos conjuntos
de instrucciones,
Pongo un ejemplo, tambien un poco sencillo para que se entienda el mecanismo del
funcionamiento. Apretamos un pulsador y si esta apagado un Led lo encendemos, “en otro caso lo
apagamos. El esquema de la programación seria algo parecido a los siguiente
Encender el led
Else {
Apagar el led
}
Como digo sólo apunto las posibilidades que tiene la función “ie” hay otras funciones
condicionales semejantes que iremos utilizando en su momento pues son la herramienta mas
adecuada para conseguir que los objetos hechos con la Tarjeta Arduino actúen como automatismos
o como robots, que es el uso lógicvo de los aparatos que utilizan la Tarjeta Arduino para su
control.
Otra cosa el indentado no es obligatorio, pero conviene hacerlo porque facilita mucho entender de
un vistazo lo que hace cada una de las funciones condicionales.
* 1º Leer el pin*
* 2º Si la lectura es “1” encender el led que sale del pin 3
* 3º Si la lecturas es “0” apagar el led que sale del pin 3
El montaje que hemos hecho para averiguar el voltaje de una linea es el más habitual y se
denomina montaje PULL DOWN, (tirar abajo. o derribar, quiere decir que el voltaje está
normalmente a 0 voltios).que como se ve en el esquema, el orden de los elementos que interviene
en el circuito a investigar es el siguiente:
Lo mas importante es que el punto de donde salga el cable que va al Pin abierto en INPUT tiene
que estar situado entre el interruptor y la mayoria de las resistencias para que estemos seguros que
cuando el pulsador no se oprina esté a 0V 0porque permanece unido a tierra, pero aumenta a ,
(cerca de), 5V cundo se oprima el pulsador, En este cso sera un poco menos pues el Led aunque
pequeña ofrece una cierta resistencia.
Sin embargo como vemos, hay otro montaje posible, donde resistencia y pulsador permutan sus
puestos. Es el montaje PULL UP, (tirar arriba o subir, o que el voltaje esta habitualmente a
5voltios).
En este caso lo mas importante es que el punto de donde salga el cable que va al Pin abierto en
INPUT tiene que estar situado antes de la mayoria de las resistencias y del pulsador para que
estemos seguros que cuando el pulsador no se oprina esté a 0V 0porque permanece unido a
tierra, pero aumenta a , (cerca de), 5V cundo se oprima el pulsador, En este cso sera un poco
menos pues el Led aunque pequeña ofrece una cierta resistencia.
Comparen con el montaje que hay, La diferencia es mínima La mayor diferencia es que el lugar
donde conectamos para estudiar el voltaje a que esta sometido el circuito, pasa de estar entre el
interruptor y la tierra (GRD) a estar entre el interruptor y el alimentador de tensión (5V) y que por
tanto al estar cortado el circuito esta parte del cable de conexión esta a 5voltios habitualmente pero
baja a cero voltios por estar DESPUES de la resistencia y en conexión con tierra (GRD)
En este tipo de montajes, si realmente existe corriente a 5V (PULL UP) el segmento de cable
donde investigamos qué voltaje, estará habitualmente a 5 voltios, puesto que esta conectado con el
Pin 5V, pero tan pronto como apretemos el pulsador caerá a cero la lectura pues toda la carga que
haya en ese segmento de cable se irá a tierra (GRD).
Generalmente y de ser indiferente por otros motivos uno u otro montaje, es preferible el montaje
PULL DOWN pues al final sabemos lo mismo, cundo alguien oprime el pulsador, pero en el
PULL UP someternos a la tarjeta a mayor stress eléctrico, sin embargo el montaje PULL UP es
imprescindible cuando el objeto del control no es tanto detectar si pasa o no electricidad por un
determinado circuito, como si en ese circuito que estamos controlando ocurre una caída de
tensión.
Por ejemplo, imaginemos que querenos establecer alguna alarma para cuando falla la luz en un
circuito, por ejemplo, queremos encender luces de emergencia, con un montaje PULL DOWN, si
el origen la corriente cesa, no detectaremos el fallo, pero si lo haremos un montaje PULL UP
sí, pues cuando falle la corriente detectaremos que el segmento queda a 0V aunque nadie haya
apretado el pulsador.
Hagamos un ejemplo en el que tratemos de detectar tanto si alguien a oprime el pulsador como si
por un fallo de la energía no pasa corriente por ese circuito. Utilizando el montaje Pull Down que
proponemos podremos hacerlo..
Mantenemos el led que nos informa si pasa o no corriente por el circuito, también colocamos la
resistencia de 220 homios y a continuación el interruptor. Es decir los componentes que utilizamos
son exactamente los mismos tan solo varia el orden de alguno de ellos. Cambien cambia es el
punto donde se saca a derivación que se lleva al pin para que Arduino nos diga si el voltaje es alto
(>3,5V) o bajo (>3,5V) . en este caso se “pincha” entre la resistencia y el interruptor. En tanto no
pulsemos el interruptor, el segmento esta con voltaje alto, pero tan pronto apretemos el interruptor
el voltaje desciende pues conectaremos ese pedazo de cable a los 0V de la tierra (GND).
Por tanto si pretendemos en este caso encender un led cuando pase corriente por ese circuito
deberemos encender el led 3 cuando detectemos que el segmento que estudiamos esté en baja y
viceversa por tanto el programa será.
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee pulsador
}
// Función loop
void loop() {
// 1º Leer el pin y deposita el resultado en “valor”
valor = digitalRead(pinint);
// 2º Si la lectura es “0” encender el led que sale del pin 4
if (valor == 0) {
// Repetir el ciclo
Como ven las diferencias entre amboa hardware y sodware son bastante cosméticas el cambio de
orden de las resistencias y los pulsadores y que encienda en un caso cuando detecta subida de
tensión (“valor =1”) y en el siguiente caso, al contrario cuando hay una caida de tensión (“valor
=0”) . Sin [Link] el segundo caso, acambio de someter a mayor stress a la Tarjeta
(normalmente se encuetra el circuito a 5V), detecta no solo las pulsaciones sino además las caidas
de tensión, si desconoectis el cable del Pin V5 en el primer caso la tarjeta no lo detecta y en el
segundo si.
Practicar
No conozco otro sistema más eficaz de aprender el manejo de la Tarjeta Arduino que el practicar.
Os dejo los ficheros de ambos sketsh sin caracteres de eedicion para que podais hacer copy/paste
directamente sin que cometais errores de escritura. Cargar cada uno de esos ficheros en la tarjeta y
ver los resultados, cometer deliberadamente erorres para ver que pasa, (olvidaros algún “}” o
cosas parecidas, dasconectar los componentes etc, hasta que estéis seguros que habéis
comprendido bien lo que he explicado.
´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´´
// Función loop
void loop() {
// 1º Leer el pin4 y deposita el resultado en “valor”
delay(100) // Para evitar los rebotes
valor = digitalRead(pinint);
// 2º Si la lectura es “1” encender el led que sale del pin 4
if (valor == 1) {
digitalWrite(pinout, HIGH); // enciende el led
}
// 3º Si la lectura es “0” apaga el led que sale del pin 4
if (valor == 0) {
digitalWrite(pinout, LOW); // apaga el led
// Repetir el ciclo
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee pulsador
}// Función loop
void loop() {
// 1º Leer el pin4 y deposita el resultado en “valor”
Delay(100) // Pera evitar rebotes
valor = digitalRead(pinint);
// 2º Si la lectura es “0” encender el led que sale del pin 4
if (valor == 0) {
// enciende el led
// Repetir el ciclo
Repaso
Que se un sensor
Cómo se maneja y un pulsador
Qué es el efecto rebote en pulsadores e interruptores
Como se corriger el efecto rebote
Para que se utiliza un pulsador en a mayoría de los casos
Definir un pin como OUTPUT
Uso de los pines de Ardiuino como sensores del voltaje de un circuito
Montaje Pull Down
Montaje Pull Up
La función condicional “If”
Las diferentes comparaciones que se admiten en la función “IF”
El símbolo = como asignación de un valor a una variable1
El símbolo == como comparación de identidad de dos variables
Es símbolo != como compararon de diferencia de dos variables
Si ha llegado a este punto con razonable aprovechamiento deberá saber resolver estos ejercicios
que le propongo
=================================================================
Puede encontrar resuelto este ejercicio en:
1º Ejercicio de uso de pines digitales de entrada INPUT – Semáforo utilizando “if”
=================================================================
2 – Luces de emergencia
Se desea encender la luz de emergencia en el momento en que falle el circuito principal y se vaya
la luz.
=================================================================
Puede encontrar resuelto este ejercicio en:
2º Ejercicio de uso de pines digitales de entrada INPUT – Luces de emergencia
=================================================================
3 – Temporizador luminoso
Para un descansillo de una escalera se desea que cuando se pulse el botón la luz se mantenga
encendida un minuto, apagándose a continuación.
=================================================================
Puede encontrar resuelto este ejercicio en:
3º Ejercicio de uso de pines digitales de entrada INPUT– Temporizador luminoso
=================================================================
Mientras se abre y se cierra una puerta queremos que permanezcan encendidas unas intermitentes
luces de peligro
=================================================================
Puede encontrar resuelto este ejercicio en:
4º Ejercicio de uso de pines digitales de entrada INPUT– Luces de alarma intermitentes
=================================================================
5 – Linterna multiuso
=================================================================
Puede encontrar resuelto este ejercicio en:
5º Ejercicio de uso de pines digitales de entrada INPUT– Linterna multiuso – 1º Parte
5º Ejercicio de uso de pines digitales de entrada INPUT– Linterna multiuso – 2º Una
posible solución
=================================================================
Estos ejemplos los presentaré resueltos próximamente. Posiblemente mi solución sea diferente a la
suya, porque hay muchas formas de hacer lo mismo. Si la tuya funciona de acuerdo con las
especificaciones que he dado, tu respuesta es válida. No obstante, hay siempre una solución que es
más elegante que las otras, y posiblemente esa sea la mía, porque tengo más experiencia, pero no
es seguro, puede que haya quien encuentre una solución mejor.
¿Que hace que una solución sea elegante? – La economía de medios y la claridad, la solución más
corta, que menos y mas pobres medios utiliza de la tarjeta y la que es mas clara y está mejor
documentada es más elegante. Tenga en cuenta que lo que yo escriba, tu tienes que entenderlo, es
fundamental ser claro, porque programar suele ser labor de equipo y el equipo, tiene que
comunicarse perfectamente.
Con mucho gusto recibiré en mi buzón sus soluciones, mandame el texto completo de tu sketch
(haga copia /pega en su email) y si es posible mandame una filmación del resultado de la prueba.
Aquí tiene mi dirección e mail faocho@[Link].
Por último ¿Se da cuenta de la velocidad con que se aprende Arduino? Creería posible que con
solo tres lecciones y conociendo únicamente seis funciones pudiera hacer una linterna multiuso,
un temporizador y unas luces de emergencia.
Félix Maocho
22/5/2016
.
Utilizar la función “if” para reducir el número de líneas del 2º Ejercicio de uso de pines digitales
de Salida OUPUT – Semáforo
Material necesario
Recordemos un poco aquel ejercicio. Se trataba de Simular un semáforo que regula el paso por el
interior de un túnel. Las especificaciones del ejercicio fueron:
1º.- En un extremos se acaba de poner la luz en verde mientras que en el otro extremo está en
rojo. Así se mantiene 25 segundos.
2º.- Para estimular el paso de los últimos coches, el verde se pone parpadeante cinco veces con
periodos de encendido y apagados de un segundo. o sea esta así 10 segundos más, mientras que
el otro extremo esta en rojo, el resto no cambian
3º.- El semáforo se pone en rojo en un extremo, pero para dar tiempo a que salgan los coches que
estuvieran dentro del túnel el otro extremo también continua en rojo durante otros 10 segundos
Se repite el proceso, pero en este caso el es otro extremo el que se pone en verde
Hardware
Lo que intentamos es aprovechar que la segunda parte del programa hace lo mismo que la primera
pero en la otra boca del túnel, acortar la función “loop” a base de camiiar para los ciclos impares
las asignaciones hechas de los pines. Dicho así resulta algo lioso por lo que prefiero escribir el
programa y comentarlo después. El nuevo programa es como sigue.
Como es el mismo programa conservamos el nombre y tan solo añadimos al código del programa
una a, que nos indicará que es la primera variación del mismo
Puntuación
Observaciones
Cambios en la función “setup”
Fíjense que he cambiado la función “setup” para inicializar los PINs de OUPUT con las variables
que tienen ahora los valores de los pines a inicializar, pina, pinb, pinc y pind no con valores fijos o
parámetros como lo habíamos hecho hasta el [Link] variables, pina, pinb, pinc y pind son
variables por que las inicio con cualquier valor en este caso a “0” pero antes de utilizarlas obtieben
el valor que conviene en ese momento
Observen que la función “digitalWrite” admite que sea una variable y no un parámetro el que
indique cual es el pin que tiene que abrir o cerrar. No es normal utilizar esta posibilidad, pero es
posible y a veces, como en este caso, conveniente.
El truco que he utilizado para llevar la cuenta de si es par o impar el loop que va a efectuarse
consiste en crear una variable, en mi caso “ par_impar” y lo primero que hago cada vez que se
inicia un nuevo loop es sumar 1 a su valor, para que vaya contando vueltas. Como solo quiero
saber si es par o impar, el primer “if” cambia el valor de la variable “par_impar” a “0” cuando ha
alcanzado el valor “2” , por ello la variable que inicialmente tenía el valor “0”, adquirirá el valor
“1” para el primer “loop” , “2” que que se cambia a “0” para el segundo, nuevamente 1 para el
tercero etc.
Sabido si es una vuelta par o impar asigno a las variables que utilizarla la función ““digitalWrite”
los calores de los pines que controlan un extremo o las de los otros extremos así convenga. Esto es
lo que se hace para simular multiprcesos.
Este truco u otro parecido es muy corriente utilizarlo, porque también es es muy corriente en
sketch, hacer cosas diferentes en las sucesivas vueltas del “loop”, cosas como apagar y encender,
avanzar y retroceder, o cosas absolutamente diferentes como pueda ser en un dumper de obras
conducir el dumper y mover un volquete, unas vueltas del “loop” las destinaremos a conducir y
otras a manejar su volquete. Esto es el “truco” para hacer dos cosas diferentes simultáneamente en
un aparato concebido solo para ser monotarea. Realmente cada vez se dedica solo a una cosa, pero
al cambiar de tarea muy rápidamente hace la sensación de efectuar dos a la vez.
Fíjense en el manejo de la función “if” La comparación viene situada entre paréntesis “(…)” y las
funciones que se ejecutarán o no según sea cierta la comparación o no vienen entre corchetes
“{…}”.
Diferencia entre “==” y “=”
También fíjense en la diferencia de uso del doble igual “==”, o identidad, con el uso del simple
igual “=” o transferencia. En el primer caso compara si dos valores son iguales y en el segundo la
variable, adquiere el valor de lo que hay situado a la derecha.
Mi primera intención era haber cambiado el valor de la variable en la propia función “if” que
asigna el valor a los pines si era el if de los pares dar a la variable el valor 1 y si era el de los
impares el 0, pero no podía hacerlo, porque el programa pasa por los dos “if” y si había entrado en
el primer “if” porque tenia el valor 1 y lo cambiaba a 0, pasaba por el segundo porque se lo
encontraba un poco más abajo para ejecutarse si el valor era 0 Por eso de 1 paso a 2 y lo cambio
en l siguiente loop, porque en este ya he asado por ese sitio.
Cambiar el valor se puede hacer y de hecho es corriente hacerlo, si se utiliza las dos funciones
combinadas “if” / “else” porque en ese caso, solamente se ejecuta un sólo grupo de instrucciones
de las dos posibles. A titulo solo de avance, pongo aquí la solución con “if” / “else” para que las
comparen y vean anticipadamente como se utiliza este par de funciones combinadas
Otra cosa que evidentemente se puede es reducir las veces en que se hace lo mismo, aquí el
parpadeo solo es de cinco veces, pero imaginemos que fuera de cinco mil, tiene que haber una
forma de hacer que una misma función se ejecute tantas veces como que ramos esa función es
“for”
La función “for” se utiliza para repetir un bloque de instrucciones entre llaves. Generalmente se
establece un contador que se va incrementando, hasta que deja de cumplirse una condición
específica. No entramos aquí en mayor explicación sobre el tema, sólo indicar que su sintaxis es:
“For” es la función
“nacionalización” es la declaración del contador y suministro del valor inicial. En nuestro caso “int
i=0”
“condición” es la condición que ha de cumplirse para que se repita el bloque de instrucciones. En
nuestro caso “i <= 5; “)
“incremento” es la forma de aumentar el contador. En nuestro caso “i++”
Con ello se podría reducir aun más el sketch que estamos realizando, quedando tal como sigue
Entraré a explicar el uso de “for” en otra ocasión solo quiero de momento que vean como
simplifica la función. Mi intencion es solo anticipar algo el conocimiento de funciones de uso muy
frecuente y simplemente oservar como paraa realizar una tarea hay muchísimos caaminos, capaces
de realizrla, tan solo que algunos son más fáciles de transitar que otros, Indudabemente un Sketch
con menos límeas es en principio más cómoco de escribir, de corregir y poner a punto.
Con los cuatro que he expuesto se consigue exactamente lo nismo sinular un semáforo según las
especificaciones que nos dieron.
2º Ejercicio de uso de pines digitales de entrada INPUT – Luces de emergencia
Para realizar este ejercicio tal como aquí se resuelve solo se necesitan los conocimientos que se
han ido explicando hasta el capítulo dedicado al Uso de los pines digitales como entrada (IN
PUT), que podemos resumir en los siguientes puntos:
Se desea encender la luz de emergencia tan pronto como falle la luz en el circuito principal.
Material necesario
Especificaciones
Se supone que existe un circuito principal, que funciona en corriente alterna a 220 voltios y
adicionalmente, para cuando falla el suministro, existen unas luces que funcionan con la energía
suministrada con unas baterías, que se pondrán en marcha automáticamente cuando se “va la luz”,
o sea, cuando hay un corte en el suministro, por fallo de la central eléctrica o porque ha saltado un
automático porque se ha producido un cortocircuito u otra causa similar.
En nuestro caso, tendremos dos circuitos independientes. uno alimentado por una batería eléctrica
que alimentara a la tarjeta Arduio y las luces de emergencia y otro que parte de un cargador
similar a los que se utilizan en telefonía, enchufado a la red eléctrica de 220 volts. El que vamos a
utilizar, se diferencia de los habituales, que estos sólo producen corriente a un único voltaje,
mientras que el nuestro, girando una pequeña rueda, puede producir corriente a diferentes voltajes.
Creamos con ello el prototipo de un aparato realmente operativo y no una maqueta, pues la
corriente que alimenta a la tarjeta Arduino, puede perfectamente proceder de una batería
convencional de automóvil de 12 voltios, que a su vez podrían ser muy adecuadas para alimentar
varias luces de emergencia. Hasta el momento,hemos unida a un PC a la tarjeta Arduino, mediante
un cable USB. que la alimenta a 5 Voltios, pero esta diseñada para actuar autónomamente, una vez
puesto a punto y cargado el “sketch”, alimentándose por el “jack” situado al lado de la entrada
USB, que admite voltajes entre 6 y 12V pues internamente. hay un regulador de tensión que
reduce el voltaje recibido al voltaje de trabajo de la tarjeta, (5V en la Arduino UNO y en la
mayoría de modelos, o 3.3V (en determinados modelos como el DUE).
Porque toma lo que necesita y el resto lo transforma retiene aunque en parte se trasforma en calor.
Lo cual no es grave, pero no es conveniente, por ello, lo mejor es colocar una resistencia antes de
la entrada de Arduino que reduzca, según la ley de Hom, el voltaje a entre 7 y 9 voltios que es lo
ideal para Arduino, En nuestro caso no va a ser necesario porque ya partiremos de una pila de 9
voltios, con lo que nos ahorramos el trabajo de reducir su voltaje.
Por tanto, necesitaremos una batería de 9 voltios, (o seis baterías de un 1,5 V en un chasis
adecuado), como seven en la imagen, con un cable que las conecte convenientemente a la entrada
Si se fijan tanto el conector del cable como la batería tiene un borne macho y otro hembra, lo que
obliga a conectar la pila al conector, de una forma específica, sin la posibilidad de hacerlo al
contrario. Con ello se asegura que el polo positivo vaya a la entrada correcta de la tarjeta Arduino,
pues como es sabido, en electrónica la dirección de la circulación de la corriente es fija, si la
cambiamos, en la mayoría de los casos no funcionara el aparato e incluso hay muchas
posibilidades de que dañemos la tarjeta. Por esa misma razón, la tarjeta USB entra de un
determinado lado pero si la giramos no conseguimos introducirla.
El circuito eléctrico a vigilar sera uno real de corriente alterna a 220Volts, del que sacamos una
regleta normal con un enchufe donde enchufamos nuestro alimentador variable del que hemos
hablado. Tal como se ven en la imagen
Como ven en el cargador de la imagen
tienen un botón amarillo que se puede girar hasta poner la ranura con el voltaje que nos interese,
habitualmente tiene un rango entre 6 y 12 voltios, nosotros lo pondremos a estos 5 voltios, pues
ese es el voltaje que puede controlar Arduino UNO sin el menor problema. También observaremos
que el “kit”. posee distintas piezas con los “enchufes” más habituales en máquinas digitales.
El problema es que aquí tendremos que enchufar un cable al bus rojo y otro al azul pero ¿Como? –
Muy sencillo, haremos una prueba con el fin de saber que cable suministra voltaje y cual
suministra tierra. Construimos un circuito que sólo tenga una resistencia de 220 Ω y un led. Como
les dije, la dirección de la corriente tiene mucha importancia en electrónica, si al enchufar los
cables que proceden del cargador, luce el led quiere decir que los cables loa hemos conectado
correctamente y que el que contiene 5V es el del lado en el que esta la pata + o cátodo (la pata más
larga)
Si nos hemos confundido, en este caso no pasa nada grave porque la resistencia no tiene polaridad
y el led es un diodo, (que emite luz), y como tal si la corriente viene del lado cambiado,
simplemente no la deja pasar , (actúa a modo de válvula de rueda de bicicleta, deja pasar la
corriente en una sola dirección,)
Hecha la prueba sabremos cual es el cable con 5V y lo conectaremos al bus rojo y el cable con 0V
lo conectamos al bus azul.
Hardware
Descripción general
A la derecha de la tarjeta Arduino, tenemos colocamos las luces de emergencia, un led de color
rojo, (con la correspondiente resistencia de 220 Ω) que se encenderá cuando el pin 2 detecte que
no hay voltaje (cuando el voltaje sea menos de 3,5), por que la red eléctrica cesa de funcionar,
(corte de luz) volviéndose a apagar cuando esta vuelva. Partirá de un pin digital en OUTPUT y el
sketch sera quien mande encenderlo o apagarlo.
A la izquierda tenemos la información del estado de la red eléctrica, Un piloto azul hecho con un
led azul, con su habitual montaje en serie con una resistencia de 220 Ω), nos informa visualmente
si hay corriente, (luce el led), o no la hay (luz apagada) En este circuito estudiaremos el voltaje en
el segmento de entrada con un cable verde que acaba en el pin 2 de la tarjeta Arduino.
El montaje ha ser del tipo PULL UP, es decir pinchamos en un segmento que habitualmente esta a
5V y que solo cambie a 0V cuando se vaya la luz. Es decir el cable que va al Pin INPUT ha de
salir de un punto ANTERIOR a las resistencias que tenga el circuitos.
Como se ve en el esquema el led azul está alimentado por el bus rojo del lado superior y el circuito
finaliza en el bus azul del lado superior. Estos buses que en pruebas se alimentan de los pines 5V y
GND, serian los que trabajando en real se alimentarían del cargador conectado a la red.
Un cable verde parte de un punto que si tiene tensión sera a 5V y acaba en el pin 2 que abriremos
de INPUT,
Por otra parte las luces de emergencia se alimentan del Pin 5 y el circuito acaba en un pin GND de
la tarjeta Arduino, que indistintamente se puede alimentar de el PC mediante un cable USB o de
una batería por el conector situado a la izquierda de la tarjeta.
Software
La alarma funcionará de la siguiente forma si “se va la luz” el Pin2 detectará la caída de tensión y
encenderá las luces de emergencia que seguirán encendidas hasta que vuelva la luz. Por tanto el
sketch hará lo siguiente:
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee el voltaje
}
// Función loop
void loop() {
corriente = digitalRead(pininp); // 1º comprobar el voltaje
if (corriente == 1) { // 2º (5V en bus rojo)
if (encendida == 1) { // 2.1º encendida la luz de emergencia
digitalWrite(pinout, LOW); // 2.11 apagar luces de emergencia
encendida = 0; // 2.12 recordar que apagado la luz de emergencia
} // Cierre del “if” encendida
} // Cierre del “if” corriente
else { // 3º En otro caso, (0V en bus rojo)
if (encendida == 0) { // 3.1º no encendida la luz de emergencia
digitalWrite(pinout, HIGH); // 3.11 encender luces de emergencia
encendida = 1; // 3.12 recordar que encendida la luz de emergencia
} // Cierre del “if” encendida
} // Cierre del else del “if” corriente1
} // cierre de la función loop 4º Repetir el ciclo
Este es un ejemplo bastante completo de la función “if”. Lo primero que quiero resaltar es que el
indentado aun no siendo obligatorio facilita mucho la comprensión de sketch por lo que es muy
recomendable utilizarlo.
Lo habitual es indentar o poner un poco mas a la derecha todas los mandatos que entran entre los
caracteres “{” y “}” du una función un !if” o un “else” o cualquier otro mandato que utilice estos
identificadores de comienzo y final de mandatos controlados por una función o mandato. Con ello
gr´qafica se puede ver de un solo vistazo donde acaba y termina el párrafo controlado por los
caracteres “{” y “}”.
Desgraciadamente con el editor de Word Press que utilizo para redactar estye post,, no lo puedo
realizar sin introducir una serie de caracteres de edicion que harian imposible que Ved hiciera con
el software copiar y pegar, por lo que hwe prescindido de hacerlo. Sin embargo el programa
correctamente editado tendria el aspecto de lo que pongo a continuacion que es una imafen del
testo que compiloen el IDE de Arduino,
“}·
Observe como el indentado facilita enormemente ver los bloques de mandatos que se ejecutan
bajo el control de otras funciones y mandatos. Aconsejo utilizar estos indentados pues simplifican
mucho el trabajo de puesta a punto.
“is” anidados
El primer mandato “if”, (el que explora si no hay corriente), tiene dentro de él, o dicho
técnicamente tiene “anidado”, otro mandato “if” que verifica si no hemos encendido la luz.
Si ambos mandatos se cumplen a la vez, procedemos a ejecutar dos mandatos contenidos entre el
símbolo “{“ y el primer símbolo “}”, o sea encender el led rojo y cambiar el valor de la variable
“encendido” para recordarlo en el siguiente ciclo.
Si la primera condición no se cumple nada de lo que haya entre los “{“ y su correspondiente “}”
se ejecuta, el programa ni entrará a ver si se cumple la segunda, directamente saltara todos los
mandatos controlados por el “if”. Observe lo útil que son los indentados para observar de un golpe
de vista cuales funciones son controladas por un determinado “If”.
Fíjense en otra cosa en la diferencia entre el doble igual IGUALDAD (==) y el simple igual o
ASIGNACION Mientras que en los mandatos “if” se utiliza “==” porque estamos comparando
dos elementos a derecha e izquierda del signo “==”, cuando queremos asignar un valor a una
variable, es decir cambiar el valor que tenía por un nuevo valor utilizamos solo “=” como puede
verse tanto en la linea de lectura del voltaje como en las líneas donde asignamos nuevos valores a
la variable “encendida” para recordarlo en otro ciclo del programa.
“if! / “else”
Inmediatamente acabado de ejecutar este ·primer “if “ encontramos el mandato “else” (en otro
caso), que indica que si se ha ejecutado el primer “if “ se salten estas instrucciones pero si no se
han ejecutado se hagan estas. En nuestro caso si no se “ha ido la luz” hará estas, que simplemente
con otro “if” anidados chequea si se mandó encender las luces de emergencia y como ya hay
corriente las apaga.
Otro punto en el que nos debemos fijar es el “truco” para “recordar” en siguientes “loops” del
programa lo que hicimos en programas anteriores..
Podíamos haber simplificado el programa diciendo simplemente si no hay luz enciende las lucas
de emergencia y si la hay las apagas, pero ello obligaría al sistema a apagar o encender
innecesariamente luces por estar estas ya previamente apagadas o encendidas . Lo cual simplifica
el sketch pero “castiga innecesariamente a la tarjeta que con la ayuda de ese recuerdo, solo actúa
cuando es necesario.
Para que comprueben que lo que digo es cierto. les dejo aquí el programa simplificado
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee el voltaje
}
// Función loop
void loop() {
corriente = digitalRead(pininp); // 1º comprobar el voltaje
if (corriente == 1) { // 2º (5V en bus rojo)
digitalWrite(pinout, LOW); // 2.11 apagar luces de emergencia
} // Cierre del “if” corriente
else { // 3º En otro caso, (0V en bus rojo)
digitalWrite(pinout, HIGH); // 3.11 encender luces de emergencia
} // Cierre del else del “if” corriente
} // cierre de la función loop 4º Repetir el ciclo
Les dejo igualmente la imagen real del Sketch escrito en el escritorio IDE para que observen
nuevamente el indentado
,
Observen que el programa es mucho más corto y no utiliza la variable “encendido”. En cambio en
cada “loop· o obliga a encender o apagar las luces según haya o no corriente aunque estas estén ya
encendidas o apagadas, y si bien no tiene consecuencias es obligar a trabajar innecesariamente un
conmutador interno.
Generalmente consideramos que sis dos programas hacen lo mismo, el más corto es el más
perfecto y el que damos mejor puntuación pues sera mucho mas sencillo de poner a punto y
mantener cuandi hqya que modificarlo o arreglarlo, Sin embargo como en todo hay excepciones y
uno de ellas es no hacer trabajar inutlmente a mustros delicados circuitos electrónicos.
Puntuación
Como de costumbre procedo a puntuar este software. No me cansaré de repetir que una misma
forma de actuar de la tarjeta Arduino se puede conseguir de muchas formas y que de todas ellas la
mejor y por tanto la que yo le concedo la más alta puntuación, es aquella que es mas sencilla, mas
corta y precisa de menos medios. En este caso pese a tener menos lineas de texto la segunda forma
considero más acertada la primera por ahorrar uso de Hardware,
A mi modo de ver el primer sketch es de buena calidad. No me atrevo a puntuarlo muy alto, pues
siempre habrá alguien que lo realice con menos lineas, como yo lo he hecho, y además
conservando la calidad del proceso, Le pongo de nota un notable, pero elijo un 7 en vez de un 8
porque podía sin menoscabo haber ahorrado medios utilizando una pin menos valioso.
Habrá observado que al lado de los números que indican el pin digital que se trata algunos tiene un
misterioso gusanito tal como este “~“ que habrán visto utilizar para expresar que dos cantidades
son más o menos iguales. En este caso no tiene ese significado sino que ese pin tiene la posibilidad
de emitir la energía en forma de ondas, algo que estudiaremos con detalle pronto cuando veamos
el uso de pines analógicos. Bástenos de momento saber que algunos pines digitales en concreto
en la tarjeta UNO tiene capacidades que otros no tienen, En concreto, los pines 3, 5 6, 9, 10 y
11 pueden actuar de salida emitiendo ondas o PWM iniciales de Pulse Width Modulation
(pulsaciones con modulación) y los pines 0 y 1 que tiene la capacidad de comunicarse, es decir
emitir y recibir información asíncrona con otro aparatos que puedan recibir este tipo de
comunicaciones, algo que también enseñaremos más adelante.
Cargado cualquiera de los sketch en la tarjeta, si no funciona el prototipo es que tiene algún error
en el montaje de los cables o componentes o ha conectado a algún pin erróneo, pues el software le
he probado y funciona a la perfección.
Desconecte el cabe que va a pin 5V, Observará que ocurren las siguientes cosas
o El pin azul deja de lucir pues se ha “caído la luz”
o El pin rojo (o sea las luces de emergencia), se enciende automáticamente,
Estado así es decir con el pin 5v desconectado y las luces de emergencia conectadas apriete el
botón rojo de RESET.
o Observara que después de parpadear un momento los leds de la tarjeta (señal de que
está rearrancando), vuelve a encenderse las luces de emergencia, porque la tarjeta ha
detectado que no funcionan las luces de la red, (lus azul apagada)
Ahora vuelva a colocar el cable rojo en el pin 5V, es decir vuelve a haber electricidad en el bus
rojo y ocurre que vuelve todo como al principio, se enciende el led azul y se apaga el rojo.
Apriete nuevamente el botón rojo de RESET.
o Veremos parpadear los leds de la tarjeta, pero aparentemente no pasa nada, sigue
encendida la luz azul y apagada la luz rojas, porque la tarjeta a rearancar encuentra que
todo está normal.
Por último saque el cable azul que acaba en pin GRD o tierra y observe que se apaga le led azul
pero NO SE ENCIENDEN las luces de emergencia.
Porque un pin en INPUT funciona como un voltímetro dice si un segmente de cable tiene un
voltaje de 5V o de 0V pero no mide realmente si PASA corriente. Al sacar el cable del PIN 5V se
corta la corriente pero TAMBIEN el bus rojo, pasa de estar a 5V o estar 0V y eso lo detecta el
voltímetro en el que hemos trasformado nuestro Pin 2
Pro al desconectar el Pin GRD, dejamos abierto el circuito que permitía dar luz al led Azul pero
pese a ello el bus rojo sigue unido a el pin 5V y por tanto hasta donde se corta el circuito está a 5V
y nuestro voltímetro no nota la diferencia, por lo que no manda encender las luces rojas.
¿Como solucionarlo ?
Si quisiéramos controlar este bus habríamos de poner por ejemplo un cable amarillo que fuera
desde el bus azul a por el ejemplo el pin 3 e investigar que es lo que pasa en este segundo punto
del circuitos
Les dejo el esquema y el programa pero ya no les doy mas explicaciones porque todo es igual pero
al revés y deben poder entenderlo sin problema.
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp1, INPUT); // Pin abierto como INPUT, lee el voltaje bus rojo
pinMode(pininp2, INPUT); // Pin abierto como INPUT, lee el voltaje bus azul
}
// Función loop
void loop() {
//* Primera parte Comprobar el voltaje del bus rojo
corriente1 = digitalRead(pininp1); // 1.1º comprobar el voltaje
if (corriente1 == 1) { // 1,2º hay 5V en bus rojo
if (encendida1 == 1) { // 1.2.1º encendida la luz de emergencia
digitalWrite(pinout, LOW); // 1.2.11 apagar luces de emergencia
encendida1 = 0; // 1.2.12 recordar que apagado la luz de emergencia
} // Cierre del “if” encendida1
} // Cierre del “if” corriente1
else { // 1,3º En otro caso, (0V en bus rojo)
if (encendida1 == 0) { // 1,3.1º no encendida la luz de emergencia
digitalWrite(pinout, HIGH); // 1.3.11 encender luces de emergencia
encendida1 = 1; // 1.3.12 recordar que encendida la luz de emergencia
} // Cierre del “if” encendida1
} // Cierre del else del “if” corriente1
//* Segunda parte Comprobar el voltaje del bus rojo
corriente2 = digitalRead(pininp2); // 2.1º comprobar el voltaje
if (corriente2 == 0) { // 2.2º 0V en bus azul
if (encendida2 == 1) { // 2.2.1º encendida la luz de emergencia
digitalWrite(pinout, LOW); // 2.2.11 apagar luces de emergencia
encendida2 = 0; // 2.2.12 recordar que apagado la luz de emergencia
} // Cierre del “if” encendida
} // Cierre del “if” corriente
else { // 3º En otro caso, (5V en bus azul)
if (encendida2 == 0) { // 3.1º no encendida la luz de emergencia
digitalWrite(pinout, HIGH); // 3.11 encender luces de emergencia
encendida2 = 1; // 3.12 recordar que encendida la luz de emergencia
} // Cierre del “if” encendida2
} // Cierre del else del “if” corriente2
} // cierre de la función loop 4º Repetir el ciclo
Como ven he abienrto otro pin en INPUT y he duplicado las variables de corriente y encendido
para saber si el problema lo tenía en el bus rojo o en el azul, el resto es todo prácticamente igual.
Vuelva a sacar los cables que van al V5 y a GRD y apriete RESET para ver si ahora va todo bien,
Pues no estoy seguro hasta que lo pruebe. Por un lado me hace el efecto que si se va la corriente
alterna falla tanto la una fase como la otra, Ppero por otra parte, me ha entrado la duda de como
funcionan los cargadores de las pilas, es posible que solo se queden con una de las fases de la luz,
puesto que tienen que eliminar la otra para producir corriente continua, pero además la luz alterna
va en ondas, por lo que el voltaje va fluctuando de 120V a cero por una fase y la otra.
Es posible , aun no lo se, si esa media onda que deja pasar hace que el voltaje del bus rojo varíe
entre 0 y 5V sesenta veces como la luz eléctrica, en cuyo caso este aparato utilizado como fuente
sin otro paso intermedio que iguale el voltaje no nos valga, Cuando haga el experimento se lo
contaré. Pero es posible que rectificando la corriente , es decir poniéndola sólocomo venida de una
fase, el voltaje se mantenfa inestable y el sensor que al fin y al cabo solo es un voltímetro se
vuelva un poco errático. Soño probando lo solucionaremos, pero eso lo haré otro dia.
Prácticas
Ejercitarse en utilizar otros pines y en hacer los “if”/”else” al contrario, por ejemplo preguntando
si la luz de emergencia esta encendida, y comprobar en ese caso que el pin2 detecta 5V y el tres
0V en cuyo caso hay que apagar la luz de emergencia porque todo es normal, la variable
encendida a 0, o en caso contrario no e hacer nada, y viceversa, si la luz esta apagada y alguno de
los penes en INPUT denotan algo raro encenderla y cambiar la variable encendida a 0
Repaso
Objetivo
Construir un aparato que regule la duracion de encendido de las luces de una escalera.
Para realizar este ejercicio tal como aquí se resuelve solo se necesitan los conocimientos que se
han ido explicando hasta el capítulo dedicado al Uso de los pines digitales como entrada (IN
PUT), que podemos resumir en los siguientes puntos:
Enuciado
Para un descansillo de una escalera se desea que cuando se pulse el botón la luz se mantenga
encendida un minuto, apagándose a continuación.
Material necesario
Objetivos
Se supone que hay una escalera que une dos plantas iluminada con leds en cada rellano que
normalmente se mantienen apagados, cuando alguien pulsa uno de los botones que hay en cada
planta, se encienden los led que iluminan la escalera por un tiempo, apagándose a continuación.
Tenemos que crear dos circuitos digitales. Uno alimentado desde un pin digital alimenta dos luces,
que se suponen que están en pisos diferentes. Otro es el que detecta cuando un botón se ha
oprimido. Caben dos soluciones poner los botones con montajes PULL DOWN o montaje PULL
UP
Hardware
Utilizaremos los buses rojo y azul de uno de los lados. para alimentar las luces. por tanto el rojo se
unirá a un pin digital en OUPUT, el bus azul a un pin de tierra (GRD) , y el otro par de buses los
utilizaremos para llevar la la energía a una de las patas del de los pulsadores. mientras que de la
otra pata es la que llegaremos a tierra.
Utilizaremos para los pulsadores un montaje PULL DOWN, (tirar abajo. o derribar), quiere decir
que donde extraemos el cable que irá al pin a digital abierto como INPUT. el voltaje está
habitualmente a 0 voltios, y al apretar el pulsador pasa a 5V. En un montaje de este tipo , el orden
de los elementos que interviene en el circuito PULL DOWN es el siguiente:
Descripción general
En la parte superior el pin 12 y el pin GRD están conectados con los buses superiores que
alimentan a dos Led montados en batería, a los que como es costumbre se une en serie una
resistencia de 220Ω. Estos Led solo lucirán cuando el sketch de salida electricidad por el pin 12.
En la parte inferior, los pines 5V y GRD están conectados a los dos buses inferiores. El bus rojo
alimenta a cada una de las patas del pulsador, (push button). mientras que otra pata se une a
una resistencia que va a ser común para todos los pulsadores y que tendrá un valor más elevado
de lo habitual, pues su objetivo no es solo evitar un cortocircuito. sino que deje pasar una mínima
cantidad de energía, porque no tiene sentido el que pase más, si su objetivo es solo permitir que un
segmento que va desde el pulsador a la resistencia, cambie cuando se oprime el pulsador, de estar
a 0V, (por estar unido a tierra, a estar a 5V por quedar unido la carga. Pondremos por ello una
resistencia de 1000Ω, suficientemente grande para evitar por si misma que se produzcan
cortocircuitos al unir el pin 5V al pin GRD sin ningún componente que consuma la energía que
sale por 5V
Observe que los componentes quedan en la configuración típica del PULL DOWN, entrada de 5v,
pulsador, cable que va a el in en INPUT, resistencia, salida a 0v,
De acuerdo con la codificación que se utiliza para las resistencias, la resistencia de 1000Ω lucirá
las siguientes bandas de color, marrón , negro, rojo. Para saber de cuantos homios, (Ω) tiene una
resistencia, hay que conocer el código de colores con el que se marcan. Los códigos de colores son
como siguen:
Por último un cable verde une el segmento que cambia de voltaje según se oprime el pulsador, con
el pin 2, que abriremos de INPUT.
Software
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee el voltaje
}
// Función loop
void loop() {
delay(100) // Tiempo de retardo para evitar los “rebotes” del pulsador
corriente = digitalRead(pininp); // 1º comprobar el voltaje
if (corriente == 1) { // 2º (han oprimido un pulsador)
digitalWrite(pinout, HIGH); // 2.1 Encender las luces durante un tiempo
delay (tiempo); // mantenerla encendida tiempo
digitalWrite(pinout, LOW); // 2.2 apagar las luces
} // Cierre del “if” encendida
} // cierre de la función loop 3º Repetir el ciclo
Este prototipo se pueden fácilmente escalar a tantos pisos como e queramos, tanto en lo referente a
los los led, como al número de interruptores, sin mas limitación que las caídas de tensión que se
produzcan por la longitud de los cables y teniendo en cuenta que el pin 12 sólo suministra 40
miliamperios, lo que no da a energía para encender muchos leds aun eliminando las resistencias.
Primoroso repartir mas leds utilizando mas pines de salida puesto que cada uno proporciona la
misma intensidad de corriente, hasta llegar al máximo de energía que puede suministrar una tarjeta
Arduino. A partir de ahí habría que buscar medios indirectos como un relé para alimentar las
luces.
Tiempo de retardo
Con el fin de evitar los problemas de la fluctuación del voltaje cuando se corta o da la corriente,
introducimos preventivamente mediante un “delay” un tiempo de retardo de 100 milsegundos.
Indentar un sketch
Cuando se escribe un sketch, lo habitual es indentar o poner un poco mas a la derecha todas los
mandatos que entran entre los caracteres “{” y “}” correspondientes a función, como la función
“loop”, o algunos mandatos, (come en nuestro caso los mandatos “if” y “else”). La razón para ello
es poder identificar de un vistazo, el comienzo y final de estos mandatos y saber cuales mandatos
están condicionados por ellos.. Gráficamente se puede ver de un solo vistazo donde acaba y
termina el párrafo controlado por los caracteres “{” y “}”.
Desgraciadamente, el editor de Word Press, que utilizo para redactar este post, llena de caracteres
ocultos el indentado, o lo que afloraría en el momento que se lleve con copy/paste el software del
ejercicio propuesto a su editor IDE. Por ello he renunciado a hacer este indentado en estos post.
Pero animo a introducir los indentados en su editor de los sketch de Arduino, por la claridad que
dan a los Sketch, que compensan largamente el trabajo de introducirlos.
Lo que si le puedo poner es una imagen de como que da el programa correctamente editado en el
entorno IDE de Arduino:
Un pequeño problema de este programa
Observe lo que ocurre si no se ha apretado ningún botón, el “loop”, no hace nada mas que
comprobar el voltaje. Por tanto pasará el “loop” muy rápidamente una y otra vez y obtendremos
una serie de consultas seguidas del voltaje en el pin 2 que no tiene mucho sentido,
Solo a modo de ejemplo, voy a resolver el ejemplo inicial, pero en este caso con un montaje PULL
UP. Observarán que la tarjeta funciona en todo exactamente igual, la única diferencia, es que
donde antes hacia repetidamente una lectura de un voltaje, que habitualmente esta bajo, (0V),
ahora hace la lectura repetida de un voltaje que habitualmente está alto (5V), con todo lo que
supone de mayor carga para la tarjeta. Esto no pone en peligro la tarjeta, pero naturalmente no la
favorece. Por tanto, si es absolutamente igual hacerlo de una forma o de otra, porque no se tienen
ventajas especiales hacerlo de cualquiera de las dos formas, deberemos en principio preferir la
solución PULL DOWN.
Este es el caso, el montaje PULL DOWN no tiene ninguna ventaja, porque no tratamos de
controlar las posibles caídas de tensión, (en este caso si se “va la luz” ni funcionarán los timbres ni
se pueden encender las luces, porque todo se alimentan del mismo punto), por ello es menos
adecuado aunque se puede realizar sin riesgo de estropear la tarjeta, aunque si la sometemos a
mayor desgaste
Como dijimos en el post, Uso de los pines digitales como entrada (INPUT), el montaje PULL
UP se caracteriza porque los elementos que participan en el montaje se colocan en el orden
inverso al PULLDOWN
Si se lijan es exactamente igual que la solución anterior pero cambiando el enlace de los buses,
poniendo el bus rojo a tierra y el azul a 5V, nosotros hemos preferido cambiar las conexiones de
los pulsadores y la resistencia grande. Observen con detalle las diferencias en el diagrama de
conexiones.
Como ven solamente hemos hecho tres cambio mínimos. El primero es que la resistencia esta
conectada directamente al bus rojo que porta 5V.; los otros cambios es que los pulsadores se unen
ahora por una pata al bus azul por lo que por esa parata están directamente unidos a tierra.
Como consecuencia, mientras no este cerrado el circuito, los cables conectados a la otra pata de la
resistencia y al pulsador estarán habitualmente a 5V, pero tan pronto como se cierre el circuito, se
pondrán a 0V, por quedar directamente unidos a tierra (GRD) y eso, es lo que detectará el cable
verde, que va a parar al pin 2, que cada vez que se aprieta el botón el voltaje del cable pasa de 5V
a OV
Software
El software sera exactamente lo mismo. solo que aquí lo que detecta que se ha apretado el
pulsador es que la variable “corriente” toma el valor cero, al hacer la lectura del voltaje. ESTE ES
EL UNICO CAMBIO, como resalto en el Sketch que queda así :
// Función setup
void setup() {
pinMode(pinout, OUTPUT); // Pin abierto como OUTPUT enciende led
pinMode(pininp, INPUT); // Pin abierto como INPUT, lee el voltaje
}
// Función loop
void loop() {
delay(100) // Tiempo de retardo para evitar los “rebotes” del pulsador
corriente = digitalRead(pininp); // 1º comprobar el voltaje
// ******* ESTE ES EL ÜNICO CAMBIO UN 0 POR UN ! *******
if (corriente == 0) { // 2º (han oprimido un pulsador)
// ********************************************************
digitalWrite(pinout, HIGH); // 2.1 Encender las luces durante un tiempo
delay (tiempo ); // mantenerla encendida tiempo
digitalWrite(pinout, LOW); // 2.2 apagar las luces
} // Cierre del “if” encendida
} // cierre de la función loop 3º Repetir el ciclo
Por supuesto este sketch padece de los mismos defectos que el anterior una repetida e innecesaria
consulta del voltaje en el caso de que nadie apriete el botón aquí agravado puesto que lo va a leer
continuamente es que está a 5V
Podíamos tomar alguna medida para evitar tal número de lecturas inútiles como puede ser frenar la
velocidad de ejecución del “loop” poniendo por ejemplo al principio un “delay” que haga que por
fuerza tarde más el tiempo necesario en hacer el “loop”. Sin embargo el “delay” es un arma de
dos filos, porque mientras se ejecuta el “delay” la ejecución del programa no avanza, el programa
aparece como “anestesiado”.
Por tanto, si cuando está ejecutando un “delay”· alguien aprietan y un botón y lo suelta antes de
que finalice, la máquina no se enterará de que han apretado el botón, porque para cuando vaya a
leer el voltaje, este se habrá puesto nuevamente a cero.
Cuando se utilice un “delay” hay que tener en cuenta que la “parada” del programa en ese
punto no suponga problemas. Por ejemplo, en este programa, si el vecino del primero aprieta el
botón 1 y enciende las luces de la escalara, mientras estén encendidas, no vale para nada apretar el
botón 2 porque el sistema no se entera.
En este caso concreto esto no importa, porque el vecino del segundo piso, que salga cuando aun
está encendida la luz, o da al botón y no vale para nada, o no da al botón y aprovecha la luz
encendida por el anterior. Lo que pasará, es que en este caso, el tiempo que se encuentre
encendida la luz el vecino del segundo es variable, del máximo, si sale inmediatamente que se
encendió la luz, o solo unos segundos si ya casi han pasado el tiempo de encendido previsto. En
este caso sólo tendrá que dar la luz cuando esta se apague, (si lo hace antes no valdrá para nada) y
se volverá a encender la luz, Esto es exactamente lo que ocurre en la mayoría de las escaleras y la
gente no protesta. .
Supongamos que por esas normas que se van imponiendo de ahorro de luz, el sistema de luces de
la escalera que tenemos enciende solo la luz del descansillo donde está el botón oprimido. Es decir
que vemos independizado el sistema de modo que el botón 1 1no sólo enciende la luz 1 y el
botón 2 solo enciende el la luz 2.
En este caso tendríamos que buscar otra solución, pues imaginemos que sale el vecino del primero
y enciende el botón 1, la luz 1 se enciende por el tiempo marcado, pero no así la luz 2. Ahora sale
el vecino del segundo, encuentra la luz apagada y aprieta el botón 2, pero la luz 2 no se enciende
porque el programa esta “anestesiado” en un “delay” durante un ·tiempo.
Esto no es aceptable. Y hay que buscar una solución: Para que observen los riesgos del “delay”
les dejo tanto el esquema de conexiones como un programa que funciona (mal) como indicamos,
para que comprueben la veracidad de lo que digo y busquen una solución.
Solución errónea
Cambiamos las especificaciones por la de encender independiente mente los led en d función del
botón que lo solicita.
Con las medidas de ahorro energético actuales, es corriente que al pulsar el botón de la luz de la
escalera se enciendan únicamente las luces de ese descansillo y no la totalidad de las luces de la
escalera. El sistema exige que identifiquemos cual ha sido el botón pulsado y en función de él
encender las luces que corresponda.
Para ello podremos identificar qué botón se ha pulsado y encender sólo la luz correspondiente.
Haciendo que cada pulsador se controle por diferente pin. De esa forma podríamos identificar
individualmente los pulsadores y mandar encender l en cada caso las luces correspondientes.
Muestro a continuación, una posible solución a como hacerlo. Nuevamente hemos realizado un
montaje tipo PULL DOWN por ser el más lógico en este caso, pero igualmente podríamos haber
optado por un PULL UP.
Nuevamente recordamos que el montaje PULL DOWN se caracteriza porque el orden de los
elementos que forman el circuito pulsador son :
Mientras que en el montaje PULL UP , los componentes están situados al contrario o sea:
Como pueden observar en el este caso hemos optado por el montaje PULL DOWN para cada uno
de los dos pulsadores pero hubiéramos podido optar por el montaje contrario en uno o los dos
pulsadores. Lo importante es que recordemos que si optamos por un montaje PULL DOWN lo
que leerá la Tarjeta Arduino habitualmente es 0 voltios y sólo cuando este oprimir do el pulsador
pasar a a 5 voltios, por tanto el que la variable que recoge la lectura del voltaje, (en nuestro caso
“corriente” adquiera el valor “1” es señal que han pulsado el botón. Si el montaje fuese PULL UP
sería al revés. Igualmente se han independizado los circuitos, tanto para alimentar a los led ahora
cada uno depende de unpin digital en OUPUT.
.
Descripción
Como se ve, en este caso se ha independizado la alimentación de los leds, hecha actualmente
desde los pin 12 y 13 como los circuitos de cada “push button” con lo que damos la oportunidad
de comprobar por separado el estado de cada botón y en función de ello encender las luces
correspondientes. El botón de la izquierda encenderá el pin 13 y el de la derecha el 13
Software
Podríamos en principio pensar que basta ver el estado de cada pulsador y encender o no las luces
correspondientes. Por tanto en principio valdría un sketch como el que indico:
// Función setup
void setup() {
pinMode(pinout1, OUTPUT); // enciende led1
pinMode(pinout2, OUTPUT); // enciende led2
pinMode(pininp1, INPUT); // botón1
pinMode(pininp2, INPUT); // botón2
}
// Función loop
void loop() {
delay(100) // Tiempo de retardo para evitar los “rebotes” del pulsador
corriente1 = digitalRead(pininp1); // 1º comprobar boton1
if (corriente1 == 1) { // 2º oprimido un pulsador1
digitalWrite(pinout1, HIGH); // 2.1 luz1
delay (tiempo ); // mantenerla encendida
digitalWrite(pinout1, LOW); // 2.2 apagar luz1
} // Cierre del “if” encendida1
delay(100) // Tiempo de retardo para evitar los “rebotes” del pulsador
corriente2 = digitalRead(pininp2); // 3º comprobar boton2
if (corriente2 == 1) { // 4º oprimido un pulsador21
digitalWrite(pinout2, HIGH); // 4.1 luz2
dlay (tiempo ); // mantenerla encendida
digitalWrite(pinout2, LOW); // 2.2 apagar luz2
} // Cierre del “if” encendida2
} // cierre de la función loop 5º Repetir el ciclo
Aparentemente este programa tiene que funcionar bien, pues no es mas que duplicar sketch 6.31
de antes, que funcionaba perfectamente. Solo que hay una diferencia muy sutil que quizá no se
han dado cuenta. Antes se encendían TODAS las luces y nadie va a dar a un botón mientras las
luces estén encendidas, el mayor problema que podíamos tener, es que mientras están encendidas
TODAS las luces alguien salga en otro piso y de pronto TODAS las luces se apagan y hasta que
nuevamente se aprieta un botón. Ocurre que si se aprieta un SEGUNDO botón mientras están
encendidas TODAS las luces, es sistema no se entera y las luces se apagan pasados los segundos
determinados desde que se encendió la PRIMERA luz, pero esto pasa desapercibido.
Sin embargo ahora cuando se pulsa un botón se enciende UNA luz, la que corresponde a ese piso.
Si en otro piso sale alguien, su luz estará apagada, pero cuando apriete el botón es sistema no se
entera, porque esta “anestesiado” en un largo “delay”, y por tanto DEJA A OSCURAS al la
segunda petición de encender la luz, lo cual es inadmisible.
Haga la prueba, compile este sketch monta los componentes y pruebe a encender el segundo led
cuando está luciendo el primer led o viceversa. ¿Que podemos jacer?
Desde luego hay solución y la veremos en otros ejemplos pero este ejemplo se va haciendo muy
largo así que la solución la daré en otro sitio, Sólo quiero que piensen en el problema y busquen
soluciones al mismo.
Puntuación
Como de costumbre procedo a puntuar este software. No me cansaré de repetir que una misma
forma de actuar de la tarjeta Arduino se puede conseguir de muchas formas y que de todas ellas la
mejor y por tanto la que yo le concedo la más alta puntuación, es aquella que es mas sencilla, mas
corta y precisa de menos medios.
A mi modo de ver el primer sketch es de buena calidad, pero tiene los dos defectos indicados,
lecturas innecesarias y un delay que hace que el programa no tenga un funcionamiento perfecto
que consistiría en detectar las pulsaciones y mantener las luces encendidas un rato desde la
ÚLTIMA pulsación
Si hay alguien que pueda soslayar ambos defectos con pocas lineas mas de programa, habrá
conseguido mejorarlo. Dando vueltas quizá se me ocurriera a mi alguna basada en conseguir llevar
algún tipo de contador que se ponga a cero cada vez que se pulsa un botón o algo parecido
Reseco de las lecturas sucesivas, se fácil distanciarlas algo, pero al fin y al cabo la única forma de
saber si han apretado el botón es leer el estado de el pin en INPUT, por tanto nos pongamos como
nos pongamos tendremos que hacer muchas lecturas, con nuestros actuales conocimientos . (les
anticipo que hay mejor solución como es el uso de interrupciones, pero aun no hemos llegado a
esa clase)
Cargado cualquiera de los sketch en la tarjeta, si no funciona el prototipo es que tiene algún error
en el montaje de los cables o componentes o ha conectado a algún pin erróneo, pues el software le
he probado y funciona a la perfección.
En el primer ejercicio
Oprima uno de los botones, espere 10 seg. Y oprima el segundo, vera que las luces se apagan a los
10 segundos o sea pasados los 20 segundos del primero.
En el tercer ejercicio puede observar los problemas del “delay” apite consecutivamente los dos
botones, solamente se encenderá el led correspondiente al primer pulsador.
Prácticas
Buscar solución al caso planteado en el tercer ejercicio. La hay a la altura de sus conocimientos,
solo es cuestión de cometer errores y seguir probando (la única forma de aprender es pegarse con
los ejercicios)
Repaso
Objetivo
Construir un aparato que encienda una luz intermitente cundo se h abra la puerta.
Mientras se abre y se cierra una puerta queremos que permanezcan encendidas unas intermitentes
luces de peligro
Material necesario
Objetivos
Especificaciones
Tenemos una puerta, por ejemplo de un un garaje y queremos que desde el momento que se
comienza a abrir la puerta hasta el momento que se cierre totalmente, luzcan unas luces
intermitentes que a modo de precaución, avisando que la puerta se esta abriendo, por lo que hay
que tener precaución en su proximidad.
Para ello instalaremos un sensor en la puerta que en cuanto se inicie la apertura de la puerta lo
informa a la Tarjeta Arduino por un pin abierto como INPUT y que cuando esto ocurra, por otro
pin abierto como OUTPUT se alimente intermitemente un led que se mantendrá en ese estado, en
tanto el sensor de la puerta informe que la puerta no se ha cerrado totalmente.
Un sensor de este tipo es muy fácil de montar, basta poner un extremo de un cable unido a la
puerta que contacte con otro extremo en el marco de la puerta, de modo que cuando esta comience
a abrirse se separen ambos extremos y el circuito quede roto. Una mejora de este sistema es
colocar una pletina al borde la puerta que al estar esta cerrada oprime un botón situado en el marco
de la puerta de modo que cuando la puerta se abra deje de oprimirlo. Consideramos este sistema
más prácticos porque ello libera poner cables en la puerta y centra toda la instalación en el marco.
El modelo que enseñamos en la imagn del comienzo, es solo una variacion mas sofist6icada de
este sistema. En este caso el elemento inferior atornillada en el borde la puerta y que se desplaza
con la puerta es un iman. Este imán que atrae para abajo de una pletina flexible que hay en la parte
superior, atornillada al marco de la puerta. Cuando la puerta se abre, el imán se aleja con la puerta
y la pletina vuelve a su posición de reposo que es cerrando un circuito eléctrico. Esta es una
solución real, económica y muy habitual, de sensores que detectan si una puerta está abierta o
cerrada. Por ejemplo, en esta pagina anuncian un modelo de este tipo con un coste de 11 €
La ventaja del uso en este caso de este tipo de interruptores NC, es que nos permite hacer un
montaje PULL DOWN es decir montajes en el que la situación habitual (puerta cerrada), oprime
constantemente el botón por lo que mantiene el circuito eléctrico abierto (0 voltios) y solo cuando
se abre la puerta (dejamos de apretar el botón) el voltaje se eleva (5V).
Igualmente lo podríamos hacer con un interruptor NO que al estar la puerta cerrada, mantuviera el
botón oprimido y por tanto el circuito cerrado (5 voltios) pasando a cortar el circuito (0 v) cuando
la puerta se abriera. La diferencia es que en este caso tendríamos que montar un circuito PULL
UP que detectara la caída de tensión.
La ventaja del PULL DOWN es que no precisa consumo de corriente cuando la puerta está
cerrada, que es lo que se considera más probable en este caso, aparte evitar el mayor desgaste de la
Tarjeta Arduino, pues lo que mide habitualmente el pin en INPUT es 0v y además tenemos un
consumo mayor de energía eléctrica pues habitualmente no fluirá la corriente.
Pero igual podemos poner, un simple interruptor de los que tiene una clavija con dos estados, una
posición abierta y otra cerrada, que se ajusta a un esquema como el que ponemos, Si al abrir la
puerta se pusiera en ON y al cerrarla en OFF el proceso sería exactamente lo mismo que en el caso
de tener un Pushbutton tipo NO que en estado de reposo con la puerta, mantendría “pisado” el
botón y con ello abierto el circuito.
O si fuera al revés que el interruptor se pusiera en ON al abrir la puerta sería similar al caso con el
Push Button tipo NC. Como pueden observar un mismo problema se puede resolver por distintos
medios tanto de hardware como de software.
Inicialmente mostramos una la solución teniendo un sistema de tipo NO pues es el más adecuado
ya que permite nontaje PULL DOWN (Igual daria tener un interruptor que se pusiera en ON
cuando se abriera la puerta)
Hardware
El esquema es el habitual, dos circuitos uno alimentado por el pin 12 que contiene la habitual
resistencia de 220 Ω y un led y otro circuito que contiene el sensor de la puerta, en este caso un
push button del tipo NO (normalmente abierto), es decir que cuando se pulsa corta el paso de la
electricidad y cuando queda libre, (Se abre la puerta), cierra el circuito y el voltaje sube a 5V-
Como vamos a hacer un montaje PULL DOWN el orden de los elementos será el siguiente:
Hardware
No voy a entrar en detalles porque el circuito es básicamente igual al que hemos visto con
anterioridad donde se pone una resistencia de 1000 Ω suficientes para frenar el cortocircuito que
se produciría en el circuito del botón si no la estuviera, pues uniríamos un pin a 5v con tierra sin
tener ninguna resistencia por medio.
al ser el interruptor NO el cable verde que lleva al pin en INPUT presentarçia en “reposo” 5
voltios ( puerta abierta) mientras que al se oprimido el pushbutton recibirá 0v . De haber puesto un
interruptor , debería estas cerrado el circuito cuando se simula que la puerta esta cerrada y abrirse
cuando se simula que se abre
<por ello al hacer las pruebas nuestro dedo tendrá que simular que la puerta está cerrada
oprimiendo de forma continua el botón con lo que se cortará el paso de corriente.
Software
// Función loop
void loop() {
delay (100) ; // Retardo para evitar los problemas de “rebote” de los interruptores
corriente = digitalRead(pininp); // 1º comprobar el voltaje
if (corriente == 1) { // 2º (han abierto la puerta o liberado el pulsador)
digitalWrite(pinout, HIGH); // 2.1 Encender las luces durante un tiempo
delay (tiempo); // parada durante un tiempo
digitalWrite(pinout, LOW); // 2.2 apagar las luces
delay (tiempo); // parada durante un tiempo
} // Cierre del “if” encendida
} // cierre de la función loop 3º Repetir el ciclo
Igualmente si el sensor fuera de tal forma que permite la corriente cuando está cerrada la puerta y
la corta cuando se abre, (o ponemos un interruptor que esta encendido cuando la puerta esta
cerrada y se apaga cuando se abre), podremos igualmente hacer trabajar la Tarjeta Arduino sólo
que en este caso tendremos que hacer un montaje PULL UP es decir que lo que interviene en el
circuito interruptor se ordena en sentido contrario:
Hardware
Como ven las diferencias con el anterior están en la forma de alimentar el sensor, en nuestro caso
un pulsador y la situacion de la resistencia de 1000 Ω.
Software
Tampoco el software tiene muchos cambios, la única es que aquí la accion se realiza cuando el
PIN2 detecta que el voltaje ha pasado de los habituales 5V a 0V
Si observan con detalle el único cambio es que ahora lanzamos la intermitencia cuando el Pin 2
detecta un O, ‘que no aprietan el botón de tipo NC) Todo lo demás es exactamente igual
aparentemente, porque en este segundo caso hay dos pequeños inconvenietes, si lo habitual es que
la puerta este cerrada, lo habitual sera leer que hay 5 voltios en la linea algo más duro para la
tarjeta que leer que el cable está a cero voltios, pero es que ademas mientras que la puerta está
cerrada (que suponemos que es lo que ocurre en la mayoría del tiempo), el circuito del pulsador
esta cerrado es GASTANDO ENERGIA mientras que en el caso anterior estaba cerrado es decir
no gastaba energía.
Por tanto optaremos por esta solución en los casos es que lo habitual sea que la puerta se
mantenga abierta, por ejemplo en el caso de las puertas que se cierran automáticamente en caso
de incendio, pero que habitualmente permanecen abiertas.
Como hemos indicado, cuando la función “loop” se introduce en un mandato “delay” entra en
una especie de estado letárgico que no le permite hacer absolutamente nada. Este programa tiene
en tres “delay” repartidos por la funcion “loop”. Sólo el primero se ejecuta siempre, mientras que
el segundo y tercero, se ejecutan solamente si la luz parpadea. El primero tiene una duración de
una décimas de segundo, y se realiza antes de efectuar la lectura del pulsador, para dar tiempo a
que se amortigüe. Los otros dos “delay”, marcan los tiempos de parpadeo de la luz. Por tanto le
ciclo completo de “loop” cuando la luz esta encendida, dura mas de 4 segundos y cuando esta
apagada no dura mas de dos décimas de segundo.
Como la lectura del voltaje se realiza en este caso sólo una vez por “loop”, en el peor de los casos
al cerrar la puerta, la bombilla no reaccionará hasta pasados cuatro segundos, que sera cuando
haya acabado una intermitencia, se inicie otro loop y se entere de ello la Tarjeta Arduino. En este
caso que la luz intermitente s mantenga cuatro segundos después de cerrar la puerta, no tiene
importancia, por lo que la solución dada es admisible.
Pero podríamos no haber programado que en un loop en vez de una solo intermitencia, se hicieran
1000 intermitencias. Entonces el loop duraría 4000 segundos, es decir 66 minutos, mas de 1
hora. O sea, que una vez cerrada la puerta, aun podría estar luciendo una hora mas en el peor de lo
casos la intermitencia. Algo que sería inaceptable.
El mandato “delay” retarda la funcion “loop”. Cuando utilicemos funciones “delay” hemos de
preocuparnos de estudiar que su uso no ralenticen tanto el programa tanto, que lo deje inoperable e
o que impida al programa efectuar las lecturas del estado de sus sensores y por tanto le dejen
desinformado de como esta cambiando el entorno a su alrededor.
Prácticas
Para realizar este ejercicio tal como aquí se resuelve solo se necesitan los conocimientos que se
han ido explicando hasta el capítulo dedicado al Uso de los pines digitales como entrada (IN
PUT), que podemos resumir en los siguientes puntos:
Material necesario
Objetivos
Especificaciones
La linterna tiene un botón que abre y cierra un circuito. Cada vez que se cierra el circuito, aumenta
una unidad en un contador. En función del valor del contador la linterna hará lo indicado a su
número de acuerdo con lo que se indica.
Inicialmente contador = 0,
Probar si se ha apretado el contador (PIN 2)
Si se ha apretado, sumar uno al valor del contador
Si contador = 0 – No hacer nada
Si contador = 1 – Encender un Led blanco (PIN 4)
Si contador = 2 – Encender un segundo Led blanco. (PIN 7)
Si contador = 3 – Encender un tercer Led blanco (PIN 8)
Si contador = 4 – Apagar los contadores y encender intermitentemente el Led rojo (PIN 12)
Si contador = 5 – Apegar el led rojo y poner nuevamente el contador = 0
Repetir el ciclo
Hardware
Habrá por tanto que abrir un pin a INPUT para controlar el pulsador dedicaremos el Pin 2 y
cuatro pin a OUPUT para cada uno de los leds dedicaremos los pines 4, 7, 8 y 12 Elijo esos pines
porque en Arduino Uno son los que tiene menos valor por no tener otra misión posible que ser
pins de INPUT/OUPUT
El montaje del pulsador sera PULL DOWN que no precisa consumo de corriente cuando no se
oprime el botón lo que ocurrirá casi todo el tiempo, aparte del mayor desgaste de la Tarjeta
Arduino tenemos un consumo mayor de energía eléctrica. En este caso el interruptor ha de ser por
fuerza un pulsador, una llave de la luz vale para dejar pasar o cortar la corriente, dos fases, pero en
este caso el pulsador permite hacer varias cosas diferentes en conjunto tiene 5 posibilidades
diferentes.
Software
Este programa es un poco traicionero, pues como la tradicional película de chinos, tiene muchas
mas trampas que no se ven a simple vista. En principio, parece que este ejercicio no presenta
problemas muy diferentes de los que los que hemos solucionando hasta ahora, pero hay varios
problemas ocultos: ¿Cómo saber diferenciar que han oprimido el botón una vez o varias? ¿Como
contar las pulsaciones? y ¿Cómo evitar una y otra vez mandar lucir un led que ya esta
luciendo?. ¿Como hacer enterarse Arduino que hemos apretado el pulsador el si estamos
·”entretenidos” encendiendo y apagando la luz roja intermitente?.
Comenzaremos a hacer lo que aparentemente es suficiente, para que veamos donde están los
errores, pues como he escrito varias veces, no hay mejor forma de aprender que caer en el error y
aprender a salir de él.
En principio se diría que que una repetida colección de funciones if es suficiente. Probemos
Otra cosa es que puede asombrar, es que hayamos utilizado para el contador el nombre “j” esto
viene de una “vieja” tradición de los programadores, que en los comienzos de la informática
ahorraban espacio utilizando variables de un solo carácter en el caso de variables locales, (las que
se usan solo dentro de un programa, en nuestro caso todas) y solo tres caracteres para las variable
generales (que se usaban en varios programas), por ejemplo “cli” por código de cliente, “dom” por
domicilio etc.
Generalmente las variables locales se nombraban consecutivamente “a” “b” “c” “d”. Lo
podríamos seguir haciendo nada impide poner “a” en vez de “pinled1” o “d” en vez de
“pinledrojo” pero la lectura y comprensión del programa se obscurece y ahora que tenemos
memoria abundante, este ahorro no tiene sentido.
Entonces las variables que se utilizaban para contador se utilizaban las letras “j”, “k” ,”l”, …
porque no suelen ser ningún concepto, sólo un valor que aumenta poco a poco, en nuestro caso
solo el número de índice de un menú de tareas diferentes, y con esta costumbre se ha quedado
hasta nuestros tiempos, podríamos perfectamente llamarlo “contadorpulsaciones” pero prefiero
llamarlo “j” para que cuando vean una cosa así en otro programa, la entiendan.
Bien, pueden copiar y pegar este programa en el editor de IDE compilarlo y cargarlo, pero
observarán que el programa funciona imprevisiblemente, igual se enciende una luz, como varias o
el intermitente rojo ¿Porque pasa esto?
Localizar los errores
Veamos lo que pasa en el simulador. En dos lecciónes annteriores les mostraba, eun una primera
el simulador UnoArduSim y en otra posterior la forma de usarlo, algo que nos va a ser en este
caso de mucha utilidad.
Comencemos por definir primero los dispositivos de entrada/salida (I/O Devices) que vamos a
utilizar. En nuestro caso, es un pulsador, (pushbutton), y cuatro leds. (tres blancos y uno rojo).
En el simulador no hay leds blancos, por lo que utilizare tres amarillos (Y), que es lo mas parecido
que hay.
Una vez escrito y dado OK la pantalla del programa aparece con los dispositivos en la parte
derecha. Ha continuación hay que configurarlos según los utiliza el programa. El pushbutton por
el pin 2 y con montaje PULL DOWN, los leds amarillos (Yelow =Y) en los pines 4, 7 y 9 y el
rojo (Red=R) en el pin 12
´
Eligiendo la opción de menú File (fichero) y Edit/View (Editar/Ver), aparece una pantalla que nos
permite mediante copy/paste trasladar el texto del programa a la simulación. Lo compilamos, si
hemos hecho la copia completa, no dará errores, porque yo lo he depurado antes de ponerla en el
post y así por fin conseguiremos una pantalla que tiene el siguiente aspecto
A la derecha la simulación gráfica, tal como hemos explicado y configurado u a la izquierda el
programa y debajo los valores que en este momento tienen las distintas variables, en te caso los
calores iniciales.
Para que se vea claro como funciona el programa, en la opción de menú “Execute” he marcado la
opción “Animate”, que hace ver una banda azul que indica en cada momento la linea de
programa que está ejecutando, Tiene el inconveniente que retardar muchísimo la ejecución, pues
el programa además de hacer lo que corresponda tiene que situar la linea azul donde corresponda
en la imagen de la pantalla con el programa que se ejecuta , lo que hace que en la realidad todo
ocurra unas 100 veces mas lento que en la realidad. Así y todo vean lo que ocurre cuando en esta
misma opción de menú se lanza el programa oprimiendo RUN. Pueden lanzarlo y pararlo tantas
veces como quieran escribiendo RESET y muevamente RUN Nosotros lo hemos hecho un par de
veces.
Observa lo rápido que va y posiblemente su velocidad real sea de 10 a 100 veces mas rápido por
lo que la frena el representar la barra azul. A esa velocidad no hay posibilidad de apretar un
botón y levantar el dedo, antes que el programa haya leído el voltaje varias veces, por tanto la
máquina va a “pensar”, que la has apretado seguidamente varias veces y te va a situar, en
cualquiera de los menús, posiblemente en el cuarto, pues cuando esté en el cuarto va a tener que
hacer una intermitencia roja y ahí si que estará bastante tiempo.
Para verlo con detalle vamos a hacerlo a cámara lenta. El programa UnoArduSim tiene una
opción en que los programas pasan a cámara lenta. Está en la opción de menú “Execute“ es la
última línea “Slow Motion” (Amara lenta). Eligiendo esta opción todo ocurre mas lento y así
podremos hacer encender un led dos y tres y luego el rojo. Para ello basta tener el botón apretado
cuando la linea azul pasa po54r la parte alta del programa que es donde hemos situado el control
del “pushbutton”.. Veamos el vídeo.
Observarán que cuando se enciende el led rojo la barra se queda parada aquí, es porque ha
entrado en la “anestesia” que le producen los “delay” de hacer la intermitencia de la luz roja,
Mientras esté haciendo esta intermitencia, como el programa no consulta el voltaje del pulsador no
se “entera” de que le estamos mandando apagar todo, es mas cuando entremos en la parte de la
intermitencia apagada pensaremos que hemos conseguido apagar la linterna, pero veremos que no
responde a la hora de pedir que la encienda de4 nuevo y que acabada la intermitencia ,
rápidamente pasa por ahí otra ves y entra en otra intermitencia, La forma mas practica de apagar la
linterna es haciendo nuevamente RESET
Y no han acabado ahí los problemas. Hay otra cosa que me irrita bastante aunque en si mismo no
es un problema. Mientras el valor de “j” no varíe y sea por ejemplo 2, en cada “loop” la máquina
va a intentar encender el segundo led, La cosa no tiene la menor importancia porque como el led
ya esta encendido no va a hacer mas que encenderle de nuevo y ni se va a notar, pero hacer cosas
que no valen para nada es un poco tonto.
Para que lo noten voy a dejar el aparato con dos led encendidos, en la parte de las variables abajo
verán que la “j” adquiere el valor 2 pero en cada vuelta verán que entra en el “if (j ==2) y intenta
encender el led. Para que lo vean en el video con más facilidad he puesto un pequeño “delay”
inmediatamente debajo de encender el segundo led, verán así claramente que si “j” es 2 , el
programa entra en ese “if” e intenta encender el segundo led aunque ya este encendido. Veanlo
en este tercer vídeo.
Comienzo poniendo la barra azul sobre el “delay” que he puesto después de encender el
segundo led. Este “delay” es absolutamente innecesario pero ayudar a ver cuando el programa se
mete en ese “if”
Luego hago un RESET y a continuación un RUN para iniciar el programa. El programa trabaja
como antes, porque como ”j” no vale 2 y no entra en el “delay” que he puesto,
Con el ratón aprieto el pulsador y se enciende el primer led. No pasa nada especial porque “j “ ha
adquirido el valor 1 se enciende el primer led y punto. Cuando enciendo el segundo led verán que
a continuación hace el pequeño “delay” que he puesto y que a partir de entonces y mientras “j”
valga 2 va a hacer ese “delay”, señal que el programa pasa por ahí en todos los “loop” y que por
lo tanto va a intentar encender el led, aunque el led ya esta encendido.
Nuevamente pulso el botón, “j” adquiere el valor 3 se enciende el tercer led pero el programa
como es lógico ya no pasa por el “if(j==2)” y nuevamente no vuelve a parar en el “delay”,
Como hemos hecho con el valor 2 de “j” pasaria con el valor 1, 3, 4 y 5 en cada caso intentaria
entrar repetidamente en “if” que lo que hacen es encender y apagar leds.
Problemas detectados
Así pues hemos detectado tres problemas, uno menor, más bien una manía mía, “un programa no
debe dar pasos innecesarios”. Tal como está hecho este programa, los led son encendidos o
apagados como corresponda en función del Menú, en cada “loop”.
El tercer problema también es delicado, La máquina tiene mucha dificultad para diferenciar si las
pulsaciones son diferentes o es la misma pero no hemos levantado el dedo del botón, ¿Cómo lo
resolvemos?
1º) Los leds se encendían y apagaban innecesariamente cada vez que se ejecutaba un “loop” del
programa
2º) La maquina entra en “catalepsia” el tiempo que dura una intermitencia de la luz roja,
impidiendo observar si en ese tiempo se pulsa el botón
3º) La máquina no era capaz de diferenciar entre una pulsación larga y varias pulsaciones
seguidas.
1º) Hacer que los leds se encendían y apagaban sólo una vez
Al detectar una pulsación se ejecuta la opción del menú correspondiente, que enciende y apaga
determinados leds, pero una vez hecho, se busca la forma de impedir que en sucesivos “loop” sin
que se hayan percibido mas pulsaciones se vuelva a repetir encender y apagar los mismos led.
La solución es llevar el control de los “loops” mediante variable que llamaremos “primeravez”
inicializada a cero, que la detectar que hemos pulsado el botón toma el valor 1. Solo si
“primeravez” vale 1 se ejecutan las opciones de menú y una vez ejecutadas, nuevamente se vuelve
a dar el valor 0 a “primeravez” para que no repita este trabajo en los siguientes “loops”.
* delay (rebote)
* Ver si han apretado el botón
* Si han apretado el botón
* Aumentar el contador
* Poner la variable “primeravez” a 1
* Si “primeravez” es 1
* Encender y apagar leds en función del valor del contador
* Poner la variable “primeravez” a 0 para no repetir
* Si el contador es la opción 4
* Encender y apagar el led rojo una vez
* Repetir el proceso
Observen que separo la labor de apagar y encender los leds (incluido el led rojo) de la labor de
provocar la intermitencia, porque la primera labor hay que hacerla solamente una vez, mientras
que la intermitencia hay que mantenerla en tanto este vigente la opción de menú 4. “encender el
led rojo intermitentemente”
Como avisamos en múltiples lugares, el uso de los “delay” son siempre peligrosos, pies hacen
entrar el software en una especie de letargo invernal, razón por la cual cualquier otra acción que
deseemos realiza en otro punto del “loop” no se realiza.
El problema en nuestro caso es que queremos hacer dos cosas a la vez, por un lado queremos
generar una intermitencia en un led y por otro queremos estar atentos a que realicen una pulsación
en el “pushbutton”. Es decir queremos hacer dos cosas a la vez.
Se cuenta del Presidente Ford, que alcanzó la Presidencia de Norteamérica de carambola, pues
llegó a la presidencia por escalafón, debido a la dimisión de Nixon, que era tan simple, que no
podía hacer dos cosas a la vez , como andar y macar chicle. Pues bien, lo que nosotros estamos
tratando de hacer, son dos cosas a la vez, como el Presidente Ford, parpadear un led rojo, y
vigilar si aprietan el botón, y siento informarte, que la Tarjeta Arduino es tan simple como el
Presidente Ford, no puede hacer dos tareas simples a la vez, porque es monotarea y como eso
indica, sólo puede hacer una tarea.
Simulación de multitarea
Pero hasta el Presidente Ford, hubiera podido dar un paso, a continuación dar una mascada al
chicle, y seguir con otro paso, porque eso es realizar una sola tarea, en cada momento o da un paso
o masca chicle y si lo hace con la debida rapidez y buen ritmo, al espectador le parecerá que el
Presidente Ford, anda y mastica chicle a la vez, es decir simula que es multitarea, cuando la
realidad es que, sólo hace una cosa detrás de otra, aunque sea muy deprisa.
Lo mismo pasa en informática, hasta que recientemente se han generalizado los procesadores
con varios núcleos o “cores”, no importaba que tan grande y potente fuera el ordenador, tan solo
podían hacer una sola cosa a la vez, pues solo tenían un procesador, y lo dedicaban a esto, o a lo
otro, pero no a dos cosas a la vez, pero sin embargo todos hemos utilizado ordenadores, que por
ejemplo, te permiten escribir, mientras la impresora imprime, o te dejan a la vez trabajar en una
página de Excel y oír música en segundo plano.
¿Cómo lo hacían?
Pues igual que el Presidente Ford, haciendo una tarea, parando esa tarea y
continuando otra, o sea avanzando todas las tareas un pasito cada vez, así hasta acabar
con todas y volver a empezar. Esto es lo que hacen los PC’s internamente, pero a tal
velocidad, que oyes la música sin que te des cuenta que se para entre nota y nota y es lo
que vamos a hacer nosotros a mano, simular que nuestra Tarjeta Arduino es
multitarea.
Para ello, vamos a repartir los bucles del programa entre las dos tareas, los bucles pares, los
vamos a destinar a vigilar si aprietan el botón y los impares, a encender y apagar el led rojo,
pero claro, necesitamos que tanto un bucle como otro, transcurran a alta velocidad para que el
truco no se note.
En los bucles pares, no hay problema, pues sólo tenemos un “delay” muy pequeño, (rebote),
pero en el segundo si estamos en la opción de menú 4, tenemos dos “delay” largos, (parada), y
eso no lo podemos permitir, si pretendemos simular multitarea, necesitamos que este bucle sea
también muy rápido.
Pues muy sencillo, dividir la tarea que tarda, entre tantos bucles consecutivos, que pase
desapercibida. Como en el bucle par ya hay un pequeño “delay”, en el segundo bucle vamos a
sustituir los “delay” existentes , por un contador que vaya sumando los tiempos que se pierden en
el bucle par, y cundo el contador llegue a cierto valor, (en nuestro caso “tiempo “apagamos el led
rojo y así lo tenemos hasta que el cont6ador alcance el doble de “tiempo” momento en que
habremos acabado la intermitencia e iniciaremos la siguiente. Para controlar le “loop” que se
ejecuta esto añadimos una nueva variable de control que llamaremos “parimpar”
Sobre el esquema anterior añadiremos estas nuevas condiciones. El nuevo esquema será:
De esta forma conseguimos que cada bucle se dedique a cosas diferentes y como hemos
conseguido hacer que los bucles transcurran muy rápido, parecerá que hacemos dos cosas a la vez.
El problema esta resuelto, solo que poco a poco estamos ampliando el numero de variables y la
complejidad del programa, pero a mi me parece inevitable.
Abordamos por fin el último de los problemas. La primer y fundamental causa de fallo, que el
“loop” transcurre a gran velocidad, Si se fijan ahora que hemos eliminado los dos “delay” que
había en la intermitencia roja, tan solo nos queda una mínima parada de una décima de segundo.
Algo absolutamente mínimo para que el dedo apriete y se levante del botón.
Para obviar este problema se me ocurren dos soluciones, La primea es hacer una pausa o “delay”
de determinado tiempo cuando se detecte que se ha apretado el botón, para dar tiempo a que se
retire el dedo, o bien otra posibilidad es detectar cuando se ha levantado el dedo y mientras no se
levante, considerar sólo una pulsación, esté el dedo el tiempo que esté pulsando continuadamente
el botón.
La primera solución a priori parce ms sencilla , sólo se trata de instalar un nuevo ·”deláy” y tiene
la ventaja sobre la segunda que si el usuario quiere ir aumentando la intensidad de la luz, le basta
con mantener pulsado el botón, pues pasado un tiempo, el sistema automáticamente pasa a la
siguiente opción de menú.
Posiblemente concluido el aparato tendremos que hacer unas pruebas, hasta encontrar un valor
para la “pausa” suficientemente largo, para retirar el dedo con tranquilidad, pero que no sea
excesivo y haga el cambio de opción de menú muy pesado. Calculo que unos pocos experimentos
variando el valor de “pausa” serán suficientes para encontrar un tiempo idóneo.
El problema es que si hemos hecho una modificación para eliminar dos “delays” que había por
ahí, ¿No estaremos creando otra dificultad al poner un nuevo “delay” por el medio?.
En este caso no tendremos, como ocurría en el caso anterior, que preocuparnos con el tiempo de
ejecución del bucle, pues “delay (pausa)” sólo se produce en el bucle que ha detectado la
pulsación y después de encender y apagar las luces que corresponda, por tanto sólo se ejecuta una
vez por opción de menú y sólo retrasara algo la ejecución de la opción 4, que es la que pone la
intermitencia del led rojo y sólo afectará a la primera intermitencia. Incluso podemos compensar
este problema, dando al “contador_de_ tiempos” que mide el tiempo de la intermitencia un valor
inicial que compense esta pausa, pero creo que es algo sin importancia en este caso.
Como ven con los “delay” puede pasar de todo y hay que estudiar en cada caso las consecuencias
que para el programa puede tener “anestesiar” su funcionamiento durante un tiempo.
No existe una regla fija. En este ejemplo hemos visto que en un sitio, “delay (rebote)”, pese a
actuar en cada “loop impar”. es tan corto que no interfiere en el tiempo de ejecución del “loop”,
pero en cambio, esta miniparada cuenta en los “loop pares” para acumular el tiempo de las
intermitencias. Por tanto, de otra forma, hay que tenerlo en cuenta.
En cambio el “delay (tiempo)” que regulaba las intermitencias, era inaceptable y fue sustituido por
la suma de los tiempos de “delay (rebote)” realizados en los sucesivos “loop par”. Por último el
“delay (pausa)”, que vamos a colocar para dar tiempo de retirar el dedo, pese a ser claramente
perceptible, no molesta en este caso, pues sólo se ejecuta una vez por pulsación.
Como digo, no puedo daros una regla de actuación porque no la hay, pero es algo que debemos
estudiar en cada caso, y cuando un programa a vuestro juicio está “perfecto”, pero no funciona
como se esperaba, o peor aún, funciona unas veces si y otras no, que de todo lo que nos puede
pasar, lo más peligroso, observar si hay un “delay” y revisar que no pueda ser la causa del mal
funcionamiento del programa.
Veamos por fin como queda el esquema del programa definitivo incorporando esta última
modificación:
Procedamos pues a dar escribir el nuevo código una vez tenido en cuenta todos sus errores y
pasemos a probarlo,
Les dejo una película que hecho del funcionamiento en el simulador UnoArduSim, La he hecho a
velocidad normal y sin seguimiento del programa por tanto la parte de la izquierda de la pantalla
del simulador no añade nada, Por eso me he centrado solo en la parte derecha.
Primero voy apretando cinco veces seguidas el botón para que se vea como se van encendiendo
los leed hasta llegar a la cuarta opción que apaga los leds amarillos y enciende el led rojo. A
contimuación mantengo el botón apretado hasta conseguir que se enciendan dos led y
posteriormente, enciendo el tercero.
Poner a punto este programa tan largo no es cosa que ocurra en un primer intento. Yo incialmente
lo escribo tal como a mi me parece correcto e intento compilarlo. Lo habitual es que el compilador
me devuelva errores de sintaxis, es decir errores que el compilador descubre porque las cosas
están escritas de forma indebida y no las entiende. ¿Cuales son esos errores, pues pueden ser
muchos, voy a poner una lista de los mas habituales.
Por supuesto esta no es una lista exaustivas, hay mas como mala sintaxis de las funciones y otros
errores como intentar hacer operaciones con variables definidas como alfabéticas y cosas
parecidas,cosas.
A medidfa que vamos compilando la compilacion se detiene en una linea dque detecta erronea y
lanza un aviso, que unas veces es acertado y otras te introduce mas problemas porque es confuso o
la m`´aquina se ha confundido , por ejemplo si en un comentario no has puesto // posiblemente
trate de hacer alf go con el comentario y te diga que esa variable no la tienes defindo en vez que
faltan los “//”. Otra veces al llegar a un punto dice que los parentesis abiertos no coiciden con los
cerrados, pero no es en ese puntyo sino muchas lineas mas arriba que olvidaste cerrar un
partentesis, Por tanto los mensajes tenemos que tomarlos como error probable pero no como un
dogma de fe, unas feces (las mas) acierta y otras /(las menos) fracas, y nos confunde mas.
Conseguido que compile todfo el texto, hemos eliminado el 90% de los errores pero tambien es
cierto los errores mas obvios de eliminar, porque aqui comienza lo dificil ver si el programa actúa
como estaba previsto y veremos habitualmente como la Ley de Murfi, que dice aquello de que
“Si algo puede ir mal, ira mal” sie cumple con una regularidad matemática.
Por ello llo voy probando los programas por partes; en concreto este le he probado en cuatro
trozos.
Para ello deje la zona de variables y la funciíon SETUP y en elsimuylador UnoArduSim probe una
funcion loop como la que escribo.
// Función loop
void loop() {
// **************** loop par ******************************
if (parimpar == 0) {
delay ( 100) ;
parimpar = 1;
} // Fin de loop par
// **************** loop impar ******************************
else {
delay ( 100) ;
parimpar = 0;
} // Fin if (parimpar == 1)
} // fin funcion loop
Observara que solo es el proceso de ejecuciíon “loop `par /loop impar”. Como ven instale uunos
Delay provisionales para rtelentizar el progrrama y poder observar con comodidad si se cumplian
sucesivamente.
Pues en este programa tan simple había cometido un error. Inicialmente habia puesto en la primera
parte “if (parimpar == 0)” y a continuación “if (parimpar == 1)” aparente mente tenia que ir bien
entba con un valor se hacia lo que correpondíia al “loop” y al final cambiaba el valor para que a la
vez siguiente se hiciera el otro “loop”.
Pues se me escapó que si en la ultima fila de el prime “if (parimpar == 0) hago “parimpar = 1; ” al
entraen el “if (parimpar == 1)” “parimpar vale realmente 1 y se meterñá a hacer ese if cuando mi
desero era que hiciera un nuevo “loop” , Si ponemos en cambio un “else” si se cumple lo que
quiero pues o se hace una serie de instrucciones o la otra.
Pues bien este tipo de errores que noson ortográfico ni sintacticos, sino simple y duramente de c
programación los (actuales>) compiladores no los di ¡etectan pues no son inteligentes, y si lo que
escribimos se puede hacer no tiene inteligencia para saber si lo que hacen tiene sentido o es un
pampirolada.
De ambas partes del programa la segunda me parecía la mas sencilla por lo que la probé en primer
lugar. Trataba de ver si el sistema diseñado de intermitencia probaba como yo lo esperaba. Añadi
a lo que ya funcionaba anteriormente la parte del “·loop impar”, puesto que todo lo demás ya
funcionaba bien, si algo iba mal, tenía que ser lo que probaba. Em este caso cambié la funcion
“loop” por la siguiente:
// Función loop
void loop() {
// **************** loop par ******************************
if (parimpar == 0) {
if (j == 0) {
j=4 ;
digitalWrite(pinledrojo, HIGH);
delay ( 100) ;
} // Fin if (j == 0)
parimpar = 1;
} // Fin de loop par
// **************** loop impar ******************************
else {
// * Si el contador es la opcion 4 atender a la intermitencia
if (j == 4) {
k = k + rebote ; // Sumar a k “rebote”
if (k== tiempo) { digitalWrite(pinledrojo, LOW); }
if (k == dobletiempo) { digitalWrite(pinledrojo, HIGH); k = 0; }
} // Fin if (j == 4)
parimpar = 0;
} // Fin if else parimpar
} // Fin funcion loop
Observan que en el primer loop cuando aun “j” vale 0, doy a j el valor 4 Por tanto nunca mas
hara este “if” pero ya de paso aprovecho para encender por primera c vez el led rojo y como ante
pongo una paradita para ver que pasa por estepunto solo una vez. Eb kis loop para siguentes no
hara mas que poner “parimpar” a 1, Mientras que en los pares poco a poco ira aumentando el valor
de k hata llegar a “tiempo” (=2000) donde apagara el led rojo y a “dobletiempo” (=400o) donde
vulve a encender el led rojo y pone nuevamente “k” a 0 , dando por acabada la intermitencia.
Esta parte del programa funcionaba muy bien sólamente me parecio que los dos segundos
calculados era un poco lento y lo cambi a un segundo, o sea “tiempo” es igual a 1000 y
“dobletimepo” es 2000. Anuque se cumplía descubri que hay algo que hay que tenr en cuenta que
“tiempo” y “dobletiempo” han de ser múltiplos exactos de “rebote” y k comenzar con valor =
porque si no, nunca se cumpliran las condiciones “(k== tiempo)” y (k == dobletiempo)
Otra cosa que quiza os extrañe es que aqui he escrito las funciones “if” en una sola línea de la
siguiente manera
if (k== tiempo)
{ digitalWrite(pinledrojo, LOW);
}
Ambas formas de escribir son correctas, el compilador lo primero que hace es quitar saltos de
linea y espacios en blanco repetidos, el solo entiendo un gigantesco churo de mandatos separdos
por “;” y agrupados por “(” “)” y por “{” “}”, nada mas, Todfo lo otro es para los humanos que
somos muy lerdos y necesitamnos las cosas muy claras, por eso si es claro, fundameentalmente
porque cabe en una linesa, lo escribiremos como està en priimer lugar , pero si en la agrupacion
hay muchos mandatos resulta mas claro de comprensión escribirlo en varias lineas y a ser posible
que mi editor de word press no me deja con pequeños indentados que indiquen lo que abarca cada
agu rupacion de mandatos.
Probamos si funciona bien la lectura del pulsador y si la pausa que hemos puesto es suficiente 7y
no interrumpe el programa. La funció “loop” anterior motamos lo referente a la lectura del
pulsador y lo que se hace si se observa que se ha pulsado.
// Función loop
void loop() {
// **************** loop par ******************************
if (parimpar == 0) {
// * Ver si han apretado el botón (pin 2)
delay (rebote) ; // Retardo para evitar “rebote” de los interruptores
corriente = digitalRead(pininp); // 1º comprobar el voltaje
// * Si han apretado el botón (corriente == 1)
// * Aumentar el contador
//* Poner la variable “primeravez” a 1
if (corriente == 1) {
j = j + 1; // Se suma al contador j una unidad
primeravez =1 ;
} // Fin (corriente == 1)
delay (100 ) ;
parimpar = 1;
} // Fin de loop par
// **************** loop impar ******************************
else {
// * Si el contador es la opcion 4 atender a la intermitencia
if (j == 4) {
k = k + rebote ; // Sumar a k “rebote”
if (k== tiempo) { digitalWrite(pinledrojo, LOW); }
if (k == dobletiempo) { digitalWrite(pinledrojo, HIGH); k = 0; }
} // Fin if (j == 4)
parimpar = 0;
} // Fin if else parimpar
} // Fin funcion loop
Introfuzco además un pequeño “delay” al final del “loop par” para tener tiempo de ver si “j” ha
cambiado de tiempo. No es fácil calcular si el tiempo. Todo el proceso transcurrio sin dificultad
por lo que pasé directamente a el último ensayo con todas las fuhncionalidadessegún el valor de
“j” colocadas.
4º Prueba final
El software del programa al completo, probado y comprobado, listo para que Vd lo copie y pegue
y comience a hacer pruebas y modificaciones-
Aun haciendo esta prueba descubrí que si pulsaba la quinta 5 vez, como estaba previsto cesaban
las intermitencias pero que “k” se quedaba con el valor que tuviera en ese momento, lo que
ocasionaba que de volver a llevar la linterna al menú 4 la intermitencia empezaba a medias, La
verdad es que el problema no tenia excesiva importancia salvo que la primera intermitencia
pudiera tener el tiempo encendido o muy breve o muy largo en función de lo que valiera “k” en
ese momento, pero por si acaso, añadí inicializar la “k” a cero a las tareas a hacer en la opcion 5.
Como digo hay muchas soluciones a los problemas planteados y esta no es mas que una de ellas.
Por ejemplo , y quizá hubiera sido más sencillo, dedicar medio buclue a estudiar si se ha apretado
el pulsador y el otro medio acontinuación a la intermitencia hecha en múltiples bucles de mos do
que el bucle completo hubiera sido rápido, Posiblemente la cosa hubiera funcionado igual y de
forma mas sencilla. El encontrar la forma mas sencilla de sresolver el miwsmo problema es lo que
diferencia un buen programador de uno malo. Les dejo la labor de resolver este problema
atendiendo a ambas tareas en un solo bucle.
Como ya indicamos una segunda forma de detectar las pulsaciones, es controlar cuando
se deja de pulsar, de esta forma se delimita perfectamente cada pulsación
independientemente del tiempo que se mantenga el dedo en el pulsador.
Así pues como sabemos cuando se ha iniciado la pulsación por la variable “primeravez” si esta
con valor 1 y se detecta que el voltaje sigue siendo 5 voltios, (“corriente” igual 1), es que se
continua apretando, Cuando la variable, “primeravez” tenga el valor 1 y se detecte que el voltaje
es cero, (“corriente” igual 0) se ha terminado de apretar y por tanto se inicia la posibilidad de que
aprieten de nuevo porque quieran cambiar la opción de menú.
Así pues pueden ocurrir las siguientes circunstancias segun los valores de “primeravez”
y “corriente ” y la accion a tomar
Esto s es lo que se denomia un árbol de decisiónes, todas las actividades que hay que tomar en
funcion de varias circustancias concurrentes.. En este caso son solo dos las circunstancias los
valores de “corriente” y “primeravez” pero hay caso que entran tres o cuatro y las actividades
pueden ser muchas diferentes. El estudio detallado de los arboles de decisiones debe ser anterior al
diseño del programa en la fase que se denomina Analisis Funcional ypues en en función de lo que
aquí resulte que dse diseñan los programas. que se
Aquí tienen otro ejercicio que pueden intentar hacer Será un poco lioso don una mezcla de “if”
anidados,y consecutivos y “if/else”, pero a mi juicio nada que no tengan ya conocimientos
suficientes para poder resolver. Les dejo el esquema del programa a realizar
Habría que evaluar cual de todas las soluciones es la mejor, pues en principio para mi lo son
claramente las dos primeras, sin embargo esta última solución, tiene la ventaja que sea rápida o
lenta la pulsación del botón, la máquina sabe discernir sin lugar a duda cuantas veces se has
pulsado, mientras que en las primeras soluciones, esto no queda tan claro.
No obstante éstas, tiene una ventaja que si el tiempo de “parada” es el adecuado, el
funcionamiento sera perfecto, y eso es algo que podremos afinar en unos cuantos experimentos
reales, pues dependerá no solo de la velocidad de la persona apretando el pulsador, sino además de
la rapidez de la tarjeta ejecutando las instrucciones y de la velocidad con que reaccione el botón
del pushbotton cuando se le suelta. Si el usuario mantiene el dedo apretado , a una velocidad
razonable, la linterna va pasando de una a otra opción´sin necesidad de apretar repetidas veces el
botón lo cual en principio parece más cómodo.
Usabilidad.
Entramos aquí en algo que se denomina la “USABILIDAD”, o la comodidad que las personas
encuentran en el uso de un aparato. Algo que no se fácilmente mensurable. Tqampoco, como
vemos se relaciona con la calida o complejidad del software, sino con la mejor aceptacion aparato
por parte del público.
¿Que es mas cómodo, ¿pasar de una opción de menú manteniendo apretado un botón o
apretar repetidamente el mismo? — A mi, en principio, me parece mejor solución la
primera, pero lo correcto seria hacer un prototipo de cada solución, incluso hacer
prototipos con dos botones uno para subir y otro para bajar y darlos a probar a una
muestra de personas variadas, en la que entraran personas de diferentes niveles
culturales y edades, diestros y zurdos, y que la piensen destinar a usos diferentes, como
campistas, conductores, vigilantes, electricistas etc. y estudiar su respuesta y a partir de
ese muestreo, tomar la decisión más, conveniente, La usabilidad es algo que nos debe
preocupar también cundo estemos prototipando un aparato.
Firmware
Como vemos el mismo hardware, funciona con tres programas diferentes, (aunque con el
primero que pusimos lo haga mal), por tanto construida la linterna, podríamos acceder a la
Tarjeta Arduino y cambiar el programa, para por ejemplo pasar del primer programa al
segundo y despuès o al tercero o lña cuarto sin hacer ningún cambio en lo que es la mecáanica
del aparato. Esta es una ventaja adicional de todos los aparatos electrónicos que tienen
internamente un procesador, (y cada dia hay más de estos aparatos en el hogar, del ordenador, al
reloj despertador, pasando por la vitrocerámica, lavadora nevera, equipo de aire acondicionado,
televisión etc.) , que se puede cambiar el firmware sin cambiar el hardware, (sin modificar la
parte mecánica), para corregir a posteriori errores de diseño, como ocurre aquí, al pasar del
programa con errores l al programa arreglado, o para darle mejor usabilidad mejores o mas
cantidad de funcionalidades al mismo aparato, Por ejemplo podríamos utilizarle para emitir
señades de Morse luminosas sin modificar la máquina. .
Si utilizais Windows, frecuentemente tendréis que padecer actualizaciones del sistema operativo,
lo mismo pasa con las App del teléfono móvil , frecuentemente os pedirán que las actualices, eso
técnicamente se llama actualización (si es poco) o sustitución del firmware , (si es la totalidad),
Prácticas
Repetir el ejercico pero resolviendo todo en el mimo “loop”
Repetir e programa sepando las distintas pulsaciones mediante la búsqeda del momento en que
se deja de apretar el botón.
Repaso
Material necesario
Todos estos conocimientos se explican en detalle en los capítulos anteriores del curso (Busque en
el Indice)
El mundo real no es digital, es analógico. El mundo no es blanco o negro, sino con todos los
matices de grises, ni hay ruido o silencio, hay voces y susurros, ni caliente y frio, es también
templado y fresco. Algo hay que inventar para poder dar forma con ceros y unos a las cosas que
son 0,76, ó 0,23 y por supuesto, algo tiene la Tarjeta Arduino para hacerlo, se llaman los Pines
analógico, que generas salidas que se aproximan a la realidad del mundo físico.
Supongamos que queremos que un led, no sólo esté encendido y apagado, sino que este con una
luz debil, ¿Lo podremos hacer con lo que sabemos?
Pues si. Para ello nos vamos a valer de una propiedad de la vista que es la persistencia retiniana, el
fenómeno que nos hace ver moverse algo, que solo es una continuada proyección de imágenes
lévemente persistentes, que nuestro ojo une en el cerebro.
Lo que percibimos en una bombilla es la energía luminoso que desprende. Si esa bombilla recibe
menos energía, desprenderá menos energía y la veremos menos brillante. El Led luce. o no luce,
pero si conseguimos que luzca durante un tiempo y este apagado otro, como hemos hecho en las
intermitencias, por unidad de tiempo, se desprende la mitad de enegía. Si hacemos que la
intermitencia ocurra a mayor velocidad de 24 veces por segundo. lo que veremos es una luz mas
pálida.
Si hacemos 25 parpadeos por segundo no veremos la intermitencia, pero nos parecera la luz mas
apagada, porque en un segundo emite menos luz. O sea vamos a tratar de que cada parpadeo tarde
un venticincoavo de segundo, como le segundo son 1000 microsegundos la venticinco parte son
40 microsegundos.
Hagámoslo
Manos a la obra, Dejamos una luz encendida siempre como comparación y la otra la encendemos
y apagamos 25 veces en un segundo, es decir 40 centesimas de segundo de las cuales 20 está
encendida y 20 apagada.
Hardware
El hardware sera como el que se indica en la imagen de la entrada, perfectamente conocido a estas
alturas dos circuitos con un led y una resistencia como hemos visto anteriormente, Un led
“testigo” unido al pin 8 y uno que llamamos “variable” unido al pin 9 con sus respectivas
resistencias de 220 homios.
Software
Pues bien, si lo hacen, (sólo tienen que cambiar donde pongo 12 por 20 en el programa que viene a
continuación), verán que se ve parpadear las luces.
Porque no hemos tenido en cuenta el tiempo que se pierde en ejecutar las instrucciones que tienen
la función “loop” además de los “delay”. En cada “loop”, comprueba que un “if” no se cumple y
manda saltar una serie de mandatos, hace un “delay” (que si hemos tenido en cuenta), cierra
un pin, hace otro “delay” (que si hemos tenido en cuenta), y vuelve a abrir al pin. Y en todo eso
pierde un tiempo que retrasa el “loop” y por lo tanto, en un segundo no hacemos 25 “loop” sino
menos y vemos el parpadeo.
Después de algunos tanteos, he pedido que las intermitencias duren 24 milisegundos y así se ve
contínuo. El sketch para intermitencias de 24 milisegundos queda así.
Si copiamos, compilamos y subimos el Sketch a la Tarjeta Arduino, veremos algo como lo que
muestro en el vídeo
Si se fijan, la luz de la derecha es algo mas ténue que la de la izquierda, como estaba previsto. Sin
embargo lo más que aguanta sin que se vea el parpadeo son intermitencias de 24 milisegundos, 12
encendidos y 12 apagados. He probado a poner 15” y se nota el parpadeo. Indica que la Tarjeta
Arduino UNO es mas lenta que lo que parece, porque, tarda 16 microsegundos en hacer un
puñadito de mandatos. No he encontrado documentación sobre el tiempo que se tarda en encender
y apagar un pin, pero sospecho que este es el motivo del retardo.
Así capa sobre capa se va llegando a lenguajes específicos para trabajos específicos. Por ejemplo
el tratamiento de textos tiene una serie de mandatos, como poner en negrita, saltar de linea, o
simplemente escribir una “s” , esto se llama un “lenguaje ” de programación de “alto nivel”, que
es el 2que normalmente utilizan los programadores, porque es sencillo de manejar y de alto
rendimiento. Tan sencillo que todos lo utilizamos con muy poco aprendizaje e incluso los mas
espe4rtos lo manejqn con los 10 dedos y sin mirara teclado.
Un lenguaje de bajo nivel, hoy lo habitual es utilizar C o C**, toma r el mandato “s” que ha
recibido y lo guarda en la memoria en firnma de o bits (cerios y unos) y no solo eso busca un
dibujito de una s que tien guardado por ahí, (en 0 y 1 que son pixel apagados y encendidos) y lo
presenta en pantalla en el sitio que corresponde .·Y para hacer todo eso sus mandatos los
transforma en rutinas de “Ensamblador” que la máquina sabe “digerir” y trasformar en rutinas
de “lenguaje máquina”
Si no me equivoco. Arduino tiene una capa iIntemedia que es el Lenguaje C, lenguaje ya cómodo
de utilizar pero que aun anda muy próximo a la maquina y puede con facilidad mover bites y
cambiar direcciones de memoria. El lengua IDE que utilizo para este curso, no son mas que
rutinas en C que simplifican el uso de equipos que se van a utilizar especificamente como
microprocontroladores.
Asi que cundo ponemos un expresiontan sencilla como (j= j + 1) estamos diciendo en un lenguje
de nivekl alto
La primer instrucción “Lleva a procesador la variable J “ pasa a ensamblador que lo que hace
probablemente, porque no se exactamnte como lo hace es:
Por fin llegamos al lenguaje máquina donde “Busca en el indice donde se guarda la variable j “
en una complejísima operación de búsquedas dicotómicas, que consiste en mirar en la mitad de
un indice y comparar el nombre de la variable con el que esta eb esa posición del indice. Si es mas
grande, buscar en en la mitad de la parte inferios y si no al revés. Comparar, buscar etc, hasta a
llegar al valor buscado exactamente, ( suelen necesitarse de 8 a 9 búsquedas para acertar como
media) y una vez encontrado, tomar la dirección de memoria asociada, que se dio in el proceso
INT, y quizá el tipo de variable, que puede ser aunque no lo sepas aun, de lo mas
variada,numerica, textual, de 2 o 4 bits, representar un numero entero, o un número fraccionario
con 16 numero significativos, vectores, o matrices,… Vamos de lo mas variado y que cada una
necesita un espacio específico par ser guardado en el disco duro. Ya tenemos la direcion y el
número de bis que tenemos que copiar,.
El esquena superior, indica mas o menos el proceso. El programador escribe un programa, que el
compilador transforma en rutinas de ensamblador en un primer paso y posteriormente la
máquina transforma esas rutinas de lenguje máquina que es realmente lo que guarda la memoria
del ordenador. En nuestro caso, hay aun un nivel mas que seria de IDE a C, que seria en este caso
que tu escribieras (F4 = RI + F4),
Como ves en estos procesos las lineas de programa se multiplican como conejos y finalmente la
máquina que no puede mover mas que, (en esta máquina), 8 bits de golpe, o se 8 ceros y unos,
(una de las lineas que se ven en el grñafico) hace el resto.
Por todo lo contado se darán cuenta que 16.000 instrucioners de 8 bits por segundo, no son ni
mucho menos 16,000 mandatos de IDE sino lógicamente muchisimos menos. Razón por la cual,
como en este programa salta a la vista, los 16000 MHz ,no son tan rápidos como parecía.
Pese al retardo que producen las funciones, aun nos quedan unos milisegundos para jugar. En este
caso, vamos a subir y bajar la intensidad de la luz del led jugando con esos 24 segundos de
duración del “loop”, que tenemos antes de que se vea parpadear la luz
Dejaremos el hardware como esta pese, a que en este caso no vamos a utilizar el led “testigo”,
pues seguiremos utilizando a continuación el led continuación tal como está, por lo que no merece
la pena desmontarlo. En cambio el programa será como sigue
Ven que lo he conseguido, la luz sube y baja. La único truco es utilizar dos contadores, una
ascenderte y otro descendente. porque si en un momento determinado a “j” le restamos algo, entra
en valores por debajo de 25 y el ”loop” se metería nuevamente en el primer “if” y trataría
nuevamente de apagar el Led. También hay que cuidar que “k” no llegue a 0. porque no tiene
sentido un “delay” con tiempo 0 ó negativo
Veamos el resultado
Sin embargo en nuestro caso nos encontramos con dos limitaciones, La primera que la
unidad de medida que tiempo es el milisegundo, por tanto no podemos apagar o
encender la luz por menos tiempo que ese, y la segunda limitación es que para que el
efecto de parpadeo no aparezca tenemos que emitir como máximo ciclos de 24
milisegundos por lo que no tenemos mucho tiempo para perder en otros menesteres, .
Por ejemplo si no fuera un led sino dos los que quisiéramos aumentar y descender
encender, ya no podríamos pues el tiempo perdido en abrir y cerrar el segúndo led,
es superior a lo que podemos distraer,. Si en el primer caso, se redujo el tiempo teórico
de 40 milisegundos a 24 en este necesitamos otros 14 milisegundos mas por lo menos,
y por mucho que tratemos haciendo subir y bajar la luz los 5 peldaños que nos quedan
de los 10 milisegundos restantes , muy probablemente el efecto sería inapreciable.
Sintaxis de delayMicroseconds
“delayMicroseconds(value)”
Donde:
Si multiplicamos todo por 1000 en el programa anterior nada debería cambiar pero por
algún motivo en este caso vemos temblar a la luz, no se realmente el motivo, pienso
que quizá trabajar con cifras mas grandes retrasa las operaciones, el caso es que me he
visto obligado a reducir un poco la duración de los ciclos de y así funciona
perfectamente igual que antes.
Me ha costado mucho jugar con los valores iniciales de “j” y “k”, así como el incremento en cada
“loop”, para que tenga una velocidad adecuado pero al fin lo he conseguido. Vean el resultado,
una luz aumenta de brillo y la otra lo reduce hasta apagarse y volver a encenderse mientras la otra
baja.
Miren cosas curiosas de este sketch, desaparece las cosas que teníamos que hacer en el primer
“loop” y en consecuencia la variable “primerloop” que lo controlaba, porque no hay que abrir
previamente los pins que van a trabajar. Por lo demás es muy lioso en el manejo de contadores,
creo que la deben copiar y jugar cambiando el incremento de los contadores y sus límites buscan
do encontrar una solución que mueva las luces a una velocidad adecuada y que a la vez no se las
vea parpadear.
Sin embargo, hay algo que hemos hecho que es fundamental, tener a la vez dos pines que están
mandando una señal PWM o lo que es lo mismo, una señal, (hasta cierto punto), analógica, pues
es algo fundamental para nuestros aparatos, porque, por ejemplo, para manejar el desplazamiento
de un robot tenemos que controlar la velocidad de giro de dos ruedas, la derecha y la izquierda y si
sólo tienes capacidad de manejar un pin como PWM, sólo podrás manejar electrónicamente la
velocidad de un motor, como ocurre con los coches de gasolina, y como ocurre en los coches
tienes que montar en el eje tractor un complicado elemento mecánico llamado diferencial, para
permitir que cada rueda gire a diferente velocidad.
Hacelo es posible, pero muy complejo para el taller de un aficionado, porque pasamos de circuitos
digitales en los que no se necesita hardware complejo a sistemas mecánicos bastante complicados.
Vean por ejemplo una diferencial construido con piezas de Meccano, la cantidad de engranajes y
piececitas que necesitas sólo para hacer este elemento mecánico
Y aun te falta otro complejo sistema para poder guiar el coche, como es la direccion de un
vehículo
Dos motores, sencillez mecánica
Sin embargo, si somos capaces de gobernar dos motores, colocamos uno en cada rueda, como
funcionan la mayoría de los coches eléctricos actuales, no se necesita diferencial, basta con enviar
diferente energía a cada rueda, para que cada una vaya a velocidad diferente, y tampoco
necesitamos la compleja dirección., Pues mientras que en un coche eléctrico, la orientación de las
ruedas delanteras, es la que fuerza la diferente velocidad de las traseras ruedas tractoras, en un
coche con dos motores es al revés, las ruedas tractoras fuerzan la dirección de las ruedas de
dirección y basta poner ruedas locas, para que sigan solas la trayectoria del vehículo. Hemos
sustituido el volante que gira unas ruedas por un aparato que deja pasar mas energía a una rueda
que a otra. El coche eléctrico con dos motores es mecánicamente de una sencillez espantosa.
Por esto todos los robots sencillos funcionan siempre con dos motores y una rueda loca, como
ocurre en el chasis que enseño, formado por dos ruedas paralelas, que moverán motores diferentes
y una rueda de “dirección”, que puede girar libremente al rededor de un eje vertical, de modo que
siga la ruta marcada por la diferente velocidad de giro de las ruedas tractoras.
Como es lógico, pese a las modestas prestaciones de la Tarjeta Arduino, esto no se podía pasar
por alto y Arduino Uno, tiene integradas, no dos, sino seis pines PWM de fábrica, que son
capaces de forma interna de generar y modular los impulsos de forma independiente de el
programa, de forma que los seis pueden funcionar incluso concurréntemente. Y eso es la modesta
tarjeta Arduino UNO otros modelos de Arduino tienen incluso más pines PWM.
Entre los modelos mas generalizados Arduino Uno, Mini y Nano, disponemos de 6 salidas
PWM de 8bits que dan un hasta 256 niveles diferentes de salida en los pines 3, 5, 6, 9, 10 y 11.,
pero Arduino Mega tiene 15 salidas PWM de 8bis de los pines 2 a 13 y 44 a 46 y Arduino Due
tiene 13 salidas PWM de 8bits en los pins 2 a 13 y dos salidas con resolución de 12bits (4096
niveles) .
Dejo para el siguiente post la explicación de como se manejan. Lo único que anticipo, es que
como ocurre con los pines digitales, cuando le mandas que envíen energía con un cierto nivel, la
mandan de forma continuada independientemente de lo que después haga el programa, porque de
generar las ondas PWM como tu solicitas, se encarga automáticamente los circuitos internos de la
tarjeta y lo harán en tanto, tu no des la orden de cesar, o cambiar el nivel de energía, que estas
mandando, Por tanto el sketch queda liberado para hacer otras cosas.
Repaso
Conocer la diferencia entre una pin PWM y uno realmente analógico. Comprender los problemas
que esta diferencia puede dar lugar en la realidad
Identificar en una Tarjeta Arduino cuales son los pin PWM. Conocer el mandato “analogWrite” y
su sintaxis. Controlar la energía que permitimos salir por un pin PWM
Material necesario
En el capítulo anterior del Curso de Arduino acabamos diciendo que existen en la Tarjeta
Arduino unos pines que emiten Pulso con Modulaxción, o en inglés “Pulse Width
Modulation”, (PWM), que son esas ondas rectangulares que indican que unas veces se permite la
salida a 5 voltios y otras a 0 voltios, que se utilizan para bien controlar la cantidad de energía que
se emite, o incluso para establecer sistemas de comunicación con otros equipos.
En este capítulo nos centraremos en el primer uso, es decir, como una forma de controlar la
energía que damos salida un pin, Como la energía se puede emitir entre nada a el máximo
posible de una forma gradual, a estos pines se les llama también “analógicos”, porque la energía
que en un lapso de tiempo puede dejarse salir, con bastante aproximación, a la intensidad que
deseemos incluso siguiendo una gráfica que evolucione poco a poco.
Posibles problemas
Debe de quedar claro, que esta denominación de “analógicos” no es del todo correcta, porque
no podemos emitir voltaje a 0,1 o a 3,7 voltios, sino que emitimos la energía que emitiéramos, si
todo el tiempo emitiéramos a esos voltajes, pero en realidad, estamos enviando pequeñas
“píldoras” de energia de corta duración, que entregamos a 5 voltios. Por tanto, si por ejemplo
queremos alimentar un equipo que funcione a 3, 5V por este sistema, corremos el riesgo de
quemarlo, porque la energía eléctrica que recibe llega a 5 voltios, aunque la reciba durante
pequeñas fracciones de tiempo ,como se ve en el gráfico, donde a una mayor cantidad de energía
enviada corresponde mas tiempo de voltaje a 5 voltios.
Otros problemas que pueden ocurrir, es que al ser una onda periódica, se acople con otro
elemento vibrante y de lugar a imprevistas vibraciones o ruidos, que podemos eliminar, con
solo variar un poco en mas o en menos el valor de “value” para que se desacoplen.
Por último, tener en cuenta lo que la constante conexión y desconexión, puede suponer en el
dispositivo alimentado. Si solo apretar un pulsador, crea corrientes parásitas, no indico lo que en
determinados casos, produce esas conexiones en motores, relés, o electroimanes. Se pueden
generar voltaje parásitos, que puede dañar la salida o el dispositivo o la tarjeta, por lo que es
necesario tomar las medidas pertinentes.
En cuanto a trabajar con transistores, en general, los de tipo BJT, o bipolar, que son muy
comunes, son apropiados para funcionar como amplificación de señales PWM, pero no lo son los
transistores MOS, o de efecto campo.
Sin embargo, y pese a estos problemas, los pin PWM valen para múltiples cosas como es
alimentar a un led, o hacer sonar un zumbador, etc etc, Los pines PWM se pueden utilizaren
muchos casos como si realmente fueran analógicos, pues generalmente el aparato receptor, posee
una inercia que hace que aparentemente trabaje de forma continua, pero con la recepción de
menos energía, cuando en realidad el aparato funciona a pulsos y la inercia hace que parezca
funcione en los momento en que debería dejar de funcionar.
Pues son algunos de los pines digitales, que con el correspondiente mandato pueden actuar como
pines PWM. Concretamente en la Tarjeta Arduino UNO, son los pines 3, 5, 6, 9, 10 y 11 que
como observarán en la imagen de la tarjeta, tiene impreso delante un carácter con forma de onda “
~ “ que indica que son pines con capacidad PWM como por otra parte, señala el texto en vertical
que acompaña a los pines digitales DIGITAL(PWM ~)
El mandato que los maneja es “analogWriten” que es muy parecido al mandato para manejar los
pines digitales “digitalWriten”, con la diferencia que en vez de ser posibles sólo dos niveles
“LOW” y “HIGH”, aquí hay 256 niveles posible de 0 al 255. Con 0 no se emite nada, igual que
con “LOW” y con 255 se emite igual que con “HIGH” mientras que con el resto de los valores
se mandan niveles intermedios de energía.
Donde
“analogWrite” es el mandato
“pin” es el numero de pin que vamos a utilizar
“value” es el nivel de energía entre 0 y 255 que queremos emitir
Hay que tener en cuenta las siguientes cosas, lo mas fundamental es que el pin tenga la posibilidad
de ser PWM, o sea, 3, 5, 6, 9, 10 y 11 en Arduino UNO pero otros valores en otras tarjetas
Arduino, “value” ha de ser un número positivo entre 0 y 255 en Arduino UNO pero hay tarjetas
de Arduino que permiten mas niveles, normalmente hasta 4.096
El numero de niveles de niveles posibles esta relacionado, como ya vimos en el caso anterior, con
la frecuencia de la onda que se emite, cuantos mas “picos” entren un una fracción de tiempo
determinado, mas “picos” podemos hacer planos, por tanto mas niveles de energía podemos
alcanzar, sin que se noten los “apagones”.
La Tarjeta Arduino UNO, (y la Mini y la Nano e incluso la Mega), es muy modesta y sólo
permite mandar ondas a una frecuencia relativamente baja de 490Hz para los pines 3, 9 10 y11,
mientras que para el 5 y 6 cuya frecuencia es de 980Hz. Con esta frecuencia lo mas que podemos
hacer, es dividir por la mitad, (mas o menos), por lo que nos tenemos que conformar con 256
pisos o sea, 8 bits, (2 elevado a 8)
En tarjetas mas potentes como Due. La señas PWM tiene mayor frecuencia al menos en algunos
de sus pines y admite en estos hasta 4096 niveles es decir, 12 bits. Sin embargo, no preocuparos
en exceso, en la mayoría de los proyectos, tendrás sobrado con 256 niveles y solo en proyectos
muy sofisticados, precisarás mas frecuencia, pero lo razonable es que para entonces, el problema
será que te faltarán pins y tendrás que comprar tarjetas mas poderosas, sobre todo porque
necesitaras mas pines.
Ejemplos de uso
Voy a repetir los ejemplos que en el capítulo anterior, solo que ahora, utilizando pines PWM,
Utilizaremos para ello los pines 9 y 10.
Hardware
El hardware será como siempre pero por otros pines, el 9 y el 10 con dos circuitos, cada uno con
un led y una resistencia de 220Ω
El problema a resolver es el mismo que hicimos en el capítulo anterior, comparar dos leds uno a
plena carga, que abriremos en modo digital y uno a media potencia, que por fuerza tenemos que
abrir como PWM.
El problema a resolver es el mismo que hicimos en el capítulo anterior, comparar dos leds uno a
plena carga, que abriremos en modo digital y uno a media potencia, que por fuerza tenemos que
abrir como PWM.
Si copiamos, compilamos y subimos el Sketch a la Tarjeta Arduino, veremos algo como lo que
mostré en el vídeo del capítulo anterior. La luz del led de la derecha, es mas tenue que la de la
izquierda.
Pueden hacer diferentes pruebas modificando el valor de “value”. Si en vez de 128 pone 64 se
verá aun mas la diferencia y si ponen 192 la diferencia es menor. Si ponen 0 el led aparecerá
apagado y si ponen 255 se verá como el led que actúa como pin digital en HIGH.
Fíjense que los pin PWM que solo funcionan de salida OUPUT pero no de INPUT por ello no
se declaran en la función “setup”. Si si se usan, solo hay una forma de hacerlo. En cambio
tenemos que declarar como OUTPUT el pin 9 porque siendo PWM lo utilizamos en este caso
como digital y como tal puede trabajar en INPUT o en OUPUT.
El utilizar un pin PWM como digital es un derrocha que debemos habitualmente evitar pues
estamos utilizando un recurso mas valioso y pudiera ser que en el futuro lo echaremos de menos.
De ser posible, deben utilizarse los pines menos valioso entre los disponibles, que lógicamente
sean adecuados para lo que queremos realizar con ellos, con el fin de no podar posibilidades
futuras. En este caso lo he utilizado, por utilizar el mismo hardware en distintos ejemplos.
Observen que finalizada la orden de emisión por el pin PWM, el pin emite de continuo de
forma autónoma e independientemente de lo que se haga a continuación en ese “loop” y
sucesivos, En este caso no se hace nada, pero podríamos hacer muchas cosas con la seguridad que
el pin emitirla como le hemos mandado hasta nueva orden.
Observarán también que la programación de pines PWM es mucho mas sencilla que generar
manualmente Ondas con Modulación. Por lo tanto de forma habitual preferiremos esta solución a
la manual. Mas aun pueden comparar lo sencillo que resulta conseguir que una luz suba y baje en
comparación a como era hacerlo de forma manual.
A modo de prueba cambie “pinled2” al valor 4 y modifiquen el harware para que el cable salga
del pin 4 que no es PWM. Observarán que la compilación no detecta el error pero el pin deja de
funcionar porque el pin4 no es PWM en una Tarjeta Arduino UNO por lo que lógicamente no
puede atender al mandato “analogWrite“. Les dejo una fotografías con los distintos niveles de
brillos que corresponen a distintos valores de “value”
Nivel 0 Nivel 127
Nivel 192 Nivel 255
A continuación vamos a hacer como hicimos en el capítulo anterior que la luz de un pin PWM
suba y baje
Pueden hacer diferentes pruebas no modificando el valor de los “delayMicroseconds” con lo que
aceleran y retrasan el parpadeo de la luz.
Como ven resulta mas sencillo que en el programa similar anterior, la luz sube y baja. El truco
nuevamente es utilizar dos contadores, una ascenderte y otro descendente. Solo hay que tantear un
poco los valores de partida y nacionalización de los contadores para que no repitan cosas ni se
sega el valor de “value” del rango comprendido entre 0 y 255.
Observen que aquí “setup” excepcionalmente no hace absolutamente nada, pero aun así, hay que
declararla, porque el programa interno de Arduino espera encontrarla.
Como son muy sencillos he escrito parte de los “if” en una sola linea. Se puede usar este medio, o
no, según resulte cómodo y quede legible el programa para cualquiera que lo lea.
He puesto “delayMicroseconds”, en primer lugar porque siendo nuevo conviene ejercitar un poco
y además, porque al manejar una cifra mayor, permite a hacer los ajustes de velocidad con mayor
finura que el “delay” normal con el fin de poder frenar un poco la velocidad del “loop” y que la
subida y bajada se realice a una velocidad razonable.
Tienen que tener en cuenta que int solo vale para definir números comprendidos entre el rango de
-32,768 to 32,767, por tanto pausa se encuentra cerca del límite . Este límite fien limitado a que
para guardar el valor utiliza 16 bits, uno que indica el signo y otros 15 para guardar el número en
base 2. Si tuviérramos que guardar un número mas grande pode riamos definir la variable como
“long” en u cuyo caso utilizaremos 32 bits pra guardar el valor, lo que permite guardar valores
comprendidos entre -2,147,483,648 y 2,147,483,647.
Hagamos ahora el programa que permite que una luz suba mientras la otra baja. Solo tendremos
que intercalar en el programa anterior dos instrucciones y retocar los “delayMicroseconds” hasta
llegar a tener una velocidad convenientes final.
/* Sketch E7.14 Luz de dos leds uno suben y otro bajan con PWM
* Contadores j yk a cero
* Si j 0 led1 emite a (255-k) y led2 a “k”
* k = k -1
* Si (k == 0) j = 0
* Repetir el ciclo
*/
// Área de definición de variables y parámetros
int pinled1 = 9;
int pinled2 = 10;
int j = 0 ; // contador de la bajada
int k= 0 ; // contador de las subidas
int pausa = 30000 ;
// Función setup
void setup() { }
// Función loop
void loop() {
// si (j <255) baja la luz poco a poco
if (j < 255) { analogWrite(pinled1, j); analogWrite(pinled2, (255 -j)); j = j +1 ;
delayMicroseconds(pausa) ; // frena el loop } if (j==255) { j = 256 ; k= 256 ; } if (k>0) {
analogWrite(pinled1, (256- k)) ;
analogWrite(pinled2, k -1) ;
k = k -1 ;
delayMicroseconds (pausa) ; // frena el loop
}
if (k==1) { j = 0 ; } //
} // fin función loop
Queda patente la sencillez que supone el manejo de pines PWM, como indicamos este programa,
es exactamente el anterior con tres líneas nuevas, la relacionar de la variable “pinled1” y dos
lineas con mandados “analogWrite” que gobierne la energía que se manda a este led.
Observarán que el manejo de pins PWM no platea especiales problemas una vez que se ha
comprendido bien que es lo que hacen los led PWM y cómo lo hacen.
Repaso
Vamos a repetir los mismos ejercicios que hemos hecho con los pines digitales en OUPUT, pero
en este cosa utilizando pin es PWM
=================================================================
Puede encontrar resuelto este ejercicio en:
1º Ejercicio de uso de pines PWM – Simular un faro y qué es una “función”
=================================================================
Para una maqueta nos proponemos hacer un faro que luzca con la misma cadencia del faro
existente en la Ria de Ribadeo
Datos
En la página de Protección civil encontrara los destellos características de cada faro. Viene en la
última columna y hay que saber interpretarlo Según el tipo de juego que proporcione la señal,
podremos encontrar Grupos de destellos (GpD), que agrupa varios destellos y ocultaciones a un
ritmo determinado entre sí, el Destello único (D), que se repite en todo el ciclo), Ocultaciones
(Oc) y Grupo de ocultaciones (GpOc), donde los períodos de oscuridad son más frecuentes o
duraderos que los de luz), o, simplemente, Luz fija (F). Luego viene un letra que es el color del
faro generalmente “blanca” (B) pero a veces “verde” (V) o “roja” (R) y por último la duración
del ciclo en segundos seguido de una s (20s)
Nos proponemos simular el faro situado de la Ria de Ribadeo, que tiene el siguiente ciclo
=================================================================
Puede encontrar resuelto este ejercicio en:
2º Ejercicio de uso de pines digitales de entrada INPUT – Semáforo utilizando “if”
=================================================================
2 – Luces de emergencia
Ejercicio 2 – Simular un semáforo que regula el paso en un túnel.
1º.- En un extremos se acaba de poner la luz en verde mientras que en el otro extremo está en
rojo. Así se mantiene 25 segundos.
2º.- Para estimular el paso de los últimos coches, el verde se pone parpadeante cinco veces con
periodos de encendido y apagados de un segundo. o sea esta así 10 segundos más, mientras que
el otro extremo esta en rojo
3º.- El semáforo se pone en rojo en un extremo, pero para dar tiempo a que salgan los coches que
estuvieran dentro del túnel el otro extremo también continua en rojo durante otros 10 segundos
Se repite el proceso, pero en este caso el es otro extremo el que se pone en verde y el inicial
continúa en rojo.
Félix Maocho
19/2/2017
.
Enunciado
Para una maqueta nos proponemos hacer un faro que luzca con la misma cadencia del faro
existente en la Ria de Ribadeo cuyo ciclo de funcionamiento es como se indica a continuación:
Material necesario
Tarjeta Arduino
Tarjeta “protoboard”
2 Cables (preferiblemente uno gris y uno rojo
Resistencia de 220 Ω
Led (preferible de color blanco)
Simular el faro de la ria de Ribadeo
Hardware
La única diferencia que vanos a hacer es iniciar el circuito en un led PWM en ves de un digital. En
este caso utilizaremos el del 9.
Software
Simplemente vamos a cambiar en el programa inicial el valor del pin de salida, que ahora va a
ser el 9, eliminar del “setup” la declaración del pin como OUPUT, porque los pin PWM no lo
necesitan y cambiar el mandato “digitalWrite” por el mandato “analogWriter” al nivel máximo
o sea 255. o 0 para apagar
void setup() { }
void loop() {
// 1º Tres destellos de 5 décimas seguidos de apagado 3 décimas
// **** 1 destello
analogWrite(pinblanco, 255);
delay(tiempo1);
analogWrite(pinblanco, 0);
delay(tiempo2);
// **** 2 destello
analogWrite(pinblanco, 255);
delay(tiempo1);
analogWrite(pinblanco, 0);
delay(tiempo2);
// **** 3 destello
analogWrite(pinblanco, 255);
delay(tiempo1);
analogWrite(pinblanco, 0);
delay(tiempo2);
// 2º Mantener apagado 6 décimas de segundo (600 ms) ******
delay(tiempo3);
// 3º Destello de 10 décimas de segundos (1000 ms) **********
analogWrite(pinblanco, 255);
delay(tiempo4);
// 4º Apagado 16 segundo (16000 ms) **********************
analogWrite(pinblanco, 0);
delay(tiempo4);
// Repetir el ciclo *******************************************
}
Simulación
Funciones
Como ven, la cosa ha sido demasiado sencilla, Así que voy a aprovechar para enseñar una cosa
nueva, el uso de funciones..
Una función es una agrupación de mandatos que se efectúan siempre en el mismo orden. Tanto
“setup” como “loop” son dos funciones del sistema, El sistema sabe que primero ejecuta una
sola vez “setup” y a continuación se repite indefinidamente “loop”,
Estas funciones son de lo mas sencillo, pues no necesitan ni parámetros de entrada, o valores que
precisan conocer las funciones para efectuar su trabajo, ni devuelven ningún valor o parámetro de
salida., Simplemente cuando se inician ejecutan los mandatos que tiene en le interior de las llaves
{… } y no calculan ningún valor que haya que devover, pero ello se denominan vaciás, “void” y
en la zona donde se depositan los parámetros de entrada tampoco hay nada “()” Ese sentido
exactamente tienen las expresiones “void setup () ” y “void loop()” que no devuelven nada y que
no necesitan ningún parámetro de entrada.
Estas son dos funciones del sistema, pero podemos construir nuestras propias funciones, que
utilicen, o no, parámetros de entrada y que devuelvan, o no algún valor. La sintaxis de una función
es como sigue:
Donde
“tipo” ó “void”, es el tipo del valor que devuelve la funcion de entre todos plos posinbles. (init,
long, bite,…), sólo se permite salir un unico valor, si deseamos sacr varios lo sacaremos en un
“string” de varios elementos en el que cada valor que deseamos sacar ocupa una posicion
determinada
“nombreDeLaFuncion” nombre que damos a á función. tal cual con mayúsculas y minúsculas y
que no sea nombre reservado del sistema (por ejemplo “setup” “loop” o nombres de mandatos
como “delay”, “int”, “if”, etc
“tipo parentrada1“ tipo y nombre que se usará internamente en lq funcion con el parámetro que
se introduzca mos en primer lugar. Se pueden introducir varios parámetros de igual forma
separándolos con una, dentro del mismo paréntesis (…).
Las llaves “{….}”, limitan los mandatos sobre los que actúa la función. Dentro de la función hay
que definir necesariamente las variables que se utilicen entre los paréntesis diferentes de los
parámetros de entrada, incluidas si se precisa la variable que hemos llamado “parsalida” que
puede tener cualquier nombre De existir un parámetro de salida entrada la última linea del
programa será “return(parsalida);” , o sea el mandato que manda salir fuera de la funcion el
valor del para metro de salida. Si la función no devuelve nada, esta linea se omite.
Ejemplo de función
Como sé que todo lo explicado, es un poco confuso, creo que lo mejor es poner una ejemplo
cuanto antes. Definamos una función que vamos a llamar “destelloPWM” que lo que va a hacer
es mandar salir por un determinado pin, un destello de determinados microsegundos de
duración. Según eso la función será como sigue
Hemos hecho una función que una vez probada funcionará sea cual sea el pin PWM que deseemos
manejar, la duración que queremos de la ráfaga e incluso la intensidad que deseamos que tenga la
luz.
Pues bien hecho esto volvamos a nuestro programa anterior y utilicemos la funcion
Como van a ver el la simulación, el programa funciona exactamente ifual al arrancar el programa
empieza a emitir el “faro de Ribadeo” lanzando sus tres destello yseguido del mas largo y un
silencio. Para que se vea como trabaja la función pongo el programa en “Animate”, (la barra
azul), y en “Slow Motion”, (cámara lenta), para que se vea que cada vez que se invoca a la
funcion el prgrama baja al Área de definición de las funciones y recorre la función.
Observen como se invoca una función sin respuesta, (es una función “void”)
Directamente se nombra la funcion y seguido se abre paréntesis y se colocan los parámetros que
alimentan a la funcion uno tras otro, separados por comas.
Como ven la forma de definir la funcion,, aparte de documentarlo un poco, (algo de buena
educación hacia los demás y para uno mismo), de modo que explique que se pretende que haga la
función, la función en si. consiste en una cabecera, que indica el tipo del el parámetro de salida,
(si existe) o “void! si no existe, el nombre de la función y entre paréntesis, “(….)”, los tipos y
nombres de los parámetros de entrada que se utilizan dentro de la función, A continación se abre
las llaves “{” y se declaran las variables locales, o variables que sólo tiene existencia dentro de
la función. Es decir de coincidir su nombre con otra que este ela función “loop” u otra variable la
máquina las reconoce como diferentes, una con un valor fuera de la función y otra con el valor que
corresponda dentro de la función. Luego viene los mandatos que hacen lo que se pretende que
haga la función y por último, de efectuar la función un cálculo, este valor se “saca”· fuera de la
función con el mandato “return”. Como en nuestro caso la funcion no hace ningún calculo, es
una función “void”, se omite esta sentencia.
*/ Nombre de sketch
* descripción de su funcionamiento si no tiene repuesta
*/
// Área de definición de variables
// definicion del tipo y nombre de la variables // uso que las damos
void setup () ¨{…………}
void loop () {…………..}
// ´´Area de definición de funciones
* descripción de las funciones y sus mandatos
La ventaja de utilizar funciones cuando la misma rutina se utiliza varias veces en el mismo sketch,
como ocurre en este caso es evidente. Con ponerlo a punto en un solo lugar, tiene a punto su
funcionamiento en diversos puntos. Por otra parte da claridad al programa pues dejan claro lo que
hacen una colección de mandatos que a veces no se sabe bien que hacen de un primer vistazo.
Ademas vamos crean do con el s uso una librería de rutinas que ya están probadas, Por tanto si en
otro programa vamos a utilizar ráfagas de luz desde un pin PWM, ya la tenemos programadas y
probadas, por tanto si somos veteranos y tenemos una extensa librería de funciones, adquirimos
una alta velocidad de programación junto con una alta fiabilidad.
Por otra parte permite dividir un sckech complejo en diversos módulos independientes que actuan
como cajas negras, se les entrega unos parámetros, hace unas cosas y da un parámetro de salida,
esto tiene la ventaja de permitir dividir un proceso complejo 4en otrosd msas sencillos que
podermos depurar más fácilmente,
La importancia de este tema que hemos introducido aquí un poco a contrapelo, es tan grande que a
partir de este momento lo iremos incluyendo en nuestro curso en todos los ejemplos.
Ejercicio 2 – Simular un semáforo que regula el paso en un túnel
Félix Maocho
28/2/2017
Enunciado
Para una maqueta deseamos simular un semáforo que regule el paso en un corto túnel
que no permite el cruce de dos vehículos, no hay el riesgo que los vehículos choquen,
porque desde un extremo se ve la salida, por tanto si hay o no un coche en su interior,
pero para regular bien el trafico se desea lo siguiente
1º.- En un extremos se acaba de poner la luz en verde mientras que en el otro extremo
está en rojo. Así se mantiene 25 segundos.
2º.- Para estimular el paso de los últimos coches, el verde se pone parpadeante cinco
veces con periodos de encendido y apagados de un segundo. o sea esta así 10 segundos
más, mientras que el otro extremo esta en rojo<
3º.- El semáforo se pone en rojo en un extremo, pero para dar tiempo a que salgan los
coches que estuvieran dentro del túnel el otro extremo también continua en rojo durante
otros 10 segundos
Se repite el proceso, pero en este caso el es otro extremo el que se pone en verde y el
inicial continúa en rojo. Todos los pines utilizados seran PWM
Material necesario
Hardware
Aunque en la imagen se vean transparentes esos leds son de color verde. Tenemos unidos a los
pines 6 y 10 leds verdes y a los pines 9 y 11 afules los ines 6 y 9 alimentan el semáforo de un lado
y el 10 y el 11 el del otro lado , cada circuito está protegido por una resistencia de 220 Ω como es
habitual, Todos los pines utilizados pon PWM como eexigía el enunciado del problema
Software
Como ello añadiría muy poco a lo que sabemos prefiero utilizar las “funciones” con el
fin de ir viendo no sólo como se usan sino como se platea la resolución de un sketch.
Como dijimos las funciones permiten solucionar un sketch que se ve como muy
complejo en varias funciones que en principio parecen mas sencillas, probar cada una
por separado y montarlas finalmente. Veamos como se establece el proceso.
Observen que lo que hemos hecho en este paso es dividir un problema al cual no sabemos como le
“hincaremos el diente” en dos problemas mas sencillos, que ademas deben ser muy similares o
simétricos.
Observen también que aun no hemos definido nada, salvo declarar los parámetros de los pines que
el hardwware nos dice que vamos a utilizar y “bautizado” las dos funciones en que hemos dividido
el sketch, que de momento pensamos que no van a tener parámetros de entrada ni de salida,
aunque esto no es definitivo.
Si lo compilan y aconsejo que se haga en el simulador UnoArduSim verán que no da error (salvo
que hayamos olvidado o algo o cometido una falta de ortografía, aunque naturalmente aun no hace
nada,. Como es muy sencillo todos los errores de dactilografía que hayamos cometido los
encontraremos muy facilmente y sera muy sencillo subsanarlos. Por otra parte estamos escribiendo
un seudocódigo que cualquiera puede entender perfectamente
La ventaja es que si desarrollamos una función pero no tocamos nada más, los errores que
detectemos, estarán en este función en concreto no en otro lado.
Sin embargo, encender dos determinados semáforos o apagarlos es bastante inmediato, aunque no
tanto hacer parpadear el semáforo. Podíamos decidir si lo que es sencillo lo hacemos en la misma
función o lo sacarlo fuera. Yo me he decidido sacarlo fuera, porque esto de encender y apagar dos
semáforos lo vamos a hacer en muchas partes del programa. Por ejemplo la función un poco mas
abajo, “sinCirculacion” volverá a utilizar la rutina de encender y apagar dos semáforos.
Quiero que se fijen en la función “parpadearSemaforo”, para ejecutarla hemos hecho uso de una
función que ya conocemos, “destelloPWM”, pues la realizamos en ejercicio anterior, Esta es una
de las ventajas del uso de funciones, la posibilidad de “reciclar” elementos de código ya
finalizados y probados en nuevos sketch. La ventaja es obvia por un lado ya esta perfectamente
escrito y por otro está probado que funciona. Tener una amplia librea de rutinas habituales ahora
mucho tiempo de programación y da gran fiabilidad a los sketch que escribamos. Observen que la
función la estamos utilizando para dos cosas aparentemente contradictorias, encender y apagar
una luz para hacer la intermitencia.
Mandato “for”
La condición en nuestro caso es esta (int i=0; i<veces; i++) que quiere decir:
“int i = 0; “ – definimos dentro del mandato “for” un contador llamado “i” Que sera un contador
con el valor inicial “0”
“i <veces; ” – mientras “i” sea inferior a “veces” que tiene el valor “5”, que en este caso hemos
pasado por parámetro de entrada, se ejecuta lo que hay entre las llaves { … }.
“i++” – es la forma de sumar “1” a “i”al finalizar de hacer lo que haya entre llaves. O sea lo mismo
que escribir i=i+1
Lo que “for” hace es crear dentro del bucle cono “loop”, un pequeño bucle que contiene los
mandatos o funciones indicados por las llaves, que se ejecutarán, que se repetirá en tanto se
cumpla la condición que gobierna el “for”. En nuestro caso que “i” valga menos de 5. Por tanto si
“i” es menor que 5, que va ser lo que valga “veces”, apagara, esperará y encenderá el pin
indicado, haciendo la intermitencia tantas veces y en la cadencia que indican los parámetros de
entrada. Al final “i” pasará a valer un dígito mas, llega al valor 5 y como ya no se cumple que
“(i<5)” y se deja de hacer el bucle.
El mandato “for” es tan importante, que volveremos en ella en múltiples ocasiones. Poco a poco,
ira adquiriendo destreza en su uso. Este mandato es fundamental cuando deseamos repetir una
misma acción un numero indeterminado a priori de veces. Supongamos que deseamos hacer andar
un robot hasta llegar a una pared, el telémetro dirá a que distancia está la pared y en función de eso
el mandato “for” dará los pasos que convenga.
Solo nos basta compilar y la prueba final. La cosa ya funciona como lo previsto, unicvamete yo
prolongaría el tiempo en que ambos semáforos están en rojo, que me parece un poco corto. Como
el programa estáa suficientemente parametrizado, basta cambiar el valor de “timpo3” a otro valor
mayor h y probar hasta que encontremos un valor a nuestro gusto.
Como puede observe si un extremo del túnel está en verde el opuesto está en rojo, en un momento
determinado el semáforo verde parpadea 5 veces y se pone en rojo estando cerrados los dos
extremos del túnel . A continuación se abre la circulación en la otra dirección.
Voy a cambiar un poco el sketch para poner un “delay” en el mandato “for”, de modo que haga
una pequeña parada que nos permita ver los distintos valores que toma “i” antes de alcanzar el
valor 5 y salir del mandato “for” el programa pasa con las opciones “Animate” y “SlowMotion”
activadas para que se vea mejor el funcionamiento, Cuando la luz verde comienza a parpadear el
sketch ha entrado en el mandato “for”.
Cuando la “i” adquiere el valor 5 se acaba el mandato “for” porque deja de cumplirse la condición
de se produzca el bucle “(i>5)”
Identificar en una Tarjeta Arduino cuales son las entradas analóguicas. Comprender en qué
consisten y para qué valen. Entender el funcionamiento de los sensores, qué es su rango de
funcionamiento, la precision que ofrecen y el tiempo preciso mínimo para efectuar dos lecturas
consecutivas de un sensor.
Material necesario
Saber que son los pines digitales y como funcionan tanto en OUPUT como en Input, Saber que
son los pimes PWM o pines “analogicos” de salida Tener nocion de los que supone una entrada
analógica..
Al igual que hay salidas analógicas, mediante los pin PWM, tiene que haber entradas analógicas
y en efecto, hay en un Arduino UNO seis entradas analógicas, marcadas de A0 a A5, se
encuentran situadas en el lado puesto a los pines digitales de 0 a 13 que hemos estado utilizando
habitualmente, junto las salidas de fuerza o POWER que también hemos utilizado el pin V5 los
pines GND etc.
Las entradas analógicas son pues entradas que admiten recibir voltajes comprendidos entre
los 0 voltios y los 5 voltios y se utilizan principalmente para leer las medidas que diferentes
sensores realizan sobre la realidad física.
Pues todos los que puedas pensar que existan. En una lista que no pretende ser exclusiva tengo
localizados los siguientes.
Pulsadores o sensores
de contacto que suelen ser no analógicos sino digitales, hay contacto o no
Sensor de sonido, que miden el nivel de ruido audible
Sensor de ultrasonidos, que miden el nivel de ruido no audible
Sensor de Temperatura, o termómetros
Sensores de humedad o higrómetros
Sensores barométricos o de presión
Sensores de lluvia
Sensor de gas y de humo
Inclinómetro o sensor de inclinación
Giroscopios y acelerómetros Miden cambios de dirección y de velocidad
Sensores de magnetismo o magnetómetros
Sensores RFID o de etiquetas
Sensor de impacto
Sensor laser y fotosensores
Sensores de campo magnético
Sensor de distancia
Sensor de voz
GPS
Y como digo, no es mas que una lista de sensores que se venden en el mercado a precios reducidos
y por tanto al alcance de los aficionados de Arduino, pero no es ni mucho menos exhaustiva. Por
ejemplo, hoy mismo me he enterado de un sensor de chispas eléctricas que puede detectar rayos
que caen a 20 km de distancia.
En casi todos e los casos, los sensores tiene tres cables uno que le alimenta con energía a un
voltaje alto, lo habitual si se han pensado para Arduino, es es a 5 voltios, a veces es a 3,3 voltios,
y otras veces a otros el voltajes, como 9 o 12 voltios. Otro cable se conecta tierra, (GND), es decir
a 0 voltios. y un tercer cable que acaba en alguno de los pines analógicos de entrada, que porta
un voltaje proporcional a la medida que obtiene el sensor. Si por ejemplo, el sensor es un
termómetro médico, 43ºC dará una señal de 5 voltios y 34ºC dará una señal de 0 volts mientras
que un voltaje de 3 voltios se corresponderá con algo de fiebre y uno de 4 voltios con mucha
fiebre.
Si el sensor funciona con 3,3 voltios el montaje será igual pero alimentando a el sensor a 3,3
voltios en vez que a 5 voltios y muy probablemente la salida analógica no sera superior a 3,3
voltios,por lo que si no hacemos nada, funcionará bien, pero estamos desperdiciando la parte de
los voltajes entre 3,5 u 5 voltios, por lo que en la practica perdemos precisión en la lectura.
Lo que están viendo es el montaje tradicional de cualquier sensor, el cable rojo une la salida de 5
voltios, (o de 3,3 v, según convenga), a una pata del sensor. El cable azul conecta otra de las
patas con tierra (GND) y por último, el cable amarillo va a parar a una entrada analógica, (en
este caso a la entrada A0), que que es la que, analizando el voltaje leído, nos permite saber el valor
que ha medido el sensor. En este caso concreto se representa el sensor de temperatura, M35 que
vale más o menos 1 euro, y que es un sensor con una precisión de 0.5 ºC y una sensibilidad de 10
mV/ºC. Es decir que por cada ºC de temperatura de diferencia produce un cambio de voltaje de 10
micro voltios.
Como ven en el esquema del sensor viene claramente marcada la pata que va a 5V, la pata que va
a GND (tierra) y la pata de salida (OUT). Este sensor es muy sufrido, pues su manual indica que
puede ser alimentado entre 4 y 20 Voltios, algo que viene muy bien, porque las baterías tienen un
voltaje decreciente a medida que se van descargando y por tanto, podemos alimentar este sensor
con una batería de 9 voltios, e incluso despistarnos y dejar que baje hasta 4 voltios. Lo ideal es
alimentar un sensor de este tipo a los 5 voltios y no obligar al sensor a rectificar la alimentación,
pero no siempre es posible.
Ee intervalo de lectura, dice el manual que va de los 2ºC a los 150ºC, eso indica que no es sensor
adecuado para un invernadero, donde podemos medir en las noches de invierno hasta
-10ºC,pero que en cambio si es muy adecuado para controlar la destilación de vino, pues el
alcohol destila a hacia los 70ºC y el agua a los 100ºC. Con esto quiero resaltar, que no hay un
sensor universal que valga para todo, sino que para cada proyecto, tendremos que buscar el más
adecuado de acuerdo con lo que queremos controlar, lo que si puedo (casi) asegurar es que le
encotyrarán en el mercado y se asombrarán de lo poco que vale (salvo excepciones) .
Este sensor indica que cada grado se corresponde a 0,01 voltios, y como lo máximo que leemos es
1023 y eso se corresponde a 5 voltios por una regla de tres compuesta podemos saber que
O lo que es lo mismo
0ºC, (si los midiera, que no puede pues su rango termina en 2), corresponderá a una lectura de 0
voltios, 2ºC corresponde a un valor leído de 4,092 pero como solo leemos números enteros sera lo
que leemos 4 y 150ºC, lo mas que registra el termómetro, será de 306,9, o sea 307.
Como ven, con Arduino UNO perdemos bastante de la precisión que podíamos obtener del
aparato, pues no podemos aprovechar lecturas por debajo de 4 y superiores a 307, o sea lo mas que
podemos apreciar en el rango que funciona el sensor son diferencias de 0,5º aproximadamente,
algo que puede ser suficiente para la mayoría de las cosas que deseemos hacer, pero no para todas.
Por ejemplo, el M35 es un sensor mas que suficiente, para vigilar una incubadora de huevos de
gallina, pues en este caso, andamos por el entorno de los 40 ºC y donde una diferencia menor
que medio grado, no tiene especial significado, pero si queremos estudiar la variación del
punto de congelación del agua, en función de la salinidad, no nos valdrá por dos motivos,
hablamos de temperaturas que rondan los 0º. algo que se sale de el intervalo de este sensor,
pero ademas donde una diferencia mínima apreciable de 0,5ºC es inadmisible en experimentos
de ese tipo donde por fuerza necesitamos poder medir hasta las centésimas de grado.
.
Montaje para un sensor de mayor voltaje de salida
Si el sensor genera voltajes de más de cinco voltios, (para Arduino UNO), por ejemplo puede dar
salida a voltajes de 0 a 12 voltios haremos un montaje tal como se indica a continuación.
.
El problema, es que con ello cerramos en parte el abanico de posibilidades de medición y la finura
que se obtiene con este tipo de sensores se pierde por la incapacidad de Arduino de recibir esos
voltajes tan altos.
Repito estamos en una descripción general de las lecturas analógicas, no se preocupen mucho si
no entienden todo al detalle, pues tendremos tiempo de volver a ello, dentro de poco todo serán
sensores y actuadores en nuestro sketch.
Parecido a esto que hemos contado para las temperaturas, se aplica a las señales de sensores que
miden si hay mucha o poco luz, (fotómetros), o poca o mucha distancia, (telémetros). Arduino
recibirá por una entrada analógica, (entre las pin A0 a la A5), un voltaje que tendremos por
programa que identificar que significa y una vez “traducido”, según suponga o no un riesgo para
nuestro invento, establecer que medidas hay que tomar en los actuadores para realizar las acciones
correctoras correspondientes.
Los sueños
Por ejemplo, puedes hacer un reloj flexible, como el que ideó Dalí, que con sus sensores analicen
tu tensión arterial, y cuando te aburres y la tensión baja, hagan que el reloj adelante, de forma
que las horas de aburrimiento pasan mas deprisa, pero cuando los sensores detectan que la tensión
sube y estas mas activo, por ejemplo porque estas con la persona amada, frene las agujas y las
horas pasen mucho más despacio. ¿A quien no le apetecería tener un reloj así?
Espero que con este ejemplo te hayas dado cuenta del potencial que tiene Arduino, y de por qué
sólo nuestra falta de imaginación, puede hacer que no hagamos aparatos prodigiosos, que realizan
cosas que sólo podíamos pensar que existieran en los sueños.
La realidad
La lectura de una entrada analógico nos permite obtener una magnitud que puede variar dentro de
dos valores una máximo y otro mínimo que llamamos intervalo. Por ejemplo, si leemos 75 en el
caso anterior, el sensor ha medido es un valor que mas o menos anda por 36,5ºC es decir no
tenemos fiebre pero si le 82 tenemos aproximadamente 40ºC es decir una fiebre apreciable y habrá
que tomar medidas como rociarnos con agua fresca o llamar a una ambulancia, lo que decidamos.
Observen la diferencia fundamental con las entradas digitales, un voltaje, tanto 75 como 80
corresponde a voltajes que no llegan a 3,5 voltios por tanto en un caso como en otro un pin
digital nos habría dado de respuesta “LOW” y habríamos pensado que la temperatura era normal.
En muchos casos, las medidas son, si o no, por ejemplo. ¿Está encendida la luz? Basta con
contestar si o no y estaremos perfectamente informados de la realidad exterior, pero en la
mayoría de los casos ese nivel es excesivamente grueso y no nos vale, , Si pregunto, ¿qué tal
día hace?, no me basta que digan hace frío o calor, quiero que me digan hace 18 ºC a la
sombra. Esto solo lo hace una entrada analógica.
Sin embargo, solo hemos variado el grueso de la contestación, porque si yo quiero saber el frío
que voy a pasar en la calle para decidir si llevo abrigo o no, saber que hace 18ºC es suficiente.
Pero si estoy tratando de obtener el cultivo de una bacteria, la respuesta que necesito es no solo los
grados de temperatura, sino las décima, No me vale una respuesta que diga 36º o 37º, sino que
necesito una precisión mayor, por ejemplo 36,54ºC.
Esto hace que el número de sensores sea inagotable, porque en función de lo que queramos
saber, tanto el intervalo en donde empieza y acaba de leer como el número de divisiones que tiene
internamente el intervalo varía muchísimo. Como hemos visto Arduino UNO da un intervalo
dividido en 1024 peldaños, que en la mayoría de los casos son mas que suficientes, (aunque
rara vez aprovechemos todos), pero hay quien necesita que el intervalo esté dividido en más
peldaños.
Así que a la hora elegir sensor, deberemos tener claro cual es el intervalo de medidas que
necesitamos y la “finura de grano” que necesitamos en la lectura. Volviendo a los
termómetros, no es lo mismo un termómetro clínico, que uno meteorológico, o un termómetro
para controlar la fundición del acero. Igual pasa con cualquier otro sensor, las medida de
distancia que precisas para un automóvil en carretera, nada tiene que ver con las medidas que
necesitamos en cristalografía microscópica, ni por supuesto, con las distancias que medimos
para saber a cuanto están las estrellas, donde unos cuantos días luz de más o menos, pierden
absolutamente la importancia, cuando el Sol está a solo 20 minutos luz.
Tranquilos, no se pongan nerviosos porque de estos conceptos volverán a vernos una y otra vez, y
nos vamos a tropezar con ellos constantemente, tan solo recuerden que hay unas cosas que
caracterizan a los sensores que utilicen, los voltajes máximos a los que trabajan, le medida
máxima y mínima que calculan, que marca el intervalo de trabajo, la “finura de medida”
que podemos obtener con ese sensor. Y en muchos caso la separación de tiempo entre dos
lecturas consecutivas
Sin embargo visto desde Arduino, mida el sensor lo que mida, siempre se ve igual, a cuanto
voltaje lleva la medida que me da el sensor y que “peldaño” adjudico a ese voltaje el traducir
eso a valores habituales y el realizar las acciones consecuencia de esas lecturas, es trabajo tuyo
como programador.
Es importante entender que lo real, es siempre analógico, pero la medida que damos, es
siempre digital, con mas o menos precisión. Un metro de costurera de tela mide como mínimo
milímetros, si comparamos la longitud de la circunferencia con el diámetro utilizando el metro,
nos saldrá que π es 3,14 aunque sabemos perfectamente que π tiene un número inconmensurable
de decimales. Por tanto siempre que damos una medida, por precisa que sea, es siempre una
abstracción matemática y digital de algo que es analógico y que por fuerza, se diga o no se
diga, tiene una determinada precisión. π es real y por tanto analógico, cualquier valor que
demos de π es digital y esta por fuerza sujeto a un cierto margen de error,
Por tanto otra característica de cualquier sensor es su margen de error, Cada modelo de sensor
tiene su margen de error y nos valdrá o no para nuestro objetivo si el margen de error es
suficientemente pequeños como que dos valores contiguos, no genere como consecuencia
acciones diferentes de los actuadores.
Sin embargo la precisión viene marcada por dos factores, lo “fino” de la lectura del sensor y el
número de niveles que puede dar la Tarjeta Arduino. La tarjetas mas habituales como Arduino
Uno, Mini Pro, y Mega, se dispone de 10 bites en las entradas analógicas lo que proporciona
1024 niveles digitales, es decir un numero diferente por cada 2,44 mili voltio. Arduino Due tiene
una resolución de 12bits, 4096 niveles digitales, lo que supone una precisión de 0,61 mV
Sin embargo esto dice poco porque ¿Cuantos grados de temperatura supone una lectura de
625 y cuantos grados de temperatura supone una lectura de 626?
Pues dependerá primero del intervalo, si el termómetro mide entre 44ºC y 35ºC o sea 9 grados de
temperatura y la maquina produce 1024 peldaños podemos obtener la temperatura con
milésimas de grado sin gran dificultad, (siempre que el termómetro sea capaz de medir con
milésimas de precisión), pero si el termómetro solo mide con décimas, que es lo normal, aunque
teóricamente las lecturas de 625 y 626 sea diferentes, están dando la misma temperatura porque
nuestro sensor no da más de si.
Hay otro concepto que es también muy importante y hay que tener en cuenta, y es lo que tarda un
sensor en dar una nueva lectura. Si no acordamos del termómetro clínico de mercurio, para
tomar dos lecturas seguidos, había que agitar el termómetro en el aire con dos intenciones, dejar
que el aire enfrié de nuevo el termómetro y hacer bajar la columna de mercurio a su primitiva
posición. Solo cuando eso se ha conseguido se puede hacer una nueva lectura. En los
termómetros digitales actuales, el proceso es mas rápido pero aun así, el termómetro se ha de
preparar de alguna forma antes de hacer la dos lecturas consecutivas, pues si no la lectura anterior
puede interferir en la siguiente. Eso pasa en todo los sensores, cada lectura provoca una cierta
inercia que influye en la siguiente y solo dos lecturas consecutivas, si son validadas si entre ellas
hay un cierto tiempo de separación,
Si en un sketch de Arduino mandamos hacer dos lecturas mas rápidas que el tiempo de
preparación entre ellas obtendremos lecturas no fiables, conviene que esté especificado en el
sensor a la frecuencia mínima de lecturas y que en el sketch separemos las lecturas como mínimo
lo que diga esa cifra.
Por hoy creo que ya hemos dado bastante teoría. Dejamos para el siguiente capitulo el manejo de
los pines analógicos de INPUT.
Repaso
Cuales son los pines analógicos de entrada y donde están situados en la Tarjeta Arduino UNO
Qué son y para qué se usan las entradas analógicas
Que son los sensores, que hacen y como se comunican con la Tarjeta Arduino.
Cómo funciona los sensores y cfomo se montan los circuitos con sensores
Cómo se deduce el valor de la medida realizada por el sensor de la lectura de la entrada
analógica.
Qué es el intervalo de un sensor y que es la precisión de un sensor
Cómo influye en la precisión de un sensor las limitaciones de la Tarjeta Arduino.
Cómo se realiza el montaje de un sensor con salida superior a 5 voltios.
Que es lo que hacen el 90% de los sketch de Arduino
Cual es la diferencia entre automática y robóticas y los automatas
Diferencias y semejanzas entre lecturas difitales y ·analogicas, la importancia de la precision y la
“finura” de la lectura·
Razón por la que existen miles de sensores diferentes.
Cómo se arregla Arduino para tratar igual a sensores tan diferentes
Intervalo de separacion entre dos lecturas consecutivas
Félix Maocho
9/4/2017
Comprender por qué las simulaciones digitales no alcanzan nunca la identidad as a la realidad
física. Cómo se reperesntan las operaciones aritméticas en Arduino y cuales son las diferencias
con la aritmética clásica . Tipos de variables, razones de por que hay diferentres tipos, foma de
elegir el tipo adecuado en cada caso. El riesgo del “overflow” o desbordamiento, como prevenirlo
y eludirlo. Ámbito alcance de las variables del Sistema, Globales y Locales. .Uso del mandato
“millis”
Material necesario
Saber que son los pines digitales y analógicos, y las nociones que hemos estado dando hasta el
momento de variables, mandatos, funciones,
Previo a la resolución del siguiente ejercicio hay que conocer una serie de conceptos que
necesitaremos para su desarrollo y aunque ninguno es absolutamente nuevo, pues los hemos
utilizado habitualmente. en esta ocasión les necesitamos entender con mayor profundidad, por lo
que dedicaremos esta entrada a explicarlos con más profundidad.
Porque la simulación digital de la realidad analógica es algo defectuosa y da lugar a que aparezcan
efectos sorprendentes. Un vídeo da 24 imágenes por segundo, que son entre si. un poco diferentes
y es el cerebro, el encargado de interpretar las diferencias. Si las imágenes sucesivas muestran
imágenes de igual aspecto en posiciones ligéramente más atrasadas, en vez de interpretar el
cerebro que la rueda avanza, interpreta que retrocede, pues la imagen parece ir para atrás.
Si vwmoas en la realidad la peonza del vídeo, recibimos un continuo de imágenes y la vemos rotar
correctamente, pero cuando la filmamos, se muestran una sucesión de momento, y según la
velocidad de rotación, nuestro cerebro se engaña y la vemos unas veces girar en un sentido y otras
en otro, e incluso, a cierta velocidad de giro parece que no se mueve.
Lo mismo pasa al hacer un video de una salida PWM, la pantalla del ordenador selecciona una
serie de momentos de la salida. La realidad es que en determinado momento, los led o lucen a toda
potencia o están apagados, pero si lo vemos en real, nuestro cerebro lo que percibe es que lucen
mas o menos. según el tiempo que están luciendo y el tiempo que están apagados, pues en cierto
tiempo, hemos recibido más o menos radiación luminosa.
Sin embargo, al aparecer sólo momentos determinados de la emisión, según la frecuencia del pin
PWM, los momentos seleccionados serán a veces varios seguidos apagados y a veces, varios
encendidos, eso hace que nuestro cerebro en vez de una atenuación de la luz, vea un parpadeo de
la luz más o menos rápido. La simulación parece imperfecta cuando en realidad es perfecta, la luz
unas veces esta encendida y otras apagada pero no luce de forma medianamente potente nunca.
Veamos una prueba. Vamos a hacer un programa que simplemente aumenta el numero que
controla la frecuencia de la salida PWM de 8 en 8 unidades. El hardware sera un led unido a un
pin PWM, por ejemplo el “5” y el software consiste simplemente aumentar el valor de “var”
hasta “255” y a continuación reducirlo hasta “0” mostrando en cada instante, durante un cierto
tiempo la luz que se genera en el pin PWM 5
Como observan, lo que debiera verse como una luz que cada vez brilla mas para después ir
perdiendo brillo, se ve como una luz intermitente y bastante irregular, que en unos momentos
predomina que está apagado hasta predominar que está encendida y volver a disminuir. Esto es lo
más que podemos acercar el mundo digital a lo que vemos en el mundo real.
Como indicamos los pins PWM envían a los led una onda de pulsos modulados cuya gráfica
varia en función de “var” como se ve a continuación.
Si estos pulsos cíclicos los cortamos 24 veces por segundo, es decir de una forma regular pero
arbitraria, el primer corte caerá sobre cualquier punto de la onda, sea cundo está en alto o en bajo y
el segundo, como no será a una cantidad exacta de ondas, caerá o un poco mas a la derecha o a la
izquierda, como pasaba con los radios de las ruedas, por tanto varios cortes seguidos caerán en
lo alto de la onda y a continuación caerán en lo bajo. Por tanto. al hacer la emisión, tendremos
varios “fotogramas” seguidos apagados y varios encendidos, dando lugar al parpadeo que
observamos.
Operaciones aritméticas
Quizá la diferencia de mayor calado es que el signo “=” no quiere decir que lo que a hay al lado
izquierdo tenga el mismo valor que lo que hay al lado derecho, este signo no es de igualdad sino
de asignación, sino que es mas bien es de asignación, o que traslada el valor de la expresión que
tiene a la izquierda a la variable que tiene a la derecha. Por eso en Informática tiene sentido lo
que en matemáticas es un absurdo como la siguiente expresión
x=x+1
En Matemáticas clásica seria como afirmar que “0” es igual a “1”, mierras que en informática
quiere decir que si antes x valía “5”, a partir de ahora vale “6”.
Quizá lo mas correcto sería haber utilizado el signo “←”, pero el utilizar el “=” como asignación
tiene ya mucha historia encima y no es fácil cambiarlo. Por eso cuando queremos indicar una
identidad estamos obligados a utilizar el doble igual “==” , como por ejemplo hacemos en las
condiciones que hacen que se ejecuten una serie de mandatos por ejemplo escribimos
if(8== var)
Esta es quizá la mayor de las diferencias con las matemáticas clásicas, pero no la única vamos a
repasar todas las operaciones relacionadas con las cuatro reglas para observar la diferenciar
Asignación a = b
Suma a + b
Resta a – b
Multiplicación a * b
División a / b
Todo es conocido, salvo que la multiplicación se utiliza el símbolo “*” en lugar del “x” que
podría confundirse con el nombre de una variable.
Menos conocidos son las operaciones con operadores compuestos, es una forma de abreviar la
escritura pero a mi no me gustan en exceso por que lo que se abrevia no se compensa con la
obscuridad que se introduce en las expresiones. Observarán que todos los operadores compuestos
tiene una equivalencia tradicional mucho mas comprensible.
Operadores compuestos
De todas estas expresiones la única que yo utilizo y en un lugar muy concreto es el incremento,
cuando quiero aumentar el valor de un contador una unidad.
Declaración de variables
Cuando en la zona de “Declaración de variables
escribimos una instrucción del tipo:
int nomvar = 0
Estamos declarando una variable, o sea, que estamos indicando al ordenador que utilizaremos en
el sketch una variable de nombre “nomvar” que inicialmente va a tener el valor “0” y que es del
tipo “int”, o lo que es lo mismo que será un número entero con signo que ocupará en memoria 16
bits (2 btytes u octetos) que puede contener números comprendidos entre -32,768 y 32,767
Pero en muchos casos se tiene que guardar valores mas grandes, por ejemplo en este programa nos
encontraremos que en un momento tenemos que multiplicar 255*800 = 204000 una cantidad
claramente mas larga ¿Como declaramos la variable que contenga el valor de ese producto?
– Tenemos la posibilidad de declarar variables de tipos diferentes que pueden contener valores de
diferentes clases
Los nombres de los los diferentes tipos son, char, byte, int, unsigned int, long, unsigned long,
float y double, que podemos traducir por, caracteres, (alfanumericos), byte, entero, entero sin
signo, larga, larga sin signo. flotante, (coma flotante, 6 dígitos entre enteros y decimales de
precisión), y doble (precisión), que indican mas o menos claramente que tipo de contenidos
pueden tener
En la resolución de este problema utilizaremos “int” como hemos utilizado habitualmente que
vale para utilizar enteros positivos y negativos moderadamente grandes. En la memoria del
ordenador se destina un espacio de 16-bit (2 byte u octetos) . O lo que es lo mismo 16 espacios
consecutivos rellenos de “0” y “1” en el que un espacio indica el signo, que indican si el numero
es positivo o negativo y los 15 espacios siguientes, si en la composición del numero representado
en potencias de 2 esa potencia entra o no. Con ello el rango de valores va de -32,768 to 32,767 (de
(-2^15) (2^15) – 1).
13764=0*(2^14)+1(2^13)+1(2^12)+0(2^11)+1*(2^10)+0(2^9)+1(2^8)+1(2^7)+0*(2^6)+1(2^5)+1
(2^4)+1(2^3)+0*(2^2)+1(2^1)+0(2^01)=(0*16384)+(1*8192)+(1*4096)+
+(0*2048)+(1*1024)+(0*512)+(1*256)+(1*128)+(0*64)+(1*32)+(1*16)+(1*8)+(0*4)+(1*2)+0(1
)=8192+4096+1024+256+128+32+16+8+2
Esta página te permite cambiar un número ene base decimal (los normales) una basa a otro en
base a base binaria, (formado por “1” y “0” , si quieres saber cual es el valor en base 2 de
cualquier número decimal basta introducir el numero decimal yen la casilla d correpondiente y
pulsar para que en la otra casilla aparezca el número buscado tal como indica la imagen
“unsigned int” es igual que “int” reserva en la memoria del ordenador los mismo 16 bits, solo
que no utiliza un bit para signo, lo que le permite dedicar una potencia de 2 mas para guardar el
número, pero siempre el número es positivo. Con ello podemos duplicar la capacidad del número
mas grande, pero perdemos la capacidad de guardar números negativos. Algo que se puede utilizar
para guardar números que por lógica siempre sean positivos, como lo es por ejemplo el cuenta
kilómetros de un coche, su rango va de 0 a 65,535 o sea (2^16) – 1)
“byte”, es muy parecido a “int”, solo que ocupa la mitad, solo 8 bits, y además no indica signo,
por lo que solamente vale para si necesitamos números positivos pequeños que como máximo
valgan de 0 a 255 o sea ((2^8)-1). Por ejemplo, utilizaremos este tipo de variables para los
parámetros de los pin utilizados
“long” en cambio reserva en la memoria del ordenador 32 bits, (4 bytes u octetos),y los guarda
con signo lo que permite guardar un rango -2,147,483,648 a 2,147,483,647. o sea (2^31)-1
Análogamente “unsigned ´long” sólo guarda números positivos en 32 dígitos por lo que permite
conservar números el doble de grandes de 0 a 4,294,967,295 (2^32 – 1).
Aunque parezca muy grande en este programa vamos a necesitar una variable de este tipo, porque
utilizaremos el mandato “millis” que devuelve en este formato los milisegundos que lleva el
sketch en funcionamiento y será el valor que toma el resultado cuando el sketch ha estado en
funcionamiento [Link] milisegundos, que son 49 días, 17 horas, 2 minutos, 47 segundos
y 292 milisegundos. Algo que puede ser mucho tiempo en la mayoría de los casos pero que hay
que tener en cuenta en equipos que vayan a trabajar de forma ininterrumpida como por ejemplo un
semáforo
Pasado ese tiempo la cifra no cabe en ningún sitio y se produce el error de “overflow”, (desbordar)
que explicaremos a continuación.
Pudiera resultar que al efectuar una suma, el resultado sea superior al rango que puede contener el
tipo elegido para contener el resultado, en cuyo caso obtendremos valores erróneos y difíciles de
predecir, mas aun si el tipo elegido tiene signo. pues puede que aparezca un resultado negativo
cuando todos los elementos que intervienen en la operación son positivos
Un ejemplo nos explicara mejor lo que ocurre que mucha teoría. Este pequeño sketch no hacemos
que sumar a y b y guardarlo en c: el resultado de la operación es 23900+30000= 53900. Hemos
definido todas las variables como “int” con a y b aparentemente no tenemos problemas, pero c
tendrá que albergar a 53900 que supera el rango de “int” que admite valores entre – 32768 a
32767.
Si observan c adquiere el valor -11636 absolutamente absurdo pues no solamente es erróeo, sino
que además es negativo en una suma donde ambos sumandos son enteros. Tenemos pues un típico
caso de “overwlow”.
Pudiera parecer que si declaramos del tipo “long” a c1 los problemas desaparecen, pero podemos
observar que no desaparecen hasta que declaramos como “long” todos los componentes que
intervienen en la suma.
C1 que contendrá el resultado de la suma de dos elementos “int” n continñúa dando el resultado
erroneo pese a que le hemos declarado como “long” que tiene un rango de -2,147,483,648 a
2,147,483,647.
Es de resaltar lo traicioneros que son estos problemas de “overflow” pues, por un lado la
compilación no detecta la posibilidad de que se produzcan “overflows”, por tanto creeremos
que le programa esta bien y por otra parte no siempre se producen errores sino que sólo se
producirán en los casos que los cálculos no quepan con lo cual tendremos errores intermitentes
que son los más difíciles de localizar pues al introducir unos valores de prueba unas veces darán
error y otras no, sin que estemos seguros que hemos probado todas las probabilidades.
Por tanto en nuestro caso bastaría haber hecho solo a “a” o “b” (ademas de “c” que lo va a
recibir) “long” para que la operación fuera correcta. Hacemos un último ensayo con estos tipos de
valores
Similar a lo que he explicado para la suma ocurre con la resta, el producto y la división, al
menos el resultado y uno de los componentes de la operación han de ser de un tipo con un
rango suficiente para contener los cálculos numéricos.
A la hora de declarar las variables debemos estudiar el máximo valor que vayan a tomar tanto
como resultado final como en los cálculos internos y en función de ello definir el tipo de variable a
utilizar y en caso de duda declararlas de un tipo pon mayor rango.
No obstante si podemos elegir con seguridad variables de rango mas reducido, hacerlo, pues
tiene dos ventajas, por un lado ahorramos memoria, que es algo que equipos modestos, como
Arduino Uno tiene escaso. Pero eso no es lo mas importante, al operar con variables mas largas.
Lo mismo que como ocurre en el cálculo manual, el tiempo de cálculo de dispara.
No se tarda lo mismo en multiplicar dos números de tres cifras que dos de cinco. Si bien el espacio
de memoria destinado a las variables crece linealmente, variables el doble de grandes, precisan el
doble de espacio, el tiempo de proceso de las operaciones crece geométricamente, dos variables el
doble de grandes, precisan para procesarse, el cuadrado de tiempo, eso quiere decir que si dos
pequeñas precisan 3 nano segundos, dos grandes precisan 9 y eso si ralentiza mucho los sketch.
Las “Variables del Sistema” se las utiliza y se las reconoce en cualquier lugar. Ejemplo de estas
variables son, HIGH y LOW definidas para indicar que un pin se ponga en “ALTO“, (5 voltios)
o en “BAJO”. (0 voltios). Estas variables tiene unos nombres reservados, que no se pueden
utilizar para un uso diferente. Podemos utilizarlas en cualquier momento, pero no podemos
cambiar su valor, son realmente mas que variables, “Parámetros del Sistema”
Las variables que definimos en la zona que nosotros llamamos “Área de declaración de
variables”, anterior a la función “setup” son “Variables Globales”. Pueden tener libremente el
nombre que queramos darla y son del tipo y valor inicial que deseemos que tengan, se pueden
utilizar en cualquier lugar del programa y también, a diferencia de las “Variables del Sistema” se
puede cambiar su valor en el transcurso del programa.
Por último están las “Variables Locales”, que se declaran dentro de un párrafo limitado por un
determinado par de corchetes “{…}” como pueden ser los de una función o de incluso de algún
mandato condicional como “if” o “for”. Estas variables sólo tiene existencia, en el transcurso de
la ejecución del contenido de los los corchetes, desapareciendo una vez que ha finaliza la
ejecución de lo limitado por ellos.
Igual que las “Variables Globales“ cuando se declaran, se las adjudica un tipo y un valor inicial
que se pueden cambiara en el transcurso de la ejecución del párrafo donde se las declaró.
Mientras que los nombres de las “Variables del Sistema” son fijos y exclusivos, los de las
variables Globales y Locales son de libre elección, por lo que pudiera ocurrir que un mismo
nombre, se utilizara tanto como Variable Global y Local, o que se declare en dos funciones
diferentes de un mismo sketch. Hay cierta probabilidad que esto ocurra con nombres genéricos
como “numero”, “pin”, “tiempo”, “primeravez”, sin embargo no se produce problemas, el
sketch sabrá en cualquier momento a que variable nos estamos refiriendo.
Las variables locales priman dentro de los corchetes donde se declararon, por tanto si hemos
declarado en dos funciones una variable con el mismo nombre, no hay duda, en la función que se
esté ejecutando, actúa la variable declarada dentro de la función, pues entonces la otra no tiene
existencia, El problema puede surgir entre una variables declarada en el “Área de declaración de
variables” y otra con el mismo nombre declarada en una función.
Por ejemplo una variable global llamada “numero” y declarada con el mismo nombre dentro de
una función. En el interior de esa función, “numero” será la variable declarada localmente, con le
valor inicial que la diéramos ahí, no “existiendo” mientras se ejecute esta función, la variable
global “numero”, que volverá a existir a todos los efectos, con el último valor que tuviera, tan
pronto como finalice la función, fuera el que fuera el valor que “numero” haya adquirido en el
interior de los corchetes de la función.
Algo sumamente útil, pues una forma de programar eficiente, consiste en hacer copy/paste de la
funciones que previamente hemos programado y probado en otro sketch, Si esas funciones utilizan
variables declaradas en su interior, no nos tendremos que preocupar de que en nuestro programa
existan variables con el mismo nombre, a los efectos es como si una variable, tuviera además de
nombre, apellido, el de la función que la declaró de forma que aunque coincidan en el nombre
tengan cada una su propia identidad.
Pese a ello y para mayor claridad es norma, no de obligado cumplimiento pero si conveniente, que
las variables del sistema cono HAIG o LOW, se escriban en mayúscula las variables globales se
escriban en minúscula con nombres de mas de cinco letras que de alguna forma indiquen su
naturaleza como “primeravez” “looppar” o cosas parecidas y que las variables locales se las
nombre con nombres de tras letras como “num” “val” “pin” etc. De modo que de un vistazo
sepamos si nos referimos a una variable del Sistema Global o Local.
Mandato millis
Por ejemplo el mas famoso sketch de Arduino la luz intermitente, la resolvíamos con un
“delay”
void setup() {
pinMode(13, OUTPUT);
}
void loop() {
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
delay(1000);
}
Como hemos visto repetidas veces el mandato “delay” tiene el inconveniente de que
“paraliza” el sketch de Arduino hasta su nacionalización lo que dificulta el hacer otras tareas en
el mismo loop. Sin embargo el mandato “millis” no genera esos problemas, por lo que en muchas
ocasiones es mas practico utilizar este mandato
Lo que hace el mandato “millis” es devolver ver los milisegundos que han transcurrido desde
que el sketch se puso en marchaba. Su sintaxis es la siguiente
tiempo = millis()
Donde
El video hecho con UnoArduSim permite ver como funciona perfectamente la intermitencia
mientras que el “loop” va tan deprisa que casi no somos capaces de fer el valor de la variable
“tiempo” que cuyo cambio indica que se inició un nuevo “loop”
He utilizado variables del tipo “byte” en los casos en que los valores nunca subirán por encima de
255 como son le parámetro “pinoutput” que tiene un valor fijo de “13” y las variables
“primerloop” y “pinencendido” que solo adquieren valores de “0” y “1” En cambio he utilizado
variables del tipo “unsigned long” para todas las variables relacionadas con el tiempo, la razón es
que “millis” devuelve un valor de este tipo, y por otra parte algunas de estas variables podrían
alcanzar con el tiempo valores muy elevados por lo que conviene hacerlas de este tipo, “periodo”
podía haber sido una variable de un tipo más ligero, pero entrando en operaciones aritméticas con
las otras por seguridad prefiero mantenerla del tipo “unsigned long”
Por último piensen el porqué nunca podemos decir que un sketch funcionará perfectamente.
Este sketch, (se supone que), funcionará perfectamente los primeros 49 días, 17 horas, 2 minutos,
47 segundos y 292 milisegundos. Pasado este tiempo “millis()” se pone a “0” y vuelve a contar,
por tanto habrá una vez que tendremos la variable “iniciotiempo” con un valor muy grande y la
variable “tiempoactual” con un valor muy pequeño, en consecuencia la linea donde dice
dará como resultado un número negativo y como “tiempotranscurrido” esta definido como
“unsigned long” que solo acepta valores positivos entre 0 y 4294967295, nos producirá un
“overflow”
Así pues, teniendo en marcha un programa para hacer parpadear un led que funciona
perfectamente, pasados 49 días falla “misteriosamente”. Como ven, nunca se puede asegurar
que un sketch es perfecto, solamente que ha pasado todas las pruebas que le hemos hecho.
Cuanto más extensas y completas que sean las pruebas, mas probabilidades hay que el
sketch funcione bien en todas circunstancias, pero nunca tendremos al 100% la seguridad de
que su funcionamiento es “perfecto”.
Para evitar este “overflów” tendríamos que incluir un nuevo “if” que substituya la linea que
produce el posible “overflow” que dijera
Repaso
Para realizar este ejercicio tal como aquí se resuelve solo se necesitan los conocimientos que se
han ido explicando hasta el capítulo dedicado al uso de entradas analógicas, que podemos resumir
en los siguientes puntos:
Saber crear sketch o programa. Conocer las funciones “int”, “delay”, “pinMode” , “digitalWrite”,
“analogicWrite, “analogicRead” , “if” y “millis”. Saber que es una función cómo se definen y la
forma de llamarlas desde algún punto del sketch. Saber que se pueden declarar variables de
diversos tipos y conocer los tipos “byte”,”int”, “long” y “unsigned long”
Material necesario
Objetivos
Especificaciones
La linterna tiene un potenciómetro que controla su funcionamiento, Mientras que el pin de entrada
analógico mide valores, (“val”), por debajo 20, la linterna está apagada, por encima de 50 y debajo
de 900, (aproximadamente los 9/10 de 1023), tres pines PWM permiten alimentan cada uno a un
led con un brillo (“num”) proporcional a la lectura, (num = 880*val/255) Si a lectura excede a 900
se apagan las luces y enciende un intermitente rojo.
Hardware
Habrá por tanto que abrir un pin digital, (el 4), a OUPUT, para alimentar el intermitente rojo
y tres pines PWM ( los pines 5, 6 y 9 ) para controlar los leds blancos. Para leer el pulsador
destinaremos el pin A0
Linterna-multiuso
Todo lo que hacemos es conocido. 4 circuitos diferentes, alimentados por los pin 4, (led rojo) y 5.
6 y 9 (pines PWM que alimentan leds blancos), todos con sus correspondientes resistencias de 220
Ω y otro circuito que contiene el potenciómetro, en este caso del tipo botón, alimentado a partir de
los pines V5 y GND y que da su lectura por el pin A0
Análisis Funcional
Nuevamente nos encontramos con un ejemplo con trampa. Aparentemente basta con leer A0 y
hacer en cada momento lo que indique la lectura, apagar, encender las luces blancas, o hacer la
intermitencia roja, pero nos vamos a encontrar con el problema ya conocido de la intermitencia y
el botón.
En este caso vamos a utilizar un sistema que permite el control de amibos procesos en un mismo
“loop”. Para ello utilizaremos el mandato “millis” que aprendimos en el capítulo anterior
“Conceptos previos a la resolución de la “Linterna con potenciómetro”
El mandato “millis” devuelve los milisegundos que han transcurrido desde el inicio del
arranque del Sketch, Si leemos el tiempo en el instante de iniciar un semiperíodo de la
intermitencia y lo volvemos a leer repetidas veces, bastara que la diferencia de tiempos sea
superior al semiperíodo para saber que tenemos que cambiar el estado del led rojo.
La primera medida va a ser comparar la lectura del potenciómetro con la hecha en el loop anterior,
pues si no ha variado, dejamos todo como está antes, y tan solo si es necesario atendemos al
cambio de intermitencia, si hay que efectuar la intermitencia Si el potenciómetro ha variado,
actuamos de acuerdo con lo que indique su valor actual y luego, si viene al caso. cuidamos la
intermitencia.
Si el valor del potenciómetro está por debajo 20. apagamos las luces, Si esta entre 20 y 900
encendemos las luces rojas de forma proporcional, Si esta por encima de 900 iniciamos la
intermitencia de luz roja, si no lo habíamos hecho antes.
Para evitar los “overgflow” si el tiempo medido por “millis” es inferior del tiempo actual,
deducimos que hemos superado mayor tiempo posible de medir (4,294,967,295), en ese caso en
vez de por diferencia sumaremos los milisegundos para llegar al límite y los transcurridos desde el
inicio.
En función de este análisis diseñamos el funcionamiento del sketch, de forma que los “loops” se
sucedan con frecuencia y podamos vigilar los posibles cambios del potenciómetro. El Análisis
Funcional se centra en pensar en el QUE VA A HACER el programa y no tanto en el COMO
LO VA A HACER, que es el objeto del Análisis Orgánico. Por tanto, de momento, no
pretendemos averiguar COMO se van a hacer las cosas, sino que nos centramos en QUÉ se va a
hacer.
El programa será pues en principio como sigue, aunque aun esta sujetos a cambios que surjan al
profundizar mas en el avance del análisis :
El Análisis Funcional se ha acabado, aun no sabemos como haremos las cosas pero sabemos LO
QUE TENEMOS QUE HACER, la estructura general que tendrá el programa y lo que tiene que
hacer cada función. En principio, parece que las funciones no generen parámetros, solo la función
“actuar” parece necesitar el valor leído en A0. Por otra parte la funcion “cambiarintermitencia”
precisa para actuar, recibir por parámetro si el led rojo está encendido o apagado.t
Se han originado dos funciones una “actuar”, que se ejecutará con cada cambio del pulsador y
otra “cambiarintermitencia” que se ejecutará sólo, si estamos realizado intermitencias y hay que
cambiar el estado del led rojo.
Hemos declarado una serie de parámetros y variables que utilizaremos en el programa con tipos de
acuerdo con el uso que se las va a dar en es Sketch, los que nunca superaran el valor de 255 los
declaramos de tipo “byte”, los que nunca llegaran a 30.000 de tipo “int”, y todos los relacionados
con el tiempo los declaramos de tipo “unsigned long” posiblemente algunos como
“semiperíodo” no fuera necesario pero ante la duda, los hacemos todos grandes,
Vamos a compilar y eliminar los errores preliminares antes de continuar. Aconsejo para ello
utilizar el simulados UnoArduSim porque te marca donde ha encontrado el error y indica el valor
de las variables en ese momento, lo que facilita bastante la comprobación.
Esto es un recurso muy habitual para hacer paradas en el programa que permitan copribar que el
programa pasa por ese punto y que den tiempo a cerciorarse del valor de las variables,
Normalmente finalizadas las pruebas estas lineas se eliminan o se dejan como comentarios para
que no interfieran en el funcionamieento del programa cuando actua en real.
Lo habitual es que el sketch tenga la primera vez que le compilé muchos pequeños errores
como dejar paréntesis abiertos, errores en los nombres de variables y funciones, faltas de “;” al
final de las lineas y cosas por el estilo. El error que más me costó encontrar es que faltaba la línea
final con el “}” de cierre de la función “loop” con lo que el compilador entendía que toda el área
de definición de funciones pertenecía a la función loop y se armaba el taco y los mensajes de error
que generaban, no hacían mas que aumentar el desconcierto.
En el momento que está el programa solo podemos comprobara en cuanto a sus funcionamientos
las siguientes cosas:
Que si no se cambia el potenciómetro el programa no pasa por ninguno de las dos lineas de
“delay” que hemos puesto como control, pero que “valoranterior” vale lo mismo que
“valoractual”
Que si se cambia el potenciómetro el programa pasa por la primera de las dos lineas de “delay”
de control, y que “valoranterior” vale diferente que “valoractual”
Que en ningún caso c entra en el segundo delay de control porque nunca “intermitencia”
adquiere el valor “1”
Análisis Orgánico
En esta fase, se comienza a “traducir” las funciones descritas en mandatos del lenguaje, o sea
CÓMO se hace lo pensado en el Análisis Funcional, es el trabajo de los programadorees. Es por
tanto la fase donde definimos los mandatos que van a hacer las cosas. Si alguna de las funciones
aun presenta complejidad, las descomponemos a su vez en funciones más simples como en nuestro
caso ocurre con la función “actuar”
Función actuar
Según el valor de “val”, apagamos los led, (<20) encendemos los led blancos (entre 20 y 920), y
pasado el 920 iniciamos la intermitencia roja
Con el fin de no apagar innecesariamente los led cundo esten encendidos lo marcaremos con una
variable que adquiere el valor 1 y si están apagados le damos el valor 0, (esto se llama
tecnicamente utilizar un “flag” o bandera). Para ello añadimos una nueva variable mas que nos
faltaba “encendidoblanco” que será también de tipo “byte”.
}
else {
// iniciar intermitencia *********
testigo =3 ; // ********** Linea provisional de control ************************
}
Observarán que para el control de la funcion hemos añadido en el área de deeclaración de
variables la vartiable “testigo” que nos indicará por los valores que toma si la función actúa como
se espera según los valores de “val” que demos con el potenciómetro. Algo que poderemos leer
cuando se para en el delay que hemos puesto a la salidade la función.
La variable “testigo” la podíamos haber declarado comno local pero al desaparecer al salir de la
función nos dejaria menos tiempo para ver su valor despues de variar el potenciómetro, pues
mientras este no varíe el valor de “testigo” sera el del último sitio por donde pasó.
Esta función origina módulos de programa, el que apaga todo, el que enciende blancas y el que
inicia las intermitencias rojas.
En este momento al compilar no podremos mas que quitar los errores de “ortografía” y ver si su
funcionamiento es correcto según el valor de “vaL” pues aun no hace nada mas.
Para no hacer trabajar inútilmente a la tarjeta comprobamos previamente a apagar los led si están
encendidos y ponemos los indicadores de led apagados y de no intermitencia. Ello nos obliga a
usar otro “flag” mas “encendidoblanco” que nos dirá si hay que apagar los leds blancos. Lo
declaramos en el Área de declaración de variables porqeu otras funciones tendran que encargarse
de encederla
Como siempre compilamos y quitamos errores, pero no podemos probar mas de lo probado
proque nadie ha encendido las luces que este módulo apaga, eso lo dejaremos para más adelante.
Tomamos como parámetro de entrada el valor que generó la lectura del potenciómetro, y con el
generamos “num” que será proporcional a “val”; hacemos una regla de tres num =
(val*^255)/(1023-20). Simplificando la formula queda num =val*255/1003 aproximadamente
num =val* (255/1000)= val* 0.255
Para eliminar problemas de oferflow vamos a definir como flotante (float) el resultado de la
operación (val*0.255) (observen que en los sketch, los decimales se separan de los enteros con un
punto (.) como hacen los americanos y no con una coma) Luego se lo vamos asignar a un valor int
que llamaremos “brillo” que es lo que podemos llevar a analogWriten como para metro de
intensidad de luz. No obstante y pese a nuestro cuidado para evitar sorpresas vigilaremos este
punto con mucho cuidado en las pruebas..
Observen que hemos declarado dos nuevas variables que necesitamos para realizar los
calculos “num” y “brillo” que se podian haber declarado dentro de la función “actuar”, es
decir de forma que sólo tengan existencia cuando el sketch está dentro de la función, oues al salir
desaparecen, algo que se puede observar bien en el simulador vigilando las variables que
aparecen en la esquina inferior izquierda. Esto es lo adecuado, ¿para que cargar al ordenado con el
recuerdo de variables que solo va a utilizar aquí?. Sin embargo las hemos declarado como globales
es decir en el Área de declaracion de variables, porque queriamos a observar sus valores con todo
detalle y estando declaradas ahi no desapqarecen y se pueden analizar con detalle.
Si movemos el patín del potenciómetro entre 0 volts y 2,5 volts deberemos ver que cuando está en
cero se pagan las luces blancas y cundo esta aumentando cada vez lucen mas los leds, lo que
notaremos sólo parcialmente, viendo como cada vez está parpadeando mas rato encendidos pues la
variacion del brillo en esta simulación como explicamos en el capítulo anterior Conceptos
previos a la resolución de la “Linterna con potenciómetro” es muy mala y sólo se observan
intermitencias que duran mas tiempo encendidas a medida que aumenta el voltaje en el
potenciómetro..
Aun no podemos probar la intermitencia roja pero si podemos probar todo lo que nos faltaba,
Función “cambiarintermitencia”
Sólo nos resta definir la segunda función del programa, en la que solo entraremos si se ha iniciado
la intermitencia, osea cuando “intermitencia == 1”. Si el led rojo esta encendido lo apagamos y
viceversa, la funcvion tiene como entrada el flag,(bandera) que indica si el pin rojo está encendido
o apagado
Les paso el sketch completo tal como queda al final, Les dejo las lineas que he pued to de control
para que puedan jugar con ellas, pero lo correcto seria una vez acabadas las pruebas retirarlas pues
no hacen mas que entorpecer y retrasar el funcionamiento del sketch cuando este programa
funcione en real.
Es una pena que el editor de WordPress se como los espacios en blanco según ellos “innecesarios”
porque desaparecen los indentados que indican lo que abarca cada par de corchetes “{…}” lo que
facilita mucho la comprensión del programa. Les copio por ello un pantallazo de el aspecto del
programa en UnoArduSim para que tengan al menos una idea de lo que yo realmente manejo.
La otra recomendación que les hago es que no pretendan poner a punto un programa de arriba
abajo, hay que g hacerlo por fases como lo hemos hecho en este caso, porque asi los errores están,
(sobre todo), en lo ultimo que hemos escrito con lo que resulta mucho mas fácil de controlar sus
posibles fallos. Se que es pesado el sistema pero creanme y es experiencia de muchos años , pese a
todo la forma más rápida de poner a punto un programa.
Les dejo la prueba final, Cambiando el potenciómetro recorro las diferentes posibilidades que
tiene la linterna tanto de encender las los leds balancos como el rojos intermitente.
Curso de Arduino – Comunicaciones asincronas
Conocimientos básicos sobre comunicaciones asíncronas, que son, codificación ASCII Unicode,
codificación binaria, velocidad de conexión y forma de realizar la comunicación asíncrona y
utilidad del módulo UART del procesador.
Material necesario
Por mucho que nos parezcan suficientes los 20 pines de nuestra Tarjeta Arduino Uno, la realidad
nos demostrará que son insuficientes para cualquier tarea de mediana complejidad. Por ejemplo,
un brazo robótico sencillo. como el que muestro en la imagen de comienzo, precisa al menos tres
motores, uno en cada eje, para situar la mano en cualquier punto a su alcance, y lógicamente al
menos uno mas, para que la mano haga algo, ya sea agarrar, atornillar, ,,,
Pues bien, nuestra Tarjeta Uno solo tiene seis salidas PWM y se necesitan dos por motor para
hacerlo girar a derechas o a izquierdas. Por tanto las seis salidas PWM nos serán insuficientes
para manejar cuatro motores.
Esto no supone mayor problema, porque podemos utilizar dos tarjetas, una tarjeta para controlar el
movimiento del brazo y otra para controlar el movimiento de la mano. Sin embargo, supone que
tendremos que establecer algún tipo de conversación entre las tarjetas, para que se informen unas a
otras de lo que hacen y cuando deben entrar en acción.
Hay diferentes formas de hacerlo, por ejemplo, podemos destinar un pin digital en OUPUT de
una tarjetas, para emitir o no voltajes en “HIGH” o “LOW” y desde un pin digital en INPUT de
la otra tarjeta, averiguar cuando ese circuito esta en alto o no. También se puede hacer, de forma
mas compleja, con pines analógicos, por ejemplo emitiendo luz con mas o menos intensidad y
detectando la luminosidad con un fotómetro, lo que nos permite unas respuestas mas variadas, en
función de la intensidad del pulso emitido.
Comunicación asíncrona
Sin embargo, hay prevista una forma estandar para la comunicación de la tarjeta, con otros
aparatos capaces de entrar en comunicación con ella, que es la comunicación asíncrona. Esta
comunicación permite poner en contacto dos aparatos, que sean capaces de emitir y recibir este
tipo de comunicaciones, para enviarse mensajes entre ellos. La Tarjeta Arduino UNO posee dos
pines digitales, el “0” y el “1” que tienen a su lado otra marca RX← el pin 0 y TX→ el pin 1
destinado a este fin,,
Al igual que ocurre en los pines marcados con el símbolo ~, que aparte de ser pines digitales
normales y corrientes, pueden configurarse como pines capaces de producir ondas de pulsos con
modulación, PWM (Pulse width modulation), los pines 0 y 1, además de ser pines digitales, con
las misma capacidad de entrada y salida de cualquier otro pin digital, pueden configurarse para un
uso diferente. En este caso, están preparados para transmitir, (TX) y recibir (RX), comunicaciones
a otros aparatos, que por su parte tienen que ser capaces de recibir y enviar el mismo tipo de
comunicaciones.
Estos leds parapadearan siempre te la tarjeta se comunique con otro equipo, sea un Pc por el cable
USB o por los pines TX y RX, y de igual forma que se carga el programa y por el mismo cable, la
tarjeta puede comunicarse con el ordenador cundo se lo ordenen los mandatos convenientes del
Sketch.
Conviene por ello acostumbrase a no usar como digitales los pines “0” y “1” al igual que no
conviene hacerlo con los pines PWM o con los que se utilizan para entrada analógica, pues
debemos reservarlos para otros usos, salvo en caso de necesidad, pues frecuentemente vamos a
utilizar las comunicaciones asíncronas unas veces por el cable USB y otras para comunicar la
Tarjeta Arduino con otros aparatos compatibles, como puede ser otra tarjeta. Sin embargo si nos
faltan pines y no vamos a tener comunicaciones asíncronas podemos utilizarles normalmente sin
problema.
Convenientemente configurados al
principio del programa, (en la función “setup”), estos pines pueden actuar como un puerto serie.
“Puerto serie” es el nombre que se da a los lugares, o “puertos”, que permiten enviar y recibir
comunicaciones entre dos dispositivos. El funcionamiento de estos puertos es similar a la forma
de comunicación del antiguo telégrafo de Morse, un aparato donde un texto se transforma en
impulsos eléctricos que transportan una codificación, que el aparato receptor puede
decodificar grabar en un soporte de papel, que alguien traduce a texto, y a su vez, el receptor
puede mandar al origen, otras comunicaciones, estableciéndose así el diálogo entre ambos puntos.
Igual que en el aparato de Morse, podemos trasformar un texto, en vez de puntos y rayas como en
el Morse, en subidas y bajadas de tensión, que se transmiten por el pin TX (transmitir), por un
cable hasta otro aparato que las recibe en un pin RX (recibir), y utilizar esas subidas y bajadas de
tensión para grabar “ceros” o “unos” en una memoria que llamamos “bufer de recepción”, que
posteriormente se leen y transforman nuevamente en el mensaje de texto que se envió.
Para que se pueda entenderse el mensaje trasmitido, aparte de estar conectados los aparatos
capaces de enviar y recibir los impulsos, hay que guardar una serie de convenciones diferentes,
es decir debe existir una norma de comunicación común.
Al pasar la comunicación del Morse al mundo digital, difieren los medio utilizados pero no por
ello cambian los problemas básicos. Hay que declarar de alguna forma cual es el comienzo y el
final de los textos, aquí serán impulsos vacíos al inicio y a final de cada ocho ondas de voltaje
que se manden, luego no ocuparan ocho ondas sino diez.
Hay que ponerse de acuerdo a que velocidad se transmite y recibe, la velocidad se mide aquí en
baudios o bytes por segundo.
Hay que ponerse de acuerdo en la codificación y genialmente sera la codificación ASCII Unicode
que tiene un determinado octeto de bytes, (8 unos o ceros), para codificar, no solo letras y
números, sino otros muchos caracteres como estos ¿ ^ ) & y también caracteres cirílicos, griegos,
Yo creo que con esto tiene suficiente teoría de lo que es una comunicación asíncrona, aunque claro
está, la cosa en la realidad tiene mas complicación, pues puede haber ruidos parásitos en la linea y
hay sistemas de control, que garantizan que la información que se ha recibida es correcta, para eso
con cada octeto se envía una cifra de paridad parecida a la letra final del DNI, que es el resultado
de una ecuación con los unos y ceros enviados, de modo que si donde había un “1” se recibió “0”
o se bailó un par de números se detecte como erróneo, en cuyo caso se vuelve a solicitar
nuevamente el envío del octeto y otras normas parecidas que indican el principio y final del
mensaje, pero que como son afortunadamente son absolutamente trasparentes a su uso, lo vamos a
dejar para los Ingenieros de telecomunicaciones que son los que tienen que lidiar ese toro.
Así pues pensemos que enviar un octeto es solo algo parecido al gráfico que pongo a continuación
que es lo que se mandaría para enviar el octeto “11010011” que según esta página es “Latin
capital letter O with acute” o sea la ”O” mayúscula y acentuada aguda “Ó”
La linea del reloj indica la velocidad en baudios, como ven cada cero y uno modifican dos
semiperiodos de la frecuencia, y a parte hay otros semiperiodos que se destinan a otros usos como
es el comienzo y final u el bit de paridad o control de la calidad de lo recibido y como es la misma
para cada aparato cada onda corresponde a la transmisión de un byte como ven hace falta
bastantes mas de 8 ondas para mandar un octeto de bites, lo que produce una merma superior al
20% de la cantidfad teót rica que se pudiera mandar imprescindibles para sincronizar los equipos
y confirmar la calidad de los envíos etc.. Como digo la realidad es bastante compleja, pero
afortunadamente lo que es preciso que nosotros comprendamos es bastante sencillo, pues de todo
se encarga el procesador automáticamente sin nuestra intervención.
Pero para que se comuniquen en los dos
sentidos los dos aparatos se necesitan dos pines, uno definido como de salida o OUPUT que envía
sus señales a otro pin en el otro aparato definido de entrada o INPUT y viceversa, El pin definido
como INPUT capaz de “escuchar” los impulsos que se le manden desde el transmisor, es el pin
“0”, o “RX”. Es el pin Receptor y el “1”, o TX, será el Transmisor, y lógicamente el cable que los
une ira cruzado de la TX a la RX y viceversa.
Las tierras pueden esta unidas entre si o cada una unida a una tierra diferente eso no afecta, lo que
eso muy importante para las comunicaciones asíncronas es que el cable que parte de TX de un
aparato acabe en el RX del otro y viceversa.
¿Que es UART?
Todas las tarjetas Arduino actuales tiene un módulo UART, por tanto pueden procesar sin
dificultad los datos en secuencia de bits y viceversa liberándonos así de muchas molestias.
Arduino UNO solo tiene un módulo UART lo que indica que solo puede mandar el mismo
mensaje por el cable USB y los pines “0” y “1” por tanto en puridad solo puede comunicarse
con otro aparato, Lo que si puede es comunicarse con varios aparatos por ejemplo conectar el pin
TX con varios pins RX de otra tarjetas y mandar a todas el mismo mensaje., Sera trabajo de cada
aparato saber si el mensaje es para el o para otro
Por ejemplo podemos codificar que si el octeto comienza por “111” es para un equipa y si es
comienza por “110” es para otro y que si recibo un mensaje que comienza por “101” es respuesta
del “111” y si comienza por “011” es respuesta del otro y aun nos quedarían la combinación de
cinco bytes para enviar distintas instrucciones. Pero para trabajar en redes se suelen utilizar
tarjetas que tiene varias UART de modo que pueden comunicar con varios equipos sin tanta
complicación.
Por
ejemplo la Tarjeta Arduino MEGA, tiene 4 UART diferentes lo quele permite realizar
comunicaciones por al cable USB y los pines o (TX) y 1 (RX) igual que la tarjeta UNO, pero
además por los pines 14 (TX) y15 (RX), 16 (TX) y 17 (RX), 18 (TX) y 19 (RX). Lo que da idea
de la importancia que tiene las comunicaciones en los grandes proyectos.
Esta forma de comunicación se llama “comunicación asíncrona”, pues no hace falta que ambos
equipos estén simultáneamente alerta, aunque si conectados y encendidos. Como pasa en el
Morse, en el que el telegrafista que recibe el telegrama, no hace falta que lo lea según llega, ni
siquiera hace falta que esté en ese momento, porque lo puede leer después del papel donde queda
escrito.
Como una Tarjeta Arduino, realiza una transmisiones asíncronas, si por ejemplo transmite un
mensaje cuando así se lo indique en alguno punto del sketch en la función “loop”. El mensaje
generado en la UART parte y se graba en “bufer de recepción” del destino, exactamente igual
que ocurría en el Morse donde el papel hace de “buffer de recepción” y cuando en la tarjeta de
llegada, el “loop” de su sketch indique que es el momento adecuado de leer esa memoria, su
UART leerá el contenido grabado y en otro momento el “loop”, si procede, mandara su respuesta,
que el otro aparato leerá cuando se lo tenga previsto en su programa.
Como ya he comentado al hablar del telégrafo y el teléfono, la principal diferencia entre una
comunicación sincronía y una asíncrona, es que la primera exige tener “en directo“ emisor y
receptor, es decir que estén sincronizados ambos aparatos y la segunda no lo necesita. La
comunicación asíncrona es más económica en medios, (y lógicamente más barato el equipo
que precisa). La comunicación sincrónica, precisa de mas medios, pero admite mayor flujo de
datos.
Para muchas cosas, la comunicación asíncrona será suficientemente rápida, pero para otras será
insuficiente. Para enviar unas pocas cifras, por ejemplo, el peso que detecta una balanza, es más
que suficiente, pero si lo que pretendemos comunicar, es una imagen, o un sonido, quizá no tenga
la suficiente velocidad para ser práctica.
Como cada vez los PC son mas rápidos y tiene un reloj interno capaz de generar ondas con mas
baudios. conlo que aumenta la velocidad de las comunicaciones asíncronas, que poco a poco,
van sustituyendo a las síncronas. Por ejemplo, lo que ven a la izquierda, es el cable que antes
usaban las impresoras para conectarse a un PC . Cables gordos de muchos hilos y enchufes con
muchos pines muy voluminosos, pues la conexión de la impresora con el PC era antes síncronas,
mientras que hoy, gracias al aumento de velocidad de los equipos, generalmente se conectan con
un cable USB, que solo tiene en su interior cuatro cables, es decir hoy se conectan
asíncronamente.
Sin embargo para algunos usos, sigue siendo aun necesario conectar los aparatos con gruesas
cintas de cables en paralelo porque aun necesitan una conexión asíncrona.
Cables USB
1, – De color rojo que lleva 5V para dar energía si lo precisa al otro equipo, Es el que alimenta de
corriente eletrica del PC a la tarjeta Arduino,
2 y 3. – De colores blanco y verde, son los cables para la comunicación asíncrona se cruzan en el
interior del cable de modo que el RX conecta por el otro extremo con el TX y viceversa.
4 – es el cable de tierra o masa que suministra un equipo a otro en caso de necesidad como
pasaba con el 5.V, los conectores son de varios tipos pero estandarizados, pues poco a poco se
construyen cada vez mas pequeños. .
En el mundo del PC, hay varias normas de comunicacion, Arduino y el PC utilizan las indicadas
para los puertos USB, por eso el PC puede cargar el programa en Arduino y esas son las mismas
que se utilizan en los pines RX y TX que es el uso del ASCII Unicode, los voltajes que
significan cero y uno, son 0 y 5V y la velocidad de transferencia es una entre varias posibles,
pero hay otros equipos que utilizan otras normas que son diferentes a las USB
Como es lógico, sólo pueden ponerse en comunicación directa equipos que utilizan protocolos
iguales y habrá que arbitrar la forma de traducir un protocolo a otro si son diferentes mediante
algún sistema intermedio que los traduzca. Por ejemplo hay componentes especiales que traducen
las comunicaciones asíncronas en infrarrojas, para poder controlar un robot hecho con Arduino,
con un mando parecido a los de la televisión.
La diferentes velocidades en que se puede operar con las normas USB son 300, 600, 1200, 2400,
4800, 9600, 14400, 19200, 28800, 38400, 57600, y 115200 baudios/segundo. Lo habitual para
conectar con el PC son 9600, velocidad media que no suele dar problemas como las muy rápidas
y que salvo excepciones, que lo justifiquen es la que se acostumbra a utilizar, aunque la tendencia
a futuro es aumentar la velocidad a medida que los equipos sean mas eficientes para así mandar
más información en menos tiempo. Sin embargo mientras utilicemos las actuales Tarjetas UNO
que son muy económicas no podemos utilizar con seguridad velocidades muy altas por lo que en
lo posible mantener una velocidad de 9600 que es la habitual o menos si conectáis con equipos
aun mas pobres y solo subir de estas velocidades si es imprescindible.
Repaso
Identificar cuales son los pins RX y TX capaces de comunicarse con otros aparatos
Saber que el parpadeo de los leds TX y RX indican que la tarjeta se esta comunicando,
Conocer que existen unas normas de comunicacion.
Que son los códigos ASCII
Que es un puerto serie.
Saber como conectar dos dispositivos por su puerto serie
Qué es el módulo UART y su importancia
Que son comunicaciones asíncronas y síncronas, y cual es su diferencia fundamental, sus ventajas
y sus inconvenientes
Como es un cable USB.
Otras normas de comunicació diferentes a las comunicaciones asincronas
Velocidades de las comunicaciones asincronas y cual elegir
Curso de Arduino – Transmisión de Comunicaciones asíncronas
Material necesario
Como indicamos, las comunicaciones asíncronas vale igual para comunicar entre si, dos Tarjetas
Arduino, como para comunicar la Tarjeta con otro tipo de aparatos, capaces de recibir y enviar
comunicaciones asíncronas.
Por ello podemos probar esta comunicación, entre dos Tarjetas Arduino, pero precisaríamos
tenerla, lo que su pone un gasto que de momento sólo nos valdría para esta prueba. Tan solo las
tendríamos que conectar como indica este esquema, le puerto RX con el TX y viceversa y las dos
masas.
Como no las tenemos, no podemos probar los pines TX y RX, pero si podemos probar la la
comunicación asíncronas a través del cable USB, con el PC.
USB son las iniciales de Universal Serial Bus, que indica que permite comunicaciones seriales,
Además por este cable es por donde cargamos los programas en la tarjeta, señal evidente que la
comunicación entre Pc y Tarjeta es posible.
Preparar el PC
Dependiendo de la “relise” que tenga el programa puede variar un poco su aspecto pero
habitualmente el comando es la situada la última a la derecha de los diferentes programas que
existen. Por ejemplo en una “relise” muy antigua la “0011 Alpha”, (que es muy poco probable
que utilices), aparece con un dibujito y el sitio donde se reciben y envían los datos esta al pie de la
pantalla un sitio para escribir donde se va a escribir al lado del botón que dice “send” (enviar)
que se pulsa una vez hemos escrito el mensaje que queremos enviar y en la parte inferior la
pantalla donde se reciben los datos enviados desde la tarjeta.
Sin embargo en otras “relise” mas modernas, por ejemplo la “1,5.4”, (lo más probable que tu
utilices una con una numeración superiór) el aspecto es como sigue;
Al al pinchar en la especie de lupa que viene marcada como “Monitor Serie”, hace que aparezca
una nueva pantalla como la que viene a continuacion, que hace mas o menos lo mismo que la
antigua, lo que queremos enviar lo escribimos en la primera linea y cuando acabemos pulsamos
“Send” o “enviar” según el idioma que hayamos configurado por defecto.
No obstante para que aparezca esta pantalla previamente a poner el programa Arduino en marcha
debemos conectar la tarjeta Arduino (u otro aparato receptor/emisor asíncrono al PC, pues si no
nos dará un error.
(Observen que yo utilizo la “relise” 1.5.7 y no es la última, pero que lo referente a las
comunicaciones asíncronas es igual que en la anterior).
Board at COM3 is not aviable (La tarjeta en COM3 no está disponible)
que nos avisa que la Tarjeta Arduino no esta conectada al puerto COM3. COM3 es en nuestro
caso el puerto de comunicaciones que se eligió automáticamente al instalar el programa Arduino
en mi PC. En otros PC puede haberse destinado otro puerto COM. Si la enchufamos hasta oír el
ruido típico de haber enchufado un equipo por USB y esperamos un poquito mas para que la
máquina asigne el COM3 a esa salida USB, llegaremos sin problemas a esa pantalla
Como ven es muy fácil utilizar las comunicaciones asíncronas en el PC. Basta escribir algo en la
linea superior y dar a “enviar· para que automáticamente pase a la tarjeta, mientras que en la
pantalla recibimos todo lo que la tarjeta quiera mandar.
Hay en Internet otras pantallas mas cómodas y sofisticadas para seguir las comunicaciones
asíncronas como HyperTerminal (para Windows) -Enlace o ZTerm (para Mac)-XXXX-
Linux-Enlace, etc. , pero a mi juicio, pese a su sencillez, (o quizá debido a ello), este monitor
estándar, es más que suficiente para comenzar, y con toda seguridad pasará una larga temporada
sin que notes que “se te queda pequeña”.
En esta pantalla, en la esquina inferior izquierda veremos la velocidad en que trabaja el PC. en
nuestro caso 57600 Baudios y hay formas sencillas de poderlo modificar, en este caso basta
desplegar el menú de las velocidades y elegir la que queramos, pero por defecto, la velocidad que
viene es 9600 baudios y mi consejo es utilizarla, si no hay razón de mayor peso que aconseje lo
contrario. En cualquier caso, la velocidad seleccionada, debe coincidir con el valor que hemos
definido en el programa y a través del comando [Link](), que veremos más adelante..
Comenzaremos pre indicar los mandatos que se utilizan en comunicaciones, Hay tres tipos de
datos los utilizados en la preparación de las comunicaciones , los utilizados en la transmisión de
datos y los utilizados en la recepción de los datos:
Mandato [Link]
Configura en la tarjeta el puerto serie y fija la velocidad en baudios que decidamos que será en
función de la capacidad de los aparatos que pensemos conectar y, muy importante, la misma en los
dos aparatos conectados. Lo podemos traducir por [Link]. Su sintaxis es
[Link](velocidad)
Donde
[Link] es el nombre del mandatos. Este mandato se utiliza en la funciona “setup” puesto
que es un mandato de configuración del equipo y una vez declarado no se puede modificar
posteriormente en el sketch
velocidad, es el numero en baudios o bytes por segundo de la transmisión, que puede ser una de
las velocidades soportadas por los aparatos, (al menos teóricamente). La comunicación asíncrona
debe ser declarada igual en el aparato receptor y el emisor, este mandato es la que los sincroniza.
Los valores que Arduino soporta son 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800,
38400, 57600, y 115200 baudios/segundo. La velocidad típica y por defecto de un PC son 9600
baudios. por lo que pondremos a Arduino a trabajar también a 9600, aunque otras velocidades
pueden ser soportadas si ponemos tarjeta y Pc a la misma velocidad
Son dos mandatos semejantes en todo, que cargan unos caracteres situados entre paréntesis en la
UART, dispositivo especializado en transformarlos en octetos y transmitirlos como impulsos
eléctricos que en al Tarjeta Arduino UNO son emitidos simultáneamente por el pin TX, y el
cable de emision del USB, Ppor tanto utilizar el pin 1 como igital no es compatible como la
comunicación serial, razón por la cual debemos evitar en la medida de lo posible no utilizar estos
pines salvo que lo precisemos y estemos seguros que no vamos a necesitar la comunicación serial,
La diferencia entre [Link] y Serial,println es parecida a la que hay escribiendo entre el
“punto” y el “punto y aparte”
Su sintaxis es
Donde
[Link] y [Link], son los nombres de los mandatos que mandan el mensaje
acompañado de un mandato de línea nueva (ln) o lo que es lo mismo, retorno del carro y cambio
de linea
mensaje, es el mensaje que queremos comunicar. Según el contenido que tenga el mensaje, la
unidad UART, actuará de diferente forma:
Si se envían caracteres entre comillas (“…”), por ejemplo “Contador: “, enviara la el texto
«Contador: » incluido el espacio en blanco, tal como se le indicó, pero no envía las comillas de
inicio y fin.
Si no hay comillas, asume que es una variable o parámetros definido previamente, y en ese
caso enviara el contenido de la variable o parámetro que en ese momento de la ejecución del
programa tenga la variable. Si se envía un texto sin comillas, si es un número, lo considera como
tal, si son letras lo considera una variable con valor, y emite el valor que en ese momento tuviera
la variable
Si se envía un número con varios decimales, por defecto envía sólo los dos primeros decimales
O sea, si en el sketch hay una linea que dice “nun = 78; ” siendo num una variable definida , si se
envía escribe el mandato como:
Hay que eludir incluir al carácter “ dentro del mensaje, para no confundir a la UART. Se
pueden utilizar como comillas, por ejemplo los caracteres « » u otros cualquiera y en todo caso,
sustituirlos posteriormente mediante programación por por comillas si se considera
imprescindible.
tipo, es un parámetro opcional, (o sea que se puede poner o no como queramos), que solo puede
añadir cuando se envían números, para indicar su naturaleza. Los valores permitidos son, un
numero entero, (numero de decimales redondeados), BIN (binario o de base 2), OCT (octal o
base 8), DEC (decimal o en base 10), HEX (hexadecimal, o base 16). Para los números de
punto flotante, este parámetro especifica el número de decimales a utilizar.
Los otros paramentos son menos usados y tiene la ventaja de utilizar la UART para codificar de
diferentes formas distintos números sin necesidad de programación adicional así por ejemplo si
mandamos el numero 78 o una variable que adquiere ese valor según lo que indique el segundo
parámetro, recibiremos los siguientes valores, recibiremos los siguentes valores:
Con estos dos únicos mandatos ya podemos mandatr mensajes a pantalla de comunicaciones
asincronas del PC. Vemos un ejemplos. Vamos a enviar a la pantalla del Pc un contador de los
loops que hace el sketc
Amalisis Funcional.
El ejercicio tiene el objeto de ver un ejemplo de uso de las funciones con el suso de las funciones
[Link] y [Link]. [Link] llevará como mensaje un texto “”loop N- ” y a
continuacion y por lo tanto seguido el numero que hace el loop saltando de linea una vez escrito
En el Àrea de declaracion de variables definimoos una varia “x” que llevara el contador de los
loops
Seleccionar como velocidad 9600 baudios. Escribir el numero de loops realizados al comienzo del
loop y retardar un poco el loop para que tenga un ritmo tranquilo la emisión.
Como siempre compilamos y corregimos errores. Esta vez no lo podemos hacer en el simulador
UnoArduSin por que la función de transmisión si bien la soporta sin problemas a la hora de
compilara no la contempla, (o al menos yo h no he sabido como se hace), por lo que compilamos
directamente en nuestro programa Arduino.
Para que no tengamos errores siempre que compilemos algún sketch con conumicaciones
asíncronas, debemos tener físicamente conectada la Tarjeta Arduino con el PC mediante el
cable USB, en otro caso dará errores del puerto COM.
Tódo parece perfecto y fenomenal pero no lo es tanto, Como esto lo i hicieron, (como casi todo ),
en USA, la uart pasa bien los caracteres que usan los USA pero no los que usamos los demás
como la Ñ ,las vocales acentuadas etc. Os voy a poner unos ejemplos de estas cosas para que
veais como se emite y que se recibe.
el programa es muy parecido al anterior , solo que los textos tendrán algún acento que otro y una
“ñ” y el Nº para que vean como se recibe. A parte en el 10 loop empezara a escribir los numeros
de acuerdo con lo que hemos indicado de t referente a los tipos:
Vomo onservaran tanto la “ñ” de “Año” como la “ú” de “Número” como la “º” de “Nº”, son
substituidas por extraños caracteres,
Igualmente la (x) se emite correctamente, pero sale un tanto confuso y poco practico. En efecto en
binario o base 2 (BIN) 11=1(2^3)+1(2^2)+0(2^1)+1 (2^0)=8+2+1 y en base 8 (OCT)
11=1(8^1)+3(8^0)= 8+3 , así como en base 10 (DEC) 11=1(10^1) +1(10^0) y en base 16, o
hexadecimal (HEX) vale B(16^0^0=11
Como ven las comunicaciones asíncronas, no son tan sencillas como las había explicado hasta
ahora, Puede que en la carrera de telecomunicaciones, estudiadas en profundidad, den para todo un
trimestre de estudio, no es ese el propósito de esta capítulo, sino solo indicar la capacidad de las
comunicaciones asíncronas de la Tarjeta Arduino y lo básico para mandar mensajes.
Eso es conocer [Link] y [Link], con eso y con un poco de gracia para eliminar las
trampas que nos podamos encontrar. es más que suficiente. Hay soluciones para mejorar estas
comunicaciones pero superan el objetivo de este capítulo, les enseño sólo lo suficiente o para que
puedan mandar fuera de la Tarjeta Arduino, por ejemplo la lectura de un sensor, como un
termómetro o la distancia a un obstáculo. Creo que ello lo podrán conseguir sin gran esfuerzo, con
estos conocimientos, eludiendo poner caracteres que den problemas. Pero si de repente ven que
sale algo inesperado, lo mas cómodo el cambiar el carácter o la palabra que de problema por otra
que no los de.
Repaso
Dejo un par de ejercicios para que intente resolverlos, en breve tendrá la solución en otro capítulo
=================================================================
Puede encontrar resuelto este ejercicio en:
1º Ejercicio de comunicaciones – Informar por donde pasa el loop
=================================================================
aleatorio = random(2)
Si es “o” enviar un mensaje que diga; “loop numero X – Pasa por Punto A”
Si es “1” enviar un mensaje que diga; “loop numero X – Pasa por Punto B”
2º Ejercicio – Voltímetro
Mediante un potenciómetro vamos a poder variar manualmente el voltaje de una linea.,
Ese voltaje se puede detectar en una de las entradas analógicas con valores que varían entre 1023
para los 5 voltios y o para cero voltios,
Comunicar a la pantalla el voltaje de esa linea con dos decimales de precisión, con una frecuencia
aproximada de un segundo.
Para realizar este ejercicio tal como aquí se resuelve solo se necesitan los conocimientos que se
han ido explicando hasta el capítulo “Transmisión de Comunicaciones asíncronas “ que podemos
resumir en los siguientes puntos:
Saber establecer una comunicación entre la Tarjeta Arduino y el PC y conocer los mandatos
[Link], [Link] y [Link]
En función del valor de un numero aleatorio hay dos caminos posibles el A que recorre si el
numero aleatorio es par y el B si el número aleatorio es impar. Se trata de informar a la pantalla
del PC el número de loop que se esta ejecutando y si se pasa por el punto A o por el B. El mandato
random(max), devuelve de forma aleatoria un valor entre 0 y el valor marcado , excluido este
último. De forma que la linea
aleatorio = random(2)
Si es “o” enviar un mensaje que diga; “loop numero x – Pasa por Punto A”
Si es “1” enviar un mensaje que diga; “loop numero x – Pasa por Punto B”
Material necesario
Objetivo
Especificaciones
Al comienzo del loop generamos una valor aleatoria que puede ser 0, ó 1 mediante el mandato
“random” que guardamos en la variable “aleatorio”-
Si “aleatorio” es 0, hacemos escribir en el PC “loop numero x – valor de aleatorio Pasa por
Punto A”
en otro caso, hacemos escribir “loop numero x – valor de aleatorio Pasa por Punto B”
siendo x un contador que aumenta en con cada loop
Análisis funcional
El programa será pues en principio como sigue, aunque aun esta sujetos a cambios que surjan al
profundizar mas en el avance del análisis :
Observen
El mandato “random(max)” genera un valor aleatorio comprendido entre 0, y (max -1) ambos
incluidos, el número devuelto es del tipo long pero como en nuestro caso sólo será 0 o 1 podemos
guardarlo en una variable declarada como byte.
Todo lo demás no creo que a estas alturas les cree la menor dificultad para entenderlo. El ejemplo
es de una gran sencillez pero permite observar una de las utilidades mas grande las
comunicaciones asíncronas como es la puesta a punto de programas.
Cuando trabajamos con el simulador UnoArduSim, o con otros simuladores nos suelen dar
herramientas para saber en cualquier momento el valor de las variables y por donde pasa el
programa. No ocurre lo mismo cuando estamos y a con el programa y Arduino y trabajando
con la tarjeta en real.
Una forma de conocer el valor que adquiere una variable en un determinado punto o saber que
esta haciendo el programa es es poner mensajes que bien informan por donde ha pasado como
hacemos aquí poniendo ” – Pasa por punto A” y ” – Pasa por punto B”, o bien en donde
interese mandar como mensaje el valor de las variables motivo de estudio como nosotros hacemos,
con la variable “x“ y sobre todo “aleatoria” que si no fuese por este sistema, nunca podríamos
saber el valor que toma.
Una de los usos más típicos de esta comunicación es en la fase de poner a punto un programa,
Cuando un programa es un poco enrevesado, puede haber errores que sea difíciles de localizar en
que punto del programa se producen, porque por algún pequeño defecto, como por ejemplo haber
puesto mal los corchetes de inicio final de las funciones tipo “if” hacen que el programa actúe de
forma imprevista. En estos casos, resulta útil colocar en lugares estratégicos mandatos que carguen
el valor de las variables en esos puntos y los manden al PC para analizar si están adquiriendo o no
el valor previsto.
Otra uso habitual es recibir información en el PC de aquellos valores que queremos conservar y
elaborar, como por ejemplo hacer gráficas de temperaturas que se alcanzan en algún proceso
industrial, bien como control de calidad, bien simplemente para controlar el proceso. Por ejemplo
coordinando el ángulo de giro de una plataforma rotatoria y la altura de un sensor de distancias,
podemos hacer un scanner de tres dimensiones e ir enviando esas medidas a un Pc, para construir
la imagen tridimensional de los objetos puestos en estudio.
A la izquierda del último pin digital, el pin 13 aparece en Arduino UNO dos pines más, el
primero es el pin marcado como GND contracción de la palabra inglesa “ground” (suelo o tierra)
o lo que es lo mismo la entrada de cierre de un circuito con voltaje 0.
El siguiente pin situado a la izquierda viene marcado como AREF y si buscamos en el manual
veremos que es el acrónimo de Analog REFerence (referencia analógica, lo cual no indica mucho
más. Para eso para explicar la utilidad del pin AREF y el mandato asociado “analogReference· es
a lo que dedicamos este post.
La existencia de pin AREF y del mandato “analogReferenca”, se deben a la necesidad que a vece
se plantes de tener una lectura de los sensores de extrordinaria prrecisión. Como indicamos en el
capítulo dedicado a las entradas analógicas, los sensores son capaces de traducir una medida de
una manifestación física cualquiera, sonido, luz, distancia, temperatura, etc. en una corriente
electrica cuyo voltaje varía proporcionalmente a la intensif¡dad de lo que miden. Por su parte
Arduino el capaz de comparar el voltaje que recibe por una entrada analógica y compararla con
un voltaje de 5v y en funcion de eso generar un valor comprendido entre 0 y 1024, que ya
podemos utilizar en nuestro programa para mandar hacer a Arduino lo que consideremos v.
El problema es que en funcion del sensor que utilicemos y la manofestación física que queramos
monitorizar se produciran un rango de voltajes determinados. Por ejemplo si con un termómetro
pensado para medir la temperatura de la calle que puede variar d entre -25º y 75º deseamos medir
la temperatura del cuerpo humano que como mucho varía entre los 34º y loa 48º o podremos
hacerlo, pero el problema es que el voltaje 0v querrá decir que se miden -25º y el voltaje 5v 75º
por lo que el rango de los 5 voltios mide 100º o lo que es lo mismo a 1º de remperatura es
equivalente a 0,05v, por un lado, y por otro 1024 unidades equivales a 5v luego a un grado le
correponden 200 unidades.
Primer problema que se nos plantea, el termómetro utilizado lo mas que mide son grados
centigrados, es decir con el podremos saber si un señor esta a 36º o a 37º pero no si esta a 36,6º,
segundo problema 34º minimos de una persona viva le corresponde en nuestro cas,o un voltaje
aproximad de (0,05 x (25 +34) =2,95 volts aproximadamete 590 unidades y los 48º cmtigrados
( 0,05 x( 25 +48) =3,65 Volts aproximadammente 730 unidades.
Observen que el problema en nuestro caso reside en que dificilmente un termómetro pensado para
medir la temperatura de la calle, marcará con precision las décinmas de temperatura pero por otro
lado de las 1024 fracciones que nos puede proporcionalr Arduino al final terminamos utilizando
una gana muy pequeña. Tememos pues que por un lado elegir un sensor no solo que mida los que
deseamos medir sino que lo mis da en un rango y precisión adecuado a lo que va a medir.
Evidentemente para medir la temperatura del cuerpo humano, es conveniente utilizar como sensor
un termómetro clínico, que sólo medirá temperaturas dentro del rango adecuado, pero con
precisión de décimas, pero por el otro lado, convendría que los 1024 niveles que mide Arduino, se
repartieran entre los voltajes máximos y mínimos que por lógica podemos recibir.
Vamos a repasar antes para que valían las entradas analógicas. En el post anterior vimos este
montaje que con su software que pongo a continuación, media el voltaje de un circuito mediante
una derivación hecha con el cable amarillo a un pin analógico. EL voltaje que aumenta o
disminuye según girara el potenciómetro, encendiendo un led cada 0,5 voltios o sea que 5 leds
encendidos supriman un voltaje entre 2,5v y 3v. (Si tienes alguna duda sobre su funcionamiento
mira el post dedicado a las Salidas Analógicas)
/*
Prueba de pin Analógico
Voltímetro. Cada led encendido equivale a 0,5 volts
por el circuito que contiene el potenciómetro
Este ejemplo es de dominio público
*/
// Declaración de variables
int tension =0; // variable que almacena el voltaje (de 0 a 1023)
espera1 =1000; // milisegundos de espera para dar tiempo a hacer la lectura
// indicadores de estado de los Led 0=apagado 1=encendido
int encendido2 =0;
int encendido3 =0;
int encendido4 =0;
int encendido5 =0;
int encendido6 =0;
int encendido7 =0;
int encendido8 =0;
int encendido9 =0;
int encendido10 =0;
int encendido11 =0;
void setup() {
// incializa los pines 2 a 11 como OUTPUT
pinMode(2, OUTPUT);
pinMode(3, OUTPUT);
pinMode(4, OUTPUT);
pinMode(5, OUTPUT);
pinMode(6, OUTPUT);
pinMode(7, OUTPUT);
pinMode(8, OUTPUT);
pinMode(9, OUTPUT);
pinMode(10, OUTPUT);
pinMode(11, OUTPUT);
}
void loop() {
tension = analogRead(A0); // 1º) realizar la lectura por el pin A0
// 2º) Encender un led por cada 100 unidades de tension
if tension > 100 { // si es mayor que 100 (0.5v)
digitalWrite(2, HIGH);
encendido2 =1; // led del pin2 como encendido
}
if tension > 200 {
digitalWrite(3, HIGH);
encendido3 =1;
}
if tension > 300 {
digitalWrite(4, HIGH);
encendido4 =1;
}
if tension > 400 {
digitalWrite(5, HIGH);
encendido5 =1;
}
if tension > 500 {
digitalWrite(9, HIGH);
encendido9 =1;
}
if tension > 900 {
digitalWrite(10, HIGH);
encendido10 =1;
}
if tension > 1000 {
digitalWrite(11, HIGH);
encendido8 =11;
}
// Acabados de encender los led que marcan cada uno 0,5v
delay(espera1); // 3º) esperar para que se capte la lectura
// 4º) Apagar los led encendidos
if encendido2 =1; // si esta encendido el led 2, lo apagamos
digitalWrite(2, LOW);
encendido2 =0; // ponemos el indicador en apagado
}
if encendido3 =1;
digitalWrite(3, LOW);
encendido3 =0;
}
if encendido4 =1;
digitalWrite(4, LOW);
encendido4 =0;
}
if encendido5 =1;
digitalWrite(5, LOW);
encendido5 =0;
}
if encendido6 =1;
digitalWrite(6, LOW);
encendido6 =0;
}
if encendido7 =1;
digitalWrite(7, LOW);
encendido7 =0;
}
if encendido8 =1;
digitalWrite(8, LOW);
encendido8 =0;
}
if encendido9 =1;
digitalWrite(9, LOW);
encendido9 =0;
}
if encendido10 =1;
digitalWrite(10, LOW);
encendido10 =0;
}
if encendido11 =1;
digitalWrite(11, LOW);
encendido11 =0;
}
} // Fin de la funcion loop
La entrada analógica nos genera un valor comprendido entre 0 y 1023 que es proporcional al
voltaje, de modo que si el voltaje es 0v, el valor que obtenemos es 0, mientras que si el voltaje es
5v, el valor será 1023 unidades, lo que hace que aproximadamente por cada 0,5v, aumente 100
unidades la respuesta.
Pero, claro está, tal como está construido este circuito, el voltaje que reciba el potenciómetro
nunca será 5v porque la resistencia de 220 Ω reducirá la tensión que llega al potenciómetro, por lo
tanto,una parte de muestro contador que media de 0 a 5 voltio no se va a utilizar nunca.
En el propio post dimos una solución, hacer que cada led se encienda no a los 0,5v, sino a los
0,4v, de modo que solo podremos medir voltajes sólo de 0 a 4 voltios, pero con mayor precisión.
Sin embargo, lo que no podemos es evitar con este sistema, es desaprovechar una parte de la
escala de 1024 valores que genera Arduino. Si medimos como mucho cuatro voltios, nunca
recibiremos respuestas superiores a 800 unidades, con lo que estamos desaprovechando un 20%
de su precisión, pero si el voltaje máximo fuera de solo un voltio, solo aprovechamos unas 200
unidades desaprovechando un 80%
Pudiera ocurrir, que si necesitamos mucha precisión en la lectura, deseemos tener los 1024
niveles de respuesta repartidos, no entre O y 5 voltios que es lo estándar, sino entre 0 y 4 voltios
en el primer caso o entre 0 y 1 voltio, ¿Como lo podemos conseguirlo?
Para eso está el pin AREF, y el mandato analogReference(EXTERNAL). El reparto de los 1024
niveles se hace en proporción del voltaje de la corriente que entra por AREF, si esta es de 4
voltios los 1024 niveles se reparten entre o y 4 voltios y si entra 1v. se reparten entre 0 y un
voltio, por tanto mediante este mandato la lectura será mucho más fina que con la comparación
estándar.
Un ejemplo
Sé, que por más que he intentado explicarlo esta explicación es un poco confusa, pero espero que
un ejemplo pueda aclararla. Sólo necesito cambiar un mínimo tanto el hardwar como el programa.
Veamos como queda el muevo montaje.
Modificaciones en el hardware
Como ves, la única diferencia con el montaje anterior, es un cable verde que esta en el lado
izquierdo de la imagen, que conecta el cable que entra en el potenciómetro con el pin AREF.
Este cable permite llevar a AREF el máximo voltaje que entra en el potenciómetro y que nos
valdrá como referencia a la hora de comparar el voltaje medido en AO, de modo que si A0 no
detecta voltaje, seguirá dando el valor 0, pero si el potenciómetro fuera de resistencia 0Ω el
voltaje saliente sería igual al voltaje entrante por lo que el valor generado sería 1023 unidades.
/*
Prueba de pin AREF
Mide la proporcion de voltaje que deja pasar el potenciómetro.
Se enciende una luz por cada 10% del votaje inicial que queda
una vez atravesado el potenciómetro
Este ejemplo es de dominio público
*/
// Declaración de variables
int primer_loop =1; // control del primer loop 1 = primero 2= los siguientes
int tension =0; // variable que almacena el voltaje (de 0 a 1023)
espera1 =1000; // milisegundos de espera para dar tiempo a hacer la lectura
// indicadores de estado de los Led 0=apagado 1=encendido
int encendido2 =0;
int encendido3 =0;
int encendido4 =0;
int encendido5 =0;
int encendido6 =0;
int encendido7 =0;
int encendido8 =0;
int encendido9 =0;
int encendido10 =0;
int encendido11 =0;
void setup() {
// incializa los pines 2 a 11 como OUTPUT
pinMode(2, OUTPUT);
pinMode(3, OUTPUT);
pinMode(4, OUTPUT);
pinMode(5, OUTPUT);
pinMode(6, OUTPUT);
pinMode(7, OUTPUT);
pinMode(8, OUTPUT);
pinMode(9, OUTPUT);
pinMode(10, OUTPUT);
pinMode(11, OUTPUT);
// Compara entradas analógicas con el voltaje del pin AREF
analogReference(EXTERNAL); }
void loop() {
if primera_vez =1{ // Cosas que solo se hacen la primera vez
tension = analogRead(A0);
tension = analogRead(A0);
primera_vez =2;
}
tension = analogRead(A0); // 1º) realizar la lectura por el pin A0
// 2º) Encender un led por cada 100 unidades de tension
if tension > 100 { // si es mayor que 100 (0.5v)
digitalWrite(2, HIGH);
encendido2 =1; // led del pin2 como encendido
}
if tension > 200 {
digitalWrite(3, HIGH);
encendido3 =1;
}
if tension > 300 {
digitalWrite(4, HIGH);
encendido4 =1;
}
if tension > 400 {
digitalWrite(5, HIGH);
encendido5 =1;
}
if tension > 500 {
digitalWrite(9, HIGH);
encendido9 =1;
}
if tension > 900 {
digitalWrite(10, HIGH);
encendido10 =1;
}
if tension > 1000 {
digitalWrite(11, HIGH);
encendido8 =11;
}
// Acabados de encender los led que marcan cada uno 0,5v
delay(espera1); // 3º) esperar para que se capte la lectura
// 4º) Apagar los led encendidos
if encendido2 =1; // si esta encendido el led 2, lo apagamos
digitalWrite(2, LOW);
encendido2 =0; // ponemos el indicador en apagado
}
if encendido3 =1;
digitalWrite(3, LOW);
encendido3 =0;
}
if encendido4 =1;
digitalWrite(4, LOW);
encendido4 =0;
}
if encendido5 =1;
digitalWrite(5, LOW);
encendido5 =0;
}
if encendido6 =1;
digitalWrite(6, LOW);
encendido6 =0;
}
if encendido7 =1;
digitalWrite(7, LOW);
encendido7 =0;
}
if encendido8 =1;
digitalWrite(8, LOW);
encendido8 =0;
}
if encendido9 =1;
digitalWrite(9, LOW);
encendido9 =0;
}
if encendido10 =1;
digitalWrite(10, LOW);
encendido10 =0;
}
if encendido11 =1;
digitalWrite(11, LOW);
encendido11 =0;
}
} // Fin de la funcion loop
Modificaciones en el software
Observen
El “aparato” diseñado ha dejad de ser un voltímetro, puesto que ahora cada led pasa de indicar
0,5v para indicar que es el 10% de la corriente que entra en el potenciómetro. Como la
corriente que llega es aproximadamente, 3,75 voltios cada luz encendida representa en este caso
0,357 voltios de modo que si antes 5 ledz encendidos indicaban un voltaje entre 2,5 y 3 voltios,
ahora es un voltaje comprendido entre el 50% y el 6% del voltaje que entra al
potenciómetro, es decir aproximadamente de 1,875v u 2,250v, luego tenemos una lectura más
precisa.
Sintaxis de “analogReference”
(DEFAULT) – Referencia analógica por defecto, de 5 voltios en Arduino UNO, (puede ser de 3,3v
en algunos Arduino compatibles)
(INTERNAL) – Donde compara con 1,1 voltios la mayoría (pero no en todas las tarjetas
compatibles Arduino
(INTERNAL1V1) – Para comparar con 1.1v en Arduino Mega solamente
(INTERNAL2V56) – Para comparar con 2.56v en Arduino Mega solamente
(EXTERNAL) – Para comparar con la tensión aplicada al pin AREF (0 a 5V solamente).
/*
Prueba de lectura entradas analogicas con cambio de referencia
Mide en las vueltas pares el porcentaje de voltaje que deja pasar el
potenciometro (un led encendido equivalente al 10% del voltaje)
y en las vueltas impares el voltaje (un led encendido eauivale a 0,5V
Este ejemplo es de dominio público
*/
// Declaración de variables
int par_impar =0; // control de vuelta par 0 = par 1 = impar
int tension =0; // variable que almacena el voltaje (de 0 a 1023)
espera1 =1000; // milisegundos de espera para dar tiempo a hacer la lectura
// indicadores de estado de los Led 0=apagado 1=encendido
int encendido2 =0;
int encendido3 =0;
int encendido4 =0;
int encendido5 =0;
int encendido6 =0;
int encendido7 =0;
int encendido8 =0;
int encendido9 =0;
int encendido10 =0;
int encendido11 =0;
void setup() {
// incializa los pines 2 a 11 como OUTPUT
pinMode(2, OUTPUT);
pinMode(3, OUTPUT);
pinMode(4, OUTPUT);
pinMode(5, OUTPUT);
pinMode(6, OUTPUT);
pinMode(7, OUTPUT);
pinMode(8, OUTPUT);
pinMode(9, OUTPUT);
pinMode(10, OUTPUT);
pinMode(11, OUTPUT);
}
void loop() {
if par_impar =0{ // Loop par
analogReference(EXTERNAL); // Compara con voltaje de AREF
par_impar =1;
}
else { // Loop impar
analogReference(DEFAULT); // Compara con 5 voltios
par_impar =0;
}
tension = analogRead(A0); // hace dos lecturas perdidas
tension = analogRead(A0);
tension = analogRead(A0); // 1º) realizar la lectura por el pin A0
// 2º) Encender un led por cada 100 unidades de tension
if tension > 100 { // si es mayor que 100 (0.5v)
digitalWrite(2, HIGH);
encendido2 =1; // led del pin2 como encendido
}
if tension > 200 {
digitalWrite(3, HIGH);
encendido3 =1;
}
if tension > 300 {
digitalWrite(4, HIGH);
encendido4 =1;
}
if tension > 400 {
digitalWrite(5, HIGH);
encendido5 =1;
}
if tension > 500 {
digitalWrite(9, HIGH);
encendido9 =1;
}
if tension > 900 {
digitalWrite(10, HIGH);
encendido10 =1;
}
if tension > 1000 {
digitalWrite(11, HIGH);
encendido8 =11;
}
// Acabados de encender los led que marcan cada uno 0,5v
delay(espera1); // 3º) esperar para que se capte la lectura
// 4º) Apagar los led encendidos
if encendido2 =1; // si esta encendido el led 2, lo apagamos
digitalWrite(2, LOW);
encendido2 =0; // ponemos el indicador en apagado
}
if encendido3 =1;
digitalWrite(3, LOW);
encendido3 =0;
}
if encendido4 =1;
digitalWrite(4, LOW);
encendido4 =0;
}
if encendido5 =1;
digitalWrite(5, LOW);
encendido5 =0;
}
if encendido6 =1;
digitalWrite(6, LOW);
encendido6 =0;
}
if encendido7 =1;
digitalWrite(7, LOW);
encendido7 =0;
}
if encendido8 =1;
digitalWrite(8, LOW);
encendido8 =0;
}
if encendido9 =1;
digitalWrite(9, LOW);
encendido9 =0;
}
if encendido10 =1;
digitalWrite(10, LOW);
encendido10 =0;
}
if encendido11 =1;
digitalWrite(11, LOW);
encendido11 =0;
}
} // Fin de la funcion loop
Modificaciones en el software
Observen
Volvemos a tener un ejemplo claro como primero, ligeros cambios en programa pueden dar
lugar a cambios sorprendentes en el funcionamiento de un mismo hardware, segundo que es
posible a un equipo ya proyectado, “actualizar el firmware” de modo que sin cambios mecánicos
en el aparato su funcionamiento varié, algo muy utilizado actualmente con todos los aparatos
unidos a Internet, al fin y al cabo una versión de una app, es una “actualización del firware”
Como norma general el uso de esta posibilidad de mejora de la lectura de sensores SÓLO DEBE
UTILIZARSE cuando sea INPRESCINDIBLE, lo cual es muy raro, porque normalmente son
los sensores que utilizamos los que son incapaces de discernir con tanta finura los diferentes
niveles del objeto que evaluaran y de nada nos vale que por programa definamos la centésima de
grado centigrado si el sensor solo es capas de darnos una aproximación de una décima de grado en
el mejor de los casos.
En segundo lugar debernos tener en cuenta muy bien lo que estaos haciendo, primero ya que lo
hacemos introducir como voltaje de referencia un voltaje, con seguridad es superior al más alto
que vayamos a leer en las entradas analógicas y ademas muy próximo por arriba ,de la entrada
mas alta, pues si no, la ganancia de calidad de lectura que tennos es muy reducida.
De hacer lecturas por varias entradas analógicas, debemos de estar seguros en cada lectura de estar
haciendo una comparación con una referencia mayor que la le entrada por el pin de entrada
analógica pues en otro caso podemos quemar el Arduino. Es especial hay que tener cuidado si
vamos a hacer lecturas con comparación EXTERNAL o INTERMAL o con DEFOUTL pues si
previamente no hemos puesto el nivel adecuado de comparación podemos dar lugar a un error que
rompa la Tarjeta Arduino.
Ademas puede ocurrir que de utilizar el mandato analogReference , que la tarjeta Arduino no
soporte alguno de los parámetros estándar (con Arduino UNO por ejemplo los parámetros
“INTERNAL1V1” y “INTERNAL2V56” o en otras tarjetas que DEFOULT suponga 3, 3v en
vez de 5v). Lo que ocasiona que el programa funcione bien con unas tarjetas pero no con otras.
Por todo ello ,salvo de ser una NECESIDAD INEVITABLE aconsejo no utilizar este mandato ni
el pin AREF. Este post solo tiene la utilidad de que sepamos para que valen simplemente.
Mandatos utilizados
Material necesario
s un capítulo estrictamente teórico por lo que no se precisa de material , n6 6bstante c6n e3 f5n de
q4e ex*er50enten y 4t535cen 36s 5nterr4*t6res se ac6nse1a e3 4s6 de:
Todos estos conocimientos se explican en detalle en el capitulo “Principales opciones del Menú
de Inicio de Arduino”
Interruptores
Los interruptores son de los componentes más sencillos que utilizaremos en nuestros montajes
electrónicos y a pesar de ello, son indispensables en múltiples circuitos. Su función es permitir o
impedir, a nuestra voluntad el paso de la corriente por un circuito eléctrico.
En este esquema se representan los dos estados posibles de un interrptor, abierto y cerrado,
Cuando está abierto, impide el paso de la corriente y por tanto el led que hay en el circuito se
mantiene apagados. Cuando cerramos el interruptor, la corriente circula por el circuito y el led
emite luz.
Aunque la función de cualquier interruptor es siempre la misma, abrir o cerrar un circuito, hay
muchos tipos de interruptores y algunos son un poco más complicados que el representado en este
esquema. Por ejemplo, el siguiente esquema presenta un interruptor que dependiendo de la
posición que tenga envía la corriente por un circuito o por otro pero ni impide el paso de la
corriente por alguno de los circuitos ni conecta ambos a la vez.
Por ejemplo uniendo dos leed, uno rojo y uno verde a estos circuitos, podríamos hacer un
semáforo y tener la seguridad que uno de los dos led brillaría siempre y nunca lo harían los dos a
la vez
Un uso corriente con estos interruptores, son las llaves combinadas que se ponen en los pasillos.
Desde cualquiera de ellas podemos encender la luz si esta apagada o apagarla si está encendida
como indica el esquema que pongo a continuación.
Tipos de interruptores
Existe una amplia variedad de interruptores, cada uno diseñado específicamente para satisfacer
necesidades concretas, por ello es imposible hacer una clasificación de todos los interruptores
existentes, pues según para que se van utilizan tendrán formas y propiedades diferentes,
Encontraremos en el mercado todo tipo de interruptores específicamente diseñados para realizar el
trabajo de abrir y cerrar circuito de una forma segura tato para la tarea encomendada como para
quien lo utilice.
Si busca en Internet encontrará cientos de ellos todos diferentes, por ejemplo el primero que
enseño se utilizaba antiguamente para interrumpir la corriente trifásica industrial, mientras, que en
la actualidad tiene la forma que enseño a la derecha
No obstante, en los circuitos digitales los más comunes los modelos como estos que enseñamos
que se pueden agrupar en varias familias concretas, pulsadores, llaves, pulsadores rotativo y
pulsadores magnéticos..
Son interruptores que se caracterizan en que cambian de fase, (pasa de abierto o cerrado o
viceversa), solamente el tiempo en que se aprietan un botón. Un ejemplo muy conocido es el
timbre de la puerta, en el que solo cierra el circuito del timbre, durante el tiempo que mantenemos
apretados el botón del pulsador. Así pues el pulsador tiene un estado de reposo, al pulsar el botón
cambia de estado para volver al estado de reposo tan pronto como cesan de pulsar el botón
En general el mecanismo es un muelle que mantiene en una posición dada un contacto hasta que la
pulsación le obliga a cambiar de posición
Según como estén los pulsadores en estado de reposo se dividen en dos grupos, los normalmente
abierto (Normally Open NO) y los normalmente cerrado (Normally Closet NC), los mas
habituales son los primeros los NO, que en su estado normal, (no presionado), mantiene cortada la
corriente como en el esquema que menos puesto un poco más arriba. Al ser pulsados, cierran el
circuito. Por el contrario los NC funcionan al revés, dejan pasar la corriente hasta que se oprime el
pulsador.
Pongo uno debajo de otro los esquemas de los dos tipos de pulsadores
Hay incluso pulsadores con cuatro contactos que según conectemos los cables del circuito puede
funcionar indistintamente como NO o como NC. Añado el esquema de estos últimos, en estado de
reposo conecta dos bornes y mantiene separados el otro par y viceversa
Conmutadores o swiches
Son interruptores en los que el estado se mantiene fijo por tiempo indefinido, en la posición que
los dejemos, abierto o cerrado un circuito, Son las habituales llaves de la luz con dos posiciones
abiertas o cerradas que utilizamos habitualmente para encender la luz eléctrica. El esquema que lo
representa indica claramente cual de los dos posibles estados, abierto o cerrado tiene en ese
momento.
Muchos de los switch o llavde ña luz están preparadas para servir de llaves combinadas, su
esquema e sería como el que muestra la imagen Como ven en este caso hay tres bornes de salida,
uno de ellos es común, en nuestro caso el del centro y los otros dos es donde se unen dos circuitos
diferentes de los que en solo uno de los dos circulará la corriente.
Interruptores rotatorios
Una generalización de este mecanismo son los interruptores rotatorios, en el que girando el
interruptor, se va conectando consecutivamente diferentes circuitos que realizan cada uno de ellos
una cierta actividad.
El blog Open Electronics, explica cómo “convertir” una placa Arduino en un controlador como
PLC, sin tener que gastar un montón de dinero en materiales y capacitación.
Los relés son similares a los pulsadores que vinos en primer lugar solo que en vez de tener que
pulsar un botón, electrolizan hace la misma función de apretar el pulsador según una corriente
eléctrica cree un campo magnético o no.
Cuando pasa la oriente suministrada por los dos terminales de la izquierda la varilla vertical
central abandona el contacto NC ( normalmente cerrado) y entra contacto con el contacto NO
normalmente abierto y así se mantiene mientras pase corriente por la bobina , y cuando este cesa
vuelve a su posición inicial de reposo.
Los relees permiten controlar con circuitos electrónicos que utilizan corrientes eléctricas de
muy baja energía, aparatos eléctricos que necesitan consumir mucha energía, como en general
son los electrodomésticos que nos rodean. Por ejemplo, podemos controlar el funcionamiento de
una bombilla, mediante una tarjeta Arduino. Por tanto los relés permiten que podamos trasformar
todo lo que hasta ahora eran maquetas en objetos reales de uso normal. Igual que una bombilla
podríamos haber conectado cualquier aparato eléctrico. De ahí la importancia del relé, hace de
punte entre el mundo de la electrónica y el mundo de la electricidad que es el que
habitualmente nos rodea.
Generalmente los relés tienen por un extremo las dos bornes que alimentan a la bobina uno
conectado a tierra y otro conectado a 5Volts al que llegara corriente o no según controle una
tarjeta Arduino. En el otro extremo hay habitualmente tres bornes de los que utilizaremos al
menos dos, el denominado común, (COM), y uno de los bornes, o el normalmente cerrado (NC) y
el normalmente abierto (NO). A veces en vez de venir indicado con estas iniciales, viene indicado
algo mas crípticamte con una lineas que están en contacto o separadas.
Siendo un aparato ampliamente utilizado, con frecuencia un mismo elemento contiene diversos
relés, aunque estén puestos juntos el funcionamiento de cada uno, es el mismo que tendrían si
fueran independientes, e incluso con frecuencia no utilizaremos la totalidad de los que contiene la
tarjeta. Por ejemplo este componente agrupa cuatro relés.
Para terminar, tenga en cuenta cuando tenga que utilizar un interruptor, la forma de su
funcionamiento. En caso de duda . Antes de utilizarlo, hacer pruebas utilizando los interruptores
en sencillos circuitos formados por el interruptor, una resistencia de 240 Ohmios y un led
orientado de forma que la pata más larga (ánodo) quede unida a la fuente de 5 Voltios y la corta
(cátodo) quede conectado a tierra, tal como se ve en los esquemas puesto al inicio del post.
Repaso
El objetivo del era familiarizarlos con todo tipo de interruptore y explicar los diferentes modelos
dentro de un tipo.
Por Félix
Maocho
22/11/2015
Curso de Arduino – Utilizar los pin digitales como entradas de corriente a un circuito
Repaso de los pin digitales de Arduino utilizados como OUPUT es decir como interruptores de
circuitos así como de algunas de las instrucciones o mandatos más habituales.
Para las prácticas de este post se necesita la tarjeta controladora Arduino, la tarjeta de prototipado
protoboard, (conveniente pero no necesaria), un PC, el cable de conexión a Arduino, un led, (en
nuestro caso rojo, puede ser de cualquier color), una resistencia variable (llamadas a veces
reostatos o potenciometros) y una resistencia fija de 220 homios, así como los cables de conexión ,
(macho/macho si se trabaja con tarjeta protoboard).
Preliminar
La tarjeta Arduino es una controladora de circuitos eléctricos, es decir un sistema capaz de activar
mediante un programa, diversos interruptores para mantener con ellos apagados o encender,
diversos circuitos eléctricos a corriente continua de 5 voltios. Por tanto su misión principal es
encender y apagar según le indiquen algunas instrucciones sus múltiples salidas/entradas. En este
post nos centraremos en el uso como OUTPUT o sea salidas digitales es decir, como interruptores
de los pines las marcados con los números 0 al 13 que solo tienen en estado OUPUT dos estados
posibles, (con alguna matización que estudiaremos). o estar abiertas, o estar cerradas y actuar
permitiendo fluir la energía, del pin hacia el sumidero o tierra marcado con las letras GND, o
cortar circuito y no dejar fluir la electricidad.
En la imagen de entrada se encuentran en el borde superior de la tarjeta Arduino, Los pines 0 y 1,
además de ser digitales como las demás, tiene un uso específico que es servir de entrada/salida de
las comunicaciones asíncronas, (Reception/trasmition),(RX/TX), o sea de transmisión y recepción
de de datos enviados o procedentes de otros aparatos. Ello hace que, de no ser imprescindible,
deban dejar en el proyecto libres y sin usarlos como pines digitales, pues con frecuencia, durante
el proceso de depuracion de programas, es muy conviente comunicar al PC, por esta vía, el valor
que adquire una variabe en un determinado paso de ejecución de un programa.
Salida digitales
Los pines vienen configurados como de entrada por defecto, El motivo es que así protegen mejor
la placa si por error reciben una descarga de 5 volts, Cando se configuran como de salida y por
error de reciben una descarga eléctrica, posiblemente resulta dañada la placa. Por ese motivo y
como medida de precaución cualquier pin de salida se le pone en serie habitualmente una
resistencia de nos 220 Ω como protección.
Las salidas input/ouput de Arduino son capaces de producir una salida de electricidad a 5
Voltios, aunque con un transferencia de energía de 40 miliamperimetros, y como total podremos
tener funcionando a la vez 5 salidas es decir 200 miliamperímetros, cantidad muy reducida, pero
suficiente para hacer brillar un lee un led que conectemos a estos Pin, así como podemos
conseguir que el Led parpadee, simplemente mandando salir o no salir energía por el pin.
El montaje del hardware es muy sencillo conectamos el pin 13 que es el que vamos a utilizar en
este caso con un resistencia de 220 Ω precaución que se toma para evitar cortocircuitos, a esta
resistencia se conecta el ánodo (la pata mas larga) del Led y el cátodo se conecta a un cable que va
a tierra (GND).
Para que luzca el led. la corriente debe circular en el sentido del ánodo al cátodo, en el sentido
contrario, ni luce ni deja pasar la corriente. Tal como está si el Pin 13 deja pasar corriente el led
lucirá si no pasa estará apagado.
Puesto que en el post indicado allí tiene detallado este ejemplo, aquí como recordatorio sólo
pongo el programa que gobernaba este ejemplo.
/*
Parpadea
Enciende un LED un segundo , luego por otro segundo lo apaga y repite
Este ejemplo es de dominio público
*/
// Declaración de variables
int salida = 13; // Damos al parámetro “salida” el valor 13
void setup() {
// inicializa el pin Numero = “salida”· (=13) como de salida (output).
pinMode(salida, OUTPUT);
}
void loop() {
digitalWrite(salida, HIGH); // Ponemos el pin parámetro “salida” en HiGH (alto)
// HIGH equivale a 5 volts que es lo que da el pin
delay(1000); // espera por un segundo = 1000 milisegundos
digitalWrite(salida, LOW); // Ponemos el pin parámetro “salida” en LOW (bajo)
// LOW equivale a 0 volts o sea sin corriente
delay(1000); // espera por un segundo = 1000 milisegundos
}
En la función “setup”, (que Arduino como viene mandado de fábrica solo recorre la primera vez
que se ejecuta el programa enciende de fabrica), informamos a la tarjeta que utilizaremos el pin
“salida” como OUPUT, es decir que permitirá salir energía a 5 volts.
En la función “loop”, (que Arduino como viene mandado de fábrica recorre en bucle una vez tras
otra mientras el programa esté conectado a la fuente de energía), indicamos que ponga en HIGH el
pin llamado “salida” espere un segundo, ponga el pin llamado “salida” en LOW y espere un
segundo, es decir que deje salir corriente a 5 volts, durante un segundo y lo tenga apagado durante
otro segundo.
Si en este circuito sustituimos la resistencia que hay en el circuito por una resistencia
variable, podremos hacer que el led luzca más o menos brillante, aumentando y disminuyendo la
resistencia, lo cual es lógico porque la ley fundamental de la electricidad dice que la intensidad
de la corriente es da diferencia de potencial dividido por la resistencia:
Como el pin produce siempre corriente a 5 Voltios (V), a más resistencia (R) tiene que haber
menor intensidad de corriente (I) y como la energía eléctrica consumida de una corriente es en
un determinado tiempo. es proporcional a la intensidad de la corriente. Para dispar la
energía más deprisa, el led lucirá más brillante mientras que si la resistencia aumenta el led
tendrá que disipar menos energía en el mismo tiempo, por tanto lucirá más tenue.
El circuito tendrá entonces esta forma, como ven hemos sustituido una resistencia de 220 Ω, que
evita que llegue excesivo voltaje al led por una resistencia variable, potenciómetro o reostato,
que según se gire la cabeza presenta mas o menos resistencia, logícamente si aumentamos la
resistencia disminuye el brillo de la luz y viceversa.
En este caso como ya no va a parpadear, pues si queremos que no luzca bata con poner la máxima
resistencia no necesitamos los tiempos de espera, ni encender ni apagar el led, basta encenderlo en
la primera vuelta y ya está, la luz subirá o bajará según demos nosotros al reostato, el programa
por tanto lo modificaremos de esta forma.
/*
Regulador de luz
Enciende un LED en la primera y luce más o menos de acuerdo
con lo que giremos a el reostato
Este ejemplo es de dominio público
*/
// Declaracion de variables
int primera_vuelta =1 // Damos a la varianble “primera_vuelta” el valor inicial 1
int salida = 13; // Damos al parámetro “salida” el valor 13
void setup() {
// incializa el pin Numero = “salida”· (=13) como de salida (output).
pinMode(salida, OUTPUT);
}
void loop() {
// Solo si “primera_vuelta” = 1 hace lo siguiente
if primera_vuelta = 1 {
digitalWrite(salida, HIGH); // Ponemos el pin parámetro “salida” en HiGH (alto)
// HIGH equivale a 5 volts que es lo que da el pin
primera_vuelta = 0 // pone primera_vuelta a 0 para no volverlo a hacer
}
// en la primera vuelta enciende el pin y en las demás no hace nada mas.
}
Como podemos comprobar moviendo el reostato podemos hacer que luzca mas o menos fuerte o
incluso apagar del todo girando al máximo de resistencia el reostato.
Recordemos lo que es el cine, una serie de fotogramas que se enseñan en rápida secuencia de
forma que le ojo humano no detecta lo que ocurre entre ambos fotogramas, que no es mas que una
cortinilla negra que cubre la imagen mientras se sustituye un fotograma por el siguiente, el cine va
a 24 imágenes por segundo y en televisión son 25.
Pues bien, como solo podemos ver 24 imágenes por segundo, vamos a hacer que esas imágenes
brillen más o menos, ¿Como, si no podemos cambiar la intensidad de la corriente, pues jugando
con la duración, como la energía consumida es la intensidad por el tiempo, si reducimos el tiempo
durante el cul pasa la intensidad, reducimos la energía, es decir que si en el mismo tiempo se gasta
menos energía, la luz brillará menos.
Así pues cada segundo haremos pasar 25 ciclos de apagado y encendido, por tanto cada ciclo dura
una venticincoava parte de mil milésimas, es decir 40 milésimas, de las que un tiempo, estará
encendido y el resto apagado, cuanto más tiempo esté encendido mas energía se gastará y más
brillará.
Vamos a comprobarlo. Sólo nos basta modificar algo el primer programa de intermitencia. Cada
ciclo en vez de durar dos segundos, durar-a solo 40 milsegundos y repartidos en dos periodos, uno
encendido, que durara 40-x milisegundos y otro apagado que durará x segundos. Vamos a ir
aumentando y disminuyendo poco a poco a para cver que la intensidad de la luz baja y sube.
El hardware será igual que en el primer caso y el led estará alimentado por el pin 13
/*
Parpadeo del brillo
Enciende un LED poco a poco, y lo vuelve a a apagar lentamente y repite
Este ejemplo es de dominio público
*/
// Declaracion de variables
int salida = 13; // Damos al parámetro “salida” el valor 13
int x = 0; // Damos a la variable “x” el valor 0
int sube = 1 ; // Damos al parámetro “sube” el valor 1
void setup() {
// incializa el pin Numero = “salida”· (=13) como de salida (output).
pinMode(salida, OUTPUT);
}
void loop() {
x= x + 1;
if x = 40 { // Si x alcanza el valor 40 cambiamos a “sube” = 0
sube = 0;
}
x= x – 1;
if x = 0 {
sube = 1;
Claro está, que como casi siempre en informática hay otras forma de conseguir hacer las mismas
cosas y unas son más sencillas que otras. Los informáticos valoramos la sencillez, pues cuanto
más sencillo es algo menos probabilidades hay de que al programarlas se mos pase por alto algo y
metamos la pata, aparte que para poner a punto un programa, cuantas menos líneas tenga mejor
que mejor.
Existen unos determinados pin que internamente por hardware hacen exactamente lo mismo
que yo he hecho a mano, encender y apagar muchas veces el pin de forma que se pueda controlar
con cierta facilidad, cuanta energía sale por el pin son las salidas PWM (puelse width
modulation) o en castellano pines de pulso modulado, que son los pines que habitualmente junto
al número de pin tienen dibujado el carácter “~” y que en Arduino UNO normalmente son los
pines 3, 5, 6, 9, 10 y 11.
Si se fijan bien en las placas Arduno UNO representadas en los esquemas anteriores a las salidas
3, 5, 6, 9, 10 y 11 las antecede un pequeño “~”, mientras que al resto de los pines o sea el 2, 4, 7,
8, 12 y 13, carecen de este símbolo, eso indica que las salidas 3, 5, 6, 9, 10 y 11 son ademas de
salidas con las mismas características que el resto de los pines, Salidas PWM o salida con
modulación.
La diferencia es que mientras que todos los
pines puede enviar una corriente continua de 5 voltios, o no enviarla, los que pueden modular la
corriente, en vez de mandar una corriente continua, mandan pulsos eléctrico de corta duración
seguido de otro corto momento en que esta apagada la corriente. Como ven exactamente lo mismo
que lo que hemos hecho nosotros con software en el caso anterior. Y puesto que lo hacen ellos no
lo tendremos que hacer nosotros.
Lo que si le tendremos que decir que tipo de pulso queremos mandar. Como ven en el dibujo,
en nuestra mano esta desde no mandar nada de energía, tener la salida siempre a 0 volts, a estar
mandando siempre, o sea tener la salida a 5 volts.
En estos casos extremos, funcionan como cualquier pin o mandan o no mandan energís, pero hay
muchas posibilidades intermedias, como mandar un 35% un 50% o un 75% del tiempo 5 voltios y
el resto de tiempo cero voltios,
En concreto tenemos 256 pulsos diferentes, Este numero 256 se lo encontraran muchas veces en
informática, como en general se encuentran cualquiera de las potencias de 2 (256 es 2 a la octava
potencia, y en base dos se es el número mayor que se escribe en un octeto, (ocho bits, o mínimos
de información binaria, que tiene dos valores posibles, si o no, cargado o descargado, 0 ó y 1 ). El
nuestro caso serán ocho unos, que indican que el número 255 = 1+2+4+8+16+32+64+128 o sea
con el “cero” los 255 posibles pulsos que pueden salir por los pin PWM.
¿Como se usan estos pin? – Pues observe las diferencia con el programa anterior, Lo primero será
que el circuito eléctrico del Led ha de estar unido a un pin PWM. Como el 13, no lo es PWM, lo
trasladamos al 11, El resto del circuito sigue valiendo igual como se ve en la foto. También hemos
puesto nuevamente la resistencia de 220 homios pues en algun momento el voltaje será de 5
voltios y se podría provocar un cortocircuito. Lo que varia bastante es el programa que pasa a ser ;
/*
Parpadea del brillo usando pin PWM
Enciende un LED poco a poco, y lo vuelve a a apagar lentamente y repite
Este ejemplo es de dominio público
*/
// Declaracion de variables
int salida = 11; // Damos al parámetro “salida” el valor 11 en vez de 13
int x = 0; // Damos a la variable “x” el valor 0
int sube = 1; // Damos al parámetro “sube” el valor 1
void setup() {
// No es necesario unuculzar el pin como output.
// por tanto en este caso en la funcion setup no hay que hacer nada
}
void loop() {
sube = 0;
x= x – 1;
if x = 0 {
sube = 0;
Observen que tuvimos que definir las mismas variables y con los mismos valores, excepto “salida”
que ahora vale 11 porque utilizaremos el pin 11 que es PWM La estructura de subir y bajar el
valor del brillo no cambia salvo que en este caso tenemos que movernos entre los valores 0 y 255
En setup no hacemos nada los pin PMW están siempre abiertos indistintamente como de salida y
entrada, según hagamos analogWrite o analogRead sabran actuar de salida (Write=Escribir) o
entrada (Read=Leer)
Como internamente ya genera los impulsos variables según le indique x no tenemos que apagarlos,
los generara hasta que se mande otra cosa.
Aqui dejamos el primer capítulo dedicado al repaso del manejo de los pin de Arduino
Félix Maocho
PD
Resuminos las funciones de Arduino que hemos utilizado de no entender el funcionamiento o la
sintaxis de alguna buscarla en el Manual en español en PDF
Documentacion
Función Setup que solo se ejecuta al incio del programa void setup() { ……….}
Pausa delay(tiempo);
Incrementar una vriable var = var +1
Reducir una variable var = var – 1