mirror of
https://github.com/netbirdio/netbird.git
synced 2026-05-12 19:59:56 +00:00
[client/ui] Tray menu opens on click; hide window at startup
Left-click on the tray icon now opens the menu on every platform — the window is reached through a new "Open NetBird" entry. Only the action that matches the current daemon state is shown: Connect when disconnected, Disconnect when connected. The main window starts hidden and is only surfaced via the tray, single-instance launch, or daemon events.
This commit is contained in:
@@ -118,7 +118,7 @@ func main() {
|
||||
Title: "NetBird",
|
||||
Width: 960,
|
||||
Height: 640,
|
||||
Hidden: false,
|
||||
Hidden: true,
|
||||
BackgroundColour: application.NewRGB(24, 26, 29),
|
||||
URL: "/",
|
||||
Mac: application.MacWindow{
|
||||
|
||||
@@ -139,32 +139,15 @@ func NewTray(app *application.App, window *application.WebviewWindow, svc TraySe
|
||||
t.applyIcon()
|
||||
t.tray.SetTooltip(trayTooltip)
|
||||
t.tray.SetMenu(t.buildMenu())
|
||||
// Tray click handling is platform-specific by design:
|
||||
//
|
||||
// On Windows and macOS the OS-level tray protocol cleanly separates left
|
||||
// and right click. AttachWindow plus an explicit OnClick gives the
|
||||
// expected "click the icon to toggle the window, right-click to open the
|
||||
// menu" UX, and the platform never delivers both events at once.
|
||||
//
|
||||
// On Linux the tray rides on the org.kde.StatusNotifierItem D-Bus protocol
|
||||
// (libayatana-appindicator). The SNI Activate signal *is* left-click, but
|
||||
// several environments — GNOME Shell with the AppIndicator extension is
|
||||
// the loudest offender — also pop the attached menu on left-click,
|
||||
// regardless of the ItemIsMenu property the spec defines for that purpose.
|
||||
// Worse, AttachWindow on its own is enough to trigger this: Wails3's
|
||||
// SystemTray.applySmartDefaults installs ToggleWindow as the default
|
||||
// click handler whenever a window is attached, so even without an
|
||||
// explicit OnClick the window pops up alongside the menu. The result
|
||||
// looks like a bug to users.
|
||||
//
|
||||
// Mirror the legacy Fyne client's behaviour on Linux: skip both
|
||||
// AttachWindow and OnClick so left-click only opens the menu, and expose
|
||||
// the window through an explicit "Open NetBird" item. Right-click still
|
||||
// opens the menu through Wails' default rightClickHandler fallback.
|
||||
if runtime.GOOS != "linux" {
|
||||
t.tray.AttachWindow(window)
|
||||
t.tray.OnClick(func() { t.toggleWindow() })
|
||||
}
|
||||
// Left-click on the tray icon opens the menu on every platform. The
|
||||
// window is reached through the explicit "Open NetBird" entry. This
|
||||
// matches macOS NSStatusItem convention (click → menu), the Linux
|
||||
// StatusNotifierItem spec, and the legacy Fyne client. On Linux,
|
||||
// AttachWindow plus Wails3's applySmartDefaults would also pop the
|
||||
// window alongside the menu on environments like GNOME Shell with the
|
||||
// AppIndicator extension, so we intentionally skip both AttachWindow
|
||||
// and OnClick here. Right-click still opens the menu through Wails'
|
||||
// default rightClickHandler fallback.
|
||||
|
||||
app.Event.On(services.EventStatus, t.onStatusEvent)
|
||||
app.Event.On(services.EventSystem, t.onSystemEvent)
|
||||
@@ -195,16 +178,17 @@ func (t *Tray) buildMenu() *application.Menu {
|
||||
SetEnabled(false)
|
||||
|
||||
menu.AddSeparator()
|
||||
// On Linux the tray icon's left-click handler is intentionally unbound
|
||||
// (see NewTray for the rationale), so expose the window through an
|
||||
// explicit menu entry. Windows and macOS get the window via left-click.
|
||||
if runtime.GOOS == "linux" {
|
||||
menu.Add(menuOpenNetBird).OnClick(func(*application.Context) { t.ShowWindow() })
|
||||
menu.AddSeparator()
|
||||
}
|
||||
// The tray icon's left-click handler is intentionally unbound (see
|
||||
// NewTray for the rationale), so expose the window through an explicit
|
||||
// menu entry on every platform.
|
||||
menu.Add(menuOpenNetBird).OnClick(func(*application.Context) { t.ShowWindow() })
|
||||
menu.AddSeparator()
|
||||
// Only the action that applies to the current state is visible: Connect
|
||||
// when disconnected, Disconnect when connected. applyStatus swaps them on
|
||||
// each daemon status change.
|
||||
t.upItem = menu.Add(menuConnect).OnClick(func(*application.Context) { t.handleConnect() })
|
||||
t.downItem = menu.Add(menuDisconnect).OnClick(func(*application.Context) { t.handleDisconnect() })
|
||||
t.downItem.SetEnabled(false)
|
||||
t.downItem.SetHidden(true)
|
||||
|
||||
menu.AddSeparator()
|
||||
|
||||
@@ -245,17 +229,6 @@ func (t *Tray) buildMenu() *application.Menu {
|
||||
return menu
|
||||
}
|
||||
|
||||
func (t *Tray) toggleWindow() {
|
||||
if t.window == nil {
|
||||
return
|
||||
}
|
||||
if t.window.IsVisible() {
|
||||
t.window.Hide()
|
||||
return
|
||||
}
|
||||
t.window.Show()
|
||||
}
|
||||
|
||||
func (t *Tray) openRoute(route string) {
|
||||
if t.window == nil {
|
||||
return
|
||||
@@ -466,9 +439,11 @@ func (t *Tray) applyStatus(st services.Status) {
|
||||
t.statusItem.SetEnabled(needsLogin)
|
||||
}
|
||||
if t.upItem != nil {
|
||||
t.upItem.SetHidden(connected || needsLogin)
|
||||
t.upItem.SetEnabled(!connected && !needsLogin)
|
||||
}
|
||||
if t.downItem != nil {
|
||||
t.downItem.SetHidden(!connected)
|
||||
t.downItem.SetEnabled(connected)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user