Está en la página 1de 22

Manual de visi on en rob otica

Jose M. Ca nas Universidad Rey Juan Carlos jmplaza@gsyc.escet.urjc.es versi on 1.5

Resumen Este manual describe diferentes aspectos relevantes del manejo de im agenes en rob otica, incluyendo su captura, su procesamiento y su visualizaci on. Est a orientado a servir de gu a al programador que se enfrenta a estas tareas, y en este sentido se incluye el c odigo de ejemplos b asicos que pueden servir de base. En la parte de captura se describe el estandard que se ha extendido en el mundo linux: la interfaz Video4Linux, y el m as reciente v4l2. La hemos probado con una c amara convencional m as tarjeta digitalizadora BT878, y sobre una c amara USB. En la parte de procesamiento se describe la librer a Gandalf, de software libre, que ofrece manejo de matrices. En la parte de visualizaci on comentamos Tambi en varias herramientas para programar interfaces gr acas: la librer a XForms y la librer a Qt

Indice
1. Introducci on 2. Captura de im agenes 2.1. Dispositivos hardware . . . . . . . . . . . 2.2. Instalaci on de video4linux . . . . . . . . . 2.2.1. Digitalizadoras BT878KHF en PC 2.2.2. Utilizar webcams USB en debian . 2.3. Video4linux API . . . . . . . . . . . . . . 1 2 2 2 3 3 5 7 7 8 9

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

. . . . .

3. Procesamiento de im agenes 3.1. Librer a Gandalf . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3.1.1. Instalaci on en el PC de la librer a Gandalf . . . . . . . . . . . . . . . 3.1.2. Compilaci on de un programa que usa la librer a Gandalf. . . . . . .

4. Visualizaci on en interfaces gr acas 4.1. X-Window system . . . . . . . . . . . . . . . . . . . . . . . . 4.2. Librer a XForms . . . . . . . . . . . . . . . . . . . . . . . . . 4.2.1. Elementos gr acos de XForms . . . . . . . . . . . . . . 4.2.2. Construcci on visual de la interfaz gr aca con XForms 4.2.3. Interacci on de XForms con el programa . . . . . . . . 4.3. Librer a Qt . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4.3.1. Instalacion de Qt Free en Linux . . . . . . . . . . . . . 4.3.2. Hola mundo . . . . . . . . . . . . . . . . . . . . . . . .

. . . . . . . .

. . . . . . . .

. . . . . . . .

. . . . . . . .

. . . . . . . .

. . . . . . . .

. . . . . . . .

. . . . . . . .

12 12 13 14 15 16 19 19 20

Agradecimientos
Este manual ha sido realizado en parte por los alumnos del grupo de rob otica de la URJC. Contribuciones importantes se deben a ellos: Francisco Valverde, David Lobato y Marta Mart nez.

1.

Introducci on

La visi on es un sensor m as que los robots pueden utilizar para inferir el estado de su entorno. Es un sensor muy complejo que entrega un ujo continuo de im agenes, pero es dif cil extraer de ese ujo informaci on directamente u til para la acci on del robot. Hoy d a hay en el mercado c amaras disponibles a precios razonables. Las im agenes que la c amara proporciona se pueden capturar en un ordenador y poner disponibles a los programas de control. En el grupo de rob otica1 de la Universidad Rey Juan Carlos tenemos varios escenarios t picos donde utilizamos las im agenes capturadas por una c amara. En el primero la c amara hace de ojo del robot. Por ejemplo en el robot pioneer est a conectada al ordenador port atil de a bordo, que toma decisiones de movimiento basandose en las im agenes. Del mismo modo el robot EyeBot desarrolla comportamiento sigue-pelota utilizando su c amara local. En el segundo marco tenemos una c amara cenital situada encima de un tablero de ping pong donde unos robots EyeBot juegan al futbol. En este caso se utiliza b asicamente como sensor de posici on para todos los jugadores. Normalmente en aplicaciones rob oticas adem as de capturar im agenes querremos visualizarlas. Resulta muy u til por ejemplo para depurar los algoritmos perceptivos o los programas de control. En esta l nea describimos varias librer as que permiten desarrollar interfaces gr acas en m aquinas linux: XForms y Qt.
1

http://gsyc.escet.urjc.es/robotica/

2.

Captura de im agenes

Para ordenadores personales y port atiles que corren sobre el sistema operativo linux se ha desarrollado la interfaz video4linux. Esta interfaz homogeneiza el acceso a las im agenes con independencia de la c amara concreta que se trate. Al ser gen erico los programas o aplicaciones pueden funcionar sobre c amaras o digitalizadoras de distintos fabricantes sin necesidad de recodicaci on. Antes de su existencia cada fabricante entregaba un driver espec co para su c amara o capturadora, que entregaba su imagen de un modo no estandarizado. Por ejemplo si nuestra aplicaci on funcionaba sobre una digitalizadora Matrox Meteor ten amos que instalar el driver correspondiente y utilizar en nuestro c odigo sus funciones espec cas para capturar las im agenes.

2.1.

Dispositivos hardware

C amaras USB, Tarjetas digitalizadoras.

2.2.

Instalaci on de video4linux

