Вы находитесь на странице: 1из 8

CONTROL DE ARDUINO CON JOYSTICK DE PS2

El control mediante Bluetooth es práctico porque siempre tenemos a mano un móvil con él, pero un poco
errático y al final siempre nos deja la sensación de ser un tanto incomodo o de fundir las baterías del móvil
demasiado deprisa y en el mejor de los casos, incómodo para estar un rato con él.

Por eso, y como siempre solemos comentaros, al final, alguien tenía que venir con una solución “y por eso el
mercado nos proporciona una impecable para controlar nuestros robots, motores o proyectos varios con un
mando único, que a muchos nos resultará familiar: Un mando como el de la PlayStation 2 inalámbrico.

Estos mandos se pueden conseguir por poco dinero en estos momentos (Gran cosa las bajadas de precios de
todos los componentes electrónicos) y tiene la enorme virtud de ser ergonómicos y muy cómodos de manejar,
además de estar dotados de dos joysticks analógicos y como 14 botones incluidos.

Estos mandos vienen con un receptor inalámbrico, que podemos conectar a nuestros Arduinos y usarlos para
recibir las señales de control, sin complicarnos mucho la vida, y un mando inalámbrico aparte muy similar al que
habréis usado más de uno para jugar con la PS2 de Sony.

MATERIAL REQUERIDO.

ARDUINO MEGA O EQUIVALENTE.

UN MOTOR SHIELD V1

UN CHASIS ROBOT CON 4 MOTORES.


UN PORTA PILAS

UN MANDO INALÁMBRICO TIPO PS2

En esta sesión vamos a ver como conectar este tipo de mando inalámbrico a nuestros Arduinos y veremos que
gracias a las librerías que nuevamente se ha trabajado Mr. Bill Porter, son pero que muy fáciles de implementar
y usar.TO

Como estamos montando un coche a control remoto vamos a utilizar un Arduino Mega como el que venimos
usando en las sesiones anteriores, para que el que quiera pueda tener un robot funcional.
Tampoco es necesario que os compliquéis la vida entendiendo la utilidad de cada cable, ya que la librería que
vamos a usar, se va a encargar de la gestión a condición de que definamos correctamente los pines.

Lo más cómodo es que conectéis los pines a vuestro Arduino en secuencia. En mi caso que uso un MEGA y la
tabla de conexión seria así:

CONEXIÓN RECEPTOR PS2 A ARDUINO MEGA

RECEPTOR 1 2 3 4 5 6 7 8 9

MEGA 22 24 26 28 30 32 34 36 38

PIN data command vibration GND 5V Attention Clock – acknoledge

Si disponéis de un pin header plano o a 90º es ideal para esto, porque dispondréis de un peine de pines que se
conecta directamente a los conectores de la Mega y el enganche es más fiable, porque están agrupados.

De nuevo, tenemos un par de pines que son GND y 5V, pero como el consumo es despreciable podemos poner
en HIGH el pin 30 y en LOW el pin 28.

EL PROGRAMA DE CONTROL

Lo primero es descargar la librería PS2X_lib y que la instaléis siguiendo el procedimiento habitual.


Como ya es costumbre de la casa, vamos a empezar con un programa mínimo para comprobar unos pocos
botones y después iremos viendo el resto de los mandos disponibles.

Vamos a empezar incluyendo la librería y creando un controlador tipo para el manejo del mando. Prog_96_1

#include <PS2X_lib.h> //for v1.6

PS2X ps2x; // Creamos la clase del mando PS2

Después vamos a definir el setup para que nos alimente el receptor con GND y 5V.

Serial.begin(57600);

pinMode(28, OUTPUT) ; pinMode(30, OUTPUT);


digitalWrite(28, LOW); //Set Ground for remote

digitalWrite(30, HIGH); // Set 5V for remote

delay(500);

LEYENDO LOS JOYSTICKS DEL MANDO

Ya habíamos usado antes este truco de alimentar algo con un pin del Arduino, pero recordar que este no debe

Después de esto, si hemos detectado correctamente el mando ya podemos pasar a controlar los botones que se
pulsan, Pero antes tenemos que salir si no hemos detectado el mando:

60352911

String S, Sentido = "" ;


if(error == 1) return; //Salir si no encontramos mando

Vamos a hacer un pequeño programa que detecte los botones de la mano izquierda: UP, DOWN, LEFT, RIGTH.

while(true)
{ ps2x.read_gamepad(); //Leemos el mando

if(ps2x.Button(PSB_PAD_UP)) //Es TRUE mientras se pulsa el boton


Serial.println("UP");
else if(ps2x.Button(PSB_PAD_DOWN))
Serial.println("DOWN");
else if(ps2x.Button(PSB_PAD_RIGHT))
Serial.println("RIGHT");
else if(ps2x.Button(PSB_PAD_LEFT))
Serial.println("LEFT");
else
Serial.println("STOP");
}
Si volcáis este programa Prog_96_1 a vuestro Arduino, veréis que detecta con un mensaje en la consola el botón
que pulsáis. Naturalmente la librería provee variables para todos los botones disponibles en el mando mediante
la función ps2x.Button().

BOTONES DE LA IZQUIERDA

BOTON UP DOWN RGHT LEFT

FLAG PSB_PAD_UP PSB_PAD_DOWN PSB_PAD_RIGHT PSB_PAD_LEFT

BOTONES DE LA DERECHA

BOTON Circle Red Cross Blue Square Pink Green Triangle

FLAG PSB_RED PSB_BLUE PSB_PINK PSB_GREEN

