0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« on: March 11, 2007, 09:34:25 am » |
I built a roving robot, I call it "Marvin" since it just drives around and not do anything apart from occasionally colliding into stuff. It uses a ultrasonic sensor for distance, two converted servos for driving the wheels, and another servo for rotating the sensor. Here's a picture:  And a video clip of it in action with an old navigation algorithm:
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Newbie
Karma: 0
Posts: 5
Arduino rocks
|
 |
« Reply #1 on: March 30, 2007, 06:34:24 am » |
Hi i need your help ... do u have any example codes to move a servo up n down ? like if i press A the servo will go UP n when i press S the servo will go down ... Thnx
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« Reply #2 on: April 07, 2007, 02:47:55 pm » |
I can give you the code, but I think this explains it better than my uncommented code: http://todbot.com/blog/wp-content/uploads/2006/10/arduino_spooky_projects_class3.pdfI also read somewhere in the forum that someone posted a way of driving two servos with the PWM pins, but I can't seem to find the post. Search servo in the forum see if you can find it. -Z-
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Jr. Member
Karma: 0
Posts: 56
|
 |
« Reply #3 on: August 06, 2007, 07:11:43 pm » |
Could you give more information about the servors and the sensor that you use for your robot ?
|
|
|
|
|
Logged
|
|
|
|
|
Sweden
Offline
Newbie
Karma: 0
Posts: 27
Arduino really rocks
|
 |
« Reply #4 on: August 15, 2007, 08:16:26 am » |
Yeah! Nice work man! Im building robots aswell so it's great to see someone else that does here too. I like how the robot feels so alive and active when it moves. It's not a rigid kind of movement. Could you give more information about the servors and the sensor that you use for your robot ? Lets see if i can help you... The sensor is an ultrasonic sensor. It provides the robot a range sensing and gives a higher input the farer away the detected oblect is. The servos seems to be of standard size, where the two driving servos have been modified to be continous driving. An unmodified servo is restricted to about 180 degrees movement and can be positioned in a specific degree. What else do you need to know?
|
|
|
|
« Last Edit: August 15, 2007, 08:17:30 am by Fredrik_Andersson »
|
Logged
|
|
|
|
|
0
Offline
Jr. Member
Karma: 0
Posts: 56
|
 |
« Reply #5 on: August 19, 2007, 03:45:12 am » |
Lets see if i can help you...
The sensor is an ultrasonic sensor. It provides the robot a range sensing and gives a higher input the farer away the detected oblect is.
The servos seems to be of standard size, where the two driving servos have been modified to be continous driving. An unmodified servo is restricted to about 180 degrees movement and can be positioned in a specific degree.
What else do you need to know? It should be ok. I will try to do that and I will post the result later.
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« Reply #6 on: August 20, 2007, 04:42:03 pm » |
Sorry I've been too busy with my uni project to browse the arduino forums lately. Fredrik, thanks for the answer, you are exactly right! I bought my ultrasonic sensor here: http://www.sparkfun.com/commerce/product_info.php?products_id=639I've connected the analog output directly to an analog-in to read the distance. Good luck! -Z-
|
|
|
|
« Last Edit: August 20, 2007, 04:42:12 pm by zitron »
|
Logged
|
|
|
|
|
0
Offline
Newbie
Karma: 0
Posts: 4
Arduino rocks
|
 |
« Reply #7 on: August 24, 2007, 06:10:12 am » |
The ultrasonic sensor on a servo is an awesome idea. I just my steal it someday :-*
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« Reply #8 on: August 27, 2007, 04:20:35 am » |
The ultrasonic sensor on a servo is an awesome idea. I just my steal it someday :-* It wasn't my idea, I stole it from someone else  .
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Jr. Member
Karma: 0
Posts: 56
|
 |
