CONTROL DE EVENTOS

Anuncio
REPÚBLICA BOLIVARIANA DE VENEZUELA
MINISTERIO DE EDUCACIÓN SUPERIOR
FACULTAD DE INGENIERIA
ESCUELA DE ING. ELECTRÓNICA
CÁTEDRA DE COMPUTACIÓN V
SECCION 255
REALIZADO POR:
GÓNGORA, RODRIGO
MICHIELI, JORGE
NEEF, LABERTO
TORO, HOMERO
CARACAS, JUNIO DE 2005
CONTROL DE EVENTOS
En el pasado, un programa que quisiera saber lo que estaba haciendo el
usuario, debía recoger la información él mismo. En la práctica, esto significaba
que una vez inicializado, el programa entraba en un gran bucle en el que
continuamente se bloqueaba para comprobar que el usuario estuviese haciendo
algo interesante (por ejemplo, pulsar un botón, pulsar una tecla, mover una
barra o mover el ratón) y tomar las acciones oportunas. Esta técnica se conoce
como polling.
El polling funciona, pero se vuelve demasiado difícil de manejar con las
aplicaciones modernas por dos razones fundamentales:

Primero, el uso de polling tiende a colocar todo el código de control de
eventos en una única localización (dentro de un gran bucle);

Segundo, las interacciones dentro del gran bucle tienden a ser muy
complejas. Además, el polling necesita que el programa esté ejecutando
el bucle, consumiendo tiempo de CPU, mientras está esperando a que el
usuario se decida a hacer algo, lo que supone un gran despilfarro de
recursos.
El AWT resuelve estos problemas abrazando un paradigma diferente, en el que
están basados todos los sistemas modernos de ventanas: la orientación a eventos.
Dentro del AWT, todas las acciones que pueda realizar el usuario caen dentro
de un gran saco que son los eventos.
Un evento describe, con suficiente detalle, una acción particular del usuario. En
lugar de que el programa activamente recoja todos los eventos generados por el
usuario, el sistema Java avisa al programa cuando se produce un evento
interesante.
La Clase Event
Un contenedor soltado en un entorno gráfico se convierte en rápido receptor de
eventos de todo tipo, singularmente de los relacionados con el movimiento del
ratón, pulsaciones de teclas, creación/movimiento/destrucción de partes
gráficas y, por último, los referidos a acciones del usuario respecto de
componentes (elección de un menú, pulsación de un botón, etc.).
La clase Event es el jugador principal en el juego de los eventos. Intenta
capturar las características fundamentales de todos los eventos que genera el
usuario. Los datos miembro de la clase Event son los que se indican a
continuación:
1. id - El tipo de evento que se ha producido
2. target - Componente sobre el que se ha producido el evento
3. x, y - Las coordenadas en donde se ha producido el evento relativo al
Componente que actualmente está procesando ese evento. El origen se
toma en la esquina superior izquierda del Componente
4. key - Para eventos de teclado, es la tecla que se ha pulsado. Su valor será
el valor Unicode del carácter que representa la tecla. Otros valores que
puede tomas son los de las teclas especiales como INICIO, FIN, F1, F2,
etc.
5. when - Instante en que se ha producido el evento
6. modifiers - La combinación aritmética del estado en que se encuentran
las teclas modificadoras Mays, Alt, Ctrl.
7. clickCount - El número de clicks de ratón consecutivos. Sólo tiene
importancia en los eventos MOUSE_DOWN
8. arg - Es un argumento dependiente del evento. Para objetos Button, este
objeto arg es un objeto String que contiene la etiqueta de texto del botón
9. evt - El siguiente evento en una lista encadenada de eventos
Una instancia de la clase Event será creada por el sistema Java cada vez que se
genere un evento. Es posible, sin embargo, que un programa cree y envíe
eventos a los Componentes a través de su método postEvent().
TIPOS DE EVENTOS
Los eventos se catalogan por su naturaleza, que se indicará en el miembro id de
su estructura. Los grandes grupos de eventos son:
 Eventos de Ventana
Son los que se generan en respuesta a los cambios de una ventana un frame o
un dialogo.



WINDOW_DESTROY
WINDOW_EXPOSE
WINDOW_ICONIFY


WINDOW_DEICONIFY
WINDOW_MOVED
 Eventos de Teclado
Son generados en respuesta a cuando el usuario pulsa y suelta una tecla
mientras un Componente tiene el foco de entrada.




KEY_PRESS
KEY_RELEASE
KEY_ACTION
KEY_ACTION_RELEASE
 Eventos de Ratón
Son los eventos generados por acciones sobre el ratón dentro de los límites de
un Componente.






MOUSE_DOWN
MOUSE_UP
MOUSE_MOVE
MOUSE_ENTER
MOUSE_EXIT
MOUSE_DRAG
 Eventos de Barras
Son los eventos generados como respuesta a la manipulación de barras de
desplazamiento (scrollbars).





SCROLL_LINE_UP
SCROLL_LINE_DOWN
SCROLL_PAGE_UP
SCROLL_PAGE_DOWN
SCROLL_ABSOLUTE
 Eventos de Lista
Son los eventos generados al seleccionar elementos de una lista.


LIST_SELECT
LIST_DESELECT
 Eventos Varios
Son los eventos generados en función de diversas acciones.

ACTION_EVENT




