Donnerstag, 30. Oktober 2014

CD-Roboter als Linienverfolger


Das CD-Roboter-Prototyp hat heute die erste Probefahrt bestanden. Mit einem Aufsatz vorne bestehend aus zwei Photowiderständen, einem hellen LED und drei Widerständen konnte ich den Roboter mit der Linienverfolgefunktion ausstatten. Die Photowiderstände waren leider nicht vom gleichen Typ, so musste ich etwas messen und ausprobieren. Viele Schaltungen für die Liniendetektion benutzen Potentiometer. Ich hatte gerade keine zur Hand, aber Arduino kann ja auch selbst ausrechnen, was der Unterschied zwischen hell und dunkel ist. Wichtig ist nur, dass die Photowiderstände in einem möglichst linearen Bereich zwischen dem hellen und dunkleren Bereichen arbeiten.

Als Spannungsteiler nahm ich etwa gleich große Widerstandswerte, wie die Werte der LDRs bei dunkel.
Das LED befindet sich in der Mitte zwischen beiden LDRs. Diese Positionierung ist gut geeignet für eine helle Linie auf dunklem Hintergrund.


Erstellt mit Circuit-Lab
Vor der Fahrt wird der Roboter kalibriert. Nach dem ersten Blinken hat man 2 Sekunden Zeit den Roboter auf die Linie zu stellen. Die Helligkeit der Linie wird gemessen. Danach blinkt es 2-mal - man sollte den Roboter auf den Hintergrund stellen. Es wird die Helligkeit des Hintergrundes gemessen. Danach folgt 3-mal Blinken und nach 3 Sekunden (Zeit um den Roboter wieder auf die Linie zu stellen) fährt der Roboter los.

Auf dem Video sieht man, dass der Roboter die Linie aus der Mitte selbstständig findet. Leider hatte ich gerade keine dunklere Fläche als Pappkarton, so dass die Probefahrt im Dunkeln stattfinden sollte - damit der Kontrast zwischen hell und dunkel ausreichend war.
Das Algorithmus ist sehr einfach. Nach der Kalibrierung wird für jedes LDR ein Threshold für Dunkel ausgerechnet, das von mir willkürlich als die Mitte zwischen Hell- und Dunlkel definiert wurde.
Wenn die Werte beider LDRs unterhalb (hell) des Thresholds liegen, fährt der Roboter vorwärts. Wird an einer Seite dunkler (LDR Wert > Thresholds), gibt es eine leichte Drehung in die entgegengesetzte Richtung. Wenn beide LDRs zu dunkel messen, fährt der Roboter zurück mit leichter Drehung nach rechts.

Hier ist das Arduino -Quellcode:

/*
CD-Roboter Tests
Valentin Heinitz, 2014-10-30
http://heinitz-it.de
Die Software ist Public-Domain.

Einfacher Linienverfolger. Linie ist heller als sonstige Fläche.
Vor der Fahrt erfolgt die Kalibrierung - Aufnahme der Lichtintensitäten über der hellen und dunklen Flächen.

uC: Arduino Nano
Motorentreiber L293D

*/
void motors_stop() {
  digitalWrite(2, HIGH);
  digitalWrite(3, HIGH);
  digitalWrite(4, HIGH);
  digitalWrite(5, HIGH);
}

void motorR_fw() {
  digitalWrite(3, HIGH);
  digitalWrite(2, LOW);
}

void motorL_fw() {
  digitalWrite(4, HIGH);
  digitalWrite(5, LOW);
}

void motorR_bw() {
  digitalWrite(2, HIGH);
  digitalWrite(3, LOW);
}

void motorL_bw() {
  digitalWrite(5, HIGH);
  digitalWrite(4, LOW);
}

void turnRight( int ms)
{
    motorR_bw();
    motorL_fw();
    delay(ms);
    motors_stop();
}

void turnLeft( int ms)
{
    motorR_fw();
    motorL_bw();
    delay(ms);
    motors_stop();
}

void forward( int ms)
{
  int steps = ms/20;
  for( int i=0; i<steps; ++i)
  {
    digitalWrite(6, HIGH);
    delayMicroseconds(10);
    digitalWrite(6, LOW);
    int distance = pulseIn(7, HIGH) / 2;
    if ( distance < 700 )
    {
     
      break;
    }
    else
    {
      motorR_fw();
      motorL_fw();
      delay(20);
    }
  }
  motors_stop();
}

