Coche fantástico Arduino: secuencia de LEDs, circuito y código
Coche fantástico con Arduino: 8 LEDs con 220 Ω, código con array y bucle for, velocidad con potenciómetro, millis, 74HC595, WS2812B, ESP32 y Pico.
El coche fantástico con Arduino es un clásico efecto de LEDs en el que una fila de LEDs se enciende uno tras otro, recorre la fila de un extremo a otro y vuelve, igual que la luz frontal de KITT, el coche que hablaba en la famosa serie de los años 80 El coche fantástico (El auto increíble en Latinoamérica, Knight Rider en inglés). Solo necesitas un Arduino Uno, 6 u 8 LEDs, una resistencia de 220 Ω por cada LED y algunos cables jumper. Si la luz avanza en una sola dirección y vuelve a empezar desde el principio, se llama secuencia de LEDs o luz corrediza. Los dos son proyectos clásicos que se hacen justo después del semáforo y la forma más divertida de aprender dos de las herramientas más importantes de la programación: los arrays y el bucle for.
En esta guía montarás el circuito y escribirás primero el código de la secuencia simple y después el del coche fantástico, que va y vuelve. Luego ajustarás la velocidad con un potenciómetro, añadirás un efecto en el que los LEDs se acumulan en un extremo y harás funcionar el mismo efecto con millis() sin bloquear nunca el código. En las últimas secciones verás cómo controlar 8 LEDs con solo 3 pines usando el chip 74HC595, cómo hacer un coche fantástico con estela desde un único pin con LEDs direccionables WS2812B, las versiones para ESP32 y Raspberry Pi Pico (MicroPython) y las soluciones a los errores más comunes.

¿Qué es el efecto coche fantástico y en qué se diferencia de una secuencia de LEDs?
En la serie, la luz roja del parachoques delantero de KITT barre sin parar de izquierda a derecha, como un ojo que vigila. En electrónica este efecto también se llama escáner Larson (Larson scanner), por el productor de la serie, Glen A. Larson; los ojos de los robots cylon de su otra serie, Galáctica, funcionan igual. En el escáner real se ve detrás del punto encendido una estela roja que se apaga poco a poco, una cola. En un circuito de LEDs sencillo cada LED está totalmente encendido o totalmente apagado; para imitar la estela hay que bajar el brillo de los LEDs de forma gradual con PWM. Lo haremos más adelante con los WS2812B y el ESP32. La tabla resume los efectos que vas a programar en este artículo y cuántos pasos dura una vuelta con 8 LEDs.
| Efecto | Qué hace | Una vuelta con 8 LEDs | En este artículo |
|---|---|---|---|
| Secuencia simple | Una sola luz avanza de izquierda a derecha y vuelve a empezar | 8 pasos | Paso 1 |
| Coche fantástico | Una sola luz va y vuelve entre los dos extremos | 14 pasos | Pasos 2 y 3 |
| LEDs que se acumulan | Cada luz corre hasta el último hueco libre de la derecha y se queda allí | 36 pasos | Paso 4 |
| Encuentro en el centro | Dos luces llegan desde los extremos al centro y luego se separan | 8 pasos | Sección 74HC595 |
| Coche fantástico con estela | El LED de cabeza brilla al máximo y los de detrás se van apagando | 14 pasos | Secciones WS2812B y ESP32 |
Materiales y cómo elegir la resistencia
| Material | Cantidad | Nota |
|---|---|---|
| Arduino Uno (o Nano) | 1 | También vale un ESP32 o una Raspberry Pi Pico |
| LED de 5 mm | 6–8 | Del mismo color y del mismo lote para que brillen igual |
| Resistencia de 220 Ω | 6–8 | Una por LED; 330 Ω en la Pico |
| Potenciómetro de 10 kΩ (B10K) | 1 | Solo para las versiones con velocidad ajustable |
| Protoboard | 1 | Basta con media protoboard (400 puntos) |
| Cables jumper | 12–15 | Macho-macho |
| 74HC595 o tira WS2812B de 8 LEDs | 1 | Opcional: para las secciones de ahorro de pines y de efecto con estela |
Un LED no limita su propia corriente, así que cada LED lleva una resistencia en serie. El valor se calcula con la ley de Ohm: R = (tensión de alimentación − tensión directa del LED) / corriente. Un LED rojo tiene una tensión directa de unos 2 V, de modo que a 5 V con 220 Ω la corriente es (5 − 2) / 220 ≈ 13,6 mA. Así el LED brilla bastante y te quedas por debajo de los 20 mA recomendados para un pin de Arduino. En el efecto de LEDs que se acumulan, cuando los ocho LEDs están encendidos a la vez, la corriente total es de unos 109 mA, todavía dentro del límite de 200 mA que el Uno admite sumando todos los pines. Para reconocer una resistencia de 220 Ω por sus bandas de color usa la herramienta código de colores de resistencias; para otros colores y tensiones, la calculadora de resistencia para LED.
Conexión del circuito: 8 LEDs y un potenciómetro
La pata larga (ánodo) de cada LED va a través de una resistencia a un pin digital de la placa, y la pata corta (cátodo) a GND. En la protoboard lo más ordenado es unir el pin GND del Arduino a la línea azul (−) y llevar las patas cortas de los ocho LEDs a esa línea. Coloca los LEDs con la misma separación, de izquierda a derecha y en el orden de los pines; así el orden del array en el código coincide con el orden físico de la luz. Las dos patas exteriores del potenciómetro van a 5V y GND, y la pata central (el cursor) a A0. La tabla muestra los pines que usan todos los códigos de este artículo; si usas 6 LEDs, sáltate las dos últimas filas de LEDs y borra los dos últimos pines del array en el código. Puedes ver la distribución de pines de tu placa en la herramienta Pinout.
| Función | Arduino Uno | ESP32 | Raspberry Pi Pico |
|---|---|---|---|
| LED 1 (extremo izquierdo) | D2 | GPIO 18 | GP8 |
| LED 2 | D3 | GPIO 19 | GP9 |
| LED 3 | D4 | GPIO 21 | GP10 |
| LED 4 | D5 | GPIO 22 | GP11 |
| LED 5 | D6 | GPIO 23 | GP12 |
| LED 6 | D7 | GPIO 25 | GP13 |
| LED 7 | D8 | GPIO 26 | GP14 |
| LED 8 (extremo derecho) | D9 | GPIO 27 | GP15 |
| Pata central del potenciómetro | A0 | GPIO 34 | GP26 (ADC0) |
| Patas exteriores del potenciómetro | 5V y GND | 3V3 y GND | 3V3(OUT) y AGND |
| Cátodos de los LEDs (pata corta) | GND | GND | GND |
| Resistencia en serie | 220 Ω | 220 Ω | 330 Ω |




