Bluetooth robot BT-Bot

Bluetooth robot BT-Bot

Please see this post Bluetooth controlled DC motor, BT module review for a more in-depth demonstration of the Bluetooth part.

Update: A similar project has been made using a PIC mcu (I’m using an AVR) over at Blazing Elektroniks.

For the past weeks I have had this robot to play with. Today I added some additional intelligence to it, and decided to post it here as a finished project.

The controls are based on my previous post on motor control via bluetooth. One extra motor was added to the code, I etched a new PCB for the L298 board so it took up less space, and attached it all to a robot chassis. The chassis is called “Mr. Basic” and is produced by Dagu specifically for the Let’s Make Robots community. You can buy it at dealextreme.com.

Since my last post on bluetooth motor control I have switched to another android application called QkCtrl. This application provides much more flexibility, and I recommend it. The bluetooth SPP module provides a wireless standard UART interface and is very easy to use and to set up. The whole concept is based on sending individual characters to the microcontroller for each key press in QkCtrl, and then interpreting character on the AtTiny2313 to execute different commands. The QkCtrl layout is user-definable, my layout is pictured below together with explanations on which button sends which character.

Forward ‘U’ Starts the motors on a forward direction. Speed is 1/3 at startup.
Backward ‘D’ Starts the motors in a backward direction. Speed is 1/3 at startup.
Left ‘L’ Makes a small turn to the left when motors are running forward/backward
Right ‘R’ Makes a small turn to the right when motors are running forward/backward
Stop ‘C’ Stops both motors
Speed down ‘s’ Decreases motor speed. Affects both motors
Speed up ‘f’ Increases motor speed. Affects both motors
Pirouette L ‘a’ Full speed pirouette to the left
Pirouette R ‘e’ Full speed pirouette to the right
Alarm ‘P’ Activates “burglar” alarm (robot wiggling with sound when motion is detected)
Child safe ‘H’ When robot is ran against a wall, it automatically stop and changes direction
Headlamp ‘l’ Turn headlamp LEDs on and off
Horn ‘h’ Honks the horn for half a second

The next image explains each component of the robot (click to enlarge)
1 Bluetooth SPP modem
2 AtTiny2313 microcontroller
3 PIR motion sensor
4 Ultrasonic distance sensor
5 L298 dual motor control board
6 One of two LED headlamps
7 Buzzer/horn
8 One of two motors
9 Battery for the motors
10 Battery for the controls and logic (regulated to 5v with L7805)
11 On/off switch

A short demo video

The code is a bit messy without any comments, it will be improved and a schematic will be posted.

#include <avr/io.h>
#include <avr/interrupt.h>
#define F_CPU 8000000UL //Defines clock speed
#define USART_BAUDRATE 9600 //Baudrate for serial comm.
#define BAUD_PRESCALE (((F_CPU / (USART_BAUDRATE * 16UL))) - 1)
#include <util/delay.h>

uint16_t distance;
uint8_t count = 0;
uint8_t ovf = 0;
uint8_t alarm = 0;
uint8_t light = 0;
uint8_t speed = 100;
uint8_t pir = 0;
uint8_t distanceSensor = 0;
char rotDir = 'L';
char state;

void forward(void)
{
	state = 'U';
	PORTB |= (1<<PIN1) | (1<<PIN4);
	PORTB &= ~(1<<PIN0) & ~(1<<PIN3);
	OCR0A = speed;
	OCR0B = speed;
}

void backward(void)
{
	state = 'D';
	PORTB |= (1<<PIN0) | (1<<PIN3);
	PORTB &= ~(1<<PIN1) & ~(1<<PIN4);
	OCR0A = speed;
	OCR0B = speed;
}

void rightTurn(void)
{
	PORTB |= (1<<PIN0) | (1<<PIN1);
	_delay_ms(350);
	if (state == 'U') forward();
	else if (state == 'D') backward();
}

void leftTurn(void)
{
	PORTB |= (1<<PIN3) | (1<<PIN4);
	_delay_ms(350);
	if (state == 'U') forward();
	if (state == 'D') backward();
}

void leftPirouette(void)
{
	state = 'a';
	rotDir = 'L';
	//PORTB = 0b00001010;
	PORTB |= (1<<PIN1) | (1<<PIN3);
	PORTB &= ~(1<<PIN0) & ~(1<<PIN4);
	OCR0A = 254;
	OCR0B = 254;
}

void rightPirouette(void)
{
	state = 'e';
	rotDir = 'R';
	//PORTB = 0b00010001;
	PORTB |= (1<<PIN0) | (1<<PIN4);
	PORTB &= ~(1<<PIN3) & ~(1<<PIN1);
	OCR0A = 254;
	OCR0B = 254;
}

void stop(void)
{
	if (state == 'U')
	{
		backward();
		_delay_ms(40);
	}

	else if (state == 'D')
	{
		forward();
		_delay_ms(40);
	}

	state = 'C';
	GIMSK &= ~(1<<INT1);
	PORTB |= (1<<PIN0) | (1<<PIN1) | (1<<PIN3) | (1<<PIN4);
	OCR0A = 0;
	OCR0B = 0;
	_delay_ms(1000);
	GIMSK |= (1<<INT1);
}