void backward( int ms)
{
    motorR_bw();
    motorL_bw();
    delay(ms);
    motors_stop();
}

int DirMostRight=0;
int DirRight=1;
int DirFront=2;
int DirLeft=3;
int DirMostLeft=4;
int ObstacleRange=700;
int ShortThoughtTime=500;
int LongThoughtTime=2000;
int GoRange=1000;
int ranges[5]={0,0,0,0,0};

const int lrdLeft = A0;
const int lrdRight = A1;

int vLeft = 0;
int vRight = 0;

void checkObstacle()
{
 
  turnRight(200);
  digitalWrite(6, HIGH);
  delayMicroseconds(10);
  digitalWrite(6, LOW);
  ranges[0] = pulseIn(7, HIGH) / 2;
  delay(ShortThoughtTime);
  turnLeft(100);
  digitalWrite(6, HIGH);
  delayMicroseconds(10);
  digitalWrite(6, LOW);
  ranges[1] = pulseIn(7, HIGH) / 2;
  delay(ShortThoughtTime);
  turnLeft(100);
  digitalWrite(6, HIGH);
  delayMicroseconds(10);
  digitalWrite(6, LOW);
  ranges[2] = pulseIn(7, HIGH) / 2;
  delay(ShortThoughtTime);
  turnLeft(100);
  digitalWrite(6, HIGH);
  delayMicroseconds(10);
  digitalWrite(6, LOW);
  ranges[3] = pulseIn(7, HIGH) / 2;
  delay(ShortThoughtTime);
  turnLeft(100);
  digitalWrite(6, HIGH);
  delayMicroseconds(10);
  digitalWrite(6, LOW);
  ranges[4] = pulseIn(7, HIGH) / 2;
  delay(ShortThoughtTime);
  turnRight(200);
}

int vleftRefLine=0;
int vleftRefOffroad=0;

int vrightRefLine=0;
int vrightRefOffroad=0;

int thleft=0;
int thright=0;

void setup() {
  pinMode(2, OUTPUT);
  pinMode(3, OUTPUT);
  pinMode(4, OUTPUT);
  pinMode(5, OUTPUT);
  pinMode(6, OUTPUT);
  pinMode(7, INPUT);
  pinMode(8, OUTPUT);
  motors_stop();
  Serial.begin(9600);          
  Serial.write("CDRobot: Version 0.1\n");
  Serial.write("Copyright: 2014, heinitz-it.de\n");
  //delay(5000);
 
  digitalWrite(8, HIGH); //1-Mal blinken: Aufnahme der Lichtintensitaet auf der Linie (Hell)
  delay(100);     
  digitalWrite(8, LOW);
 
  delay(2000);   
  digitalWrite(8, HIGH);
  delay(300);   
  vleftRefLine = analogRead(lrdLeft); 
  vrightRefLine = analogRead(lrdRight); 
  digitalWrite(8, LOW);
  delay(1000);
 
  digitalWrite(8, HIGH); //2-Mal blinken: Aufnahme der Lichtintensitaet ausserhalb der Linie (dunkler)
  delay(100);     
  digitalWrite(8, LOW);
  delay(100);
  digitalWrite(8, HIGH);
  delay(100);     
  digitalWrite(8, LOW);
 
  delay(2000);
  digitalWrite(8, HIGH);
  delay(300);    
  vleftRefOffroad = analogRead(lrdLeft); 
  vrightRefOffroad = analogRead(lrdRight);
  digitalWrite(8, LOW);
  delay(1000);
 
  digitalWrite(8, HIGH); //3-Mal blinken: Auf die Linie stellen, gleich geht's los
  delay(200);     
  digitalWrite(8, LOW);
  delay(100);
  digitalWrite(8, HIGH);
  delay(200);     
  digitalWrite(8, LOW);
  delay(100);
  digitalWrite(8, HIGH);
  delay(200);     
  digitalWrite(8, LOW);
 
  delay(3000);
 
  thleft = (vleftRefLine -vleftRefOffroad)/2 + vleftRefOffroad;
  thright = (vrightRefLine -vrightRefOffroad)/2 + vrightRefOffroad;
 
  vLeft = analogRead(lrdLeft); 
  vRight = analogRead(lrdRight);
  Serial.print("Lth = " );                      
  Serial.print(thleft);     
  Serial.print("\t Rth = ");     
  Serial.println(thright); 
  digitalWrite(8, HIGH); 
}


