¿Nos ayudas a pagar el Hosting?

Compartir en facebook Compartir en google+ Compartir en twitter Compartir en pinterest Compartir en linkedin

Controla tu Orange Pi con un Gamepad y Python

Publicado en Septiembre de 2018

Controla tu Orange Pi con un Gamepad y PythonEn esta guía vamos a explicar como utilizar un gamepad o joystick analógico para controlar nuestros proyectos en Python lo que tiene la ventaja de proporcionar una cantidad de información superior a la que podríamos obtener simplemente con pulsadores. Vamos a usar un gamepad de ordenador con puerto USB. Por casa tenía un viejo Logitech Dual Action y funcionó todo a la primera.

Que necesitas:

Vamos a usar una librería de Python que se llama evdev (más info pulsando aquí) sobre Armbian actualizado, así que ya deberías tener Python instalado, pero vamos a comprobarlo con:

python --version

En mi caso me devuelve:

Python 2.7.9

También necesitaremos pip, que es un sistema de administración de paquetes utilizado para instalar y administrar paquetes de software y estará instalado si la versión es superior a 2.7.9. Puedes comprobarlo con:

pip --version
pip 1.5.6 from /usr/lib/python2.7/dist-packages (python 2.7)

Si no los tienes, puedes instalarlo con:

sudo apt install python-pip
sudo apt install python-dev

Instalamos el paquete evdev:

sudo pip install evdev

Ahora necesitamos identificar el mando que ya tendremos conectado por USB con:

sudo python /usr/local/lib/python2.7/dist-packages/evdev/evtest.py
ID  Device               Name                                Phys                                Uniq
-----------------------------------------------------------------------------------------------------
0   /dev/input/event0    vmouse                              vmouse/input0
1   /dev/input/event1    sunxi-gpiokey                       sunxikbd/input0
2   /dev/input/event2    sunxi-ths                           sunxiths/input0
3   /dev/input/event3    Logitech Logitech Dual Action       usb-sunxi-ohci-1/input0
4   /dev/input/event4    sunxi-ir                            sunxi-ir/input1
5   /dev/input/event5    MCE IR Keyboard/Mouse (sunxi-ir)    /input0

Select devices [0-5]:					

Nos pide que elijamos el dispositivo que queremos testear, en mi caso es el ID número 3. Pulsamos 3 mas Intro y probamos a pulsar algún botón:

Select devices [0-5]: 3
Listening for events (press ctrl-c to exit) ...
time 1537545054.34    type 3 (EV_ABS), code 0    (ABS_X), value 128
time 1537545054.34    --------- SYN_REPORT --------
time 1537545054.35    type 3 (EV_ABS), code 0    (ABS_X), value 139
time 1537545054.35    type 3 (EV_ABS), code 1    (ABS_Y), value 128
time 1537545054.35    --------- SYN_REPORT --------
time 1537545055.23    type 3 (EV_ABS), code 0    (ABS_X), value 140
time 1537545055.24    --------- SYN_REPORT --------
time 1537545151.14    type 4 (EV_MSC), code 4    (MSC_SCAN), value 589826
time 1537545151.14    type 1 (EV_KEY), code 289  (BTN_THUMB), value 1
time 1537545151.14    --------- SYN_REPORT --------
time 1537545151.26    type 4 (EV_MSC), code 4    (MSC_SCAN), value 589826
time 1537545151.26    type 1 (EV_KEY), code 289  (BTN_THUMB), value 0
time 1537545151.26    --------- SYN_REPORT --------
time 1537545152.28    type 4 (EV_MSC), code 4    (MSC_SCAN), value 589825
time 1537545152.28    type 1 (EV_KEY), code 288  (['BTN_JOYSTICK', 'BTN_TRIGGER']), value 1
time 1537545152.28    --------- SYN_REPORT --------
time 1537545152.38    type 4 (EV_MSC), code 4    (MSC_SCAN), value 589825
time 1537545152.38    type 1 (EV_KEY), code 288  (['BTN_JOYSTICK', 'BTN_TRIGGER']), value 0
time 1537545152.38    --------- SYN_REPORT --------

¡Funciona!. Este paquete permite recuperar el estado de las teclas y botones además de datos sobre la posición de cada eje de los joysticks analógicos como ejes X e Y en valores entre 0 y 255 siendo 127 centrado. Si subimos el mando tendremos 255 en el eje Y, centrado dara 127 y abajo 0. Tendremos esos mismos datos en el eje X para izquierda y derecha. Y diferentes nombres para cada uno de los botones con valores 1 (pulsado) y 0 (sin pulsar).

Para identificar cada uno de los botones y controles de nuestro mando. Crea un archivo llamado localizar.py con:

sudo nano localizar.py

y escribe este código:

#Importamos evdev
from evdev import InputDevice, categorize, ecodes

#Creamos el objecto gamepad
gamepad = InputDevice('/dev/input/event3')

#Muestra la info del gamepad
print(gamepad)

#Muestra los codigos
for event in gamepad.read_loop():
    #Botones 
    if event.type == ecodes.EV_KEY:
        print(event)
    #Joystick
    elif event.type == ecodes.EV_ABS:
        absevent = categorize(event)
        print ecodes.bytype[absevent.event.type][absevent.event.code], absevent.event.value

Recuerda cambiar la línea gamepad = InputDevice('/dev/input/event3') con el nombre de tu mando /eventx. Ejecútalo y te mostrará los nombres de ejes y botones según los vayas manipulando. Para identificarlos, ejecuta el programa, pulsa un botón o mueve un mando para ver que respuesta te da. Apúntalos en una hoja.