Paso 1: código de la secuencia de LEDs con array y bucle for
Podrías escribir ocho líneas pinMode y dieciséis líneas digitalWrite para ocho LEDs, pero el código se alarga y cambiar el número de LEDs se vuelve pesado. En su lugar guardas los números de pin en un array y lo recorres en orden con un bucle for. El primer elemento del array es LEDS[0], es decir, D2; el último es LEDS[7], es decir, D9. Así el mismo código funciona sin cambios con 6, 8 o 12 LEDs; solo editas el array. Tienes los fundamentos de arrays y bucles explicados con más detalle en Fundamentos de programación de Arduino.
1// Yürüyen LED: 8 LED sırayla yanar / Running light: 8 LEDs light up one after another
2const int LEDS[] = {2, 3, 4, 5, 6, 7, 8, 9}; // LED pinleri / LED pins
3const int LED_SAYISI = sizeof(LEDS) / sizeof(LEDS[0]); // dizideki LED sayısı (8) / number of LEDs (8)
4const int BEKLE = 100; // adım süresi (ms) / step time (ms)
5
6void setup() {
7 for (int i = 0; i < LED_SAYISI; i++) {
8 pinMode(LEDS[i], OUTPUT); // tüm LED pinleri çıkış / all LED pins as outputs
9 }
10}
11
12void loop() {
13 for (int i = 0; i < LED_SAYISI; i++) {
14 digitalWrite(LEDS[i], HIGH); // sıradaki LED'i yak / light the next LED
15 delay(BEKLE);
16 digitalWrite(LEDS[i], LOW); // söndür ve devam et / turn it off and move on
17 }
18}| Línea | Qué hace |
|---|---|
| const int LEDS[] = {2, ..., 9}; | Array que guarda los pines de los LEDs en orden de izquierda a derecha; LEDS[0] = 2, LEDS[7] = 9 |
| sizeof(LEDS) / sizeof(LEDS[0]) | Calcula el número de elementos: en el Uno 16 bytes / 2 bytes = 8; se actualiza solo cuando añades o quitas pines |
| for (int i = 0; i < LED_SAYISI; i++) | Cuenta la variable i de 0 a 7; en cada vuelta se procesa un elemento del array |
| pinMode(LEDS[i], OUTPUT) | Configura los ocho pines como salida con un solo bucle |
| digitalWrite, delay(BEKLE), digitalWrite | Enciende el LED, espera BEKLE milisegundos, lo apaga y pasa al siguiente |
Con BEKLE (el tiempo de paso) a 100 ms, la luz recorre los ocho LEDs en 0,8 segundos y vuelve a empezar enseguida. Si lo bajas a 30 ms, el recorrido es muy rápido; si lo subes a 300 ms, parece lento, como lámparas que se encienden una a una. Para cargar el código elige la placa y el puerto en el menú Herramientas y pulsa Subir; si la carga falla, repasa la lista de comprobación de Arduino no sube el código.
Paso 2: código del coche fantástico (ida y vuelta)
Para el efecto coche fantástico la luz tiene que dar la vuelta al llegar al extremo derecho. Lo haces con dos bucles: el primero cuenta de izquierda a derecha y el segundo de derecha a izquierda. El detalle importante está en los LEDs de los extremos. Si los dos bucles cuentan completos de 0 a 7 y de 7 a 0, el LED de la derecha se enciende una vez al final del bucle de ida y otra vez al principio del de vuelta; la luz se queda el doble de tiempo en los extremos y el movimiento parece dar tirones. Por eso el bucle de ida se detiene en 6 y el de vuelta en 1. Así cada vuelta dura exactamente 14 pasos y la luz se queda en los extremos lo mismo que en el centro. Además, hemos pasado las tres líneas que encienden y apagan un LED a una pequeña función llamada yakSondur() ("encender y apagar"); el código queda más corto y más fácil de leer.
1// Karaşimşek (Knight Rider): ışık iki uç arasında gidip gelir / light bounces between the two ends
2const int LEDS[] = {2, 3, 4, 5, 6, 7, 8, 9};
3const int LED_SAYISI = sizeof(LEDS) / sizeof(LEDS[0]);
4const int BEKLE = 80; // adım süresi (ms) / step time (ms)
5
6void yakSondur(int i) {
7 digitalWrite(LEDS[i], HIGH);
8 delay(BEKLE);
9 digitalWrite(LEDS[i], LOW);
10}
11
12void setup() {
13 for (int i = 0; i < LED_SAYISI; i++) pinMode(LEDS[i], OUTPUT);
14}
15
16void loop() {
17 for (int i = 0; i < LED_SAYISI - 1; i++) { // soldan sağa: 0..6 / left to right: 0..6
18 yakSondur(i);
19 }
20 for (int i = LED_SAYISI - 1; i > 0; i--) { // sağdan sola: 7..1 / right to left: 7..1
21 yakSondur(i);
22 }
23}Paso 3: ajustar la velocidad con un potenciómetro
En lugar de cambiar el código y volver a cargarlo cada vez que quieras otra velocidad, puedes usar un potenciómetro. Un potenciómetro es un divisor de tensión: la tensión de la pata central varía entre 0 y 5 V según la posición del eje, y analogRead() la convierte en un número entre 0 y 1023. map(deger, 0, 1023, 400, 20) transforma ese número en un tiempo de paso entre 400 y 20 ms; como el rango está escrito al revés, cuanto mayor es la lectura, más corto es el paso y más rápida va la luz. Hacia qué lado tienes que girar para acelerar depende de qué pata exterior conectaste a 5V; si te parece al revés, intercambia los dos cables exteriores o el 400 y el 20 en map(). Puedes leer cómo funciona un potenciómetro por dentro en ¿Qué es un potenciómetro?.

