player 1

Dependencies:   4DGL-uLCD-SE PinDetect SparkfunAnalogJoystick mbed-rtos mbed SDFileSystem

Fork of 4180FinalLab by Rishi Bhargava

Wireless 2 Player Pong game

Files at this revision

API Documentation at this revision

Comitter:
Mpmart08
Date:
Tue Apr 26 18:24:46 2016 +0000
Parent:
3:591086e44bf9
Child:
5:11bb21342e3f
Commit message:
stuff

Changed in this revision

4DGL-uLCD-SE.lib Show annotated file Show diff for this revision Revisions of this file
SparkfunAnalogJoystick.lib Show annotated file Show diff for this revision Revisions of this file
ball.cpp Show annotated file Show diff for this revision Revisions of this file
ball.h Show annotated file Show diff for this revision Revisions of this file
main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed-rtos.lib Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
paddle.cpp Show annotated file Show diff for this revision Revisions of this file
paddle.h Show annotated file Show diff for this revision Revisions of this file
--- a/4DGL-uLCD-SE.lib	Sun Apr 24 01:23:28 2016 +0000
+++ b/4DGL-uLCD-SE.lib	Tue Apr 26 18:24:46 2016 +0000
@@ -1,1 +1,1 @@
-http://mbed.org/users/jlind6/code/4DGL-uLCD-SE/#d901d4d206e6
+http://developer.mbed.org/users/4180_1/code/4DGL-uLCD-SE/#2cb1845d7681
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/SparkfunAnalogJoystick.lib	Tue Apr 26 18:24:46 2016 +0000
@@ -0,0 +1,1 @@
+http://developer.mbed.org/teams/a/code/SparkfunAnalogJoystick/#98f381ce9b3a
--- a/ball.cpp	Sun Apr 24 01:23:28 2016 +0000
+++ b/ball.cpp	Tue Apr 26 18:24:46 2016 +0000
@@ -6,7 +6,7 @@
     diameter = size;
 }
 
-void Ball::setVx(uint8_t newvx){
+void Ball::setVx(double newvx){
     vx = newvx;
 }
 
@@ -14,8 +14,8 @@
     vxDir = dir;
 }
 
