h

Dependencies:   mbed 4DGL-uLCD-SE PinDetect

main.cpp

Committer:
cdong49
Date:
2019-10-21
Revision:
0:5b7c2ab43c28

File content as of revision 0:5b7c2ab43c28:

#include "uLCD_4DGL.h"
#include "PinDetect.h"
#include "mbed.h"
#include <ctime>    // For time()
#include <cstdlib>  // For srand() and rand()
#include "Speaker.h"
uLCD_4DGL uLCD(p9, p10, p11);

PinDetect pbLeft(p21); //left
PinDetect pbRight(p22); //right
PinDetect pbExit(p23); //Exit
Speaker mySpeaker(p24);

int lemur_game();
void print_result_screen(bool left, int delay);
void print_exit_screen();
int check_value_in_random_array(int &val);
void clear_random_array();
void generate_shape(int box, int shape);
void start_up_hello();
void clear_screen(); 
void print_two_white_rect();
void print_random_circle(int x1, int y1, int x2, int y2);
void print_random_triangle(int x1, int y1, int x2, int y2);
void print_random_square(int x1, int y1, int x2, int y2);
void pick_spot(int box, int index, int* result);

int arr[4]; // store x1, y1, x2, y2
int rand0 = 0; // number of random objects in left box
int rand1 = 0; // the number of random objects in right box
int random_check_array[15] = {};
int random_check_value = 0;
int trial_number = 1;
int correct_trial_number = 0;


int main() {
    start_up_hello();
    pbLeft.mode(PullUp);
    pbRight.mode(PullUp);
    pbExit.mode(PullUp);
    wait_ms(1000);
    print_two_white_rect(); // init the 2 rectangular box
    srand(time(0));
    lemur_game(); // start trial!
}

int lemur_game() {
    while(1) {
        Timer t = Timer();
        int shape = rand()%3;
        generate_shape(0, shape);
        generate_shape(1, shape);
        t.start();
        bool done = false;
        int left = 0;
        while(!done) {
            if(!pbLeft) {
                t.stop();
                done = true;
                left = true;
                wait_ms(1000);
            }
            if(!pbRight) {
                t.stop();
                done = true;
                left = false;
                wait_ms(1000);
            }
            if(!pbExit) {
                print_exit_screen();
                return 1;
            }   
        } 
        
        print_result_screen(left, t.read_ms());
        t.reset();
        clear_screen(); 
    }    
}

void print_result_screen(bool left, int delay) { // print result screen after each trial
    if((left && rand0 < rand1) || (!left && rand1 < rand0)) { // check if the button hit was right or not
        correct_trial_number++; // if its right, execute the correct code
        uLCD.cls();
        uLCD.textbackground_color(0x000000);
        uLCD.color(GREEN);
        uLCD.text_bold(TEXTBOLD);
        uLCD.text_height(1.5);
        uLCD.text_width(1.5);
        uLCD.locate(6, 4);
        uLCD.printf("Trial %d\n", trial_number);
        uLCD.locate(2, 6);
        uLCD.printf("You are correct!\n");
        uLCD.locate(4,8);
        uLCD.printf("time: %dms\n", delay);
        uLCD.locate(1, 10);
        uLCD.printf("fraction correct:\n");
        uLCD.locate(6, 12);
        uLCD.printf("%.2f%%\n", (((float)correct_trial_number)/trial_number)*100.0);
        wait_ms(2000); //wait 2s
        uLCD.cls();
    } else {   
        uLCD.cls(); // execute the incorrect code
        uLCD.textbackground_color(0x000000);
        uLCD.color(GREEN);
        uLCD.text_bold(TEXTBOLD);
        uLCD.text_height(1.5);
        uLCD.text_width(1.5);
        uLCD.locate(6, 4);
        uLCD.printf("Trial %d\n", trial_number);
        uLCD.locate(1, 6);
        uLCD.printf("You are incorrect\n");
        uLCD.locate(4,8);
        uLCD.printf("time: %dms\n", delay);
        uLCD.locate(1, 10);
        uLCD.printf("fraction correct:\n");
        uLCD.locate(6, 12);
        uLCD.printf("%.2f%%\n", (((float)correct_trial_number)/trial_number)*100.0);
        wait_ms(2000); //wait 2s
        uLCD.cls();
    }
    trial_number++; // increment trial_number
}
void print_exit_screen() { // print exit screen when exit button is hit
    uLCD.cls();
    uLCD.textbackground_color(0x000000);
    uLCD.color(GREEN);
    uLCD.text_bold(TEXTBOLD);
    uLCD.text_height(1.5);
    uLCD.text_width(1.5);
    uLCD.locate(4, 4);
    uLCD.printf("Trial Done!\n");
    uLCD.locate(2, 7);
    uLCD.printf("You've been an\n");
    uLCD.locate(3, 10);
    uLCD.printf("Awesome lemur\n");
    wait_ms(2000); //wait 2s
    uLCD.cls();
}

