Archive for the ‘Uncategorized’ Category

Instalación del Java Comm API en Windows

Sunday, March 22nd, 2009

La versión del Comm API (Java(tm) Communications API) para Windows está formada por tres archivos:

  • win32com.dll
  • comm.jar
  • javax.comm.properties

 
Si queremos ejecutar alguna aplicación que haga uso del puerto serie o el paralelo debemos realizar la instalación en el JRE (cuyo path es parecido a “C:\Archivos de programa\Java\jre6\” o “C:\Archivos de programa\Java\jre1.6.0_03″), para ello tenemos que colocar los archivos en:

  • win32com.dll
    • PATH_JRE\bin\
  • comm.jar
    • PATH_JRE\lib\ext\
  • javax.comm.properties
    • PATH_JRE\lib\

Si queremos desarrollar alguna aplicación que haga uso del puerto serie o el paralelo debemos realizar la instalación en el JDK (cuyo path parecido a “C:\Archivos de programa\Java\jdk1.6.0_12″), para ello tenemos que colocar los archivos en:

Rotando una imagen a través de java.awt.geom.AffineTransform

Sunday, March 22nd, 2009

Mediante AffineTransform se puede rotar una imagen dibujada sobre un Graphics.
Esto se debe a que en realidad AffineTransform agrega una transformada al objeto Graphipcs.

Para rotar se pasa a una instancia de AffineTransform a través de rotate(), pasándole el ángulo en radianes y el centro de rotación. Luego esta instancia se asigna al objeto Graphics (debemos asignársela a Graphics2D en realidad)

  1. AffineTransform at = new AffineTransform();  
  2. at.rotate(r, 100100); //se asigna el angulo y centro de rotacion  
  3. ((Graphics2D) g).setTransform(at);  

Ejemplo

Por ejemplo creamos un panel que muestra un cuadrado girado una determinada cantidad de grados llamada JPanelImagenGiratoria.java:

  1. import java.awt.Color;  
  2. import java.awt.Graphics;  
  3. import java.awt.Graphics2D;  
  4. import java.awt.geom.AffineTransform;  
  5.   
  6. public class JPanelImagenGiratoria extends javax.swing.JPanel {  
  7.   
  8.     private int grados = 0;  
  9.   
  10.     public int getGrados() {  
  11.         return grados;  
  12.     }  
  13.   
  14.     public void setGrados(int grados) {  
  15.         this.grados = grados;  
  16.         repaint();  
  17.     }  
  18.   
  19.     @Override  
  20.     public void paint(Graphics g) {  
  21.         super.paint(g); //se borra el contenido anterior  
  22.   
  23.         double r = Math.toRadians(grados); //se convierte a radianes lo grados  
  24.   
  25.         AffineTransform at = new AffineTransform();  
  26.         at.rotate(r, 100100); //se asigna el angulo y centro de rotacion  
  27.         ((Graphics2D) g).setTransform(at);  
  28.   
  29.         //se dibuja  
  30.         g.setColor(Color.BLUE);  
  31.         g.drawRect(5050100100);  
  32.   
  33.     }  
  34. }  

y un frame para realizar la prueba del panel llamada PruebaPanel.java. Prestar atención al observador de cambios del JSlider agregado mediante addChangeListener():

  1. import java.awt.BorderLayout;  
  2. import javax.swing.JFrame;  
  3. import javax.swing.JSlider;  
  4.   
  5. public class PruebaPanel{  
  6.   
  7.     public static void main(String[] args) {  
  8.         final JFrame jf = new JFrame(“Prueba Imagen Giratoria”);  
  9.         jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);  
  10.         jf.setSize(200250);  
  11.   
  12.         final JPanelImagenGiratoria ig = new JPanelImagenGiratoria();  
  13.   
  14.         final JSlider js = new JSlider(0360);  
  15.         js.addChangeListener(new javax.swing.event.ChangeListener() {  
  16.   
  17.             public void stateChanged(javax.swing.event.ChangeEvent evt) {  
  18.                 ig.setGrados(js.getValue());  
  19.             }  
  20.         });  
  21.         js.setValue(0);  
  22.   
  23.         jf.setLayout(new BorderLayout());  
  24.         jf.add(ig, BorderLayout.CENTER);  
  25.         jf.add(js, BorderLayout.SOUTH);  
  26.   
  27.         jf.setLocationRelativeTo(null);  
  28.         jf.setVisible(true);  
  29.     }  
  30. }  

