2012-01-12 11 views
5

Hay un JTable en mi aplicación con columnas de encabezado de tamaño variable. Normalmente, cuando muevo el cursor sobre el encabezado de la tabla para cambiar el tamaño, el icono del cursor cambia a la flecha de cambio de tamaño, como < ->.El icono del cursor no cambia después de activar el método setCursor

Pero las cosas son diferentes en el siguiente escenario.

Hay una acción de botón en el mismo Frame, y durante la acción realizada, coloco el cursor en el icono ocupado y lo cambio al cursor predeterminado una vez que se completa la acción, usando el método Container.setCurosr(Cursor cursor).

A veces, si muevo el cursor sobre el encabezado de la tabla de redimensionamiento, después de una acción de botón, el icono del cursor no cambia para cambiar el tamaño de la flecha, el cursor no cambia en absoluto.

¿Se puede considerar esto como un error en Java Swing o existe una solución para este problema?

Actualización: Código de ejemplo adjunta

import java.util.*; 
import java.awt.*; 
import javax.swing.*; 
import java.awt.event.*; 

public class ColumnResizeIconTest extends JFrame { 

JScrollPane scrollPane; 
JTable table; 
JButton button; 

public ColumnResizeIconTest() { 
    setLayout(new BorderLayout()); 
    addComponents(); 
    setSize(300,300); 
} 

private void addComponents() { 
    addButton(); 
    addTable(); 
} 

private void addButton() { 
    button = new JButton("Click Me"); 
    button.addActionListener(new ActionListener() { 
     public void actionPerformed(ActionEvent ae) { 
      setWaitCursor(); 
      for(int i=0; i<2000; i++) { 
       System.out.print(i); 
      } 
      setDefaultCursor(); 
     } 
    }); 
    add(button, BorderLayout.NORTH); 
} 

private void addTable() { 
    scrollPane = new JScrollPane(createTable()); 
    add(scrollPane, BorderLayout.CENTER); 
} 

private JTable createTable() { 
    Object[][] cellData = { { "1-1", "1-2","1-3" }, { "2-1", "2-2", "2-3" }, { "3-1", "3-2", "3-3" } }; 
    String[] columnNames = { "column1", "column2", "column3" }; 
    table = new JTable(cellData, columnNames); 
    return table; 
} 

private void setWaitCursor() { 
    Container container = getContentPane(); 
    setWaitCursor(container); 
} 

private void setWaitCursor(Container container) { 
    for(int iCount = 0; iCount < container.getComponentCount(); iCount++) { 
     Component child = (Component) container.getComponent(iCount); 
     if(child instanceof Container) { 
      setWaitCursor((Container) child); 
     } else { 
      child.setCursor(new Cursor(Cursor.WAIT_CURSOR)); 
     } 
    } 
    container.setCursor(new Cursor(Cursor.WAIT_CURSOR)); 
} 

private void setDefaultCursor() { 
    Container container = getContentPane(); 
    setDefaultCursor(container); 
} 

private void setDefaultCursor(Container container) { 
    for(int iCount = 0; iCount < container.getComponentCount(); iCount++) { 
     Component child = (Component) container.getComponent(iCount); 
     if(child instanceof Container) { 
      setDefaultCursor((Container) child); 
     } else { 
      child.setCursor(new Cursor(Cursor.DEFAULT_CURSOR)); 
     } 
    } 
    container.setCursor(new Cursor(Cursor.DEFAULT_CURSOR)); 
} 

public static void main(String[] argv) throws Exception { 
    ColumnResizeIconTest test = new ColumnResizeIconTest(); 
    test.setVisible(true); 
} 
} 

Haga clic en el botón varias veces y tratar de cambiar el tamaño de la columna de la tabla. El cursor está atascado con el cursor predeterminado.

+0

¿qué versión de java en qué plataforma? –

+2

1) Para una mejor ayuda antes, publique un [SSCCE] (http://sscce.org/). 2) * "Se puede considerar esto como un error ..." * Probablemente. * ".. en Java Swing .." * Probablemente no. * "... ¿o hay una solución para este problema?" * Arregle su código (probablemente). –

+1

@ Andrew Thompson cuánto probablemente por hoy, de acuerdo con 4 probablemente de su 3. – mKorbel

Respuesta

8

Como ya mencioné en mi comentario: no es del todo trivial volver a/s et los cursores, ni siquiera para un solo componente :-) El problema base (en la configuración recursiva del cursor para esperar) es la suposición de que todos los componentes do tienen el cursor predeterminado.