LOAD_FILE
SAVE_FILE
GOT_FOCUS
LOST_FOCUS
El applet EventosPrnt.java está diseñado para observar los eventos que se
producen sobre él. Cada vez que se genera un evento, el applet responde
imprimiendo el evento que ha capturado en la línea de comandos desde donde
se ha lanzado el applet.
Una vez que se haya compilado el código y cargado el applet en el appletviewer
o en un navegador con soporte Java, jugar un poco con el applet. Mover el
cursor dentro del applet, picar con el ratón, picar y arrastrar, teclear algo,
cambiar el tamaño de la ventana y taparla y destaparla con otra. Las acciones
anteriores harán que en la ventana en donde se haya lanzado el appletviewer, o
en la consola Java en caso de Netscape, vayan apareciendo los textos que
indican los eventos que está recibiendo el applet.
Lo cierto es que el uso de System.out.println() en un applet es algo que no
debería utilizarse, e incluso puede llegar a no funcionar en algunos sistemas,
pero tenía la ventaja de ser la forma más fácil de ver los eventos. No obstante,
vamos a reescribir el código del applet utilizando una Lista.
Una Lista es una lista de cadenas o Strings definidas en java.awt.List. Crearemos
una lista de 25 líneas y no permitiremos selección múltiple, que son los dos
parámetros que necesita el constructor del objeto List.
El código EventosList.java que se muestra a continuación corresponde al
anterior ejemplo un poco modificado.
import java.awt.*;
import java.applet.Applet;
public class EventosList extends Applet {
List lista;
public void init() {
lista = new List( 25,false );
add( lista );
lista.addItem( "Evento init" );
}
public void start() {
lista.addItem( "Evento start" );
}
public void destroy() {
lista.addItem( "Evento destroy" );
}
public void paint( Graphics g ) {
lista.addItem( "Evento paint" );
}
public void update( Graphics g ) {
lista.addItem( "Evento update" );
}
public boolean mouseUp( Event evt,int x, int y ) {
lista.addItem( "Evento mouseUp en ("+x+","+y+")" );
return false;
}
public boolean mouseDown( Event evt,int x, int y ) {
lista.addItem( "Evento mouseDown en ("+x+","+y+")" );
return false;
}
public boolean mouseDrag( Event evt,int x, int y ) {
lista.addItem( "Evento mouseDrag en ("+x+","+y+")" );
return false;
}
public boolean mouseMove( Event evt,int x, int y ) {
lista.addItem( "Evento mouseMove en ("+x+","+y+")" );
return false;
}
public boolean mouseEnter( Event evt,int x, int y ) {
lista.addItem( "Evento mouseEnter en ("+x+","+y+")" );
return false;
}
public boolean mouseExit( Event evt,int x, int y ) {
lista.addItem( "Evento mouseExit" );
return false;
}
public boolean keyDown( Event evt,int x ) {
lista.addItem( "Evento keyDown,carácter "+(char)x );
return true;
}
public void getFocus() {
lista.addItem( "Evento getFocus" );
}
public void gotFocus() {
lista.addItem( "Evento gotFocus" );
}
public void lostFocus() {
lista.addItem( "Evento lostFocus" );
}
}
El applet VisorEventos.java muestra los datos que componen cada evento que
se produce. Hemos incorporado un botón y una lista, tal como se puede
apreciar en la figura, para poder generar diferentes eventos.
Moviendo el ratón o actuando sobre los dos Componentes, botón y lista,
podemos observar los datos que el sistema Java envía en la recolección de esos
eventos
GENERACION Y PROPAGACION DE EVENTOS
Tomemos el applet, EventosPro.java, que aparece en la figura siguiente.
Consta de dos instancias de la clase Button, embebidas dentro de una instancia
de la clase Panel. Esta instancia está a su vez embebida dentro de otra instancia
de la clase Panel. Esta última instancia de la clase Panel está situada junto a una
instancia de la clase TextArea, y ambas están embebidas dentro de una
instancia de la clase Applet.
La figura siguiente presenta los elementos que conforman este applet en forma
de árbol, con el TextArea y Button como hojas y la instancia de Applet como
raiz.
Cuando un usuario interactúa con el applet, el sistema Java crea una instancia
de la clase Event y rellena sus datos, miembro con la información necesaria
para describir la acción. Es en ese momento cuando el sistema Java permite al
applet controlar el evento.
Este control comienza por el Componente que recibe inicialmente el evento (por
ejemplo, el botón que ha sido pulsado) y se desplaza hacia arriba en el árbol de
Componentes, componente a componente, hasta que alcanza al Contenedor de
la raíz del árbol. Durante este camino, cada Componente tiene oportunidad de
ignorar el evento o reaccionar ante él en una (o más) de las siguientes maneras:
1. Modificar los datos miembros de la instancia de Event
2. Entrar en acción y realizar cálculos basados en la información
contenida en el evento
3. Indicar al sistema Java que el evento no debería propagarse más
arriba en el árbol
El sistema Java pasa información del evento a un Componente a través del
método handleEvent() del Componente. Todos los métodos handleEvent() deben
ser de la forma:
public boolean handleEvent( Event evt )
Un controlador de eventos solamente necesita una información: una referencia
a la instancia de la clase Event que contiene la información del evento que se ha
producido.
El valor devuelto por el método handleEvent() es importante. Indica al sistema
Java si el evento ha sido o no completamente controlado por el controlador. Un
valor true indica que el evento ha sido controlado y que su propagación debe
detenerse. Un valor false indica que el evento ha sido ignorado, o que no ha
sido controlado en su totalidad y debe continuar su propagación hacia arriba en
el árbol de Componentes.
Veamos la descripción de una acción con el applet de la figura anterior. El
usuario pulsa el botón "Uno". El sistema run-time del lenguaje Java capturará la
información sobre el evento (el número de clicks, la localización del click, la
hora en que se ha producido la pulsación y el Componente que ha recibido el
click) y empaqueta todos esos datos en una instancia de la clase Event.
El sistema Java comienza entonces por el Componente que ha sido pulsado (en
este caso, el botón "Uno") y, a través de una llamada al método handleEvent() del
Componente, ofrece a éste la posibilidad de reaccionar ante el evento. Si el
Componente no controla el evento, o no lo hace completamente (indicado por
un valor de retorno false), el sistema Java presentará la instancia de Event al
siguiente Componente por encima en el árbol (en este caso, una instancia de la
clase Panel). El sistema Java continúa de este mismo modo hasta que el evento
es controlado en su totalidad o ya no hay Componentes a los que informar.
En la figura siguiente mostramos el camino recorrido por el evento en su
intento de que algún Componente lo controle.
Cada Componente del applet añade una línea al objeto TextArea indicando que
ha recibido un evento. Luego permite que el evento se propague al siguiente
Componente.
El código del controlador de eventos usado en el ejemplo es el que muestran las
siguientes líneas:
public boolean handleEvent( Event evt) {
if( evt.id == Event.ACTION_EVENT )
ta.appendText( "Panel " + str + " recibe action...\n" );
else if( evt.id == Event.MOUSE_DOWN )
ta.appendText( "Panel " + str + " recibe mouse_down...\n" );
return super.handleEvent( evt );
}
METODOS DE CONTROL DE EVENTOS
El método handleEvent() es un lugar para que el programador pueda
insertar código para controlar los eventos. A veces, sin embargo, un
Componente solamente estará interesado en eventos de un cierto tipo (por
ejemplo, eventos del ratón). En estos casos, el programador puede colocar el
código en un método de ayuda, en lugar de colocarlo en el método
handleEvent().
No hay métodos de ayuda para ciertos tipos de eventos, aquí está la lista de los
que están disponibles para los programadores:
action( Event evt,Object obj )
gotFocus( Event evt,Object obj )
lostFocus( Event evt,Object obj )
mouseEnter( Event evt,int x,int y )
mouseExit( Event evt,int x,int y )
mouseMove( Event evt,int x,int y )
mouseUp( Event evt,int x,int y )
mouseDown( Event evt,int x,int y )
mouseDrag( Event evt,int x,int y )
keyDown( Event evt,int key )
keyUp( Event evt,int key )
(false indicará que el método de ayuda no maneja el evento)
La implementación del método handleEvent() proporcionada por la clase
Component invoca a cada método de ayuda. Por esta razón, es importante que
las implementaciones redefinidas del método handleEvent() en clases derivadas,
siempre finalicen con la sentencia:
return( super.handleEvent( evt ) );
El siguiente trozo de código ilustra esta regla 
public boolean handleEvent( Event evt ) {
if( evt.target instanceof MiBoton )
{
// Hace algo...
return true;
}
return( super.handleEvent( evt ) );
}
No seguir esta regla tan simple hará que no se invoquen adecuadamente los
métodos de ayuda.
El applet EventosRaton.java, que controla los eventos de ratón exclusivamente a
través de código insertado en sus métodos de ayuda; va dibujando una línea
(rubber band) entre el último punto donde se ha producido un click de ratón y la
posición actual del cursor.
ACTION_EVENT 
Algunos de los eventos que más frecuentemente tendremos que controlar son
los siguientes:




ACTION_EVENT
MOUSE_DOWN
KEY_PRESS
WINDOW_DESTROY
En la documentación de la clase Event se encuentra toda la lista de eventos que
cualquier aplicación puede necesitar manejar y su documentación; como
ejemplo de uso vamos a detenernos en el primero de ellos, ACTION_EVENT.
Como ejemplo del manejo de eventos vamos a ver este evento que se provoca al
pulsar un botón, seleccionar un menú, etc. Para su control podemos manejarlo
en el método handleEvent() o en el método action().
Los dos métodos anteriores pertenecen a la clase Component por lo que todas
las clases derivadas de ésta contendrán estos dos métodos y se pueden
sobrecargar para que se ajuste su funcionamiento a lo que requiere nuestra
aplicación.
Veamos el siguiente ejemplo, en que se controla este evento a través del método
handleEvent(), que es el método general de manejo de eventos:
public boolean handleEvent( Event evt ) {
switch( evt.id ) {
case Event.ACTION_EVENT:
// evt.arg contiene la etiqueta del botón pulsado
// o el item del menú que se ha seleccionado
if( ( "Pulsado "+n+" veces" ).equals( evt.arg ) )
return( true );
default:
return( false );
}
}
Pero en este caso, cuando se produce este evento se llama al método action(),
que sería:
public boolean action( Event evt,Object arg ) {
if( ( "Pulsado "+n+" veces" ).equals( arg ) )
return( true );
return( false );
}
Como se puede comprobar, incluso si las etiquetas cambian se puede recibir el
evento. Los ejemplos anteriores corresponden al control de un evento
producido por un botón que cambia su etiqueta cada vez que se pulsa. Aunque
esta no es la única forma de manejar eventos; de hecho se puede hacer:
if( evt.target == miBoton ), en donde se comparan objetos en lugar de etiquetas.
EL VISOR DE APPLETS DE SUN
El visualizador de applets (appletviewer) es una aplicación que
permite ver en funcionamiento applets, sin necesidad de la utilización
de un navegador World-Wide-Web como HotJava, Microsoft Explorer o
Nescape.
Applet
La definición más extendida de applet, muy bien resumida por Patrick
Naughton, indica que un applet es "una pequeña aplicación accesible en
un servidor Internet, que se transporta por la red, se instala
automáticamente y se ejecuta in situ como parte de un documento web".
Claro que así la definición establece el entorno (Internet, Web, etc.). En
realidad, un applet es una aplicación pretendidamente corta (nada
impide que ocupe más de un gigabyte, a no ser el pensamiento de que
se va a transportar por la red y una mente sensata) basada en un
formato gráfico sin representación independiente: es decir, se trata de
un elemento a embeber en otras aplicaciones; es un componente en su
sentido estricto.
Un ejemplo en otro ámbito de cosas podría ser el siguiente: Imaginemos
una empresa, que cansada de empezar siempre a codificar desde cero,
diseña un formulario con los datos básicos de una persona (nombre,
dirección, etc.). Tal formulario no es un diálogo por sí mismo, pero se
podría integrar en diálogos de clientes, proveedores, empleados, etc. El
hecho de que se integre estática (embebido en un ejecutable) o
dinámicamente (intérpretes, DLLs, etc.) no afecta en absoluto a la
esencia de su comportamiento como componente con que construir
diálogos con sentido autónomo.
Pues bien, así es un applet. Lo que ocurre es que, dado que no existe
una base adecuada para soportar aplicaciones industriales Java en las
que insertar nuestras miniaplicaciones (aunque todo se andará), los
applets se han construido mayoritariamente, y con gran acierto
comercial (parece), como pequeñas aplicaciones interactivas, con
movimiento, luces y sonido... en Internet.
Llamadas a Applets con appletviewer
Un applet es una mínima aplicación Java diseñada para ejecutarse en
un navegador Web. Por tanto, no necesita preocuparse por un método
main() ni en dónde se realizan las llamadas. El applet asume que el
código se está ejecutando desde dentro de un navegador. El
appletviewer se asemeja al mínimo navegador. Espera como argumento
el nombre del fichero html que debe cargar, no se le puede pasar
directamente un programa Java. Este fichero html debe contener una
marca que especifica el código que cargará el appletviewer:
<HTML>
<APPLET CODE=HolaMundo.class WIDTH=300 HEIGHT=100>
</APPLET>
</HTML>
El appletviewer crear un espacio de navegación, incluyendo un área
gráfica, donde se ejecutará el applet, entonces llamará a la clase applet
apropiada. En el ejemplo anterior, el appletviewer cargará una clase de
nombre HolaMundo y le permitirá trabajar en su espacio gráfico.
ARQUITECTURA DE APPLETVIEWER
El appletviewer representa el mínimo interfaz de navegación. En la
figura se muestran los pasos que seguiría appletviewer para
presentarnos el resultado de la ejecución del código de nuestra clase.
Esta es una visión simplificada del appletviewer. La función principal de
esta aplicación es proporcionar al usuario un objeto de tipo Graphics
sobre el que dibujar, y varias funciones para facilitar el uso del objeto
Graphics.
Ciclo de vida de un Applet
Cuando un applet se carga en el appletviewer, comienza su ciclo de
vida, que pasaría por las siguientes fases:

Se crea una instancia de la clase que controla el applet. En el
ejemplo de la figura anterior, sería la clase HolaMundo.

El applet se incializa.

El applet comienza a ejecutarse.

El applet empieza a recibir llamadas. Primero recibe una llamada
init (inicializar), seguida de un mensaje start (empezar) y paint
(pintar). Estas llamadas pueden ser recibidas asíncronamente.
METODOS DE APPLETVIEWER
Vamos a utilizar como excusa la función asociada al appletviewer de los
siguientes métodos para adentrarnos en su presentación, aunque a lo
largo de secciones posteriores, volveremos a referirnos a ellos, porque
también son los métodos propios de la clase Applet.
init()
El método init() se llama cada vez que el appletviewer carga por primera
vez la clase. Si el applet llamado no lo sobrecarga, init() no hace nada.
Fundamentalmente en este método se debe fijar el tamaño del applet,
aunque en el caso de Netscape el tamaño que vale es el que se indique
en la línea del fichero html que cargue el applet. También se deben
realizar en este método las cargas de imágenes y sonidos necesarios
para la ejecución del applet. Y, por supuesto, la asignación de valores a
las variables globales a la clase que se utilicen. En el caso de los applet,
este método únicamente es llamado por el sistema al cargar el applet.
start()
start() es la llamada para arrancar el applet cada vez que es visitado. La
clase Applet no hace nada en este método. Las clases derivadas deben
sobrecargarlo para comenzar la animación, el sonido, etc. Esta función
es llamada automáticamente cada vez que la zona de visualización en
que está ubicado el applet se expone a la visión, a fin de optimizar en
uso de los recursos del sistema y no ejecutar algo que no puede ser
apreciado (aunque el programador puede variar este comportamiento y
hacer que un applet siga activo aun cuando esté fuera del área de
visión). Esto es, imaginemos que cargamos un applet en un navegador
minimizado; el sistema llamará al método init(), pero no a start(), que sí
será llamado cuando restauremos el navegador a un tamaño que
permita ver el applet. Naturalmente, start() se puede ejecutar varias
veces: la primera tras init() y las siguientes (porque init() se ejecuta
solamente una vez) tras haber aplicado el método stop().
stop()
stop() es la llamada para detener la ejecución del applet. Se llama
cuando el applet desaparece de la pantalla. La clase Applet tampoco
hace nada en este método, que debería ser sobrecargado por las clases
derivadas para detener la animación, el sonido, etc. Esta función es
llamada cuando el navegador no incluye en su campo de visión al
applet; por ejemplo, cuando abandona la página en que está insertado,
de forma que el programador puede paralizar los threads que no
resulten necesarios respecto de un applet no visible, y luego recuperar
su actividad mediante el método start().
destroy()
El método destroy() se llama cuando ya no se va a utilizar más el applet,
cuando se necesita que sean liberados todos los recursos dispuestos
por el applet, por ejemplo, cuando se cierra el navegador. La clase
Applet no hace nada en este método. Las clases derivadas deberían
sobrecargarlo para hacer una limpieza final. Los applet multithread
deberían utilizar destroy() para detener los threads que quedasen
activos.
El appletviewer también contiene la clase Component (componente),
que usa dos métodos para ayudas al applet a escribir en el espacio
gráfico que el appletviewer le proporciona para su ejecución.
paint( Graphics g )
Es la función llamada cada vez que el área de dibujo del applet necesita
ser refrescada. La clase Applet simplemente dibuja un rectángulo gris
en el área, es la clase derivada, obviamente, la que debería sobrecargar
este método para representar algo inteligente en la pantalla. Cada vez
que la zona del applet es cubierta por otra ventana, se desplaza el
applet fuera de la visión o el applet cambia de posición debido a un
redimensionamiento del navegador, el sistema llama automáticamente a
este método, pasando como argumento un objeto de tipo Graphics que
delimita la zona a ser pintada; en realidad se pasa una referencia al
contexto gráfico en uso, y que representa la ventana del applet en la
página web.
update( Graphics g )
Esta es la función que realmente se llama cuando se necesita una
actualización de la pantalla. La clase Applet simplemente limpia el área
y llama al método paint(). Esta funcionalidad es suficiente para la
mayoría de los casos; aunque, de cualquier forma, las clases derivadas
pueden sustituir esta funcionalidad para sus propósitos especiales. Es
decir, en las situaciones detalladas anteriormente que dañan la zona de
exposición del applet, el sistema llama al método paint(), pero en
realidad la llamada se realiza al método update(), cuyo comportamiento
establecido en la clase Component es llamar al método paint(), tras
haber rellenado la zona del applet con su color de fondo por defecto.
Pudiera parecer así que se trata de un método de efecto neutro, pero si
la función paint() cambiara el color del fondo, podríamos percibir un
flick de cambio de colores nada agradable. Por tanto, habrá que
cuidarse por lo común, de eliminar este efecto de limpia primero,
sobrecargando el método update(), para que llame únicamente a paint().
Otra solución sería insertar el código de pintado en una sobrecarga del
método update() y escribir un método paint() que sólo llame a update().
La última solución pasaría por usar el mismo método setBackground(
Color ), en el método init() para así evitar el efecto visual sin tener que
sobrecargar el método update(). Estas son las mismas razones que
aconsejan usar el método resize() inserto en init(), para evitar el mismo
desagradable efecto.
repaint
Llamando a este método se podrá forzar la actualización de un applet,
la llamada a update(). Pero hay que tener cierto cuidado, porque AWT
posee cierta inteligencia (combinación casi siempre nefasta), de forma
que si se llama a update() mediante repaint() con una frecuencia muy
corta, AWT ignorará las llamadas a update() que estime oportuno, pues
considera a esta función como un bien escaso.
Sinopsis
La llamada a appletviewer es de la forma:
appletviewer [-debug] urls...
El appletviewer toma como parámetro de ejecución, o bien el nombre
del un fichero html conteniendo el tag (marca) <APPLET>, o bien un
URL hacia un fichero HTML que contenga esa marca.
Si el fichero html no contiene un tag <APPLET> válido, el appletviewer
no hará nada. El appletviewer no muestra otras marcas html.
La única opción válida que admite la llamada a appletviewer es -debug,
que arranca el applet en el depurador de Java, jdb. Para poder ver el
código fuente en el depurador, se tiene que compilar el fichero .java con
la opción -g.
Ejemplo de uso
En el ejemplo de llamada al appletviewer siguiente, hacemos que se
ejecute el applet básico que crearemos en la sección siguiente y que
lanzaremos desde un fichero html del mismo nombre que nuestro
fichero de código fuente Java.
%appletviewer HolaMundo.html
Esta llamada lanzaría la ejecución de HolaMundo.class
appletviewer, abriéndose en pantalla la ventana siguiente:
en
el
FUNCIONES DE MENU DE APPLETVIEWER
El appletviewer tiene un único menú mostrado en la imagen siguiente y
que vamos a explicar en cada una de sus opciones, ya que lo usaremos
a menudo cuando vayamos avanzando en nuestros conocimientos de
Java.