« Reply #9 on: August 27, 2007, 04:32:46 am » |
what is the type of servo motor ? Do you have the schema of your circuit ? What is the goal of the capacitor ?
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« Reply #10 on: October 07, 2007, 06:45:34 am » |
#define LeftWheelPin 6 #define RightWheelPin 5 #define ArmServoPin 4 #define SonarPin 0
#define runningLED 2 #define errorLED 7
short ArmAngle, dAngleMax,dAngleMin, dAngleMaxTemp, dAngleMinTemp; short ArmAngleRange, ArmAngleTarget; short LeftSpeed; short RightSpeed; short ArmTrim = 0; int distance, dmax, dmin, dmaxtemp, dmintemp;
unsigned long lastPulseL; unsigned long lastPulseR; unsigned long lastPulseA;
int i, k; unsigned short refreshTime = 15; unsigned long timeLast, timeLastFast; unsigned long timeLastSlow; unsigned int timeStart;
// --------------------------------------------------- LED flashing void flashLED(short pin, short times) { for (i = 0; i<=times; i++) { digitalWrite(pin, HIGH); delay(100); digitalWrite(pin, LOW); delay(500); } }
// ---------------------------------------------------- Refreshes all servo pulses void updateServos() {
if (millis() - lastPulseL >= refreshTime) { digitalWrite(LeftWheelPin, HIGH); delayMicroseconds((LeftSpeed+90)*11+500); digitalWrite(LeftWheelPin, LOW); lastPulseL = millis(); }
if (millis() - lastPulseR >= refreshTime) { digitalWrite(RightWheelPin, HIGH); delayMicroseconds((-RightSpeed+90)*11+500); digitalWrite(RightWheelPin, LOW); lastPulseR = millis(); }
if (millis() - lastPulseA >= refreshTime) { digitalWrite(ArmServoPin, HIGH); delayMicroseconds((ArmAngle+ArmTrim+90)*11+500); digitalWrite(ArmServoPin, LOW); lastPulseA = millis(); }
} // end updateServos
// ----------------------------------------------------- Rover move and turn function void move(int speed, int turnSpeed) { //LeftSpeed = speed - turnSpeed; //RightSpeed = speed + turnSpeed;
if (LeftSpeed < 30 && LeftSpeed < (speed - turnSpeed)) { LeftSpeed++; //LeftSpeed = ((LeftSpeed*10)+1)/10 } else if (LeftSpeed > -30 && LeftSpeed > (speed - turnSpeed)) { LeftSpeed--; //LeftSpeed = ((LeftSpeed*10)-1)/10; }
if (RightSpeed < 30 && RightSpeed < (speed + turnSpeed)) { RightSpeed++; } else if (RightSpeed > -30 && RightSpeed > (speed + turnSpeed)) { RightSpeed--; }
//if (speed == 0 && turnSpeed == 0) { // LeftSpeed = 0; // RightSpeed = 0; //} } // End move
// -------------------------------------------------- Update ArmAngle void armturn() {
if (ArmAngle < 90 && ArmAngle < ArmAngleTarget) { ArmAngle = ArmAngle ++; } else if (ArmAngle > -90 && ArmAngle > ArmAngleTarget) { ArmAngle = ArmAngle --; } }
// ------------------------------------------------- sonar distance function long ping() { long raw;
raw = analogRead(SonarPin)+analogRead(SonarPin)+analogRead(SonarPin)+analogRead(SonarPin); raw = raw/4; return raw + raw*123/512; }
// -------------------------------------------------- Main navigation function void roving() { int speed, turn; randomSeed(millis()); if (dmax > 300 && abs(dAngleMax) < 10) { ArmAngleRange = 15; speed = 20; turn = -dAngleMax; } else if (dmax > 60) { ArmAngleRange = 60; speed = 16; turn = -dAngleMax/4; } else if (dmax > 30) { ArmAngleRange = 70; speed = dmax/5 - 6; turn = -dAngleMax/24; } else if (dmax <= 30) { ArmAngleRange = 80; speed = 0; turn = -dAngleMax/20; digitalWrite(runningLED, HIGH); } if ((dmin <= 19)&&(abs(dAngleMin)<60)) { ArmAngleRange = 80; digitalWrite(errorLED, HIGH); speed = -4; if (dAngleMin !=0) { turn = dAngleMin/20; } else { if (random(0,1)) { turn = -2; } else { turn = 2; } } } /* else { move(0,0); flashLED(errorLED,5); } */ move(speed, turn); }
void setup() { pinMode(LeftWheelPin, OUTPUT); pinMode(RightWheelPin, OUTPUT); pinMode(ArmServoPin, OUTPUT); pinMode(errorLED, OUTPUT); pinMode(runningLED, OUTPUT); pinMode(SonarPin, INPUT); Serial.begin(9600);
LeftSpeed = 0; RightSpeed = 0; ArmAngleRange = 80; ArmAngleTarget = 80; distance = 50; dmaxtemp = 20; dmintemp = 1000;
flashLED(runningLED,5);
timeStart = millis();
move(0,0); }
// -------------------------------------------------- Main Loop void loop() {
digitalWrite(errorLED, LOW);
if (millis() - timeLast > 100) { distance = ping(); if (distance < dmintemp) { dmintemp = distance; dAngleMinTemp = ArmAngle; } if (distance > dmaxtemp) { dmaxtemp = distance; dAngleMaxTemp = ArmAngle; } roving(); timeLast = millis(); updateServos(); }
if ((millis() - timeLastSlow > 500) && (abs(ArmAngle) >= abs(ArmAngleTarget))) { if (ArmAngleTarget > 0) { ArmAngleTarget = ArmAngleRange*-1; } else { ArmAngleTarget = ArmAngleRange; } dAngleMax = dAngleMaxTemp; dAngleMin = dAngleMinTemp; dmax = dmaxtemp; dmin = dmintemp; dmaxtemp = 10; dmintemp = 1000; /* Serial.print("Angles: "); Serial.print(dAngleMax,DEC); Serial.print(", "); Serial.print(dAngleMin,DEC); Serial.print(" - Distances: "); Serial.print(dmax,DEC); Serial.print(", "); Serial.println(dmin,DEC); */ timeLastSlow = millis(); updateServos(); }
if (millis() - timeLastFast > 4) { armturn(); timeLastFast = millis(); }
//updateServos(); //Serial.println(distance,DEC); digitalWrite(runningLED, LOW);
updateServos(); }
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« Reply #11 on: October 07, 2007, 06:49:21 am » |
This code is more "advanced" than the one used in the video. Basically every time the sonar servo completes a sweep, the angle for the direction with the maximum distance is determined, and the robot tries to turn in that direction. The direction with the minimum distance is also determined, and the rover tries to turn away from that direction.
-Z-
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Jr. Member
Karma: 0
Posts: 56
|
 |