void longBeep(void)
{
	PORTD |= (1<<PIN6);
	_delay_ms(500);
	PORTD &= ~(1<<PIN6);
}

void shortBeep(void)
{
	PORTD |= (1<<PIN6);
	_delay_ms(50);
	PORTD &= ~(1<<PIN6);
}

void lights(void)
{
	if (light == 0)
	{
		PORTB |= (1<<PIN5) | (1<<PIN6);
		light = 1;
	}

	else
	{
		PORTB &= ~(1<<PIN5) & ~(1<<PIN6);
		light = 0;
	}
}

void faster(void)
{
	if (OCR0A < 244 && OCR0B < 244)
	{
		speed += 10;
		OCR0A = speed;
		OCR0B = speed;
	}
}

void slower(void)
{
	if (OCR0A > 10 && OCR0B > 10)
	{
		speed -= 10;
		OCR0A = speed;
		OCR0B = speed;
	}
}

ISR(TIMER1_OVF_vect)
{
	ovf = 1;

	if(count == 25)
	{
	 	//Pulse the DYP-ME007 trigger pin
		PORTD |= (1<<PIN4);
		_delay_us(100);
		PORTD &= ~(1<<PIN4);
		count = 0;
	}
	else count++;
}

ISR(INT0_vect)
{
	if(PIND & (1<<PIN2))
	{
		TCNT1 = 0;
		ovf = 0;
	}

	else
	{
		distance = TCNT1;

		if (ovf == 1);
		else if (distance > 15000 && distanceSensor == 1)
		{
			if (alarm == 1)
			{
				alarm = 0;
				forward();
			}
		}

		else if (distance <= 15000 && alarm == 0 && distanceSensor == 1)
		{
			stop();
			longBeep();
			alarm = 1;
			if (rotDir == 'L') leftPirouette();
			else if (rotDir == 'R') rightPirouette();
		}
	}
}

ISR(INT1_vect)
{
	if (state == 'C' && pir == 1)
	{
		shortBeep();
		forward();
		_delay_ms(250);
		shortBeep();
		backward();
		_delay_ms(250);
		shortBeep();
		stop();
	}
}

//Serial com. Interrupt Service Routine (runs each time a byte is received)
ISR(USART_RX_vect)
{
	char ReceivedByte;
	ReceivedByte = UDR; // Retrieves byte from serial port (bluetooth module)
	//UDR = state; // Echoes it back for fun

	switch (ReceivedByte) //Which ASCII character was received?
	{
		case '!':	shortBeep();
					_delay_ms(50);
					shortBeep();
					_delay_ms(50);
					shortBeep();
					break;

		case 'U': 	forward();
					break; //Increase PWM duty cycle

		case 'C': 	stop();
					break; //Break motor by raising both direction inputs, PWM duty cycle 0%

		case 'D': 	backward();
					break; //Decrease PWM duty cycle

		case 'L': 	leftTurn();
					break;

		case 'R': 	rightTurn();
					break;

		case 'a':	leftPirouette();
					break;

		case 'e':	rightPirouette();
					break;

		case 'h':	longBeep();
					break;

		case 'l':	lights();
					break;

		case 'f':	faster();
					break;

		case 's':	slower();
					break;

		case 'P':	if (pir) pir = 0;
					else pir = 1;
					UDR = 'P';
					break;

		case 'H':	if (distanceSensor) distanceSensor = 0;
					else distanceSensor = 1;
					UDR = 'H';
					break;

		default:	UDR = '?';
					break; //Character unknown to my routine, discard character

	}

}

int main(void)
{
	//I/O Initialization
	DDRB |= (1<<PIN0) | (1<<PIN1) | (1<<PIN2) | (1<<PIN3) | (1<<PIN4) | (1<<PIN5) | (1<<PIN6); //DIR1, DIR2 and Enable pins as outputs
	DDRD |= (1<<PIN4) | (1<<PIN5) | (1<<PIN6);
	PORTB=0; //All initialized to 0

	//Timer0 initialization
	TCCR0A |= (1<<COM0A1) | (1<<COM0B1) | (1<<WGM00); //Phase correct PWM mode
	TCCR0B |= /*(1<<WGM02) |*/ (1<<CS00) | (1<<CS01); //div64
	OCR0A = 0; //Initialize PWM duty cycle to 0%
	OCR0B = 0;

	//Timer1 initialization
	TCCR1B |= (1<<CS10); //No prescaling (max count ~8ms)
	TIMSK |= (1<<TOIE1); //overflow interrupt

	//UART
	UCSRB |= (1 << RXEN) | (1 << TXEN); //Enable Tx and Rx
	UCSRC |= (1 << UCSZ0) | (1 << UCSZ1);
	UBRRL = BAUD_PRESCALE;			//Sets
	UBRRH = (BAUD_PRESCALE >> 8);	//baudrate registers
	UCSRB |= (1 << RXCIE); //Enable USART-interrupt

	//External interrupts
	MCUCR |= (1<<ISC10) | (1<<ISC11) | (1<<ISC00); //INT1 rising trig. INT0 logic trig.
	GIMSK |= (1<<INT1) | (1<<INT0); //INT 0 and 1 enabled

	sei(); //Enable global interrupt

	/* This program is completely interrupt driven, so nothing goes on in while loop*/
	while(1); //Never gets out from here!

	return 0; //Never reaches this point!
}

