Raspberry Pi Roboter: Automatisch Hindernissen ausweichen (Teil 4)

13. Januar 2017
29 Comments

Unser Roboter kann inzwischen schon einiges und selbst ferngesteuert werden. Jedoch wollen wir zusätzlich einen Autopilot Modus erstellen, wodurch der Raspberry Pi Roboter selbstständig seinen Weg suchen kann. Putzroboter u.ä. nutzen vergleichbare Methoden, um nicht an einem Hindernis stecken zu bleiben.

Wir nutzen dafür einen Servo Motor und einen Ultraschallsensor, womit wir die Entfernung messen. Anschließend erweitern wir den bisherigen Code und lassen den Roboter dorthin fahren, wo am meisten Platz ist.

 

 

Zubehör

Diese Erweiterung setzt im Grunde nur auf zwei Komponenten, nämlich den Motor zum Drehen und außerdem auf das Ultraschall Modul zum Bestimmen der Entfernung. Insbesondere habe ich diese Teile verwendet:

Daneben brauchen wir außerdem noch die Jumper Kabel, Heißkleber und evtl. noch das Breadboard.

 

 

Befestigung des Motors und Ultraschallsensors

Bevor wir mit dem Anschluss fortfahren, müssen wir die beiden Module an der Roboter Karosserie befestigen. Dafür nutzen wir den Heißkleber, womit wir zuerst den Servo Motor an der Vorderseite (über dem Vorderrad und vor den IR Line-Follow Sensoren). Meine Karosserie hatte einen Papierüberzug über dem Plastik, welchen ich an der zu klebenden Stelle entfernt habe, damit der Kleber besser haftet.

Anschließend habe ich einen der beigefügten Aufsätze des Servomotors genommen und darauf das HC-SR04 Modul mit Heißkleber befestigt (siehe Bilder). Der Aufsatz lässt sich außerdem einfach auf dem Motor fixieren und auch wieder abnehmen. Die Kabel des Servos kannst du an der unteren Seite der Karosserie zum Pi führen (in der Mitte befindet sich ein Loch). Die Jumperkabel vom Ultraschallsensor habe ich zusammengeklebt und mit ein wenig Spielraum an einer Stelle befestigt. Diesen Schritt solltest du allerdings noch abwarten, bis wir die Funktionalität testen und damit auch die beste Position der Kabel finden.

 

Aufbau und Verkabelung

In den vorherigen Tutorials haben wir einige der GPIOs bereits mit den bisherigen Modulen belegt. Für dieses Tutorial benötigen wir jedoch nur drei zusätzliche GPIOs, wobei ich GPIO12, 13 (US Sensor) und 22 (Servo) verwende. Falls du andere IO Pins nutzen willst, musst du dies im Code später auch entsprechend anpassen.

Das Ultraschallmodul wird über die 5V des Pi’s mit Strom versorgt, wohingegen der Servomotor über die Batterien angeschlossen werden sollte. Masse / Ground vom Raspberry Pi und den Batterien sind (wie bisher auch) weiterhin miteinander verbunden.

Raspberry Pi Roboter Servo + Ultraschall Steckplatine

Neben den bisher angeschlossenen Modulen, kommen Servomotor und Ultraschallsensor (links) dazu.

Der Ultraschallsensor (ECHO) ist über einen 330Ω Widerstand an GPIO13 angeschlossen und außerdem über einen 10kΩ Widerstand an GND. Die genaue Funktionsweise des US Sensors habe ich bereits in einem vorherigen Tutorial beschrieben. Ebenso sieht es auch mit der Verwendung des Servomotors mittels PWM aus.  Details zu beiden Modulen findest du dafür auch in den entsprechenden Tutorials.

 

Raspberry Pi Roboter Code erweitern

Um im Folgenden Distanzen von verschiedenen Richtungen aus messen zu können, erstellen wir eine neue Datei, in welcher wir für das bewegliche Ultraschallmodul eine Klasse definieren:

sudo nano ultrasonic.py

Die Klasse hat nur wenige Funktionen (zum rotieren und messen) und fällt deshalb nicht all zu lang aus:

Gespeichert wird im Editor wie immer mit STRG+O und geschlossen mit STRG+X.

Bevor wir fortfahren wollen wir den Ultraschallsensor noch richtig positionieren. Dazu kannst du testweise die Python Konsole öffnen (sudo python) und folgende Zeilen eingeben (geschlossen wird mit exit()):

Wir lassen den Servo Motor also um 90° rotieren und fixieren nun das Ultraschall Modul mittig auf dem Servomotor, sodass die „Augen“ direkt nach vorne schauen. Das machen wir, da der Motor gleich jeweils 90° nach links und recht rotieren wird und dabei die Entfernungen misst, auf welche wir daraufhin  den Roboter reagieren lassen.

