Initial Release

Dependencies:   MCP23S17 Motor SDFileSystem mbed-rtos mbed wave_player

main.cpp

Committer:
EngineerGuy1GT
Date:
2017-12-06
Revision:
0:5be0a1cce3f6

File content as of revision 0:5be0a1cce3f6:

#include "mbed.h"
#include "rtos.h"
#include "Motor.h"
#include "SDFileSystem.h"
#include "wave_player.h"
#include "SongPlayer.h"
#include "Speaker.h"
#include "MCP23S17.h"
#include "mbed.h"

Serial pc(USBTX, USBRX);

//ZIGBEE (XBEE)
Serial xbee(p9, p10);
DigitalOut xbee_rst(p8);
    
//DC MOTORS
Motor motor_left(p26, p30, p29); // pwm, fwd, rev
Motor motor_right(p23, p25, p24); // pwm, fwd, rev

//SD CARD
SDFileSystem sd(p11, p12, p13, p14, "sd"); // (MOSI,MISO,SCLK,CS,NAME)

// I/O EXPANDER
SPI IO_spi(p5, p6, p7); //MOSI(SI), MISO(SO), SCLK(SCK)
DigitalOut IO_rst(p15);

//Speaker
AnalogOut DACout(p18);
wave_player waver(&DACout);
FILE *wave_file;

//LED Signals
DigitalOut brake_sig(p20);
DigitalOut left_turn_sig(p22);
DigitalOut right_turn_sig(p21);

//Mutex Lock
Mutex mutex;

//Threads
Thread motor_thread;
Thread speaker_thread;
Thread RGB_LED_bar_thread;

volatile float left_speed;
volatile float right_speed;
volatile float old_left;
volatile float old_right;
volatile char RX_char;

float get_left_speed(char input)
{
    switch(input)
    {
        case 'f':
            return 1.0;
        case 'm':
            return 0.66;
        case 's':
            return 0.33;
        case 'n':
            return 0;
        case 'r':
            return -0.33;
        case 'l':
            return -0.66;
        case 'e':
            return -1.0;
        default:
            return old_left;
    }
}

float get_right_speed(char input)
{
    switch(input)
    {
        case 'F':
            return 1.0;
        case 'M':
            return 0.66;
        case 'S':
            return 0.33;
        case 'N':
            return 0;
        case 'R':
            return -0.33;
        case 'L':
            return -0.66;
        case 'E':
            return -1.0;
        default:
            return old_right;
    }
}

void control_motors()
{
    // reset the Zigbee (at least 200ns)
    xbee_rst = 0;
    wait_ms(1); 
    xbee_rst = 1;
    wait_ms(1); 
    pc.printf("ZIGBEE COMMUNICATION SETUP COMPLETE\n\r");
    
    while(1)
    {
        if(xbee.readable()) 
        {
            RX_char = xbee.getc();
            //pc.printf("receiving... %c\n\r", RX_char);
            pc.putc(RX_char); 
            
            left_speed = get_left_speed(RX_char);
            old_left = left_speed;
            right_speed = get_right_speed(RX_char);
            old_right = right_speed;
            
            //Signal and Brake Control
            if((left_speed == 0) && (right_speed == 0))
            {
                brake_sig = 1;
                left_turn_sig = 0;
                right_turn_sig = 0;
            }
            
            else if(left_speed > right_speed)
            
            {
                brake_sig = 0;
                left_turn_sig = ! left_turn_sig;
                right_turn_sig = 0;
            }
            
            else if(left_speed < right_speed)
            {
                brake_sig = 0;
                right_turn_sig = ! right_turn_sig;
                left_turn_sig = 0;
            }
            
            else
            {
                brake_sig = 0;
                left_turn_sig = 0;
                right_turn_sig = 0;
            }
            
            motor_left.speed(left_speed);
            motor_right.speed(right_speed);
        }
    }
}

void speaker()
{
    //Mount the filesystem
    //sd.mount();
    //wave_file=fopen("/sd/wavfiles/police_siren.wav","r");
    //waver.play(wave_file);
    //Thread::wait(31000);  //wait 31 seconds
    while(1)
    {
        if (RX_char == 'w')
        {
            wave_file=fopen("/sd/wavfiles/police_siren.wav","r");
            waver.play(wave_file);
            fclose(wave_file);
            Thread::wait(31000);  //wait 31 seconds
        }
        Thread::wait(500);  //wait 500ms
    }
}