Imágenes:

                                                                                                                                                                                      

Fuente: http://lefunes.wordpress.com/2008/05/30/rotando-una-imagen-a-traves-de-javaawtgeomaffinetransform/

GUI con Java I (A.W.T)

Sunday, March 22nd, 2009

Java incorpora en el lenguaje dos bibliotecas gráficas: AWT y Swing. La primera es más básica y a veces compleja, pero su look es generalmente más liviano y rápido que Swing, aunque este último es mucho más agradable a la vista.

Para comenzar con los diseños de GUI, quiero comenzar con AWT y viendo algunas cosillas básicas para ir despertando el apetito de los lectores.

Primero, para ponernos de acuerdo, llamaremos widget a cualquier objeto gráfico. Esto incluye ventanas, botones, combobox y cualquier objeto que podamos poner en una GUI. Llamaremos contenedor (o container) a un widget que puede alojar dentro de si a otros widgets. Y, finalmente, llamaremos layout a la disposición de los objetos dentro de un contenedor.

Cuando se programan GUIs, el esquema de programación cambia: no importa si estás usando objetos, funciones o un conjunto de ifs y gotos: ahora tu preocupación es responder a las acciones que el usuario podría realizar en la GUI (como pinchar un botón, poner el mouse sobre un texto, etcétera). A estas acciones se les suele llamar eventos, los que deben ser manejados con una función/método.

La visión de Java en este sentido es que, al generarse un evento, se llama a los manejadores correspondientes, llamados listeners en Java. Esto significa que si quiero realizar una acción cuando se genere un evento en un widget, debo agregar el listener correspondiente al widget para que este realice una acción; para los más avanzados en Java -como ya imaginarán- los listeners son usualmente interfaces, y por razones obvias: de esa forma yo pongo cuerpo al método según lo que quiera realizar.

 

¿Aburrido de tanta lectura? Si… yo también estoy aburrido de escribir. Veamos un código pequeño, que al final todos aprendemos viendo código y haciendo desastres… xD

 

import java.awt.*;

public class Ventana {
   private Frame ventanaPrincipal;

   public Ventana() {
      ventanaPrincipal = new Frame("Ejemplo AWT"); //Si... el título de la ventana
      ventana.setSize(200, 130);                   //El tamaño... ancho y alto
      ventana.setVisible(true);                    //Hace visible la ventana
      //¿te imaginas como ocultar una ventana?
   }

   public static void main(String args[]) {
      Ventana v = new Ventana();
   }
}

 

Y con ese pequeño código conseguimos lo siguiente:

ventana1.jpg

Pero, si te fijas bien, al hacer click en la X de la barra de la ventana, esta no se cierra. Si ejecutaste el código desde una consola, tendrás que ‘matar’ el programa con Ctrl+C. ¿Qué pasó? Simple: hay que manejar el evento ‘cerrar ventana’. Para ello, tendremos que implementar la interfaz WindowListener del paquete java.awt.event. Código de ejemplo en este preciso instante:

 

import java.awt.*;
import java.awt.event.*;

public class Ventana2{
	private Frame principal;

	public Ventana2() {
		principal = new Frame("Ejemplo AWT");
		principal.setSize(235, 130);
		principal.addWindowListener(new EscuchaEventosVentana());
		principal.setVisible(true);
	}

	class EscuchaEventosVentana implements WindowListener {
		//Este evento es cuando se pulsa la X
		public void windowClosing(WindowEvent e) {
			System.out.println("Solicita cerrar la ventana");
			Frame ventana = (Frame)e.getWindow();
			ventana.setVisible(false);
			ventana.dispose();
		}
		//Ocurre cuando ya se cerró la ventana
		public void windowClosed(WindowEvent e) {
			System.out.println("Ventana cerrada; terminar");
			System.exit(0);
		}
		public void windowIconified(WindowEvent e) {
			System.out.println("Iconified");
		}
		public void windowActivated(WindowEvent e) {
			System.out.println("Activated");
		}
		public void windowDeactivated(WindowEvent e) {
			System.out.println("Deactivated");
		}
		public void windowDeiconified(WindowEvent e) {
			System.out.println("Deiconified");
		}
		public void windowOpened(WindowEvent e) {
			System.out.println("Opened");
		}
	}