Anschließend müssen wir unsere bisherige robot.py Datei noch erweitern. Dafür importieren wir am Anfang die gerade erstellte Klasse:

Außerdem muss die Klasse initiliaisert werden. In der robot.py Datei, ergänzen wir die die Parameter der __init__ Funktion und fügen eine Zeile hinzu, sodass die Funktion folgend aussieht:

Nun können wir die Funktion, die auf die gemessenen Distanzen reagiert und den Roboter entsprechend steuert, am Ende unserer Robot-Klasse anlegen:

 

Autopilot testen

Es wird Zeit den Autopilot Modus zu testen, weshalb wir eine kleine Testdatei erzeugen, in der die Roboter-Klasse geladen wird und der Ultraschall-Autopilot gestartet wird:

sudo nano test_us.py

Die Datei enthält lediglich folgenden Inhalt:

Nachdem die Datei gespeichert wurde, platzieren wir den Roboter auf dem Boden und rufen die Python Datei von der Konsole aus auf (abgebrochen werden kann mit STRG+C):

sudo python test_us.py

Wichtig: Falls dein Roboter sich zu schnell oder zu langsam dreht, liegt das aller Wahrscheinlichkeit nach an einer falsch eingestellten Geschwindigkeit. Im ersten Tutorial der Reihe haben wir bereits u.a. die Geschwindigkeit auf einer Geraden (DIST_PER_SEC) und für eine Drehung (SEC_PER_TURN) definiert. Da diese jedoch vom Untergrund abhängig ist, muss sie ggf. angepasst werden. Ich hatte z.B. beim Testen die Geschwindigkeit auf dem Tisch gemessen, welche aber von der tatsächlichen Geschwindigkeit auf dem Fußboden abweicht, weshalb erst eine Anpassung die Funktionen richtig arbeiten ließ.

 

Weiter geht es mit dem Folgen der eigenen Stimme.