Más los botones centrales, de SELCT ( PSB_SELECT) y Start (PSB_START) . Para los botones traseros
tenemos:

BOTONES TRASEROS

BOTON L1 L2 R1 R2

FLAG PSB_L1 PSB_L2 PSB_R1 PSB_R2

Los botones de la izquierda, tienen además, la curiosidad de que detectan de modo analógico la presión que
ejerces en ellos con valores entre 0 y 255, mediante el comando

ps2x.Analog( Flag )

Donde Flag representa cualquiera de los valores indicados en la primera table. Por ejemplo para imprimir la
intensidad con que s epulsa el botón UP, bastaría con hacer:

Serial.println(ps2x.Analog(PSAB_PAD_UP), DEC);
LEYENDO LOS JOYSTICKS DEL MANDO

Por ultimo para detectar el movimiento de los dos joysticks incluidos en el mando, tenemos que entender que al
ser analógicos tenemos que leer de cada uno, dos valores, X e Y, tal y como hacíamos en una sesión
previa Joystick y Servo.

Como el mando nos devuelve un valor entre 0 y 255, cuando el joystick esta en reposo en la posición central, la
lectura que nos da es de 127 tanto en X como en Y. Espero que el siguiente gráfico os resulte sencillo:

Para leer los joysticks tenemos que leer independientemente la posición en X e Y de cada uno de ellos

JOYSTICK IZQUIERDO JOYSTICK DERECHO

EJE X Y X Y

FLAG PSS_LX PSS_LY PSS_RX PSS_RY

Para leer los valores de los joysticks podemos usar el siguiente trozo de código:

Serial.print("Stick Values:");
Serial.print(ps2x.Analog(PSS_LY), DEC);
Serial.print(",");
Serial.print(ps2x.Analog(PSS_LX), DEC);
Serial.print(",");
Serial.print(ps2x.Analog(PSS_RY), DEC);
Serial.print(",");
Serial.println(ps2x.Analog(PSS_RX), DEC);
Ahora te puede parecer muy complicado pero es una tontería (En serio), simplemente el mando tiene tantos
botones que hay que usar un montón de flags para definir cada uno, pero siempre es lo mismo.
La librería viene con un ejemplo magnifico de uso, pero tiene el inconveniente de que muestra todas las
posibilidades a la vez y puede ser un poco avasallador, pero si vais a usar este mando desde luego os recomiendo
que la echéis una ojeada.

Para aquellos que hayáis hecho el montaje como el de este ejemplo, os pongo el ejemplo corregido para que os
funcione a la primera, en la que simplemente he adaptado el ejemplo incluido a nuestros pines.

MOVIENDO NUESTRO ROBOT CON EL MANDO DE LA PS2


Solo nos queda ya montar un programa completo que incorpore el control de los motores y la dirección del
movimiento respondiendo a las pulsaciones del mando a distancia.

Vamos a empezar usando los 4 botones de la izquierda como controles simples de dirección. Para ello tenemos
que incluir un par de librerías. Una para el control de la controladora de motores y otra para el manejo del
mando de la PS2:

#include <AFMotor.h>
#include <PS2X_lib.h> //for v1.6
PS2X ps2x; // Creamos la clase del mando PS2
AF_DCMotor Motor1(1); // Instanciamos los motores
AF_DCMotor Motor2(2);
AF_DCMotor Motor3(3);
AF_DCMotor Motor4(4);
Y definimos algunas variables que usaremos luego
int error = 0; // Para reconocer el mando
byte type = 0; // Tipo del mando. Volveremos sobre ello
int Vel = 180 ; // Define la velocidad base del Rover
En el setup, definimos los pines que alimenten el mando de la PS2
void setup()
{ Serial.begin(57600);
pinMode(28, OUTPUT) ; pinMode(30, OUTPUT);
digitalWrite(28, LOW); // Ground para el receptor
digitalWrite(30, HIGH); // 5V para el receptor
delay(500);

// GamePad(clock, command, attention, data, Pressures?, Rumble?)


error = ps2x.config_gamepad(34,24,32,22, true, true);
if(error == 0)
Serial.println("Controlador encontrado y configurado");
type = ps2x.readType();
if ( type == 1)
Serial.println("Hallado controlador DualShock.");
}
Fijaros en la línea

error = ps2x.config_gamepad(34,24,32,22, true, true);

Aquí es donde inicializamos el controlador de la PS2 con los pines que usamos y nos aseguramos de que no haya
error, para indicar que ha encontrado un mando compatible. Y por último leemos el tipo de mando que ha
encontrado, que puede ser de varios tipos, Tipo DualShock = 1 o tipo Guitar Hero = 2.

Por último el loop es una variante del programa Prog_76_1, al que añadimos el control de los movimientos del
robot que ya vimos en las sesiones previas.

void loop()
{
if(error == 1) return; //Salir si no encontramos mando
While(true)
{ ps2x.read_gamepad(); //Leemos el mando
if(ps2x.Button(PSB_PAD_UP)) //Es TRUE mientras se pulsa el boton
{ Serial.println("UP"); Avance(); }
else if(ps2x.Button(PSB_PAD_DOWN))
{ Serial.println("DOWN"); Retroceso(); }
else if(ps2x.Button(PSB_PAD_RIGHT))
{ Serial.println("RIGHT"); giroDerecha();}
else if(ps2x.Button(PSB_PAD_LEFT))
{ Serial.println("LEFT"); giroIzquierda() ; }
else
{ Serial.println("STOP"); Paro() ; }
delay(500); // Para que no saque mensajes continuamente
}
}

Вам также может понравиться