Control Automático Educación

LCD I2C Raspberry Pi Pico

En esta guía completa, te enseñaremos a programar un LCD 16×2 I2C con la Raspberry Pi Pico utilizando MicroPython. Además, exploraremos cómo el mismo código y librería pueden ser aplicados en otras plataformas como NodeMCU ESP8266 o ESP32. Si estás trabajando con módulos I2C para pantallas LCD, este tutorial te proporcionará todas las herramientas y conocimientos necesarios para simplificar tus proyectos de electrónica.

Si estás familiarizado con otros microcontroladores como PIC o Arduino, y has trabajado con el protocolo I2C, este tutorial te resultará bastante sencillo. Si aún no has explorado el uso del I2C con PIC, te invitamos a revisar nuestra guía detallada sobre I2C con PIC, donde cubrimos la implementación de este protocolo en microcontroladores PIC como el PIC16F877A. También, si estás usando Arduino, no te pierdas nuestro tutorial sobre I2C con Arduino, donde exploramos cómo conectar y programar periféricos I2C como pantallas LCD en placas Arduino.

Antes de comenzar te invito a que visites nuestro CURSO GRATUITO DE MICROPYTHON en Raspberry Pi Pico o ESP.

Y que te suscríbas al canal, si te interesa los temas de programación en microcontroladores y principalmente la teoría de la ingeniería de control:

Entendiendo el Protocolo I2C: Comunicación Simple y Eficiente

El protocolo I2C (Inter-Integrated Circuit) es una tecnología de comunicación serie ampliamente utilizada en proyectos electrónicos, desde sistemas embebidos hasta microcontroladores como el Raspberry Pi Pico. Su principal ventaja es que permite conectar múltiples dispositivos a un mismo bus utilizando solo dos cables: SDA (Serial Data Line) para la transmisión de datos y SCL (Serial Clock Line) para la sincronización de estos datos.

i2c conexión
18. Comunicación I2C

¿Cómo Funciona I2C?

A diferencia de otros protocolos como SPI, que requiere múltiples cables para cada dispositivo, I2C simplifica la comunicación permitiendo que todos los dispositivos compartan el mismo bus de datos. Esto es posible porque cada dispositivo conectado al bus tiene una dirección única, que se utiliza para identificarlo durante la comunicación.

Cuando un dispositivo maestro, como la Raspberry Pi Pico, desea comunicarse con un dispositivo esclavo, como un LCD 16×2 o un sensor de temperatura, primero envía un pulso de reloj a través de la línea SCL para sincronizar todos los dispositivos en el bus. Luego, el maestro envía la dirección del esclavo con el que quiere comunicarse a través de la línea SDA, seguida por los datos que quiere transferir. El dispositivo esclavo que tiene la dirección correspondiente responde y recibe o envía los datos según sea necesario.

Configuración de Dispositivos en I2C

Para usar el I2C en tus proyectos con Raspberry Pi Pico o cualquier otro microcontrolador, lo primero que debes hacer es configurar los pines SDA y SCL en tu código. Estos pines deben estar conectados correctamente a los dispositivos esclavos, como el LCD I2C, que estamos utilizando en este tutorial. Por ejemplo, en la Raspberry Pi Pico, los pines comunes para I2C son el Pin 0 para SDA y el Pin 1 para SCL.

Es importante mencionar que el protocolo I2C también requiere la adición de resistencias pull-up en las líneas SDA y SCL para garantizar que las líneas se mantengan en un estado alto cuando no se está transmitiendo datos. Esto es esencial para evitar errores de comunicación en el bus I2C.

Aplicaciones del Protocolo I2C

El protocolo I2C es increíblemente versátil y se utiliza en una variedad de aplicaciones más allá de la conexión de pantallas LCD. Por ejemplo, puedes conectar varios sensores (como acelerómetros, giroscopios, o sensores de temperatura), módulos de memoria EEPROM, relojes en tiempo real (RTC), y más. La capacidad de conectar múltiples dispositivos a través de un solo bus hace que I2C sea la opción preferida en muchos proyectos de sistemas embebidos y electrónica.

