Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
main.cpp
- Committer:
- kunaljacy
- Date:
- 2012-05-05
- Revision:
- 0:04e850e5bb86
File content as of revision 0:04e850e5bb86:
#include "mbed.h"
#include "MODSERIAL.h"
// Serial Communication with XBee, iRobot, and PC
MODSERIAL xbee_receive(p9, p10); // tx, rx
Serial irobot(p13, p14); // tx, rx
Serial pc(USBTX, USBRX);
// LEDs for wireless communication status
DigitalOut l1(LED1);
DigitalOut l2(LED2);
// PWM channels for arm motor speed control
PwmOut m1s(p21); // shoulder
PwmOut m2s(p22); // elbow
PwmOut m3s(p23); // gripper
PwmOut m4s(p24); // wrist
// Digial channels for arm motor direction control
DigitalOut m1d1(p19); // shoulder
DigitalOut m1d2(p20);
DigitalOut m2d1(p27); // elbow
DigitalOut m2d2(p28);
DigitalOut m3d1(p29); // gripper
DigitalOut m3d2(p30);
DigitalOut m4d1(p25); // wrist
DigitalOut m4d2(p26);
// Create Command
const char Start = 128;
const char FullMode = 132;
const char DriveDirect = 145; // 4: [Right Hi] [Right Low] [Left Hi] [Left Low]
const char SensorStream = 148;
const char PlaySong = 141;
const char Song = 140;
const char BumpsandDrops = 7;
/* Global variables with sensor packet info */
char Sensor_byte_count = 0;
char Sensor_Data_Byte = 0;
char Sensor_ID = 0;
char Sensor_Num_Bytes = 0;
char Sensor_Checksum = 0;
short mode;
void start();
void stop();
void autonomous();
void receive_sensor();
void findBomb();
void diffuseBomb();
void returnHome();
void turn_right();
void turn_left();
void returnHome();
void playsong();
typedef struct {
short xAxis;
short yAxis;
short grip;
short left_velocity;
short right_velocity;
short wrist;
short elbow;
short mode;
} xbee_packet;
xbee_packet packet;
char packetFound = 0;
void receive_xbee_packet() {
char tmp;
packetFound = 0;
char cs = 0;
char data[16];
l1 = 0;
l2 = 0;
if (xbee_receive.rxBufferGetCount() < 20) {
l1 = 1;
return;
}
while (xbee_receive.rxBufferGetCount() > 19) {
tmp = xbee_receive.getc();
if (tmp == 0xF1) {
tmp = xbee_receive.getc();
if (tmp == 0xE2) {
packetFound = 1;
break;
}
}
}
if (packetFound == 1) {
l2 = 1;
tmp = xbee_receive.getc();
cs = tmp;
data[0] = xbee_receive.getc();
cs ^= data[0];
data[1] = xbee_receive.getc();
cs ^= data[1];
data[2] = xbee_receive.getc();
cs ^= data[2];
data[3] = xbee_receive.getc();
cs ^= data[3];
data[4] = xbee_receive.getc();
cs ^= data[4];
data[5] = xbee_receive.getc();
cs ^= data[5];
data[6] = xbee_receive.getc();
cs ^= data[6];
data[7] = xbee_receive.getc();
cs ^= data[7];
data[8] = xbee_receive.getc();
cs ^= data[8];
data[9] = xbee_receive.getc();
cs ^= data[9];
data[10] = xbee_receive.getc();
cs ^= data[10];
data[11] = xbee_receive.getc();
cs ^= data[11];
data[12] = xbee_receive.getc();
cs ^= data[12];
data[13] = xbee_receive.getc();
cs ^= data[13];
data[14] = xbee_receive.getc();
cs ^= data[14];
data[15] = xbee_receive.getc();
cs ^= data[15];
tmp = xbee_receive.getc();
if (cs == tmp) {
memcpy(&packet, data, 16);
}
}
}
void receive_sensor() {
char start_character;
Sensor_Data_Byte = 0;
// Loop just in case more than one character is in UART's receive FIFO buffer
while (irobot.readable()) {
switch (Sensor_byte_count) {
// Wait for Sensor Data Packet Header of 19
case 0: {
start_character = irobot.getc();
if (start_character == 19) Sensor_byte_count++;
break;
}
// Number of Packet Bytes
case 1: {
Sensor_Num_Bytes = irobot.getc();
Sensor_byte_count++;
break;
}
// Sensor ID of next data value
case 2: {
Sensor_ID = irobot.getc();
Sensor_byte_count++;
break;
}
// Sensor data value
case 3: {
Sensor_Data_Byte = irobot.getc();
irobot.getc();
Sensor_byte_count = 0;
return;
}
// Read Checksum and update LEDs with sensor data
case 4: {
Sensor_Checksum = irobot.getc();
// Could add code here to check the checksum and ignore a bad data packet
Sensor_byte_count = 0;
break;
}
}
}
return;
}
void actuate() {
short right = packet.right_velocity;
short left = packet.left_velocity;
short xAxis = packet.xAxis;
short yAxis = packet.yAxis;
short grip = packet.grip;
short wrist = packet.wrist;
short elbow = packet.elbow;
if (right || left){
irobot.printf("%c%c%c%c%c", DriveDirect, char((right >> 8) & 0xFF), char(right & 0xFF), char((left >> 8) & 0xFF), char(left & 0xFF));
return;
}
stop();
if (xAxis < 0) {
irobot.printf("%c%c%c%c%c", DriveDirect, char(((-xAxis * 5) >> 8) & 0xFF), char(-xAxis * 5 & 0xFF), char(((xAxis * 5) >> 8) & 0xFF), char((xAxis * 5) & 0xFF));
return;
} else if (xAxis > 0) {
irobot.printf("%c%c%c%c%c", DriveDirect, char(((-xAxis * 5) >> 8) & 0xFF), char(-xAxis * 5 & 0xFF), char(((xAxis * 5) >> 8) & 0xFF), char((xAxis * 5) & 0xFF));
return;
}
stop();
if (yAxis < 0) {
m1d1 = 1;
m1d2 = 0;
m1s.write((float) (-yAxis)/50);
} else if (yAxis > 0) {
m1d1 = 0;
m1d2 = 1;
m1s.write((float) yAxis/50);
} else {
m1d1 = 0;
m1d2 = 0;
m1s = 0;
}
if (elbow < 0) {
// pc.printf("elbow\r\n");
m2d1 = 1;
m2d2 = 0;
m2s.write((float) (-elbow)/50);
} else if (elbow > 0) {
m2d1 = 0;
m2d2 = 1;
m2s.write((float) elbow/50);
} else {
m2d1 = 0;
m2d2 = 0;
m2s.write(0);
}
if (wrist < 0) {
m4d1 = 1;
m4d2 = 0;
m4s.write((float) 0.2);
} else if (wrist > 0) {
// pc.printf("wrist\r\n");
m4d1 = 0;
m4d2 = 1;
m4s.write((float) 0.2);
} else {
m4d1 = 0;
m4d2 = 0;
m4s.write(0);
}
if (grip == -1) {
// pc.printf("gripper\r\n");
m3d1 = 1;
m3d2 = 0;
m3s.write((float) 0.2);
} else if (grip == 1) {
m3d1 = 0;
m3d2 = 1;
m3s.write((float) 0.2);
} else {
m3d1 = 0;
m3d2 = 0;
m3s.write(0);
}
}
int main() {
int count = 0;
wait(5); // wait for Create to power up to accept serial commands
irobot.baud(57600); // set baud rate for Create factory default
start();
wait(.5);
while (1) {
receive_xbee_packet();
mode = packet.mode;
if (packetFound == 1 && !mode) {
//pc.printf("X: %d\tY: %d\tF: %d\tL: %d\tR: %d\tE: %d\tW: %d\r\n", packet.xAxis, packet.yAxis, packet.grip, packet.left_velocity, packet.right_velocity, packet.elbow, packet.wrist);
actuate();
} else if (packetFound && mode && !count) {
autonomous();
}
else if (packetFound && mode && count) {
stop();
}
}
}
// SEMI-AUTONOMOUS CODE GOES HERE
void autonomous(){
char bnd;
stop();
/*
findBomb();
diffuseBomb();
findBomb();
diffuseBomb();
returnHome();
//pc.printf("BND: %X\r\n", Sensor_Data_Byte);
wait(0.5);
*/
irobot.printf("%c%c", 136, char(1));
while(1){
receive_xbee_packet();
mode = packet.mode;
if (!mode){
start();
return;
}
}
}
void start() {
irobot.putc(Start);
irobot.putc(FullMode);
wait(.5);
}
void stop() {
irobot.printf("%c%c%c%c%c", DriveDirect, char(0), char(0), char(0), char(0));
}
// Reverse - reverse drive motors
void reverse() {
int speed_right = 200;
int speed_left = 200;
irobot.putc(DriveDirect);
irobot.putc(char(((-speed_right)>>8)&0xFF));
irobot.putc(char((-speed_right)&0xFF));
irobot.putc(char(((-speed_left)>>8)&0xFF));
irobot.putc(char((-speed_left)&0xFF));
wait(.85);
}
// Left - drive motors set to rotate to left
void turn_left() {
int speed_right = 200;
int speed_left = 200;
irobot.putc(DriveDirect);
irobot.putc(char(((speed_right)>>8)&0xFF));
irobot.putc(char((speed_right)&0xFF));
irobot.putc(char(((-speed_left)>>8)&0xFF));
irobot.putc(char((-speed_left)&0xFF));
wait(.85);
}
// Right - drive motors set to rotate to right
void turn_right() {
int speed_right = 200;
int speed_left = 200;
irobot.putc(DriveDirect);
irobot.putc(char(((-speed_right)>>8)&0xFF));
irobot.putc(char((-speed_right)&0xFF));
irobot.putc(char(((speed_left)>>8)&0xFF));
irobot.putc(char((speed_left)&0xFF));
wait(.85);
}
// Play Song - define and play a song
void playsong() { // Send out notes & duration to define song and then play song
irobot.putc(Song);
irobot.putc(char(0));
irobot.putc(char(2));
irobot.putc(char(64));
irobot.putc(char(24));
irobot.putc(char(36));
irobot.putc(char(36));
wait(0.2);
irobot.putc(PlaySong);
irobot.putc(char(0));
}
void findBomb(){
int right = 400;
int left = 400;
int c = 0;
Sensor_Data_Byte = 0;
printf("before while loop: %X\r\n", Sensor_Data_Byte);
while((Sensor_Data_Byte != 3) && (Sensor_Data_Byte != 2) && (Sensor_Data_Byte != 1)){
irobot.putc(SensorStream);
irobot.putc(1);
irobot.putc(BumpsandDrops);
receive_sensor();
printf("bnd: %X\r\n", Sensor_Data_Byte);
irobot.printf("%c%c%c%c%c", DriveDirect, char((right >> 8) & 0xFF), char(right & 0xFF), char((left >> 8) & 0xFF), char(left & 0xFF));
if (!c) {
wait(1);
}
c = 1;
}
Sensor_Data_Byte = 0;
playsong();
pc.printf("bomb found\r\n");
}
void diffuseBomb(){
// diffuse the bomb --- motor values here
//pc.printf("X: %d\tY: %d\tF: %d\tL: %d\tR: %d\tE: %d\tW: %d\r\n", packet.xAxis, packet.yAxis, packet.grip, packet.left_velocity, packet.right_velocity, packet.elbow, packet.wrist);
Sensor_Data_Byte = 0;
int right;
int left;
pc.printf("diffusing bomb\r\n");
stop();
wait(10);
right = -100;
left = -100;
irobot.printf("%c%c%c%c%c", DriveDirect, char((right >> 8) & 0xFF), char(right & 0xFF), char((left >> 8) & 0xFF), char(left & 0xFF));
wait(0.25);
stop();
pc.printf("bomb diffused, turning right\r\n");
// turn right
turn_right();
pc.printf("turned right, going home/diffusing next bomb\r\n");
Sensor_Data_Byte = 0;
}
void returnHome(){
// move the robot for some time
int right = 200;
int left = 200;
irobot.printf("%c%c%c%c%c", DriveDirect, char((right >> 8) & 0xFF), char(right & 0xFF), char((left >> 8) & 0xFF), char(left & 0xFF));
wait(8);
// turn right
turn_right();
// move the robot for some time
irobot.printf("%c%c%c%c%c", DriveDirect, char((right >> 8) & 0xFF), char(right & 0xFF), char((left >> 8) & 0xFF), char(left & 0xFF));
wait(3);
stop();
}