Let's Make Robots!

Update- Laser Cat

 I cant think of a good name, but im sure theres a good one somewhere, if any of you think of anything let me know. 


Laser Cat


The idea of this project is to help me learn a few things needed for my longterm project Airborne bot. It is basicaly a laser controlled by an arduino using two servos. It is for my two cats Harry and Fifi (girls cat. Fifi ffs! ) to play with.


WHen it is complete it will enable me to move the laser using a web page with a control panel and a video feed the user will click a position on the video feed and the laser will move to that point with the cats chasing it. Each time a cat manages to hit the laser point with its paw it will gain a point. THe first one to ten will get a treat which will be thrown to it from the unit. 


Im using processing to build the control panel for it to process the image from the camera and send serial output to the arduino to give the servos their position. The scoring will be worked out by dividing the target wall up into paw sized grid  blocks. I think i can work out whether the cat has scored by working out if there is a change in color in the wall in that grid and if the grid thats changed is the one that the laser is in at the time, my theory is that thelicght cream wall with eiher go ginger or black letting me know which cat got the point. Possible problems that i will have to work round is differentiating between cat paw color change and laser color change. 


So far i have the base unit built so that i can lay some code down, and i have the video feed going to processing and being displayed on screen. The servo is able to move along the x axis controled by mouse clicks. However im finding it difficult to control two servos through serial communication.  


Eventually i plan to have the unit completely wireless and mounted in the garden.


The aims of this project are to help me gain a better understanding of the following areas:



serial communication

working with coordinates

controling things with processing

working with video

wireless communication




 Update 13/ april/ 09

Ive finaly finished writing the code for the control of it. Unfortunatly i have played with it so much that my ginger cat is frustrated with it and the black cat isnt here so i cant post a video of them playing with it yet. 




Here is the arduino code: 

#include <Servo.h> 




Servo myservo1;  // create servo object to control a servo 


Servo myservo2;  




int userInput[3];   // raw input from serial buffer, 3 bytes


int startbyte;      // start byte, begin reading input


int pos = 0;    // variable to store the servo position 


int i;              // iterator




void setup() 



   // attaches the servos on pin 9 and 10 to the servo object 

   myservo1.attach(9);  //x axis

   myservo2.attach(10); //y axis





void loop() 



  // if the buffer has the right ammount of data in it


  if (Serial.available() > 2) {  


    //read the first byte  


    startbyte = Serial.read();  

    // if it's really the startbyte (255)  


    if (startbyte == 255) {  


      // then get the next two bytes  

      for (i=0;i<2;i++) {  


        userInput[i] = Serial.read();  





      // first byte is the servo we want to move


      int servo1 = userInput[0];  


      // second byte = which position?  


     int servoPosition1 = userInput[1]; 


    // print some debug lines to the serial port


    Serial.print("Servo: " );




    Serial.print(" Move: ");


    // map the input from the serial port to the min and max for the 


    // camera width


     servoPosition1 = map(servoPosition1, 0, 179, 78,108);








      //repeat for servo 2


      if (startbyte == 254) {  


      // then get the next two bytes  


      for (i=0;i<2;i++) {  


        userInput[i] = Serial.read();  





      int servo2 = userInput[0];  


    // second byte = which position? 


    int servoPosition2= userInput[1];

    Serial.print("Servo: " ); 


    Serial.print(" Move: ");


    servoPosition2 = map(servoPosition2, 119, 1, 54, 78);











I need to neaten the code up a bit and correct an error with recognising which server to move, but it works. 


Here is the processing code: 

import fullscreen.*;


import processing.serial.*;

import processing.video.*; 

 FullScreen fs; 

Serial port;

//set up a few settings for the gui. you need to change this to the

// screen resolution you are using

int scrnWidth=1024; //width of screen, full screen comming soon!!

int scrnHeight=768; //height of screen 

int camSizeX=640; //width of cam box

int camSizeY=480; //height of cam box


// layout settings. 

int leftMargin = round((scrnWidth - camSizeX) / 2);


int camPosX=leftMargin;//x coordinate of top left corner of camera box

int camPosY=0;//y coordinate of top left corner of camera box

int textOffsetX=leftMargin + 0;

int textOffsetY = camSizeY + 5;


// serial in variables to hold any values given back from the arduino 

String returnText="";



 Serial myPort;  // The serial port

Capture cam;

int inByte =0;

int read=0;

void setup()


    size(scrnWidth, scrnHeight);

    // Create the fullscreen object

   // fs = new FullScreen(this); 


    // enter fullscreen mode

   //  fs.enter();




  cam = new Capture(this, camSizeX, camSizeY);


 //set up the text settings



  //sets the port to the one your arduino is using

  myPort  = new Serial(this, "COM3", 9600);  




void draw()



  PFont font;

  font = loadFont("Verdana-48.vlw"); 



 background(32, 62, 22);



  camDisplay(); //put cam on screen


   mousePos(); // put mouse pos on screen






 while (myPort.available() > 0) {

     int gb = myPort.read();

   char fg = char(gb);



     String inBuffer = myPort.readString();   

    if (inBuffer != null) {





  // text("Recieved", 5, 482);

  //text(inByte,  220, 482);






void mousePressed() {

      fill(6, 191, 41);

      int posNewX = round( 179 - (mouseX  - 190) / 3.6 ) ;

      int posNewY =mouseY / 4;




      char c = char(255);





      text( "Here:" + posNewX, 5, 560);



      char d = char(254);





      text( posNewY, 5, 540);






void mousePos(){


fill(6, 191, 41);


text("mouseX: " + mouseX + " / " + "mouseY" + mouseY, textOffsetX, camSizeY-10); 

//text(mouseX, 210, 510);

int msPo=179 - round(mouseX / 3.6);

text("sent " + msPo, textOffsetX, camSizeY + 20);

text(returnText,  textOffsetX, camSizeY + 40);

//text("mouseY", 5, 441); 

//text(mouseY, 210, 441);




 void camDisplay(){


   if (cam.available() == true) {


    image(cam, camPosX, camPosY);

    // The following does the same, and is faster when just drawing the image

    // without any additional resizing, transformations, or tint.

    //set(160, 100, cam);






 void guideLines(){

   stroke(240, 17, 17);

 line(78, 0, 78, scrnHeight);

 line(108, 0, 108, scrnHeight);




 void drawGrid(){

   stroke(36, 137, 48);

for (int i = 10; i < scrnWidth; i+=10) {

     line(i, 00, i, scrnHeight);


    //line(i, 0, i, 150);


  for (int i = camPosY; i < camPosY + camSizeY + 10; i+=10){

     //ne(0, i, scrnWidth, i);

     line(camPosX, i, camSizeX, i );


    //line(i, 0, i, 150);




To get processing to pic up my cam i had to install vdig, there are ways to do it without vdig though, see the processing.org site for details.


As soon sd my cat gets in i will post a video , in the meantime im going to tidy my code up. 



Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.

my cat goes MAD when it sees a laser point, it will never stop chasing it no matter how long it tries :P... oh and nice work!