En este tutorial, hemos enfocado nuestro uso de I2C en la Raspberry Pi Pico, pero si estás trabajando con otros microcontroladores como el ESP8266, ESP32, o incluso PIC y Arduino, el proceso es muy similar. La clave está en configurar correctamente los pines y entender cómo identificar la dirección I2C de cada dispositivo para asegurar una comunicación eficiente.

I2C con MicroPython en Raspberry Pi Pico / ESP8266/32

Una de las maneras más efectivas de conectar un LCD 16×2 o LCD 20×4 a una Raspberry Pi Pico o a un ESP8266/ESP32 es mediante un módulo I2C. Este protocolo simplifica considerablemente la conexión al usar solo dos pines: SDA y SCL. Si quieres aprender más sobre cómo configurar I2C en PIC o I2C en Arduino, no dudes en visitar nuestras guías especializadas.

Inicialmente, debemos conocer las funciones de i2c con micropython para poder determinar la dirección i2c del componente y posteriormente conectar la Raspberry Pi Pico lcd 16×2 i2c o el esp8266 micropython lcd i2c. A partir de la documentación oficial de MicroPython podemos determinar:

i2c = machine.I2Cid = -1 , * , scl , sda , frecuencia = 400000 )

Se construye el objeto I2C usando los siguientes parámetros:

Dirección Modulo LCD I2C

Cuando trabajas con un LCD 16×2 I2C en una Raspberry Pi Pico o un ESP8266 programado en MicroPython, es crucial identificar la dirección I2C del módulo para una correcta configuración. Este paso es similar al proceso que seguimos en otros microcontroladores, como los PIC o Arduino, donde también se requiere conocer la dirección I2C para establecer la comunicación adecuada. Puedes encontrar más información sobre cómo hacerlo en nuestros tutoriales dedicados a I2C en PIC y I2C en Arduino.

Podemos usar el siguiente código estandar con MicroPython para ver cual es la dirección del Módulo I2C.

import machine
import utime


i2c = machine.I2C(0, scl=machine.Pin(9), sda=machine.Pin(8), freq=200000)

direccion = hex(i2c.scan()[0])

print('La dirección I2C es ', direccion)

LCD I2C con MicroPython

En este tutorial de la Raspberry Pi Pico con Display LCD via I2c donde empleamos también el nodemcu esp8266 donde conectamos un lcd de los que venden en el mercado veremos como programarlo paso a paso en MicroPython.

Inicialmente, deberemos descargar alguna librería que sea capaz de controlar el LCD via I2C directamente con MicroPytho, esto la podremos encontrar directamente en el IDE de Thonny, pero para este caso usaremos la librería RPI-PICO-I2C-LCD (click para descargar)

Instalación de la Librería

Una vez descargada y descomprimida la librería, verás tres archivos con extensión .py. Para que la librería funcione correctamente en tu Raspberry Pi Pico, asegúrate de transferir los archivos lcd_api.py y pico_i2c_lcd.py a la memoria de la placa utilizando el IDE de Thonny. Si estás familiarizado con la configuración de I2C en otros microcontroladores, como los PIC o Arduino, este proceso te resultará sencillo y rápido.

Se abrirá la ventana de archivos, donde en la parte superior te muestra los archivos que tiene tu computador y en la parte inferior los archivos de tu raspberry pi pico, debes dar click derecho sobre los archivos que deseas pasar a la memoria de la pico y dar click donde dice Upload to/

Finalmente verifica que los archivos se encuentren dentro de la Flash de la PICO

Funciones de la librería

Raspberry Pi Pico LCD I2C

El circuito empleado en micropython con la Raspberry Pi Pico usando el módulo I2C y un LCD16x2 será el siguiente, donde alimentaremos el display con el pin VBUS de la placa (Pin 40)

ESP8266 LCD display

El circuito con el esp8266 empleando un lcd 16×2 será el siguiente:

Display 7 Segmentos

Código en MicroPython Display LCD – I2C

El siguiente código puede ser usado tanto con la Raspberry Pi Pico como en un ESP, a modo de ejemplo el NodeMCU ESP8266, basta solo configurar los pines empleados para la comunicación i2c.

import utime
from machine import I2C,Pin
from lcd_api import LcdApi
from pico_i2c_lcd import I2cLcd

#Dirección del I2C y tamaño del LCD
I2C_ADDR  =  0x27
I2C_NUM_ROWS = 2
I2C_NUM_COLS = 16