« Reply #12 on: October 14, 2007, 08:47:03 am » |
This code is more "advanced" than the one used in the video. Basically every time the sonar servo completes a sweep, the angle for the direction with the maximum distance is determined, and the robot tries to turn in that direction. The direction with the minimum distance is also determined, and the rover tries to turn away from that direction.
-Z- How do you do to synchronize the servo of your sensor ? After few seconds, the angle of mine is not respected... It starts to go more on the right a little bit and it difficult to calibrate it. After three minutes, it is not anymore in the good direction.
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Full Member
Karma: 0
Posts: 221
|
 |
« Reply #13 on: October 14, 2007, 03:46:27 pm » |
This code is more "advanced" than the one used in the video. Basically every time the sonar servo completes a sweep, the angle for the direction with the maximum distance is determined, and the robot tries to turn in that direction. The direction with the minimum distance is also determined, and the rover tries to turn away from that direction.
-Z- How do you do to synchronize the servo of your sensor ? After few seconds, the angle of mine is not respected... It starts to go more on the right a little bit and it difficult to calibrate it. After three minutes, it is not anymore in the good direction. What do you mean? The servo driving the sonar is just a normal servo controlled through PWM, I've never needed to calibrate it. I check the angle of the sonar just by knowing the angle I'm telling the servo to point. The angle is probably not 100% accurate, but the robot only needs a rough idea which direction is clear of stuff. -Z-
|
|
|
|
|
Logged
|
|
|
|
|
0
Offline
Jr. Member
Karma: 0
Posts: 56
|
 |
« Reply #14 on: October 14, 2007, 05:38:34 pm » |
Ok I know why I have a problem with my servo. My servo has a continuous rotation. So it is difficult to know exactly where is the servo after few moments.
|
|
|
|
|
Logged
|
|
|
|
|
|