void loop()
{
  vLeft = analogRead(lrdLeft); 
  vRight = analogRead(lrdRight);
 
  if( vLeft > thleft && vRight > thright )
  {
    backward(50);
    turnRight(20);
  }
  else if( vLeft > thleft )
  {
     turnRight(30);
  }
  else if( vRight > thright )
  {
     turnLeft(30);
  }
  else
  {
    forward(30);
  }
  delay(10);
}

Sonntag, 19. Oktober 2014

CD-Roboter - ein Lernroboter für 10Euro

Seit einiger Zeit überlege ich mir, welche Baukästen oder fertige Roboter man in einem Kinderkurs für Roboterbau und Programmierung wohl benutzen könnte. Die Aufgaben, die die Kinder und die Jugendlichen in so einem Kurs lösen müssten, wären die gewöhnlichen Standardaufgaben:
  • Eine vorgegebene Route abfahren
  • Eine Linie verfolgen
  • Aus einem Labyrinth entkommen
  • Einem Lichtpunkt nach fahren
Die Lego-Roboter kommen für mich allein aus dem Preisgrund nicht in Frage. Ich habe mir erst die Preisgrenze bis 50Euro gesetzt. Für den Preis eines Lego Baukastens könnte man damit schon 5-6 Roboter anschaffen, was für eine Klasse schon ausreichend wäre.
Mein erster Ansatz war dieser Fahrgestell mit Arduino UNO und dem  Motorentreiber-Board:

Quelle: amazon.de, http://ecx.images-amazon.com/images/I/513vDuODwCL._SX425_.jpg

Von diesem Teil war ich begeistert. Alles zusammen kostete auch etwa zw. 40 und 50 Euro.
Ein 15-jähriger Sohn eines Freundes (meine Söhne sind noch zu klein dafür :-) brauchte weniger als 2 Stunden, um den Roboter aufzubauen. Nach einer Stunde Programmierung fuhr der Roboter schon herum.
Das teuerste an dem Ganzen war allerdings das Fahrgestell - ca. 20 Euro. Auch die Motorentreiber-Platine war für meinen Fall überdimensioniert und zu teuer. Ein L293D wäre für mich völlig ausreichend. Ein weiteres Manko sind die Motoren. Es sind die günstigen und einfachsten DC Motoren, die man bei Pollin.de schon für 50cent bekommt. Die Batterien halten mit solchen Motoren nicht lange.
Das alles wäre noch akzeptabel für einen Kurs. Nur die Erfahrung aus einem anderen Kurs hat gezeigt, die Kinder werden viel mehr motiviert, wenn Sie das, woran sie arbeiten und basteln am Ende des Kurses auch mitnehmen können. So habe ich mir ein neues Ziel gesetzt - Roboter für 10Euro Materialkosten.

Nach einigen Experimenten und durchstöbern der Onlinekataloge kam ich  auf einen Prototyp, der dem Ziel schon sehr naht.

  • Statt UNO kommt jetzt Arduino Nano zum einsatz - 7.0 Eur.
  • Ein L293D dient als Motorentreiber - 1,20
  • Als Motoren dienen die Solarmotoren RF 300 2 x 1,90 Eur
  • Die Lauf- und die Zahnräder sind von Opitec.de - < 1 Eur
  • Das Getriebe wird auf einem Winkelprofil von Hornbach (1,65 pro Meter) aufgebaut. 
  • Als Achsen dienen M3 Schrauben, ebenfalls von Hornbach.
  • Alles wird an 2 alten CD mit Heißkleber befestigt.

Alles in einem unter 15 Euro. Wenn man die Bauteile bei aliexpress.com in größeren Mengen bestellt, kommt man auf deutlich unter 10 Euro!

Die ersten Tests mit dem Prototyp waren recht positiv. Der Roboter ist sehr wendig, die Fahrtgeschwindigkeit (ca 0,5 m/s) ist genau die richtige für die Tests in einem Raum.
Sobald ich mit den Tests und den Verbesserungen fertig bin, werde ich eine detaillierte Beschreibung in weiteren Blogs veröffentlichen. Es gibt noch einiges an der Konstruktion der Getriebe zu verbessern, so dass die Kinder ab 11 Jahren so einen Roboter in etwa 1 Stunde selbständig zusammenbauen könnten.

