Code for a robotic pet to interact with.

Dependencies:   mbed wave_player Servo Motordriver mbed-rtos 4DGL-uLCD-SE SDFileSystem_OldbutworkswithRTOS HC_SR04_Ultrasonic_Library

main.cpp

Committer:
jprocter3
Date:
2019-04-18
Revision:
9:8a5b623fff86
Parent:
8:ddddef6634cd
Child:
10:29a382784838

File content as of revision 9:8a5b623fff86:

#include "mbed.h"
#include "motordriver.h"
#include "rtos.h"
#include "uLCD_4DGL.h"
#include "mpr121.h"
#include "ultrasonic.h"
uLCD_4DGL uLCD(p28,p27,p29); // serial tx, serial rx, reset pin;
DigitalOut speaker(p18);
Motor m1(p23, p7, p8, 1); // pwm, fwd, rev
Motor m2(p24, p9, p10, 1); // pwm, fwd, rev
InterruptIn interrupt(p26);
I2C i2c(p13, p14);
Mpr121 mpr121(&i2c, Mpr121::ADD_VSS);

DigitalOut led1(LED1);
DigitalOut led2(LED2);
DigitalOut led3(LED3);
DigitalOut led4(LED4);

enum {ROAM, STOP, SLEEP};
volatile int state;

volatile int energy;
volatile bool touched;
volatile bool fed;

void dist(int distance)
{
    //control wheels
    if (state == ROAM) {
        if(distance < 250) {
            m1.stop(0);
            m2.stop(0);
            Thread::wait(100);
            m1.speed(.75);
            m2.speed(-.75);
            Thread::wait(500);
        } else {
            m1.speed(.5);
            m2.speed(.5);
        }    
    } else { // stop for STOP and SLEEP
        m1.stop(0);
        m2.stop(0);    
    }

    if (state == STOP && distance < 60) {
        //increase food status
        fed = true;
        Thread::wait(3000); // make sure fed state lasts atleast 3 seconds
        fed = false;
    }
}

ultrasonic mu(p6, p7, .1, 1, &dist);

void sonar(void const *argument) {
    while(1) {
        mu.checkDistance();
        Thread::wait(100);
    }
}

void touchpad(void const *argument) {
    while(1) {
        if (mpr121.read(0x00)) { // touchpad has any interaction
            touched = true;
            Thread::wait(5000); // make sure touched state lasts 5 seconds
        }
        else { // no touchpad interaction
            touched = false;
        }
        Thread::wait(100); // runs 10 times a second
    }
}

void screen(void const *argument) {
    while(1) {
        uLCD.filled_rectangle(0, 0, 127, 127, BLACK); // clear screen
        switch(state) {
            case ROAM: {
                uLCD.circle(64, 64, 50, BLUE); // blue circle in the center
            } break;
            case STOP: {
                uLCD.locate(0,0);
                if (energy < 30) { // tired
                    uLCD.color(RED+GREEN);
                    uLCD.printf("0"); // yellow 0's
                } else if (fed || touched) { // touched or fed
                    uLCD.color(RED);
                    uLCD.printf("<3");
                } else { // wondering
                    uLCD.color(BLUE);
                    uLCD.printf("?"); // blue ?'s
                }
            } break;
            case SLEEP: {
                uLCD.locate(0,0);
                uLCD.color(BLUE);
                uLCD.printf("Z"); // blue Z's
            }
        }
        
        Thread::wait(100);    
    }
}

void sound(void const *argument) {
    while(1) {
        switch(state) {
            case STOP: {
                if (energy < 30) { // tired
                    
                } else if (fed || touched) { // touched or fed
                    
                } else { // wondering
                    
                }
            } break;
            case SLEEP: {
                
            }
        }
        
        Thread::wait(100);    
    }
}

int main() {
    uLCD.cls();
    uLCD.printf("Change baudrate.....");
    uLCD.baudrate(3000000); //jack up baud rate to max
    uLCD.background_color(BLACK);
    uLCD.text_bold(ON);
    uLCD.text_mode(OPAQUE);
    uLCD.text_width(5);
    uLCD.text_height(5);
    uLCD.cls();
    mu.startUpdates();

    state = ROAM;
    energy = 70;

    Thread thread1(sonar);
    //Thread thread2(touchpad);
    //Thread thread3(screen);
    //Thread thread4(sound);
    
    while(1) {
        // Status LEDS
        led1 = state == ROAM; // no leds on = ROAM, 1 led on = STOP, both on = SLEEP
        led2 = state > STOP;
        led3 = touched;
        led4 = fed;
        
        // Update state
        if (energy < 5) { // sleeps for 10 seconds and wake up with 50 more energy
            state = SLEEP;
            Thread::wait(10000);
            energy += 50;
        } else if (energy < 30 || touched || fed) {
            state = STOP;
        } else {
            state = ROAM;
        }
        
        // Update energy
        switch(state) {
            case ROAM: energy -= 2;
                break;
            case STOP : energy -= 1;
                break;
        }
        
        // Make sure energy stays in 0-100
        if (energy < 0) {
            energy = 0;
        } else if (energy > 100) {
            energy = 100;
        }
        
        Thread::wait(1000); // runs once per second
    }
}