1// Hız ayarlı karaşimşek: potansiyometre adım süresini belirler / Speed-adjustable Knight Rider: the pot sets the step time
2const int LEDS[] = {2, 3, 4, 5, 6, 7, 8, 9};
3const int LED_SAYISI = sizeof(LEDS) / sizeof(LEDS[0]);
4const int POT = A0; // potansiyometrenin orta bacağı / pot wiper
5
6int adimSuresi() {
7 int deger = analogRead(POT); // 0–1023
8 return map(deger, 0, 1023, 400, 20); // değer büyüdükçe hızlanır / faster as the value rises
9}
10
11void yakSondur(int i) {
12 digitalWrite(LEDS[i], HIGH);
13 delay(adimSuresi()); // her adımda yeniden okunur / read again on every step
14 digitalWrite(LEDS[i], LOW);
15}
16
17void setup() {
18 for (int i = 0; i < LED_SAYISI; i++) pinMode(LEDS[i], OUTPUT);
19}
20
21void loop() {
22 for (int i = 0; i < LED_SAYISI - 1; i++) yakSondur(i); // sağa / to the right
23 for (int i = LED_SAYISI - 1; i > 0; i--) yakSondur(i); // sola / to the left
24}En esta versión el tiempo de paso se vuelve a leer en cada LED, así que la velocidad cambia en cuanto giras el eje. Sin embargo, mientras delay() está en marcha, el Arduino no puede hacer nada más: aunque gires el eje en mitad de un paso lento de 400 ms, la nueva velocidad solo se aplica a partir del siguiente paso. Para un efecto con unos pocos LEDs no es un problema, pero cuando añadas un botón para cambiar de modo o lecturas de sensores tendrás que pasar al método con millis() del paso 5.
Paso 4: el efecto de LEDs que se acumulan
En el efecto de LEDs que se acumulan, la primera luz corre hasta el final de la derecha y se queda encendida allí. La segunda luz también corre, pero esta vez se detiene una posición más a la izquierda; en cada vuelta el destino se desplaza un LED a la izquierda hasta que toda la barra se llena. En el código lo haces con dos bucles anidados: el exterior cuenta cuántos LEDs se han acumulado (dolu, "lleno") y el interior cuántos pasos corre la luz en esta vuelta. El LED que llega a su destino (hedef) no se apaga; de eso se encarga precisamente la línea if (i < hedef). Con ocho LEDs, llenar toda la barra lleva 8 + 7 + 6 + ... + 1 = 36 pasos.
1// Birikerek dolan efekt: her ışık en boş uca kadar gider ve orada kalır / Stacking effect: each light runs to the last free spot and stays
2const int LEDS[] = {2, 3, 4, 5, 6, 7, 8, 9};
3const int LED_SAYISI = sizeof(LEDS) / sizeof(LEDS[0]);
4const int BEKLE = 60;
5
6void setup() {
7 for (int i = 0; i < LED_SAYISI; i++) pinMode(LEDS[i], OUTPUT);
8}
9
10void loop() {
11 for (int dolu = 0; dolu < LED_SAYISI; dolu++) { // dolu: sağda birikmiş LED sayısı / LEDs already stacked on the right
12 int hedef = LED_SAYISI - 1 - dolu; // bu turda ışığın duracağı yer / where the light stops this round
13 for (int i = 0; i <= hedef; i++) {
14 digitalWrite(LEDS[i], HIGH);
15 delay(BEKLE);
16 if (i < hedef) digitalWrite(LEDS[i], LOW); // hedefte yanık kalır / stays lit at the target
17 }
18 }
19 delay(600); // dolu çubuğu göster / show the full bar
20 for (int i = LED_SAYISI - 1; i >= 0; i--) { // sağdan sola boşalt / empty from right to left
21 digitalWrite(LEDS[i], LOW);
22 delay(BEKLE);
23 }
24 delay(300);
25}Al final del código la barra llena se muestra durante 0,6 segundos, después los LEDs se apagan uno a uno de derecha a izquierda y el efecto vuelve a empezar. Si quieres una barra que se llena más sencilla, basta con quitar el bucle interior y encender los LEDs en orden sin apagarlos nunca; ese aspecto es ideal para un indicador de carga o una barra de nivel de sonido. Recuerda que en este efecto los ocho LEDs están encendidos a la vez: mientras cada LED tenga su propia resistencia, el brillo no baja.
Paso 5: coche fantástico sin bloqueo con millis()
En el código que usa delay(), el Arduino se congela durante el tiempo indicado en cada paso; aunque alguien pulse un botón mientras tanto, no se entera. millis(), en cambio, devuelve los milisegundos que han pasado desde que se encendió la placa. La lógica es esta: el bucle gira sin parar, en cada vuelta comprueba si ha pasado suficiente tiempo desde el último paso y, si es así, da un solo paso y sale enseguida. En el código siguiente el coche fantástico y el LED integrado funcionan a la vez como dos tareas independientes: mientras la luz recorre la fila a la velocidad que marca el potenciómetro, el LED de D13 parpadea una vez por segundo a su propio ritmo. Para saber más, consulta Arduino millis() y delay().
1// millis() ile bekletmesiz karaşimşek + potansiyometre / Non-blocking Knight Rider with millis() + pot
2const int LEDS[] = {2, 3, 4, 5, 6, 7, 8, 9};
3const int LED_SAYISI = sizeof(LEDS) / sizeof(LEDS[0]);
4const int POT = A0;
5
6int konum = 0; // şu an yanan LED / the LED that is lit now
7int yon = 1; // +1 sağa, -1 sola / +1 right, -1 left
8unsigned long sonAdim = 0; // son adımın zamanı / time of the last step
9unsigned long sonBlink = 0; // dahili LED için / for the onboard LED
10
11void setup() {
12 for (int i = 0; i < LED_SAYISI; i++) pinMode(LEDS[i], OUTPUT);
13 pinMode(LED_BUILTIN, OUTPUT); // Uno'da D13 / D13 on the Uno
14 digitalWrite(LEDS[konum], HIGH);
15}
16
17void loop() {
18 unsigned long simdi = millis();
19 unsigned long aralik = map(analogRead(POT), 0, 1023, 400, 20); // adım süresi (ms) / step time (ms)
20
21 // Görev 1: karaşimşek / Task 1: Knight Rider
22 if (simdi - sonAdim >= aralik) { // taşmaya karşı güvenli / overflow-safe
23 sonAdim = simdi;
24 digitalWrite(LEDS[konum], LOW);
25 konum += yon;
26 if (konum == LED_SAYISI - 1 || konum == 0) yon = -yon; // uçta yön değiştir / reverse at the ends
27 digitalWrite(LEDS[konum], HIGH);
28 }
29
30 // Görev 2: dahili LED kendi temposunda yanıp söner / Task 2: the onboard LED blinks at its own pace
31 if (simdi - sonBlink >= 500) {
32 sonBlink = simdi;
33 digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
34 }
35 // Buraya buton, sensör ya da seri port kodu eklenebilir / button, sensor or serial code can go here
36}Aquí hay dos detalles importantes. Primero, las variables de tiempo deben ser unsigned long; si usas int, en el Uno el valor se desborda a los 32,7 segundos aproximadamente y la temporización se estropea: el efecto se para o se acelera sin control. Segundo, la comparación se hace con una resta de la forma simdi - sonAdim >= aralik (ahora menos el último paso, comparado con el intervalo); este método sigue funcionando bien incluso cuando millis() vuelve a cero, más o menos cada 49,7 días. Como guardamos la posición y la dirección de la luz en dos variables (konum y yon), ya no hay bucles: en cada paso la posición sube o baja en uno y, al llegar a los extremos, la dirección cambia de signo.
8 LEDs con 3 pines usando el 74HC595
Ocho LEDs ocupan ocho pines del Uno; cuando quieras añadir una pantalla LCD, sensores y botones a tu proyecto, empezarán a faltarte pines. El registro de desplazamiento 74HC595 controla sus ocho salidas con solo tres pines del Arduino (datos, reloj y latch). El estado de cada LED es un bit de un byte: la expresión 1 << i pone a 1 solo el bit i, es decir, enciende un único LED. Con operaciones de bits también es fácil crear patrones: (1 << i) | (0x80 >> i) produce dos luces que llegan a la vez desde los dos extremos hacia el centro. Encadenando dos chips puedes hacer incluso un coche fantástico de 16 LEDs con los mismos tres pines; el encadenado, el control rápido por SPI y el uso con displays de 7 segmentos se explican paso a paso en el artículo Registro de desplazamiento 74HC595.
| Pin del 74HC595 | Conexión (Arduino Uno) |
|---|---|
| DS (14) | D11 |
| SH_CP (11) | D13 |
| ST_CP (12) | D10 |
| OE (13) | GND (salidas siempre activas) |
| MR (10) | 5V (reset desactivado) |
| VCC (16) / GND (8) | 5V / GND, con un condensador de 100 nF al lado |
| Q0 (15), Q1–Q7 (1–7) | Cada una a través de 470 Ω al ánodo de un LED |
| Pata central del potenciómetro | A0 |
1// 74HC595 ile 3 pinden 8 LED: karaşimşek ve ortada buluşma / 8 LEDs from 3 pins with a 74HC595: Knight Rider and meet-in-the-middle
2const int DATA_PIN = 11; // DS (14)
3const int CLOCK_PIN = 13; // SH_CP (11)
4const int LATCH_PIN = 10; // ST_CP (12)
5const int POT = A0;
6
7void yaz595(byte desen) {
8 digitalWrite(LATCH_PIN, LOW);
9 shiftOut(DATA_PIN, CLOCK_PIN, MSBFIRST, desen); // 8 biti gönder / send the 8 bits
10 digitalWrite(LATCH_PIN, HIGH); // çıkışlara aktar / copy to the outputs
11}
12
13void setup() {
14 pinMode(DATA_PIN, OUTPUT);
15 pinMode(CLOCK_PIN, OUTPUT);
16 pinMode(LATCH_PIN, OUTPUT);
17 yaz595(0); // açılışta hepsi sönük / all off at startup
18}
19
20void loop() {
21 int bekle = map(analogRead(POT), 0, 1023, 400, 20);
22
23 for (int i = 0; i < 7; i++) { yaz595(1 << i); delay(bekle); } // Q0 -> Q7
24 for (int i = 7; i > 0; i--) { yaz595(1 << i); delay(bekle); } // Q7 -> Q0
25
26 for (int i = 0; i < 4; i++) { // uçlardan ortaya / from the ends to the middle
27 yaz595((1 << i) | (0x80 >> i));
28 delay(bekle);
29 }
30 for (int i = 3; i >= 0; i--) { // ortadan uçlara / from the middle to the ends
31 yaz595((1 << i) | (0x80 >> i));
32 delay(bekle);
33 }
34}En las salidas del 74HC595 se recomienda 470 Ω en lugar de 220 Ω: la corriente total que pasa por los pines VCC y GND del chip no debe superar 70 mA. Con 470 Ω circulan unos 6,4 mA por LED e, incluso con los ocho LEDs encendidos, el total se queda en 51 mA. En el coche fantástico solo hay uno o dos LEDs encendidos a la vez, así que los LEDs se siguen viendo bien.
Coche fantástico con estela desde un solo pin con WS2812B
La versión que más se parece al escáner real de KITT se hace con LEDs direccionables WS2812B. Cada WS2812B lleva su propio controlador integrado; por larga que sea la tira, ajustas el color y el brillo de cada LED por separado con un único cable de datos. Para la estela guardamos un array: en cada paso el brillo de todos los LEDs se divide entre tres y el LED de cabeza se pone a 255. Así los LEDs de detrás se apagan rápido pasando por 255, 85, 28 y 9, y aparece una estela natural detrás de la luz. Si divides entre 2 en vez de entre 3, la estela se alarga; con 5, se acorta. Para pasar de 8 a 60 LEDs con el mismo método solo tienes que cambiar el valor de NUM_LEDS.

