Simón Dice Arduino

Este proyecto recrea el clásico juego “Simón Dice” utilizando un Arduino, una pantalla LCD I2C, 4 LEDs y 4 pulsadores. A medida que avances, la secuencia de luces será más larga, y tendrás que replicarla usando los pulsadores. Es una excelente práctica para aprender a trabajar con componentes electrónicos, lógica de programación y manejo de secuencias.

Materiales necesarios

  1. Arduino UNO (o compatible).
  2. 4 LEDs (rojo, amarillo, verde y azul, o colores a tu elección).
  3. 4 resistencias de 220 ohms (para los LEDs).
  4. 4 pulsadores.
  5. Pantalla LCD con adaptador I2C.
  6. Protoboard.
  7. Cables de conexión (macho-macho y macho-hembra).
  8. Fuente de alimentación o cable USB para el Arduino.

Circuito

LEDs:

  • Conecta el ánodo (patita larga) de cada LED a un pin digital del Arduino (pines 2, 3, 4, 5).
  • Conecta el cátodo (patita corta) de cada LED a una resistencia de 220 ohms y luego a GND.

Pulsadores:

  • Conecta un terminal de cada pulsador a un pin digital del Arduino (pines 6, 7, 8, 9).
  • El otro terminal se conecta a GND.
  • Usa resistencias de 10k ohms conectadas entre los pines de los pulsadores y GND, o configura los pines como INPUT_PULLUP para evitar rebotes.

Pantalla LCD:

  • Conecta los pines I2C (SDA y SCL) al Arduino:
    • SDA: Pin A4 en Arduino UNO.
    • SCL: Pin A5 en Arduino UNO.
  • Conecta VCC y GND de la pantalla al 5V y GND del Arduino.

Código

#include <Wire.h>
#include <LiquidCrystal_I2C.h>

// Configuración de la pantalla LCD
LiquidCrystal_I2C lcd(0x27, 16, 2); // Cambia 0x27 si la dirección I2C es distinta

// Pines de LEDs y pulsadores
const int leds[] = {2, 3, 4, 5};
const int buttons[] = {6, 7, 8, 9};

// Variables de control
int sequence[100]; // Almacena la secuencia generada
int level = 0;     // Nivel actual del juego

void setup() {
  // Configuración de LEDs y botones
  for (int i = 0; i < 4; i++) {
    pinMode(leds[i], OUTPUT);
    pinMode(buttons[i], INPUT_PULLUP);
  }

  // Inicialización de la pantalla LCD
  lcd.init();
  lcd.backlight();
  lcd.setCursor(0, 0);
  lcd.print("Simon Dice");
  delay(2000);
  lcd.clear();

  randomSeed(analogRead(A0)); // Inicializa el generador de números aleatorios
  iniciarJuego();
}

void iniciarJuego() {
  level = 1; // Comienza en el nivel 1
  generarSecuencia(); // Genera una secuencia inicial
  jugarNivel();       // Inicia el nivel
}

void generarSecuencia() {
  for (int i = 0; i < 100; i++) {
    sequence[i] = random(0, 4); // Genera valores aleatorios entre 0 y 3
  }
}

void jugarNivel() {
  lcd.clear();
  lcd.setCursor(0, 0);
  lcd.print("Nivel: ");
  lcd.print(level);
  delay(1000);

  // Muestra la secuencia al jugador
  mostrarSecuencia();

  // Espera la respuesta del jugador
  if (verificarSecuencia()) {
    level++;
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Correcto!");
    delay(1000);
    jugarNivel(); // Pasa al siguiente nivel
  } else {
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Fallaste!");
    lcd.setCursor(0, 1);
    lcd.print("Nivel: ");
    lcd.print(level);
    delay(3000);
    iniciarJuego(); // Reinicia el juego
  }
}

void mostrarSecuencia() {
  for (int i = 0; i < level; i++) {
    int led = sequence[i];
    digitalWrite(leds[led], HIGH);
    delay(500);
    digitalWrite(leds[led], LOW);
    delay(250);
  }
}

bool verificarSecuencia() {
  for (int i = 0; i < level; i++) {
    bool pulsado = false;
    while (!pulsado) {
      for (int j = 0; j < 4; j++) {
        if (digitalRead(buttons[j]) == LOW) { // Botón presionado
          pulsado = true;
          if (sequence[i] != j) { // Verifica si coincide con la secuencia
            return false;
          }
          // Parpadea el LED correspondiente como confirmación
          digitalWrite(leds[j], HIGH);
          delay(250);
          digitalWrite(leds[j], LOW);
          delay(250);
        }
      }
    }
  }
  return true; // Si pasa por toda la secuencia correctamente
}

void loop() {
  // El código principal se maneja en `jugarNivel()`
}

Versiones y mejoras posibles

Mejoras posibles

  1. Agregar un buzzer para retroalimentación sonora.
  2. Implementar un tiempo límite para cada nivel.
  3. Registrar puntuaciones máximas usando una EEPROM.