Como con todos los dispositivos hardware de un ordenador, si queremos que funcione el kernel del sistema debe incluir soporte para el. Esto se puede conseguir de varias maneras. Por ejemplo se puede patchear el c odigo fuente del kernel para que incluya drivers espec cos. En dispositivos con mejor soporte esos drivers vienen con la propia distribuci on del kernel, e incluirlos en el kernel puede ser tan sencillo como activar una opci on al recompilar, o cargar como m odulo en tiempo de ejecuci on. Hemos probado dos conguraciones. Dos programas muy buenos para probar si la instalaci on ha sido buena son xawtv y vic. Xawtv es un programa muy completo que digitaliza las im agenes de una c amara y las muestra por pantalla, permitiendo una total conguraci on del dispositivo de captura. La p agina de referencia para este programa es http://bytesex.org/xawtv/2 , aunque en las versiones m as recientes ya viene como paquete debian que se puede instalar por el procedimiento estandard de debian (sin traerse el fuente comprimido tar.gz y compilarlo en local). Vic es un programa que se utiliza para transimitir y recibir audio y video desde otras maquinas remotas. La parte u til en este entorno es la que congura el dispositivo de video, captura im agenes y muestra una versi on reducida en local. 2.2.1. Digitalizadoras BT878KHF en PC

Esta tarjeta tiene un chipset de la familia BT8x8 de Book Tree. Es con diferencia la m as difundida en el mundo linux, y por ello tiene amplio soporte software. El m odulo con su driver se llama bttv.
2

http://bytesex.org/xawtv/

La conguraci on exitosa se hizo sobre un kernel 2.2.17, utilizando el m odulo bttv-0.5.35. El primer paso fue recompilar el kernel activando varias opciones como m odulos: 1. 2. 3. 4. 5. videoforlinux (en character devices), como m odulo. bt848 video for linux, como m odulo. CONFIG SOUND=y CONFIG SOUND ES1371=y (es de la tarjeta Creative Ensoniq, muy popular) CONFIG SOUND OSS=y Utilizar webcams USB en debian

2.2.2.

Para que una c amara USB funcione sobre linux (1) el kernel debe ofrecer soporte para el bus USB. Adem as (2) el driver concreto de la c amara debe incluirse tambi en, bien dentro del kernel compilado, bien como m odulo. Desde la versi on 2.2.7 empez o el soporte USB de modo experimental dentro del kernel y se ha estabilizado en las versiones 2.4.*, ofreciendo ya soporte completo. Los m odulos implicados son usbcore, usb-uhci, usb-ohci. En cuanto a las distintas c amaras del laboratorio, hemos probado las siguientes: C amara Terratec : ov511

C amaras Philips : pwc Una p agina muy u til para las c amaras Philips es http://www.smcc.demon.nl/webcam Obtener el kernel Lo primero es conseguir un kernel con soporte para USB, los 2.2.x tienen soporte desde la versi on 2.2.18, pero es preferible utilizar un 2.4.x, ya que aun teniendo tambi en soporte para video4linux en el que est an basados la mayor a de los programas que utilizan los drivers de las c amaras USB, tiene adem as muchas m as c amaras soportadas a parte de las compatibles con ov511. Para realizar este documento se ha utilizado el 2.4.14. Bien, para conseguir un kernel, hay 2 opciones: bien instalar la imagen que vendr a en los CD de la distribuci on que tengas, bien baj artela de ftp://ftp.kernel.org/pub/linux/kernel/v2.4. Si vas a instalar la imagen desde los CDs, abre un terminal y ejecuta dselect (es una herramienta para instalar paquetes en debian, mucho mas sencillo que hacerlo directamente con apt-get), selecciona select pulsa space para pasar la introducci on, entraras en un men u con todos los paquetes de la distribuci on, ahora pulsa /.aparecer a en la esquina inferior izquierda search:pon kernel-source. Cuando encuentres la que buscas pulsa +e intro, a continuaci on volver as al men u inicial. Ahora selecciona install y d ale los CDs que vaya pidiendo. Esto instala la imagen en el directorio /usr/src. El u nico problema es que las fuentes que en mi distribuci on (potato r4) son las del 2.2.19 y a no ser que tengas una woody no creo que vengan las 2.4.x por lo tanto recomiendo la 4

opci on del FTP. Para ello con ectate a ftp://ftp.kernel.org/pub/linux/kernel/v2.4 y b ajate el kernel (.tgz) que m as te guste al directorio /usr/src y descompr melo (tar xvzf kernel-source-2.x.y.tgz o bzip2 -dc kernel-source-2.x.y.tar.bz2 2>/dev/null | tar tvvf -). Compilando e instalando el kernel Hay muchas formas de recompilar el kernel, en este documento no vamos a extendernos demasiado en este tema, si quieres mas informaci on (otros dispositivos) puedes mirar el kernel-HOWTO en debian.org o el del directorio /usr/share/doc/HOWTO en el que encontraras documentaci on sobre el kernel y otras cosas interesantes. Una vez en la carpeta del kernel descomprimido hacemos make xconfig y aparecer a una ventana con un men u, en este men u hay una pesta na en la que pone video4linux support(en la 2.2.19 dentro de C haracter devices) pincha en ella y activa la opci on para que soporte dispositivos de v deo (pinchando en ). Ahora cierra esta ventana (Main Menu) on video4linux y pincha en USB support.activa support for USB si has activado la opci podr as seleccionar USB ov511 camera support. Pincha en Save and exit en el terminal pon make dep, luego make clean para compilar nalmente el kernel hay 2 opciones: 1. Si no estas muy convencido de lo que le has metido a tu kernel puedes hacer make bzdisk, con esto compilar as el kernel y meter as la imagen en un diskette. Una vez compilado reinicia el sistema con el diskette y si todo ha ido bien prueba con la siguiente opci on. make bzImage con esto compilar as el kernel en el directorio /usr/src/kerne-source2.x.y/arch/i386/boot .
2 2 2 2