Restart
La función Restart llama al método stop() y seguidamente llama de
nuevo a start(), que es el método que ha lanzado inicialmente la
ejecución del applet. Se puede utilizar Restart para simular el
movimiento entre páginas en un documento html.

Reload
La función Reload llama al método stop() y luego al método destroy() en
el applet actual. A continuación carga una nueva copia del applet y la
arranca llamando al método start().

Clone
La función Clone crea una copia del applet actual en una ventana de
appletviewer nueva. En realidad es un appletviewer idéntico con el
mismo URL.

Tag
La función Tag muestra en una ventana hija del appletviewer el código
html cargado para su ejecución. Es similar a la función View Source que
figura en la mayoría de los navegadores, Netscape, Internet Explorer y
HotJava incluidos.

Info
La función Info lee los comentarios de documentación contenidos en el
fichero html y muestra la información de los parámetros (si la hay).

Properties
El appletviewer tiene las funciones básicas de presentación de un
navegador y la función Properties (propiedades de la red) permite
cambiar o establecer el modo de seguridad o fijar los servidores de
proxy o firewall.

Close
La función Close llama al método destroy() de la ventana actual del
appletviewer, teminando su ejecución.

Quit
La función Quit llama al método destroy() de cada una de las copias del
appletviewer que se encuentren lanzadas, concluyendo la ejecución de
todas ellas y terminando entonces el appletviewer.
UN APPLET BASICO EN JAVA
Vamos a comenzar la creación del código fuente del un applet que
satisfaga nuestras necesidades. Recordamos que Java utiliza la
extensión .java para designar los ficheros fuente.
HolaMundo
A continuación está el código fuente del applet HolaMundo, que es la
versión applet de la mínima aplicación Java que antes habíamos
escrito. Guardar este código en un fichero fuente Java como
HolaMundo.java.
//
// Applet HolaMundo de ejemplo
//
import java.awt.Graphics;
import java.applet.Applet;
public class HolaMundo extends Applet {
public void paint( Graphics g ) {
g.drawString( "Hola Mundo!",25,25 ) ;
}
}
Componentes básicos de un Applet
El lenguaje Java implementa un modelo de Programación Orientada a
Objetos. Los objetos sirven de bloques centrales de construcción de los
programas Java. De la misma forma que otros lenguajes de
programación, Java tiene variables de estado y métodos.
Veamos como se descompone un applet en sus piezas/objetos:
/*
Sección de importaciones
*/
public class NombreDelNuevoApplet extends Applet {
/*
Aquí se declaran las variables de estado (public y private)
*/
/*
Los métodos para la interacción con los objetos se
declaran y definen aquí
*/
public void MetodoUno( parámetros ) {
/*
Aquí viene para cada método, el código Java que
desempeña la tarea.
Qué código se use depende del applet
*/
}
}
Para HolaMundo, se importan las dos clases que necesita. No hay
variables de estado, y sólo se tiene que definir un método para que el
applet tenga el comportamiento esperado.
Clases incluidas
El comando import carga otras clases dentro de nuestro código fuente.
El importar una clase desde un paquete de Java hace que esa clase
importada esté disponible para todo el código incluido en el fichero
fuente Java que la importa. Por ejemplo, en el applet HolaMundo se
importa la clase java.awt.Graphics, y podremos llamar a los métodos de
esta clase desde cualquier método de nuestro programa que se
encuentre en el fichero HolaMundo.java. Esta clase define una área
gráfica y métodos para poder dibujar dentro de ella. La función paint()
declara a g como un objeto de tipo Graphics; luego, paint() usa el
método drawString() de la clase Graphics para generar su salida.
La clase Applet
Se puede crear una nueva clase, en este caso HolaMundo, extendiendo
la clase básica de Java: Applet. De esta forma, se hereda todo lo
necesario para crear un applet. Modificando determinados métodos del
applet, podemos lograr que lleve a cabo las funciones que deseamos.
import java.applet.Applet;
. . .
public
class
HolaMundo
extends
Applet
{
Métodos de Applet
La parte del applet a modificar es el método paint(). En la clase Applet,
se llama al método paint() cada vez que el método arranca o necesita ser
refrescado, pero no hace nada. En nuestro caso, lo que hacemos es:
public void paint( Graphics g ) {
g.drawString( "Hola Mundo!",25,25 );
}
De acuerdo a las normas de sobrecarga, se ejecutará este último paint()
y no el paint() vacío de la clase Applet. Luego, aquí se ejecuta el método
drawString(), que le dice al applet cómo debe aparecer un texto en el
área de dibujo.
Otros métodos básicos para dibujar son:
drawLine( int x1,int y1,int x2,int y2 )
drawRect( int x,int y,int ancho,int alto )
drawOval( int x,int y,int ancho,int alto )
Tanto para drawRect() como para drawOval(), las coordenadas (x,y) son
la esquina superior izquierda del rectángulo (para drawOval, el óvalo es
encajado en el rectángulo que lo circunscribe).
COMPILACION DE UN APPLET
Ahora que tenemos el código de nuestro applet básico y el fichero fuente
Java que lo contiene, necesitamos compilarlo y obtener un fichero .class
ejecutable. Se utiliza el compilador Java, javac, para realizar la tarea. El
comando de compilación será:
%javac HolaMundo.java
Eso es todo. El compilador javac generará un fichero HolaMundo.class
que podrá ser llamado desde cualquier navegador con soporte Java y,
por tanto, capaz de ejecutar applets Java.
Llamada a Applets
¿Qué tienen de especial HotJava, Microsoft Explorer o Netscape con
respecto a otros navegadores? Con ellos se puede ver html básico y
acceder a todo el texto, gráfico, sonido e hipertexto que se pueda ver
con cualquier otro navegador. Pero además, pueden ejecutar applets,
que no es html estándar. Ambos navegadores entienden código html
que lleve la marca <APPLET>:
<APPLET CODE="SuCodigo.class" WIDTH=100 HEIGHT=50>
</APPLET>
Esta marca html llama al applet SuCodigo.class y establece su ancho y
alto inicial. Cuando se acceda a la página Web donde se encuentre
incluida la marca, se ejecutará el byte-code contenido en
SuCodigo.class, obteniéndose el resultado de la ejecución del applet en
la ventana del navegador, con soporte Java, que estemos utilizando.
Prueba de un Applet
El JDK, Kit de Desarrollo de Java, incluye el visor de applets básico,
appletviewer, que puede utilizarse para la visualización rápida y prueba
de nuestros applets, tal como se ha visto ya. La ejecución de un applet
sobre appletviewer se realiza a través de la llamada:
%appletviewer fichero.html
En nuestro caso el fichero con el código html que ejecutará nuestro
applet HolaMundo es HolaMundo.html que generará la salida que se
mostraba en la sección sobre el de appletviewer.
LA MARCA APPLET DE HTML
Dado que los applets están mayormente destinados a ejecutarse en
navegadores Web, había que preparar el lenguaje HTML para soportar
Java, o mejor, los applets. El esquema de marcas de HTML, y la
evolución del estándar marcado por Netscape hicieron fácil la adición de
una nueva marca que permitiera, una vez añadido el correspondiente
código gestor en los navegadores, la ejecución de programas Java en
ellos.
La sintaxis de las etiquetas <APPLET> y <PARAM> es la que se muestra
a continuación y que iremos explicando en párrafos posteriores:
<APPLET CODE= WIDTH= HEIGTH= [CODEBASE=] [ALT=]
[NAME=] [ALIGN=] [VSPACE=] [HSPACE=]>
<PARAM NAME= VALUE= >
</APPLET>
Atributos obligatorios:
CODE : Nombre de la clase principal
WIDTH : Anchura inicial
HEIGHT : Altura inicial
Atributos opcionales:
CODEBASE : URL base del applet
ALT : Texto alternativo
NAME : Nombre de la instancia
ALIGN : Justificación del applet
VSPACE : Espaciado vertical
HSPACE : Espaciado horizontal
Los applets se incluyen en las páginas Web a través de la marca
<APPLET>, que para quien conozca html resultará muy similar a la
marca <IMG>. Ambas necesitan la referencia a un fichero fuente que no
forma parte de la página en que se encuentran embebidos. IMG hace
esto a través de SRC=parámetro y APPLET lo hace a través
CODE=parámetro. El parámetro de CODE indica al navegador dónde se
encuentra el fichero con el código Java compilado .class. Es una
localización relativa al documento fuente.
Por razones que no entiendo muy bien, pero posiblemente relacionadas
con los packages y classpaths, si un applet reside en un directorio
diferente del que contiene a la página en que se encuentra embebido,
entonces no se indica un URL a esta localización, sino que se apunta al
directorio del fichero .class utilizando el parámetro CODEBASE, aunque
todavía se puede usar CODE para proporcionar el nombre del fichero
.class.
Al igual que IMG, APPLET tiene una serie de parámetros que lo
posicionan en la página. WIDTH y HEIGHT especifican el tamaño del
rectángulo que contendrá al applet, se indican en pixels. ALIGN
funciona igual que con IMG (en los navegadores que lo soportan),
definiendo cómo se posiciona el rectángulo del applet con respecto a los
otros elementos de la página. Los valores posibles a especificar son:
LEFT, RIGHT, TOP, TEXTTOP, MIDDLE, ABSMIDDLE, BASELINE,
BOTTOM y ABSBOTTOM. Y, finalmente, lo mismo que con IMG, se
puede especificar un HSPACE y un VSPACE en pixels para indicar la
cantidad de espacio vacío que habrá de separación entre el applet y el
texto que le rodea.
APPLET tiene una marca ALT. La utilizaría un navegador que
entendiese la marca APPLET, pero que por alguna razón, no pudiese
ejecutarlo. Por ejemplo, si un applet necesita escribir en el disco duro
de nuestro ordenador, pero en las características de seguridad tenemos
bloqueada esa posibilidad, entonces el navegador presentaría el texto
asociado a ALT.
ALT no es utilizado por los navegadores que no entienden la marca
APPLET, por ello se ha definido la marca </APPLET>, que finaliza la
descripción del applet. Un navegador con soporte Java ignorará todo el
texto que haya entre las dos marcas <APPLET> y </APPLET>, sin
embargo, un navegador que no soporte Java ignorará las marcas y
presentará el texto que se encuentre entre ellas.
ATRIBUTOS DE APPLET
Los atributos que acompañan a la etiqueta <APPLET>, algunos son
obligatorios y otros son opcionales. Todos los atributos, siguiendo la
sintaxis de html, se especifican de la forma: atributo=valor. Los
atributos obligatorios son:
CODE
Indica el fichero de clase ejecutable, que tiene la extensión .class. No se
permite un URL absoluto, como ya se ha dicho, aunque sí puede ser
relativo al atributo opcional CODEBASE.
WIDTH
Indica la anchura inicial que el navegador debe reservar para el applet
en pixels.
HEIGHT
Indica la altura inicial en pixels. Un applet que disponga de una
geometría fija no se verá redimensionado por estos atributos. Por ello, si
los atributos definen una zona menor que la que el applet utiliza,
únicamente se verá parte del mismo, como si se visualiza a través de
una ventana, eso sí, sin ningún tipo de desplazamiento.
Los atributos opcionales que pueden acompañar a la marca APPLET
comprenden los que se indican a continuación:
CODEBASE
Se emplea para utilizar el URL base del applet. En caso de no
especificarse, se utilizará el mismo que tiene el documento.
ALT
Como ya se ha dicho, funciona exactamente igual que el ALT de la
marca <IMG>, es decir, muestra un texto alternativo, en este caso al
applet, en navegadores en modo texto o que entiendan la etiqueta
APPLET pero no implementen una máquina virtual Java.
NAME
Otorga un nombre simbólico a esta instancia del applet en la página
que puede ser empleado por otros applets de la misma página para
localizarlo. Así, un applet puede ser cargado varias veces en la misma
página tomando un nombre simbólico distinto en cada momento.
ALIGN
Se emplea para alinear el applet permitiendo al texto fluir a su
alrededor. Puede tomas los siguientes valores: LEFT, RIGHT, TOP,
TEXTTOP,
MIDDLE,
ABSMIDDLE,
BASELINE,
BOTTOM
y
ABSBOTTOM.
VSPACE
Indica el espaciado vertical entre el applet y el texto, en pixels. Sólo
funciona cuando se ha indicado ALIGN = LEFT o RIGHT.
HSPACE
Funciona igual que el anterior pero indicando espaciamiento horizontal,
en pixels. Sólo funciona cuando se ha indicado ALIGN = LEFT o RIGHT.
Es probable encontrar en algunas distribuciones otras etiquetas para la
inclusión de applets, como <APP>. Esto se debe a que estamos ante la
tercera revisión de la extensión de HTML para la incrustación de applets
y ha sido adoptada como la definitiva. Por ello, cualquier otro medio
corresponde a implementaciones obsoletas que han quedado
descartadas.
PASO DE PARAMETROS A APPLETS
El espacio que queda entre las marcas de apertura y cierre de la
definición de un applet, se utiliza para el paso de parámetros al applet.
Para ello se utiliza la marca PARAM en la página HTML para indicar los
parámetros y el método getParameter() de la clase java.applet.Applet
para leerlos en el código interno del applet. La construcción puede
repetirse cuantas veces se quiera, una tras otra.
Los atributos que acompañan a la marca PARAM son los siguientes:
NAME
Nombre del parámetro que se desea pasar al applet.
VALUE
Valor que se desea transmitir en el parámetro que se ha indicado antes.
Texto HTML
Texto HTML que será interpretado por los navegadores que no
entienden la marca APPLET en sustitución del applet mismo.
Para mostar esta posibilidad vamos a modificar nuestro applet básico
HolaMundo para que pueda saludar a cualquiera. Lo que haremos será
pasarle al applet el nombre de la persona a quien queremos saludar.
Generamos el código para ello y lo guardamos en el fichero HolaTal.java
import java.awt.Graphics;
import java.applet.Applet;
public class HolaTal extends Applet {
String nombre;
public void init() {
nombre = getParameter( "Nombre" );
}
public void paint( Graphics g ) {
g.drawString( "Hola "+nombre+"!",25,25 );
}
}
Si compilamos el ejemplo obtendremos el fichero HolaTal.class que
incluiremos en nuestra página Web. Vamos a generar el fichero
HolaTal.html, en el que incluiremos nuestro applet, y que debería tener
el siguiente contenido:
<HTML>
<APPLET CODE=HolaTal.class WIDTH=300 HEIGHT=100>
<PARAM NAME="Nombre" VALUE="Agustin">
</APPLET>
</HTML>
Por supuesto, que puedes sustituir mi nombre por el tuyo. Este cambio
no afectará al código Java, no será necesario recompilarlo para que te
salude a ti el applet.
Los parámetros no se limitan a uno solo. Se puede pasar al applet
cualquier número de parámetros y siempre hay que indicar un nombre
y un valor para cada uno de ellos.
El método getParameter() es fácil de entender. El único argumento que
necesita es el nombre del parámetro cuyo valor queremos recuperar.
Todos los parámetros se pasan como Strings, en caso de necesitar
pasarle al applet un valor entero, se ha de pasar como String,
recuperarlo como tal y luego convertirlo al tipo que deseemos. Tanto el
argumento de NAME como el de VALUE deben ir colocados entre dobles
comillas (") ya que son String.
El hecho de que las marcas <APPLET> y <PARAM> sean ignoradas por
los navegadores que no entienden Java, es inteligentemente
aprovechado a la hora de definir un contenido alternativo a ser
mostrado en este último caso. Así la etiqueta es doble:
<APPLET atributos>
parámetros
contenido alternativo
</APPLET>
Nuestro fichero para mostrar el applet de ejemplo lo modificaremos para
que pueda ser visualizado en cualquier navegador y en unos casos
presente la información alternativa y en otros, ejcute nuestro applet:
<HTML>
<APPLET CODE=HolaTal.class WIDTH=300 HEIGHT=100>
<PARAM NAME="Nombre" VALUE="Agustin">
No verás lo bueno hasta que consigas un navegador
<I>Java Compatible</I>
</APPLET>
</HTML>
CONCLUSION
Para nosotros la realización de este trabajo fue un poco
confuso y complicado, debido a que nuestro manejo sobre el tema no es
mucho que podamos decir. Con la investigación del tema pudimos
comprender de una manera un poco más profunda sobre los Eventos y
Applets en el lenguaje JAVA. A pesar de que este lenguaje es nuevo,
relativamente, es un lenguaje que está agarrando mucha fuerza en el
mundo de la WEB, por lo que es de gran importancia realizar un
estudio, del mismo.
Los eventos dentro del java nos permiten mantener un control
de todas aquellas acciones que ocurren en interacción con las cosas
que ocurren dentro del programa basado en java.
Los applets, nos permiten crear elementos de forma gráfica, por
lo que permiten una mejor interacción con el usuario. Los applets son
muy sencillos de usar y nos permiten, a la hora de verlo funcionando,
llamar más la atención del usuario por medios gráficos.
A pesar de que fue un trabajo complejo, por nuestro escaso
dominio del tema, nos pareció muy interesante ya que nos permitió
generar conocimientos que no existían en nuestras personas.
Descargar