int check_value_in_random_array(int &val) { // return -1 if not found. This takes in a value and we compare it with every value in our random_check_array
    for(int i = 0; i < sizeof(random_check_array)/sizeof(int); i++) { // if our current random_check_array does not contain any value equals to val, return -1
        if(random_check_array[i] == val) { // else return 1
            return 1;    
        }    
    }    
    return -1;
}
void clear_random_array() { // reset random array and random_check_value
    for(int i = 0; i < sizeof(random_check_array)/sizeof(int); i++) {
        random_check_array[i] = -1;
    }      
    random_check_value = 0;
}
void generate_shape(int box, int shape) { // This method will generate the shapes in a specific box, box = 0 -> left box, box = 1 -> right box. shape = 0 -> circle
    int pos; // shape = 1 -> triangle, shape = 2 -> square
    if(box == 0) { // left box
        do {
            rand0 = rand()%15 + 1;    
        } while(rand0 == rand1); // randomly get the number of shape for this box and make sure it is not the same number as the other box
        for(int i = 0; i < rand0;i++) { // loop from 0 to that number-1 to generate shapes
            pos = rand()%18;  // pos will check to make sure all shapes are uniquely placed and no shape is overwritten by any other shape
            while(check_value_in_random_array(pos) == 1) {
                pos = rand()%18;        
            }
            
            random_check_array[random_check_value] = pos; // push pos onto the random_check_value array to keep checking
            random_check_value++;
            pick_spot(box, pos, arr); // call pick_spot to assign values to arr element. arr[0] stores x1, arr[1] stores y1, arr[2] stores x2, arr[3] stores y3
            if(shape == 0) { // generate the shape based on our random input
                print_random_circle(arr[0], arr[1], arr[2], arr[3]);
            } else if(shape == 1) {
                print_random_triangle(arr[0], arr[1], arr[2], arr[3]);
            } else if(shape == 2) {
                print_random_square(arr[0], arr[1], arr[2], arr[3]);
            }
        }
        clear_random_array(); // clear to reset random_check_array
    } else if(box == 1) { // do the same thing but with box 1
        do {
            rand1 = rand()%15 + 1;    
        } while(rand0 == rand1);
        for(int i = 0; i < rand1;i++) {
             pos = rand()%18;
            while(check_value_in_random_array(pos) == 1) {
                pos = rand()%18;        
            }
            random_check_array[random_check_value] = pos;
            random_check_value++;
            pick_spot(box, pos, arr);
            if(shape == 0) {
                print_random_circle(arr[0], arr[1], arr[2], arr[3]);
            } else if(shape == 1) {
                print_random_triangle(arr[0], arr[1], arr[2], arr[3]);
            } else if(shape == 2) {
                print_random_square(arr[0], arr[1], arr[2], arr[3]);
            }
        }
        clear_random_array();
    }
}
void start_up_hello() { // 1.1, print the startup screen and play some music
    uLCD.textbackground_color(0x000000);
    uLCD.color(GREEN);
    uLCD.text_bold(TEXTBOLD);
    uLCD.text_height(1.5);
    uLCD.text_width(1.5);
    uLCD.locate(4, 4);
    uLCD.printf("Welcome to\n");
    uLCD.locate(2, 7);
    uLCD.printf("Peter's Awesome\n");
    uLCD.locate(3, 10);
    uLCD.printf("Lemur Party\n");
    wait_ms(5000);
    mySpeaker.PlayNote(400, 0.5, 0.5);
    mySpeaker.PlayNote(400, 0.5, 0.5);
    mySpeaker.PlayNote(450, 0.8, 0.5);
    mySpeaker.PlayNote(400, 0.8, 0.5);
    mySpeaker.PlayNote(540, 0.8, 0.5);
    mySpeaker.PlayNote(500, 0.8, 0.5);
    
    wait_ms(2000); //wait 2s
    uLCD.cls();
}   
void clear_screen() { // clear the trial screen, leaving two empty white boxes
    uLCD.cls(); 
    print_two_white_rect();
    wait_ms(200);     
}
void print_two_white_rect() { // print the empty white boxes
    uLCD.filled_rectangle(0, 0, 62, 1, 0xFFFFFF);   // I was a dumbass here I should've called rectangle 2 times instead of doing a bunch of small filled_rectangle lmao
    uLCD.filled_rectangle(64,0, 126, 1, 0xFFFFFF);  // I'm too lazy to fix this to make it cleaner so bear with me! :D
    
    uLCD.filled_rectangle(0, 0, 1, 122, 0xFFFFFF);
    uLCD.filled_rectangle(61, 0, 62, 122, 0xFFFFFF);
    uLCD.filled_rectangle(64, 0, 65, 122, 0xFFFFFF);
    uLCD.filled_rectangle(125, 0, 126, 122, 0xFFFFFF);
    
    uLCD.filled_rectangle(0, 121, 62, 122, 0xFFFFFF);
    uLCD.filled_rectangle(64, 121, 126, 122, 0xFFFFFF);
}

