Rolly Bot

I got this totally simple robot running. All it is, is an Arduino, two servos and an IR receiver.

What other sensors to add to make it interesting?

http://inventorartist.com/rolly-bot/

Issues:

The servos aren't even. They often drift when it's sitting.

The servo power isn't even. It doesn't go straight when commanded the same power to each servo for instance...

Thanks for any ideas...

A "continuous revolution" 'servo' has the feedback loop removed, thus reducing it to a gear motor with ESC (Electronic Speed Control). You will need to experimentally determine the middle of the ESC 'dead' zone to get them to stop. It will probably be different for each servo. Then you need to tune the speed values to match the speeds closely. You mat want to switch from .write(0 through 180) to .writeMicroseconds(1000 through 2000) to get more precise control.

You could add rotation feedback on the wheels to get more precise control.

You can get sonar range finders for under $2 each (http://www.fasttech.com/product/1012007) if you want your robot to sense its surroundings.

Nice and simple. Cheap too to run on carpet or grass.

Going to build this, only slightly bigger, so a 7.2 Volt RC battery will fit. Will use a Pro Mini and have a 5 Volt regulator for servo power.

The servos aren’t even. They often drift when it’s sitting.

You will probably get more control of the servos using writeMicroseconds. If you made your own continuous rotation servos, you might send the servos a 1500us signal, then tweak the pot (if available) such that the servo will not rotate. If drift continues to be a problem, you probably can use the servo detach function to stop the servo rotation. Below is some servo test code that includes the detach function.

// zoomkat 12-25-13 serial servo test
// type servo position 0 to 180 in serial monitor
// or for writeMicroseconds, use a value like 1500
// Send an a to attach servo or d to detach servo
// for IDE 1.0.5 and later
// Powering a servo from the arduino usually *DOES NOT WORK*.

#include <Servo.h> 
String readString; //String captured from serial port
Servo myservo;  // create servo object to control a servo 
int n; //value to write to servo

void setup() {
  Serial.begin(9600);
  myservo.writeMicroseconds(1500); //set initial servo position if desired
  myservo.attach(7, 500, 2500);  //the pin for the servo control, and range if desired
  Serial.println("servo all-in-one test code 12-25-13"); // so I can keep track of what is loaded
  Serial.println();
}

void loop() {
  while (Serial.available()) {
    char c = Serial.read();  //gets one byte from serial buffer
    readString += c; //makes the string readString
    delay(2);  //slow looping to allow buffer to fill with next character
  }

  if (readString.length() >0) {
    Serial.println(readString);  //so you can see the captured string 

      // attach or detach servo if desired
    if (readString == "d") { 
      myservo.detach(); //detach servo
      Serial.println("servo detached");
      goto bailout; //jump over writing to servo
    }
    if (readString == "a") {
      myservo.attach(7); //reattach servo to pin 7
      Serial.println("servo attached");
      goto bailout;
    }    

    n = readString.toInt();  //convert readString into a number

    // auto select appropriate value
    if(n >= 500)
    {
      Serial.print("writing Microseconds: ");
      Serial.println(n);
      myservo.writeMicroseconds(n);
    }
    else
    {   
      Serial.print("writing Angle: ");
      Serial.println(n);
      myservo.write(n); 
    }

bailout: //reenter code loop
    Serial.print("Last servo command position: ");    
    Serial.println(myservo.read());
    Serial.println();
    readString=""; //empty for next input
  }
}

Thanks! I think the detach() method will cure the drift...

for the uneven power, I'll tinker some more... perhaps a sensor or a multiplier for the power level...

Thanks! I think the detach() method will cure the drift...

What I did: remove servoRight.attach(9); and servoLeft.attach(10); from void.setup() Put servoRight.attach(9); and servoLeft.attach(10); in all movement commands. Put servoRight.detach(); and servoLeft.detach(); in the stop command. Works like a charm.

Working on accelerator buttons now.

Any pictures or video of yours? I'd love to post them if you don't have a site...

@inventorArtist;
I will post them and the code when i tidy up the wiring a bit and mount the boards and battery properly.
I have the accelerator working, Had to change speed to only + numbers and use direction to turn and reverse.
Also using microseconds for speed = stop 1500 ~ 1620 fast.
It has 6" wheels and the frame is 1.5 x 6.5" so a 7.2V RC battery will fit. All of 1/8" plywood.
It’s using a Arduino Pro Mini and a home made breakout board for standard servos and power supply.

Here is the code, subject to change.

/* Rolly_Robot Pro Mini 18 July 2014 JDS

IR Codes for DVR Remote
16720350 MULT
16763190 POWER
16716270 SEARCH
16714230 |<
16718310 ||<
16724430 |>
16728510 >||
16726470 >>
16761150 >|
16771350 ADD
16746870 FN
16742790 MENU
16767270 LEFT
16750950 RIGHT
16755030 UP
16734630 DOWN
16769310 1
16736670 2
16752990 3
16765230 4
16732590 5
16748910 6
16773390 7
16740750 8
16757070 9
16730550 0
16738710 ESC
16722390 -/--
Repeat 4294967295

Left servo pin 10
Right servo pin 11
IR is on pin 12

 The IR sensor's pins to Arduino like so:
 Pin 1 to Vout (pin 12 on Arduino)
 Pin 2 to GND
 Pin 3 to Vcc (+5v from Arduino)
*/

#include <IRremote.h>
#include <Servo.h>

int IRpin = 12;  // pin for the IR sensor
int LED = 13;    // LED pin
IRrecv irrecv(IRpin);
decode_results results;
unsigned long PrevResult;

Servo servoRight;
int servoRightZero = 1500;
int servoRightDirection = -1;

Servo servoLeft;
int servoLeftZero = 1500;
int servoLeftDirection = 1;

int Speed = 50;
int rightSpeed = 0;
int leftSpeed = 0;

void setup() {
  irrecv.enableIRIn(); // Start the receiver
  Serial.begin(9600);
}
void loop() {
  digitalWrite(LED, LOW);
  if (irrecv.decode(&results))
  { Serial.println(PrevResult);
    digitalWrite(LED, HIGH);
    switch (results.value)
    {
      case 16755030://forward
        PrevResult = 16755030;
        servoRight.attach(11);
        servoLeft.attach(10);
        Serial.println("Forward");
        servoRightDirection = -1;
        servoLeftDirection = 1;
        rightSpeed = Speed;
        leftSpeed = Speed;
        break;

      case 16742790://stop
        PrevResult = 16742790;
        Serial.println("Stop");
        //rightSpeed = 0;
        //leftSpeed = 0;
        servoRight.detach();
        servoLeft.detach();
        break;

      case 16734630://backward
        PrevResult = 16734630;
        servoRight.attach(11);
        servoLeft.attach(10);
        Serial.println("Backward");
        servoRightDirection = 1;
        servoLeftDirection = -1;
        rightSpeed = Speed;
        leftSpeed = Speed;
        break;

      case 16767270://left
        PrevResult = 16767270;
        servoRight.attach(11);
        servoLeft.attach(10);
        Serial.println("Left turn");
        rightSpeed = Speed;
        leftSpeed = Speed / 2;
        break;

      case 16750950://right
        PrevResult = 16750950;
        servoRight.attach(11);
        servoLeft.attach(10);
        Serial.println("Right turn");
        rightSpeed = Speed / 2;
        leftSpeed = Speed;
        break;

      case 16771350://ADD
        PrevResult = 16771350;
        servoRight.attach(11);
        servoLeft.attach(10);
        Serial.println("Left Dime");
        servoRightDirection = -1;
        servoLeftDirection = -1;
        rightSpeed = Speed;
        leftSpeed = Speed;
        break;

      case 16746870://FN
        PrevResult = 16746870;
        servoRight.attach(11);
        servoLeft.attach(10);
        Serial.println("Right Dime");
        servoRightDirection = 1;
        servoLeftDirection = 1;
        rightSpeed = Speed;
        leftSpeed = Speed;
        break;

      case 16718310://||< Slower
        PrevResult = 16718310;
        Serial.print("Slower ");
        if (Speed >= 10)
        {
          Speed = Speed - 10;
        }
        rightSpeed = Speed;
        leftSpeed = Speed;
        Serial.println(Speed);
        break;

      case 16726470://>> Faster
        PrevResult = 16726470;
        Serial.print("Faster ");
        if (Speed < 120)
        {
          Speed = Speed + 10;
        }
        rightSpeed = Speed;
        leftSpeed = Speed;
        Serial.println(Speed);
        break;
        
      case 4294967295:// repeat
        if (PrevResult == 16718310) //slower
        {
          if (Speed >= 10)
        {
          Speed = Speed - 10;
          delay(250);//blocking delay to slow speed change
        }
        rightSpeed = Speed;
        leftSpeed = Speed;
        }
        
        if (PrevResult == 16726470) //faster
        {
          if (Speed < 120)
        {
          Speed = Speed + 10;
          delay(250);//blocking delay to slow speed change
        }
        rightSpeed = Speed;
        leftSpeed = Speed;
        }
        break;
    }

    servoLeft.writeMicroseconds(servoLeftZero + leftSpeed * servoLeftDirection);
    servoRight.writeMicroseconds(servoRightZero + rightSpeed * servoRightDirection);

    irrecv.resume();
  }
}

Video: http://youtu.be/yoWkaAfGMZc

Wow! I love it! Yours works great! I'm just making another since my friend wanted mine. :)

Wow! I love it! Yours works great! I'm just making another since my friend wanted mine.

Thank You for the design, it's cool and different and for posting on your web page. http://inventorartist.com/rolly-bot/

You’re most welcome, I’m really happy someone likes the design. :slight_smile:

I’m making another one!

I managed to catch a video of it bouncing off the wall by the way. It’s a cool “feature”. :slight_smile:

I made another one with a bunch of little improvements.

I even made a program that can have smooth actions. For instance there is a stop button that brings the speed down gradually to zero.

http://inventorartist.com/rolly-bot/

If anybody wants one I'd be glad to run the parts off on my cnc....

Cool. I made another one. It's a Flatpack, 4 leg walker. The dog gos nuts when it's walking around on the floor. I guess it's the noise it makes walking, kinda loud.

I just went to your youtube channel looking for a video...

Do you have a Web site?

It's not there yet. Just YouTube and FaceBook. I don't use Keek or Twitter any more.