Una cámara móvil

Una vez que tenemos un bot que nos permite controlar remotamente nuestro proyecto (Segundo bot: avanzamos) y sabemos mover los motores (Movimiento suave con los servos) llega el momento de montar la cámara encima (Una cámara en la Raspberry Pi) y controlarla remotamente.
Recordemos que el control se hace mediante XMPP (por ejemplo, con programas como Pidgin, Google Talk o nuestro cliente de mensajería favorito); la idea era evitar abrir puertos en el router para controlarlo vía web y, sin embargo, poder enviar instrucciones desde internet sin problemas.

Para el montaje seleccionamos un par de cajas (como forma barata y simple de proporcionar el soporte para todo). En una caja más grande hicimos un par de agujeros (para poder colocar dos motores, aunque finalmente sólo hemos utilizado uno):

Hemos pintado la caja #raspi

A post shared by Fernando Tricas García (@ftricas) on

Dentro de la caja van las conexiones (baterías para alimentar los motores, y cables para controlarlos desde la Raspberry Pi, que se queda fuera de la caja).

Caja como soporte para los motores

A post shared by Fernando Tricas García (@ftricas) on

La cámara se monta en una caja más pequeña que se sujeta al servo seleccionado.

Y tenemos un prototipo de mejor aspecto #raspi

A post shared by Fernando Tricas García (@ftricas) on

Cuando se le da la instrucción de movimiento, la cámara va a la posición elegida, se detiene para hacer la foto y la envía por correo. Finalmente, vuelve a su posición inicial.
Toda la secuencia puede verse en el siguiente vídeo.

El código del proyecto está disponible en err-plugins (puede evolucionar más adelante; el código en su estado actual puede verse en pruebas.py).

Recientemente se publicó un proyecto similar en “Raspberry Eye” Remote Servo Cam. Tiene dos diferencias fundamentales: se han incluido movimientos en dos ejes (nuestro proyecto sólo se mueve a derecha e izquierda) y se controla mediante una página web.

¿Qué haremos a continuación?
Tengo varias ideas, pero no se todavía qué haré: sería interesante que la cámara tuviera cierta autonomía (¿detección de movimiento o cambios en la escena?); tampoco me importaría pensar en movilidad real (¿embarcar la cámara en algún tipo de dispositivo con ruedas? me encantó este hexápodo).
Yendo más allá, tal vez podríamos pensar en otros dispositivos de control (¿wearables?).

Por supuesto, ideas, comentarios, sugerencias… Serán bienvenidos.

Anuncios

Segundo bot: avanzamos

En Raspberry Pi: ¿qué temperatura hace en mi casa? hablábamos del primer bot que nos permitía interactuar con la Raspberry Pi desde donde nos encontráramos.

Estuve probando SleekXMPP y phenny pero ambos tenían algunas limitaciones así que continué buscando hasta que encontré otro proyecto interesante, err que, además de estar en ese momento con cierta actividad proporciona una arquitectura modular para añadir características e incluso tiene una comunidad en Google+, Err.

Lo primero que hice fue adaptar las pruebas que ya había hecho con phenny a la nueva arquitectura, y añadirle un par de cosas más relacionadas con la toma de fotos y su envío. Puede verse el código del módulo en err-plugins (en el futuro podría cambiar así que nos fijaremos en la versión actual con sus dos ficheros.

El primero es pruebas.plug, que contiene información sobre el módulo en sí, con la sintaxis que define el bot:

[Core]
Name = Pruebas
Module = pruebas

[Documentation]
Description = let’s try things !

Y el fichero pruebas.py que contiene el código en sí. Esencialmente es un fichero con código en Python. Por ejemplo, para que el bot tome una fotografía nos la envíe, sería:

<br />
@botcmd<br />
def foto(self, msg, args):<br />
	&quot;&quot;&quot;Take a picture&quot;&quot;&quot;<br />
	quien=msg.getFrom().getStripped()<br />
	yield &quot;I'm taking the picture, wait a second &quot;<br />
	if(args):<br />
		try:<br />
			cam=int(args)<br />
		except:<br />
			cam=0<br />
	else:<br />
		cam=0<br />
	yield &quot;Camera %s&quot;%cam<br />
	self.camera(&quot;/tmp/imagen.png&quot;,cam)<br />
	yield &quot;Now I'm sending it&quot;<br />
	self.mail(&quot;/tmp/imagen.png&quot;, quien)<br />
	my_msg = &quot;I've sent it to ... %s&quot;%quien<br />
	yield my_msg<br />

Con la primera línea decimos que es una instrucción para el bot y luego definimos una función que es la que se ocupa de las acciones correspondientes. El nombre de la función será la instrucción (con un prefijo configurable, que permite al bot diferenciar entre lo que se le indica a él y lo que son otros textos que no interpretará).

En nuestro caso, la instrucción:

.foto

Ejecutaría una función que es muy parecida a la que comentábamos el otro día en Una cámara en la Raspberry Pi. Las diferencia serían:

  • Recibe los parámetros a través de la llamada a la función

    def foto(self, msg, args):
  • Responde al que le envió la orden:

    quien=msg.getFrom().getStripped()
  • El argumento puede ser 0, 1 o ninguno (no se hace validación) porque tenemos dos cámaras en la Raspberry. Por defecto dispara con la cámara 0.
  • A continuación nos indica qué cámara hemos elegido:

    yield "Camera %s"%cam
  • Invoca a la función que realmente realiza la fotografía, cuyos parámetros son muy similares a los que ya comentamos en su momento (el nombre del fichero donde se almacenará la foto y la cámara elegida):

    self.camera("/tmp/imagen.png",cam)
  • Invoca a la función de envío por correo, cuyos parámetros son el fichero donde está la imagen y a quién se envía el mensaje.

    self.mail("/tmp/imagen.png", quien)
  • Finalmente responde al que dio la orden, nuevamente con yield.

Si miramos el código, la diferencia de estas dos funciones es que no van precedidas con @bootcmd, así que no están disponibles como instrucciones. Por lo demás necesitan (igual que contábamos en su momento) los parámetros de configuración adecuados.

Errbot nos proporciona un mecanimos para eso, mediante:

<br />
def get_configuration_template(self):<br />
return{'ADDRESS' : u'kk@kk.com', 'FROMADD' : u'kk@kk.com',<br />
'TOADDRS' : u'kk@kk.com', 'SUBJECT' : u'Imagen',<br />
'SMTPSRV' : u'smtp.gmail.com:587', 'LOGINID' : u'changeme',<br />
'LOGINPW' : u'changeme'}<br />

Podemos definir en un diccionario los parámetros que podremos configurar (vistos, recuerden en Una cámara en la Raspberry Pi).

Y, tecleando en nuestro cliente de mensajería:

.config Pruebas

En este caso, Pruebas es el nombre del módulo y el punto (.) es el indicador que hemos elegido para las instrucciones. La instrucción config nos devuelve la configuración que el módulo tenga en ese momento (si no está configurado muestra los valores que hemos puesto en la definición; si ya lo hemos configurado mostrará los valores que tenga). Los valores que se devuelven pueden utilizarse como patrón para configurar el módulo:

.config Pruebas {'TOADDRS': u'mydir@mail.com', 'SMTPSRV':
u'smtp.gmail.com:587', 'LOGINPW': u'mypassword',
...
}

Con esto, ya falta menos para hacer el montaje final. Seguiremos
informando.