29 Kommentare

  1. Hallo,

    eines ist mir noch nicht klar, wo sind der Raspi und das Steckbord?
    Beide müssen doch auf dem „Wagen“ untergebracht sein?

    Danke und beste Grüße
    Hans

    Antworten
  2. Hallo Felix,

    Bin ein großer Fan deines Blogs. Aber der 10 KOhm als Spannungsteiler mit 330 Ohm kann nicht funktionieren. Die 330 Ohm und die 470 Ohm sind da eine bessere Alternative.

    Antworten
  3. Hallo Felix,

    ich habe da ein Problem. Habe alles wie auf dem Schaltplan beschrieben angeschlossen und die Datei ausgeführt. Der Servokopf dreht sich nach links und rechts um jeweils 90°.
    Ist es normal, dass der sich permanent dreht?
    Leider fährt der Roboter überall gegen die Möbel, weißt du evtl. woran das liegen könnte? Der Roboter macht keine Anstalten auszuweichen und fährt beliebig links und rechts, recht planlos 🙁 leider.

    Antworten
  4. Hallo Felix, Hallo Klaus
    Bei mir war es das gleiche Problem. Tausch mal den 10K gegen 470R und du wirst sehen das es klappt.Am 10K Widerstand fallen 4,84V an die an den 3,3V Raspi Eingang gehen, das ist zuviel.
    lg
    Harald

    Antworten
    • Es scheint hier auch unterschiedliche Module zu geben: Bei einigen ist ein 470k Ohm Widerstand ausreichen, bei anderen wird widerum ein 10k Ohm Widerstand benötigt.

      Antworten
    • Hallo Harald Frenzen,

      danke für den Tip. Das werde ich demnächst mal probieren, sobald ich einen passenden Widerstand habe. Hast du den Roboter auch wie im ersten Teil des Tutorials beschrieben kalibriert? (Das müsste ich evtl. nochmal machen)
      Funktioniert der Code bei dir bzw. weicht der Roboter den Hindernissen mit dem hier angegebenen Code aus? Das wär echt super.
      Eine Frage noch, da hier leider kein Video zu sehen ist. Fährt der Roboter so lange geradeaus bis er ein Hindernis sieht und macht dann einen 90°-Manöver oder wie kann ich mir das vorstellen?

      Antworten
      • Der Roboter fährt dorthin, wo am meisten Platz ist. Dabei sind bis zu 90° Manöver Möglich, ja.

  5. Hallo Klaus,
    Ja ich hab den wie im Tutorial beschrieben kalibriert was auch unbedingt notwendig ist. Danach ist er jedoch wie du auch beschrieben hast mehr oder weniger wahllos durch die Gegend gefahren. Erst das umstellen des Widerstandes hat bei mir den gewünschten Erfolg gebracht. er fährt um Gegenstände herum und weicht diesen aus. Respekt an Felix, klasse Arbeit.
    Hab jedoch zusätzlich bei meinem Robbi die Geschwindigkeit gedrosselt weil der Roboter mir auf den Fliesen viel zu schnell war. Hierzu kannst du die beiden Enable-Eingänge des L293D mit einem PWM Signal beschicken.
    Lg
    Harald

    Antworten
  6. Das klingt ja ganz gut. Werde leider erst nächste Woche wieder Zeit haben das zu testen. Vielen Dank schonmal. Wie genau hast du das mit dem PWM gemacht? Ich habe auch Fliesen und würde den Roboter gern etwas langsamer fahren lassen.
    Wäre nett, wenn du den Code dazu evtl. posten könntest, sofern das für dich und Felix okay ist 🙂

    Danke und Grüße
    Klaus

    Antworten
  7. Hi ,
    ich habe das Problem dass beim testen des Autopiloten mit test_us.py einfach gar nichts passiert bzw. das programm direkt in die exception springt.
    Wenn ich nur den Servo ansteuere funktioniert er, gleiches beim Sensor.
    Gebe ich die test_us.py Zeile für Zeile(ohne try und except) in die python konsole ein so kommt bei der Zeile r.autoPilotUSon() der Fehler “ AttributeError: Robot instance has no attribute ‚autoPilotUSon‘ “
    Ich verstehe den Fehler nicht ganz da Ja eigentlich in jeder function ein self attribut steht..?
    Würde mich freuen wenn jemand helfen kann 🙂

    Gruß
    Basti

    Antworten
    • Der Fehler besagt nur, dass die Funktion nicht vorhanden ist. Hast du in der Robot Datei geschaut und auf Rechtschreibfehler geprüft? Das self hat damit nichts zu tun (ist nur dazu da, um Klassenfunktionen / -variablen anzusprechen).

      Antworten
  8. Hallo,

    es funktioniert jetzt schon etwas besser, allerdings habe ich noch eine Frage. Mein Robbi steckt manchmal an einem Schuh oder Ähnlichem fest. Kann man den Code iwie anpassen, sodass er dann rückwärts fährt um aus solchen Situationen zu entweichen? :/
    Leider weiß ich nicht wie 🙁

    Antworten
    • Und eine Frage noch. Was hast du auf dem Ultraschallsensor für eine grüne Platine montiert? War das schon so oder fehlt mir hier vll. ein Stück?

      Liebe Grüße
      Klaus

      Antworten
      • Die Platine hatte ich früher einmal montiert, um die Widerstände direkt anzubringen. Da ich das Teil noch so rumliegen hatte, habe ich es einfach verwendet. Ist aber nicht nötig – du kannst auch einfach der Schaltung folgen.

    • Ja, aber der Schuh ist ja so hoch, dass der Sensorkopf ihn eigentlich erkennen/scannen müsste. Weißt du vll, wie der Roboter langsamer fahren kann oder was ich dafür am code ändern muss? 🙁
      Leider klappt das alles nicht wie beschrieben, habe den Robbi kalibriert und alles, links und rechts ist auch nicht vertauscht, also fährt in die Richtungen wie er soll, allerdings weiß ich nicht, wieso er diese blöden Entscheidungen trifft 🙁
      Brauch dringend Hilfe 🙁

      Antworten
      • Hast du zwischenzeitlich die gemessen Werte loggen lassen? Ich meine in einem der anderen Tutorials hat jemand gesagt, dass er PWM genutzt hat, um den Roboter langsamer fahren zu lassen.

    • Wow, das ging schnell mit der Antwort. Nein, habe ich nicht, wie kann ich die denn loggen lassen? Die werden ja in der Konsole ausgegeben, während das Script läuft.
      Ist es denn auch normal, dass der Robbi jedes mal nach links/rechts abbiegt, wenn der Sensorkopf links/rechts bei 90° angekommen ist? Ich kann mir nicht so recht vorstellen, wie das alles ablaufen soll 🙁

      Antworten
      • Mit print() kannst du etwas auf der Konsole ausgeben lassen. Am besten du loggst den Winkel und den Wert des Sensors. Ich denke, dass das das Problem ist, da wahrscheinlich der Abstand nicht richtig gemessen wird.

    • Also, er fährt auch permanent durch ohne anzuhalten, ist das normal?
      Wenn ich den Code richtig verstanden habe, sollten die Motoren stoppen, sobald er <5 cm vor einem Hindernis steht oder? 🙁

      Antworten
  9. Ich habe alles nach Plan durchgeführt und angeschlossen, aber schon 3 Servos zerschossen. Hilfe, was kann ich tun?

    Antworten
    • Wie zerschossen? Hast du zu viel Spannung drauf gegeben? Bald wird ein Tutorial zu einem Servo Driver Board kommen, womit man sehr einfach mehrere gleichzeitig steuern kann.

      Antworten

Hinterlasse einen Kommentar

Deine Email Adresse wird nicht veröffentlicht.

Blog abonnieren

Abonniere Tutorials-RaspberryPi, um kein Tutorial mehr zu verpassen!