Programación en castellano
-Tutoriales

Gráficos con Java 2D


Soportar Interacción con el Usuario

Para permitir que el usuario interactúe con los graficos que hemos dibujado, necesitamos poder determinar cuando el usuario pulsa sobre uno de ellos. El método hit de Graphics2D proporciona una forma para determinar fácilmente si ha ocurrido una pulsación de ratón sobre una Shape particular. De forma alternativa podemos obtener la posición del click de ratón y llamar a contains sobre la Shape para determinar si el click ocurrió dentro de los límites de la Shape.

Si estamos usando texto primitvo, podemos realizar una simple comprobación obteniendo la línea exterior de la Shape que corresponde al texto y luego llamando a hit o contains con esa Shape. El soporte de edición de texto requiere una comprobación mucho más sofisticada. Si queremos permitir que el usuario edite el texto, generalmente deberíamos usar uno de los componentes de texto editable de Swing. Si estamos trabajando con texto primitivo y estamos usando TextLayout para manejar la forma y posición del texto, también podemos usar TextLayout para realizar la comprobación para la edición de texto. Para más información puedes ver Java 2D Programmer's Guide.

. Ejemplo: ShapeMover

Este applet permite al usuario arrastrar la Shape por la ventana del applet. La Shape se redibuja en cada nueva posición del ratón para proporcionar información al usuario mientras la arrastra.

Pulsa sobre la imagen para ejecutar el  applet.

Esta es una imagen del GUI del applet. Para ajecutar el applet, pulsa sobre ella. El applet aparecerá en una nueva ventana del navegador.

ShapeMover.java contiene el código completo de este applet.

Se llama al método contains para determinar si el cursor está dentro de los límites del rectángulo cuando se pulsa el botón. Si es así, se actualiza la posición del rectángulo.

public void mousePressed(MouseEvent e){
    last_x = rect.x - e.getX();
    last_y = rect.y - e.getY();
    if(rect.contains(e.getX(), e.getY())) updateLocation(e);
...
public void updateLocation(MouseEvent e){
    rect.setLocation(last_x + e.getX(), last_y + e.getY());
    ...
    repaint();

Podrías haber sobservado que redibujar la Shape en cada posición del ratón es muy lento, porque el rectángulo relleno es renderizado cada vez que se mueve, Usando el doble buffer podemos eliminar este problema. Si estamos usando Swing, el dibujo usará doble buffer automáticamente; si no es así tendremos que cambiar todo el código de renderizado. El código para una versión swing de este programa es SwingShapeMover.java . Para ejecutar la versión Swing, visita SwingShapeMover.

Si no estamos usando Swing, el Ejemplo: BufferedShapeMover en la siguiente lección nos muestra cómo podemos implementar el doble buffer usando un BufferedImage. Podemos dibujar en un BufferedImage y luego copiar la imagen en la pantalla.

. Ejemplo: HitTestSample

Esta aplicación ilustra la comprobación de pulsaciones dibujando el cursor por defecto siempre que el usuario pulse sobre el TextLayout, como se muestra en la siguiente figura.

Pulsa sobre la imagen para ejecutar el  applet.

Esta es una imagen del GUI del applet. Para ajecutar el applet, pulsa sobre ella. El applet aparecerá en una nueva ventana del navegador.

HitTestSample.java contiene el código completo de este applet.

El método mouseClicked usa TextLayout.hitTestChar para devolver un objeto java.awt.font.TextHitInfo que contiene la posición del click (el índice de inserción) en el objeto TextLayout.

La información devuelta por los métodos de TextLayout, getAscent, getDescent y getAdvance se utiliza para calcular la posición del origen del objeto TextLayout para que esté centrado tanto horizontal como verticalmente.

...
private Point2D computeLayoutOrigin() {
  Dimension size = getPreferredSize();
  Point2D.Float origin = new Point2D.Float();

  origin.x = (float) (size.width - textLayout.getAdvance()) / 2;
  origin.y =
    (float) (size.height - textLayout.getDescent()
             + textLayout.getAscent())/2;
  return origin;
}

...
public void paintComponent(Graphics g) {
  super.paintComponent(g);
  setBackground(Color.white);
  Graphics2D graphics2D = (Graphics2D) g;
  Point2D origin = computeLayoutOrigin();
  graphics2D.translate(origin.getX(), origin.getY());

  // Draw textLayout.
  textLayout.draw(graphics2D, 0, 0);

  // Retrieve caret Shapes for insertionIndex.
  Shape[] carets = textLayout.getCaretShapes(insertionIndex);

  // Draw the carets.  carets[0] is the strong caret and
  // carets[1] is the weak caret.
  graphics2D.setColor(STRONG_CARET_COLOR);
  graphics2D.draw(carets[0]);
  if (carets[1] != null) {
    graphics2D.setColor(WEAK_CARET_COLOR);
    graphics2D.draw(carets[1]);
  }
}

...
private class HitTestMouseListener extends MouseAdapter {

    /**
     * Compute the character position of the mouse click.
     */
    public void mouseClicked(MouseEvent e) {

      Point2D origin = computeLayoutOrigin();

      // Compute the mouse click location relative to
      // textLayout's origin.
      float clickX = (float) (e.getX() - origin.getX());
      float clickY = (float) (e.getY() - origin.getY());

      // Get the character position of the mouse click.
      TextHitInfo currentHit = textLayout.hitTestChar(clickX, clickY);
      insertionIndex = currentHit.getInsertionIndex();

      // Repaint the Component so the new caret(s) will be displayed.
      hitPane.repaint();
    }
 
Patrocinados
 

Copyright © 1999-2007 Programación en castellano. Todos los derechos reservados.
Formulario de Contacto - Datos legales - Publicidad
Mantenida por: Claudio y Dani.

Hospedaje web y servidores dedicados linux por Ferca Network

red internet: jugar gratis | amor | navidad 2009 | registro de dominios | servidores dedicados
más internet: comprar | gratis | posicionamiento en buscadores | decoración libre | gifs animados