Nuova sezione libri disponibile!

Inviare Goals alla Navigation Stack - versione nodo ROS Python

Fiorella Sibona

lettura in 4 minuti

Ehilà!

Questo post ha l'obbiettivo di fornire un esempio in codice Python per inviare una posa goal (posizione ed orientamento desiderati) ad un robot, nel mio caso un robot TurtleBot3 simulato, sfruttando la ROS Navigation Stack. Solitamente, ad un robot autonomo mobile viene richiesto di raggiungere un'ubicazione desiderata. Per fare ciò, deve avere alcune informazioni e combinarle tra loro: avere una mappa dell'ambiente in cui si trova, percepire ciò che lo circonda, localizzare se' stesso e pianificare i propri movimenti. La ROS Navigation Stack assume il ruolo di "guidare" la base mobile a muoversi verso quell'obbiettivo, evitando eventuali ostacoli e mettendo insieme tutte le informazioni a disposizione. Usando codice, l'utente può inviare alla navigation stack una posa desiderata da far assumere al robot. Per scrivere il nodo correttamente, ho seguito il tutorial per il nodo C++ "Sending Goals to the Navigation Stack", quindi il mio scopo è quello di darvi un equivalente per il nodo Python.

Nota: Uso ROS Kinetic. Assumerò che il lettore abbia conoscenze a proposito di Nodi ROS, Topics, Messaggi e Actions. Alcune informazioni a proposito di queste ultime verranno date durante la descrizione delle librerie.

1. La libreria actionlib

La ROS navigation stack è basata sulle ROS Actions: infatti le Actions sono la scelta migliore nei casi in cui un nodo voglia inviare una richiesta ad un altro nodo e riceverà una risposta dopo un tempo relativamente lungo. Per evitare che l'utente si chieda che cosa stia succedendo e se tutto stia andando come desiderato o meno, le Actions implementano un meccanismo di feedback, il quale permette all'utente di ricevere informazioni di tanto in tanto. Le Actions sono basate sul paradigma Client-Server: la libreria actionlib fornisce gli strumenti e un'interfaccia per creare un Action Server che esegua le richieste di goal inviate dal Client. Gli elementi principali del meccanismo delle ROS actions sono: goal, result, e feedback. Ognuno di essi è specificato da un tipo di Messaggio ROS, contenuto in un action definition file, con estensione ".action".

Per maggiori informazioni fate riferimento alla descrizione dettagliata di actionlib.

2. Il nodo MoveBase

Il nodo ROS move_base, è il componente più importante della navigation stack il quale permette di configurare, runnare ed interagire con quest'ultima. Il nodo movebase implementa un _SimpleActionServer, un action server con la restrizione di ricevere un solo goal alla volta, che riceve goals in messaggi di tipo geometry_msgs/PoseStamped. Per comunicare con questo nodo, viene usata l'interfaccia SimpleActionClient. Il nodo move_base cerca di raggiungere la posa desiderata combinando un motion planner globale ed uno locale per portare a termine il task di navigazione il quale include evitare ostacoli.

\n

3. Creazione del Nodo - Codice

Ecco qui il codice dell'intero nodo senza commenti. Per i commenti andate alla Sezione 4.

#!/usr/bin/env python
# license removed for brevity

import rospy
import actionlib
from move_base_msgs.msg import MoveBaseAction, MoveBaseGoal

def movebase_client():

    client = actionlib.SimpleActionClient('move_base',MoveBaseAction)
    client.wait_for_server()

    goal = MoveBaseGoal()
    goal.target_pose.header.frame_id = "map"
    goal.target_pose.header.stamp = rospy.Time.now()
    goal.target_pose.pose.position.x = 0.5
    goal.target_pose.pose.orientation.w = 1.0

    client.send_goal(goal)
    wait = client.wait_for_result()
    if not wait:
        rospy.logerr("Action server not available!")
        rospy.signal_shutdown("Action server not available!")
    else:
        return client.get_result()

if __name__ == '__main__':
    try:
        rospy.init_node('movebase_client_py')
        result = movebase_client()
        if result:
            rospy.loginfo("Goal execution done!")
    except rospy.ROSInterruptException:
        rospy.loginfo("Navigation test finished.")

4. Creazione del Nodo - Codice e commenti

Ecco qui il codice completo di commenti. L'intero codice del nodo senza commenti è dato nella Sezione 3.

#!/usr/bin/env python
# license removed for brevity

import rospy