	public static void main(String args[]) {
		Ventana2 v = new Ventana2();
	}
}

 

Si: WindowListener propone 7 métodos para implementar. Si sólo se interesa 1 de los 7, simplemente pon corchetes vacíos (cuerpo vacío) en el método que no te interesa implementar. En este caso, he implementado todos los métodos para que veas cuando se lanza cada evento.

 

Ok, no somos expertos en GUI, pero al menos podemos crear una ventana. ¿Te animas a probar ahora un botón?

Con el fin de ahorrar código, te explico de antemano: el listener asociado a un botón es el ActionListener. Así que ahora haremos cosas un poco más divertidas…

 

import java.awt.*;
import java.awt.event.*;

public class Ventana3{
	private Frame principal;
	private Button boton;

	public Ventana3() {
		principal = new Frame("Ejemplo AWT");
		principal.setSize(235, 130);
		principal.addWindowListener(new EscuchaEventosVentana());
		boton = new Button("Salir");
		boton.addActionListener(new EscuchaEventoBoton());
		principal.add(boton); //agrega el botón a la ventana
		principal.setVisible(true);
	}

	class EscuchaEventoBoton implements ActionListener {
		public void actionPerformed(ActionEvent e) {
			//Como se agregará al único botón disponible,
			//no me molestaré en confirmar que sea el botón correcto
			System.out.println("Boton salir presionado!");
			principal.setVisible(false);
			System.exit(0);
		}
	}   

	class EscuchaEventosVentana implements WindowListener {
		//Este evento es cuando se pulsa la X
		public void windowClosing(WindowEvent e) {
			System.out.println("Solicita cerrar la ventana");
			Frame ventana = (Frame)e.getWindow();
			ventana.setVisible(false);
			System.exit(0);
		}
		//Ocurre cuando ya se cerró la ventana
		public void windowClosed(WindowEvent e) {}
		public void windowIconified(WindowEvent e) {}
		public void windowActivated(WindowEvent e) {}
		public void windowDeactivated(WindowEvent e) {}
		public void windowDeiconified(WindowEvent e) {}
		public void windowOpened(WindowEvent e) {}
	}

	public static void main(String args[]) {
		Ventana3 v = new Ventana3();
	}
}

 

 

Bien… ya con esto tenemos al fin un botón. ¿Y si quisiera varios botones? ¿Bastaría con hacer varios add en la ventana y tendría varios botones? ¡Pues has la prueba! En un próximo artículo responderemos a esa pregunta.

AWT posee una tremenda cantidad de controles disponibles para utilizar. Mira la documentación del paquete java.awt y te darás cuenta de la cantidad. Sun pone también a disposición algunos tutoriales de cómo crear GUI, pero están en inglés y algunas cosas no se ven con tanta calma, por eso quiero hacer algunos artículos donde veamos GUI con más detalle… pero no puedo explicártelo todo: la idea es también investigar.

Si alguien lo desea, podría solicitar un artículo de un control en específico para revisarlo en detalle. O mejor aún: si tienes blog, podemos ponernos de acuerdo y hacer una serie de artículos donde tomemos controles y los expliquemos en detalle, un control por artículo. A quien le parezca la idea, que se apunte.

Y no se desesperen… Swing viene pronto

Fuente: http://esteparioprogramador.bligoo.com/content/view/258936/GUI_con_Java_I_A_W_T.html

Una opinión crítica sobre SWT

Sunday, March 22nd, 2009

En SWT Happens se presenta una opinión crítica sobre SWT (sistema de widgets “no oficiales” de Java).

Es un artículo del weblog Hacknot, lo cual a mi me da una cierta confianza en cuanto a su “neutralidad”, algo que no se puede dar por sentado cuando se lee sobre SWT y Swing, una nuevalucha religiosa en Java en la que es difícil encontrar opiniones formadas y no autocomplacientes con la opción elegida por el autor. Hacknot, por el contrario, es un weblog que recomiendo vivamente por su visión escéptica con las balas de plata en computación. Sus artículos suelen estar siempre refrendados por la experiencia real en proyectos reales.