1// WS2812B ile kuyruklu karaşimşek (tek veri pini) / Knight Rider with a fading tail on WS2812B (one data pin)
2#include <Adafruit_NeoPixel.h>
3
4const int DATA_PIN = 6; // DIN, 330 Ω üzerinden / DIN through 330 Ω
5const int NUM_LEDS = 8; // şerit ya da çubuktaki LED sayısı / LEDs on the strip or stick
6const int POT = A0;
7
8Adafruit_NeoPixel strip(NUM_LEDS, DATA_PIN, NEO_GRB + NEO_KHZ800);
9
10uint8_t seviye[NUM_LEDS]; // her LED'in kırmızı parlaklığı / red brightness of each LED
11int konum = 0;
12int yon = 1;
13
14void setup() {
15 strip.begin();
16 strip.setBrightness(80); // 0–255; USB için düşük tut / keep it low on USB power
17 strip.show(); // hepsini söndür / all off
18}
19
20void loop() {
21 for (int i = 0; i < NUM_LEDS; i++) seviye[i] = seviye[i] / 3; // kuyruk söner / the tail fades
22 seviye[konum] = 255; // baştaki LED tam parlak / the head is full brightness
23
24 for (int i = 0; i < NUM_LEDS; i++) {
25 strip.setPixelColor(i, strip.Color(seviye[i], 0, 0)); // yalnız kırmızı / red only
26 }
27 strip.show();
28
29 konum += yon;
30 if (konum == NUM_LEDS - 1 || konum == 0) yon = -yon; // uçta yön değiştir / reverse at the ends
31 delay(map(analogRead(POT), 0, 1023, 150, 20));
32}Coche fantástico con ESP32: estela por PWM en cada pin
En el Uno es difícil hacer un coche fantástico con estela usando LEDs normales, porque el PWM solo está en los pines 3, 5, 6, 9, 10 y 11, y en nuestro array D2–D9 solo hay cuatro de ellos. En el ESP32, gracias al hardware LEDC, casi cualquier pin de salida puede generar PWM, y el ESP32 clásico tiene 16 canales PWM. Como analogWrite() funciona directamente en el núcleo actual de Arduino para ESP32, puedes aplicar la lógica de la estela de los WS2812B a LEDs normales. Los pines de la tabla son GPIO seguros que no afectan al arranque; el potenciómetro va al GPIO 34 del canal ADC1, que lee bien incluso con el Wi-Fi activo, y como el ADC del ESP32 es de 12 bits el valor va de 0 a 4095. Los pines del ESP32 dan 3,3 V, así que por un LED rojo con 220 Ω circulan unos 6 mA; los LEDs se ven algo más tenues que en el Uno. Para preparar la placa, consulta ¿Qué es el ESP32?.
1// ESP32: her pinde PWM ile kuyruklu karaşimşek / ESP32: Knight Rider with a PWM tail on every pin
2const int LEDS[] = {18, 19, 21, 22, 23, 25, 26, 27};
3const int LED_SAYISI = sizeof(LEDS) / sizeof(LEDS[0]);
4const int POT = 34; // ADC1, yalnızca giriş / ADC1, input only
5
6int parlaklik[LED_SAYISI]; // 0–255
7int konum = 0;
8int yon = 1;
9unsigned long sonAdim = 0;
10
11void setup() {
12 // analogWrite() pini PWM için kendisi hazırlar / analogWrite() sets the pin up for PWM itself
13}
14
15void loop() {
16 unsigned long aralik = map(analogRead(POT), 0, 4095, 400, 20); // ESP32 ADC 12 bit: 0–4095
17 if (millis() - sonAdim >= aralik) {
18 sonAdim = millis();
19 for (int i = 0; i < LED_SAYISI; i++) parlaklik[i] /= 3; // kuyruk söner / the tail fades
20 parlaklik[konum] = 255;
21 for (int i = 0; i < LED_SAYISI; i++) analogWrite(LEDS[i], parlaklik[i]);
22 konum += yon;
23 if (konum == LED_SAYISI - 1 || konum == 0) yon = -yon;
24 }
25}Coche fantástico con Raspberry Pi Pico y MicroPython
En la Raspberry Pi Pico escribes el mismo efecto en unas pocas líneas de MicroPython. Guardar los objetos Pin en una lista cumple la misma función que el array en Arduino. time.ticks_ms() y time.ticks_diff() son los equivalentes en MicroPython de millis() y de la resta segura frente al desbordamiento. El potenciómetro va a GP26 (ADC0); read_u16() da un valor entre 0 y 65535 y el código lo convierte en 400–20 ms. Se recomienda que la corriente total de todos los GPIO de la Pico no supere los 50 mA; por eso en la tabla elegimos 330 Ω: circulan unos 4 mA por LED e, incluso con los ocho encendidos, el total ronda los 32 mA. El proyecto coche fantástico para Pico de BlueGrays usa 6 LEDs en los pines GP9–GP14; si has montado ese circuito, basta con cambiar la lista PINLER a [9, 10, 11, 12, 13, 14]. Para la instalación y la carga del código con Thonny, consulta ¿Qué es la Raspberry Pi Pico?.
1# Raspberry Pi Pico: potansiyometreyle hız ayarlı karaşimşek / Pico: Knight Rider with pot speed control
2from machine import Pin, ADC
3import time
4
5PINLER = [8, 9, 10, 11, 12, 13, 14, 15] # GP8–GP15
6leds = [Pin(p, Pin.OUT) for p in PINLER]
7pot = ADC(26) # GP26 = ADC0
8
9def adim_suresi():
10 # read_u16: 0–65535 -> 400–20 ms
11 return 400 - pot.read_u16() * 380 // 65535
12
13konum, yon = 0, 1
14leds[konum].on()
15son = time.ticks_ms()
16
17while True:
18 if time.ticks_diff(time.ticks_ms(), son) >= adim_suresi(): # millis() benzeri / like millis()
19 son = time.ticks_ms()
20 leds[konum].off()
21 konum += yon
22 if konum == len(leds) - 1 or konum == 0:
23 yon = -yon # uçta yön değiştir / reverse at the ends
24 leds[konum].on()Todos los GPIO de la Pico también pueden generar PWM; con machine.PWM y un valor duty_u16() para cada LED puedes llevar el efecto con estela del ESP32 a la Pico. Si quieres usar WS2812B, el módulo neopixel integrado en MicroPython controla una tira desde un único GPIO; pero un WS2812B alimentado a 5 V no siempre lee de forma fiable la señal de datos de 3,3 V de la Pico, así que si los colores fallan, añade un conversor de nivel entre ambos.
Ideas de proyectos con el coche fantástico
- Vúmetro (indicador de nivel de sonido): decide cuántos LEDs de la barra se encienden según el volumen medido con el sensor de sonido KY-038.
- Barra de LEDs para sensor de aparcamiento: enciende más LEDs a medida que disminuye la distancia medida con el HC-SR04 y haz que parpadeen todos cuando estés muy cerca.
- Juego de atrapar la luz: mientras la luz va y viene rápido, intenta pulsar un botón justo cuando se enciende el LED del centro; con cada acierto, acorta el tiempo de paso.
- Decoración nocturna automática: que el efecto arranque solo cuando un LDR detecte que oscurece.
- Luz trasera para coche de maqueta o bicicleta: haz un coche fantástico rojo con estela en una tira WS2812B y enciende todos los LEDs al máximo al pulsar el botón de freno.
- Indicador de nivel: muestra la posición de un potenciómetro o la tensión de una batería como una barra que se llena.
- Pantallas más grandes: lleva la misma lógica a una matriz de LEDs MAX7219 o a un cubo de LEDs.
Errores comunes y cómo solucionarlos
| Síntoma | Causa | Solución |
|---|---|---|
| Los LEDs brillan muy poco | Falta pinMode(OUTPUT); digitalWrite solo activa la resistencia pull-up interna | Configura todos los pines como OUTPUT con un bucle en setup() |
| Un LED no se enciende nunca | El LED está al revés, o una resistencia o un cable están desplazados una fila | Pata larga a la resistencia y al pin, pata corta a GND; prueba el LED solo con 5V y una resistencia |
| Los LEDs de los extremos se quedan el doble de tiempo | Los dos bucles incluyen los LEDs de los extremos | Usa i < LED_SAYISI − 1 en el bucle de ida e i > 0 en el de vuelta |
| Un pin cualquiera parpadea o el programa hace cosas raras | Te sales del array: i <= LED_SAYISI | Cambia la condición a i < LED_SAYISI; no existe el elemento LEDS[8] |
| El código no sube o los LEDs parpadean durante la carga | Hay LEDs conectados a D0 y D1 | Empieza el array en D2 |
| El potenciómetro no cambia la velocidad | A A0 llega una pata exterior en lugar de la central, o el valor se lee una sola vez fuera del bucle | Conecta la pata central a A0; llama a analogRead en cada paso |
| El efecto se estropea a los 32 segundos aproximadamente | El valor de millis() se guarda en una variable int | Declara las variables de tiempo como unsigned long |
| Los WS2812B no se encienden o salen colores al azar | Falta el GND común, falta la resistencia de datos o la tira está conectada por el extremo equivocado (DOUT) | Une los GND, añade 330 Ω y conecta por el extremo DIN, donde empiezan las flechas |
El coche fantástico parece sencillo, pero contiene ideas básicas que usarás después en cualquier proyecto: arrays, bucles, lecturas analógicas, map(), temporización sin bloqueo, operaciones de bits y LEDs direccionables. Como siguiente paso, echa un vistazo al proyecto semáforo con Arduino o a la lista de ideas de proyectos con Arduino. En la aplicación BlueGrays encontrarás la secuencia de LEDs, el coche fantástico y sus versiones con velocidad ajustable, los efectos de acumulación y coche fantástico con WS2812B, y los proyectos de secuencia de LEDs con ESP32 y coche fantástico con Pico, cada uno con su esquema paso a paso y el código listo para probar en tu propia placa.
Preguntas frecuentes
¿Cuántos LEDs puedo controlar con un Arduino Uno?
El Uno tiene 20 pines que pueden usarse como salidas digitales, D0–D13 y A0–A5; si dejas libres D0 y D1 para la comunicación serie, puedes controlar 18 LEDs directamente. Pon una resistencia a cada LED y mantén la corriente total por debajo de 200 mA; si los 18 van a estar encendidos a la vez, elige 330 Ω o más. Para más LEDs se usa un registro de desplazamiento 74HC595 o una tira WS2812B, que controla cientos de LEDs con un solo pin.
¿Qué resistencia necesito para una secuencia de LEDs?
En un Arduino Uno de 5 V, 220 Ω va bien para LEDs rojos y da unos 13,6 mA por LED; 330 Ω también sirve, pero los LEDs brillan algo menos. En el ESP32 de 3,3 V se recomiendan 220 Ω y en la Pico 330 Ω. En efectos en los que solo hay un LED encendido funciona también una única resistencia común, pero el brillo baja cuando se encienden varios, así que lo correcto es una resistencia por LED.
¿Se puede hacer el coche fantástico sin Arduino?
Sí, el método clásico es un temporizador 555 y un contador CD4017. El 555 genera los pulsos de reloj y el 4017 pone en HIGH sus 10 salidas una tras otra, lo que por sí solo da una secuencia simple. Para la ida y vuelta las salidas se combinan con diodos: las 10 salidas se conectan a 6 LEDs en el orden 1-2-3-4-5-6-5-4-3-2, y la velocidad se ajusta con un potenciómetro en el 555.
¿Qué diferencia hay entre una secuencia de LEDs y el efecto coche fantástico?
En la secuencia simple la luz avanza en una dirección y, tras el último LED, vuelve a empezar; con 8 LEDs una vuelta son 8 pasos. En el coche fantástico la luz da la vuelta al llegar al extremo y va y viene entre los dos lados; con 8 LEDs una vuelta son 14 pasos. En el código la diferencia también es pequeña: para el coche fantástico añades un segundo bucle que cuenta hacia atrás.
¿Por qué usar millis() en lugar de delay() en una secuencia de LEDs?
Mientras delay() está en marcha el Arduino no puede hacer nada más; se pierde las pulsaciones de botones y no puede leer sensores. Con millis(), en cada vuelta del bucle solo se da un paso cuando ha pasado el tiempo, y en el resto del tiempo se ejecutan otras tareas. Así, mientras la luz recorre la fila, los botones, el potenciómetro o los comandos por el puerto serie responden al instante.
¿Cómo se añade una estela al efecto coche fantástico?
Para la estela hay que bajar poco a poco el brillo de los LEDs que van detrás, y para eso se necesita PWM. En el Uno el PWM solo está en los pines 3, 5, 6, 9, 10 y 11, así que con esos pines puedes hacer un coche fantástico con estela de 6 LEDs. Lo más fácil es usar una tira WS2812B, en la que controlas cada LED por separado, o un ESP32 o una Pico, que tienen PWM en todos los pines.
Proyectos para hacer después de leer esto
Ver todos los proyectos
Efecto coche fantástico con LED
La clásica luz que va y viene: un punto de luz recorre seis LED de un extremo al otro y luego regresa. El Arduino enciende cada LED una décima de segundo antes de pasar al siguiente, da la vuelta en c

