summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorWill Norris <will@tailscale.com>2026-04-16 14:03:32 -0700
committerWill Norris <will@tailscale.com>2026-04-16 14:03:32 -0700
commit3241adb490f439d985b8c72df1d65d5d0706c9f5 (patch)
treeb8a7e59cfa898a1306952ac4775dcd28d7039938
parent69572c74357f0abf53187d5b6303e576c7d33255 (diff)
downloadtailscale-will/systray-colors.tar.xz
tailscale-will/systray-colors.zip
client/systray: support several different color themeswill/systray-colors
Currently we only have a dark theme icon with white and grey dots over a black background. For some desktops, a logo with black and grey dots over a white background might be preferable. And for desktops where the bar is *almost* black or white, but not quite, an option to render the logo with dots only and no background can look really nice. Add a new -theme flag to the systray command with the default staying the same as it is today. Updates #18303 Change-Id: Ia101a4a3005adb9118051b3416f5a64a4a45987d Signed-off-by: Will Norris <will@tailscale.com>
-rw-r--r--client/systray/logo.go46
-rw-r--r--cmd/systray/systray.go2
-rw-r--r--cmd/tailscale/cli/configure_linux.go8
-rw-r--r--cmd/tailscale/cli/systray.go13
4 files changed, 60 insertions, 9 deletions
diff --git a/client/systray/logo.go b/client/systray/logo.go
index a0f8bf7d0..334cd7917 100644
--- a/client/systray/logo.go
+++ b/client/systray/logo.go
@@ -11,6 +11,7 @@ import (
"image"
"image/color"
"image/png"
+ "log"
"runtime"
"sync"
"time"
@@ -204,12 +205,49 @@ var (
)
var (
- bg = color.NRGBA{0, 0, 0, 255}
- fg = color.NRGBA{255, 255, 255, 255}
- gray = color.NRGBA{255, 255, 255, 102}
- red = color.NRGBA{229, 111, 74, 255}
+ black = color.NRGBA{0, 0, 0, 255}
+ white = color.NRGBA{255, 255, 255, 255}
+ darkGray = color.NRGBA{102, 102, 102, 255}
+ lightGray = color.NRGBA{153, 153, 153, 255}
+ red = color.NRGBA{229, 111, 74, 255}
+ transparent = color.NRGBA{}
+
+ // default values to dark theme
+ bg = black
+ fg = white
+ gray = darkGray
)
+// SetTheme sets the color theme of the systray icon.
+//
+// Supported themes are:
+// - dark - white and gray dots over black background
+// - dark:nobg - white and grey dots over transparent background
+// - light - black and gray dots over white background
+// - light:nobg - black and grey dots over transparent background
+func SetTheme(theme string) {
+ switch theme {
+ case "dark":
+ bg = black
+ fg = white
+ gray = darkGray
+ case "dark:nobg":
+ bg = transparent
+ fg = white
+ gray = darkGray
+ case "light":
+ bg = white
+ fg = black
+ gray = lightGray
+ case "light:nobg":
+ bg = transparent
+ fg = black
+ gray = lightGray
+ default:
+ log.Printf("unknown theme: %q", theme)
+ }
+}
+
// render returns a PNG image of the logo.
func (logo tsLogo) render() *bytes.Buffer {
const borderUnits = 1
diff --git a/cmd/systray/systray.go b/cmd/systray/systray.go
index 9dc35f142..68a339782 100644
--- a/cmd/systray/systray.go
+++ b/cmd/systray/systray.go
@@ -15,9 +15,11 @@ import (
)
var socket = flag.String("socket", paths.DefaultTailscaledSocket(), "path to tailscaled socket")
+var theme = flag.String("theme", "dark", "color theme for Tailscale icon: dark, dark:nobg, light, light:nobg")
func main() {
flag.Parse()
lc := &local.Client{Socket: *socket}
+ systray.SetTheme(*theme)
new(systray.Menu).Run(lc)
}
diff --git a/cmd/tailscale/cli/configure_linux.go b/cmd/tailscale/cli/configure_linux.go
index 9ba3b8e87..da0444908 100644
--- a/cmd/tailscale/cli/configure_linux.go
+++ b/cmd/tailscale/cli/configure_linux.go
@@ -18,7 +18,7 @@ func init() {
maybeSystrayCmd = systrayConfigCmd
}
-var systrayArgs struct {
+var configSystrayArgs struct {
initSystem string
installStartup bool
}
@@ -32,7 +32,7 @@ func systrayConfigCmd() *ffcli.Command {
Exec: configureSystray,
FlagSet: (func() *flag.FlagSet {
fs := newFlagSet("systray")
- fs.StringVar(&systrayArgs.initSystem, "enable-startup", "",
+ fs.StringVar(&configSystrayArgs.initSystem, "enable-startup", "",
"Install startup script for init system. Currently supported systems are [systemd, freedesktop].")
return fs
})(),
@@ -40,8 +40,8 @@ func systrayConfigCmd() *ffcli.Command {
}
func configureSystray(_ context.Context, _ []string) error {
- if systrayArgs.initSystem != "" {
- if err := systray.InstallStartupScript(systrayArgs.initSystem); err != nil {
+ if configSystrayArgs.initSystem != "" {
+ if err := systray.InstallStartupScript(configSystrayArgs.initSystem); err != nil {
fmt.Printf("%s\n\n", err.Error())
return flag.ErrHelp
}
diff --git a/cmd/tailscale/cli/systray.go b/cmd/tailscale/cli/systray.go
index ca0840fe9..07de5c786 100644
--- a/cmd/tailscale/cli/systray.go
+++ b/cmd/tailscale/cli/systray.go
@@ -7,6 +7,7 @@ package cli
import (
"context"
+ "flag"
"github.com/peterbourgon/ff/v3/ffcli"
"tailscale.com/client/systray"
@@ -17,10 +18,20 @@ var systrayCmd = &ffcli.Command{
ShortUsage: "tailscale systray",
ShortHelp: "Run a systray application to manage Tailscale",
LongHelp: "Run a systray application to manage Tailscale.",
- Exec: runSystray,
+ FlagSet: (func() *flag.FlagSet {
+ fs := newFlagSet("systray")
+ fs.StringVar(&systrayArgs.theme, "theme", "dark", "color theme for Tailscale icon: dark, dark:nobg, light, light:nobg")
+ return fs
+ })(),
+ Exec: runSystray,
+}
+
+var systrayArgs struct {
+ theme string
}
func runSystray(ctx context.Context, _ []string) error {
+ systray.SetTheme(systrayArgs.theme)
new(systray.Menu).Run(&localClient)
return nil
}