2.

Copia el archivo bzImageen /boot y edita el archivo /etc/lilo.conf y a nade las siguientes lineas y cambia la l nea default=Linux por default=LinuxUSB. image=/boot/bzImage label=LinuxUSB (o como quieras que se llame tu imagen) read-only optional Guarda los cambios y ejecuta lilo y lilo -q. Con esto la pr oxima vez que reinicies tu sistema lo har as con tu nuevo kernel (si quieres volver a utilizar tu viejo kernel vuelve a cambiar el default=Linux y haz lilo y lilo -q). Ultimos retoques Ahora ya tienes soporte para tu webcam, pero si ejecutas cualquiera de los programas que existen puede suceder que aparezca el siguiente mensaje no such le or device: /dev/videoesto signica que no se crearon los enlaces en /dev, si esto pasa debemos hacerlo a mano. ejecuta esto: mknod /dev/video0 c 81 0, mknod /dev/video1 c 81 5

1,ln -s video0 video nalmente chmod 666 /dev/video /dev/video0 /dev/video1.(mira man mknod, man ln man chmodpara m as informaci on). Con esto ya tienes totalmente congurado el dispositivo. MAKEDEV video.
2 2

Figura 1: Imagen tomada con el interfaz video4linux

2.3.

Video4linux API

Para capturar im agenes utilizando v4l previamente hay que abrir e inicializar el dispositivo correctamente. Por convenio los dispositivos de video en linux aparecen en los cheros /dev/video0, /dev/video1,.... En esta inicializaci on se especican cosas como el tama no de la imagen digitalizada, el formato en el que queremos que se entregue (RGB,YUV...), y la conguraci on de la propia tarjeta de captura. Por ejemplo es t pico que las tarjetas capturadoras tengan varias entradas de video anal ogico (conector S-Video, conector RCA...) y que admita se nales de entrada en distintos formatos (PAL,SECAM,NTSC,etc). En esta etapa se puede especicar que nos interesa digitalizar las im agenes que vienen por la entrada RCA, que vienen en PAL. Una vez inicializado se pueden leer las im agenes con una simple llamada al sistema read(). Sin embargo este modo de leer im agenes es relativamente lento. Cuando se desea capturar a un ritmo mayor es conveniente preparar una zona de la memoria para que el driver deje ah las im agenes que va capturando. Normalmente estas transferencias se hacen por DMA desde la tarjeta a la memoria que le indiquemos. Para que nuestra aplicaci on pueda leer de la zona de memoria (del kernel) donde el driver recoge las im agenes es necesario solicitarlo al kernel con la llamada mmap(). En este u ltimo caso es necesario preparar la captura con alguna funci on adicional, tal y como muestra el siguiente ejemplo: struct video_mmap gb; static struct video_mbuf gb_buffers; 6