# Raspberry Pi Pico
i2c = I2C(0, sda=Pin(0), scl=Pin(1), freq=400000)

#Esp8266
#i2c = I2C(sda=Pin(4), scl=Pin(5), freq=100000)

#Configuración LCD
lcd = I2cLcd(i2c, I2C_ADDR, I2C_NUM_ROWS, I2C_NUM_COLS)

battery_0 = [0x0E,
  0x1B,
  0x11,
  0x11,
  0x11,
  0x11,
  0x11,
  0x1F]
battery_15 = [0x0E,
  0x1B,
  0x11,
  0x11,
  0x11,
  0x11,
  0x1F,
  0x1F]
battery_30 = [  0x0E,
  0x1B,
  0x11,
  0x11,
  0x11,
  0x1F,
  0x1F,
  0x1F]
battery_45 = [0x0E,
  0x1B,
  0x11,
  0x11,
  0x1F,
  0x1F,
  0x1F,
  0x1F]
battery_60 = [0x0E,
  0x1B,
  0x11,
  0x1F,
  0x1F,
  0x1F,
  0x1F,
  0x1F]
battery_75 = [0x0E,
  0x1B,
  0x1F,
  0x1F,
  0x1F,
  0x1F,
  0x1F,
  0x1F]
battery_100 = [0x0E,
  0x1F,
  0x1F,
  0x1F,
  0x1F,
  0x1F,
  0x1F,
  0x1F]


def lcd_str(message, col, row):
    lcd.move_to(col, row)
    lcd.putstr(message)


def main():
    lcd.custom_char(0, bytearray(battery_0))
    lcd.custom_char(1, bytearray(battery_15))
    lcd.custom_char(2, bytearray(battery_30))
    lcd.custom_char(3, bytearray(battery_45))
    lcd.custom_char(4, bytearray(battery_60))
    lcd.custom_char(5, bytearray(battery_75))
    lcd.custom_char(6, bytearray(battery_100))
    
    
    while True:
        lcd.clear()
        lcd_str("Battery:", 0, 0)
        lcd.move_to(0,1)
        for i in range(0,7):
            lcd.putchar(chr(i))
        utime.sleep(3)
        
        lcd.clear()
        lcd.move_to(0,0)
        lcd.putstr("Suscribete a    ")
        utime.sleep(1)
        lcd.move_to(0,1)
        lcd.putstr("Control       ")
        utime.sleep(1)
        lcd_str("Automatico    ", 0, 0)
        utime.sleep(1)
        lcd_str("Educacion    ", 0, 1)
        utime.sleep(1)
        
        lcd.clear()
        lcd_str("Numeros en", 3,0)
        lcd_str("Esquinas", 4,1)
        utime.sleep(1)
        
        lcd_str("1", 0,0)
        utime.sleep(1)
        lcd_str("2", 15,0)
        utime.sleep(1)
        lcd_str("3", 0,1)
        utime.sleep(1)
        lcd_str("4", 15,1)
        utime.sleep(1)
        
        lcd.clear()
        lcd_str("Suscribete", 0, 0)
        lcd_str("Activa: CAMPANA", 0, 1)
        lcd.blink_cursor_on()
        utime.sleep(2)
        
        #Backspace
        for j in range(1, -1, -1):
            for i in range(15, -1, -1):
                lcd.move_to(i, j)
                lcd.putstr(' ')
                utime.sleep_ms(100)
        utime.sleep(1)
        lcd.hide_cursor()
        
        #BackLight
        lcd.clear()
        lcd.backlight_off()
        lcd_str("BackLight OFF", 0, 0)
        utime.sleep(3)
        
        lcd.clear()
        lcd.backlight_on()
        lcd_str("BackLight ON", 0, 0)
        utime.sleep(3)


if __name__ == '__main__':
    main()

Eso es todo por la entrada del dia de hoy, espero les haya gustado y hayan aprendido algo nuevo. Si te ha servido el contenido de esta entrada, de los videos y los códigos de implementación y deseas apoyar mi trabajo invitandome a un café super barato, puedes hacerlo en el siguiente link:

👉 Invitar a Sergio a un Café ☕️

Que esten muy bien, nos vemos en la siguiente entrada.

Salir de la versión móvil