En resumen dice sobre SWT:

  • Si elijes SWT por su fidelidad a la plataforma, no creas que esto es tan gran virtud. Normalmente los usuarios no tienen problemas en usar interfaces alejados de su s.o. nativomientras estos sean buenos. Ejemplos: Firefox, Winamp, etc. Por otro lado se utiliza un planteamiento de mínimo común denominador de las plataformas soportadas, por lo que puede haber una característica no disponible en windows sólo porque dicha característica no está disponible en motif.
  • Si las necesidades de tu aplicación se alejan de las necesidades del proyecto Eclipse la dificultad aumenta. SWT fue creado como soporte para el proyecto Eclipse y está orientado hacia él, dejando de lado características que Eclipse no utiliza.
  • SWT tiene muchos fallos. Es una plataforma relativamente joven y se nota.
  • Si elijes SWT sólo porque piensas que Swing es feo, no lo hagas. Hoy en día se puede hacer aplicaciones atractivas en Swing y ejemplos hay muchos.

Mucho más en el artículo.

Fuente: http://www.juanjonavarro.com/masquecodigo/2005/04/27/una-opinion-critica-sobre-swt

SWT ahora se porta como un .jar

Sunday, March 22nd, 2009

Hace un tiempo, basado en la experiencia que tuve y tengo haciendo soft con GUIs, al utilizar Java se me plantearon las dos alternativas serias que existen en el lenguaje: Swing ySWT.

Si bien el tema es motivo de “guerra santa” permanente entre la gente que está a favor deSunNetbeans y por último, Swing contra la de IBMEclipse y SWT, yo probé un poquito de las dos. Me gustó más SWT, más que nada porque Swing se veía horrible y lento en Linux (y no me parece cambiar de SO por ese motivo). Así que, como el que tenía la decisión era yo, hice entre otras cosas chiquitas, un programita para enviar SMS a través de internet a los celulares de Argentina, Sonar.

Sonar está escrito en Java+SWT, y como éste último utiliza los widgets nativos de la plataforma, existe un swt.jar para interfacear desde java (lo que se llama un wrapper), que llama a las distintas librerías compartidas nativas, según la plataforma donde esté corriendo.

Algo así, comparado con Swing:


(Extraído de http://www.developer.com/open/article.php/10930_3316241_2)

No quiero seguir con esta intro, para eso está Google, la Wikipedia y éste link. :-D

Como SWT utiliza librerías nativas, cada vez que se quiera ejecutar un programa que las utilice, debe ejecutarse configurando en el java.library.path, la ubicación de las librerías nativas (excepto todo lo que pertenezca al JDK en sí). Y SWT no está en la JDK.

Por ejemplo, este script Bash de inicio es típico de un programa en SWT:

#!/bin/bash
export PATH=$PATH:$(dirname $(readlink -f $0))
java -Djava.library.path=./swt/ -jar sonar.jar

(El mecanismo de MANIFEST.MF que incluye el .jar incluye por su parte a ./swt/swt.jar y listo.)

Esto era un inconveniente, más que nada para los usuarios de Swing, que no estaban acostumbrados a esto, ya que Swing está dentro de la JDK. Mecanismos como Java Web Start (que me parecen muy útiles) eran complicados de implementar con SWT, siendo éste el principal motivo.

El punto es que una buena noticia de la última versión de desarrollo de SWT (la 3.3M4) va a incluir las librerías nativas en el mismo swt.jar, haciendo innecesario definir esta constante.

Esto permite que todos los mecanismos estándar de ejecución de aplicaciones (hacer “doble click” en el .jar en Windows y Linux, por ejemplo) se apliquen a SWT tal como se aplican a Swing.

SWT, en mi opinión, es uno de los mejores toolkits multiplataforma (que utilizan el look and feel nativo) que conozco. Sólo con Java está bueno. Combinado con Jython es una masa!

Fuente: http://marcelosoft.blogspot.com/2006/12/swt-ahora-se-porta-como-un-jar.html

Motivos prýcticos para no usar SWT

Sunday, March 22nd, 2009
En este weblog el autor comenta una serie de problemas prýcticos que se ha encontrado con SWT. A diferencia de muchas otras guerras entre Swing y SWT los motivos por los que prefiere uno u otro son pragmíticos y tangibles, y no discusiones sobre si uno tiene más rendimiento que el otro con más fidelidad con las aplicaciones nativas del sistema operativo. 

El autor comienza contando como no le fue posible bajarse una versrión de Eclipse para Mac OS X sobre Intel; sýlo la beta de la versrión 3.2 soporta esta plataforma por causa de SWT. Tambrión se pregunta quý sucederý con el editor visual de eclipse, justo ahora que empezaba a funcionar en Mac OS X. ýCuanto tiempo tardarý que quizýs cuando aparezca Windows Vista suceda algo similar. 

Tambrión se queja del soporte para Linux, plataforma la cual todavía no se soporta la impresrión en SWT. El artículo concluye diciendo que SWT sýlo funciona correctamente para Windows, y que si quieres limitarte a aplicaciones para esta plataforma quizýs deberýas haber elegido otro lenguaje de programacrión. 

ýstas no son, ni mucho menos, las primeras quejas que oigo sobre SWT en otras plataformas diferentes de Windows. Yo siempre usado Swing, nunca he sentido necesidad de emplear otra cosa, así que nunca he experimentado estos problemas personalmente pero ¿alguno de vosotros los ha padecido?

Fuente: http://www.javahispano.org/contenidos/es/motivos_pr_cticos_para_no_usar_swt/

Aplicaciones java dejan de iniciarse

Sunday, March 22nd, 2009

Desde hace unos días me he dado cuenta que las aplicaciones java no me funcionan, intento ejecutar jEdit y se queda bloqueado en la pantalla de inicio o intento ejecutar azureus y me da una excepción:

Starting Azureus...
Java exec found in PATH. Verifying...
Suitable java version found [java = 1.5.0_04]
Configuring environment...
Loading Azureus:
java -Xms16m -Xmx128m -cp "/opt/azureus/Azureus2.jar:/opt/azureus/swt.jar:/opt/azureus/swt-mozilla.jar:/opt/azureus/swt-pi.jar" -Djava.library.path="/opt/azureus" -Dazureus.install.path="/opt/azureus" org.gudy.azureus2.ui.swt.Main ''
StartSocket: passing startup args to already-running Azureus java process.
DEBUG::Sun Jun 26 21:43:59 CEST 2005
  java.net.SocketException: Network is unreachable
        at java.net.PlainSocketImpl.socketConnect(Native Method)
        at java.net.PlainSocketImpl.doConnect(PlainSocketImpl.java:333)
        at java.net.PlainSocketImpl.connectToAddress(PlainSocketImpl.java:195)
        at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:182)
        at java.net.SocksSocketImpl.connect(SocksSocketImpl.java:364)
        at java.net.Socket.connect(Socket.java:507)
        at java.net.Socket.connect(Socket.java:457)
        at java.net.Socket.(Socket.java:365)
        at java.net.Socket.(Socket.java:178)
        at org.gudy.azureus2.ui.swt.StartSocket.(StartSocket.java:44)
        at org.gudy.azureus2.ui.swt.Main.(Main.java:75)
        at org.gudy.azureus2.ui.swt.Main.main(Main.java:98)

Azureus TERMINATED.

Después de reinstalar 20 veces el JDK, probando tanto java 1.4 como 1.5… he encontrado el problema gracias a un foro. Resulta que últimamente casi siempre utilizo wireless y por tanto cuando Ubuntu inicia la configuración de las tarjetas de red en el arranque, presiono CTRL+c para que se lo salte. En consecuencia, también se salta la configuración de la interfaz loopback. Esto hace que aplicaciones como jEdit o azureus no arranquen… solución:

sudo ifconfig lo 127.0.0.1 up

La verdad es que la gestión de la configuración de redes en GNU/Linux sigue siendo bastante precaria a nivel gráfico. Por consola es una maravilla, te montas los scripts que quieras y haces miles de virguerias. Pero los usuarios medios lo que quieres es configurar la red lo más automatizado posible, si estas cerca de la wireless del trabajo que se conecte a esa sin demasiadas preguntas y si estas en la wireless de tu casa lo mismo. Ojala mejore este aspecto.

Fuente: http://www.marblestation.com/blog/?p=416

GUI (Graphical User Interface) Interface gráfica de usuario en JAVA

Sunday, March 22nd, 2009

Para crear una aplicación con GUI “ventanas” usando JAVA: Elegir entre AWT, SWING, o SWT:

La descripción de cada una:

* AWT (Abstract Windowing Toolkit) fue el primer acercamiento de Java al desarrollo de interfaces gráficas (GUI). Permite mostrar ventanas con controles variados como cajas de texto y botones. Las GUIs con AWT son fáciles de desarrollar, y usan los controles propios del sistema operativo en el que se programa, por ejemplo, en windows aparecerá una ventana de texto típica de windows, en Mac, una ventana con sus respectivas características, etc. Pero algunos sistema operativos difieren de otros en el conjunto de controles, por lo que Sun solo implementó los controles comunes a los sistemas operativos a los que se dirige Java, que por lo general, es un conjunto reducido y simple respecto de los realmente disponibles.

* Swing fue introducido posteriormente motivado por la creciente demanda de los desarrolladores de tener una implementación no nativa, esto es, independiente de la plataforma, de controles de más alto nivel como árboles, tablas y texto. Con esto se gana en funcionalidad, pero con el inconveniente de hacer las aplicaciones Java con Swing demasiado específicas de Java. Sun añadió una emulación look and feel para aproximar el aspecto de las aplicaciones swing al sistema operativo sobre las que se ejecuta, pero no abarca las nuevas versiones de los sistemas operativos (Windows Me, 2000 en adelante, por ejemplo). Además, al estar implementado sobre Java y no de forma nativa en el sistema operativo, los tiempos de respuesta de las interfaces Swing son sensiblemente más lentas que las nativas.

El Standard Widget Toolkit (SWT) ha sido creado por IBM como reemplazo de la Java Abstract Windowing Toolkit (AWT) y Swing. De manera más precisa, el SWT es un conjunto de widgets para desarrolladores Java que ofrece una API portable y una integración muy ligada con la interfaz gráfica de usuario nativa al sistema operativo de cada plataforma. Así, cada plataforma debe adaptar el SWT para los gráficos nativos suyos. Esto parece que entra en contradicción con la filosofía de Java de ser independiente de la plataforma, pero ofrece ventajas en la unicidad del aspecto del GUI diseñado sea cual sea la plataforma sobre la que se ejecute. Hasta el momento los entornos a los que se ha portado SWT son Windows, Linux GTK, Linux Motif, Solaris Motif, AIX Motif, HPUX Motif, Photon QNX, y Mac OS X. Los gráficos en Java han tenido una larga y exitosa evolución: empezó con el básico AWT, viéndose ampliado por el potente paquete Swing. Actualmente se está empezando a imponer SWT. Describamos brevemente la evolución de cada uno de ellos:

* SWT (Standard Widget Toolkit) ofrece un conjunto de elementos que hacen uso directo de los controles nativos a través de la Interfaz Nativa de Java (JNI). Si los controles no están ofrecidos por el sistema operativo, SWT crea los suyos propios según las necesidades. Esto significa que se necesita código nativo para poder funcionar en cada sistema operativo, pero IBM ha sido capaz de adaptar SWT a un buen número de sistemas. Es muy destacable la importancia de SWT porque es el entorno gráfico de desarrollo que viene con Eclipse y debe ser utilizado en los plug-ins desarrollados para el mismo. Eclipse es una herramienta de desarrollo altamente potente, libre distribución, código abierto y adaptable a cualquier lenguaje de programación. Para saber más sobre Eclipse visítese su página www.eclipse.org.

SWT se compone esencialmente de tres elementos:

  • 1. En el nivel inferior se encuentra una librería nativa que interacciona directamente con el sistema operativo. Es la denominada JNI, la Java Native Interface. Al ser la parte más dependiente de la plataforma, debe ser portada en función de la misma.
  • 2. Por encima de la anterior capa está la clase Display, la interfaz por la que el SWT se comunica con la interfaz gráfica.
  • 3. El nivel superior lo forma la clase Shell, representa el tipo de ventana de más alto nivel y que es donde se alojan los widgets, controles o componentes. El shell es la parte de la interfaz que está directamente controlada por el sistema de ventanas del sistema operativo. La clase Shell es hija de la clase Display, en cuyo caso es la ventana o marco principal a partir de la cual se construye el resto de la interfaz, o bien hija de otro shell, siendo el ejemplo más común las ventanas de diálogo.

Para mostrar lo anterior, estudiemos el siguiente ejemplo “Hola mundo”:

