En un artículo anterior les mostraba como instalar Micropython en una placa basada en el ESP 8266. Ahora seguiremos avanzando en el uso de este lenguaje viendo como conectarnos a un detector de movimiento a través de los pines de Entradas y Salidas, también llamados GPIO (General Purpose Input/Output, Entrada/Salida de uso general).
La clase machine
Para controlar distintos elementos del hardware, Micropython pone a nuestra disposición un módulo denominado machine que incluye, entre otras, la clase Pin. Esta clase nos permite definir objetos vinculados con los pines de entrada y salida y nos provee de distintos métodos para definir y controlar su funcionamiento. Por lo tanto lo primero que debemos hacer es incluir esa clase en nuestro programa:
from machine import Pin
Una vez hecho esto podemos crear o instanciar objetos de la clase Pin a través del siguiente constructor, que inicializa distintas características del objeto:
nombre = Pin (id, modo, pull, valor)
nombre : El identificador del objeto asociado con el pin
id: El identificador o número del pin físico. En el ESP8266 podemos usar los pines 0, 1, 2, 3, 4, 5, 12, 13, 14, 15 y 16. Es obligatorio proveer un identificador de pin.
Identificador de pin
Hay que tener cuidado con el identificador de pin. Las distintas placas que emplean el ESP8266 tienen su propia identificación (Como D0, D1, etc). Como MicroPython debe funcionar en todas ellas, utiliza solamente la numeración física del ESP8266 (GPIO0, GPIO1, etc). Se debe consultar la documentación de cada placa para conocer la correspondencia entre pines físicos y la identificación usada en esa placa
modo: Indica si el pin es entrada (Pin.IN) o salida (Pin.OUT). Su uso es opcional. Si no se especifica, se asume que el modo es Entrada.
pull: Especifica si se activa o no el PULL UP cuando el pin se configura como entrada. Es opcional, si no se especifica, no se activa el PULL UP. Si se suministra el valor Pin.PULL_UP se activa el PULL UP correspondiente. En el ESP8266, en los pines 0 a 15 se puede activar el PULL UP, el 16 tiene un PULL DOWN.
valor: Permite definir el valor del pin (0 o 1) cuando se lo configura como salida en el momento de su creación. También es opcional, si no se suministra un valor, no se inicializa el pin.
Ejemplos
LedIncluido = Pin (2, Pin.OUT) #define como salida el pin 2
Salida = Pin (5, Pin.OUT, value=1) #define como salida el pin 5 y lo inicializa a 1
Tecla = Pin (16, Pin.IN) #define como entrada el pin 16
Tecla = Pin (4, Pin.IN, pull=Pin.PULL_UP) #define como entrada el pin 4 y activa el PULL UP interno
Métodos
Para actuar sobre los pines, la clase Pin pone a nuestra disposición una serie de métodos:
value()
Permite especificar el valor de un pin configurado como salida o leerlo si está configurado como entrada. Ejemplos:
print (Tecla.value()) #imprime el valor de la entrada "Tecla"
Salida.value (1) #fija la salida "Salida" a 1
on ()
Pone a 1 un pin configurado como salida.
off ()
Pone a 0 un pin configurado como salida. Ejemplo:
while (True):
Salida.on ()
sleep (1)
Salida.off ()
sleep (1)
init (modo, pull, valor)
Reinicializa el pin con los parámetros suministrados. Sólo se cambian los argumentos especificados, mientras que el resto permanece inalterado. El significado de cada parámetro es el mismo que se explicó mas arriba en el constructor. En el siguiente ejemplo se puede ver que se declara un pin como entrada y luego se lo cambia a salida con el método init:
datos = Pin (4, Pin.IN)
datos.init (Pin.OUT, value=1)
Aplicación: Detector de movimiento con sensor PIR
Vamos a aplicar lo aprendido hasta ahora a un caso práctico construyendo un detector de movimiento con un sensor PIR, un sensor de Infrarrojos similar al HC-SR 501 y una placa Nodemcu.
El sensor cuenta con tres pines, Vcc (alimentación de 5 volts), OUT (Salida de activación) y GND. Pueden existir muchas variaciones, de acuerdo al fabricante. La placa del que yo utilicé es la siguiente:
Tiene dos controles para ajustar el tiempo en que permanece activa la salida al detectar el movimiento y la sensibilidad, un selector de Modo de salida (en la posición H la salida permanece activa mientras se detecte movimiento y en la posición L la salida se activa por un tiempo determinado) y el conector de tres pines ya explicado.
El Nodemcu utilizado es el modelo denominado “V3” y tiene la siguiente asignación de pines
Las conexiones del detector de movimiento se muestran en la siguiente imagen:
Como se puede ver, el circuito consiste en el Nodemcu, que tiene un led conectado a D1, un buzzer conectado a D5 y el sensor conectado a D2. Tanto el led como el zumbador sirven para indicar que se ha detectado movimiento. El sensor se debe alimentar con 5V, los que se toman de la salida Vu (V usb) del Nodemcu. En otros modelos este pin no está disponible y esta tensión debe tomarse de V in.
El programa se muestra a continuación. En la primer parte se incluyen los módulos necesarios y luego se crean los pines a utilizar, buzzer para el zumbador en GPIO14 (D5) , declarado como salida e inicializado a un valor 0, led para el led en GPIO5 (D1) también declarado como salida e inicializado a 0 y PIR, una entrada en GPIO4 (D2) para leer la salida del sensor.
A continuación se definen dos funciones, bip () que activa la salida buzzer por 0.2 segundos para luego desactivarla, haciendo un corto “bip” en el zumbador y flash () que prende y apaga rápidamente 10 veces el led.
Finalmente, la parte principal del programa consiste en un bucle que se repite indefinidamente en donde se consulta si el valor de la entrada PIR es 1. Si eso ocurre, se llama alas funciones bip y flash para indicar que el sensor ha detectado movimiento. Si en cambio la entrada vale 0, no sucede nada y se repite el bucle.
#Detector de movimientos con sensor PIR
#Prueba de control de GPIO
from machine import Pin
from time import sleep
buzzer = Pin (14, Pin.OUT, value = 0) #Salida del zumbador
led = Pin (5, Pin.OUT, value = 0) #Salida del LED
PIR = Pin (4, Pin.IN) #Entrada del sensor
def bip (): #Hace sonar un bip
buzzer.on ()
sleep (0.2)
buzzer.off ()
def flash (): #Prende el led 10 veces
for veces in range (0,10):
led.on ()
sleep (0.1)
led.off ()
sleep (0.5)
while (True):
if (PIR.value()==1): #Se activa la salida del sensor?
bip ()
flash ()
En el video pueden ver como funciona el detector de movimiento
Conclusión
Vimos en este artículo cómo acceder a los pines de entrada y salida a través de Micropython y lo aplicamos a un caso sencillo, el de leer un sensor de movimiento. En los siguientes artículos veremos como utilizar mas funcionalidades de este potente lenguaje.
Cualquier duda o sugerencia, la pueden dejar mas abajo en los comentarios.