This is a demo for controlling your ShieldBot using your mobile phone

Dependencies:   BLE_API ShieldBot_v12 mbed nRF51822

Fork of BLE_LoopbackUART by Bluetooth Low Energy

main.cpp

Committer:
Kevin_Lee
Date:
2015-09-15
Revision:
12:900318ccf3ae
Parent:
10:633cec718bf4

File content as of revision 12:900318ccf3ae:

/*    
 * main.cpp
 * A Demo for ShieldBot
 *   
 * Copyright (c) 2015 seeed technology inc.  
 * Author      : Jiankai.li
 * Create Time:  Sep  2015
 * Change Log : 
 *
 * The MIT License (MIT)
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 * 
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 * 
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */


#include "mbed.h"
#include "BLEDevice.h"

#include "UARTService.h"
#include "ShieldBot_v12.h"
#define NEED_CONSOLE_OUTPUT 1 /* Set this if you need debug messages on the console;
                               * it will have an impact on code-size and power consumption. */

#if NEED_CONSOLE_OUTPUT
#define DEBUG(...) { printf(__VA_ARGS__); }
#else
#define DEBUG(...) /* nothing */
#endif /* #if NEED_CONSOLE_OUTPUT */

BLEDevice  ble;
DigitalOut led1(LED1);

UARTService *uartServicePtr;
Shieldbot shieldbot = Shieldbot();

void turnLeft()
{
    shieldbot.drive(-127,127);   //turn left on a dime
    wait(0.4);
    shieldbot.stop();
}

void turnRight()
{
    shieldbot.drive(127,-127);   //turn left on a dime
    wait(0.4);
    shieldbot.stop();
}


void processPacket(uint8_t *packet)
{
    static int16_t speed = 255;
    uint8_t cmd = packet[0];
    DEBUG("comand: %c\n\r", cmd);
    switch(cmd) {
    case 'a':
        turnLeft();
        break;
    case 'd':
        turnRight();
        break;
    case 's':
        shieldbot.backward();
        break;
    case 'w':
        shieldbot.forward();
        break;
    case ' ':
        shieldbot.stop();
        break;
    case '-':
        speed -= 50;
        if(speed <= 5){
            speed = 5;
        }
        shieldbot.setMaxSpeed(speed);
        break;
    case '+':
        speed += 50;
        if(speed >= 255) {
            speed = 255;
        }
        shieldbot.setMaxSpeed(speed);
        break;
    default:
        break;
    }
}

void disconnectionCallback(Gap::Handle_t handle, Gap::DisconnectionReason_t reason)
{
    DEBUG("Disconnected!\n\r");
    DEBUG("Restarting the advertising process\n\r");
    ble.startAdvertising();
}

void onDataWritten(const GattCharacteristicWriteCBParams *params)
{
    if ((uartServicePtr != NULL) && (params->charHandle == uartServicePtr->getTXCharacteristicHandle())) {
        uint16_t bytesRead = params->len;
        DEBUG("received %u bytes\n\r", bytesRead);
        ble.updateCharacteristicValue(uartServicePtr->getRXCharacteristicHandle(), params->data, bytesRead);
        processPacket((uint8_t *)params->data);
    }
}

void periodicCallback(void)
{
    led1 = !led1;
}

int main(void)
{
    led1 = 1;
    Ticker ticker;
    ticker.attach(periodicCallback, 1);

    DEBUG("Initialising the nRF51822\n\r");
    ble.init();
    ble.onDisconnection(disconnectionCallback);
    ble.onDataWritten(onDataWritten);

    /* setup advertising */
    ble.accumulateAdvertisingPayload(GapAdvertisingData::BREDR_NOT_SUPPORTED);
    ble.setAdvertisingType(GapAdvertisingParams::ADV_CONNECTABLE_UNDIRECTED);
    ble.accumulateAdvertisingPayload(GapAdvertisingData::SHORTENED_LOCAL_NAME,
                                     (const uint8_t *)"ShieldBot", sizeof("ShieldBot") - 1);
    ble.accumulateAdvertisingPayload(GapAdvertisingData::COMPLETE_LIST_128BIT_SERVICE_IDS,
                                     (const uint8_t *)UARTServiceUUID_reversed, sizeof(UARTServiceUUID_reversed));

    ble.setAdvertisingInterval(Gap::MSEC_TO_ADVERTISEMENT_DURATION_UNITS(1000));
    ble.startAdvertising();

    UARTService uartService(ble);
    uartServicePtr = &uartService;

    while (true) {
        ble.waitForEvent();
    }
}