void RGB_LED_bar()
{
    //Device Opcode Defined:
    // 0 1 0 0   A2 A1 A0 0
    
    //chipR --> Red
    //chipG --> Green
    //chipB --> Blue
    
    //MCP23S17 ChipR
    // A0, A1, A2 of MCP23S17 chip0 are tied to ground on the breadboard, so the 8-bit address for writes is 0x40
    // This is referred to as the opcode in the device datasheet
    //A2=0      A1=0        A0=0
    char OpcodeR = 0x40;
    // Next create a MCP23S17
    // mbed p16 is connected to ~chipSelect on the MCP23S17
    MCP23S17 chipR = MCP23S17(IO_spi, p16, OpcodeR);
    
    //MCP23S17 ChipG
    //A2=0      A1=0        A0=1
    char OpcodeG = 0x42;
    // Next create a MCP23S17
    // mbed p17 is connected to ~chipSelect on the MCP23S17
    MCP23S17 chipG = MCP23S17(IO_spi, p17, OpcodeG);
    
    //MCP23S17 ChipB
    //A2=0      A1=1        A0=0
    char OpcodeB = 0x44;
    // Next create a MCP23S17
    // mbed p19 is connected to ~chipSelect on the MCP23S17
    MCP23S17 chipB = MCP23S17(IO_spi, p19, OpcodeB);
    
    IO_rst = 0;
    wait_us(10);
    IO_rst = 1;
    
    //0x00 = 'input'    0xFF = 'output'
    //Set all 8 Port A bits to output direction
    chipR.direction(PORT_A, 0x00);
    chipG.direction(PORT_A, 0x00);
    chipB.direction(PORT_A, 0x00);
    //Set all 8 Port B bits to output direction
    chipR.direction(PORT_B, 0x00);
    chipG.direction(PORT_B, 0x00);
    chipB.direction(PORT_B, 0x00);
    
        int init_wait = 500;
        mutex.lock();
        chipR.write(PORT_A, 0xFF);
        chipR.write(PORT_B, 0xFF);
        mutex.unlock();
        Thread::wait(init_wait);
        mutex.lock();
        chipG.write(PORT_A, 0xFF);
        chipG.write(PORT_B, 0xFF);
        mutex.unlock();
        Thread::wait(init_wait);
        mutex.lock();
        chipB.write(PORT_A, 0xFF);
        chipB.write(PORT_B, 0xFF);
        mutex.unlock();
        Thread::wait(init_wait);
        mutex.lock();
        chipR.write(PORT_A, 0x00);
        chipR.write(PORT_B, 0x00);
        mutex.unlock();
        Thread::wait(init_wait);
        mutex.lock();
        chipG.write(PORT_A, 0x00);
        chipG.write(PORT_B, 0x00);
        mutex.unlock();
        Thread::wait(init_wait);
        mutex.lock();
        chipB.write(PORT_A, 0x00);
        chipB.write(PORT_B, 0x00);
        mutex.unlock();
        Thread::wait(init_wait);
        
        bool flag = 0;
        volatile int redA_i = 0b10000000;
        volatile int greenA_i = 0b10000000;
        volatile int redB_i = 0b00000001;
        volatile int greenB_i = 0b00000001;
        volatile int redA;
        volatile int redB;
        volatile int greenA;
        volatile int greenB;
        volatile int blueA = 0b11111111;
        volatile int blueB = 0b11111111;
        
        
    while(1)
    {
        //2-PART CYCLON SWEEP (LED LIGHTING EFFECT)
        mutex.lock();
        if (flag == 0)
        {
            redA_i = redA_i>>1;
            greenA_i = greenA_i>>1;
            redB_i = redB_i<<1;
            greenB_i = greenB_i<<1;
            if (redA_i == 0b00000001)
            {
                flag = 1;
            }
        }
        else if (flag == 1)
        {
            redA_i = redA_i<<1;
            greenA_i = greenA_i<<1;
            redB_i = redB_i>>1;
            greenB_i = greenB_i>>1;
            if (redA_i == 0b10000000)
            {
                flag = 0;
            }
        }
        redA = redA_i ^ 0b11111111; //XOR
        greenA = greenA_i ^ 0b11111111; //XOR
        redB = redB_i ^ 0b11111111; //XOR
        greenB = greenB_i ^ 0b11111111; //XOR
        chipR.write(PORT_A, redA);
        chipR.write(PORT_B, redB);
        chipG.write(PORT_A, greenA);
        chipG.write(PORT_B, greenB);
        chipB.write(PORT_A, blueA);
        chipB.write(PORT_B, blueB);
        mutex.unlock();
        Thread::wait(100);
    }
}


int main()
{
    
    // Start Threads
    motor_thread.start(control_motors);
    speaker_thread.start(speaker);
    RGB_LED_bar_thread.start(RGB_LED_bar);
    
}