diff options
| author | Igor Soarez <igor@soarez.org> | 2026-10-22 18:01:04 +0300 |
|---|---|---|
| committer | Igor Soarez <igor@soarez.org> | 2026-10-22 18:01:04 +0300 |
| commit | f4a7346fd32f906ccc814364462c18afb3f10616 (patch) | |
| tree | c4502bc0a6725233e9ba45c5350bf7be44100f1d /menubar/hotkey.swift | |
| parent | 7649396bf30a65096fc3944e1404835e661f00af (diff) | |
agent search: spotlight-style fuzzy finder on ctrl+opt+cmd+shift+u
a centered, non-activating key panel that lists every agent and jumps to
the chosen one through the same dingger focus path as a row click.
- fzf-style matching: each word must match one of name, session, window,
harness, status, or directory, letters in order; the best alignment wins
(word starts and consecutive runs score higher), matched title letters
are highlighted.
- empty query keeps the menu's order, so enter jumps to the top waiting
agent.
- the selection follows the agent, not the position, as states change;
the list scrolls to keep it visible.
- keys: arrows, ctrl+n/p, ctrl+j/k, enter, esc, ctrl+u; the shortcut again
or clicking elsewhere closes it.
- search_hotkey setting; an unedited config file is upgraded. menu item
"Search Agents...". rows carry the pane's directory.
- --print-search and --snapshot-search debug flags; the panel's background
and snapshot code are shared.
selftest covers matching, ranking, highlighting, and selection; e2e step
15 checks queries through the real binary (fails when search only looks at
titles). e2e resolves relative binary paths, which tmux hooks need.
Diffstat (limited to 'menubar/hotkey.swift')
| -rw-r--r-- | menubar/hotkey.swift | 25 |
1 files changed, 23 insertions, 2 deletions
diff --git a/menubar/hotkey.swift b/menubar/hotkey.swift index c5ab178..136d94d 100644 --- a/menubar/hotkey.swift +++ b/menubar/hotkey.swift @@ -12,6 +12,7 @@ import Carbon.HIToolbox struct Settings: Equatable { var hotkey = "ctrl+opt+cmd+e" var jumpHotkey = "ctrl+opt+cmd+u" + var searchHotkey = "ctrl+opt+cmd+shift+u" static var directory: String { environment["DINGGER_CONFIG_DIR"] ?? (NSHomeDirectory() + "/.config/dingger") @@ -28,10 +29,28 @@ struct Settings: Equatable { # Jump to the agent at the top of the waiting list (blocked first, then # the longest done), like clicking the tmux status line. jump_hotkey = "ctrl+opt+cmd+u" + # Search all agents by name, session, window, harness, status, or + # directory, and jump to one. + search_hotkey = "ctrl+opt+cmd+shift+u" + + """ + + /// Earlier templates, replaced on upgrade if the user never edited them. + private static let olderTemplates = [firstTemplate, secondTemplate] + + private static let secondTemplate = """ + # dingger settings. The menu bar app reloads this file when you save it. + # Shortcuts: modifiers ctrl, opt, cmd, shift; keys a-z, 0-9, f1-f12, space. + + [shortcuts] + # Show or hide the floating panel. + hotkey = "ctrl+opt+cmd+e" + # Jump to the agent at the top of the waiting list (blocked first, then + # the longest done), like clicking the tmux status line. + jump_hotkey = "ctrl+opt+cmd+u" """ - /// The first template, replaced on upgrade if the user never edited it. private static let firstTemplate = """ # dingger settings. The menu bar app reloads this file when you save it. @@ -46,7 +65,7 @@ struct Settings: Equatable { /// upgrade it if it is still an unedited older template. static func ensureFile() { let existing = try? String(contentsOfFile: path, encoding: .utf8) - guard existing == nil || existing == firstTemplate else { return } + guard existing == nil || olderTemplates.contains(existing!) else { return } try? FileManager.default.createDirectory(atPath: directory, withIntermediateDirectories: true) try? template.write(toFile: path, atomically: true, encoding: .utf8) } @@ -64,6 +83,7 @@ struct Settings: Equatable { switch parts[0] { case "hotkey": settings.hotkey = value case "jump_hotkey": settings.jumpHotkey = value + case "search_hotkey": settings.searchHotkey = value default: break } } @@ -139,6 +159,7 @@ enum GlobalHotkey { enum Id: UInt32 { case panel = 1 case jump = 2 + case search = 3 } private static var references: [UInt32: EventHotKeyRef] = [:] |
