>>
Lección 07

Despliegues.


Despliegues.


Un despliegue es un objeto de la clase Layout. Los contenedores tienen un método setLayout(Layout l) con el que se les puede asignar cualquier despliegue. La finalidad de los despliegues es facilitar al programador el trabajo de acomodar los componentes gráficos. En este curso se presentan tres despliegues que son los más fáciles de utilizar: BorderLayout, FlowLayout y GridLayout. Estos tres despliegues pueden combinarse para obtener una gran variedad de interfaces, como puede verse en los ejemplos al final de esta sección.

Estos despliegues tienen dos virtudes importantes: la sencillez y la automatización. Los tres están diseñados para realizar cierta presentación automáticamente y sin necesidad de colocar cada componente exactamente en una posición numérica o manualmente, como suele hacerse en otros lenguajes o en entornos de programación visual.

Nota: Cabe mencionar que la colocación numérica de los componentes también se puede hacer en Java si se aplica el Layout null (setLayout(null)) y la posición y dimensiones de cada componente se determinan con el método

setBounds(int left,int top,int width,int height)

de la clase Component. Este sistema tiene el inconveniente de que la presentación no se ajusta automáticamante cuando se cambian las dimensiones de la ventana, pero en muchas ocasiones es útil y además cuando el programador quiere controlarlo todo no hay mejor opción.

El más sencillo de los despiegues (aparte de null) es GridLayout. Tiene dos constructores. El más simple es:

GridLayout(int filas,int columnas)

Cuando a un Panel (o cualquier otro contenedor) se le aplica este despliegue mediante