Como ve en el encabezado de la tabla, esa suposición no es correcta: en ese componente, el "predeterminado" es el cursor predeterminado o el resizeCursor, dependiendo de la ubicación del mouse. Además, el alternar entre los cursores internos no es muy inteligente: no comprueba el estado (desde el principio, fue golpeado por ese hecho hace un tiempo :-)

No estoy del todo seguro de lo que quiere alcanzar, por lo tanto, no tenga una solución concreta, excepto dejar caer la configuración recursiva por completo, es muy difícil hacerlo bien. Las opciones podrían ser

  • hacer el GlassPane (de RootPane del marco) visible y establecer el waitCursor en él
  • uso JLayer (JDK7) o JXLayer (jdk6) en un área más pequeña y establecer el waitCursor en ese
  • use una visualización menos intrusiva, fiJProgressBar o una JXBusyLabel (in the SwingX project) en algún lugar

Adición (por @mKorbel :-)

el problema es fácilmente reproducible, con un pequeño cambio a la SSCCE PO (gracias por eso): el cambio el método addButton como se muestra a continuación, luego haga clic en el botón y mientras se muestra el cursor de espera, mueva el mouse al encabezado y luego a otra columna (a través del borde de la columna). Hacerlo varias veces dará lugar a cursores impredecibles en el encabezado ...

private void addButton() { 
    button = new JButton("Click Me"); 
    final ActionListener off = new ActionListener() { 

     @Override 
     public void actionPerformed(ActionEvent e) { 
      setDefaultCursor(); 
      button.setEnabled(true); 
     } 

    }; 
    button.addActionListener(new ActionListener() { 
     public void actionPerformed(ActionEvent ae) { 
      setWaitCursor(); 
      button.setEnabled(false); 
      Timer timer = new Timer(2000, off); 
      timer.setRepeats(false); 
      timer.start(); 
     } 
    }); 

    add(button, BorderLayout.NORTH); 
} 
+0

hasta ..., estaba seguro de que el viernes 13 es mañana, si recuerdo correctamente este es un problema de EDT, leí una pregunta similar (no sé dónde), sobre eso, que este proceso debe estar dividido en dos acciones separadas, de lo contrario no es garantía de órdenes de eventos para los Objetos que provienen del sistema operativo nativo, tal vez sea lo mismo que con Focus – mKorbel

+0

Olvidé por +1 – mKorbel

+0

@mKorbel Las infracciones EDT a menudo son culpable natural - no esta vez, sin embargo, es simplemente una lógica incompleta :-) – kleopatra

1

1) que tiene código de redireccionamiento de

for(int i=0; i<2000; i++) { 
    System.out.print(i); 
} 

a los antecedentes de tareas, puede implementa javax.swing.Timer, SwingWorke r, o envuelva estas líneas de código dentro Runnable#Thread, ejemplo here

2) tiene que restaurar Cursor en Error/Exception también, esa es probablemente la razón por la que no se cambió el Cursor

+0

Temo que hayas entendido mi problema correctamente. Antes de hacer clic en el botón, si coloco el cursor sobre el espacio entre los encabezados de columna de la tabla, el cursor será <-> lo que significa que puedo cambiar el tamaño. Cuando hago clic en el botón, dentro de la acción realizada, cambiará el cursor al reloj de arena y comenzará la acción. cuando la acción finaliza, el cursor cambia al cursor predeterminado y deja la acción ejecutada. Después de eso, si coloco el cursor en el espacio de la columna del encabezado de la tabla, el icono es el ícono predeterminado, no <->. Esto sucede si hago clic en el botón varias veces. Pero todavía puedo cambiar el tamaño de la columna. – AnupD

+0

no puede generar su problema, ni si presiono JButton muchas veces, redirigí Cursor al JFrame, JButton, JTable y puedo generar este problema con el Cursor, cuando y solo si se generó alguna excepción y no se cambió el Cursor en el bloque final, entonces hay Cursor.WAIT_CURSOR, hmm permanezca para siempre – mKorbel

+0

hmm .. Tengo la excepción, pero ese no es el caso aquí. Me gustaría poder compartir un video o una captura de pantalla del problema contigo. – AnupD

Cuestiones relacionadas