fd = open(video, O_RDWR); ... gb_buffers.frames=2; if (cap.type & VID_TYPE_CAPTURE) { /* map grab buffer */ if (-1 == ioctl(fd,VIDIOCGMBUF,&gb_buffers)) { perror("ioctl VIDIOCGMBUF"); } map = mmap(0,gb_buffers.size,PROT_READ|PROT_WRITE,MAP_SHARED,fd,0); if ((char*)-1 != map) printf("Error\n"); else {perror("mmap"); close(fd); exit(-1); } } gb.frame=0; gb.width=win.width; gb.height=win.height; gb.format=vpic.palette; Con ioctl(fd,VIDIOCGMBUF,&gb buffers)) se le pregunta al driver por la conguraci on de la tarjeta, tama no de im agenes, etc, que deja en la variable gb buffers, para luego pedir la compartici on del tama no adecuado. Con map = mmap(0,gb buffers.size,PROT READ|PROT WRITE,MAP SHARED,fd,0); se le pide al sistema operativo compartir la zona, y este entrega su direcci on, si todo va bien. Una vez congurada la captura por memoria mapeada tenemos al driver que constantemente estar a volcando en esa zona las im agenes recien capturadas. En realidad no estar a continuamente, sino que ir a volcando im agenes en el buer hasta que se llene. Una vez que est a saturado no sigue capturando, sino que espera a que el proceso del usuario lea alg un frame. En el ejemplo actual se han congurado memoria para dos cuadros. Mientras el usuario est a leyendo en uno el driver est a rellenando el otro, de manera que si el lector es sucientemente r apido no se detiene nunca la captura. for(;;) { gb.frame=(gb.frame+1)%2; if (-1 == ioctl(fd,VIDIOCMCAPTURE,&gb)) { perror("VIDIOCMCAPTURE"); 7

} /* "libera" ese frame para que el driver pueda cargar ahi nueva imagen.*/ if (-1 == ioctl(fd,VIDIOCSYNC,&gb.frame)) { perror("VIDIOCSYNC"); }

3.
3.1.

Procesamiento de im agenes
Librer a Gandalf

Gandalf es una librer a de C dise nada para soportar el desarrollo de aplicaciones inform aticas en el campo de la visi on. Esta librer a est a compuesta por cuatro paquetes: COMMON : Este paquete dene distintos tipos de datos y funciones para usar en los otros paquetes incluidos en Gandalf. Dispone de diversas funciones para memoria din amica, listas enlazadas, arrays, varias funciones num ericas y permite el manejo de excepciones. LINEAR ALGEBRA : Contiene distintas funciones para el manejo de vectores y matrices. Para aquellos con tama no 2, 3 y 4 dispone de unas funciones predenidas, pero tambi en dispone de otras m as generales para el manejo de matrices y vectores de cualquier tama no. IMAGE : Permite la manipulaci on de im agenes de cualquier formato y tipo. Soporta im agenes en los diferentes niveles de gris, im agenes en RGB con o sin canales Alpha; y distintas profundidades de p xeles. VISION : Este paquete es m as completo que el anterior y posee funciones para la identicaci on de bordes, l neas o esquinas de una gura. 3.1.1. Instalaci on en el PC de la librer a Gandalf

Para la instalaci on de la librer a conviene seguir los siguientes pasos: 1. Bajar el chero gandalf-1-1.tgz de la p agina http://gandalf-library.sourceforge.net . Tambi en conviene bajarse el tutorial incluido en dicha p agina, que explica el contenido de los paquetes de la librer a y las funciones que contienen. A continuaci on descomprimimos el chero, con lo que se crea el directorio gandalf. Dentro de este directorio habr a un chero INSTALL que contiene los pasos a seguir para la instalaci on, que a continuaci on describimos.

2.

3.

Compilamos y construimos la librer a Gandalf, para ello ejecutamos los siguientes comandos: cd gandalf ./configure make

4.

Instalamos las cabeceras y los cheros de la librer a: make install

5.

Comprobamos si est a bien instalada la librer a ejecutando: cd gandalf/TestFramework make ./cUnit -all Esto te comprobar a de una sola vez si los cuatro paquetes se han instalado satisfactoriamente, pero si por el contrario, queremos mirar como se ha instalado un determinado paquete, por ejemplo, el common, lo que har amos ser a: cd gandalf/common make all ./listtext Esto es as , porque cada paquete posee su propio test. El programa TestFramework/cUnit.c lo que hace es compilar y enlazar los tests de cada paquete.

3.1.2.

Compilaci on de un programa que usa la librer a Gandalf.

A la hora de compilar un programa que usa la librer a Gandalf, lo hemos de hacer mediante el uso de un Makefile. El modo de usarlo es el siguiente, supongamos que tenemos el siguiente programa, que se llama prueba.c: /*********************************************************************/ /* PROGRAMA PRUEBA QUE USA LA LIBRER IA GANDALF */ /* */ /* Este programa pide al usuario los datos de 2 matrices, y muestra */ /* ambas matrices por pantalla, luego las suma, las resta, */ /* multiplica y halla su determinada traspuesta y su inversa si la */ /* tuviera. */ 9

/*********************************************************************/ #include <gandalf/common.h> #include <gandalf/linalg.h> #include <stdio.h> int main (){

/* Declaramos las variables */ int i, j; Gan_Matrix33 m33A, m33B, m33C; double dDetA, dDetB; float A[3][3]; float B[3][3]; /* Pedimos los datos por teclado */ printf ("Introduzca los datos de la matriz A: \n"); for (i=0;i<3;i++){ for (j=0;j<3;j++){ printf ("Introduzca A(%d,%d): ", i,j); scanf ("%g", &A[i][j]); } } printf ("Introduzca los datos de la matriz B: \n"); for (i=0;i<3;i++){ for (j=0;j<3;j++){ printf ("Introduzca B(%d,%d): ", i,j); scanf ("%g", &B[i][j]); } } /* Definimos las matrices */ gan_mat33_fill_q (&m33A,A[0][0], A[0][1], A[0][2], A[1][0], A[1][1], A[1][2], A[2][0], A[2][1], A[2][2]); gan_mat33_fill_q (&m33B, B[0][0], B[0][1], B[0][2], B[1][0], B[1][1], B[1][2], B[2][0], B[2][1], B[2][2]); printf ("\n"); /* Escribimos por pantalla las matrices */ gan_mat33_print (&m33A, "Matriz 1", 3, "%f"); gan_mat33_print (&m33B, "Matriz 2", 3, "%f"); 10

printf ("\n"); /* Sumamos y escribimos por pantalla el resultado */ m33C = gan_mat33_add_s(&m33A, &m33B); gan_mat33_print (&m33C, "Suma", 3, "%f"); printf ("\n"); /* Restamos y escribimos por pantalla el resultado */ m33C = gan_mat33_sub_s(&m33A, &m33B); gan_mat33_print(&m33C, "Resta", 3, "%f"); printf ("\n"); /* Multiplicamos y escribimos por pantalla el resultado */ /* C = A*B */ m33C = gan_mat33_rmultm33_s (&m33A, &m33B); gan_mat33_print(&m33C,"Multiplicaci on", 3, "%f"); printf ("\n"); /* Hallamos el determinante de A y B y lo sacamos por pantalla */ dDetA = gan_mat33_det_q (&m33A); printf ("El determinante es: %g\n", dDetA); dDetB = gan_mat33_det_q (&m33B); printf ("El determinante es: %g\n", dDetB); printf ("\n"); /* Tasponemos las matrices A y B y lo sacamos por pantalla */ gan_mat33_tpose_i(&m33A); gan_mat33_print(&m33A, "Transpuesta de A", 3, "%f"); gan_mat33_tpose_i(&m33B); gan_mat33_print(&m33B, "Transpuesta de B", 3, "%f"); printf ("\n"); /* Invertimos las matrices A y B (si se pueden invertir, y sacamos el resultado por pantalla */ gan_mat33_tpose_i(&m33A); if (dDetA!=0){ gan_mat33_invert_i (&m33A); gan_mat33_print(&m33A, "Inversa de A", 3, "%f"); } else { printf ("El determinante de A es 0, por lo que no se puede hallar su inversa. \n"); } 11

gan_mat33_tpose_i(&m33B); if (dDetB!=0){ gan_mat33_invert_i (&m33B); gan_mat33_print(&m33B, "Inversa de B", 3, "%f"); } else { printf ("El determinante de B es 0, por lo que no se puede hallar su inversa. \n"); } return 0; } Pues bien, este programa digamos que est a situado en el directorio ejemplo. Y el directorio gandalf que creamos cuando instalamos la librer a est a en /users/pepe, el Makele quedar a as : # Generated automatically from Makefile.in by configure. CC = gcc PNG_LIBS = -lpng -lz JPEG_LIB = -ljpeg TIFF_LIB = -ltiff LAPACK_LIBS = OPENGL_LIBS = -lglut -lGLU -lGL -lXmu -lX11 X_LIBS = -L/usr/X11R6/lib include /users/pepe/gandalf/Make.inc include /users/pepe/gandalf/config PACKAGE = ejemplo TOPLEVEL = /users/pepe/gandalf EXECUTABLES = prueba targets: $(EXECUTABLES)