Zur Programmierung  habe ich Minibloq ausprobiert. Die einfachen Fahrtenprogramme  mit fester Route konnte ich schnell zusammen klicken. Für die Ansteuerung von Sensoren ist allerdings ein Hardwaredefinition-Profil nötig. Sobald ich mir schlüssig bin, welche Sensoren ich für alle Lernziele brauche, werde ich probieren so einen Profil für meinen "CDRoboter" zu erstellen.

Hier sind einige Bilder des Prototyps:



Offensichtlich bin ich nicht der Erste, der nach einem sehr günstigen Lernroboter sucht oder es vor hat, einen zu bauen. Allerdings habe ich meine Preisgrenze von 10 Euro noch bei keinem Modell gesehen.

  • Grove Enterprises LLC beschreibt auf ihrer Seite http://superawesomerobots.com/ ihr Vorhaben, einen Roboterbausatz für 50-70 $ zu entwickeln.
  • MIT hat einen Lern-Roboter für 20$ entwickelt: https://sites.google.com/site/mitprintablerobots/
  • ArduBot ist ein auf einer spezieller Lochrasterplatine aufgebautes Fahrgestell. Die Kosten einer solchen Platine liegen schon bei über 10 Euro. Da komme ich mit zwei zusammen geklebten CDs deutlich günstiger weg.
  • Institut für Robotik und Mechatronik bei DLR hat schon vor einiger Zeit ASURO entwickelt. Preis ca. 50 Euro. ASURO wurde noch in pre-Arduino Zeit geschaffen und nach heutigem Stand der Technik völlig veraltet. Sehr viele diskrete Bauelemente machen den Aufbau nur für geübte Hobbyelektroniker möglich.
  • Die Frima Conrad Elektronik bietet einen ASURO-ähnlichen Bausatz PRO-BOT128 für ebenfalls ca. 50 Euro an. Allerdings kostet die Entwicklungsumgebung noch extra.
  • Die Firma Elenco bietet viele gut aussehende Roboterbausätze mit mMn. wenig didaktischem Nutzen. z.B. dieser Käferroboter. Die Roboter von Elenco haben sehr hochwertige und leicht aufzubauende Mechanik, sind aber nicht programmierbar. Auch die Preise fangen bei einfachsten Modellen mit 20Euro an.
  • Das Frauenhofer Institut hat einige Roboterkurse für die Schulen ausgearbeitet und daraus resultierend als Roberta kommerzialisiert. Die Roboter-Kits basieren auf  Lego - wie originell! Die Initiative wurde anscheinend mit öffentlichen Mitteln finanziert. Die Lernmaterialien kosten ab 40Euro.
  • Bei Kikstarter werden jede Menge Roboterprojekte für Lernkits finanziert. Nun, von Kikstarter sollte man nichts Nützliches und schon gar nichts Gemeinnütziges erwarten. Es ist eine clevere Kampagne, mit der die ganze Welt die US-Startups und die Diplomarbeiten der US-Eliteuniversitäten finanziert.
  • Wenn man bei Amazon nach "robot chassis" sucht, findet man einige günstige Fahrgestelle mit Rädern und Motoren, die man zusammen mit einem Arduino relativ einfach zu einem Roboter ausbauen kann. Man kommt allerdings nicht unter 30 Euro aus. Interessanterweise kosten die Chassis bei dem Chinesischen Amazon-Pendant Ali Express nicht weniger. Dagegen kosten die Motoren und Getriebe (eigentlich die Hauptteile eines Chassis) als Einzelteile nur einen Bruchteil von dem, was man bei Amazon zahlt.

P.S.:
Nachdem ich diesen Beitrag schon geschrieben habe, kam ich auf eine hervorragende Seite eines Bastlers. Er baute seinen Roboter ebenfalls auf einer CD auf. Es gibt viel auf dieser Seite zu lernen und viele Ideen abzugreifen.: http://www.ermicro.com/blog/?p=983
Der Autor beschreibt seine Projekte immer sehr ausführlich mit Quellcode, Schaltplänen und den mechanischen Bauplänen. Jenseits der Technik, gibt es auf seiner Seite oft interessante Gedanken und Informationen rund um das Thema des Projekts. So habe ich zum Beispiel erfahren, dass der erste Roboter in der Klasse bereits in 1949 gebaut wurde: http://www.ias.uwe.ac.uk/Robots/gwonline/gwonline.html