ENIB 2024 : Space Invador de l'espace : Différence entre versions
(→étapes de fabrication) |
(→ne pas modifier sous cette ligne) |
||
(37 révisions intermédiaires par 2 utilisateurs non affichées) | |||
Ligne 1 : | Ligne 1 : | ||
− | + | Space Invador de l'espace <br> | |
− | |||
− | |||
==Introduction== | ==Introduction== | ||
− | + | <html> | |
+ | <iframe width="560" height="315" src="https://www.youtube.com/embed/-yKLlO2uGNM?si=6mpKVUQX0jqe-2RU" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe> | ||
+ | </html> | ||
− | L'objectif de notre jeu est de tuer l'ennemi. Notre Space Invador se compose de 16x16 leds représentant un vaisseau et des ennemis à abattre. Grâce aux boutons poussoirs, nous pouvons commander la position du vaisseau. | + | L'objectif de notre jeu est de tuer l'ennemi. Notre Space Invador se compose de 16x16 leds représentant un vaisseau et des ennemis à abattre. Grâce aux boutons poussoirs, nous pouvons commander la position du vaisseau et donc diriger les tirs. |
==Outil et matériel== | ==Outil et matériel== | ||
· Carte arduino | · Carte arduino | ||
− | · | + | <br> |
+ | · 16x16 leds | ||
+ | <br> | ||
+ | · Boutons poussoirs | ||
+ | <br> | ||
+ | · Câbles électroniques | ||
+ | <br> | ||
+ | · Planches de chêne | ||
==fichiers à joindre== | ==fichiers à joindre== | ||
Ligne 18 : | Ligne 25 : | ||
===Code Arduino=== | ===Code Arduino=== | ||
<syntaxhighlight lang="Arduino" line> | <syntaxhighlight lang="Arduino" line> | ||
− | # | + | #include <FastLED.h> |
− | #include < | + | #include <SPI.h> |
+ | |||
+ | #define NUM_STRIPS 1 | ||
+ | #define NUM_LEDS_PER_STRIP 256 | ||
+ | CRGB leds[NUM_STRIPS][NUM_LEDS_PER_STRIP]; | ||
+ | |||
+ | int color[5] {0x000000,0x000001,0x010000,0x000100,0x010100}; | ||
+ | int position, position_vaisseau = 4, delay_tire = 0, level = 1; | ||
+ | bool vivant = true, en_partie = true, ennemi = true; | ||
+ | |||
+ | int level_actuelle[16][16]; | ||
+ | |||
+ | const int level_1[16][16] { \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 2, 2, 2, 0, 0, 0, 0, 2, 2, 2, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \ | ||
+ | }; | ||
+ | |||
+ | const int level_2[16][16] { \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 2, 2, 0, 0, 2, 2, 2, 2, 0, 0, 2, 2, 0, 0}, \ | ||
+ | {0, 0, 2, 2, 0, 0, 0, 2, 2, 0, 0, 0, 2, 2, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 2, 2, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \ | ||
+ | }; | ||
+ | |||
+ | const int level_3[16][16] { \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 2, 0, 0, 0, 2, 2, 0, 0, 0, 2, 0, 0, 0}, \ | ||
+ | {0, 0, 2, 2, 2, 0, 2, 2, 2, 2, 0, 2, 2, 2, 0, 0}, \ | ||
+ | {0, 0, 2, 0, 2, 0, 0, 2, 2, 0, 0, 2, 0, 2, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \ | ||
+ | }; | ||
+ | |||
+ | const int level_4[16][16] { \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 2, 2, 0, 2, 2, 0, 2, 2, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \ | ||
+ | }; | ||
+ | |||
+ | const int game_over[16][16] { \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {2, 2, 2, 0, 2, 2, 2, 0, 2, 0, 2, 0, 2, 2, 2, 0}, \ | ||
+ | {2, 0, 0, 0, 2, 0, 2, 0, 2, 2, 2, 0, 2, 0, 0, 0}, \ | ||
+ | {2, 0, 2, 0, 2, 2, 2, 0, 2, 0, 2, 0, 2, 2, 0, 0}, \ | ||
+ | {2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 0, 0}, \ | ||
+ | {2, 2, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 2, 2, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 2, 2, 2, 0, 2, 0, 2, 0, 2, 2, 2, 0, 2, 2, 2}, \ | ||
+ | {0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 0, 0, 2, 0, 2}, \ | ||
+ | {0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 2, 0, 0, 2, 2, 0}, \ | ||
+ | {0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 0, 0, 2, 0, 2}, \ | ||
+ | {0, 2, 2, 2, 0, 0, 2, 0, 0, 2, 2, 2, 0, 2, 0, 2}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \ | ||
+ | }; | ||
+ | |||
+ | const int win[16][16] { \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 2, 0, 0, 0, 2, 0, 2, 2, 2, 0, 2, 0, 0, 2, 0}, \ | ||
+ | {0, 2, 0, 2, 0, 2, 0, 0, 2, 0, 0, 2, 2, 0, 2, 0}, \ | ||
+ | {0, 2, 0, 2, 0, 2, 0, 0, 2, 0, 0, 2, 0, 2, 2, 0}, \ | ||
+ | {0, 0, 2, 0, 2, 0, 0, 2, 2, 2, 0, 2, 0, 0, 2, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \ | ||
+ | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \ | ||
+ | }; | ||
+ | |||
void setup() { | void setup() { | ||
− | // | + | // tell FastLED there's 60 NEOPIXEL leds on pin 2 |
+ | FastLED.addLeds<NEOPIXEL, 2>(leds[0], NUM_LEDS_PER_STRIP); | ||
+ | |||
+ | // tell FastLED there's 60 NEOPIXEL leds on pin 3 | ||
+ | FastLED.addLeds<NEOPIXEL, 3>(leds[1], NUM_LEDS_PER_STRIP); | ||
+ | |||
+ | // tell FastLED there's 60 NEOPIXEL leds on pin 4 | ||
+ | FastLED.addLeds<NEOPIXEL, 4>(leds[2], NUM_LEDS_PER_STRIP); | ||
+ | Serial.begin(9600); | ||
+ | memcpy(level_actuelle,level_1,sizeof(level_1)); | ||
+ | |||
+ | pinMode(A0,INPUT); | ||
+ | pinMode(D7,INPUT); | ||
+ | } | ||
+ | |||
+ | |||
+ | void affiche() { | ||
+ | //carte | ||
+ | for(int x = 0; x < 16; x++) { | ||
+ | for(int y = 0; y < 16;y++){ | ||
+ | if (x%2 == 1){ | ||
+ | position = x*16+y; | ||
+ | } | ||
+ | else{ | ||
+ | position = x*16+15-y; | ||
+ | } | ||
+ | leds[0][position] = color[level_actuelle[x][y]]; | ||
+ | } | ||
+ | } | ||
+ | |||
+ | FastLED.show(); | ||
+ | } | ||
+ | |||
+ | void create_vaisseau(){ | ||
+ | //pos entre 2 et 15 | ||
+ | clear(); | ||
+ | level_actuelle[13][position_vaisseau] = 1; | ||
+ | level_actuelle[13][position_vaisseau-1] = 1; | ||
+ | level_actuelle[12][position_vaisseau-1] = 1; | ||
+ | level_actuelle[13][position_vaisseau-2] = 1; | ||
+ | level_actuelle[14][position_vaisseau-2] = 1; | ||
+ | level_actuelle[14][position_vaisseau] = 1; | ||
+ | FastLED.show(); | ||
+ | } | ||
+ | |||
+ | void clear(){ | ||
+ | for(int x = 10; x < 15; x++) { | ||
+ | for(int y = 0; y < 16;y++){ | ||
+ | if (level_actuelle[x][y] == 1){ | ||
+ | level_actuelle[x][y] = 0; | ||
+ | } | ||
+ | } | ||
+ | } | ||
+ | } | ||
+ | |||
+ | |||
+ | void move(){ | ||
+ | position_vaisseau = int(analogRead(A0)*16/1024); | ||
+ | if (position_vaisseau >= 16){ | ||
+ | position_vaisseau = 15; | ||
+ | } | ||
+ | else if (position_vaisseau <= 1){ | ||
+ | position_vaisseau = 2; | ||
+ | } | ||
+ | } | ||
+ | |||
+ | void tirer() { | ||
+ | if (true) { | ||
+ | level_actuelle[11][position_vaisseau-1] = 103; | ||
+ | } | ||
+ | } | ||
+ | |||
+ | void tick(){ | ||
+ | ennemi = false; | ||
+ | for(int x = 0; x < 16; x++) { | ||
+ | for(int y = 0; y < 16;y++){ | ||
+ | if (level_actuelle[x][y] == 3){ //tire joueur | ||
+ | if (x==0){ | ||
+ | level_actuelle[x][y] = 0; | ||
+ | } | ||
+ | else if ((level_actuelle[x-1][y]==4) || (level_actuelle[x-1][y]==104)){ | ||
+ | level_actuelle[x-1][y] = 3; | ||
+ | level_actuelle[x][y] = 104; | ||
+ | } | ||
+ | else if (level_actuelle[x-1][y]!=0){ | ||
+ | level_actuelle[x-1][y] = 0; | ||
+ | level_actuelle[x][y] = 0; | ||
+ | } | ||
+ | else{ | ||
+ | level_actuelle[x-1][y] = 3; | ||
+ | level_actuelle[x][y] = 0; | ||
+ | } | ||
+ | } | ||
+ | |||
+ | else if (level_actuelle[x][y] == 2){ //vaisseau enemi | ||
+ | ennemi = true; | ||
+ | if ((level_actuelle[x+1][y] == 0)&(random(0,40)==1)){ | ||
+ | level_actuelle[x+1][y] = 104; //chiffre temporaire pour pas refaire son action | ||
+ | } | ||
+ | } | ||
+ | else if (level_actuelle[x][y] == 104){ | ||
+ | level_actuelle[x][y] = 4; | ||
+ | } | ||
+ | else if (level_actuelle[x][y] == 103){ | ||
+ | level_actuelle[x][y] = 3; | ||
+ | } | ||
+ | else if (level_actuelle[x][y]== 4){ | ||
+ | if (x==15){ | ||
+ | level_actuelle[x][y] = 0; | ||
+ | } | ||
+ | if ((level_actuelle[x+1][y] == 0) &(x<15)){ | ||
+ | level_actuelle[x+1][y] = 104; | ||
+ | level_actuelle[x][y] = 0; | ||
+ | } | ||
+ | else if (level_actuelle[x+1][y] == 3){ | ||
+ | level_actuelle[x+1][y] = 104; | ||
+ | level_actuelle[x][y] = 3; | ||
+ | } | ||
+ | else if (level_actuelle[x+1][y] == 1){ | ||
+ | level_actuelle[x][y] = 0; | ||
+ | //game over | ||
+ | en_partie = false; | ||
+ | vivant = false; | ||
+ | } | ||
+ | } | ||
+ | } | ||
+ | } | ||
} | } | ||
void loop() { | void loop() { | ||
− | + | while (en_partie){ | |
+ | tick(); | ||
+ | affiche(); | ||
+ | create_vaisseau(); | ||
+ | if ((digitalRead(D7)) & (delay_tire == 0)){ | ||
+ | tirer(); | ||
+ | delay_tire = 2; | ||
+ | } | ||
+ | else if (delay_tire !=0){ | ||
+ | delay_tire -= 1; | ||
+ | } | ||
+ | move(); | ||
+ | if (!ennemi){ | ||
+ | if (level == 4){ | ||
+ | en_partie = false; | ||
+ | |||
+ | } | ||
+ | else{ | ||
+ | level +=1; | ||
+ | } | ||
+ | if(level==2){ | ||
+ | memcpy(level_actuelle,level_2,sizeof(level_2)); | ||
+ | } | ||
+ | else if(level==3){ | ||
+ | memcpy(level_actuelle,level_3,sizeof(level_3)); | ||
+ | } | ||
+ | else if(level==4){ | ||
+ | memcpy(level_actuelle,level_4,sizeof(level_4)); | ||
+ | } | ||
+ | } | ||
+ | delay(75); | ||
+ | } | ||
+ | if (vivant){ | ||
+ | memcpy(level_actuelle,win,sizeof(win)); | ||
+ | } | ||
+ | else{ | ||
+ | memcpy(level_actuelle,game_over,sizeof(game_over)); | ||
+ | } | ||
+ | affiche(); | ||
+ | delay(200); | ||
+ | if (digitalRead(D7)){ | ||
+ | memcpy(level_actuelle,level_1,sizeof(level_1)); | ||
+ | level = 1; | ||
+ | vivant = true; | ||
+ | en_partie = true; | ||
+ | } | ||
} | } | ||
+ | |||
</syntaxhighlight> | </syntaxhighlight> | ||
Ligne 37 : | Ligne 341 : | ||
===étape 1=== | ===étape 1=== | ||
− | Création du code arduino et test de celui-ci sur la carte. | + | Création du code arduino et test de celui-ci sur la carte. Toutes nos leds s'allument. |
+ | |||
+ | [[Fichier:Carte arduino.jpg|vignette]|350px]] | ||
===étape 2=== | ===étape 2=== | ||
− | Création de la maquette en carton. | + | Création de la maquette en carton. Ce n'est pas la version finale, juste le prototype. |
+ | |||
+ | [[Fichier:Maquette en carton.jpg|vignette]|350px]] | ||
+ | [[Fichier:Maquette carton.jpg|vignette]|350px]] | ||
+ | |||
+ | |||
+ | Création de la maquette finale en bois. | ||
+ | |||
+ | <br> | ||
+ | |||
+ | [[Fichier:T.jpg|vignette]|350px]] | ||
===étape 3 === | ===étape 3 === | ||
Test du jeu. | Test du jeu. | ||
+ | |||
+ | [[Fichier:A.jpg|vignette]|350px]] | ||
===Troubleshouting=== | ===Troubleshouting=== | ||
Ligne 54 : | Ligne 372 : | ||
==Sources et documentation complémentaire== | ==Sources et documentation complémentaire== | ||
+ | * https://www.makercase.com/#/ | ||
+ | * https://www.festi.info/boxes.py/ | ||
+ | * https://boxdesigner.connectionlab.org/ | ||
==ne pas modifier sous cette ligne== | ==ne pas modifier sous cette ligne== | ||
[[Catégorie:Enib2024]] | [[Catégorie:Enib2024]] |
Version actuelle datée du 2 février 2024 à 15:06
Space Invador de l'espace
Sommaire
Introduction
L'objectif de notre jeu est de tuer l'ennemi. Notre Space Invador se compose de 16x16 leds représentant un vaisseau et des ennemis à abattre. Grâce aux boutons poussoirs, nous pouvons commander la position du vaisseau et donc diriger les tirs.
Outil et matériel
· Carte arduino
· 16x16 leds
· Boutons poussoirs
· Câbles électroniques
· Planches de chêne
fichiers à joindre
Code Arduino
1
2 #include <FastLED.h>
3 #include <SPI.h>
4
5 #define NUM_STRIPS 1
6 #define NUM_LEDS_PER_STRIP 256
7 CRGB leds[NUM_STRIPS][NUM_LEDS_PER_STRIP];
8
9 int color[5] {0x000000,0x000001,0x010000,0x000100,0x010100};
10 int position, position_vaisseau = 4, delay_tire = 0, level = 1;
11 bool vivant = true, en_partie = true, ennemi = true;
12
13 int level_actuelle[16][16];
14
15 const int level_1[16][16] { \
16 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
17 {0, 0, 0, 2, 2, 2, 0, 0, 0, 0, 2, 2, 2, 0, 0, 0}, \
18 {0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0}, \
19 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
20 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
21 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
22 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
23 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
24 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
25 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
26 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
27 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
28 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
29 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
30 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
31 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \
32 };
33
34 const int level_2[16][16] { \
35 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
36 {0, 0, 2, 2, 0, 0, 2, 2, 2, 2, 0, 0, 2, 2, 0, 0}, \
37 {0, 0, 2, 2, 0, 0, 0, 2, 2, 0, 0, 0, 2, 2, 0, 0}, \
38 {0, 0, 0, 0, 0, 0, 0, 2, 2, 0, 0, 0, 0, 0, 0, 0}, \
39 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
40 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
41 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
42 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
43 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
44 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
45 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
46 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
47 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
48 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
49 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
50 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \
51 };
52
53 const int level_3[16][16] { \
54 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
55 {0, 0, 0, 2, 0, 0, 0, 2, 2, 0, 0, 0, 2, 0, 0, 0}, \
56 {0, 0, 2, 2, 2, 0, 2, 2, 2, 2, 0, 2, 2, 2, 0, 0}, \
57 {0, 0, 2, 0, 2, 0, 0, 2, 2, 0, 0, 2, 0, 2, 0, 0}, \
58 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
59 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
60 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
61 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
62 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
63 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
64 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
65 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
66 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
67 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
68 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
69 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \
70 };
71
72 const int level_4[16][16] { \
73 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
74 {0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0}, \
75 {0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0}, \
76 {0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0}, \
77 {0, 0, 0, 0, 2, 2, 0, 2, 2, 0, 2, 2, 0, 0, 0, 0}, \
78 {0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0}, \
79 {0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0}, \
80 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
81 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
82 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
83 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
84 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
85 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
86 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
87 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
88 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \
89 };
90
91 const int game_over[16][16] { \
92 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
93 {2, 2, 2, 0, 2, 2, 2, 0, 2, 0, 2, 0, 2, 2, 2, 0}, \
94 {2, 0, 0, 0, 2, 0, 2, 0, 2, 2, 2, 0, 2, 0, 0, 0}, \
95 {2, 0, 2, 0, 2, 2, 2, 0, 2, 0, 2, 0, 2, 2, 0, 0}, \
96 {2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 0, 0}, \
97 {2, 2, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 2, 2, 0}, \
98 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
99 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
100 {0, 2, 2, 2, 0, 2, 0, 2, 0, 2, 2, 2, 0, 2, 2, 2}, \
101 {0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 0, 0, 2, 0, 2}, \
102 {0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 2, 0, 0, 2, 2, 0}, \
103 {0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 0, 0, 0, 2, 0, 2}, \
104 {0, 2, 2, 2, 0, 0, 2, 0, 0, 2, 2, 2, 0, 2, 0, 2}, \
105 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
106 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
107 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \
108 };
109
110 const int win[16][16] { \
111 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
112 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
113 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
114 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
115 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
116 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
117 {0, 2, 0, 0, 0, 2, 0, 2, 2, 2, 0, 2, 0, 0, 2, 0}, \
118 {0, 2, 0, 2, 0, 2, 0, 0, 2, 0, 0, 2, 2, 0, 2, 0}, \
119 {0, 2, 0, 2, 0, 2, 0, 0, 2, 0, 0, 2, 0, 2, 2, 0}, \
120 {0, 0, 2, 0, 2, 0, 0, 2, 2, 2, 0, 2, 0, 0, 2, 0}, \
121 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
122 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
123 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
124 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
125 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, \
126 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} \
127 };
128
129
130 void setup() {
131 // tell FastLED there's 60 NEOPIXEL leds on pin 2
132 FastLED.addLeds<NEOPIXEL, 2>(leds[0], NUM_LEDS_PER_STRIP);
133
134 // tell FastLED there's 60 NEOPIXEL leds on pin 3
135 FastLED.addLeds<NEOPIXEL, 3>(leds[1], NUM_LEDS_PER_STRIP);
136
137 // tell FastLED there's 60 NEOPIXEL leds on pin 4
138 FastLED.addLeds<NEOPIXEL, 4>(leds[2], NUM_LEDS_PER_STRIP);
139 Serial.begin(9600);
140
141 memcpy(level_actuelle,level_1,sizeof(level_1));
142
143 pinMode(A0,INPUT);
144 pinMode(D7,INPUT);
145 }
146
147
148 void affiche() {
149 //carte
150 for(int x = 0; x < 16; x++) {
151 for(int y = 0; y < 16;y++){
152 if (x%2 == 1){
153 position = x*16+y;
154 }
155 else{
156 position = x*16+15-y;
157 }
158 leds[0][position] = color[level_actuelle[x][y]];
159 }
160 }
161
162 FastLED.show();
163 }
164
165 void create_vaisseau(){
166 //pos entre 2 et 15
167 clear();
168 level_actuelle[13][position_vaisseau] = 1;
169 level_actuelle[13][position_vaisseau-1] = 1;
170 level_actuelle[12][position_vaisseau-1] = 1;
171 level_actuelle[13][position_vaisseau-2] = 1;
172 level_actuelle[14][position_vaisseau-2] = 1;
173 level_actuelle[14][position_vaisseau] = 1;
174 FastLED.show();
175 }
176
177 void clear(){
178 for(int x = 10; x < 15; x++) {
179 for(int y = 0; y < 16;y++){
180 if (level_actuelle[x][y] == 1){
181 level_actuelle[x][y] = 0;
182 }
183 }
184 }
185 }
186
187
188 void move(){
189 position_vaisseau = int(analogRead(A0)*16/1024);
190 if (position_vaisseau >= 16){
191 position_vaisseau = 15;
192 }
193 else if (position_vaisseau <= 1){
194 position_vaisseau = 2;
195 }
196 }
197
198 void tirer() {
199 if (true) {
200 level_actuelle[11][position_vaisseau-1] = 103;
201 }
202 }
203
204 void tick(){
205 ennemi = false;
206 for(int x = 0; x < 16; x++) {
207 for(int y = 0; y < 16;y++){
208 if (level_actuelle[x][y] == 3){ //tire joueur
209 if (x==0){
210 level_actuelle[x][y] = 0;
211 }
212 else if ((level_actuelle[x-1][y]==4) || (level_actuelle[x-1][y]==104)){
213 level_actuelle[x-1][y] = 3;
214 level_actuelle[x][y] = 104;
215 }
216 else if (level_actuelle[x-1][y]!=0){
217 level_actuelle[x-1][y] = 0;
218 level_actuelle[x][y] = 0;
219 }
220 else{
221 level_actuelle[x-1][y] = 3;
222 level_actuelle[x][y] = 0;
223 }
224 }
225
226 else if (level_actuelle[x][y] == 2){ //vaisseau enemi
227 ennemi = true;
228 if ((level_actuelle[x+1][y] == 0)&(random(0,40)==1)){
229 level_actuelle[x+1][y] = 104; //chiffre temporaire pour pas refaire son action
230 }
231 }
232 else if (level_actuelle[x][y] == 104){
233 level_actuelle[x][y] = 4;
234 }
235 else if (level_actuelle[x][y] == 103){
236 level_actuelle[x][y] = 3;
237 }
238 else if (level_actuelle[x][y]== 4){
239 if (x==15){
240 level_actuelle[x][y] = 0;
241 }
242 if ((level_actuelle[x+1][y] == 0) &(x<15)){
243 level_actuelle[x+1][y] = 104;
244 level_actuelle[x][y] = 0;
245 }
246 else if (level_actuelle[x+1][y] == 3){
247 level_actuelle[x+1][y] = 104;
248 level_actuelle[x][y] = 3;
249 }
250 else if (level_actuelle[x+1][y] == 1){
251 level_actuelle[x][y] = 0;
252 //game over
253 en_partie = false;
254 vivant = false;
255 }
256 }
257 }
258 }
259 }
260
261 void loop() {
262 while (en_partie){
263 tick();
264 affiche();
265 create_vaisseau();
266 if ((digitalRead(D7)) & (delay_tire == 0)){
267 tirer();
268 delay_tire = 2;
269 }
270 else if (delay_tire !=0){
271 delay_tire -= 1;
272 }
273 move();
274 if (!ennemi){
275 if (level == 4){
276 en_partie = false;
277
278 }
279 else{
280 level +=1;
281 }
282
283 if(level==2){
284 memcpy(level_actuelle,level_2,sizeof(level_2));
285 }
286 else if(level==3){
287 memcpy(level_actuelle,level_3,sizeof(level_3));
288 }
289 else if(level==4){
290 memcpy(level_actuelle,level_4,sizeof(level_4));
291 }
292 }
293 delay(75);
294 }
295 if (vivant){
296 memcpy(level_actuelle,win,sizeof(win));
297 }
298 else{
299 memcpy(level_actuelle,game_over,sizeof(game_over));
300 }
301 affiche();
302 delay(200);
303 if (digitalRead(D7)){
304 memcpy(level_actuelle,level_1,sizeof(level_1));
305 level = 1;
306 vivant = true;
307 en_partie = true;
308 }
309 }
étapes de fabrication
étape 1
Création du code arduino et test de celui-ci sur la carte. Toutes nos leds s'allument.
étape 2
Création de la maquette en carton. Ce n'est pas la version finale, juste le prototype.
Création de la maquette finale en bois.
étape 3
Test du jeu.
Troubleshouting
Difficultés rencontrées : création du code arduino
Solutions : test du code, analyse des erreurs, aide des intervenants
Sources et documentation complémentaire
- https://www.makercase.com/#/
- https://www.festi.info/boxes.py/
- https://boxdesigner.connectionlab.org/