#include #include #include #include #include #include #include #include "bitmap.h" #include "sound.h" const bool SOUND_ENABLE = false; const short INIT_X = 0; const short INIT_Y = 48; const unsigned long display_interval = 100; const unsigned long nunchuk_interval = 100; const unsigned int sound_tempo = 10; U8G2_ST7920_128X64_2_SW_SPI u8g2(U8G2_R0, /* clock=*/ 2, /* data=*/ 10, /* cs=*/ 7); //A5 A4 A3 A2 ArduinoNunchuk nunchuk = ArduinoNunchuk(); Tone tone1; short posX = INIT_X; short posY = INIT_Y; unsigned int nextLaneY = INIT_Y - 16; unsigned long last_display = millis(); unsigned long last_nunchuck = millis(); unsigned long last_note = millis(); unsigned long next_note = millis(); short notes_index = 0; short intro_size = sizeof(notes_intro)/sizeof(notes_intro[0]); short fishes[8][2] = {{random(128,255) , 32}, {random(128,255) , 32}, {random(128,255),48}, {random(128,255),48}, {random(128,255),16}, {random(128,255),16}, {random(128,255),1}, {random(128,255) , 1} }; bool game_init = true; bool jump = false; bool jumpBack = false; bool jumpInProgress = false; unsigned int score = 50; //set A3 and A2 has +5V / GND void nunchuck_setpowerpins() { #define pwrpin PORTC3 #define gndpin PORTC2 DDRC |= _BV(pwrpin) | _BV(gndpin); PORTC &=~ _BV(gndpin); PORTC |= _BV(pwrpin); delay(100); // wait for things to stabilize } void setup(void) { //init serial for debug Serial.begin(115200); //init nunchuck nunchuck_setpowerpins(); nunchuk.init(); //init lcd u8g2.begin(); //init sound tone1.begin(8); } void play_intro(){ if(SOUND_ENABLE){ if(millis() >= next_note){ next_note = millis() + interval_intro[notes_index]; tone1.play(notes_intro[notes_index], interval_intro[notes_index]); if(notes_index < intro_size - 1){ notes_index++; } } } } void play_sound(uint16_t _note, uint32_t _duration){ if(SOUND_ENABLE){ tone1.play(_note, _duration); } } void display_welcome_page() { u8g2.setFont(u8g2_font_5x7_mf); u8g2.drawStr(0, 7, "Welcome to Carrot game!"); u8g2.drawStr(15, 25, "Press Z to start."); u8g2.drawXBMP(posX, posY, 16, 16, fish); } void display_game() { u8g2.setFont(u8g2_font_5x7_mf); char score_str[] = "000"; sprintf(score_str, "%03d", score); u8g2.drawStr(110, 62, score_str); for (int i = 0; i < 8; i++) { if(fishes[i][0] != NULL){ u8g2.drawXBMP(fishes[i][0], fishes[i][1], 16, 16, fish_reverse); } } u8g2.drawXBMP(posX, posY, 16, 16, carrot); //swimelanes u8g2.drawHLine(0, 0, 128); //top u8g2.drawHLine(0, 16, 128); u8g2.drawHLine(0, 32, 128); u8g2.drawHLine(0, 48, 128); u8g2.drawHLine(0, 63, 128); //bottom } void compute_fishes_position(){ short fish_step = (200 + score)/100; for (int i = 0; i < 8; i++) { if(fishes[i][0] != NULL){ if(fishes[i][0] <= fish_step) { fishes[i][0] = 128; score = score - 10; play_sound(NOTE_B1,300); if (score <= 0){ play_sound(NOTE_G1,300); play_sound(NOTE_F1,300); play_sound(NOTE_E1,300); play_sound(NOTE_D1,300); play_sound(NOTE_C1,300); game_init = true; } } else{ fishes[i][0] = fishes[i][0] - fish_step; } //does carrot eat the fish if( (posX > (fishes[i][0] - 8) && posX < (fishes[i][0] + 8) ) && (posY > (fishes[i][1] - 8) && posY < (fishes[i][1] + 8) )){ fishes[i][0] = random(128,255); play_sound(NOTE_B5,100); score = score + 10; } Serial.print("score: "); Serial.println(score); } } } void compute_cat_position() { if (game_init) { if (posX < 112) { posX = posX + 2; } else { posX = INIT_X; if (posY < 48) { posY = posY + 16; } else { posY = INIT_Y; } } } //game else { //compute X pos if (nunchuk.analogX < 120 && posX >= 4) { if (nunchuk.analogX < 80) { if(posX >= 8){ posX = posX - 8; }else{ posX = posX - 4; } } else { posX = posX - 4; } } if (nunchuk.analogX > 140 && posX < 112) { if (nunchuk.analogX > 180) { posX = posX + 8; } else { posX = posX + 4; } } //compute jump //detect a new jump if(nunchuk.zButton == 1 && !jump && !jumpBack && posY > 0){ Serial.println("jump!"); //tone1.play(NOTE_B4,500); jump = true; jumpInProgress = true; nextLaneY = posY - 16; posY = posY - 4; Serial.println(nextLaneY); } else { //continue a current jump if (jump) { if (posY > nextLaneY && jumpInProgress) { posY = posY - 4; } else { if (posY != nextLaneY){ jumpInProgress = false; posY = posY + 4; } else{ jump = false; } } } } if(nunchuk.cButton == 1 && !jump && !jumpBack && posY < 48){ Serial.println("jump bottom!"); //tone1.play(NOTE_B2,500); jumpBack = true; jumpInProgress = true; nextLaneY = posY + 16; posY = posY + 4; Serial.println(nextLaneY); } else { //continue a current jump if (jumpBack) { if (posY < nextLaneY && jumpInProgress) { posY = posY + 4; } else { if (posY != nextLaneY){ jumpInProgress = false; posY = posY - 4; } else{ jumpBack = false; } } } } } } void loop(void) { if(millis() - last_display >= display_interval){ u8g2.firstPage(); do { if(game_init){ display_welcome_page(); score = 50; } else{ display_game(); } } while ( u8g2.nextPage() ); last_display = millis(); } if(millis() - last_nunchuck >= nunchuk_interval){ nunchuk.update(); if(init){ if(nunchuk.zButton == 1){ if(game_init){ game_init = false; //set default pos to avoid issue posX = INIT_X; posY = INIT_Y; } } } last_nunchuck = millis(); if(game_init){ play_intro(); } else{ compute_cat_position(); compute_fishes_position(); } } // Serial.print(posX); // Serial.print(' '); // Serial.println(posY); // Serial.print(nunchuk.analogX, DEC); // Serial.print(' '); // Serial.println(nunchuk.analogY, DEC); //Serial.print(' '); // Serial.print(nunchuk.accelX, DEC); // Serial.print(' '); // Serial.print(nunchuk.accelY, DEC); // Serial.print(' '); // Serial.print(nunchuk.accelZ, DEC); // Serial.print(' '); // Serial.print(nunchuk.zButton, DEC); // Serial.print(' '); // Serial.println(nunchuk.cButton, DEC); //delay(interval); }