open ejemplo java css javafx-8 fxml

ejemplo - ¿Cómo controlar el retraso de la información sobre herramientas de JavaFX?



open dialog javafx (7)

De hecho, desde JavaFX 2, el comportamiento de la información sobre herramientas se gestiona internamente dentro de la clase Tooltip mediante el campo estático BEHAVIOR que no puede modificarse utilizando métodos públicos específicos, por lo tanto, por ahora. Si no desea reinventar la rueda o esperar a Java 9, La única manera es usar la API de Reflection como sigue:

/** * Hack allowing to modify the default behavior of the tooltips. * @param openDelay The open delay, knowing that by default it is set to 1000. * @param visibleDuration The visible duration, knowing that by default it is set to 5000. * @param closeDelay The close delay, knowing that by default it is set to 200. * @param hideOnExit Indicates whether the tooltip should be hide on exit, * knowing that by default it is set to false. */ private static void updateTooltipBehavior(double openDelay, double visibleDuration, double closeDelay, boolean hideOnExit) { try { // Get the non public field "BEHAVIOR" Field fieldBehavior = Tooltip.class.getDeclaredField("BEHAVIOR"); // Make the field accessible to be able to get and set its value fieldBehavior.setAccessible(true); // Get the value of the static field Object objBehavior = fieldBehavior.get(null); // Get the constructor of the private static inner class TooltipBehavior Constructor<?> constructor = objBehavior.getClass().getDeclaredConstructor( Duration.class, Duration.class, Duration.class, boolean.class ); // Make the constructor accessible to be able to invoke it constructor.setAccessible(true); // Create a new instance of the private static inner class TooltipBehavior Object tooltipBehavior = constructor.newInstance( new Duration(openDelay), new Duration(visibleDuration), new Duration(closeDelay), hideOnExit ); // Set the new instance of TooltipBehavior fieldBehavior.set(null, tooltipBehavior); } catch (Exception e) { throw new IllegalStateException(e); } }

Estaba jugando con JavaFX Tooltip . Me di cuenta de que, para mí, personalmente, la demora entre pasar sobre algo y la información sobre herramientas que aparece en realidad es demasiado larga. Una mirada en la API revela:

Normalmente, la información sobre herramientas se "activa" cuando el mouse se mueve sobre un Control. Por lo general, hay un cierto retraso entre el momento en que la información sobre herramientas se "activa" y el momento en que se muestra. Los detalles (como la cantidad de demora, etc.) se dejan a la implementación de Skin.

Después de una investigación adicional, no pude encontrar ninguna posibilidad de controlar este comportamiento. JavaFX CSS Reference no tiene información sobre el tiempo de retardo y una evaluación en tiempo de ejecución de getCssMetaData() tampoco ayudó.

Sé que hay una forma de controlar la información sobre herramientas de forma manual a través de onMouseEntered y onMouseExited , pero ¿realmente no hay otra forma? ¿O me estoy perdiendo una opción obvia?


En Java 9 y posteriores, puedes hacer

Tooltip tooltip = new Tooltip("A tooltip"); tooltip.setShowDelay(Duration.seconds(3));

También hay una propiedad hideDelay , para el retraso entre la información sobre herramientas que aparece y se oculta de nuevo. Los valores predeterminados son 1 segundo para el showDelay y 200 milisegundos para el hideDelay .


Encuentro que con la implementación anterior todavía hay un retraso que a veces no puedo explicar.

Lo siguiente ha funcionado para mí y eliminó el retraso por completo:

public static void bindTooltip(final Node node, final Tooltip tooltip){ node.setOnMouseMoved(new EventHandler<MouseEvent>(){ @Override public void handle(MouseEvent event) { // +15 moves the tooltip 15 pixels below the mouse cursor; // if you don''t change the y coordinate of the tooltip, you // will see constant screen flicker tooltip.show(node, event.getScreenX(), event.getScreenY() + 15); } }); node.setOnMouseExited(new EventHandler<MouseEvent>(){ @Override public void handle(MouseEvent event){ tooltip.hide(); } }); }


Extiende la información sobre herramientas o la clase de aplicación. (Solo java8)

/** * <p> * Hack TooltipBehavior */ static { try { Tooltip obj = new Tooltip(); Class<?> clazz = obj.getClass().getDeclaredClasses()[1]; Constructor<?> constructor = clazz.getDeclaredConstructor( Duration.class, Duration.class, Duration.class, boolean.class); constructor.setAccessible(true); Object tooltipBehavior = constructor.newInstance( new Duration(250), //open new Duration(5000), //visible new Duration(200), //close false); Field fieldBehavior = obj.getClass().getDeclaredField("BEHAVIOR"); fieldBehavior.setAccessible(true); fieldBehavior.set(obj, tooltipBehavior); } catch (Exception e) { Logger.error(e); } }



Uso el siguiente truco para esto a través de Reflexión.

public static void hackTooltipStartTiming(Tooltip tooltip) { try { Field fieldBehavior = tooltip.getClass().getDeclaredField("BEHAVIOR"); fieldBehavior.setAccessible(true); Object objBehavior = fieldBehavior.get(tooltip); Field fieldTimer = objBehavior.getClass().getDeclaredField("activationTimer"); fieldTimer.setAccessible(true); Timeline objTimer = (Timeline) fieldTimer.get(objBehavior); objTimer.getKeyFrames().clear(); objTimer.getKeyFrames().add(new KeyFrame(new Duration(250))); } catch (Exception e) { e.printStackTrace(); } }


Hola, no puedo hacer comentarios hasta que alcancé una reputación de 50, pero quería corregir la respuesta dada por Bruno Pado. El código que publicó no funcionó en JDK 8u121. El problema fue en qué campo declarado accedía. La solución es simple, cambie el índice de 1 a 0. Código de trabajo publicado a continuación:

/** * <p> * Hack TooltipBehavior */ static { try { Tooltip obj = new Tooltip(); Class<?> clazz = obj.getClass().getDeclaredClasses()[0]; Constructor<?> constructor = clazz.getDeclaredConstructor( Duration.class, Duration.class, Duration.class, boolean.class); constructor.setAccessible(true); Object tooltipBehavior = constructor.newInstance( new Duration(250), //open new Duration(5000), //visible new Duration(200), //close false); Field fieldBehavior = obj.getClass().getDeclaredField("BEHAVIOR"); fieldBehavior.setAccessible(true); fieldBehavior.set(obj, tooltipBehavior); } catch (Exception e) { Logger.error(e); } }

Espero que esto ayude a cualquiera que busque editar el retardo de la información sobre herramientas mientras esperamos a JFX9.