Tabla de contenido:
Video: Arduino OLED Snake Game: 3 pasos
2024 Autor: John Day | [email protected]. Última modificación: 2024-01-30 08:42
Hola y bienvenido, a nuestras instrucciones sobre cómo hacer un juego OLED arduino, este proyecto surgió cuando intentábamos hacer nuestro primer juego con un arduino, así que pensamos dónde era mejor comenzar que el clásico Snake de Nokia (bueno en al menos un clon de serpiente:)).
Que necesitarás
Suministros
Arduino UNO o clon
Pantalla OLED
4 diodos
Resistencia de 500-1k
4 botones del controlador
Zumbador piezoeléctrico pasivo
Opcional
BreadBoard sin soldadura
Tenga en cuenta que estos enlaces son solo por ejemplo
Paso 1: el circuito
En la imagen de arriba puede ver nuestro circuito, usamos el pin d3 en el arduino como un pin de solicitud de interrupción para que el arduino dé prioridad a la lectura de las entradas del controlador que son d4 d5 d6 d7. Lo básico del circuito es que se presiona un botón de dirección que sube a 5v, esto activa el pin de solicitud de interrupción (cable púrpura d3) y un pin de dirección correspondiente, la función de interrupción llama a una función de dirección de actualización y ese código mueve la serpiente en consecuencia. El pin 9 se utiliza como pin de sonido, ya que es un PWM (~ modulación de ancho de pulso) que está conectado directamente a un piezoeléctrico de 5v en el pin + y el - vuelve a 0v / tierra.
(Para su información, en el arduino uno y los clones solo d2 y d3 pueden actuar como pines de solicitud de interrupción).
Pines de dirección:
d4 Up NARANJA
d5 Abajo ROSA
d6 Izquierda AZUL
d7 Derecha MARRÓN
d9 sonido GRIS
Cada botón tiene una entrada de conexión de 5v y una salida que se conecta primero a su respectiva entrada digital en el arduino, esta misma salida de cada botón se conecta luego a su propio diodo, usamos los diodos para detener la retroalimentación de voltaje a través del otros botones y activándolos. En el extremo del cátodo (-) de los 4 diodos los unimos para crear una unión de salida que se conecta a d3 y luego a través de una resistencia a 0v / tierra para tirar de los pines arduino hacia abajo para no dejar pines flotantes cuando no esté activado.
(Para su información, un pin flotante puede recibir voltaje fantasma y causar un comportamiento inusual)
Se utilizan 2 pines analógicos para controlar la pantalla, estos son los pines i2c del hardware arduino.
A5 está conectado a SCL AMARILLO
A4 está conectado a SDA GREEN
La salida de + 5v y 0v (tierra) del arduino se utiliza como fuente de energía para todo el circuito, que puede ser alimentado por un cargador USB o de teléfono.
Paso 2: el código
// ------------------------ ANJAWARE SNAKE Games Con la ayuda de la gente de la red --------------- -------
#incluir
#include // https://github.com/adafruit/Adafruit-GFX-Library #include // https://github.com/adafruit/Adafruit-GFX-Library // conjunto de visualización (ancho, alto) Adafruit_SSD1306 display (128, 64); // definir pines de entrada estos son los pines en el arduino que nunca cambian así que #define #define INTPIN 3 // solo los pines 2 y 3 pueden ser pines interrumpidos en UNO #define UPPIN 4 // estos son pines conectados al interruptor relevante #define DWNPIN 5 #define LFTPIN 6 #define RHTPIN 7 #define SND 9 // define direcciones #define DIRUP 1 // estos valores es lo que la "serpiente" mira para decidir- #define DIRDOWN 2 // la dirección en que viajará la serpiente # definir DIRLEFT 3 #definir DIRRIGHT 4
// establecer variables de botón
// volitile porque necesitamos que se actualice con el interupt, por lo que puede ser cualquier bit del valor del ciclo
// nunca es superior a 4, por lo que solo se necesita un int de 8 bits para ahorrar recursos volátiles uint8_t buttonpressed = 0; bool butup = 0; bool butdown = 0; // usamos esto para establecer true para "detectar" en qué dirección presionó bool butleft = 0; bool butright = 0;
// entradas de serpiente
byte snakePosX [30]; // matriz para hacer el cuerpo del byte serpiente snakePosY [30];
int snakeX = 30; // posición de la cabeza de la serpiente
int snakeY = 30; int tamaño de la serpiente = 1; // recuento del tamaño de la serpiente limitado al tamaño de la matriz
// ints del mundo
uint8_t worldMinX = 0; // estos establecen los límites del área de juego
uint8_t worldMaxX = 128; uint8_t worldMinY = 10; uint8_t worldMaxY = 63;
// recolecta scran (comida) y posición de scran
bool scranAte = 0; uint8_t scranPosX = 0; uint8_t scranPosY = 0;
// puntúa variables
Playcore largo = 0; puntuación alta larga = 30; // establecer la puntuación alta en 3 recopilar como punto de partida
// --------------------------- esto es lo que ejecuta la interrupción en caso de aumento de voltaje ------------ -------------
vacío interrumpido presionado () {retraso (150); // ligero retraso para la protección adicional de "rebote" updatedirection (); } // ------------------ actualiza el valor de la dirección presionando el botón ----------------- void updatedirection () { // Serial.println ("dirección de actualización"); butup = digitalRead (UPPIN); // comprobar qué entrada fue alta y establecer bool true relevante butdown = digitalRead (DWNPIN); butleft = digitalRead (LFTPIN); butright = digitalRead (RHTPIN); // estos si los enunciados miran qué entrada fue alta e ingresa el valor relevante en "botón presionado" // variable, esta variable dicta la dirección del movimiento if (butup == true) {buttonpressed = DIRUP; // Serial.println ("UP presionado"); // Serial.println (botón presionado); butup = falso; tono (SND, 1500, 10); } if (butdown == true) {buttonpressed = DIRDOWN; // Serial.println ("ABAJO presionado"); // Serial.println (botón presionado); butdown = falso; tono (SND, 1500, 10); }
si (butleft == verdadero)
{botón presionado = DIRLEFT; // Serial.println ("IZQUIERDA presionada"); // Serial.println (botón presionado); butleft = falso; tono (SND, 1500, 10); } if (butright == true) {buttonpressed = DIRRIGHT; // Serial.println ("DERECHO presionado"); // Serial.println (botón presionado); butright = falso; tono (SND, 1500, 10); }}
// -------------------------- dibuja las rutinas de visualización ------------------ -----------------
void updateDisplay () // dibuja puntuaciones y contornos
{// Serial.println ("Actualizar pantalla");
display.fillRect (0, 0, display.width () - 1, 8, NEGRO);
display.setTextSize (0); display.setTextColor (BLANCO); // dibujar puntuaciones display.setCursor (2, 1); display.print ("Puntuación:"); display.print (String (playcore, DEC)); display.setCursor (66, 1); display.print ("Alto:"); display.print (String (puntuación más alta, DEC)); // dibujar área de juego // pos 1x, 1y, 2x, 2y, color display.drawLine (0, 0, 127, 0, WHITE); // borde superior display.drawLine (63, 0, 63, 9, BLANCO); // separador de puntuación display.drawLine (0, 9, 127, 9, BLANCO); // debajo del borde del texto display.drawLine (0, 63, 127, 63, BLANCO); // borde inferior display.drawLine (0, 0, 0, 63, BLANCO); // borde izquierdo display.drawLine (127, 0, 127, 63, BLANCO); // borde derecho
}
// ----------------------------------- actualizar el área de juego ---------- --------------------
void updateGame () // esto actualiza la pantalla del área de juego
{display.clearDisplay ();
display.drawPixel (scranPosX, scranPosY, BLANCO);
scranAte = scranFood ();
// comprobar las rutinas de las serpientes
if (outOfArea () || selfCollision ())
{ juego terminado(); }
// mostrar serpiente
para (int i = 0; i0; i--) {snakePosX = snakePosX [i-1]; snakePosY = snakePosY [i-1]; } // agrega un píxel extra a la serpiente if (scranAte) {snakeSize + = 1; snakePosX [snakeSize-1] = snakeX; snakePosY [serpienteSize-1] = snakeY; }
switch (botón presionado) // era snakeDirection
{caso DIRUP: serpienteY- = 1; rotura; caso DIRDOWN: snakeY + = 1; rotura; caso DIRLEFT: snakeX- = 1; rotura; caso DIRRIGHT: snakeX + = 1; rotura; } snakePosX [0] = snakeX; snakePosY [0] = snakeY; updateDisplay (); display.display (); // --------------------- coloca el scran -------------------
vacío placeScran ()
{scranPosX = aleatorio (worldMinX + 1, worldMaxX-1); scranPosY = aleatorio (worldMinY + 1, worldMaxY-1); } // ------------------------ SCRAN ATE PUNTO HACIA ARRIBA ---------------- bool scranFood () {if (snakeX == scranPosX && snakeY == scranPosY) {playcore = playcore + 10; tono (SND, 2000, 10); updateDisplay (); placeScran (); return 1; } else {return 0; } } //--------------------- fuera del área---------------------- bool outOfArea () {return snakeX = worldMaxX || snakeY = worldMaxY; } //---------------------- juego terminado----------------------- --- void gameOver () {uint8_t rectX1, rectY1, rectX2, rectY2; rectX1 = 38; rectY1 = 28; rectX2 = 58; rectY2 = 12; display.clearDisplay (); display.setCursor (40, 30); display.setTextSize (1); tono (SND, 2000, 50); display.print ("JUEGO"); tono (SND, 1000, 50); display.print ("OVER"); if (playcore> = highscore) // compruebe si la puntuación es más alta que la puntuación alta {highscore = playcore; // declaración única para actualizar la puntuación alta} for (int i = 0; i <= 16; i ++) // esto es para dibujar rectanlges alrededor del juego sobre {display.drawRect (rectX1, rectY1, rectX2, rectY2, WHITE); Serial.println ("si bucle"); display.display (); rectX1- = 2; // desplazarse 2 píxeles rectY1- = 2; rectX2 + = 4; // desplazar 2 píxeles desde el último punto rectY2 + = 4; tono (SND, i * 200, 3); } display.display (); // Limpiar pantalla después de la fama sobre rectX1 = 0; // establecer la posición inicial de la línea rectY1 = 0; rectX2 = 0; rectY2 = 63; para (int i = 0; i <= 127; i ++) {uint8_t cnt = 0; display.drawLine (rectX1, rectY1, rectX2, rectY2, NEGRO); rectX1 ++; rectX2 ++; display.display (); } display.clearDisplay (); Playcore = 0; // restablecer los detalles de la serpiente y el jugador snakeSize = 1; snakeX = display.width () / 2; serpienteY = display.height () / 2; waitForPress (); // esperar a que el jugador inicie el juego} // ------------------------- esperar el bucle de pulsaciones ---------- --------------- void waitForPress () {bool esperando = 0; // El ciclo termina cuando esto es cierto display.clearDisplay (); while (esperando == 0) {drawALineForMe (BLANCO); // dibuja una línea blanca aleatoria drawALineForMe (BLACK); // dibuja una línea negra aleatoria para que la pantalla no se llene completamente en blanco display.fillRect (19, 20, 90, 32, BLACK); // fondo en blanco para el texto display.setTextColor (WHITE); display.setCursor (35, 25); display.setTextSize (2); // display de fuente más grande.println ("SERPIENTE"); // x y w h r col display.drawRoundRect (33, 22, 62, 20, 4, BLANCO); // Serpiente de borde display.drawRect (19, 20, 90, 32, BLANCO); // cuadro de borde - 3 display.setCursor (28, 42); display.setTextSize (0); // la fuente vuelve a la pantalla normal.println ("presione cualquier tecla"); display.display (); esperando = digitalRead (INTPIN); // verifica si la tecla presionada esperando cambiará a 1 terminando mientras el botón presionado = 0; // presionar el botón de reinicio}} // -------------------- DIBUJAR un color de entrada de línea aleatorio uint8_t -------------- ----- vacío drawALineForMe (uint8_t clr) {uint8_t línea1X, línea1Y, línea2X, línea2Y = 0; // establecer coordenadas aleatorias para una línea y luego dibujarla // variable no menos no más line1X = random (worldMinX + 1, worldMaxX-1); line1Y = aleatorio (worldMinY + 1, worldMaxY-1); line2X = aleatorio (worldMinX + 1, worldMaxX-1); line2Y = aleatorio (worldMinY + 1, worldMaxY-1); display.drawLine (línea1X, línea1Y, línea2X, línea2Y, clr); } // ------------------------------------- detección de colisiones -------- -----------------------
for (byte i = 4; i <tamaño serpiente; i ++) {if (serpienteX == serpientePosX && serpienteY == serpientePosy ) {return 1; tono (SND, 2000, 20); tono (SND, 1000, 20); } return 0; }
//-------------------------------- CONFIGURACIÓN--------------- -------------------------------
configuración vacía () {retraso (100); // simplemente dale a las cosas la oportunidad de "arrancar" // Serial.begin (9600); // desmarque esto si desea ver las salidas en serie display.begin (SSD1306_SWITCHCAPVCC, 0x3C); display.clearDisplay (); // comenzar con una pantalla limpia display.setTextColor (WHITE); // configurar el tamaño de rotación del color del texto, etc. display.setRotation (0); display.setTextWrap (falso); display.dim (0); // establece el brillo de la pantalla pinMode (INTPIN, INPUT); // establece los puertos correctos para las entradas pinMode (UPPIN, INPUT); pinMode (DWNPIN, ENTRADA); pinMode (LFTPIN, ENTRADA); pinMode (RHTPIN, ENTRADA); // este es el comando interupt esto "detiene" el arduino para leer las entradas // comando-función-pin-función para ejecutar-condición en el pin attachInterrupt (digitalPinToInterrupt (INTPIN), interruptpressed, RISING); // Serial.println ("Configuración aprobada"); waitForPress (); // muestra la pantalla de inicio de la serpiente placeScran (); // coloca el primer trozo de comida} // --------------------- BUCLE PRINCIPAL ----------------- ---------------------- vacío loop () {updateGame (); // esta función es la que lleva el código principal}
Paso 3:
Recomendado:
DIY 37 Leds Arduino Roulette Game: 3 pasos (con imágenes)
DIY 37 Leds Arduino Roulette Game: Roulette es un juego de casino que lleva el nombre de la palabra francesa que significa rueda pequeña
Jumping Man Game con Arduino: 3 pasos
Jumping Man Game con Arduino: ¡Hola a todos! Bienvenido a mi primer Instructable. He sido un gran fanático del juego Jumping Dinosaur, así que intenté construir un juego similar con la ayuda de un Arduino UNO y una pantalla LCD. Este es un proyecto interesante y solo requiere un esfuerzo de
¡POiNG! - ¡Arduino Arcade Game !: 3 pasos
¡POiNG! - ¡Arduino Arcade Game !: Crearemos un arcade de estilo PONG que utiliza partes del " The Most Complete Starter Kit UNO R3 Project " kit de Elegoo Inc. Divulgación completa: la mayoría de las piezas suministradas para este Instructable fueron proporcionadas al autor por Elegoo
Cómo usar el motor paso a paso como codificador rotatorio y pantalla OLED para pasos: 6 pasos
Cómo usar el motor paso a paso como codificador rotatorio y pantalla OLED para pasos: En este tutorial aprenderemos cómo rastrear los pasos del motor paso a paso en la pantalla OLED. Mire un video de demostración. El crédito para el tutorial original es para el usuario de YouTube " sky4fly "
Arduino Snake en un monitor VGA: 5 pasos
Arduino Snake en un monitor VGA: Bueno … Compré un Arduino. Inicialmente, la inversión estuvo motivada por algo que haría que mi hija se interesara en la programación. Sin embargo, resultó que me resultó más divertido jugar con esta cosa. Después de jugar con la fabricación de LED