prueba: prueba.c libtool $(CC) $(INCLUDES) $(CFLAGS) -static prueba.c -o prueba $(LIB) $(EXTERNAL_LI GARBAGE += $(EXECUTABLES) include /users/pepe/gandalf/make.targets

12

Figura 2: Arquitectura cliente/servidor en una m aquina (izquierda) y en una red (derecha)

4.

Visualizaci on en interfaces gr acas

Un aspecto relevante de nuestras aplicaciones es su interfaz gr aca. A trav es de ella el robot muestra los valores de los distintos sensores de un modo gr aco. De este modo para el usuario resulta sencillo interpretar lo que se le est a mostrando por pantalla. Esta interfaz gr aca tambi en ofrece herramientas para que usuario humano pueda mover el robot a su voluntad. X-Window es el sistema de ventanas escogido para desarrollar nuestras interfaces, por ser el m as extendido dentro del mundo Unix-Linux y ajustarse a nuestras necesidades.

4.1.

X-Window system

El sistema X-Window [X.Org] fue desarrollado a mediados de los a nos 80 en el MIT, movido por la necesidad de dotar al sistema operativo Unix de una interfaz gr aca de usuario. X-Window es el encargado de visualizar la informaci on de manera gr aca y es totalmente independiente del sistema operativo (los sistemas Unix-Linux no necesitan de X-Window para funcionar, pudiendo trabajar en modo texto). Es el sistema gr aco m as extendido en el mundo Unix-Linux. La casi totalidad de las aplicaciones gr acas desarrolladas para Linux han adoptado este sistema llegando a convertirlo en el est andar. As pues Linux ofrece todas las librer as necesarias para desarrollar aplicaciones y generar salidas gr acas conforme a ese est andar. La gran diferencia entre X-Window y la interfaz gr aca de otros sistemas operativos es que X-Window distribuye el procesamiento de aplicaciones, especicando un enlace clienteservidor. El cliente X especicar a qu e hacer al servidor X, que se encargar a de c omo hacerlo. El servidor X es un programa que se ejecuta en una m aquina. A este servidor le llegan solicitudes de clientes X para generar la salida gr aca de una aplicaci on en la pantalla que administra el servidor, que puede ser la de la m aquina que ejecuta el cliente o la de otra m aquina remota. El sistema X-Window oculta las peculiaridades del sistema operativo y del hardware asociado al mismo, simplicando la labor del desarrollador y proporcionando una alta portabilidad de las aplicaciones cliente. La gran ventaja de X-Window es que el servidor X de una aplicaci on y el cliente X 13

donde se trabaja no tienen por qu e estar en la misma m aquina. Se puede utilizar X-Window en una m aquina y conectarse a otra remota, ejecutar un programa en esta m aquina remota y visualizar e interactuar con este programa en la m aquina local. Esta caracter stica de X-Window permite utilizar la interfaz gr aca en cualquier m aquina que soporte este sistema gr aco, consigui endose as una implementaci on adicional a la perseguida, que es la posibilidad de hacer una teleoperaci on remota sobre el robot. Esto implica que el operario de la interfaz gr aca no ha de estar obligatoriamente delante del ordenador donde se ejecuta el programa cliente, sino que puede conectarse a este desde cualquier ordenador y teleoperar el robot. En cuanto a la programaci on, la librer a Xlib ofrece funciones para crear ventanas sencillas y visualizar en ellas im agenes, siempre que tengan un formato adecuado. Ese formato debe entenderlo el servidor X, y en el fondo, la tarjeta de video.

4.2.

Librer a XForms

El sistema X-Window es un sistema relativamente complejo, que ofrece varias interfaces de acceso a su funcionalidad, desde las de m as bajo nivel hasta otras m as elaboradas que ocultan al programador detalles que normalmente no necesita. Las interfaces de bajo nivel permiten m axima exibilidad y control de los detalles de la interacci on gr aca, pero suelen resultar demasiado complicadas para la mayor parte de aplicaciones. En esta direcci on han surgido paquetes software que se montan encima del sistema XWindow ofreciendo distintos objetos gr acos y un repertorio de patrones de interacci on y visualizaci on. Esta reducci on de la exibilidad total del bajo nivel disminuye la complejidad de uso sin recortar excesivamente la funcionalidad que las aplicaciones normales pueden necesitar, facilitando de este modo la programaci on de interfaces gr acas. La librer a XForms [Zhao] es uno de estos paquetes, precisamente el que se ha elegido para desarrollar las interfaces gr acas que necesitemos. Este paquete cuenta con varias ventajas: Es software de libre distribuci on, completamente gratuito para uso no comercial (accesible en http://bragg.phys.uwm.edu/xforms ). Adem as ofrece un repertorio extenso de elementos gr acos (botones, diales , canvas , etc.), suciente para las necesidades que tenemos. Oculta mucha complejidad asociada a las ventanas gr acas, mostrando una interfaz de uso f acil y coherente. XForms est a en perfecta sinton a con el entorno inform atico disponible. Se ejecuta sobre sistema X-Window, con lo que la visualizaci on remota es posible, y est a escrita en C. Tambi en ofrece una herramienta visual, llamada fdesign , muy sencilla, para crear la interfaz gr aca del programa aplicaci on.

14

Figura 3: Elementos gr acos de XForms: Botones, diales y canvas 4.2.1. Elementos gr acos de XForms

La librer a ofrece un amplio repertorio de objetos gr acos con los que confeccionar el frontal gr aco seg un se desee, cada uno de ellos con un determinado comportamiento y funcionalidad. Estos elementos son sensibles a la interacci on con el usuario a trav es del rat on y del teclado. Por otro lado son accesibles y manipulables desde el c odigo del programa aplicaci on. As permiten la comunicaci on bidireccional: al usuario comunicar cosas al programa y al programa mostrar cosas al humano, es decir, la interacci on gr aca entre ambos. Para la implementaci on de la interfaz gr aca del teleoperador el programa cliente necesita utilizar los siguientes elementos gr acos: Bot on que el usuario puede pulsar. De diferentes tipos seg un su comportamiento cuando se pulsa con el rat on: los hay que notican el evento al pulsarlo, que lo notican cuando se suelta, otros se quedan en estado pulsado hasta que se pulse otra vez y los hay que vuelven inmediatamente a su estado de reposo. Dial (slider si no muestra el valor, varslider si lo indica) con los que el usuario puede jar un valor dentro de un rango lineal. Canvas que permite al programa pintar sus propias im agenes, puntos, rectas, etc. Nuestro programa pinta en este canvas las l neas de los infrarrojos, la silueta del robot,... dependiendo de lo que el operario quiera visualizar. Tambi en permite volcar a pantalla im agenes reales obtenidas con la c amara. Posicionador que permite conocer la posici on x y que se ha seleccionado con el rat on gracias al movimiento de unas trazas sobre un area. De este modo se especican 2 valores con un solo click de rat on. Este elemento lo utilizaremos para crear el joystick visual.

15

Figura 4: XForms: Posicionador 4.2.2. Construcci on visual de la interfaz gr aca con XForms

Una vez que se tiene en mente el dise no se construye el frontal gr aco con la herramienta visual que proporciona XForms. Esta construcci on conlleva la selecci on de los distintos elementos gr acos que conforman la interfaz, su tama no, su posici on y sus atributos. El propio paquete XForms ofrece una herramienta visual para construir el frontal gr aco de la aplicaci on. Esta herramienta se llama fdesign y crea una ventana vac a sobre la cual permite ir incorporando distintos elementos gr acos del repertorio (botones, diales , cuadros de texto, canvas ...), que se van situando rellenando el frontal gr aco. Fdesign tambi en permite congurar estos elementos: color, tipo de letra, aspecto, color cuando el rat on lo pulsa, tama no, forma, etc. La posici on se decide con el rat on, seleccionando dentro del repertorio el elemento que queremos insertar, arrastrando hasta donde queremos situarlo en el frontal y solt andolo all . El tama no tambi en se var a visualmente con el rat on, del mismo modo que el tama no de las ventanas de X-Window. Otro tipo de propiedades como color, etiquetas, etc. se conguran cambiando las propiedades del objeto, tambi en visualmente en gran medida, pulsando entre las distintas posibilidades. Una vez acabado el dise no del frontal la herramienta genera tres cheros: nombre.fd en el que guarda todos los elementos con sus atributos y los cheros nombre.h y nombre.c que son los equivalentes en lenguaje C. Gracias a estos u ltimos los programas del usuario pueden iniciar la visualizaci on del frontal, acceder a los distintos elementos del mismo y manipularlos a voluntad. Los objetos gr acos tienen asociadas gran cantidad de funciones que permiten muestrear y jar su estado, acceder y cambiar sus valores, hacer un repintado, etc.

16

Figura 5: Fdesign

Figura 6: Construcci on de una interfaz gr aca con Fdesign

17

4.2.3.

Interacci on de XForms con el programa

La librer a XForms ofrece un modelo de interacci on basado en eventos. Se asocia un area de la ventana a los elementos gr acos y se genera eventos cuando el rat on pasa por encima, cuando el rat on se pulsa o se suelta en ese area, etc. El paquete permite denir callbacks , que son funciones enganchadas a cierto evento sobre un objeto. Estas funciones son invocadas cuando ese evento se produce en el objeto asociado. El enganche entre el evento y la funci on se realiza en el momento de construir la interfaz gr aca, el programador no debe vigilar de nada, salvo denir esa funci on, la librer a se encargar a de llamar al callback cuando proceda. La librer a XForms permite dos modos de operaci on. En el primero toma completamente el control del ujo de ejecuci on y deja todo el funcionamiento del programa en modo reactivo , respondiendo a los eventos que el usuario genera. El segundo esquema permite muestrear , de modo no bloqueante, el estado de la interfaz y mantener el control del ujo de ejecuci on en el programa de la aplicaci on, que decide cu ando muestrear y c omo responder al estado en que se encuentre la interfaz [Canas01]. Este es el esquema que hemos seguido en nuestra aplicaci on, con una hebra peri odica que muestrea el estado del frontal 4 veces cada segundo. El muestreo de los elementos del frontal recorre los distintos objetos de los que consta. La funci on check forms() devuelve el elemento que ha sido modicado reri endose a el como fd nombredelForm -> elemento . Adem as de saber el elemento que ha sido modicado, tambi en es posible saber el estado en el que se encuentra y, si se desea, modicar dicho estado. Por ejemplo, si se trata de un bot on, se puede saber si est a pulsado con la funci on get button (fd nombredelForm -> bot on ) , los valores que devuelve esta funci on son PUSHED si el bot on est a pulsado y RELEASED si no lo est a. Para modicar el estado del bot on se utiliza la funci on set button (fd nombredelForm -> boton, ESTADO ) , siendo el valor de ESTADO igual a PUSHED o RELEASED seg un lo que se desee. Para un posicionador tambi en es posible conocer el valor xy del punto donde sus trazas se cruzan. El valor x se obtiene con la funci on get positioner xvalue (fd nombredelForm -> posicionador ) y el valor y se obtiene con get positioner yvalue (fd nombredelForm -> posicionador) . Para situar el posicionador en un punto se utiliza la funci on set positioner xvalue (fd nombredelForm -> posicionador, valor x) para indicarle la componente x de la posici on, y con la funci on set positioner yvalue (fd nombredelForm -> posicionador, valor y) se le indica la componente y. Para conocer el valor actual del elemento dial se utiliza la funci on get slider value (fd nombredelForm -> slider ) . Tambi en es posible determinar su valor desde el programa con la funci on set slider value (fd nombredelForm -> slider, valor) . Sobre el elemento canvas se pueden utilizar funciones que corresponden a la librer a Xlib . Esta librer a est a un nivel por debajo de XForms. Para dibujar una l nea se utiliza la funci on XDrawLine . En la llamada a esta funci on hay que especicar el canvas donde se desea pintar y las posiciones xy dentro de dicho canvas de los puntos de principio y nal del

18

segmento. Para dibujar puntos se utiliza la funci on XDrawPoints . A esta funci on tambi en hay que indicarle el canvas donde se desea dibujar los puntos, as como las posiciones de dichos puntos. En el elemento canvas tambi en es posible representar una imagen. Para ello se utiliza la funci on XPutImage , indic andole la imagen que se desea visualizar, el tama no de la misma y la posici on que va a ocupar dentro del canvas . Tambi en es posible hacer un repintado de un elemento de un form con la funci on fl redraw object (fd nombredelForm -> elemento) La interfaz gr aca se inserta en el modelo de programaci on multitarea descrito como dos tareas m as: por un lado muestrea si el usuario ha pulsado alg un bot on o slider y por otro peri odicamente refresca la imagen que se le est a mostrando. Cuanto m as corto sea el periodo de muestreo de los botones antes se entera el programa de la interacci on demandada por el usuario y el sistema ser a m as reactivo. Si la tarea de refresco se llama muy frecuentemente la visualizaci on ser a muy vivaz, pero puede consumir mucho tiempo y ralentizar al resto de las tareas, lo cual no es deseable. Se ha decidido hacer un refresco cada segundo y resulta ser un buen compromiso entre la viveza de presentaci on requerida y el ahorro de recursos computacionales que se necesita.

4.3.

Librer a Qt

Esta secci on describe el uso basico de la libreria QT. Est a permite el desarrollo de interfaces gracas muy sencillas y vistosas. El lenguaje de programacion que utiliza es C++. Qt es una libreria C++ que proporciona un toolkit para el desarrollo de interfaces gracas multiplataforma. Qt esta totalmente orientado a objetos, es facilmente extensible, y proporciona verdadera programacion de componentes mediante el mecanismo SIGNALSSLOTS. Qt es la libreria nativa de KDE, el popular entorno de escritorio de Linux. Qt es multiplataforma Una de las principales caracteristicas de Qt, es sin duda, su orientacion multiplataforma. De esta manera, podemos escribir aplicaciones portables a MS/Windows, Unix/X11, Mac y sistemas embebidos, con un minimo de restricciones inerentes a las diferencias entre sistemas ( nombres de cheros, llamadas al sistema, concurrencia, . . . ). Versiones de Qt Qt es un producto de la compa nia noruega trolltech (www.trolltech.com), y se distribuye en diferentes versiones. Estas son: Qt Enterprise Qt Professional

19

Qt Free Qt/Embedded Free Las dos primeras, permiten la costruccion de software comercial, e incluyen actualizaciones y soporte t ecnico. La tercera, Qt Free, es la versi on de Qt para Unix/X11 para el desarrollo de software gratuito y abierto. Esta versi on esta bajo licencia GPL. La u ltima permite el desarrollo de software gratuito, y tambien se acoge a la GPL. 4.3.1. Instalacion de Qt Free en Linux

Una vez obtenido el paquete qt-free-x11-XXX.tar.gz de la pagina de trolltech lo descomprimiremos en /usr/local/qt-free-x11-XXX, y crearemos el enlace qt-qt-free-x11-XXX. Deniremos las variables de entorno QTDIR=/usr/local/qt, LD LIBRARY PATH=QTDIR/lib, MAN PATH=QTDIR/doc/man y PATH=QTDIR/bin. Tras esto, conguraremos la libreria con ./congure ( desde el directorio QTDIR ). En este punto podremos modicar las opciones por defecto que se aplican a la libreria, para ver todas las posibles conguraciones ./congure -help. Y por u ltimo, compilamos com make, proceso que llevara almenos 20 o 30 minutos. Probablemente sea necesario actualizar el chero /etc/ld.conf.so y ejecutar ldcong para qu la libreria sea accesible. Para mas indicaciones sobre el proceso de instalacion debemos mirar el chero INSTALL del directirio QTDIR. 4.3.2. Hola mundo

Por supuesto, el primer programa que se presenta es el tradicional Hola Mundo. En este primer programa, veremos como crear una peque na ventana que contiene la cadena Hola Mundo. El codigo es el siguiente: 1 #include <qapplication.h> 2 #include <qlabel.h> 3 4 int main( int argc, char* argv[] ) 5 { 6 QApplication myapp( argc, argv ); 7 8 QLabel* mylabel = new QLabel( <Hola Mundo!, 0 ); 9 mylabel->resize( 120, 30 ); 10 11 myapp.setMainWidget( mylabel );

20

12 mylabel->show(); 13 return myapp.exec(); 14 } Para compilarlo simplemente ejecutamos: c++ -I$QTDIR/include -L$QTDIR/lib -lqt -o holamundo holamundo.cpp El resultado de la ejecucion lo vemos en la gura 7( el marco depende del gestor de ventanas ).

Figura 7: Ejecucion de holaMundo A continuacion describire el codigo linea a linea. En las primeras lineas tenemos las inclusiones de las cabeceras necesarias. Por lo general, existe una relacion uno a uno entre las cabeceras y las clases que declaran. En nuestro ejemplo necesitamos las decleraciones de las clases QApplication y QLAbel, contenidas en qapplication.h y qlabel.h respectivamente. En la primera linea de la funcion main, tenemos la creaci on del objeto myapp de la clase QApplication, que sera el encargado de llevar el ujo de ejecucion de la aplicacion y de manejar las principales opciones de la aplicacion ( fuentes, paleta, . . . ). Dicho objeto recibe los argumentos de la linea de comandos, por lo que si queremos utilizar alguno de los argumentos debemos hacerlo antes de crear el objeto. En la siguiente linea, creamos un objeto QLabel3 , el cual representara nuestra cadena Hola Mundo. QLabel es un widget( como la gran mayoria de las clases de Qt ), y por ello tiene una representacion graca que atiende a su estado.El segundo argumento pasado al constructor, se reere al padre del widget, que en nuestro caso no existira por lo que bastara con pasarle un 0.Con esto la aplicacion se encargara de destruirlo cuando ya no sea necesario. La linea 9 indica al widget el tama no inicial con el que aparecera por pantalla, si nos basta con que sea visible todo su contenido( Hola Mundo ), podemos eliminar dicha instruccion, ya que Qt elige el tama no mas adecuado por defecto. La linea 11, indica a la aplicaci on cual sera el widget principal, lo que signica que la aplicacion seguira ejecutando hasta que cerremos dicho widget. Para el caso de aplicaciones sin widget principal( multiples ventanas ) debemos utilizar otras t ecnicas.
El hecho de haberlo creado en el heap( usando new ) no es casual, si no, que por norma sera la manera de crear los widgets.La raz on es, que cada widget tendra un padre, de manera que cada widget sera destruido por su padre. De esta manera evitamos el desperdicio de memoria.En nuestro caso particular, el segundo parametro pasado al constructor QLabel indica que no tiene padre, y la aplicacion se encargara de su destruccion.
3

21

A continuaci on, debemos mostrar los widgets creados, que por defecto permanecen ocultos.Para ello basta con llamar al metodo show() comun a todo widget. Por u ltimo, lanzamos el bucle de eventos con el metodo exec() del objeto QApplication.De esta manera la aplicaci on pasa a procesar los eventos recividos hasta que destruyamos el widget principal( cerrando la ventana ).

Referencias
[Zhao] T.C. Zhao and Mark Overmars, Forms Library: a graphical user interface toolkit for X,http://world.std.com/ xforms/. [X.Org] X.Org, X-Window System, http://www.x.org. [Canas01] Jos e M. Ca nas, Manual del robot m ovil Hermes, Informe T ecnico, Instituto de Autom atica Industrial, Julio 2001.

22

También podría gustarte