This article has 32 comments

  1. y dnt u rite a instruction for this project or video tutorl.

  2. hiiiiii
    Yours Bluetooth Robot BT-Bot is very nice
    i m also trying to make this robot can u tell me that its AtTiny2313 microcontroller source code is correct or not and how can i burn and which software should i use for it …..
    plz reply
    thanks

  3. How you build program in android 3 ? pls i need the src of app on android , can i use any bt ?

      • Henrik Sandaker Palm
        Tuesday 25 October 2011, 1:34 pm

        I do not have the source code for the Bluetooth application for Android. It is called QkCtrl and is free to use.

        You can use any bluetooth module which supports SPP (Serial Port Profile), you just need to get the connections right. The one in my post is simple, cheap and easy to use, compared to many others available.

  4. Hello!
    I loved this car! That code wasn’t messy, althought I have to read up on the bitshifting. No big deal.

    But I wonder about the licensing?
    What license are this code under?
    Not that I am using it commercial, but when I pick it from the internet doesn’t mean that I wrote this code! ;)

    I loved your serial routine, it is well written. Thanks for showing me a nice way to use BlueTooth. That only – that code – made me wanting playing with BlueTooth. :)

    • Henrik Sandaker Palm
      Tuesday 25 October 2011, 1:31 pm

      Hello,
      no licensing. The serial routine (register set-up) is based on a tutorial by Dean Camera on XDA Developers forum (user: abcminiuser), other than that no code is borrowed from elsewhere and are free to use.

      Thank you for the kind words, and I am pleased you are motivated to start tinkering on simple bluetooth applications based on my code!

  5. Thanks a lot for the information about the serial routine, I have wroted that down so I won’t forget.
    The Arduine’s code for serial used around 6k of memory and I got some problems with space when I coded last time. So I hope the “new” code is slimmer. Thanks!

    It’s very seldom that I see well written code, I really enjoyed to read your code, so you should be proud of your own work. It’s very few peoples who have clarity in their code. That was the reason I wanted to play with bluetooth modules.

    Have a nice day and I wish you all well.
    I’ll try to be back with updates if I have done anything with bluetooth, but it’ll may take a long time. You may know how it is. ;)

  6. Hello,
    I from Brazil, I am student. Baeutiful work.
    I have a project with Android, I need help in Android to use to Bluetooth to control a rob. Do you help me?

  7. […] microHobby.net – Bluetooth robot BT-BotJun 26, 2011 … The next image explains each component of the robot (click to enlarge) 1 Bluetooth SPP modem 2 AtTiny2313 microcontroller 3 PIR motion … […]

  8. Hello ..
    It’s very very nice!!!!

    I ‘m study in Thailand
    i wanna to build this robot like you

    Are you have a tutorial to build this car with step by step

    if you see this message please.. contact me at puchong.sp@gmail.com

    i try to build this car for along time

  9. @daspilker Absolutely. QkCtrl is easy and very configurable. http://t.co/xLNCQGdo

  10. Hello
    Nice project!
    I’ve the same bluetooth modul, but i’ve problem with received data from Blue Control (Android). Received data from Blutooth modul to uC by Usart are not recognizeg by A-H characteristic. But getting the numbers f.e 181 – ‘U’, 132 – ‘D’. What is the problem? Do I need to set up an Bluetooth Module? Please, hepl!:)

    • Henrik Sandaker Palm
      Monday 1 October 2012, 2:13 pm

      Sure you’re reading it back as ASCII? 181 should not correspond to ‘U’ in any way, neither 132 and ‘D’. I’m guessing faults in UART. Try UART->USB converter and monitor communication on your PC

  11. can i get the circuit diagram please!!!!!!!!!!!!!!

  12. can we have the schematic please? … it’s been a while since you said you would post it :P

  13. Hi Henrik,

    i am interested by your object. I am just developping android’s application connected hardware and software used in medical. I have gotten a problem is a way to built Android bluetooth software but not yet finished. Could you send the source code sample of Android Bluetooth to let me prefer. Anyway, thanks.

    Tran Anh Huy

  14. […] with a wired remote so I thought I’d take it to the next level. For AVR version, visit microHobby.net It’s a similar project but it uses AVR uC instead. This uses […]

  15. Hi sir Can I have a copy of your  Android apps that controlss your robot….  .apk files

  16. Hey bro…
    Can U send me BT-bot program code for 8051.

  17. Hey bro…
    Can U send me BT-bot program code for 8051. 
    email : anil.khurana85@gmail.com

Leave a Reply