API de
sistema gráfico con Entrada
El siguiente es un programa mínimo que sólo abre una ventana gráfica:
#include <stdio.h>
#include "include/Grafico.h"
main(){
ventanaB(700,500); // abre una ventana y main queda bloqueada
//ventana(700,500); esta si no se quiere el bloqueo de main
}
Este programa mínimo asume que el
archivo Grafico.h se
encuentra
en el directorio include.
Un programa mínimo que maneja eventos de mouse, debe incluir las
siguientes funciones:
#include "include/Grafico.h"
void update(){agregar sentencias en este lugar}
void mousePress(int x, int y, int b){agregar sentencias en este lugar}
void mouseRelease(int x, int y, int boton){agregar sentencias en este lugar}
void mouseMove(int x,int y){agregar sentencias en este lugar}
void mouseDrag(int x,int y, int b){agregar sentencias en este lugar}
void keyPress(unsigned long key){agregar sentencias en este lugar}
main(){
setUpdateListener(update);
setMousePressListener(mousePress); //habilitan a las funciones con nombres en rojo como receptoras de eventos
setMouseReleaseListener(mouseRelease);
setMouseMoveListener(mouseMove);
setMouseDragListener(mouseDrag);
setKeyPressListener(keyPress);
ventanaB(700,500); // abre una ventana y main queda bloqueada
//ventana(700,500); esta si no se quiere el bloqueo de main
}
Las funciones en rojo
deben ser "habilitadas" para que los eventos sean enviados a ellas. Se
pueden inscribir las que se deseen. Pueden tener otros
nombres siempre que
conserven los parámetros.
a) Las funciones siguientes inscriben a las funciones cuyos
nombres se pasan como parámetros para que manejen los eventos de
ventana, mouse y teclado.
setUpdateListener(update);
setMousePressListener(mousePress);
setMouseReleaseListener(mouseRelease);
setMouseMoveListener(mouseMove);
setMouseDragListener(mouseDrag);
setKeyPressListener(keyPress);
b) En la función función main se debe llamar una sóla de las funciones
siguientes:
ventana(int dx, int dy)
Esta función crea una ventana de ancho dx y alto dy, es una función no-bloqueante, es
decir, se crea la ventana pero sigue la ejecución en la sentencia
siguiente. Si la función main termina la ventana se cierra. Esta
función
se debe usar si se quiere tener una hebra de ejecución mientras la
ventana está activa, esto es, combinar la programación orientada al
evento con la procedural.
ventanaB(int, int)
Esta función crea una ventana de ancho dx y alto dy, es una función bloqueante, es
decir, se crea la ventana pero no sigue la ejecución en la sentecia
siguiente. Es útil si sólo se va a crear un programa orientado al
evento.
c) Las funciones:
void mousePress(int x, int y, int boton)
void mouseRelease(int x, int y, int boton)
void mouseMove(int x,int y)
void mouseDrag(int x,int y, int boton)
son llamadas cuando ocurren los eventos
de mouse de oprimir un botón, mover el mouse y mover el mouse con un
botón oprimido dentro de la ventana. Los argumentos x e y
tienen las coordenadas del cursor al ocurrir el evento. El argumento boton indica qué botón del mouse
produjo el evento con los valores 1,2 y 3. Se les debe incorporar las
sentencias que manejen la situación para ele evento correspondiente.
Si no se incluyen sus declaraciones (aunque el cuerpo no haga nada), no
se genera el programa ejecutable. Estas funciones no deben ser llamadas
por otra función.
Pueden tener otros nombres siempre que conserven los mismos parámetros.
d) La función:
void update()
es llamada cada vez que la ventana
es abierta por la función ventana()
o ventanaB(). Se puede llamar
directamente.
Pueden tener otro nombre.
e) Los colores definidos son los siguientes:
#define negro "#000000"
#define blanco "#ffffff"
#define rojo "#ff0000"
#define verde "#00ff00"
#define azul "#0000ff"
#define amarillo "#ffff00"
#define magenta "#ff00ff"
#define cyan "#00ffff"
#define nuevocolor "#905523"
Se pueden agregar más colores creando
nuevos string estáticos o bién en forma dinámica.
f) Las siguientes funciones pueden ser llamadas desde el nuevo programa:
void ventana(int, int);
void ventanaB(int, int);
void setForegroundColor(const char *); // cambia el color del pincel
void setForegroundColorRGB(unsigned char R,unsigned char G,unsigned char B); // cambia el color del pincel
void setGrosorLinea(unsigned int); // cambia el grosor de la linea que se dibuja
int ancho(void); // devuelve el ancho de la ventana
int alto(void); // devuelve el alto de la ventana
g) Las siguientes funciones dibujan en un bufer que es memoria distinta
de la ventana, es decir, no aparecen de inmediato en ella.
Luego de dibujar todas las figuras en el bufer, se debe
llamar a la
función display(), que copia
desde el bufer a la ventana.
El bufer no se borra al ser llamada la función display();
void fillArc(int x,int y,int dx,int dy,int angulo1,int angulo2);
void drawArc(int x,int y,int dx,int dy,int angulo1,int angulo2);
void fillRect(int x, int y, int dx, int dy);
void drawRect(int, int, int, int);
void drawString(char *,int, int);
void drawLine(int, int, int, int);
void fillPolygon(Xpoint p[], int npoints); //p es una estructura de "npoints" pares: p[i].x y p[i].y
void drawPolyline(Xpoint p[], int npoints);
h) La función:
void update(void);
debe ser declarada en el programa es
para dibujos de partida, es decir, es llamada aotomáticamente al
abrirse
la ventana.
i) la función:
void display(void);
copia el contenido del bufer en el
diplay de la ventana. Se debe llamar una vez al final de de las
llamadas
a las funciones de dibujo.
j) la función:
void setCursor(unsigned int micursor);
cambia el cursor . Ver lista
de cursores
Ejemplo: setCursor(XC_watch);
k) la función:
void keyPress(unsigned long key);
entrega el código de la tecla oprimida cuando la ventana está activa.
Para detalle de los códigos ver el archivo:
/usr/include/X11/keysymdef.h