A project that creates falling asteroids at random positions along the top of the screen for a space ship at the bottom to shoot, using a Nokia N5110 LCD, joystick and pushbuttons - A revised name from my earlier project L2_2645
Dependencies: DebounceIn N5110 PowerControl mbed
Fork of L2_2645_project by
main.cpp@4:51f8b719f671, 2015-05-11 (annotated)
- Committer:
- wray2303
- Date:
- Mon May 11 14:40:23 2015 +0000
- Revision:
- 4:51f8b719f671
- Parent:
- 3:39c95d65bee5
final program bugs fixed
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
wray2303 | 0:6eba0e66ce01 | 1 | /** |
wray2303 | 0:6eba0e66ce01 | 2 | @file main.cpp |
wray2303 | 0:6eba0e66ce01 | 3 | |
wray2303 | 0:6eba0e66ce01 | 4 | @brief Program implementation |
wray2303 | 0:6eba0e66ce01 | 5 | |
wray2303 | 0:6eba0e66ce01 | 6 | @author Louis Wray |
wray2303 | 0:6eba0e66ce01 | 7 | |
wray2303 | 0:6eba0e66ce01 | 8 | @date 14th April 2015 |
wray2303 | 0:6eba0e66ce01 | 9 | */ |
wray2303 | 0:6eba0e66ce01 | 10 | |
wray2303 | 0:6eba0e66ce01 | 11 | #include "main.h" |
wray2303 | 0:6eba0e66ce01 | 12 | |
wray2303 | 0:6eba0e66ce01 | 13 | /// timer to regularly read the joystick |
wray2303 | 0:6eba0e66ce01 | 14 | Ticker pollJoystick; |
wray2303 | 0:6eba0e66ce01 | 15 | /// timer to regularly call the read bullet function |
wray2303 | 0:6eba0e66ce01 | 16 | Ticker readShoot; |
wray2303 | 0:6eba0e66ce01 | 17 | /// timer to regularly call new asteroids |
wray2303 | 0:6eba0e66ce01 | 18 | Ticker readTheAsteroid; |
wray2303 | 3:39c95d65bee5 | 19 | /// timer to create the asteroids |
wray2303 | 0:6eba0e66ce01 | 20 | Timer shootSoundtimer; |
wray2303 | 3:39c95d65bee5 | 21 | ///timeout used to stop button skip |
wray2303 | 3:39c95d65bee5 | 22 | Timeout EndGame; |
wray2303 | 0:6eba0e66ce01 | 23 | |
wray2303 | 0:6eba0e66ce01 | 24 | /** |
wray2303 | 0:6eba0e66ce01 | 25 | create enumerated type (0,1,2,3 etc. for direction) |
wray2303 | 0:6eba0e66ce01 | 26 | */ |
wray2303 | 0:6eba0e66ce01 | 27 | enum DirectionName { |
wray2303 | 0:6eba0e66ce01 | 28 | UP, |
wray2303 | 0:6eba0e66ce01 | 29 | DOWN, |
wray2303 | 0:6eba0e66ce01 | 30 | LEFT, |
wray2303 | 0:6eba0e66ce01 | 31 | RIGHT, |
wray2303 | 0:6eba0e66ce01 | 32 | CENTRE, |
wray2303 | 0:6eba0e66ce01 | 33 | UNKNOWN |
wray2303 | 0:6eba0e66ce01 | 34 | }; |
wray2303 | 0:6eba0e66ce01 | 35 | |
wray2303 | 0:6eba0e66ce01 | 36 | /** |
wray2303 | 0:6eba0e66ce01 | 37 | struct for Joystick |
wray2303 | 0:6eba0e66ce01 | 38 | */ |
wray2303 | 0:6eba0e66ce01 | 39 | typedef struct JoyStick Joystick; |
wray2303 | 0:6eba0e66ce01 | 40 | struct JoyStick { |
wray2303 | 0:6eba0e66ce01 | 41 | float x; /// current x value |
wray2303 | 0:6eba0e66ce01 | 42 | float x0; /// 'centred' x value |
wray2303 | 0:6eba0e66ce01 | 43 | float y; /// current y value |
wray2303 | 0:6eba0e66ce01 | 44 | float y0; /// 'centred' y value |
wray2303 | 0:6eba0e66ce01 | 45 | int button; /// button state (assume pull-down used, so 1 = pressed, 0 = unpressed) |
wray2303 | 0:6eba0e66ce01 | 46 | DirectionName direction; /// current direction |
wray2303 | 0:6eba0e66ce01 | 47 | }; |
wray2303 | 0:6eba0e66ce01 | 48 | /// create struct variable |
wray2303 | 0:6eba0e66ce01 | 49 | Joystick joystick; |
wray2303 | 0:6eba0e66ce01 | 50 | |
wray2303 | 0:6eba0e66ce01 | 51 | int printFlag =0; /**< flag for calling joystick value printing */ |
wray2303 | 0:6eba0e66ce01 | 52 | int state = 0; /**< integer value for what state the game is in. |
wray2303 | 0:6eba0e66ce01 | 53 | for use of the switch statement */ |
wray2303 | 0:6eba0e66ce01 | 54 | int GenAsteroidFlag = 0; /// asteroid generation flag |
wray2303 | 0:6eba0e66ce01 | 55 | int AsteroidCreatedFlag = 0; /// flag to note asteroid is created |
wray2303 | 0:6eba0e66ce01 | 56 | int BulletExistsFlag = 0; /// flag to note bullet has been fired and is on screen |
wray2303 | 2:8d28a2f491eb | 57 | int PauseNumber = 0; /// pause flag |
wray2303 | 2:8d28a2f491eb | 58 | int HighScore = 0; /// integer set for highscore |
wray2303 | 0:6eba0e66ce01 | 59 | |
wray2303 | 0:6eba0e66ce01 | 60 | int main() |
wray2303 | 0:6eba0e66ce01 | 61 | { |
wray2303 | 0:6eba0e66ce01 | 62 | asteroid.nscore = 0; |
wray2303 | 0:6eba0e66ce01 | 63 | srand(15000*randomPin); /// seeding random function |
wray2303 | 0:6eba0e66ce01 | 64 | calibrateJoystick(); /// set's centred values of joystick |
wray2303 | 3:39c95d65bee5 | 65 | pollJoystick.attach(&updateJoystick,1/50.0); /// read joystick 50 times per second |
wray2303 | 0:6eba0e66ce01 | 66 | ship.SetValues(42,39); /// initialise ships starting x,y coordinates |
wray2303 | 0:6eba0e66ce01 | 67 | |
wray2303 | 0:6eba0e66ce01 | 68 | PHY_PowerDown(); /// power down ethernet connection |
wray2303 | 0:6eba0e66ce01 | 69 | |
wray2303 | 0:6eba0e66ce01 | 70 | while(1) { |
wray2303 | 0:6eba0e66ce01 | 71 | |
wray2303 | 0:6eba0e66ce01 | 72 | switch(state) { /// switch statement this enables the game to switch between states giving a start state |
wray2303 | 0:6eba0e66ce01 | 73 | /// a game play state and subsequently a game over state giving choice to start again. |
wray2303 | 0:6eba0e66ce01 | 74 | |
wray2303 | 0:6eba0e66ce01 | 75 | case 0: |
wray2303 | 0:6eba0e66ce01 | 76 | startUpDisplay(); /// call start up display function |
wray2303 | 0:6eba0e66ce01 | 77 | state=1; |
wray2303 | 0:6eba0e66ce01 | 78 | break; |
wray2303 | 0:6eba0e66ce01 | 79 | |
wray2303 | 0:6eba0e66ce01 | 80 | case 1: |
wray2303 | 0:6eba0e66ce01 | 81 | Game(); /// game play |
wray2303 | 0:6eba0e66ce01 | 82 | break; |
wray2303 | 0:6eba0e66ce01 | 83 | |
wray2303 | 0:6eba0e66ce01 | 84 | case 2: |
wray2303 | 2:8d28a2f491eb | 85 | lcd.clear(); /// clears display |
wray2303 | 2:8d28a2f491eb | 86 | PauseDisplay(); /// applies pause screen |
wray2303 | 0:6eba0e66ce01 | 87 | break; |
wray2303 | 0:6eba0e66ce01 | 88 | |
wray2303 | 0:6eba0e66ce01 | 89 | case 3: |
wray2303 | 0:6eba0e66ce01 | 90 | EndDisplay(); /// end of game display |
wray2303 | 0:6eba0e66ce01 | 91 | break; |
wray2303 | 0:6eba0e66ce01 | 92 | } |
wray2303 | 0:6eba0e66ce01 | 93 | |
wray2303 | 0:6eba0e66ce01 | 94 | Sleep(); /// sleep function when nothings happening mbed can sleep and save power consumption |
wray2303 | 0:6eba0e66ce01 | 95 | } |
wray2303 | 0:6eba0e66ce01 | 96 | } |
wray2303 | 0:6eba0e66ce01 | 97 | |
wray2303 | 2:8d28a2f491eb | 98 | |
wray2303 | 2:8d28a2f491eb | 99 | void Read() |
wray2303 | 2:8d28a2f491eb | 100 | { |
wray2303 | 2:8d28a2f491eb | 101 | FILE *fp = fopen("/local/HSCORES.txt","r"); /// open file or create then open if not already made. and read value |
wray2303 | 2:8d28a2f491eb | 102 | fscanf(fp, "%i", &HighScore); /// look in the local file system |
wray2303 | 2:8d28a2f491eb | 103 | fclose(fp); /// close file |
wray2303 | 2:8d28a2f491eb | 104 | } |
wray2303 | 2:8d28a2f491eb | 105 | |
wray2303 | 2:8d28a2f491eb | 106 | void Write() |
wray2303 | 2:8d28a2f491eb | 107 | { |
wray2303 | 2:8d28a2f491eb | 108 | FILE *fp = fopen("/local/HSCORES.txt","w"); /// open file or create then open if not already made. make ready for writing to the file |
wray2303 | 2:8d28a2f491eb | 109 | fprintf(fp, "%i\r\n", HighScore); /// print value to the local file |
wray2303 | 2:8d28a2f491eb | 110 | fclose(fp); /// close file |
wray2303 | 2:8d28a2f491eb | 111 | } |
wray2303 | 2:8d28a2f491eb | 112 | |
wray2303 | 2:8d28a2f491eb | 113 | |
wray2303 | 0:6eba0e66ce01 | 114 | void startUpDisplay() |
wray2303 | 0:6eba0e66ce01 | 115 | { |
wray2303 | 0:6eba0e66ce01 | 116 | lcd.init(); /// initialise the display |
wray2303 | 0:6eba0e66ce01 | 117 | lcd.clear(); |
wray2303 | 0:6eba0e66ce01 | 118 | lcd.printString("Space-Teroid",6,1); /// opening message |
wray2303 | 0:6eba0e66ce01 | 119 | lcd.printString("Press S5 to",12,3); |
wray2303 | 0:6eba0e66ce01 | 120 | lcd.printString("Play",30,4); |
wray2303 | 0:6eba0e66ce01 | 121 | lcd.drawLine(0,0,0,47,1); /// draw outline |
wray2303 | 0:6eba0e66ce01 | 122 | lcd.drawLine(83,0,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 123 | lcd.drawLine(0,0,83,0,1); |
wray2303 | 0:6eba0e66ce01 | 124 | lcd.drawLine(0,47,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 125 | lcd.refresh(); /// refesh LCD to create this display |
wray2303 | 0:6eba0e66ce01 | 126 | |
wray2303 | 0:6eba0e66ce01 | 127 | while(!buttonP) { /// while the pause flag or pause button has not been set or used , the mbed will sleep saving power and allowing |
wray2303 | 0:6eba0e66ce01 | 128 | /// the user to start when they are ready |
wray2303 | 0:6eba0e66ce01 | 129 | sleep(); |
wray2303 | 0:6eba0e66ce01 | 130 | } |
wray2303 | 0:6eba0e66ce01 | 131 | GenAsteroidFlag = 1; |
wray2303 | 0:6eba0e66ce01 | 132 | lcd.clear(); /// when flag has been set while loop has been broken and start up display will be escaped |
wray2303 | 0:6eba0e66ce01 | 133 | ship.shape(); /// the ships shape is drawn and and the game can begin |
wray2303 | 0:6eba0e66ce01 | 134 | } |
wray2303 | 0:6eba0e66ce01 | 135 | |
wray2303 | 2:8d28a2f491eb | 136 | |
wray2303 | 0:6eba0e66ce01 | 137 | void Game() |
wray2303 | 0:6eba0e66ce01 | 138 | { |
wray2303 | 0:6eba0e66ce01 | 139 | lcd.drawLine(0,0,0,47,1); /// draw outline repeatedly when asteroid is falling |
wray2303 | 0:6eba0e66ce01 | 140 | lcd.drawLine(83,0,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 141 | lcd.drawLine(0,0,83,0,1); |
wray2303 | 0:6eba0e66ce01 | 142 | lcd.drawLine(0,47,83,47,1); |
wray2303 | 2:8d28a2f491eb | 143 | |
wray2303 | 0:6eba0e66ce01 | 144 | if (printFlag) { /// if print flag set, clear flag and use joysticks horizontal position |
wray2303 | 0:6eba0e66ce01 | 145 | printFlag = 0; |
wray2303 | 0:6eba0e66ce01 | 146 | |
wray2303 | 0:6eba0e66ce01 | 147 | if (joystick.direction == LEFT && ship.xs>=7) { /// 7 represents the left most boundary |
wray2303 | 0:6eba0e66ce01 | 148 | ship.ShipLeft(); /// if joystick moves left, call ship moving left function |
wray2303 | 0:6eba0e66ce01 | 149 | } |
wray2303 | 0:6eba0e66ce01 | 150 | if (joystick.direction == RIGHT && ship.xs<=76) { /// 76 represents the right most boundary |
wray2303 | 0:6eba0e66ce01 | 151 | ship.ShipRight(); /// if joystick moves right, call the ship moving right function |
wray2303 | 0:6eba0e66ce01 | 152 | } else {} /// else do nothing |
wray2303 | 0:6eba0e66ce01 | 153 | } |
wray2303 | 0:6eba0e66ce01 | 154 | |
wray2303 | 0:6eba0e66ce01 | 155 | if(button) { |
wray2303 | 0:6eba0e66ce01 | 156 | AsteroidCreatedFlag = 0; |
wray2303 | 0:6eba0e66ce01 | 157 | GenAsteroidFlag = 0; |
wray2303 | 0:6eba0e66ce01 | 158 | asteroid.destroyAsteroid(); |
wray2303 | 0:6eba0e66ce01 | 159 | readTheAsteroid.detach(); |
wray2303 | 0:6eba0e66ce01 | 160 | PWM1 = 0; |
wray2303 | 0:6eba0e66ce01 | 161 | state = 2; |
wray2303 | 0:6eba0e66ce01 | 162 | |
wray2303 | 0:6eba0e66ce01 | 163 | } else {} |
wray2303 | 0:6eba0e66ce01 | 164 | |
wray2303 | 0:6eba0e66ce01 | 165 | if(BulletExistsFlag==0) { /// check if there is already a bullet on the screen, a rule of the game one bullet at a time! |
wray2303 | 0:6eba0e66ce01 | 166 | if(buttonS) { /// if shoot button is pressed |
wray2303 | 0:6eba0e66ce01 | 167 | |
wray2303 | 0:6eba0e66ce01 | 168 | shootSoundtimer.start(); /// start timer for shooting sound |
wray2303 | 0:6eba0e66ce01 | 169 | PWM1.period(2e-3); /// set the period of the PWM |
wray2303 | 0:6eba0e66ce01 | 170 | PWM1 = 0.5; /// set the duty cycle |
wray2303 | 0:6eba0e66ce01 | 171 | BulletExistsFlag=1; /// bullet exists flag set |
wray2303 | 0:6eba0e66ce01 | 172 | bullet.SetValues(ship.xs,ship.ys-1); /// set the bullets values according to where the ship is |
wray2303 | 0:6eba0e66ce01 | 173 | |
wray2303 | 0:6eba0e66ce01 | 174 | bullet.collision(); /// chec for bullet collision |
wray2303 | 0:6eba0e66ce01 | 175 | if(bullet.collision()==true) { |
wray2303 | 0:6eba0e66ce01 | 176 | readShoot.detach(); |
wray2303 | 0:6eba0e66ce01 | 177 | bullet.clearBullet(); |
wray2303 | 0:6eba0e66ce01 | 178 | BulletExistsFlag=0; |
wray2303 | 0:6eba0e66ce01 | 179 | /** if bullet colision happens during sound being made then |
wray2303 | 2:8d28a2f491eb | 180 | *buzzer doesnt stop, thisis because of the interrupt the button makes |
wray2303 | 2:8d28a2f491eb | 181 | *here we reset the buzzer manually */ |
wray2303 | 0:6eba0e66ce01 | 182 | shootSoundtimer.stop(); /// stop the timer |
wray2303 | 0:6eba0e66ce01 | 183 | shootSoundtimer.reset(); /// reset the timer |
wray2303 | 0:6eba0e66ce01 | 184 | PWM1 = 0.0; /// turn of the PWM |
wray2303 | 0:6eba0e66ce01 | 185 | } |
wray2303 | 0:6eba0e66ce01 | 186 | |
wray2303 | 0:6eba0e66ce01 | 187 | else if(bullet.collision()==false) { /// if bullet co-ordinates are not off the screen |
wray2303 | 0:6eba0e66ce01 | 188 | bullet.createBullet(); /// create the bullet |
wray2303 | 2:8d28a2f491eb | 189 | readShoot.attach(&ReadBullet,0.045); /// set ticker to read the position of the bullet |
wray2303 | 0:6eba0e66ce01 | 190 | } else {} |
wray2303 | 0:6eba0e66ce01 | 191 | |
wray2303 | 0:6eba0e66ce01 | 192 | if(AsteroidCreatedFlag==1) { /// check if an asteroid has been created |
wray2303 | 2:8d28a2f491eb | 193 | readTheAsteroid.attach(&ReadAsteroid,0.045); /// set ticker for asteroid movement |
wray2303 | 0:6eba0e66ce01 | 194 | } else {} |
wray2303 | 0:6eba0e66ce01 | 195 | } else {} |
wray2303 | 0:6eba0e66ce01 | 196 | } |
wray2303 | 0:6eba0e66ce01 | 197 | |
wray2303 | 0:6eba0e66ce01 | 198 | if(GenAsteroidFlag == 1) { /// check if an asteroid is to be generated |
wray2303 | 0:6eba0e66ce01 | 199 | int A = rand() % 75 + 6; /// returns random value between 6 and 7 |
wray2303 | 0:6eba0e66ce01 | 200 | asteroid.SetAsteroidValue(A,0); /// set asteroid position according to randomly generated value |
wray2303 | 0:6eba0e66ce01 | 201 | asteroid.createAsteroid(); /// create asteroid |
wray2303 | 0:6eba0e66ce01 | 202 | AsteroidCreatedFlag = 1; /// set flag to state an asteroid has been created and is on screen |
wray2303 | 0:6eba0e66ce01 | 203 | GenAsteroidFlag=0; /// reset Generate asteroid flag so no more asteroid are created |
wray2303 | 0:6eba0e66ce01 | 204 | if(AsteroidCreatedFlag==1) { /// if asteroid has been created |
wray2303 | 2:8d28a2f491eb | 205 | readTheAsteroid.attach(&ReadAsteroid,0.045); /// set ticker to read and move asteroid |
wray2303 | 0:6eba0e66ce01 | 206 | } else {} |
wray2303 | 2:8d28a2f491eb | 207 | } else {} |
wray2303 | 2:8d28a2f491eb | 208 | } |
wray2303 | 0:6eba0e66ce01 | 209 | |
wray2303 | 0:6eba0e66ce01 | 210 | |
wray2303 | 0:6eba0e66ce01 | 211 | void ReadAsteroid() |
wray2303 | 0:6eba0e66ce01 | 212 | { |
wray2303 | 0:6eba0e66ce01 | 213 | bullet.collision(); /// check if the bullet has made a collision this must mean an asteroid has been shot |
wray2303 | 0:6eba0e66ce01 | 214 | if(bullet.collision()==false) { /// if no collision and the asteroid y position is less than the end of the screen move the asteroid |
wray2303 | 0:6eba0e66ce01 | 215 | asteroid.ya=asteroid.ya+1; /// move asteroids y position down the screen |
wray2303 | 0:6eba0e66ce01 | 216 | asteroid.erasePrevAsteroid(); /// erase the previous asteroid |
wray2303 | 0:6eba0e66ce01 | 217 | asteroid.createAsteroid(); /// create the asteroid in its new position |
wray2303 | 0:6eba0e66ce01 | 218 | } else {} |
wray2303 | 0:6eba0e66ce01 | 219 | |
wray2303 | 0:6eba0e66ce01 | 220 | ////////// using a double check seems to make the game run smoother ////////////// |
wray2303 | 0:6eba0e66ce01 | 221 | bullet.collision(); /// check if the bullet has made a collision this must mean an asteroid has been shot |
wray2303 | 0:6eba0e66ce01 | 222 | if(bullet.collision()==true) { /// if a collision is made |
wray2303 | 0:6eba0e66ce01 | 223 | BulletExistsFlag=0; /// reset the bullet exists flag |
wray2303 | 0:6eba0e66ce01 | 224 | readShoot.detach(); |
wray2303 | 0:6eba0e66ce01 | 225 | readTheAsteroid.detach(); /// detach the read asteroid function from the ticker |
wray2303 | 0:6eba0e66ce01 | 226 | bullet.clearBullet(); /// clear the bullet from the screen |
wray2303 | 0:6eba0e66ce01 | 227 | AsteroidCreatedFlag=0; /// reset Asteroid created Flag to state there is no longer an asteroid on screen |
wray2303 | 0:6eba0e66ce01 | 228 | GenAsteroidFlag=1; /// set the Generate asteroid flag |
wray2303 | 0:6eba0e66ce01 | 229 | asteroid.destroyAsteroid(); /// destroy on screen asteroid |
wray2303 | 2:8d28a2f491eb | 230 | |
wray2303 | 2:8d28a2f491eb | 231 | /** if bullet colision happens during sound being made then |
wray2303 | 2:8d28a2f491eb | 232 | buzzer doesnt stop, thisis because of the interrupt the button makes |
wray2303 | 2:8d28a2f491eb | 233 | here we reset the buzzer manually*/ |
wray2303 | 2:8d28a2f491eb | 234 | shootSoundtimer.stop(); /// stop the timer |
wray2303 | 2:8d28a2f491eb | 235 | shootSoundtimer.reset(); /// reset the timer |
wray2303 | 2:8d28a2f491eb | 236 | PWM1 = 0.0; /// turn of the PWM |
wray2303 | 0:6eba0e66ce01 | 237 | } else {} |
wray2303 | 0:6eba0e66ce01 | 238 | |
wray2303 | 0:6eba0e66ce01 | 239 | asteroid.armageddon(); /// check if asteroid has reached the bottom of the screen |
wray2303 | 0:6eba0e66ce01 | 240 | if(asteroid.armageddon() == true) { /// if asteroid has it the bottom of the screen ... RUN!!! |
wray2303 | 0:6eba0e66ce01 | 241 | /// armageddon takes place and the game is over |
wray2303 | 0:6eba0e66ce01 | 242 | bullet.clearBullet(); /// clear the existing bullet |
wray2303 | 0:6eba0e66ce01 | 243 | readTheAsteroid.detach(); /// detach the read asteroid function |
wray2303 | 0:6eba0e66ce01 | 244 | asteroid.destroyAsteroid(); /// destroy asteroid in place |
wray2303 | 3:39c95d65bee5 | 245 | EndGame.attach(&endState,0.3); |
wray2303 | 0:6eba0e66ce01 | 246 | } else {} |
wray2303 | 0:6eba0e66ce01 | 247 | |
wray2303 | 2:8d28a2f491eb | 248 | lcd.drawLine(0,0,83,0,1); /// keep re-drawing top line as this is damaged while asteroid moves accross it |
wray2303 | 0:6eba0e66ce01 | 249 | } |
wray2303 | 0:6eba0e66ce01 | 250 | |
wray2303 | 2:8d28a2f491eb | 251 | |
wray2303 | 0:6eba0e66ce01 | 252 | void ReadBullet() |
wray2303 | 0:6eba0e66ce01 | 253 | { |
wray2303 | 2:8d28a2f491eb | 254 | if(shootSoundtimer.read() > 0.1) { /// check when the sound timer reaches 0.1 sec |
wray2303 | 0:6eba0e66ce01 | 255 | shootSoundtimer.stop(); /// stop the timer |
wray2303 | 0:6eba0e66ce01 | 256 | shootSoundtimer.reset(); /// reset the timer |
wray2303 | 0:6eba0e66ce01 | 257 | PWM1 = 0.0; /// turn of the PWM |
wray2303 | 0:6eba0e66ce01 | 258 | } else {} |
wray2303 | 0:6eba0e66ce01 | 259 | |
wray2303 | 0:6eba0e66ce01 | 260 | if(button) { |
wray2303 | 0:6eba0e66ce01 | 261 | AsteroidCreatedFlag = 0; |
wray2303 | 0:6eba0e66ce01 | 262 | GenAsteroidFlag = 0; |
wray2303 | 0:6eba0e66ce01 | 263 | asteroid.destroyAsteroid(); |
wray2303 | 0:6eba0e66ce01 | 264 | readTheAsteroid.detach(); |
wray2303 | 0:6eba0e66ce01 | 265 | PWM1 = 0; |
wray2303 | 0:6eba0e66ce01 | 266 | state = 2; |
wray2303 | 0:6eba0e66ce01 | 267 | |
wray2303 | 0:6eba0e66ce01 | 268 | } else {} |
wray2303 | 0:6eba0e66ce01 | 269 | bullet.collision(); /// check if the bullet has collided with anything |
wray2303 | 0:6eba0e66ce01 | 270 | bullet.offScreen(); /// check if the bullet is off screen |
wray2303 | 0:6eba0e66ce01 | 271 | if (bullet.collision() == true||bullet.offScreen()==true) { /// if a collision is made or the bullet goes off the screen |
wray2303 | 0:6eba0e66ce01 | 272 | BulletExistsFlag=0; |
wray2303 | 0:6eba0e66ce01 | 273 | bullet.clearBullet(); /// clear the bullet |
wray2303 | 0:6eba0e66ce01 | 274 | readShoot.detach(); /// detach the ticker |
wray2303 | 0:6eba0e66ce01 | 275 | |
wray2303 | 0:6eba0e66ce01 | 276 | /** if bullet colision happens during sound being made then |
wray2303 | 0:6eba0e66ce01 | 277 | buzzer doesnt stop, thisis because of the interrupt the button makes |
wray2303 | 0:6eba0e66ce01 | 278 | here we reset the buzzer manually*/ |
wray2303 | 0:6eba0e66ce01 | 279 | shootSoundtimer.stop(); /// stop the timer |
wray2303 | 0:6eba0e66ce01 | 280 | shootSoundtimer.reset(); /// reset the timer |
wray2303 | 0:6eba0e66ce01 | 281 | PWM1 = 0.0; /// turn of the PWM |
wray2303 | 0:6eba0e66ce01 | 282 | } else {} |
wray2303 | 0:6eba0e66ce01 | 283 | |
wray2303 | 0:6eba0e66ce01 | 284 | bullet.y=bullet.y-1; /// move the bullet up i.e. move its y coordinate |
wray2303 | 0:6eba0e66ce01 | 285 | bullet.createBullet(); /// draw new bullet |
wray2303 | 0:6eba0e66ce01 | 286 | bullet.erasePrevBullet(); /// erase previous position |
wray2303 | 0:6eba0e66ce01 | 287 | |
wray2303 | 0:6eba0e66ce01 | 288 | ////////// double check this seems to help rid some bugs //////////// |
wray2303 | 0:6eba0e66ce01 | 289 | bullet.offScreen(); /// check if the bullet is off screen |
wray2303 | 0:6eba0e66ce01 | 290 | bullet.collision(); /// check if the bullet has collided with anything |
wray2303 | 0:6eba0e66ce01 | 291 | if (bullet.collision() == true||bullet.offScreen()==true) { /// if a collision is made or the bullet goes off the screen |
wray2303 | 0:6eba0e66ce01 | 292 | BulletExistsFlag=0; |
wray2303 | 0:6eba0e66ce01 | 293 | bullet.clearBullet(); /// clear the bullet |
wray2303 | 0:6eba0e66ce01 | 294 | readShoot.detach(); /// detach the ticker |
wray2303 | 0:6eba0e66ce01 | 295 | } else {} |
wray2303 | 0:6eba0e66ce01 | 296 | |
wray2303 | 0:6eba0e66ce01 | 297 | if (printFlag) { /// here we are checking the position of the joystick, so the user can move while the bullet is shooting else where |
wray2303 | 0:6eba0e66ce01 | 298 | printFlag = 0; |
wray2303 | 0:6eba0e66ce01 | 299 | if (joystick.direction == LEFT && ship.xs>=7) { |
wray2303 | 0:6eba0e66ce01 | 300 | ship.ShipLeft(); |
wray2303 | 0:6eba0e66ce01 | 301 | } |
wray2303 | 0:6eba0e66ce01 | 302 | if (joystick.direction == RIGHT && ship.xs<=76) { |
wray2303 | 0:6eba0e66ce01 | 303 | ship.ShipRight(); |
wray2303 | 0:6eba0e66ce01 | 304 | } else {} |
wray2303 | 0:6eba0e66ce01 | 305 | } |
wray2303 | 0:6eba0e66ce01 | 306 | } |
wray2303 | 0:6eba0e66ce01 | 307 | |
wray2303 | 2:8d28a2f491eb | 308 | |
wray2303 | 0:6eba0e66ce01 | 309 | void EndDisplay() |
wray2303 | 0:6eba0e66ce01 | 310 | { |
wray2303 | 0:6eba0e66ce01 | 311 | lcd.clear(); /// clear entire display to make way for end screen |
wray2303 | 0:6eba0e66ce01 | 312 | asteroid.nscore = asteroid.nscore-PauseNumber; /// takes points off for the asteroid destroyed when pausing game and destroy asteroid command sent |
wray2303 | 3:39c95d65bee5 | 313 | asteroid.nscore = asteroid.nscore-1; |
wray2303 | 0:6eba0e66ce01 | 314 | char buffer[14]; /// set buffer to 14, screen 84 pixels long , 6 pixel per char , 84/6 = 14 |
wray2303 | 0:6eba0e66ce01 | 315 | int score = sprintf(buffer,"Score: %d",asteroid.nscore); /// print formatted data to buffer |
wray2303 | 0:6eba0e66ce01 | 316 | if (score <= 14) { /// if string will fit on display |
wray2303 | 2:8d28a2f491eb | 317 | lcd.printString(buffer,20,5); /// display on screen |
wray2303 | 0:6eba0e66ce01 | 318 | } |
wray2303 | 0:6eba0e66ce01 | 319 | |
wray2303 | 2:8d28a2f491eb | 320 | Read(); /// read file to compare values |
wray2303 | 2:8d28a2f491eb | 321 | if(asteroid.nscore>HighScore) { /// compare current score against highscore |
wray2303 | 2:8d28a2f491eb | 322 | HighScore = asteroid.nscore; /// if current score is larger than highscore = current score |
wray2303 | 2:8d28a2f491eb | 323 | Write(); /// write this to file |
wray2303 | 2:8d28a2f491eb | 324 | } |
wray2303 | 2:8d28a2f491eb | 325 | Read(); /// read the file to then print to lcd |
wray2303 | 2:8d28a2f491eb | 326 | char buffer1[14]; /// set buffer to 14, screen 84 pixels long , 6 pixel per char , 84/6 = 14 |
wray2303 | 2:8d28a2f491eb | 327 | int Hscore = sprintf(buffer1,"HighScore:%d",HighScore); /// print formatted data to buffer |
wray2303 | 0:6eba0e66ce01 | 328 | |
wray2303 | 2:8d28a2f491eb | 329 | if (Hscore <= 14) { /// if string will fit on display |
wray2303 | 2:8d28a2f491eb | 330 | lcd.printString(buffer1,7,4); /// display on screen |
wray2303 | 2:8d28a2f491eb | 331 | } |
wray2303 | 2:8d28a2f491eb | 332 | lcd.printString("game over !",12,0); /// closing message |
wray2303 | 3:39c95d65bee5 | 333 | lcd.printString("Press S5 to",10,1); |
wray2303 | 2:8d28a2f491eb | 334 | lcd.printString("Play again",12,2); |
wray2303 | 0:6eba0e66ce01 | 335 | lcd.drawLine(0,0,0,47,1); /// draw outline |
wray2303 | 0:6eba0e66ce01 | 336 | lcd.drawLine(83,0,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 337 | lcd.drawLine(0,0,83,0,1); |
wray2303 | 0:6eba0e66ce01 | 338 | lcd.drawLine(0,47,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 339 | lcd.refresh(); /// refesh LCD to create this display |
wray2303 | 0:6eba0e66ce01 | 340 | |
wray2303 | 3:39c95d65bee5 | 341 | while(!buttonP) { /// while button b has not been pressed sleep (save power) |
wray2303 | 0:6eba0e66ce01 | 342 | Sleep(); |
wray2303 | 0:6eba0e66ce01 | 343 | } |
wray2303 | 0:6eba0e66ce01 | 344 | /// when button s pressed |
wray2303 | 0:6eba0e66ce01 | 345 | state = 0; /// set the state to 0 (intital game display |
wray2303 | 0:6eba0e66ce01 | 346 | asteroid.nscore=0; /// reset the score |
wray2303 | 0:6eba0e66ce01 | 347 | } |
wray2303 | 0:6eba0e66ce01 | 348 | |
wray2303 | 2:8d28a2f491eb | 349 | |
wray2303 | 0:6eba0e66ce01 | 350 | void PauseDisplay() |
wray2303 | 0:6eba0e66ce01 | 351 | { |
wray2303 | 0:6eba0e66ce01 | 352 | lcd.printString("PAUSE",28,1); /// print pause display message |
wray2303 | 0:6eba0e66ce01 | 353 | lcd.printString("press S5 to",11,3); |
wray2303 | 0:6eba0e66ce01 | 354 | lcd.printString("resume",24,4); |
wray2303 | 0:6eba0e66ce01 | 355 | lcd.drawLine(0,0,0,47,1); /// draw outline |
wray2303 | 0:6eba0e66ce01 | 356 | lcd.drawLine(83,0,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 357 | lcd.drawLine(0,0,83,0,1); |
wray2303 | 0:6eba0e66ce01 | 358 | lcd.drawLine(0,47,83,47,1); |
wray2303 | 0:6eba0e66ce01 | 359 | lcd.refresh(); |
wray2303 | 0:6eba0e66ce01 | 360 | while(!buttonP) { /// while button P is not pressed Sleep() to save power |
wray2303 | 0:6eba0e66ce01 | 361 | Sleep(); |
wray2303 | 0:6eba0e66ce01 | 362 | if(buttonP) { /// if button P is pressed |
wray2303 | 0:6eba0e66ce01 | 363 | lcd.clear(); /// clear LCD |
wray2303 | 0:6eba0e66ce01 | 364 | ship.shape(); /// draw the ship back on in position it was left |
wray2303 | 0:6eba0e66ce01 | 365 | GenAsteroidFlag = 1; /// reset the Generate asteroid flag |
wray2303 | 0:6eba0e66ce01 | 366 | PauseNumber = PauseNumber+1; /// increment pause amount counter |
wray2303 | 0:6eba0e66ce01 | 367 | state=1; /// state = 1 means back to the game in the switch statement |
wray2303 | 0:6eba0e66ce01 | 368 | } |
wray2303 | 0:6eba0e66ce01 | 369 | } |
wray2303 | 0:6eba0e66ce01 | 370 | } |
wray2303 | 0:6eba0e66ce01 | 371 | |
wray2303 | 3:39c95d65bee5 | 372 | void endState() |
wray2303 | 3:39c95d65bee5 | 373 | { |
wray2303 | 3:39c95d65bee5 | 374 | state = 3; |
wray2303 | 3:39c95d65bee5 | 375 | } |
wray2303 | 3:39c95d65bee5 | 376 | |
wray2303 | 2:8d28a2f491eb | 377 | |
wray2303 | 0:6eba0e66ce01 | 378 | void calibrateJoystick() |
wray2303 | 0:6eba0e66ce01 | 379 | { |
wray2303 | 0:6eba0e66ce01 | 380 | button.mode(PullDown); |
wray2303 | 0:6eba0e66ce01 | 381 | /// must not move during calibration |
wray2303 | 0:6eba0e66ce01 | 382 | joystick.x0 = xPot; /// initial positions in the range 0.0 to 1.0 (0.5 if centred exactly) |
wray2303 | 0:6eba0e66ce01 | 383 | joystick.y0 = yPot; |
wray2303 | 0:6eba0e66ce01 | 384 | } |
wray2303 | 0:6eba0e66ce01 | 385 | |
wray2303 | 2:8d28a2f491eb | 386 | |
wray2303 | 0:6eba0e66ce01 | 387 | void updateJoystick() |
wray2303 | 0:6eba0e66ce01 | 388 | { |
wray2303 | 0:6eba0e66ce01 | 389 | /// reading the joystick position 0.0 is centered returns a value in the range -0.5 and 0.5 |
wray2303 | 0:6eba0e66ce01 | 390 | joystick.x = xPot - joystick.x0; |
wray2303 | 0:6eba0e66ce01 | 391 | joystick.y = yPot - joystick.y0; |
wray2303 | 0:6eba0e66ce01 | 392 | /// read button state |
wray2303 | 0:6eba0e66ce01 | 393 | joystick.button = button; |
wray2303 | 0:6eba0e66ce01 | 394 | |
wray2303 | 0:6eba0e66ce01 | 395 | /// calculate direction depending on x,y values |
wray2303 | 0:6eba0e66ce01 | 396 | /// tolerance allows a little lee-way in case joystick not exactly in the stated direction |
wray2303 | 0:6eba0e66ce01 | 397 | if ( fabs(joystick.y) < DIRECTION_TOLERANCE && fabs(joystick.x) < DIRECTION_TOLERANCE) { |
wray2303 | 0:6eba0e66ce01 | 398 | joystick.direction = CENTRE; |
wray2303 | 0:6eba0e66ce01 | 399 | } else if ( joystick.y > DIRECTION_TOLERANCE && fabs(joystick.x) < DIRECTION_TOLERANCE) { |
wray2303 | 0:6eba0e66ce01 | 400 | joystick.direction = UP; |
wray2303 | 0:6eba0e66ce01 | 401 | } else if ( joystick.y < DIRECTION_TOLERANCE && fabs(joystick.x) < DIRECTION_TOLERANCE) { |
wray2303 | 0:6eba0e66ce01 | 402 | joystick.direction = DOWN; |
wray2303 | 0:6eba0e66ce01 | 403 | } else if ( joystick.x > DIRECTION_TOLERANCE && fabs(joystick.y) < DIRECTION_TOLERANCE) { |
wray2303 | 0:6eba0e66ce01 | 404 | joystick.direction = RIGHT; |
wray2303 | 0:6eba0e66ce01 | 405 | } else if ( joystick.x < DIRECTION_TOLERANCE && fabs(joystick.y) < DIRECTION_TOLERANCE) { |
wray2303 | 0:6eba0e66ce01 | 406 | joystick.direction = LEFT; |
wray2303 | 0:6eba0e66ce01 | 407 | } else { |
wray2303 | 0:6eba0e66ce01 | 408 | joystick.direction = UNKNOWN; |
wray2303 | 0:6eba0e66ce01 | 409 | } |
wray2303 | 0:6eba0e66ce01 | 410 | /// set flag for use of the joystick position |
wray2303 | 0:6eba0e66ce01 | 411 | printFlag = 1; |
wray2303 | 0:6eba0e66ce01 | 412 | } |