From 077a53d30eaa9582fa134836f193a60fb0e2979b Mon Sep 17 00:00:00 2001 From: nathan Date: Sat, 10 Nov 2018 15:53:39 +0100 Subject: [PATCH] Added tooltips (if possible) to checkbox menu items --- src/dorkbox/systemTray/Checkbox.java | 42 +++++++++++++++++++ src/dorkbox/systemTray/MenuItem.java | 2 +- src/dorkbox/systemTray/peer/CheckboxPeer.java | 2 + .../ui/awt/AwtMenuItemCheckbox.java | 6 +++ .../ui/gtk/GtkMenuItemCheckbox.java | 14 +++++++ .../ui/swing/SwingMenuItemCheckbox.java | 12 ++++++ 6 files changed, 77 insertions(+), 1 deletion(-) diff --git a/src/dorkbox/systemTray/Checkbox.java b/src/dorkbox/systemTray/Checkbox.java index b366366..14d83c3 100644 --- a/src/dorkbox/systemTray/Checkbox.java +++ b/src/dorkbox/systemTray/Checkbox.java @@ -32,6 +32,7 @@ class Checkbox extends Entry { private volatile boolean enabled = true; private volatile char mnemonicKey; + private volatile String tooltip; public Checkbox() { @@ -195,4 +196,45 @@ class Checkbox extends Entry { ((CheckboxPeer) peer).setShortcut(this); } } + + /** + * Specifies the tooltip text, usually this is used to brand the SystemTray icon with your product's name, or to provide extra + * information during mouse-over for menu entries. + *

+ * NOTE: Maximum length is 64 characters long, and it is not supported on all Operating Systems and Desktop Environments. + *

+ * For more details on Linux see https://bugs.launchpad.net/indicator-application/+bug/527458/comments/12. + * + * @param tooltipText the text to use as a mouse-over tooltip for the tray icon or menu entry, null to remove. + */ + public + void setTooltip(final String tooltipText) { + if (tooltipText != null) { + // this is a safety precaution, since the behavior of really long text is undefined. + if (tooltipText.length() > 64) { + throw new RuntimeException("Tooltip text cannot be longer than 64 characters."); + } + + if (!MenuItem.alreadyEmittedTooltipWarning) { + MenuItem.alreadyEmittedTooltipWarning = true; + SystemTray.logger.warn("Please disable tooltips, as they are not consistent across all platforms and tray types."); + } + } + + this.tooltip = tooltipText; + + if (peer != null) { + ((CheckboxPeer) peer).setTooltip(this); + } + } + + /** + * Gets the mouse-over tooltip for the meme entry. + * + * NOTE: This is not consistent across all platforms and tray types. + */ + public + String getTooltip() { + return this.tooltip; + } } diff --git a/src/dorkbox/systemTray/MenuItem.java b/src/dorkbox/systemTray/MenuItem.java index e74c54a..2a394aa 100644 --- a/src/dorkbox/systemTray/MenuItem.java +++ b/src/dorkbox/systemTray/MenuItem.java @@ -33,7 +33,7 @@ import dorkbox.util.SwingUtil; @SuppressWarnings({"unused", "SameParameterValue", "WeakerAccess"}) public class MenuItem extends Entry { - private static boolean alreadyEmittedTooltipWarning = false; + static boolean alreadyEmittedTooltipWarning = false; private volatile String text; private volatile File imageFile; diff --git a/src/dorkbox/systemTray/peer/CheckboxPeer.java b/src/dorkbox/systemTray/peer/CheckboxPeer.java index 7b95185..abbaf9a 100644 --- a/src/dorkbox/systemTray/peer/CheckboxPeer.java +++ b/src/dorkbox/systemTray/peer/CheckboxPeer.java @@ -31,5 +31,7 @@ interface CheckboxPeer extends EntryPeer { void setShortcut(Checkbox menuItem); + void setTooltip(Checkbox menuItem); + void setChecked(Checkbox menuItem); } diff --git a/src/dorkbox/systemTray/ui/awt/AwtMenuItemCheckbox.java b/src/dorkbox/systemTray/ui/awt/AwtMenuItemCheckbox.java index 50e3182..af2138f 100644 --- a/src/dorkbox/systemTray/ui/awt/AwtMenuItemCheckbox.java +++ b/src/dorkbox/systemTray/ui/awt/AwtMenuItemCheckbox.java @@ -122,6 +122,12 @@ class AwtMenuItemCheckbox implements CheckboxPeer { }); } + @Override + public + void setTooltip(final Checkbox menuItem) { + // no op. (awt menus cannot show tooltips) + } + @Override public void setChecked(final Checkbox menuItem) { diff --git a/src/dorkbox/systemTray/ui/gtk/GtkMenuItemCheckbox.java b/src/dorkbox/systemTray/ui/gtk/GtkMenuItemCheckbox.java index ffc2a80..b23612c 100644 --- a/src/dorkbox/systemTray/ui/gtk/GtkMenuItemCheckbox.java +++ b/src/dorkbox/systemTray/ui/gtk/GtkMenuItemCheckbox.java @@ -268,6 +268,20 @@ class GtkMenuItemCheckbox extends GtkBaseMenuItem implements CheckboxPeer, GCall } } + @Override + public + void setTooltip(final Checkbox menuItem) { + GtkEventDispatch.dispatch(new Runnable() { + @Override + public + void run() { + // NOTE: this will not work for AppIndicator tray types! + // null will remove the tooltip + Gtk2.gtk_widget_set_tooltip_text(_native, menuItem.getTooltip()); + } + }); + } + // this is pretty much ONLY for Ubuntu AppIndicators private void setCheckedIconForFakeCheckMarks() { diff --git a/src/dorkbox/systemTray/ui/swing/SwingMenuItemCheckbox.java b/src/dorkbox/systemTray/ui/swing/SwingMenuItemCheckbox.java index a72e590..f4c0726 100644 --- a/src/dorkbox/systemTray/ui/swing/SwingMenuItemCheckbox.java +++ b/src/dorkbox/systemTray/ui/swing/SwingMenuItemCheckbox.java @@ -173,4 +173,16 @@ class SwingMenuItemCheckbox extends SwingMenuItem implements CheckboxPeer { }); } } + + @Override + public + void setTooltip(final Checkbox menuItem) { + SwingUtil.invokeLater(new Runnable() { + @Override + public + void run() { + _native.setToolTipText(menuItem.getTooltip()); + } + }); + } }