single player mbedKart

Dependencies:   Motor

(notes)

Committer:
DerekW2015
Date:
Tue Dec 11 02:32:50 2018 +0000
Revision:
21:f8f6c1f5743c
Parent:
18:6c93ec600402
Child:
23:b0fe1c1046dc
Added pan and channel configuration

Who changed what in which revision?

UserRevisionLine numberNew contents of line
DerekW2015 0:a9a4c0fd5f8a 1 #include "mbed.h"
DerekW2015 0:a9a4c0fd5f8a 2 #include "Motor.h"
DerekW2015 0:a9a4c0fd5f8a 3 #include "rgbled.h"
DerekW2015 0:a9a4c0fd5f8a 4 #include "rgbSensor.h"
DerekW2015 16:40f697a68445 5 #include "xbee_functions.h"
DerekW2015 21:f8f6c1f5743c 6 #include "universal.h"
DerekW2015 11:8d4b7702ac06 7 // Define threads and mutexes
DerekW2015 11:8d4b7702ac06 8 Thread thread1;
DerekW2015 11:8d4b7702ac06 9 Thread thread2;
DerekW2015 11:8d4b7702ac06 10
DerekW2015 0:a9a4c0fd5f8a 11 // Global game actions
DerekW2015 8:92bf0cc337b5 12 bool paused = false;
DerekW2015 8:92bf0cc337b5 13 void check_unpause() {
DerekW2015 8:92bf0cc337b5 14 char bnum=0;
DerekW2015 8:92bf0cc337b5 15 char bhit=0;
DerekW2015 8:92bf0cc337b5 16 while (true) {
DerekW2015 8:92bf0cc337b5 17 if (blue.getc()=='B') { //button data packet
DerekW2015 8:92bf0cc337b5 18 bnum = blue.getc(); //button number
DerekW2015 8:92bf0cc337b5 19 bhit = blue.getc(); //1=hit, 0=release
DerekW2015 8:92bf0cc337b5 20 if (blue.getc()==char(~('!' + 'B' + bnum + bhit))) { //checksum OK?
DerekW2015 8:92bf0cc337b5 21 if (bnum == '1') { //number button 1, pause
DerekW2015 8:92bf0cc337b5 22 if (bhit=='1') paused = false;
DerekW2015 8:92bf0cc337b5 23 }
DerekW2015 8:92bf0cc337b5 24 }
DerekW2015 8:92bf0cc337b5 25 }
DerekW2015 8:92bf0cc337b5 26 }
DerekW2015 8:92bf0cc337b5 27 }
sli425 12:4fec6ed886ab 28
DerekW2015 8:92bf0cc337b5 29 void game_paused() {
DerekW2015 8:92bf0cc337b5 30 // Cycle through LEDs
DerekW2015 8:92bf0cc337b5 31 Thread pause_thread;
DerekW2015 8:92bf0cc337b5 32 pause_thread.start(check_unpause);
DerekW2015 8:92bf0cc337b5 33 while (paused) {
DerekW2015 8:92bf0cc337b5 34 int num = 1;
DerekW2015 8:92bf0cc337b5 35 for (int i = 0; i < 3; i++) {
DerekW2015 8:92bf0cc337b5 36 num *= 2;
DerekW2015 8:92bf0cc337b5 37 myled = num;
DerekW2015 8:92bf0cc337b5 38 ThisThread::sleep_for(100);
DerekW2015 8:92bf0cc337b5 39 }
DerekW2015 8:92bf0cc337b5 40 ThisThread::sleep_for(500);
DerekW2015 8:92bf0cc337b5 41 for (int i = 3; i > 0; i--) {
DerekW2015 8:92bf0cc337b5 42 num /= 2;
DerekW2015 8:92bf0cc337b5 43 myled = num;
DerekW2015 8:92bf0cc337b5 44 ThisThread::sleep_for(100);
DerekW2015 8:92bf0cc337b5 45 }
DerekW2015 8:92bf0cc337b5 46 ThisThread::sleep_for(500);
DerekW2015 8:92bf0cc337b5 47 }
DerekW2015 11:8d4b7702ac06 48 }
DerekW2015 11:8d4b7702ac06 49
DerekW2015 11:8d4b7702ac06 50 // Thread to control speed
DerekW2015 11:8d4b7702ac06 51 void speed_control() {
DerekW2015 11:8d4b7702ac06 52 // The kart has to be in one of three states at all times
DerekW2015 11:8d4b7702ac06 53 while(1) {
DerekW2015 11:8d4b7702ac06 54 while(sstate == coasting) {
DerekW2015 15:350b9128a602 55 if (speed_cmd > 0.0) speed_cmd -= coast_rate;
DerekW2015 15:350b9128a602 56 else speed_cmd = 0.0;
DerekW2015 15:350b9128a602 57 left.speed(speed_cmd);
DerekW2015 15:350b9128a602 58 right.speed(speed_cmd);
DerekW2015 11:8d4b7702ac06 59 ThisThread::sleep_for(200);
DerekW2015 11:8d4b7702ac06 60 }
DerekW2015 11:8d4b7702ac06 61 while(sstate == accelerating) {
DerekW2015 15:350b9128a602 62 if (speed_cmd < max_speed) speed_cmd += acceleration_rate;
DerekW2015 15:350b9128a602 63 else speed_cmd = max_speed;
DerekW2015 15:350b9128a602 64 left.speed(speed_cmd);
DerekW2015 15:350b9128a602 65 right.speed(speed_cmd);
DerekW2015 11:8d4b7702ac06 66 ThisThread::sleep_for(200);
DerekW2015 11:8d4b7702ac06 67 }
DerekW2015 11:8d4b7702ac06 68 while(sstate == braking) {
DerekW2015 15:350b9128a602 69 if (speed_cmd > 0.0) speed_cmd -= brake_rate;
DerekW2015 15:350b9128a602 70 else speed_cmd = 0.0;
DerekW2015 15:350b9128a602 71 left.speed(speed_cmd);
DerekW2015 15:350b9128a602 72 right.speed(speed_cmd);
DerekW2015 11:8d4b7702ac06 73 ThisThread::sleep_for(200);
DerekW2015 11:8d4b7702ac06 74 }
DerekW2015 11:8d4b7702ac06 75 }
DerekW2015 11:8d4b7702ac06 76 }
DerekW2015 11:8d4b7702ac06 77
sli425 3:6c749bff51aa 78 // Thread for checking rgb sensor values and updating game variables
sli425 3:6c749bff51aa 79 // Change later depending on behavior of RGB sensor and colors used
sli425 3:6c749bff51aa 80 int thresh = 150; //change this depending on RGB values
sli425 3:6c749bff51aa 81 void check_RGB() {
sli425 12:4fec6ed886ab 82 while(true){
sli425 12:4fec6ed886ab 83 rgbsensor.update();
sli425 12:4fec6ed886ab 84 int C_value = rgbsensor.get_C();
sli425 12:4fec6ed886ab 85 int R_value = rgbsensor.get_R();
sli425 12:4fec6ed886ab 86 int G_value = rgbsensor.get_G();
sli425 12:4fec6ed886ab 87 int B_value = rgbsensor.get_B();
sli425 12:4fec6ed886ab 88 if(C_value > thresh && R_value > thresh && G_value > thresh && B_value > thresh && current_item == 0) { //Check for if cart runs over an item box
sli425 12:4fec6ed886ab 89 itembox = true;
sli425 12:4fec6ed886ab 90 cstate = 0;
sli425 12:4fec6ed886ab 91 }
sli425 12:4fec6ed886ab 92 else if(C_value > thresh && R_value > thresh && G_value > thresh && B_value > thresh) { //Check for if cart runs over a speed boost panel
sli425 12:4fec6ed886ab 93 max_speed = 1; //change this depending on speed up panel algs
sli425 12:4fec6ed886ab 94 cstate = 0;
sli425 12:4fec6ed886ab 95 }
sli425 12:4fec6ed886ab 96 else if(C_value > thresh && R_value > thresh && G_value > thresh && B_value > thresh) { //Check if cart collides with wall
sli425 12:4fec6ed886ab 97 collide = true;
sli425 12:4fec6ed886ab 98 }
sli425 12:4fec6ed886ab 99 else if(C_value > thresh && R_value > thresh && G_value > thresh && B_value > thresh) { //Check if cart reaches next checkpoint. cstate is set to 1 upon seeing first color of checkpoint
sli425 12:4fec6ed886ab 100 cstate = 1;
sli425 12:4fec6ed886ab 101 }
sli425 12:4fec6ed886ab 102 else if(C_value > thresh && R_value > thresh && G_value > thresh && B_value > thresh && cstate == 1) {
sli425 12:4fec6ed886ab 103 //Second part of checking if cart reaches next checkpoint. If the previous color was passed through previously, updates checkpoint progress
sli425 12:4fec6ed886ab 104 cstate = 0;
sli425 12:4fec6ed886ab 105 progress++;
sli425 12:4fec6ed886ab 106 }
sli425 12:4fec6ed886ab 107 else {
sli425 12:4fec6ed886ab 108 cstate = 0;
sli425 12:4fec6ed886ab 109 }
sli425 12:4fec6ed886ab 110 ThisThread::sleep_for(500);
sli425 3:6c749bff51aa 111 }
sli425 3:6c749bff51aa 112 }
sli425 3:6c749bff51aa 113
sli425 12:4fec6ed886ab 114 void set_item() {
sli425 12:4fec6ed886ab 115 while(true){
sli425 12:4fec6ed886ab 116 if(itembox && current_item == 0) {
sli425 12:4fec6ed886ab 117 //playsound
DerekW2015 18:6c93ec600402 118 for(int n = 0; n < 10; n++){ //flash the led to simulate slot machine effect
DerekW2015 18:6c93ec600402 119 myRGBled.write(1.0,0.0,0.0);
sli425 12:4fec6ed886ab 120 ThisThread::sleep_for(50);
DerekW2015 18:6c93ec600402 121 myRGBled.write(0.0,1.0,0.0);
sli425 12:4fec6ed886ab 122 ThisThread::sleep_for(50);
DerekW2015 18:6c93ec600402 123 myRGBled.write(0.0,0.0,1.0);
sli425 12:4fec6ed886ab 124 ThisThread::sleep_for(50);
DerekW2015 18:6c93ec600402 125 myRGBled.write(1.0,1.0,0.0);
sli425 12:4fec6ed886ab 126 ThisThread::sleep_for(50);
sli425 12:4fec6ed886ab 127 }
sli425 12:4fec6ed886ab 128 current_item = rand() % 4 + 1; //change this depending on items implemented and random item alg
DerekW2015 18:6c93ec600402 129 switch(current_item) {
DerekW2015 18:6c93ec600402 130 case 1 : //mushroom
DerekW2015 18:6c93ec600402 131 myRGBled.write(1.0,0.0,0.0);
DerekW2015 18:6c93ec600402 132 break;
DerekW2015 18:6c93ec600402 133 case 2 : //green shell
DerekW2015 18:6c93ec600402 134 myRGBled.write(0.0,1.0,0.0);
DerekW2015 18:6c93ec600402 135 break;
DerekW2015 18:6c93ec600402 136 case 3 : //blue shell
DerekW2015 18:6c93ec600402 137 myRGBled.write(0.0,0.0,1.0);
DerekW2015 18:6c93ec600402 138 break;
DerekW2015 18:6c93ec600402 139 case 4 : //banana
DerekW2015 18:6c93ec600402 140 myRGBled.write(1.0,1.0,0.0);
DerekW2015 18:6c93ec600402 141 break;
DerekW2015 18:6c93ec600402 142 default :
DerekW2015 18:6c93ec600402 143 break;
sli425 12:4fec6ed886ab 144 }
sli425 12:4fec6ed886ab 145 itembox = false;
sli425 12:4fec6ed886ab 146 }
sli425 12:4fec6ed886ab 147 ThisThread::sleep_for(500);
sli425 12:4fec6ed886ab 148 }
sli425 12:4fec6ed886ab 149 }
sli425 12:4fec6ed886ab 150
sli425 12:4fec6ed886ab 151 void hold_item() {
sli425 12:4fec6ed886ab 152 if(current_item == 0){
sli425 12:4fec6ed886ab 153 return;
sli425 12:4fec6ed886ab 154 }
sli425 12:4fec6ed886ab 155 if(current_item == 1){
sli425 12:4fec6ed886ab 156 max_speed = 1;
sli425 12:4fec6ed886ab 157 current_item = 0;
sli425 12:4fec6ed886ab 158 }
sli425 12:4fec6ed886ab 159 else{
sli425 12:4fec6ed886ab 160 holding_item = true;
sli425 12:4fec6ed886ab 161 }
sli425 12:4fec6ed886ab 162 return;
sli425 12:4fec6ed886ab 163 }
sli425 12:4fec6ed886ab 164
sli425 12:4fec6ed886ab 165 void release_item(){
sli425 12:4fec6ed886ab 166 holding_item = false;
sli425 12:4fec6ed886ab 167 if(current_item == 2){
sli425 12:4fec6ed886ab 168 //hit player in front
sli425 12:4fec6ed886ab 169 return;
sli425 12:4fec6ed886ab 170 }
sli425 12:4fec6ed886ab 171 if(current_item == 3){
sli425 12:4fec6ed886ab 172 //hit player in first
sli425 12:4fec6ed886ab 173 return;
sli425 12:4fec6ed886ab 174 }
sli425 12:4fec6ed886ab 175 if(current_item == 4){
sli425 12:4fec6ed886ab 176 //hit player behind
sli425 12:4fec6ed886ab 177 return;
sli425 12:4fec6ed886ab 178 }
sli425 12:4fec6ed886ab 179 }
sli425 12:4fec6ed886ab 180
DerekW2015 0:a9a4c0fd5f8a 181 int main() {
DerekW2015 0:a9a4c0fd5f8a 182 // Start threads
DerekW2015 9:6649141315be 183 thread1.start(check_RGB);
DerekW2015 11:8d4b7702ac06 184 thread2.start(speed_control); // Since we're stopped, this won't do anything
DerekW2015 16:40f697a68445 185
DerekW2015 16:40f697a68445 186 // Initialize Xbee and remote modules
sli425 13:583181de031e 187 xbee.register_receive_cb(&receive_cb);
DerekW2015 16:40f697a68445 188 RadioStatus const radioStatus = xbee.init();
DerekW2015 21:f8f6c1f5743c 189 xbee.set_panid(PANID);
DerekW2015 21:f8f6c1f5743c 190 xbee.set_channel(CHANNEL);
DerekW2015 18:6c93ec600402 191 const XBeeLib::RemoteXBee802 remoteDevice64b = RemoteXBee802(REMOTE_NODE_ADDR64);
DerekW2015 0:a9a4c0fd5f8a 192
DerekW2015 0:a9a4c0fd5f8a 193 // Bluetooth controller code
DerekW2015 0:a9a4c0fd5f8a 194 char bnum=0;
DerekW2015 0:a9a4c0fd5f8a 195 char bhit=0;
DerekW2015 0:a9a4c0fd5f8a 196 while(1) {
DerekW2015 0:a9a4c0fd5f8a 197 if (blue.getc()=='!') {
DerekW2015 0:a9a4c0fd5f8a 198 if (blue.getc()=='B') { //button data packet
DerekW2015 0:a9a4c0fd5f8a 199 bnum = blue.getc(); //button number
DerekW2015 0:a9a4c0fd5f8a 200 bhit = blue.getc(); //1=hit, 0=release
DerekW2015 0:a9a4c0fd5f8a 201 if (blue.getc()==char(~('!' + 'B' + bnum + bhit))) { //checksum OK?
DerekW2015 0:a9a4c0fd5f8a 202 switch (bnum) {
DerekW2015 0:a9a4c0fd5f8a 203 case '1': //number button 1, pause
DerekW2015 0:a9a4c0fd5f8a 204 if (bhit=='1') {
DerekW2015 0:a9a4c0fd5f8a 205 //myled = bnum - '0'; //current button number will appear on LEDs
DerekW2015 8:92bf0cc337b5 206 paused = true;
DerekW2015 8:92bf0cc337b5 207 game_paused();
DerekW2015 0:a9a4c0fd5f8a 208 }
DerekW2015 0:a9a4c0fd5f8a 209 break;
DerekW2015 0:a9a4c0fd5f8a 210 case '2': //number button 2, accelerate
DerekW2015 0:a9a4c0fd5f8a 211 if (bhit=='1') {
DerekW2015 11:8d4b7702ac06 212 sstate = accelerating;
DerekW2015 0:a9a4c0fd5f8a 213 } else {
DerekW2015 11:8d4b7702ac06 214 sstate = coasting;
DerekW2015 0:a9a4c0fd5f8a 215 }
DerekW2015 0:a9a4c0fd5f8a 216 break;
DerekW2015 0:a9a4c0fd5f8a 217 case '3': //number button 3
DerekW2015 0:a9a4c0fd5f8a 218 if (bhit=='1') {
sli425 12:4fec6ed886ab 219 hold_item(); //holds item to protect player from incoming hazards
DerekW2015 0:a9a4c0fd5f8a 220 } else {
sli425 12:4fec6ed886ab 221 release_item(); //release item to attack
DerekW2015 0:a9a4c0fd5f8a 222 }
DerekW2015 0:a9a4c0fd5f8a 223 break;
DerekW2015 0:a9a4c0fd5f8a 224 case '4': //number button 4, brakes
DerekW2015 0:a9a4c0fd5f8a 225 if (bhit=='1') {
DerekW2015 0:a9a4c0fd5f8a 226 //myled = bnum - '0'; //current button number will appear on LEDs
DerekW2015 11:8d4b7702ac06 227 sstate = braking;
DerekW2015 0:a9a4c0fd5f8a 228 } else {
DerekW2015 11:8d4b7702ac06 229 sstate = coasting;
DerekW2015 0:a9a4c0fd5f8a 230 }
DerekW2015 0:a9a4c0fd5f8a 231 break;
DerekW2015 0:a9a4c0fd5f8a 232 case '5': //button 5 up arrow
DerekW2015 0:a9a4c0fd5f8a 233 if (bhit=='1') {
DerekW2015 0:a9a4c0fd5f8a 234 //myled = bnum - '0'; //current button number will appear on LEDs
DerekW2015 0:a9a4c0fd5f8a 235 //throw_item();
DerekW2015 0:a9a4c0fd5f8a 236 //item_box();
DerekW2015 0:a9a4c0fd5f8a 237 } else {
DerekW2015 0:a9a4c0fd5f8a 238
DerekW2015 0:a9a4c0fd5f8a 239 }
DerekW2015 0:a9a4c0fd5f8a 240 break;
DerekW2015 0:a9a4c0fd5f8a 241 case '6': //button 6 down arrow
DerekW2015 0:a9a4c0fd5f8a 242 if (bhit=='1') {
DerekW2015 11:8d4b7702ac06 243 //myled = bnum - '0'; //current button number will appear on LEDs
DerekW2015 0:a9a4c0fd5f8a 244 left.speed(-1.0);
DerekW2015 0:a9a4c0fd5f8a 245 right.speed(-1.0);
DerekW2015 0:a9a4c0fd5f8a 246 } else {
DerekW2015 0:a9a4c0fd5f8a 247 left.speed(0.0);
DerekW2015 0:a9a4c0fd5f8a 248 right.speed(0.0);
DerekW2015 0:a9a4c0fd5f8a 249 }
DerekW2015 0:a9a4c0fd5f8a 250 break;
DerekW2015 0:a9a4c0fd5f8a 251 case '7': //button 7 left arrow
DerekW2015 0:a9a4c0fd5f8a 252 if (bhit=='1') {
DerekW2015 0:a9a4c0fd5f8a 253 //myled = bnum - '0'; //current button number will appear on LEDs
DerekW2015 0:a9a4c0fd5f8a 254 left.speed(0.3);
DerekW2015 0:a9a4c0fd5f8a 255 right.speed(1.0);
DerekW2015 0:a9a4c0fd5f8a 256 } else {
DerekW2015 0:a9a4c0fd5f8a 257 left.speed(0.0);
DerekW2015 0:a9a4c0fd5f8a 258 right.speed(0.0);
DerekW2015 0:a9a4c0fd5f8a 259 }
DerekW2015 0:a9a4c0fd5f8a 260 break;
DerekW2015 0:a9a4c0fd5f8a 261 case '8': //button 8 right arrow
DerekW2015 0:a9a4c0fd5f8a 262 if (bhit=='1') {
DerekW2015 0:a9a4c0fd5f8a 263 //myled = bnum - '0'; //current button number will appear on LEDs
DerekW2015 0:a9a4c0fd5f8a 264 left.speed(1.0);
DerekW2015 0:a9a4c0fd5f8a 265 right.speed(0.3);
DerekW2015 0:a9a4c0fd5f8a 266 } else {
DerekW2015 0:a9a4c0fd5f8a 267 left.speed(0.0);
DerekW2015 0:a9a4c0fd5f8a 268 right.speed(0.0);
DerekW2015 0:a9a4c0fd5f8a 269 }
DerekW2015 0:a9a4c0fd5f8a 270 break;
DerekW2015 0:a9a4c0fd5f8a 271 default:
DerekW2015 0:a9a4c0fd5f8a 272 break;
DerekW2015 0:a9a4c0fd5f8a 273 }
DerekW2015 0:a9a4c0fd5f8a 274 }
DerekW2015 0:a9a4c0fd5f8a 275 }
DerekW2015 0:a9a4c0fd5f8a 276 }
DerekW2015 16:40f697a68445 277 // Finish up loop
DerekW2015 16:40f697a68445 278 xbee.process_rx_frames();
DerekW2015 0:a9a4c0fd5f8a 279 }
DerekW2015 0:a9a4c0fd5f8a 280 }