Luz secuencial LED
Luces que se encienden una tras otra, como si corrieran. El Arduino enciende seis LED de uno en uno; cada uno brilla un instante y se apaga, así que la luz recorre la fila de principio a fin y vuelve

Efecto coche fantástico con velocidad regulable
Una luz recorre seis LED de un extremo a otro, da la vuelta y vuelve a correr. Girando el mando del potenciómetro cambias al instante la velocidad de esa carrera: con el mando a un lado la luz casi vu

Luz secuencial LED con velocidad regulable
Seis LED se encienden uno tras otro y la luz parece correr de un extremo al otro. Al girar el mando del potenciómetro, la velocidad de esa carrera cambia al instante: hacia un lado la luz vuela, hacia

Efecto coche fantástico con WS2812B
Un punto de luz roja recorre una tira LED inteligente de un extremo al otro y vuelve, en un vaivén que nunca se detiene. En cada paso el Arduino enciende un solo LED, espera una décima de segundo y pa

Luz secuencial con WS2812B (efecto llenado)
Una tira de luz que se llena y se vacía como un vaso de agua. El Arduino enciende diez LED de color uno a uno en naranja y los deja encendidos; cuando la tira está llena, los apaga uno a uno en el mis

LED Secuencial ESP32 (Knight Rider)
6 LEDs moviéndose secuencialmente de izquierda a derecha y de derecha a izquierda (estilo Knight Rider). Ejemplo básico del uso del bucle for y arrays. Enseña la lógica del cambio de dirección.

Raspberry Pi Pico Knight Rider LED Escáner (6 LED Ida-Vuelta)
¡Efecto escáner LED "Knight Rider" clásico con Pico! 6 LEDs van de izquierda a derecha, luego de derecha a izquierda, indefinidamente. Aprende reversed() y dos bucles for separados para patrón ida-vuelta.
Más artículos
App BlueGrays
Monta este circuito paso a paso en tu teléfono
Esquema, código y lista de piezas en una sola pantalla. Más de 200 proyectos de Arduino, ESP32 y Pico listos para montar.
Escanea con tu teléfono
Apunta la cámara al código y se abrirá la tienda de apps de tu teléfono.
o ábrela en la tienda

