Lector de tarjetas RFID RC522 para ESP32 (con LCD)
En este proyecto, conectaremos el módulo RFID RC522 basado en MFRC522 al ESP32 a través de SPI y leeremos el UID de la tarjeta o etiqueta. Esto constituye la base de aplicaciones como cerraduras, sistemas de afiliación y control de acceso. Mostraremos el UID leído en la pantalla LCD; esta versión no lo compara con una lista de tarjetas autorizadas. **ATENCIÓN:** El RC522 solo funciona a **3,3 V**; si le aplicas 5 V, ¡el módulo se quemará!

Video
Diagrama del circuito

Código fuente
1// ─────────────────────────────────────────
2// BlueGrays · bluegrays.com
3// Lector de tarjetas RFID RC522 para ESP32 (con LCD)
4// ─────────────────────────────────────────
5// Lee el módulo RFID RC522 por SPI; el UID de una tarjeta escaneada se
6// muestra en HEX durante 3 s en el LCD I2C de 16x2 y luego vuelve la
7// pantalla "scan a card".
8//
9// Pines:
10// GPIO 5 -> SDA (SS) del RC522
11// GPIO 18 -> SCK del RC522, GPIO 19 -> MISO del RC522, GPIO 23 -> MOSI del RC522
12// GPIO 27 -> RST del RC522
13// GPIO 21 -> SDA del LCD, GPIO 22 -> SCL del LCD
14// RC522 3.3V -> 3.3V del RC522 -> 3V3, IRQ se deja sin conectar
15// LCD VCC -> VCC del LCD -> 5V (VIN), todos los GND en común
16
17#include <Wire.h>
18#include <LiquidCrystal_I2C.h>
19#include <SPI.h>
20#include <MFRC522.h>
21
22// Definición de pines
23const int RST_PIN = 27; // RST del RC522
24const int SS_PIN = 5; // SDA (SS) del RC522
25
26// Los pines SPI son los VSPI por defecto
27MFRC522 rfid(SS_PIN, RST_PIN);
28LiquidCrystal_I2C lcd(0x27, 16, 2); // Dirección del LCD: 0x27 o 0x3F
29
30unsigned long lastScan = 0; // Hora del último escaneo (ms)
31const unsigned long DISPLAY_HOLD = 3000; // Tiempo de visualización del UID (ms)
32bool showingCard = false; // ¿Hay un UID en pantalla?
33
34// Pantalla de espera
35void showWaitMessage() {
36 lcd.clear();
37 lcd.setCursor(0, 0);
38 lcd.print("Kart okutun");
39 lcd.setCursor(0, 1);
40 lcd.print("Scan a card");
41}
42
43void setup() {
44 Wire.begin(21, 22); // I2C: SDA=21, SCL=22
45 lcd.init();
46 lcd.backlight();
47
48 // Pantalla de bienvenida de 3 s
49 lcd.setCursor(3, 0);
50 lcd.print("BlueGrays");
51 lcd.setCursor(3, 1);
52 lcd.print("RFID v1.0");
53 delay(3000);
54
55 // Iniciar SPI y el RC522
56 SPI.begin();
57 rfid.PCD_Init();
58 delay(50);
59
60 showWaitMessage();
61}
62
63void loop() {
64 // Cuando se acaba el tiempo, volver a la pantalla de espera
65 if (showingCard && millis() - lastScan > DISPLAY_HOLD) {
66 showWaitMessage();
67 showingCard = false;
68 }
69
70 // Salir si no hay tarjeta nueva o no se puede leer
71 if (!rfid.PICC_IsNewCardPresent() || !rfid.PICC_ReadCardSerial()) {
72 delay(50);
73 return;
74 }
75
76 // Imprimir el UID en HEX, p. ej. 0A:1B:2C:3D
77 lcd.clear();
78 lcd.setCursor(0, 0);
79 lcd.print("Kart UID:");
80 lcd.setCursor(0, 1);
81 for (byte i = 0; i < rfid.uid.size; i++) {
82 if (rfid.uid.uidByte[i] < 0x10) lcd.print("0");
83 lcd.print(rfid.uid.uidByte[i], HEX);
84 // Sin separador en un UID de 7 bytes: 14 caracteres caben en la fila
85 if (rfid.uid.size <= 5 && i < rfid.uid.size - 1) lcd.print(":");
86 }
87
88 lastScan = millis();
89 showingCard = true;
90
91 // Detener la tarjeta y parar el cifrado
92 rfid.PICC_HaltA();
93 rfid.PCD_StopCrypto1();
94}
95
Preguntas frecuentes
¿A qué pines del ESP32 conecto el RC522?▾
Se utilizan los pines SPI predeterminados del ESP32: SCK = GPIO 18, MISO = GPIO 19, MOSI = GPIO 23. Utiliza los pines indicados en el código (por ejemplo, 5 y 27) para SDA (SS) y RST; la tensión de alimentación debe ser obligatoriamente de 3,3 V.
¿Funcionan a la vez la pantalla LCD y el RFID?▾
Sí. Como la pantalla LCD utiliza I2C (GPIO 21/22) y el RC522 utiliza el bus SPI, no se interfieren entre sí; los dos canales de comunicación funcionan al mismo tiempo.
¿Por qué el UID tiene 4 bytes en algunas tarjetas y 7 en otras?▾
Las tarjetas MIFARE Classic suelen utilizar un UID de 4 bytes, mientras que las etiquetas MIFARE Ultralight y NTAG utilizan uno de 7 bytes. A la hora de comparar, debes comprobar también la longitud del UID.
¿Puedo añadir tarjetas autorizadas sin cambiar el código?▾
Sí, puedes escribir un módulo que, al leer la «tarjeta de administrador», añada la siguiente tarjeta a la lista, y puedes guardar la lista en la memoria permanente a través de Preferencias.
