/******************************************** ArduGame Oscar Gonzalez Varela 2008 www.BricoGeek.com ********************************************/ #include #include #include #include #include "oled160drv.h" #define BUTTON_UP 7 #define BUTTON_RIGHT 8 #define BUTTON_DOWN 4 #define BUTTON_LEFT 3 #define BUTTON_A 12 #define BUTTON_B 13 #define SOUND_PIN 5 #define SENSOR_PIN_X 1 #define SENSOR_PIN_Y 0 #define BALL_ACCEL 0.3 #define BALL_DECEL 0.3 char use_adxl=0; float ball_x = 64; float ball_y = 64; int ball_size= 5; float acc_x = 0; float acc_y = 0; long last_time=0; char game_time=0; int game_totalpt=0; char game_level=1; #define MAX_PUNTOS 10 int mPuntos_val[MAX_PUNTOS]; int mPuntos_x[MAX_PUNTOS]; int mPuntos_y[MAX_PUNTOS]; void setup() // run once, when the sketch starts { // Set I/O pinMode(OLED_RESETPIN, OUTPUT); pinMode(SOUND_PIN, OUTPUT); pinMode(BUTTON_UP, INPUT); pinMode(BUTTON_RIGHT, INPUT); pinMode(BUTTON_DOWN, INPUT); pinMode(BUTTON_LEFT, INPUT); pinMode(BUTTON_A, INPUT); pinMode(BUTTON_B, INPUT); pinMode(SENSOR_PIN_X, INPUT); pinMode(SENSOR_PIN_Y, INPUT); randomSeed(analogRead(0)); // Init serial comunication for the OLED display Serial.begin(OLED_BAUDRATE); // Initialise display OLED_Init(); //Clear screen OLED_Clear(); } void beep (unsigned char speakerPin, int frequencyInHertz, long timeInMilliseconds) // the sound producing function { int x; long delayAmount = (long)(1000000/frequencyInHertz); long loopTime = (long)((timeInMilliseconds*1000)/(delayAmount*2)); for (x=0;x 5) { color = GetRGB(0, 255, 0); } OLED_DrawCircle(mPuntos_x[i], mPuntos_y[i], mPuntos_val[i], 0, color); } } } void DrawToolbar() { char strText[30]; // Erase first! (black) OLED_DrawRectangle(0, 110, 127, 16, 1, GetRGB(64, 64, 64)); sprintf(strText,"Time: %d", game_time); OLED_DrawText(0, 14, 0, strText, 0xFFFF); sprintf(strText,"Points: %d", game_totalpt); OLED_DrawText(0, 15, 0, strText, 0xFFFF); } void DrawMainMenu() { char exit_loop=0; //Clear screen OLED_Clear(); OLED_DrawText(1, 3, 2, "ArduGame v1.0", 0xFFFF); OLED_DrawText(1, 6, 0, "www.BricoGeek.com", 0xFFFF); OLED_DrawText(1, 10, 0, "Play Motion A", GetRGB(254, 0, 254)); OLED_DrawText(1, 11, 0, "Play Joystick B", GetRGB(254, 254, 0)); while (exit_loop == 0) { // Select (A) if (digitalRead(BUTTON_A) == HIGH) { use_adxl = 1; while (digitalRead(BUTTON_A) == HIGH) { }; exit_loop=1; } if (digitalRead(BUTTON_B) == HIGH) { use_adxl = 0; while (digitalRead(BUTTON_A) == HIGH) { }; exit_loop=1; } } // Some sound here! beep(SOUND_PIN,12500,7); } void loop() // run over and over again { int i; int x, y; char game_over=0; int remaining_points=0; int last_x, last_y, last_size; int val_x=0; int val_y=0; OLED_Clear(); DrawMainMenu(); OLED_Clear(); OLED_DrawCircle(ball_x, ball_y, ball_size, 0, GetRGB(0, 0, 254)); InitGame(); DrawmPuntos(); DrawToolbar(); game_level=1; last_time = millis(); while (!game_over) { // Read acelerometer values (0-1024) if (use_adxl == 1) { val_x = analogRead(SENSOR_PIN_X)-512; val_y = analogRead(SENSOR_PIN_Y)-512; } last_x = ball_x; last_y = ball_y; last_size = ball_size; if (use_adxl == 0) { if (digitalRead(BUTTON_A) == HIGH) { ball_size--; } if (digitalRead(BUTTON_B) == HIGH) { ball_size++; } if (digitalRead(BUTTON_UP) == HIGH) { acc_y-=BALL_ACCEL; } if (digitalRead(BUTTON_DOWN) == HIGH) { acc_y+=BALL_DECEL;} if (digitalRead(BUTTON_LEFT) == HIGH) { acc_x-=BALL_ACCEL; } if (digitalRead(BUTTON_RIGHT) == HIGH) { acc_x+=BALL_DECEL; } } else { acc_x -= (val_x/130); acc_y -= (val_y/130); } // Increase/decrease acceleration ball_x += acc_x; ball_y += acc_y; if (ball_size < 1) { ball_size=1; } if (ball_size > 10) { ball_size=10; } if ( (ball_x != last_x) || (ball_y != last_y) || (ball_size != last_size) ) { OLED_DrawCircle(last_x, last_y, last_size, 0, 0); OLED_DrawCircle(ball_x, ball_y, ball_size, 0, GetRGB(0, 0, 254)); } // Collision detection on corners if ( ((ball_x-ball_size) <= 0) || ((ball_x+ball_size) >= 127) || ((ball_y-ball_size) <= 0) || ((ball_y+ball_size) >= 110) ) { OLED_DrawCircle(ball_x, ball_y, ball_size, 0, GetRGB(254, 254, 0)); // We die! Oh noooo!!! BUUUUU!! beep(SOUND_PIN,2093,15); OLED_DrawCircle(ball_x, ball_y, ball_size, 0, 0); // Erase and reset de ball ball_x = 64; ball_y = 64; acc_x = 0; acc_y = 0; OLED_DrawCircle(ball_x, ball_y, ball_size, 0, GetRGB(0, 0, 254)); } // Collision detection on points remaining_points=0; for (i=0 ; i 0) { if (getDistance(ball_x, ball_y, mPuntos_x[i], mPuntos_y[i]) <= (ball_size+mPuntos_val[i])) { if (mPuntos_val[i] < 5) { // Bad point beep(SOUND_PIN,2000,10); game_totalpt -= mPuntos_val[i]; DrawToolbar(); } else { // Good ball! OLED_DrawCircle(mPuntos_x[i], mPuntos_y[i], mPuntos_val[i], 0, GetRGB(0, 0, 254)); // Make point blue! beep(SOUND_PIN,11100,5); game_totalpt += mPuntos_val[i]; DrawToolbar(); } // Erase point OLED_DrawCircle(mPuntos_x[i], mPuntos_y[i], mPuntos_val[i], 0, 0); mPuntos_val[i] = 0; // Point is now obsolete // Redraw all points DrawmPuntos(); } } // Green remaining points counter if (mPuntos_val[i] >= 5) { remaining_points++; } } // Detect next level if (remaining_points == 0) { char strText[30]; game_level++; // Increase level! sprintf(strText, "LEVEL %d", game_level); OLED_DrawText(1, 3, 2, strText, GetRGB(254, 254, 254)); sprintf(strText, "Total: %d pt", game_totalpt); OLED_DrawText(1, 7, 0, strText, GetRGB(254, 0, 0)); for (i=5000 ; i<20000 ; i+=600) { beep(SOUND_PIN,i,1); //delay(1); } delay(100); OLED_Clear(); InitGame(); DrawmPuntos(); DrawToolbar(); OLED_DrawCircle(ball_x, ball_y, ball_size, 0, GetRGB(0, 0, 254)); } // Detect Game Over if (game_time == 0) { char strText[30]; game_level++; // Increase level! OLED_DrawText(1, 3, 2, "* GAME OVER *", GetRGB(254, 0, 0)); delay(1); for (i=20000 ; i>=5000 ; i-=200) { beep(SOUND_PIN,i,1); //delay(1); } // Wait for button press while (digitalRead(BUTTON_A) == LOW) { } game_over=1; // Game over!!!! } // Time counter if ((millis()-last_time) > 100) { last_time = millis(); game_time--; DrawToolbar(); } } }