setLayout(new GridLayout(filas,columnas)

habrá que agregarle filas*columnas componentes y éstos se van acomodando de izquierda a derecha y de arriba a abajo (ver preImposible.java al final de la sección). El resultado son filas*columnas componentes del mismo tamaño que se ajusta a que quepan exactamente en el lugar que se les ha asignado. Esto se logra sin que el programador tenga que hacer cálculos o acomodar manualmente cada componente. En muchas aplicaciones se utiliza GridLayout con una sola fila o una sola columna (ver preDibuja.java al final de la sección).

GridLayout tiene otro constructor que permite definir la separación (en pixels) ente los componentes, misma que es cero con el primer constructor. Así, por ejemplo

crea un desplieque de 3 filas y 4 columnas donde los componentes quedan a dos pixels de separación, como muestra este ejemplo:

    setLayout(new GridLayout(3,4,2,2);
    for (int i=0;i<3*4;i++) {

      add(new Button(Integer.toString(i+1)));

    }

BorderLayout crea cinco espacios donde acomodar componentes o paneles. La localización de estos espacios queda descrita por cadenas con los nombres de "Center" y los cuatro puntos cardinales: "North", "South", "East" y "West". Por ejemplo la construcción de la izquierda crea el despliegue de la derecha:

setLayout(new BorderLayout());
add("North",new TextField("Norte"));
add("South",new TextField("Sur"));
add("East",new Button("Este"));
add("West",new Button("Oeste"));
Label lbl=new Label("Centro");
lbl.setAlignment(Label.CENTER);
add("Center",lbl);
,

BorderLayout tiene otro constructor BorderLayout(int seph,int sepv) con el que se pueden definir las separaciones vertical y horizontal entre los componentes que aparecerán en las cinco zonas.

Estos dos despliegues controlan el tamaño de los componentes adecuándolo al espacio que se les haya asignado. En cambio FlowLayout "respeta" el tamaño de los componentes y trata de acomodarlos uno tras otro dejando un espacio entre uno y el siguiente. Por supuesto en este caso a veces los componentes no caben en el espacio que se les ha asignado y puede ocurrir que algunos no se deplieguen.

El ejemplo siguiente acomoda varios componentes en un applet con un despliegue de tipo FlowLayout.

setLayout(new FlowLayout());
add(new TextField("texto"));
add(new TextField("...",8));
add(new Button("botón"));
add(new Label("etiqueta"));
add(new Checkbox("interruptor"));
Choice ch=new Choice();
ch.add("uno"); ch.add("dos"); ch.add("tres");
add(ch);
add(new TextArea(5,10));
CheckboxGroup g=new CheckboxGroup();
add(new Checkbox("si",g,true));
add(new Checkbox("no",g,false));
add(new Checkbox("tal vez",g,false));
List l=new List(4,true);
l.add("one"); l.add("two"); l.add("three");
l.add("four"); l.add("five"); l.add("six");
add(l);
,

FlowLayout es el despliegue que todo panel tiene por defecto. Hay otros dos constructores aparte del que se utiliza en el ejemplo.

FlowLayout(int align)

que permite elegir si los componentes se acomodan a la izquierda, centrados o a la derecha, según se pase como parámetro una de las constantes: FlowLayout.LEFT, FlowLayout.CENTER o FlowLayout.RIGHT respectivamente.

FlowLayout(int align,int seph,int sepv)

permite además elegir la separación entre los componentes. El valor por defecto de seph y sepv es de 5 pixels.

El tamaño de cada componente dentro de un despliegue de tipo FlowLayout depende del tipo de letra que se le haya asignado o tenga por defecto. Los tamaños se ajustan para que las cadenas que en ellos aparecen queden bien presentadas. Los campos y cuadros de texto tienen constructores con los que se puede definir su ancho (en el caso de los campos de texto) y su alto y ancho (en el caso de los cuadros o áreas de texto). Las unidades para medir esto son "filas" para el alto y "columnas" para el ancho. En la mayoría de los intérpretes y navegadores el número de columnas se calcula utilizando la letra más ancha de la fuente asignada al componente, pero en otros se usa un promedio, por lo cual el ancho de un campo de texto suele cambiar de un navegador a otro.

Advertencia: Para agregar una pizarra (Canvas) a un contenedor con despliegue de tipo FlowLayout es necesario llamar al método Canvas.setSize(int ancho,int alto) para determinar el tamaño de la pizarra, de otra manera no aparece porque su tamaño por defecto es 0x0. No conviene agregar barras de desplazamiento a un contenedor con despliegue FlowLayout porque no se puede controlar su aspecto. Se recomienda que para agregar barras de desplazamiento, se utilice BorderLayout agregando las barras horizontales al norte o al sur y las barras verticales al este o al oeste.

Existe otro tipo de despliegue llamado GridBagLayout. Es algo más complicado de utilizar pero ofrece mayor flexibilidad que los otros. Funciona de manera parecida a las tablas en HTML. GridBagLayout permite acomodar componentes en filas y columnas, pero cada fila y cada columna pueden tener un tamaño diferente y además un componente puede ocupar más de una casilla. Para lograrlo es necesario especificar algunos parámetros para cada componente que se agrega. Esto se hace utilizando objetos de la clase GridBagConstraints a través del método

setConstraints(Component comp, GridBagConstraints cons)

del despliegue. Éstas son la variables de GridBagConstraints y sus significados:

int anchor punto fijo ante cambios de tamaño
int fill cómo debe crecer
int gridheight número de filas que abarca
int gridwidth número de columnas que abarca
int gridx número de columna donde empieza
int gridy número de fila donde empieza
int weightx peso en la distribución del espacio horizontal sobrante
int weighty peso en la distribución del espacio vertical sobrante
int ipadx espacio adicional horizontal dentro de la celda
int ipady espacio adicional vertical dentro de la celda
Insets insets objeto que especifica los márgenes

Para especificar int anchor se utilizan las siguientes constantes de GridBagConstraints: CENTER, EAST, NORTH, NORTHEAST, NORTHWEST, SOUTH, SOUTHEAST, SOUTHWEST y WEST. Para especificar int fill se utilizan las siguientes constantes de GridBagConstraints: HORIZONTAL, VERTICAL, BOTH y NONE. Finalmente, hay dos constantes útiles para las variables de posición y tamaño: RELATIVE y REMAINDER. La primera sirve para especificar que el componente es el penúltimo en su fila o columna y REMAINDER indica que es el último.

En los ejemplos siguientes se utilizan despliegues de tipo GridBagLayout. El alumno debe estudiar cuidadosamente cada ejemplo y hacerle modificaciones para comprender el significado preciso de cada variable de GridBagConstraints.

El primer ejemplo muestra cómo se pueden acomodar componentes ocupando más de una casilla usando gridx, gridy, gridwidth y gridheight:

El segundo ejemplo ilustra el uso de las variables anchor, fill e ipadx:

El uso de las variables weightx y weighty se ilustra en el tercer ejemplo:

El alumno deberá crear varios ejemplos usando los diferentes despliegues para adquirir soltura en su aplicación. Los ejercicios de este capítulo lo guiarán en esta tarea.

Los generadores visuales de interfaces de usuario, como los que ofrecen Visual J++ o JBuilder, permiten acomodar manualmente cada componente exactamente donde uno lo desea. Esto puede ser muy útil cuando lo que se diseña es una interfaz para una aplicación que aparecerá en pantalla con un tamaño fijo. Sin embargo, si se quiere que la apariencia de la intefaz se ajuste a diferentes tamaño del contenedor, es más conveniente utilizar los despliegues de Java.

En los ejemplos que se presentan a continuación se utilizan repetidamente paneles, despliegues y componentes para lograr el aspecto que presenta cada uno. Son ejemplos preparativos para la lección 5 (de ahí el prefijo "pre" en los nombres). En esta lección sólo se presenta la parte visual de las interfaces de usuario mientras que en la lección 5 se convertirán en auténticas interfaces interactivas que responderán a los eventos generados por el usuario. Pero cada cosa a su tiempo. Aquí sólo se muestra cómo se crean y despliegan los componentes que vamos a necesitar en los programas de la lección 5.

En la tabla aparecen los despliegues a la izquierda y a la derecha el código que los ha generado. El alumno debe estudiar cuidadosamente cada ejemplo para desarrollar una intuición de lo que se puede lograr combinando despliegues y paneles auxiliares.


Índice

Ejercicios de la Lección 07.


José Luis Abreu y Marta Oliveró