# Importa il SimpleActionClient
import actionlib
# Importa il file .action ed i messaggi usati dalla move base action
from move_base_msgs.msg import MoveBaseAction, MoveBaseGoal

def movebase_client():

   # Crea un action client chiamato "move_base" con action definition file "MoveBaseAction"
    client = actionlib.SimpleActionClient('move_base',MoveBaseAction)

   # Aspetta che l'action si sia avviato ed abbia iniziato ad essere ricettivo per i goal
    client.wait_for_server()

   # Crea un nuovo goal con il costruttore MoveBaseGoal
    goal = MoveBaseGoal()
    goal.target_pose.header.frame_id = "map"
    goal.target_pose.header.stamp = rospy.Time.now()
   # Muovere di 0.5 metri avanti lungo l'asse x del sistema di riferimento della mappa
    goal.target_pose.pose.position.x = 0.5
    goal.target_pose.pose.orientation.w = 1.0

   # Invia il goal all'action server.
    client.send_goal(goal)
   # Aspetta che il server finisca di eseguire la richiesta
    wait = client.wait_for_result()
   # Se il risultato non arriva, assumiamo che il Server non sia disponibile
    if not wait:
        rospy.logerr("Action server not available!")
        rospy.signal_shutdown("Action server not available!")
    else:
    # Restituisce il risultato dell'esecuzione dell'action
        return client.get_result()

# Se il nodo Python viene eseguito come processo principale (eseguito direttamente)
if __name__ == '__main__':
    try:
       # Inizializza un nodo rospy per permettere al SimpleActionClient di interagire in ROS
        rospy.init_node('movebase_client_py')
        result = movebase_client()
        if result:
            rospy.loginfo("Goal execution done!")
    except rospy.ROSInterruptException:
        rospy.loginfo("Navigation test finished.")

Abbiamo finito! Questo è un semplice esempio di nodo Python per inviare una posa desideata alla navigation stack per muovere un robot mobile. Come potete notare, per motivi di semplicità, essendo questo un tutorial base, non vengono sfruttati i meccanismi di feedback propri delle Actions ed il risultato non è indicativo del reale status del goal. Per avere un esempio più completo, vi consiglio la lettura del post "Inviare una sequenza di Goals alla ROS NavStack usando Python".

Grazie per l'attenzione e a presto! :hibiscus:

Ti è piaciuto questo post?

Registrati alla newsletter per rimanere sempre aggiornato!

Ci tengo alla tua privacy. Leggi di più sulla mia Privacy Policy.

Ti potrebbe anche interessare

