ESP32 HC-SR04 Medidor de distancia por ultrasonidos
El sensor ultrasónico HC-SR04 calcula la distancia midiendo el tiempo de vuelo (Time of Flight) de la onda sonora que emite al chocar contra un objeto y rebotar. En este proyecto, enviaremos un pulso de 10 microsegundos desde el ESP32 al pin TRIG del sensor y leeremos el tiempo de eco procedente del pin ECHO mediante `pulseIn()`. Mostraremos la distancia calculada en centímetros en una pantalla LCD I2C de 16x2. Dado que el HC-SR04 funciona a 5 V, es obligatorio utilizar un **divisor de tensión**

Video
Diagrama del circuito

Código fuente
1// ─────────────────────────────────────────
2// BlueGrays · bluegrays.com
3// ESP32 HC-SR04 Medidor de distancia por ultrasonidos
4// ─────────────────────────────────────────
5// Dispara el HC-SR04 con un pulso TRIG, calcula la distancia (cm) a partir
6// del tiempo de ECHO y la muestra en un LCD I2C de 16x2 cada 0.2 s. Si no
7// vuelve ningún eco, la pantalla muestra "Menzil disinda" (fuera de
8// rango).
9//
10// Pines:
11// GPIO 5 -> TRIG del HC-SR04
12// GPIO 18 -> ECHO del HC-SR04 (mediante un divisor de tensión)
13// Divisor: ECHO -> 1k -> GPIO 18 -> 2k -> GND
14// GPIO 21 -> SDA del LCD, GPIO 22 -> SCL del LCD
15// VCC del HC-SR04 y del LCD -> 5V (VIN), GND -> GND
16
17#include <Wire.h>
18#include <LiquidCrystal_I2C.h>
19
20// Definición de pines
21const int TRIG_PIN = 5;
22const int ECHO_PIN = 18; // Necesita un divisor de tensión de 1k + 2k
23
24// Dirección del LCD: 0x27 o 0x3F
25LiquidCrystal_I2C lcd(0x27, 16, 2);
26
27const float SOUND_SPEED_CM_PER_US = 0.0343f; // Velocidad del sonido (cm/us)
28const unsigned long PULSE_TIMEOUT_US = 30000UL; // Timeout del eco (~5 m)
29
30void setup() {
31 pinMode(TRIG_PIN, OUTPUT);
32 pinMode(ECHO_PIN, INPUT);
33 digitalWrite(TRIG_PIN, LOW);
34
35 // Pines I2C por defecto de la DevKit V1
36 Wire.begin(21, 22);
37
38 lcd.init();
39 lcd.backlight();
40
41 // Pantalla de bienvenida de 3 s
42 lcd.setCursor(3, 0);
43 lcd.print("BlueGrays");
44 lcd.setCursor(1, 1);
45 lcd.print("HC-SR04 v1.0");
46 delay(3000);
47
48 // Pantalla principal
49 lcd.clear();
50 lcd.setCursor(0, 0);
51 lcd.print("Mesafe:");
52}
53
54// Lee la distancia en cm, -1 si hay error
55float readDistanceCm() {
56 // Un pulso TRIG de 10 us inicia una medición
57 digitalWrite(TRIG_PIN, LOW);
58 delayMicroseconds(2);
59 digitalWrite(TRIG_PIN, HIGH);
60 delayMicroseconds(10);
61 digitalWrite(TRIG_PIN, LOW);
62
63 unsigned long duration = pulseIn(ECHO_PIN, HIGH, PULSE_TIMEOUT_US);
64 if (duration == 0) return -1.0f;
65 // Ida y vuelta, así que se divide entre 2
66 return (duration * SOUND_SPEED_CM_PER_US) / 2.0f;
67}
68
69void loop() {
70 float distance = readDistanceCm();
71
72 // Borrar la fila inferior
73 lcd.setCursor(0, 1);
74 lcd.print(" ");
75 lcd.setCursor(0, 1);
76
77 if (distance < 0) {
78 lcd.print("Menzil disinda");
79 } else {
80 lcd.print(distance, 1); // 1 decimal
81 lcd.print(" cm");
82 }
83
84 delay(200);
85}
86Preguntas frecuentes
¿Por qué se instala un divisor de tensión en la línea ECHO?▾
El HC-SR04 funciona a 5 V y el pin ECHO suministra 5 V; las entradas del ESP32 admiten un máximo de 3,3 V. El divisor de tensión, formado por resistencias de 1 kΩ y 2 kΩ, reduce los 5 V a aproximadamente 3,3 V y protege el ESP32.
¿Se necesita un divisor para el pin TRIG?▾
No. TRIG es una señal que va del ESP32 al sensor; el nivel alto de 3,3 V del ESP32 suele ser detectado de forma fiable por el HC-SR04.
¿Es necesario utilizar un divisor con el HC-SR04P?▾
Modelos como el HC-SR04P y el RCWL-1601 pueden alimentarse a 3,3 V; en ese caso, la salida ECHO también será de 3,3 V y no se necesitará un divisor de tensión.
¿Cómo se puede medir la distancia con mayor precisión?▾
La velocidad del sonido varía con la temperatura (aproximadamente 343 m/s a 20 °C). Corregir la velocidad del sonido mediante un sensor de temperatura y calcular la mediana de varias mediciones aumenta la precisión.