sudo python localizar.py
device /dev/input/event3, name "Logitech Logitech Dual Action", phys "usb-sunxi-ohci-1/input0"
event at 1537546242.605596, code 288, type 01, val 01
event at 1537546242.709571, code 288, type 01, val 00
event at 1537546245.765512, code 289, type 01, val 01
event at 1537546245.869460, code 289, type 01, val 00
event at 1537546247.389445, code 290, type 01, val 01
event at 1537546247.493430, code 290, type 01, val 00
event at 1537546247.973419, code 291, type 01, val 01
event at 1537546248.061422, code 291, type 01, val 00
...
event at 1537546263.284986, code 292, type 01, val 01
event at 1537546263.428953, code 292, type 01, val 00
event at 1537546266.916893, code 293, type 01, val 01
event at 1537546267.028865, code 293, type 01, val 00
...
ABS_Y 129
ABS_Y 130
ABS_Y 132
ABS_Y 133
ABS_Y 136
ABS_Y 144
ABS_Y 156
...
ABS_RZ 127
ABS_RZ 130
...
ABS_Z 128
ABS_Z 127
ABS_Z 126
...
ABS_X 127
ABS_X 128
ABS_X 130

Vemos que el botón 1 corresponde al code 288, el botón 2 corresponde al code 289,... el botón 5, que sería el dedo índice de la mano izquierda, corresponde al code 292 y el 6, el de la derecha al code 293. Los ejes corresponden a los nombres ABS_Y, ABS_X, ABS_Z y ABS_RZ. Estos códigos seguramente no coincidán con tu mando, así que debes localizarlos tú mismo. Ahora pasamos todos esos datos a un archivo con los códigos de todos los controles. Crea el archivo gamepad.py:

# -*- coding: iso-8859-15 -*-
# author    : "javier pérez santos para orangepiweb.es"
# credits   : "javier pérez santos, orangepiweb.es"
# copyright : "Copyright 2018, orangepiweb.es"
#
#   ___                             ____  ___        __   _
#  / _ \ _ __ __ _ _ __   __ _  ___|  _ \(_) \      / /__| |__   ___  ___
# | | | | '__/ _` | '_ \ / _` |/ _ \ |_) | |\ \ /\ / / _ \ '_ \ / _ \/ __|
# | |_| | | | (_| | | | | (_| |  __/  __/| | \ V  V /  __/ |_) |  __/\__ \
#  \___/|_|  \__,_|_| |_|\__, |\___|_|   |_|  \_/\_/ \___|_.__(_)___||___/
#                        |___/
#
# Control de Gamepad con Python

#import evdev
from evdev import InputDevice, categorize, ecodes

#Creamos el objecto gamepad
gamepad = InputDevice('/dev/input/event3')

#Muestra la info del gamepad
print(gamepad)

#Como las variables de python no admiten numeros usamos letras
xBtn = 288
aBtn = 289
bBtn = 290
yBtn = 291
lBtn = 292
rBtn = 293

#Muestra los codigos
for event in gamepad.read_loop():
    #Botones
    if event.type == ecodes.EV_KEY:
        #print(event)
        if event.value == 1:
            if event.code == xBtn:
                print("X")
            elif event.code == bBtn:
                print("B")
            elif event.code == aBtn:
                print("A")
            elif event.code == yBtn:
                print("Y")
            elif event.code == lBtn:
                print("IZQUIERDA")
            elif event.code == rBtn:
                print("DERECHA")
        elif event.value == 0:
          print("Suelto")

    #Joystick
    elif event.type == ecodes.EV_ABS:
        absevent = categorize(event)
        #print ecodes.bytype[absevent.event.type][absevent.event.code], absevent.event.value
        if ecodes.bytype[absevent.event.type][absevent.event.code] == "ABS_X":
             if absevent.event.value == 0:
                print("Izquierda")
             elif absevent.event.value == 255:
                print("Derecha")
             elif absevent.event.value == 127:
                print("Centrado")
        elif ecodes.bytype[absevent.event.type][absevent.event.code] == "ABS_Y":
             if absevent.event.value == 0:
                print("Arriba")
             elif absevent.event.value == 255:
                print("Abajo")
             elif absevent.event.value == 127:
                print("Abajo")

Ya vemos por pantalla cada una de nuestras acciones totalmente identificada. Si ahora cambias (o añades) al comando print ("xxx") la acción que quieres ejecutar, tendrás todo el control en tu gamepad. O incluso, crear tus propios juegos en Python...

sudo python joystick.py
device /dev/input/event3, name "Logitech Logitech Dual Action", phys "usb-sunxi-ohci-1/input0"
Abajo
Arriba
Centrado
Izquierda
Izquierda
Centrado
Derecha
Centrado
Abajo
Centrado
A
Suelto
X
Suelto
Y
Suelto
B
Suelto
DERECHA
Suelto
IZQUIERDA
Suelto

Espero que te haya sido de utilidad, no dudes en escribir un comentario si ves algún error o si puedo ayudarte.


Utiliza este espacio si quieres añadir algún comentario adicional o si tienes alguna duda.
No olvides añadir tu distribución y tu placa.

Todos los comentarios serán validados antes de su publicación.

Nombre*

Email* Nunca será publicado ni compartido

Comentario*



Copyright © 2018 desde 2016. Todos los derechos reservados | Diseño JaviPSantos

Solicitamos su permiso para obtener datos estadísticos de su navegación en esta web, en cumplimiento del Real Decreto-ley 13/2012. Si continúa navegando consideramos que acepta el uso de cookies.

OK | Más información