-void Ball::setBaseVy(uint8_t baseVy){
-    vy = baseVy;
+void Ball::setVy(double newVy){
+    vy = newVy;
 }
 
 void Ball::setVyDir(bool dir){
@@ -27,11 +27,11 @@
 }
 
 uint8_t Ball::getX(){
-    return x;
+    return (uint8_t)x;
 }
 
 uint8_t Ball::getY(){
-    return y;
+    return (uint8_t)y;
 }
 
 uint8_t Ball::getFutureX(){
--- a/ball.h	Sun Apr 24 01:23:28 2016 +0000
+++ b/ball.h	Tue Apr 26 18:24:46 2016 +0000
@@ -5,9 +5,9 @@
 public:    
     Ball (uint8_t, uint8_t, uint8_t);
     // Set Functions
-    void setVx(uint8_t); // This sets the velocity
+    void setVx(double); // This sets the velocity
     void setVxDir(bool);
-    void setBaseVy(uint8_t); // This sets the velocity
+    void setVy(double); // This sets the velocity
     void setVyDir(bool);
     // Get Functions
     uint8_t getSize();
@@ -22,11 +22,11 @@
     void update(); // moves the ball on the screen one vx and vy
     
 private:
-    uint8_t vx;
+    double vx;
     bool vxDir; //false is left (-x), true is right (+x)
-    uint8_t vy;
+    double vy;
     bool vyDir; //false is up (-y), true is down (+y)
-    uint8_t x;
-    uint8_t y;
+    double x;
+    double y;
     uint8_t diameter;
 };
--- a/main.cpp	Sun Apr 24 01:23:28 2016 +0000
+++ b/main.cpp	Tue Apr 26 18:24:46 2016 +0000
@@ -1,14 +1,17 @@
 #include "mbed.h"
+#include "rtos.h"
 #include "PinDetect.h"
 #include "Speaker.h"
+#include "soundBuilder.h"
+#include "SparkfunAnalogJoystick.h"
 #include "paddle.h"
 #include "ball.h"
 
 // Pushbuttons
-AnalogIn xMove(p15); 
-PinDetect select(p13);
+SparkfunAnalogJoystick joystick(p16, p15, p14);
+//PinDetect select(p13);
 //Speaker
-//Speaker mySpeaker(p20);
+Speaker mySpeaker(p25);
 Serial pc(USBTX, USBRX);
  
 // State machine definitions
@@ -25,147 +28,212 @@
 gameStateType gameState = START;
 bool ready = false;
 
-// Pushbutton callbacks for selecting to start game
-void select_hit_callback (void)
-{
-    switch (gameState)
-    {
-    case WAIT:
-        ready = true;
-        break;
+Paddle botPaddle(0, 0, 0, 0);
+Paddle topPaddle(0, 0, 0, 0);
+Ball ball(0, 0, 0);
+
+// thread that plays game sounds through the speaker
+void speaker_thread(void const *argument) {
+
+    Speaker *player = &mySpeaker;
+
+    // Start Song
+    float sFreq[] = {550,750,550,750};
+    float sDur[] = {.3,.3,.3,.3};
+    float sVol[] = {.01,.01,.01,.01};
+    SoundBuilder startSong(sFreq, sDur, sVol, sizeof(sFreq)/sizeof(*sFreq), player);
+    
+    // End Song
+    float eFreq[] = {300,200,250,225,200,150,150,100};
+    float eDur[] = {.3,.3,.3,.3,.3,.3,.3,.3};
+    float eVol[] = {.01,.01,.01,.01,.01,.01,.01,.01};
+    SoundBuilder endSong(eFreq, eDur, eVol, sizeof(eFreq)/sizeof(*eFreq), player);
+
+    while (true) {
+        switch (gameState) {
+        case GAME: // if game is running and user dodges a pipe, play a note
+            if (topPaddle.checkHit(ball.getFutureX(), ball.getFutureY(), ball.getSize())
+            || botPaddle.checkHit(ball.getFutureX(), ball.getFutureY(), ball.getSize())
+            || ball.getFutureX() <= 10
+            || ball.getFutureX() + ball.getSize() >= 190) {
+                mySpeaker.PlayNote(440, 0.1, 0.01);
+            }
+            
+            if (ball.getY() < 5){
+                mySpeaker.PlayNote(440, 0.1, 0.01);
+                mySpeaker.PlayNote(880, 0.1, 0.01);
+            }
+            else if (ball.getY() + ball.getSize() > 245){
+                mySpeaker.PlayNote(880, 0.1, 0.01);
+                mySpeaker.PlayNote(440, 0.1, 0.01);
+            }
+            
+            break;
+        case START: // play a song at the start of the game
+            startSong.playSong();
+            Thread::wait(5000);
+            break;
+        case WIN:  // play a song when the player wins the game
+        case LOSE: // play a song when the player loses the game
+            endSong.playSong();
+            Thread::wait(5000);
+            break;
+        }
     }
 }
  
 int main() 
 {   
     // This is setting up the joystick select as a pushbutton
-    select.mode(PullUp);
-    wait(0.1);
-    select.attach_deasserted(&select_hit_callback);
-    select.setSampleFrequency();
+    //joystick.set_callback(&select_hit_callback);
     
-    pc.baud(9600);
+    pc.format(8, SerialBase::None, 1);
+    pc.baud(115200);
 
     uint8_t gameLowX = 10, gameHighX = 190, gameLowY = 5, gameHighY = 245;
     uint8_t gameCenterX = (gameHighX-gameLowX)/2, gameCenterY = (gameHighY-gameLowY)/2;
     uint8_t ballSize=10;
     uint8_t paddleWidth = 5, paddleLength = 35;
-    float botMove = xMove;
-    uint8_t score = 0;
+    float botMove = joystick.yAxis();
+    uint8_t botScore = 0;
+    uint8_t topScore = 0;
     int i = 0;
 
-    Paddle botPaddle(gameCenterX-(paddleLength/2), gameHighY, paddleLength, paddleWidth);
+    botPaddle = Paddle(gameCenterX-(paddleLength/2), gameHighY, paddleLength, paddleWidth);
     botPaddle.setLimits(gameLowX, gameHighX);
     botPaddle.setMaxMove(2);
-    Paddle topPaddle(gameCenterX-(paddleLength/2), gameLowY, paddleLength, paddleWidth);
+    topPaddle = Paddle(gameCenterX-(paddleLength/2), gameLowY, paddleLength, paddleWidth);
     topPaddle.setLimits(gameLowX, gameHighX);
     topPaddle.setMaxMove(2);
-    Ball ball(gameCenterX, gameCenterY, ballSize);
+    ball = Ball(gameCenterX, gameCenterY, ballSize);
     
+    ball.setVxDir(true);
     ball.setVyDir(true);
     
-    while (!pc.writeable() && !pc.readable()){
+    while (!pc.writeable()){
     
     }
+    
+    Thread thread1(speaker_thread);
+    
+    Thread::wait(5000);
+    
     while (1) 
     {   
         switch (gameState)
         {
         case START:
-        if (pc.writeable()){
-            pc.printf("%c%c%c%c%c\n", 0, 0, 0, 0, 0);
-            wait(.5);
-            gameState = WAIT;
-        }
+            if (pc.writeable()){
+                pc.printf("%c%c%c%c%c", 0, 0, 0, 0, 0);
+                ball.setVxDir(true);
+                ball.setVyDir(true);
+                gameState = WAIT;
+            }
             break;
         case GAME_SETUP:
-            ball.reset(gameCenterX, gameCenterY, 0, 1);
+            ball.reset(gameCenterX, gameCenterY, 0, sqrt(5.0));
             botPaddle.reset(gameCenterX-(paddleLength/2), gameHighY);
             topPaddle.reset(gameCenterX-(paddleLength/2), gameLowY);
-            ready = false;
-        if (pc.writeable()){
-            pc.printf("%c%c%c%c%c\n", 3, botPaddle.getX(), topPaddle.getX(), ball.getX(), ball.getY());
-            ball.setVx(0);
-            srand(i);
-            //if (rand()%2){
-//                ball.setBaseVy(-1);
-//            }
-//            else{
-//                ball.setBaseVy(1);
-//            }
-            gameState = GAME;
-        }
+            if (pc.writeable()){
+                pc.printf("%c%c%c%c%c", 3, botScore, topScore, 0, 0);
+                ready = false;
+                srand(i);
+                gameState = GAME;
+                Thread::wait(2000);
+            }
             break;
         case GAME:
-        if (pc.writeable()){
-            pc.printf("%c%c%c%c%c\n", 4, botPaddle.getX(), topPaddle.getX(), ball.getX(), ball.getY());
-            uint8_t size = ball.getSize(); //stored in a temp variable because used a lot
-            if (ball.getFutureX()<=gameLowX){
-                ball.reverseXDirection();
-            }
-            else if (ball.getFutureX()+size>=gameHighX){
-                ball.reverseXDirection();
-            }
-            
-            if (topPaddle.checkHit(ball.getFutureX(), ball.getFutureY(), size)){
-                ball.reverseYDirection();
-                uint8_t fx = ball.getFutureX();
-                ball.setVx(topPaddle.returnAngle(fx, size));
-                ball.setVxDir(topPaddle.returnDir(fx, size));
+            if (pc.writeable()) {
+                pc.printf("%c%c%c%c%c", 4, botPaddle.getX(), topPaddle.getX(), ball.getX(), ball.getY());
+                
+                uint8_t size = ball.getSize(); //stored in a temp variable because used a lot
+                
+                if (ball.getFutureX() <= gameLowX){
+                    ball.reverseXDirection();
+                }
+                else if (ball.getFutureX() + size >= gameHighX){
+                    ball.reverseXDirection();
+                }
+                
+                if (topPaddle.checkHit(ball.getFutureX(), ball.getFutureY(), size)) {
+                    ball.reverseYDirection();
+                    uint8_t fx = ball.getFutureX();
+                    double newVx = topPaddle.returnAngle(fx, size);
+                    double newVy = sqrt(5.0 - (newVx * newVx));
+                    ball.setVx(newVx);
+                    ball.setVy(newVy);
+                    ball.setVxDir(topPaddle.returnDir(fx, size));
+                }
+                else if (botPaddle.checkHit(ball.getFutureX(), ball.getFutureY(), size)) {
+                    ball.reverseYDirection();
+                    uint8_t fx = ball.getFutureX();
+                    double newVx = botPaddle.returnAngle(fx, size);
+                    double newVy = sqrt(5.0 - (newVx * newVx));
+                    ball.setVx(newVx);
+                    ball.setVy(newVy);
+                    ball.setVx(botPaddle.returnAngle(fx, size));
+                    ball.setVxDir(botPaddle.returnDir(fx, size));
+                }
+                
+                if (ball.getY() < gameLowY){
+                    botScore++;
+                    gameState = GAME_SETUP;
+                }
+                else if (ball.getY() + size > gameHighY){
+                    topScore++;
+                    gameState = GAME_SETUP;
+                }
+                
+                if (botScore >= 5) {
+                    gameState = WIN;
+                }
+                else if (topScore >= 5) {
+                    gameState = LOSE;   
+                }
+                
+                ball.update();
+                botMove = -joystick.yAxis();
+                if (botMove < -0.25 || botMove > 0.25) {
+                    botPaddle.move(botMove);
+                }
+                //GET OTHER PADDLE SPOT AND UPDATE topPaddle
             }
-            else if (botPaddle.checkHit(ball.getFutureX(), ball.getFutureY(), size)){
-                ball.reverseYDirection();
-                uint8_t fx = ball.getFutureX();
-                ball.setVx(botPaddle.returnAngle(fx, size));
-                ball.setVxDir(botPaddle.returnDir(fx, size));
-            }
-            
-            if (ball.getY() < gameLowY){
-                gameState = WIN;
-            }
-            else if (ball.getY() > gameHighY){
-                gameState = LOSE;
-            }
-            
-            ball.update();
-            botMove = xMove;
-            if (!botMove == .5){
-                botPaddle.move(.5-botMove);
-            }
-            //GET OTHER PADDLE SPOT AND UPDATE topPaddle
-        }
             break;
         case LOSE:
-        if (pc.writeable()){
-            pc.printf("%c%c%c%c%c\n", 5, 0, 0, 0, 0);
-            score = 0;
-            wait(5.0);
-            gameState = START;
-        }
+            if (pc.writeable()){
+                pc.printf("%c%c%c%c%c", 5, 0, 0, 0, 0);
+                botScore = 0;
+                topScore = 0;
+                Thread::wait(5000);
+                gameState = START;
+            }
             break;
         case WIN:
-        if (pc.writeable()){
-            pc.printf("%c%c%c%c%c\n", 6, 0, 0, 0, 0);
-            wait(5.0);
-            gameState = START;
-        }
+            if (pc.writeable()){
+                pc.printf("%c%c%c%c%c", 6, 0, 0, 0, 0);
+                botScore = 0;
+                topScore = 0;
+                Thread::wait(5000);
+                gameState = START;
+            }
             break;
         case WAIT:
-        if (pc.writeable()){
-            // Used to seed the rand() function so the ball has a random starting direction
-            i++;
-            if (ready){
-                pc.printf("%c%c%c%c%c\n", 2, 0, 0, 0, 0);
-                wait(2.0);
-                gameState = GAME_SETUP;
+            if (pc.writeable()){
+                // Used to seed the rand() function so the ball has a random starting direction
+                i++;
+                if (joystick.button())
+                    ready = true;
+                if (ready){
+                    pc.printf("%c%c%c%c%c", 2, 0, 0, 0, 0);
+                    Thread::wait(2000);
+                    gameState = GAME_SETUP;
+                }
+                else {
+                    pc.printf("%c%c%c%c%c", 1, 0, 0, 0, 0);
+                }
             }
-            else {
-                pc.printf("%c%c%c%c%c\n", 1, 0, 0, 0, 0);
-            }
-        }
             break;
         }
-        wait_ms(20);
-
+        Thread::wait(20);
     } 
 }
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed-rtos.lib	Tue Apr 26 18:24:46 2016 +0000
@@ -0,0 +1,1 @@
+http://developer.mbed.org/users/mbed_official/code/mbed-rtos/#ac4f3830f9ff
--- a/mbed.bld	Sun Apr 24 01:23:28 2016 +0000
+++ b/mbed.bld	Tue Apr 26 18:24:46 2016 +0000
@@ -1,1 +1,1 @@
-http://mbed.org/users/mbed_official/code/mbed/builds/024bf7f99721
\ No newline at end of file
+http://mbed.org/users/mbed_official/code/mbed/builds/082adc85693f
\ No newline at end of file
--- a/paddle.cpp	Sun Apr 24 01:23:28 2016 +0000
+++ b/paddle.cpp	Tue Apr 26 18:24:46 2016 +0000
@@ -3,9 +3,9 @@
 Paddle::Paddle(uint8_t initx, uint8_t inity, uint8_t olength, uint8_t owidth){
     x = initx;
     y = inity;
-    length = length;
-    width = width;
-    if (y < 100){
+    length = olength;
+    width = owidth;
+    if (y < 100) {
         bottom = false;
     }
     else {
@@ -41,26 +41,27 @@
 
 bool Paddle::checkHit(uint8_t ballX, uint8_t ballY, uint8_t size){
     if (ballX+size/2 >= x && ballX+size/2 <= x+length){
-        if (bottom && (ballY+size >= y && ballY <= y+width)){
+        if (bottom && (ballY+size >= y-width && ballY <= y-width)){
             return true;
         }
-        else if (!bottom && (ballY <= y+width && ballY+size >= y)){
+        else if (!bottom && (ballY+size >= y+width && ballY <= y+width)){
             return true;
         }
     }
     return false;
 }
 
-uint8_t Paddle::returnAngle(uint8_t ballX, uint8_t size){
-    return abs((ballX+size/2 - (x + length/2)));
+double Paddle::returnAngle(double ballX, double size){
+    return abs((ballX + size/2) - (x + length/2)) / 35.0 * sqrt(5.0);
 }
 
 bool Paddle::returnDir(uint8_t ballX, uint8_t size){
-    if (ballX+size/2 > (x+length/2)){
+    if ((ballX+size/2) > (x+length/2)){
         return true;
     }
-    else
+    else {
         return false;
+    }
 }
 
 void Paddle::reset(uint8_t initx, uint8_t inity){
--- a/paddle.h	Sun Apr 24 01:23:28 2016 +0000
+++ b/paddle.h	Tue Apr 26 18:24:46 2016 +0000
@@ -14,7 +14,7 @@
     // Member Functions
     void move(float); // false means move left, true means move right
     bool checkHit(uint8_t, uint8_t, uint8_t); // Using a position and size, checks to see if something has hit the paddle
-    uint8_t returnAngle(uint8_t, uint8_t); // Using a ball x position, gives a return vx and vxDir
+    double returnAngle(double, double); // Using a ball x position, gives a return vx and vxDir
     bool returnDir(uint8_t, uint8_t);
     void reset(uint8_t, uint8_t);