cmux/Sources
Lawrence Chen f6c949add7
Add cmd-click fallback for bare filenames (ls output) (#2294)
* Add cmd-click fallback for bare filenames in terminal output

When cmd-clicking text that ghostty's built-in URL/path regex doesn't
match (e.g. bare filenames from `ls` like README.md, src, config.json),
fall back to checking if the word under cursor is a valid file or
directory in the terminal panel's CWD. Uses the existing
ghostty_surface_quicklook_word API to extract the word, then resolves
it against the panel's working directory and opens it if it exists.

* Add pointing-hand cursor on Cmd-hover over bare filenames

When holding Cmd and hovering over a word that resolves to an existing
file/directory in the terminal's CWD, show the pointing-hand cursor.
Hooks into mouseMoved and flagsChanged so the cursor updates both when
moving the mouse with Cmd held and when pressing/releasing Cmd while
the mouse is stationary.

* Address PR review comments

- Refresh ghostty mouse position before quicklook_word in mouseUp and
  flagsChanged so stale coordinates don't resolve the wrong word
- Use failable String(bytes:encoding:.utf8) instead of lossy decoding
- Skip absolute-path words (already handled by ghostty's regex)
- Guard against remote terminal sessions (local fileExists would be wrong)
- Use invalidateCursorRects instead of forcing iBeam on hover deactivation
  to avoid overwriting ghostty/AppKit's cursor state

* Add preferred editor setting for cmd-click file opens

New "Open Files With" picker in Settings > App lets users choose which
editor opens when cmd-clicking bare filenames. Options: System Default,
Cursor, VS Code, Windsurf, Zed, Sublime Text, Xcode. Reuses the
existing TerminalDirectoryOpenTarget app detection infrastructure.
Defaults to system default (NSWorkspace default handler).

* Replace editor picker with free-form command field, respect $VISUAL/$EDITOR

The "Open Files With" setting is now a text field where users can type
any command (code, zed, subl, open -a Xcode, etc.). Resolution order:
1. User-configured command from settings
2. $VISUAL environment variable
3. $EDITOR environment variable
4. System default (NSWorkspace)

Removes the fixed PreferredEditor enum in favor of flexibility.

* Fix stuck pointing-hand cursor using NSCursor push/pop

invalidateCursorRects did nothing since the view has no cursor rects.
Use NSCursor push/pop stack instead so the previous cursor is properly
restored when the hover deactivates.

* Remove $VISUAL/$EDITOR fallback, use system default when empty

$EDITOR/$VISUAL are typically terminal editors (vim, nano) that can't
launch as GUI subprocesses. Empty field now falls back to system default
(opens in Finder/default app) which is the expected behavior.

* Address PR review comments (round 2)

- Use broader CWD fallback chain (panelDirectories → requestedWorkingDirectory
  → workspace currentDirectory) matching Workspace split creation logic
- Pop cursor stack in viewDidMoveToWindow to balance push if view is removed
  while hover is active
- Reset preferredEditorCommand in resetAllSettings()
- Fall back to NSWorkspace.open when the custom editor command exits non-zero
  (e.g. command not found exits 127 but /bin/sh itself succeeds)

* Clear cursor on mouse exit to prevent stuck pointing-hand

---------

Co-authored-by: Lawrence Chen <lawrencecchen@users.noreply.github.com>
2026-03-30 04:49:17 -07:00
..
Find Fix command palette focus after terminal find (#2089) 2026-03-25 17:27:54 -07:00
Panels Keep cmux browser Find shortcuts authoritative (#2356) 2026-03-30 03:16:10 -07:00
Update Fix update error details dialog overflow (#2359) 2026-03-30 03:05:48 -07:00
AppDelegate.swift Keep cmux browser Find shortcuts authoritative (#2356) 2026-03-30 03:16:10 -07:00
AppIconDockTilePlugin.swift Fix Dock persistence for manual app icons (#2360) 2026-03-30 03:34:35 -07:00
AppleScriptSupport.swift fix: read working directory from panelDirectories instead of TerminalPanel 2026-03-20 04:15:44 +08:00
Backport.swift Resync terminal portals after sidebar changes (#1253) 2026-03-12 02:46:30 -07:00
BrowserWindowPortal.swift Fix browser pane hangs from redundant portal refreshes (#2353) 2026-03-30 03:51:18 -07:00
cmuxApp.swift Add cmd-click fallback for bare filenames (ls output) (#2294) 2026-03-30 04:49:17 -07:00
CmuxConfig.swift Validate workspace color during cmux.json decode (#2112) 2026-03-24 22:58:27 -07:00
CmuxConfigExecutor.swift Sanitize command before execution, not just display (#2122) 2026-03-25 00:28:30 -07:00
CmuxDirectoryTrust.swift feat: cmux.json for custom commands (#2011) 2026-03-24 22:28:46 -07:00
ContentView.swift Fix sidebar layout loop in workspace list (#2328) 2026-03-29 17:57:17 -07:00
GhosttyConfig.swift Add configurable sidebar tint color with light/dark mode support (#1465) 2026-03-15 15:48:57 -07:00
GhosttyTerminalView.swift Add cmd-click fallback for bare filenames (ls output) (#2294) 2026-03-30 04:49:17 -07:00
KeyboardLayout.swift fix: prevent Japanese IME confirmation Enter from executing command (#2075) 2026-03-24 22:24:13 -07:00
KeyboardShortcutSettings.swift Customizable number shortcuts (#1951) 2026-03-22 14:54:54 -07:00
NotificationsPage.swift Add Jump to Latest to the notifications popover (#1167) 2026-03-10 19:30:17 -07:00
PortScanner.swift Fix workspace creation crash after restore (#1985) 2026-03-25 00:04:03 -07:00
PostHogAnalytics.swift Flush PostHog hourly active events immediately (#934) 2026-03-05 04:00:04 -08:00
RemoteRelayZshBootstrap.swift Support image drag-and-drop into SSH terminals (#1838) 2026-03-20 18:31:19 -07:00
SentryHelper.swift Auto-heal missing CLI listener socket (#679) 2026-02-28 01:19:38 -08:00
SessionPersistence.swift fix: skip identical session autosave writes (#1732) 2026-03-18 03:24:40 -07:00
SidebarSelectionState.swift Implement session persistence pass 1 with multi-window restore 2026-02-22 15:39:59 -08:00
SocketControlSettings.swift Skip quit confirmation for tagged DEV builds (#2288) 2026-03-28 03:57:25 -07:00
TabManager.swift Fix sidebar live refresh for branch and PR state (#2331) 2026-03-29 18:15:57 -07:00
TerminalController.swift fix(socket): return not_found error when surface_id is provided but unresolvable (#2150) 2026-03-26 18:45:21 -07:00
TerminalImageTransfer.swift Fix SSH image transfer followups (#1904) 2026-03-20 21:32:21 -07:00
TerminalNotificationStore.swift Fix remote proxy notification spam with cooldown, backoff, and SSH keepalive (#2325) (#2330) 2026-03-29 18:07:39 -07:00
TerminalSSHSessionDetector.swift Fix SSH image transfer cleanup and IPv6 followups (#1907) 2026-03-20 22:04:52 -07:00
TerminalView.swift Add sidebar blur effect with withinWindow blending (#9) 2026-02-04 03:04:45 -08:00
TerminalWindowPortal.swift Fix #2210: coalesce portal sync to latest geometry (#2214) 2026-03-29 17:55:40 -07:00
UITestRecorder.swift Fix frozen terminals after split churn (#12) 2026-02-13 16:45:31 -08:00
WindowAccessor.swift Polish browser suggestions, focus, and tagged reload flow 2026-02-14 21:33:28 -08:00
WindowDecorationsController.swift Refine settings/about titlebar styling and controls alignment 2026-02-14 02:11:35 -08:00
WindowDragHandleView.swift Fix titlebar double-click zoom handling (#2130) 2026-03-25 02:15:15 -07:00
WindowToolbarController.swift Fix minimal mode toggle not updating titlebar state (#2218) 2026-03-27 20:25:51 -07:00
Workspace.swift Fix remote proxy notification spam with cooldown, backoff, and SSH keepalive (#2325) (#2330) 2026-03-29 18:07:39 -07:00
WorkspaceContentView.swift Fix minimal mode toggle not updating titlebar state (#2218) 2026-03-27 20:25:51 -07:00