HB Cloud Tutorial #1 - Uso dei Led
Iniziamo ad utilizzare la piattaforma di Cloud Robotics
HB Cloud Tutorial #2 - Uso dei Bottoni
Rieccomi con il secondo tutorial legato all'uso dei bottoni per il robot **DotBot-ROS**. In questo tutorial, vedremo come configurare ed utilizzare in Python un bottone attaccato ad un pin GPIO del Raspberry Pi 3.
HB Cloud Tutorial #3 - I Motori
I Motori sono una delle parti essenziali dei robot. In questo tutorial, vederemo come è possibile in modo semplice ed intuitivo implementare un programma in Python che controlla i motori in base a comandi inviati via Wifi al Robot.
Non avete un robot? C'è il robot in cloud accessibile da remoto tramite il vostro PC o da cellulare
Non avete un robot? C'è il robot in cloud accessibile da remoto tramite il vostro PC o cellulare
Avete problemi hardware? C'è il robot in cloud accessibile da remoto tramite il vostro PC o cellulare
Avete problemi hardware? C'è il robot in cloud accessibile da remoto tramite il vostro PC o cellulare
Installiamo ROS su Raspberry Pi
Un breve tutorial su come utilizzare ROS sul Raspberry Pi
Video Corso ROS Rokers - Completati i video di Introduzione
Sono disponibili online i video tutorial del corso di ROS partito dalla community Rokers
NTBD: guida step by step
Cos'è e come utilizzare NTBD step by step, primo articolo della serie
Inviare una sequenza di Goals alla ROS NavStack usando Python
Inviare una sequenza di pose desiderate alla ROS Navigation Stack usando un nodo Python
Controllare siBOT dalla piattaforma HBR
Come controllare il manipolatore siBOT utilizzando la piattaforma HBR
Sviluppare un rilevatore di fiamma con la visione artificiale
Sviluppare un rilevatore di fiamma con la visione artificiale
Come creare messaggi custom in ROS
Creare nuovi tipi di messaggio ROS
Benvenuto a ROS 2.0
Primo contatto con ROS 2.0
Usare il braccio robotico Dobot con ROS
Come usare il braccio robotico con Robot Operating System
Scriviamo un Blog in Python e Flask
Tutorial su come implementare, a partire da zero, un blog personale utilizzando Python e Flask! Prima parte!
Un laboratorio di Fisica con Arduino e Python
Primi esperimenti con Arduino e Python per realizzare un semplice laboratorio di fisica sfruttando la potenza di Python e la versatilità di Arduino
Canopy: una Pythonica alternativa a Matlab
Presento questo interessante tool python che può essere considerato una buona alternativa a Matlab per l'analisi dei dati!
Spyder, un'altra alternativa in Python a Matlab
Una velocissima prova del tool interattivo Spyder per l'analisi scientifica in Python
Simuliamo il moto parabolico in Python e Spyder
Un piccolo tutorial per iniziare ad utilizzare Spyder con Python
Python + Arduino = Nanpy
Programmare Arduino in Python con Nanpy
Utilizzo di Nanpy con il sensore di temperatura/umidità della famiglia DHT
Come utilizzare Nanpy col sensore DHT di temperatura e Umidità
Accendere led con Arduino e Telegram
Un bot telegram in grado di controllare Arduino realizzato da 3 ragazzi del Liceo Stampacchia
Implementiamo un bot Telegram con Python
Una semplice guida per iniziare a muovere i primi passi nello sviluppo di chatbot Telegram con Python
Pillole di Python: pyscreenshot
Una semplice tutorial che mostra il funzionamento della libreria pyscreenshot
Python Decorators
Introduzione ai decoratori in Python
TDD con Flask e PyTest per lo sviluppo di API REST. Parte 1
Tutorial su come usare il Test Driver Development (TDD) con Flask e PyTest per sviluppare delle semplici API REST
Implementiamo un bot Telegram con Python - I Comandi
Vediamo come gestire i comandi del nostro bot in Telegram
4 (+1) Libri su Python (in Inglese) da cui imparare
Una lista di libri su Python (in Inglese) da cui ho imparato a programmare
Virtualenv: gestiamo meglio le dipendenze in Python
A cosa servono e come si utilizzano i virtualenv Python
Un Video Corso di ROS
Il mio video corso su come utilizzare ROS è disponibile
Leggere i codici a barre con OpenCV e zbar in Python
Come usare Python per leggere i codici a barre degli alimenti e ricavarne alcune informazioni utili
TDD con Flask e PyTest per lo sviluppo di API REST. Parte 2
Tutorial su come usare il Test Driver Development (TDD) con Flask e PyTest per sviluppare delle semplici API REST
Sviluppiamo un bot Telegram che legge i codici a barre degli alimenti
Implementiamo un bot Telegram in grado di leggere ed analizzare le immagini per la lettura ed interpretazione dei codici a barre
TDD con Flask e PyTest per lo sviluppo di API REST. Parte 3
Tutorial su come usare il Test Driver Development (TDD) con Flask e PyTest per sviluppare delle semplici API REST
Divertiamoci sviluppando UI da terminale con ASCIIMATICS
Le UI da terminale fanno molto anni '80, però sono sempre diventerti da implementare. Oggi vi voglio introdurre ad una semplice libreria per creare questo tipo di applicazione.
Sviluppiamo un Robot con tecnologie Open Source
Inizio una serie di videoguide, in cui voglio introdurvi al mondo della robotica di servizio in modo pratico, facendo vedere come è possibilile, sfruttando tecnologie completamente Open Source, quali Arduino, Raspberry Pi, ROS e Docker, costruire un piccolo robot di Servizio.
Parliamo come GMaps: come creare file audio con gtts (Google Text to Speech) in Python
gtts è una libreria in Python per sfruttare le API di Google Text to Speech per generare file audio dal testo
Robot Open Source - Introduzione a Docker
È disponibile il video "Introduzione a Docker".
I chatbot possono Parlare? Sviluppiamo un bot telegram che manda messaggi vocali
Usiamo le API di sintesi vocale di google per creare un bot in grado di mandare messaggi vocali
Buildare e usare container Docker per Raspberry Pi
In questa guida vediamo come buildare ed utilizzare Docker su Raspberry Pi (ed in generale sistemi Linux Embedded) per velocizzare la produzione di applicazioni Linux Embedded
Robot Open Source - Docker e Raspberry
È disponibile il video "Docker e Raspberry".