770 likes | 1.02k Views
Curso Programación en Java. Tema 10 Interfaz gráfico de usuario (GUI) Swing -Eventos. SWING. Swing es el conjunto de clases, interfaces, recursos, etc, para la construcción de IGU (Interfaz Gráfico de Usuario). Forma parte de Java Foundation Classes (JFC).
E N D
CursoProgramación en Java Tema 10 Interfaz gráfico de usuario (GUI) Swing -Eventos
SWING • Swing es el conjunto de clases, interfaces, recursos, etc, para la construcción de IGU (Interfaz Gráfico de Usuario). Forma parte de Java Foundation Classes (JFC). • Las JFC contiene los componenetes Swing, un API para 2D, un API para arrastrar y soltar y un API para facilitar el acceso. • Swing está construido sobre la arquitectura AWT (Abstract Window Toolkit). AWT es la biblioteca de clases, incorporada en Java 1.0, para realizar programación IGU. • AWT depende de la plataforma. Swing aparece en Java 2, es independiente de la plataforma. • Con Swing el aspecto de los elementos del interfaz gráfico es el mismo en todas las plataformas. • En la actualidad, toda, o casi toda, la progrmación gráfica se hace en Swing. • Las clases de Swing se encuentran en el paquete javax.swing. Entonces, un programa que utilice componentes gráficos y procese eventos, tendrá las sentencias import: import java.awt.*; // no siempre será necesario import java.awt.event.*; import.javax.swing.*;
JERARQUÍA DE CLASES GUI Component Container JComponet Panel Window Applet JTextComponent JLabel JPanel Frame Dialog JApplet JFrame JDialog • Las clases que empiezan por J son de swing.
ELEMENTOS DE UN GUI • Un programa que implementa una interfaz gráfico va a tener, normalmente, cuatro tipos de elementos: • Un contenedor de nivel superior: un marco (JFrame), un applet (JApplet), o bien objetos JDialog. Estos contenedores no están dentro de otra ventana, son las ventanas principales. • Componentes de la interfaz gráfica, como botones, campos de texto, ..., que se ubican en la ventana principal o en contenedores. • Contenedores. Diseñados para contener a otros elementos de la interfaz. JPanel, JScrollPane son dos contenedores. Estos contenedores a su vez son componenetes. • Elementos de para la gestión de eventos. • Los componentes siempre se añaden a una lámina o panel. Puede ser a la lámina del marco, o bien a un panel JPanel. • En general, siempre se crean clases derivadas de las clases "contenedores de nivel superior". Todo marco sera una subclase de JFrame, al igual que un applet es una subclase de JApplet.
MARCOS(I) • Una aplicación GUI se crea con una ventana principal en la que se ubican componentes. • La ventana principal es un objeto marco, que deriva de la clase JFrame. • Alguno de los métodos propios de JFrame: • JFrame() constructor • JFrame(String titulo) constructor, pone el título • void setTitle(String titulo) • void setIconImage(Image m) imagen como icono del marco • void setDefaultCloseOperation(int op) operación al cerrar el marco, constantes de JFrame: EXIT_ON_CLOSE, DO_NOTHING_ON_CLOSE, DISPOSE_ON_CLOSE, HIDE_ON_CLOSE • Container getContentPane() proporciona lámina de contenidos • void setUndecorated(boolean b) si b=true quita adornos: bordes... • public void setResizable(boolean r) si r=true se puede cambiar tamaño • void add(Component c) añade el componente a la lámina(java 1.5) • void remove(Component comp) • void setLayout(LayoutManager manager)
MARCOS(II) • Métodos de JFrame heredados de Container: • Component add(Component comp) • Component add(Component comp, int p) añade componente en la posición p. • Si se añade un componente a un contenedor ya visible, es necesario hacer una llamada a validate() • void validate() • void remove(int p) elimina componente de posición p • void remove(Component comp) • Métodos de JFrame heredados de Component: • void setVisible(boolean b) muestra componente. • void setBounds(int x, int y, sitúa el componente y cambia su tamaño • int ancho, int alto) • void setLocation(int x, int y) • void setLocation(Point p) • void setSize(int ancho, int alto) dimensiona componente. • void setSize(Dimension d) dimensiona componente.
PROPIEDADES DEL SISTEMA DE VENTANAS • La clase Toolkit (java.awt) está diseñada para establecer un comunicación con el sistema nativo de ventanas. Es una clase abstracta, entoces para obtener características del sistema de ventanas lo primero que se hace es llamar al método: • static Toolkit getDefaultToolkit() • que devuelve un objeto detivado de Toolkit con las propiedades de la ventana. • Métodos de interes de Toolkit: Image getImage(String nom);devuelve imagen (GIF, JPEG,PNG) del archivo Image getImage(URL u); • Dimension getScreenSize()devuelve la dimensión de la ventana • Dimension (java.awt) tiene los atributos public: int height, int width. Y los métodos: double getHeight(), double getWith().
Ejemplo. Marco centrado que ocupa la mitad de la pantalla. • Para centrar el marco en la pantalla se utiliza la clase Toolkit. Primero se crea el objeto derivado de Toolkit (static Toolkit getDefaultToolkit()) y después se obtiene su dimensión (Dimension getScreenSize()). El tamaño y posición del marco (coordenadas de esquina superior izquierda) se realiza llamando a setSize() y setLocation(). Como ejemplo, se pone una etiqueta y un botón en el panel de contenidos del marco. Hay que tener en cuenta que los elementos de un marco no se ponen en posiciones absolutas; se distribuyen según el "manejador" que tengan establecido. En un marco, el layout por defecto es BorderLayout. Este layout considera cinco zonas, según las coordenadas y el centro.
MarcoCentrado.java (I) import javax.swing.*; import java.awt.*; public class MarcoCentrado extends JFrame { public MarcoCentrado() { setTitle("Marco Centrado"); Toolkit k = Toolkit.getDefaultToolkit(); Dimension d = k.getScreenSize(); int alto = d.height; int ancho = d.width; setSize(ancho/2, alto/2); setLocation(ancho/4, alto/4); add(new JButton("Boton")); add(new JLabel("HOLA",SwingConstants.CENTER),BorderLayout.SOUTH); setResizable(false); }
MarcoCentrado.java (II) public static void main(String args[]) { MarcoCentrado miMarco = new MarcoCentrado(); miMarco.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); miMarco.setVisible(true); } } Nota:añadir otros tres componentes mas al marco, en el NORTH, EAST y WEST. Probar los efectos del método setUndecorated(boolean b) en la imagen del marco. Compilar y ejecutar.
LÁMINA DE CONTENIDOS. PANEL • Un marco consta de una serie de láminas. La lámina de contenidos es en la que se añaden componenrtes. El método Container getContentPane() devuelve dicha lámina. • Actualmente, en Java 5, el método add(Component) de JFrame añade un componente a la lámina de contenidos; versiones anteriores de Java exigían hacerlo directamente a dicha lámina, similar al siguiente código: marco.getContentPane().add(new Jlabel("Hola Amigos")); • Además de la lámina de contenidos, la clase JPanel define una lámina en la que se puede dibujar y poner componentes (campos de testo, botones, ....). Constructores de JPanel: JPanel() y JPanel(LayoutManager l); Por herencia, los métodos: add(Component c ) y add(Component c, int p); • La ubicación, por defecto, de componenetes en JPanel es del tipo FlowLayout. Esto significa que se disponen de izquierda a derecha y de arriba a abajo. • En el ejemplo que se pone a continuación, se crea un panel al que se añaden 5 componentes. El panel reemplaza al panel a la lámina de contenidos del marco.
MarcoPanel.java (I) import javax.swing.*; import java.awt.*; public class MarcoPanel extends JFrame { public MarcoPanel() { JPanel pa = new JPanel(); // por default FlowLayout() pa.add(new JTextField("Razones debiles", 10)); pa.add(new JButton("Boton")); pa.add(new JCheckBox("Box ",false)); pa.add(new JLabel ("Calendario", JLabel.CENTER)); pa.add(new JRadioButton("Bot Radio", true)); setContentPane(pa); setSize(300,200); }
MarcoPanel.java (II) public static void main(String[] args) { MarcoPanel m; m = new MarcoPanel(); m.setVisible(true); m.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); } } Ejecución: Nota: Pinchar con el ratón y ampliar el marco; ¿cómo se distribuyen los elementos?
VISUALIZACÍON DE COMPONENTES • Para dibujar en un panel (lámina) se utiliza el método paintComponent(Graphics g). Este método, definido en JComponent (con visibilidad protected), es necesario redefinirlo para que realiza las acciones deseadas. • paintComponent(Graphics g) tiene la particularidad de que recibe el argumento Graphics , para dibujar imágenes, texto, poner colores, establecer el tipo de letra. • Se puede afirmar que el argumento Graphics es el contexto gráfico. Graphics es una clase definida en el paquete java.awt coon métodos para dibujar texto e imagenes. • Cada vez que una ventana vaya a ser dibujada, el manejador del evento se lo hace saber a cada componente. Esto hace que se llame automáticamente a paintComponent(). • No se llama directamente al método paintComponent(). Se llama automáticamente cuando por algún cambio es necesario redibujarse. • Por ejemplo, si el usuaio aumenta, o disminuye, el tamaño de la ventana. Si se ha "tapado" la ventana por otra ventana. • Para forzar la llamada a paintComponent(Graphics g), se hace una llamada al método repaint(), el cual da lugar a una llamada paintComponent() con el objeto Graphics . • A tener en cuenta: las medidas se hacen en pixeles, y (0,0) es la esquina superior izquierda.
Ejemplo. Panel en el que se escribe una cadena y un rectángulo • Se declara una clase derivada de JPanel en la cual se redefine el método paintComponent(). Como se puede observar en la redefinición, la primera sentencia es una llamada a paintComponent() de la clase base (simplemente para pintar el color del fondo, en realidad se puede omitir). A continuación, se escribe una cadena junto a su posición de inicio: g.drawString("Cadena en Panel (" + x + "," + y + ")", x, y); También, se dibuja un rectángulo: g.drawRect(x-1, y-12, 135, 12); Al ejecutar, se recomienda cambiar el tamaño, ampliar, minimizar y sacar conclusiones. Nota: Una probado, modificar el método con el fin de añadir otra figura, por ejemplo una elipse.
PanelDibujo.java (I) import javax.swing.*; import java.awt.*; public class PanelDibujo extends JPanel { private int x=0,y=10; public void paintComponent(Graphics g) { super.paintComponent(g); g.drawString("Cadena en Panel (" + x + "," + y + ")", x, y); x++; y += 2; g.drawRect(x-1, y-12, 135, 12); } }
PanelDibujo.java (II) import javax.swing.*; import java.awt.*; public class MarcoDibujo extends JFrame { private static final int ANCHO=300, ALTO=200; public MarcoDibujo() { setTitle("Marco con panel de dibujo"); setSize(ANCHO,ALTO); setLocation(ANCHO/2,ALTO/2); } public static void main(String args[]) { MarcoDibujo marco; marco = new MarcoDibujo(); PanelDibujo uno = new PanelDibujo(); marco.add(uno); marco.setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); //marco.pack(); marco.setVisible(true); } }
CLASE Graphics • La clase Graphics (java.awt) es una clase abstracta que proporciona el contexto gráfico. La clase dispone de métodos para dibujar todo tipo de elementos. • Graphics al ser clase abstracta no se puede instanciar. El contexto gráfico se obtiene a través de los métodos paint(Graphics g) y update(Graphics g) de la clase Component. • Métodos de dibujo de Graphics: void drawString(String cad, int x, int y); (x,y) coordenadas de origen void drawLine(int x1, int y1, int x2, int y2); dibuja una línea void drawRect(int x, int y, int ancho, int alto); dibuja rectángulo void fillRect(int x, int y, int ancho, int alto); llena rectángulo con colora actual void fillRoundRect(int x, int y, int ancho, int alto, int arcoAncho, int arcoAlto); llena rectángulo redondeado void drawOval(int x, int y, int ancho, int alto); dibuja elipse void drawArc(int x, int y, int ancho, int alto, int anguloInicio, int anguloArco); dibuja arco boolean drawImage(Image m, int x, int y, ImageObserver b); ... • Graphics2D es una subclase de Graphics que se utiliza para dibujar formas en java 2D.
CONTROL DE VISUALIZACÍON(I) • La clase Component (en la parte alta de la jerarquía AWT y también de swing) dispone de los métodos que controlan la visualización de cualquier componente, tanto en las aplicaciones GUI como en los applet,s. • El método de la clase Component, void paint(Graphics g) recibe el contexto gráfico g; con g se puede llamar a los métodos de la clase Graphics. • La definición original de paint(Graphics g) no hace nada. Puede ser redefinido para realizar operaciones gráficas. • La llamada a paint() se realiza de dos formas: • Directamente por la aplicación, cuando el componente se muestra por primera vez, o bien cuando deja de estar tapado por otro componente, o cambia de tamaño. • Al llamar a repaint(), éste, indirectamente a través de update(), llama a paint() • La clase JComponent define el método paint() de tal forma que llama a paintComponent(Graphics g). Por esa razón si se quiere realizar operaciones gráficas es necesario redefinir paintComponent()
CONTROL DE VISUALIZACÍON(II) • El método repaint(), de la clase Component, se llama siempre que se desee volver a dibujar un componenete. repaint() hace una llamada a update(), que en su implementación original, llama a paint(). • repaint() está sobrecargado: • void repaint() para todo el recinto • void repaint(int x, int y, int ancho, int alto)limitado al rectángulo • El método update(), de la clase Component, normalmente es llamado por el método repaint(). Su prototipo: void update(Graphics g). Si no se redefine, realiza dos acciones: • Redibujar el componente con el color de fondo actual. l • Llamar al método paint(),pasando el contexto gráfico.
COLOR • La clase Color (java.awt) está diseñada para definir colores. La clase dispone de constantes predefinidas para los colores estándar: BLACK, BLUE, CYAN, WHITE, GRAY, RED ... También, la clase SystemColor dispone de constantes que representan colores del sistema. • Otra forma de especificar un color es creando un objeto de Color mediante sus componentes rojo, verde y azul. El constructor es el siguiente: public Color (int rojo, int verde, int azul); La escala de cada parámetro es de 0 a 255. Por ejemplo, el color GRAY está definidö: Color gray = new Color(128, 128, 128); Aumentando, o disminuyendo, estos valores se consiguen distintas tonalidades. • Métodos de interes: para especificar el color de fondo se utiliza el método setBackgroud(Color c) de la clase Component, heredado por todos los componenetes. También, el método setForeground(Color c) de la clase Component , para el color del primer plano de un componente. La clase Graphics dispone del método setColor(Color c) para dar color a las siguientes operaciones gráficas.
FUENTES (tipo de letra) • Para especificar un tipo de letra se utiliza la clase Font. El constructor de Font crea un tipo de letra que se puede aplicar a texto. Constructor: Font(String nombre, int estilo, int tamaño); Por ejemplo: Font tipo = new Font("Serif",Font.PLAIN,14); • En la clase Font están definidas constantes que representan los estilos: PLAIN, BOLD(negrita) , ITALIC (cursiva). • El método String[] getAvailableFontFamilyNames() de la clase GraphicsEnvironment proporciona un array de cadenas con los nombres de los tipos de letras disponibles. Un objeto de la clase mencionada se obtiene: GraphicsEnvironment g = GraphicsEnvironment. getLocalGraphicsEnvironment() • La clase Component dispone del método setFont(Font tipo) para poner el tipo de letra al texto del componente. • La clase Graphics dispone del método setFont(Font tipo) para poner el tipo de letra del texto que se escriba.
CARGA DE IMAGENES • Las imagenes, normalmente, están almacenadas en archivos de nuestro computador, o en algún lugar (URL) de internet. Se pueden leer, o descargar, para después visualizarlas. • Una C una imagen es llamando al método ImageIO.read(archivo), que es un método static de la clase ImageIO (paquete javax.imageio). String nomArchivo =" "; Image imag = ImageIO.read(new File(nomArchivo)); Si la imagen se encuentra en una dirección de internet: Image imag = ImageIO.read(new URL(nomURL)); • El método read() lanza la excepción IOException si el objeto imagen no está disponible. • Para visualizar la imagen se llama al método drawImage() , de la clase Graphics, en la redefinición de paintComponent(). class miPanel extends JPanel {... public void paintComponent(Graphics g) { g.drawImage(imag, 0, 0, null); // (0,0) esquina superior izda.
EJEMPLO • A un marco se añade un panel en el que se ha dibujado una imgen que se encuentra en un archivo. El tamaño del marco se ajusta a la ventana (Toolkit.getDefaultToolkit()). La clase panel, derivada de JPanel, dispone de un constructor que lee la imagen (ImegeIO.read()). Si la imagen no se puede leer, el método read() lanza una excepción que será "atrapada" y relanzada. La clase que implenta el panel redefine el método paintContent() con la finalidad de dibujar la imagen (drawImage()). • LaminaImagen.java import javax.swing.*; import javax.imageio.ImageIO; import java.awt.*; import java.io.*; public class LaminaImagen extends JPanel { private Image ima = null;
LaminaImagen.java (II) /** Constructor, carga la imagen */ public LaminaImagen() throws IOException { try { ima = ImageIO.read(new File( "C:\\Documents and Settings \\All Users\\" + "Documentos\\Mis imágenes\\ Imágenes de muestra\\Invierno.GIF")); } catch(IOException e) { System.out.println( "No se puede cargar la imagen: " +e); throw e; } } public void paintComponent(Graphics g) { super.paintComponent(g); System.out.println("PaintComponen" + ima); if (ima == null) return; // no hay imagen // this es el "observador" int ancho = ima.getWidth(this); int alto = ima.getHeight(this); System.out.println("Ancho y alto de imagen:" + ancho+", "+alto); //(0,0) esquina superior izdq. g.drawImage(ima, 0, 0, this /* for (int i = 0; i* 20 <= getWidth(); i++) for (int j = 0; j* 20 <= getHeight(); j++) if (i + j > 0) g.copyArea(0, 0, 20, 20, i*20 , j*20); */ } }
Nota: El método copyaArea() de la clase Graphics permite copiar un área de dibujo en otra posición del panel. Prototipo: void copyArea(int x, int y, int ancho, int alto, int despl_X, int despl_Y); x,y: coordenadas de la parte superior izqda de la imagen origen ancho, alto: rectangulo de la imagen origen que se va a copiar despl_X: desplazamiento horizontal desde imagen origen al destino despl_Y: desplazamiento vertical desde imagen origen al destino Por ejemplo: Se recubre la ventana con un rectángulo de 20*20 pixeles de la imagen original. for (int i = 0; i* 20 <= getWidth(); i++) for (int j = 0; j* 20 <= getHeight(); j++) if (i + j > 0) g.copyArea(0, 0, 20, 20, i*20 , j*20);
MarcoImagCentr.java(I) import javax.swing.*; import java.awt.*; public class MarcoImagCentr extends JFrame { /** Constructor */ public MarcoImagCentr() { // Dimensiones de la pantalla setTitle("Marco Con Imagen"); Toolkit k = Toolkit.getDefaultToolkit(); /* método factoría. Ventana actual */ Dimension d = k.getScreenSize(); int alto = d.height; int ancho = d.width; setSize(ancho/2, alto/2); setLocation(ancho/4, alto/4); /* setSize(ancho,alto); setLocation(0,0); */ }
MarcoImagCentr.java(II) public static void main(String args[]) { MarcoImagCentr miMarco = new MarcoImagCentr(); LaminaImagen pan; //miMarco.setUndecorated(true); miMarco.setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); try { pan = new LaminaImagen(); miMarco.add(pan); } catch (Exception e) { System.out.println("No se ha podido realizar el dibujo de la imagen"); System.exit(1); } } }
GESTORES DE POSICIONAMIENTO • La disposición de componentes no se suele determinar de modo absoluto. • De esta forma se evita depender del dispositivo. • La distribución de componentes se hace con los gestores de posicionamiento. • Objetos que implementan la interfaz LayoutManager. • Cada contenedor tiene su propio gestor de posicionamiento por omisión: • Window, JFrame y JDialog: BorderLayout. • JPanel, JApplet : FlowLayout. • Para cambiarlo, la clase Container tiene el método setLayout(LayoutManager mng). • Hay definidos hasta 7 tipos de layouts; son los siguientes: FlowLayout, BorderLayout, GridLayout, BoxLayout, GridBagLayout, CardLayout y SpringLayout.
BorderLayout • Divide al contenedor en cinco zonas. Los componentes se disponen en las posiciones superior (“North”), inferior (“South”), derecha (“West”), izquierda (“East”) y centro (“Center”). • Las posiciones están representadas por las constantes: BorderLayout.CENTER, BorderLayout.NORTH, ... • El método add(), (add (Component c, int zona)) por default, dispone el componente en el centro. • Los componentes del marco se pueden separar con el constructor: BorderLayout(int separaHorizontal, int separaVertical); Para indicar la separación en pixeles. • Con este layout, primero se sitúan los componentes de los bordes y después el componente del centro, que ocupará el espacio restante. • Cuando se modifican las dimensiones del contenedor, las dimensiones de los componenetes de los bordes no cambian, cambia el tamaño del componente central.
EJEMPLO BorderLayout • E constructor del objeto Marco (class Marco extends JFrame) crea 5 etiquetas en las posiciones indicadas. • Ejercicio: Cambiar la etiquetas por botones (JButton) y separar los componentes en 5 * 5 pixeles
FlowLayout • Los componentes se disponen en fila de izquierda a derecha. Una vez completada una línea comienza otra línea • Constructor: • setLayout(new FlowLayout(int alineación)). • La alineación puede tomar los valores: FlowLayout.RIGHT, FlowLayout.CENTER y FlowLayout.LEFT. • setLayout(new FlowLayout(int alin, int sepHztal, int sepVert)).
GridLayout • Los componentes se distribuyen en una rejilla de celdas iguales (en forma de cuadrícula). Los elementos se ubican de arriaba hacia abajo y de izquierda a derecha. • Constructores: GridLayout()coloca los componentes en una única fila y única columna. GridLayout(int f,int c)coloca los componentes en cuadrículas de f filas y c columnas. GridLayout(int f, int c, int sepHztal, int sepVert)
BoxLayout • Permite mostrar una única fila o una única columna con los componentes utilizados. El constructor necesita un argumento con el contenedor que va a utilizar y la orientación. La orientación puede ser: BoxLayout.X_AXIS o BoxLayout.Y_AXIS • Constructor: BoxLayout(Container destino, int orientacion) • Ejemplo: Marco(){ super("Marco BoxLayout"); JPanel pan = new JPanel() ; pan.setLayout(new BoxLayout(pan, BoxLayout.Y_AXIS)); pan.add(new JButton("Primera")); pan.add(new JButton("Segunda")); pan.add(new JButton("Tercera")); pan.add(new JButton("Cuarta")); pan.add(new JButton("Quinta")); pan.add(new JButton("Sexta")); add(pan); // o bien, setContentPane(pan) setSize(ancho,alto); setVisible(true); }
BoxLayout-Box • Hay un contenedor que tiene como gestor predeterminado un BoxLayout: contenedor Box. • Un objeto Box se crea con los métodos factoría de la clase Box: Box.createHorizontalBox() Box.createVerticalBox() • Estos son métodos static que crean un objeto Box con la orientación del nombre: Box cajaHoriz = Box.createHorizontalBox() • Se añaden los elementos al contenedor: cajaHoriz.add(elemento). Y después el contenedor al marco. • Ejemplo: public MarcoBotEve() { pc = getContentPane(); setTitle("Ejemplo de eventos botones"); azul = new JButton("Azul"); amar = new JButton("Amarillo"); rojo = new JButton("Rojo");
Ejemplo (continuación) cajaH = Box.createHorizontalBox(); // método factoria cajaH.add(azul); cajaH.add(Box.createHorizontalStrut(25)); // separación horizontal 25 pixeles cajaH.add(amar); cajaH.add(Box.createRigidArea(new Dimension(50,80))); // zona rígida, separación // horizontal y vertical que afecta a todos los componentes cajaH.add(rojo); /* azul.addActionListener(new OyenteBoton()); amar.addActionListener(new OyenteBoton()); rojo.addActionListener(new OyenteBoton()); */ setContentPane(cajaH); } // clase con método main public static void main(String[] args) { MarcoBotEve m ; m = new MarcoBotEve(); //m.pack(); m.setVisible(true); m.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); }
COMBINAR GESTORES DE POSICIONAMIENTO • Cada contenedor (JFrame, JPanel, JDialog,...) sólo puede tener un gestor de posicionamiento. Sin embargo un contenedor de primer nivel (un JFrame, ...) puede tener otros contenedores anidados, cada uno con su propio gestor de posicionamiento. En definitiva, se combinan o andan diversos gestores de posicionamiento. • Ejemplo: se definen tres paneles, cada uno con su propio layout. A cada panel se añaden elementos como botones, etiquetas, campos de texto y una lista. Una vez creados los tres paneles, se estable el layout del contenedor de primer nivel (marco) y se añaden. • MarcoGestores.java (I) import java.io.*; import javax.swing.*; import java.awt.*; public class MarcoGestores extends JFrame { //Constructor en el que se crean los paneles
MarcoGestores.java (II) public MarcoGestores() { JPanel pa1 = new JPanel(new FlowLayout()); // por default FlowLayout() JPanel pa2 = new JPanel(new BorderLayout()); JPanel pa3 = new JPanel(); pa3.setLayout ( new BoxLayout(pa3, BoxLayout.Y_AXIS)); String [] opc = {"Marea alta", "Bajamar", " Montaña"}; pa1.add(new JLabel (" Elegir", JLabel.CENTER)); pa1.add(new JList(opc)); pa1.add(new JButton("Pulsar")); JTextField j = new JTextField("Razones "); j.setEditable(false); pa2.add(j,BorderLayout.WEST); pa2.add(new JButton("Boton"),BorderLayout.EAST); pa3.add(new JCheckBox("Box ",false)); pa3.add(new JLabel ("Calendario", JLabel.CENTER)); pa3.add(new JRadioButton("Boton Radio", true));
MarcoGestores.java (III) /* Container ppal = getContentPane(); ppal.setLayout ( new BorderLayout()); ppal.add(pa1,BorderLayout.NORTH); ppal.add(pa2,BorderLayout.CENTER); ppal.add(pa3,BorderLayout.SOUTH); */ setLayout( new BorderLayout(10, 15)); add(pa1,BorderLayout.NORTH); add(pa2,BorderLayout.CENTER); add(pa3,BorderLayout.SOUTH); } public static void main(String[] args) { MarcoGestores m; m = new MarcoGestores(); m.setSize(200, 300); m.setLocation(20, 200); m.setResizable(false); m.setVisible(true); m.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); } }
DESACTIVAR EL GESTOR DE POSICIONAMIENTO • Mediante el mensaje setLayout(null) se desactiva el gestor de posicionamiento de un contendor. • Una vez desactivado el gestor de posicionamiento, el usuario deberá distribuir cada componente en la lámina o panel contenedor. Las coordenadas absolutas que se utilizan son en pixeles. • Métodos más utilizados (definidos en clase Component) : setSize(int ancho, int alto) setLocation(int x, int y) setBounds(int x, int y, int ancho, int alto);fija la posición y el tamaño del componente Ejemplo: JLabel etq = new JLabel("Ventana"); etq.setLocation(10,20); etq.setSize(50,60); // estas dos últimas llamadas son equivalentes a: etq.setBounds(10,20, 50,60);
COORDENAS y DISEÑO Coordenadas. • Se miden en pixeles. • El origen de coordenadas es (0,0), representa la esquina superior izquierda. • El eje x representa el eje de abscisas (horizontal), es decir de izquierda a derecha. • El eje y representa el eje de ordenadas (vertical), es decir de arriba a abajo. • Cada componente se ubica en el sistema de coordenasas padre. ¿Cuando tiene lugar el diseño? • Cuando se hace visible por primera vez; o bien, cuando se borra o añade un componente. • Cuando cambia el tamaño de un componente. • Una vez hecho visible un marco, si se cambia el tamaño de un componente, no se activará el nuevo diseño hasta llamar al método revalidate() del componente.
COMPONENTES swing • Todos los componentes que se agregan a un contenedor descienden de la clase JComponent. • Un componente representa cualquier cosa que tenga una posición, un tamaño, que pueda pintarse y que pueda recibir eventos. • Añadir componentes a un contenedor. • Método add() de la superclase Container. • public Container Add(Component comp). • Añade un componente después del anterior en el gestor de posicionamiento. • public Container Add(Component comp, int indice). • Añade un componente en la posición indice.
ETIQUETAS (JLabel) • Representan componentes con texto fijo. • No reciben eventos. • Constructores. • JLabel(). • JLabel(String mensaje). • JLabel(String mensaje, Icon icono); • JLabel(String mensaje, int alineación). • Para la alineación se pueden utilizar las constantes estáticas CENTER, LEFT y RIGHT del interface SwingConstants. • Algunos métodos. • public String getText(). • public void setText(String mensaje).
AbstractButton JButton JToogleButton JRadioButton JCheckBox BOTONES • La clase base de los botones es AbstractButton. • AbstractButton es una clase abstracta que encapsula propiedades y métodos comunes a los diversos tipos de botones:
BOTÓN- JButton • Representa el botón común. Se crea especificando una cadena, un icono, ambos, o bien sin especificar elemento. • Recibe eventos; es el click del botón. El listener asociado implementa ActionListener. • Constructores. • JButton(). • JButton(String mensaje). • JButton(String mensaje, Icon icono); • Algunos métodos (heredados de AbstractButton): • public String getText(); • public void setText(String m). • public void setIcon(Icon icono). • public void setMnemonic(char nemotécnico). • public void addActionListener(ActionListener oyente). • public boolean isSelected(). • public void setSelected(boolean flag).
BOTÓN CON DOS ESTADOS • JToogleButton es la clase base de los botones con dos estados. • JRadioButton (subclase de JToogleButton ) se utiliza para definir un grupo de botones de opción única. • Para agrupar botones de opción única, es necesario la clase ButtonGroup para agruparlos. Primero se crea un objeto ButtonGroup (constructor sin argumentos). A continuación, se añaden JRadioButton con el método de ButtonGroup, add(AbstractButton b). • Constructores de JRadioButton. • JRadioButton(). • JRadioButton(String mensaje). • JRadioButton(String mensaje, boolean selecion); • Algunos métodos: • public boolean isSelected(). • public void setSelected(boolean flag).
Casillas de verificación • JCheckBox (subclase de JToogleButton ) se utiliza para definir un casillas de verificación . • Constructores de JCheckBox. • JCheckBox(). • JCheckBox(String mensaje). crea casilla de verificación con texto inicial. • JCheckBox(String mensaje, boolean selecion); • Algunos métodos: • public boolean isSelected(). • public void setSelected(boolean flag). Listas desplegables, JComboBox • JComboBox se utiliza para crear una lista desplegable, a la que se pueden agregar opciones, editarlas, seleccionar una opción. • Constructores de JComboBox. • JComboBox(); • JComboBox(Object lista[])
JComboBox • Algunos métodos: • public void addItem(Object q). • public insertItemAt(Object q, int indice). • public void setEditable(boolean flag). Permite teclear opción • public void setMaximumRowCount(int n). Pone el máximo de opciones. • public void actionPerformed(ActionEvent ev). • public void addActionListener(ActionListener ae). • public void addItemListener(ItemListener it). • public void addStateChanged(ItemEvent ev). • public Object getSelectedItem(). Devuelve el elemento seleccionado.
EJEMPLO CON BOTONES • Una aplicación ofrece al usuario la posibilidad de elegir tipos de transporte. La elección de "avión" despliega un combobox. El código que se pone a continuación no está completo; se pueden añadir eventos para realizar más selecciones. MarcoJradio.java(I) (agrupa botones de radio en un panel) import javax.swing.*; import java.awt.*; import java.awt.event.*; class MarcoJRadio extends JPanel { ButtonGroup grb; JRadioButton jr1, jr2, jr3; /** constructor MarcoPrueba */
MarcoJradio.java(II) (agrupa botones de radio en un panel) public MarcoJRadio() { grb = new ButtonGroup(); setLayout(new GridLayout(4,1)); add (new JLabel(" Selección excluyente")); // se crea botón de radio,y seañade al panel y a la agrupación jr1 = new JRadioButton("Avion", false); add(jr1); grb.add(jr1); // se crea botón de radio,y seañade al panel y a la agrupación jr2 = new JRadioButton("Tren", false); add(jr2); grb.add(jr2); // se crea botón de radio,y seañade al panel y a la agrupación jr3 = new JRadioButton("Coche", false); add(jr3); grb.add(jr3);