void print_random_circle(int x1, int y1, int x2, int y2) { // print a circle at the specific position given with a random radius
    uLCD.filled_circle((x2 + x1)/2.0 , (y2 + y1)/2.0 , (rand() % ((21-1)/2)), RED); 
}

void print_random_triangle(int x1, int y1, int x2, int y2) { // print a triangle at the specific position
    uLCD.triangle((x2+x1)/2.0, y1, x1, y2, x2, y2, RED);  
}

void print_random_square(int x1, int y1, int x2, int y2) { // print a square at a specific position
    uLCD.filled_rectangle(x1+2, y1+2, x2-2, y2-2, RED);   
}

void pick_spot(int box, int index, int* result) { // box = 0 -> left box, box = 1 -> right box. index goes from 0-17, left to right, up to down representing the square spaces inside a box
    if(box == 0) { // we would pass our arr into result to get specific x,y coordinate out
        switch(index) {
            case 0:
                result[0] = 1;
                result[1] = 1;
                result[2] = 20;
                result[3] = 20;
                break;
            case 1:
                result[0] = 21;
                result[1] = 1;
                result[2] = 40;
                result[3] = 20;
                break;
            case 2:
                result[0] = 41;
                result[1] = 1;
                result[2] = 60;
                result[3] = 20;
                break;
            case 3:
                result[0] = 1;
                
                result[1] = 21;
                result[2] = 20;
                result[3] = 40;
                break;
            case 4:
                result[0] = 21;
                result[1] = 21;
                result[2] = 40;
                result[3] = 40;  
                break;
            case 5:
                result[0] = 41;
                result[1] = 21;
                result[2] = 60;
                result[3] = 40;  
                break;
            case 6:
                result[0] = 1;
                result[1] = 41;
                result[2] = 20;
                result[3] = 60;
                break;
            case 7:
                result[0] = 21;
                result[1] = 41;
                result[2] = 40;
                result[3] = 60;
                break;
            case 8:
                result[0] = 41;
                result[1] = 41;
                result[2] = 60;
                result[3] = 60;
                break;
            case 9:
                result[0] = 1;
                result[1] = 61;
                result[2] = 20;
                result[3] = 80;
                break;
            case 10:
                result[0] = 21;
                result[1] = 61;
                result[2] = 40;
                result[3] = 80;
                break;
            case 11:
                result[0] = 41;
                result[1] = 61;
                result[2] = 60;
                result[3] = 80;
                break;
            case 12:
                result[0] = 1;
                result[1] = 81;
                result[2] = 20;
                result[3] = 100;
                break;
            case 13:
                result[0] = 21;
                result[1] = 81;
                result[2] = 40;
                result[3] = 100;
                break;
            case 14:
                result[0] = 41;
                result[1] = 81;
                result[2] = 60;
                result[3] = 100;
                break;
            case 15:
                result[0] = 1;
                result[1] = 101;
                result[2] = 20;
                result[3] = 120;
                break;
            case 16:
                result[0] = 21;
                result[1] = 101;
                result[2] = 40;
                result[3] = 120;
                break;
            case 17:
                result[0] = 41;
                result[1] = 101;
                result[2] = 60;
                result[3] = 120;
                break;
        }
        
    } else if(box == 1) {
        switch(index) {
            case 0:
                result[0] = 65;
                result[1] = 1;
                result[2] = 84;
                result[3] = 20;
                break;
            case 1:
                result[0] = 85;
                result[1] = 1;
                result[2] = 104;
                result[3] = 20;
                break;
            case 2:
                result[0] = 105;
                result[1] = 1;
                result[2] = 124;
                result[3] = 20;
                break;
            case 3:
                result[0] = 65;
                result[1] = 21;
                result[2] = 84;
                result[3] = 40;
                break;
            case 4:
                result[0] = 85;
                result[1] = 21;
                result[2] = 104;
                result[3] = 40;  
                break;
            case 5:
                result[0] = 105;
                result[1] = 21;
                result[2] = 124;
                result[3] = 40;  
                break;
            case 6:
                result[0] = 65;
                result[1] = 41;
                result[2] = 84;
                result[3] = 60;
                break;
            case 7:
                result[0] = 85;
                result[1] = 41;
                result[2] = 104;
                result[3] = 60;
                break;
            case 8:
                result[0] = 105;
                result[1] = 41;
                result[2] = 125;
                result[3] = 60;
                break;
            case 9:
                result[0] = 65;
                result[1] = 61;
                result[2] = 84;
                result[3] = 80;
                break;
            case 10:
                result[0] = 85;
                result[1] = 61;
                result[2] = 104;
                result[3] = 80;
                break;
            case 11:
                result[0] = 105;
                result[1] = 61;
                result[2] = 124;
                result[3] = 80;
                break;
            case 12:
                result[0] = 65;
                result[1] = 81;
                result[2] = 84;
                result[3] = 100;
                break;
            case 13:
                result[0] = 85;
                result[1] = 81;
                result[2] = 104;
                result[3] = 100;
                break;
            case 14:
                result[0] = 105;
                result[1] = 81;
                result[2] = 124;
                result[3] = 100;
                break;
            case 15:
                result[0] = 65;
                result[1] = 101;
                result[2] = 84;
                result[3] = 120;
                break;
            case 16:
                result[0] = 85;
                result[1] = 101;
                result[2] = 104;
                result[3] = 120;
                break;
            case 17:
                result[0] = 105;
                result[1] = 101;
                result[2] = 124;
                result[3] = 120;
                break;
        }
    }
}