User Tools

Site Tools


Robotino Rectangle Tutorial

This tutorial is part of the Robotino Operation series.

Purpose: to explain how to write a basic robotino program using robotino api2, compile and run it. The program written in this tutorial will take in user specified rectangle and drive around it's perimeter.


The completed project ready to upload via ftp:


If you are not interested in learning about the code you can jump straight to the compile video

The finished program running:

Writing the code

boiler plate:

Below is a basic boiler plate for your robotino program. It includes some basic c libraries. More importantly, it includes the api2 library.

#include <cmath>
#include <iostream>
#include <stdlib.h>
#include "rec/robotino/api2/all.h"    // include the api2 library
using namespace rec::robotino::api2;   // we are going to be operating in the api2 namespace for this tutorial
float _rect[2]= {0,0};   // this is going to be the size of the rectangle our robotino will drive in.
bool _run = true;

Overriding the com class

The API2 com class allows us to communicate with the robotino's microcontroller. It has several virtual functions that we will need to overwrite in order to use it.

class MyCom : public Com
  		: Com( "rect" )      //  name our com after our program
  ** below we deal with the virtual functions.  for our purposes a simple cout will suffice
  	void errorEvent( const char* errorString )
  		std::cerr << "Error: " << errorString << std::endl;    // remember we are using namespace::api2 so we need to type std:: to access cout and cerr
  	void connectedEvent()
  		std::cout << "Connected." << std::endl;
  	void connectionClosedEvent()
  		std::cout << "Connection closed." << std::endl;
  	void logEvent( const char* message, int level )
  		std::cout << message << std::endl;
  	void pingEvent( float timeMs )
  		std::cout << "Ping: " << timeMs << "ms" << std::endl;

Setting up our bumper

Once again we need to override a built in API2 class. We want to tell the robotino to stop when the bumper has contact with something.

class MyBumper : public Bumper
  		: bumped( false )
  	void bumperEvent( bool hasContact )
  		bumped |= hasContact;
  		std::cout << "Bumper has " << ( hasContact ? "contact" : "no contact") << std::endl;
  	bool bumped;

Declare instances of our classes:

Now declare instances of the classes you created and an instance of OmniDrive.

 MyCom com;
 OmniDrive omniDrive;
 MyBumper bumper;

init() function:

The init function will be used to set up our robotino when the user launches our executable.

void init( const std::string& hostname )
    // Initialize the actors
    // Connect
    std::cout << "Connecting... ";
    com.setAddress( hostname.c_str() );
    com.connectToServer( true );
    if( false == com.isConnected() )
        std::cout << std::endl << "Could not connect to " << com.address() << std::endl;
  	exit( 1 );
       // if everything goes alright we say success and ask the user the size of the rectangle to trace
       std::cout << "success" << std::endl;
       std::cout << "enter rectange x in mm:" << std::endl;    
       std::cin >> _rect[0];     // just use std:cin to take in the size of the rectangle.
       std::cout << "enter rectange y in mm:" << std::endl;
       std::cin >> _rect[1];

Driving the robotino

The drive() function will be used to move the robotino around using the omniDrive class

void drive()
    float vel[2] = {0.1, 0.0};    // create an array to store our velocity
    float pos[2] = {0,0};          // create an array to store our position
    float lastTime=com.msecsElapsed();    // remember last time to measure change in time to calculate position
    while( com.isConnected() && false == bumper.value() && _run )
        pos[0]=vel[0]*(com.msecsElapsed()-lastTime)+pos[0];   // update the position
        std::cout << "Pos:" << pos[0] << "," << pos[1] <<std::endl;   //  print out the position.\
  	omniDrive.setVelocity( vel[0], vel[1], 0 );   // set the x and y velocity to our velocity setting set rotational velocity to 0
        if(pos[0]>=_rect[0] && pos[1] <= 0){    // this if statement changes the velocity when we reach the first corner of our rectange
        if(pos[0]>=_rect[0] && pos[1] >= _rect[1]){   // second corner 
        if(pos[0]<=0 && pos[1] >= _rect[1]){  // third corner 
        if(pos[0]<=0 && pos[1] <= 0){  // back to start location
        lastTime=com.msecsElapsed();   // reset the last time variable
        com.processEvents();   // sincronizes the com class and the onboard computer
 	rec::robotino::api2::msleep( 100 );   // wait 100 ms


when we are ready to quit we want to run destroy

void destroy()
    com.disconnectFromServer();   // simply disconnect the com

main program

Now we just need to write our main function to call the functions written above in the proper order.

int main( int argc, char **argv )
    std::string hostname = "";  // set our local hostname of our microcontroller
    if( argc > 1 )   // boiler plate stuff
  	hostname = argv[1];    
    try   // try to run our functions
  	init( hostname );   // these functions explained above
    // below we catch any errors that cropped up
    catch( const rec::robotino::api2::RobotinoException& e )
  	std::cerr << "Com Error: " << e.what() << std::endl;
    catch( const std::exception& e )
  	std::cerr << "Error: " << e.what() << std::endl;
    catch( ... )
  	std::cerr << "Unknow Error" << std::endl;
  rec::robotino::api2::shutdown();  // shut down API2

In order to compile your program on your robotino you will need a CMakeLists.txt file. I have included it above for download.

Create a folder on your robotino.

mkdir ~/dasl_tutorials/rect

switch to that directory

cd ~/dasl_tutorials/rect

On your pc put main.cpp document and your CMakeLists.txt file into a folder called src. Upload your src file to ~/dasl_tutorials/rect using your favorite ftp. My personal favorite is Transmit by Panic.

FTP username: robotino FTP password: robotino

Now you are all set to follow the video tutorial!

The finished program running:

robotino_rectangle.txt · Last modified: 2016/10/25 15:02 by dwallace