Post

Implementing Tray Icon for Common Linux Environments - Part two

Cryptomator issue #1645

Please find the first post of this story here.

Further development

The further development required icons that can be pressed to trigger the tray icon menus and that look good on major Linux desktop environments. I designed SVG icons for that purpose, that scale well on different sizes of task bars and screen resolutions.

On GNOME 43 and KDE 5.24.7 they look like this:

GNOME-TrayIcons Tray icons on GNOME 43

KDE-TrayIcons Tray icons on KDE 5.24.7

To enable the tray icon functionality for Cryptomator on Linux, you need to enable the appropriate setting in the Cryptomator settings file:

1
"showTrayIcon": true

Some notes from the development perspective

The integations-* API of Cryptomator is capable of handling PNG files (as byte[] streams), but needed to be widened to handle SVG as well:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
   * @param tooltip       Text shown when hovering
   * @throws TrayMenuException thrown when adding the tray icon failed
   */
-  void showTrayIcon(byte[] imageData, Runnable defaultAction, String tooltip) throws TrayMenuException;
+  default void showTrayIcon(byte[] imageData, Runnable defaultAction, String tooltip) throws TrayMenuException {
+    showTrayIcon(imageData, null, defaultAction, tooltip);
+  };
+
+  /**
+   * Displays an icon on the system tray.
+   *
+   * @param imageData     What image to show
+   * @param icon      The icon name of the icon to show. Can be an icon name following
+   *                    the Freedesktop Icon Naming Specification or a path to an icon file
+   * @param defaultAction Action to perform when interacting with the icon directly instead of its menu
+   * @param tooltip       Text shown when hovering
+   * @throws TrayMenuException thrown when adding the tray icon failed
+   */
+  void showTrayIcon(byte[] imageData, String icon, Runnable defaultAction, String tooltip) throws TrayMenuException;
+
+  /**
+   * Updates the icon on the system tray.
+   *
+   * @param imageData What image to show
+   * @throws IllegalStateException thrown when called before an icon has been added
+   */
+  default void updateTrayIcon(byte[] imageData) {
+    updateTrayIcon(imageData, null);
+  };

  /**
   * Updates the icon on the system tray.
   *
   * @param imageData What image to show
+   * @param icon    The icon name of the icon to show. Can be an icon name following
+   *                  the Freedesktop Icon Naming Specification or a path to an icon file
   * @throws IllegalStateException thrown when called before an icon has been added
   */
-  void updateTrayIcon(byte[] imageData);
+  void updateTrayIcon(byte[] imageData, String icon);

  /**
   * Show the given options in the tray menu.

On a review of my code contribution to this issue the Cryptomator devs suggested to use JDK 20 already for coding. I used JDK 19 (preview) for coding the change. JDK 20 was released shorty before and the Cryptomator project will move to it. Coding with JDK 19 (preview) makes it impossible to load compiled classes from JDK 20.

As soon as JDK 20 will be available on Arch Linux, I’ll migrate my code to JDK 20.

This post is licensed under CC BY 4.0 by the author.

Trending Tags