HolaMundo.java

 import org.eclipse.swt.widgets.*;
public class HolaMundo { public static void main(String[] args) {
 Display display = new Display();
 Shell shell = new Shell(display);
 shell.setText("Hola Mundo");
 shell.setSize(200, 100);
 shell.open();
 while (!shell.isDisposed()) {
 if (!display.readAndDispatch())
display.sleep();
 }
 display.dispose();
}
}

Conforme a lo explicado anteriormente, identificamos en el código las siguientes partes: Display display = new Display(); Representa la pantalla y su conexión con el sistema gestor de ventanas del sistema operativo en el que nos encontramos.

El objeto display contendrá a su vez una lista de objetos shell. Shell shell = new Shell(display); shell.open();

El shell equivale a una ventana abierta sobre la pantalla. Es la clase raíz de los componentes y controles.

Prestemos atención al siguiente fragmento:

while (!shell.isDisposed()) { if (!display.readAndDispatch()) display.sleep(); }

Es el denominado bucle de eventos. Ha de ser programado explícitamente y su función es detectar y ejecutar eventos. Es la forma en que liberamos la CPU para otros menesteres ajenos a la interfaz gráfica cuando no se han producido eventos a los que dedicar ciclos de proceso para atender.

Por último observamos que los recursos del sistema han de ser liberados por el programador: display.dispose(); La liberación del objeto display conlleva la finalización de todos los shells hijos contenidos.

Este artículo sólo pretende ser una breve introducción a los fundamentos de SWT. Para conseguir las librerías SWT y más información el mejor lugar de inicio es www.eclipse.org/swt.

Este artículo fue republicado desde su original: http://www.gui.uva.es/~laertes/ Ahora mi ejemplo de HolaMundo.java

import org.eclipse.swt.*;
import org.eclipse.swt.widgets.*;
import org.eclipse.swt.layout.*;
public class HolaMundo {
public static void main(String[] args) {
Display display = new Display();
Shell shell = new Shell(display);
shell.setText("HelloWorld");
FillLayout layout = new FillLayout();
layout.type = SWT.VERTICAL; shell.setLayout(layout);
Label label1 = new Label(shell, SWT.CENTER);
Label label2 = new Label(shell, SWT.LEFT);
label1.setText("Hola es mi programa jejje...");
label2.setText("mi ventana esta aquí");
shell.open(); while (!shell.isDisposed()) if (!display.readAndDispatch()) display.sleep(); }
}
Fuente: http://www.blog.doutdex.com/2007/06/09/gui-graphical-user-interface-interface-grafica-de-usuario-en-java/

Aplicaciones Swing con apariencia nativa

Sunday, March 22nd, 2009

Suele ser importante que las aplicaciones que hagamos sean fáciles de usar. Para eso es importante que su apariencia sea familiar y se comporten como el resto de aplicaciones.

Java es un lenguaje multiplataforma y de por sí se encarga de muchas de las tareas, pero hay otras no resueltas que podemos implementar nosotros y otras que están resueltas pero hay que utilizarlas y tenerlas encuenta.

Sobre este tema hay un artículo muy bueno en inglés: Make your Swing app go native (parte 2 y parte 3).

Y a continuación voy a comentar algunos consejos adicionales.

El look & feel

Lo primero de todo que deberíamos hacer en nuestra aplicación Swing es establecer que Swing utilice el look & feel del sistema. Basta esta línea de código:

UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());

Sin embargo el look & feel para Windows antes de la versión Java SE 6 no es tan bueno como se espera. En caso de estar ejecutándolse una versión anterior a Java 6 podríamos optar por utilizar WinLaf.

También ocurre que el look & feel en Mac tampoco es tan bueno como podría serlo. Por ejemplo un JFileChooser en apariencia no tiene nada que ver con el cuadro de diáolo nativo de la interfaz Mac. Para solventar esto podemos detectar si la aplicación está funcionando en MacOS X y en ese caso cargar el look & feel Quaqua (hay una versión que sólo modifica el selector de ficheros).

Quaqua look and feel

Atajos de teclado

Otra cosa que deberemos tener en cuenta es que mientras en Windows/Linux se suele utilizar la tecla Control para los atajos de teclado, mientras que en MacOS X se utiliza habitualmente la tecla Comando. Por ejemplo en una opción de menú en vez de hacer lo siguiente:

JMenuItem m = new JMenuItem("Copy");
m.setAccelerator(KeyStroke.getKeyStroke('C', InputEvent.CTRL_MASK, false));

Deberíamos hacer lo siguiente:

JMenuItem m = new JMenuItem("Copy");
m.setAccelerator(KeyStroke.getKeyStroke('C', Toolkit.getDefaultToolkit().getMenuShortcutKeyMask(), false));

Este código en Windows o Linux creará una opción de menú que se activa con Control+C y el mismo código en MacOS X creará una opción de menú que se activa con Comando+C. La magia está en el método getMenuShortcutKeyMask().

Empaquetado

Podemos empaquetar nuestra aplicación en un archivo JAR ejecutable. Sin embargo esto no es una muy buena opción ya que

  • Presuponemos que el usuario tiene la máquina virtual instalada
  • Asumimos que la extensión “.jar” está asociada a la máquina virtual
  • No podemos personalizar el icono del archivo

Para solventar esto contamos con diversas herramientas que permiten crear un “.exe” en Windows a partir de un archivo JAR. Por ejemplo launch4j. Este software tiene muchas características, entre las que destacan:

  • Poder hacer un splash screen.
  • Detecta la máquina virtual y su versión.
  • Si la versión de la JVM no es la adecuada o no se encuentra permite definir un mensaje dirigido al usuario y un enlace a la descarga de la máquina virtual.
  • Permite definir un icono personalizado para el ejecutable.
  • La herramienta se puede ejecutar desde línea de comandos, lo cual permite automatizar la tarea de empaquetado mediante scripts.

Eso en cuanto a Windows. También desearemos crear un ejecutable para MacOS X. En tal caso podemos utilizarJarBundler que permite crear un “.app” a partir de un archivo JAR. Y después podemos empaquetar ese ejecutable en unarchivo DMG desde ant.

En Linux no conozco ninguna forma estándar de crear un ejecutable. Sin embargo siempre deberíamos ofrecer la posibilidad de ejecutar la aplicación a través de un archivo JAR ejecutable estándar. Así facilitaríamos la vida a algunos usuarios (Windows, Mac) y al resto no les quitaríamos ninguna facilidad.

Fuente: http://www.debugmodeon.com/item/811/aplicaciones-swing-con-apariencia-nativa

JPanel con imagen de fondo

Sunday, March 22nd, 2009

El siguiente código presenta una clase que extiende de JPanel y tiene la gracia que al ser dibujada pinta una imagen de fondo mediante el método setBackground(File o URL).

Básicamente lo que se hace es redefinir el método paint, primero pintando con el color de fondo seleccionado, luego pintando la imagen y finalmente pintando todos los componentes que agreguemos al panel.

A parte lo explicado funciona como cualquier otro JPanel.

 import java.awt.*;
 import java.io.*;
 import java.net.URL;
 import javax.imageio.ImageIO;
 import javax.swing.JPanel;

 public class JPanelBackground extends JPanel {
 private static final long serialVersionUID = -3488034684833395929L;

    Image imagen=null;

    public void setBackground(File file) throws IOException{
        if (file==null)
            imagen=null;
        else
            imagen=ImageIO.read(file);
    }

    public void setBackground(URL url) throws IOException{
        if (url==null)
            imagen=null;
        else
            imagen=ImageIO.read(url);
    }

    @Override
    public void paint(Graphics g) {
        g.setColor(getBackground());
        g.fillRect(0,0,getWidth(),getHeight());
        if (imagen!=null)
            g.drawImage(imagen, 0, 0, null);
        Component c;
        for (int i = 0; i < getComponentCount(); i++) {
            c = getComponent(i);
            g.translate(c.getX(), c.getY());
            c.print(g);
            g.translate(-c.getX(), -c.getY());
        }
    }        
 }

Ejemplo de uso:

    JFrame frame = new JFrame();
    JPanelBackground background=new JPanelBackground();
    background.setBackground(new File("foto.jpg"));
    frame.setLayout(new BorderLayout());
    background.add(new JButton("boton"));
    frame.add(background, BorderLayout.CENTER);
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.pack();
    frame.setVisible(true);
Fuente: http://www.debugmodeon.com/item/103248/jpanel-con-imagen-de-fondo