237 Commits
Author SHA1 Message Date
Matheus NogueiraandClaude Opus 4.6 3c36da80a8 fix: add git-based fallback for file search on Linux (#257)
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-01 21:05:18 -07:00
Jinjing 0a988d5c9b fix: restore pdf preview rendering (#258) 2026-04-01 17:28:05 -07:00
Jinjing 00d3e15c71 feat: change default divider thickness to 3px for first-time users (#256)
The previous 1px default was too thin for comfortable visibility.
This changes the default to 3px, which only affects new users who
haven't customized the setting. Also updates the preview component's
fallback to stay consistent with the new default.
2026-04-01 16:38:55 -07:00
Jinjing 532ee5ca4e fix: show file action buttons only on hover without layout shift (#255)
Action buttons (revert, stage) in the Changes list now use absolute
positioning with a solid background overlay, so they appear on hover
without taking up space or shifting file names and status letters.
2026-04-01 16:29:44 -07:00
Matheus Nogueira 2ec433f6df feat: add copy remote URL to line number context menu (#253)
* feat: add copy remote URL to line number context menu

Add 'Copy Remote URL' option to the line number gutter right-click menu,
allowing users to quickly copy a shareable link to a file and line on
GitHub, GitLab, Bitbucket, or other hosted git providers.

- Install hosted-git-info to parse remote URLs and generate browse URLs
- Add getRemoteFileUrl() to resolve file URLs using default branch
- Wire up IPC handler, preload bridge, and renderer UI
- Use ExternalLink icon to distinguish from path copy options

* refactor: use @types/hosted-git-info instead of custom type declarations

Replace the custom hosted-git-info.d.ts with the @types package from
DefinitelyTyped. Use a targeted cast for browseFile() which the @types
package doesn't include yet (stuck on v3 API).

* refactor: revert to local type declarations for hosted-git-info

The @types/hosted-git-info package is stuck on the v3 API and lacks
browseFile(). A local .d.ts is cleaner than casting around stale types.
2026-04-01 20:02:05 -03:00
Jinjing e8e7d2ea8f feat: add PDF file preview support in diff viewer (#252)
* fix: address review findings

- Add sandbox="allow-same-origin" to PDF iframes to prevent script execution
- Wrap atob() in try/catch to gracefully handle corrupt base64 data
- Reset imageError state on content change to allow re-rendering
- Add click overlay on PDF iframe so popup open works correctly
- Compact test mock resets to stay within max-lines lint rule

* fix: consolidate binary preview tests to stay within max-lines limit
2026-04-01 15:12:50 -07:00
Jinjing 528e03e8a5 fix: add null-byte validation to resolveRegisteredWorktreePath (#251) 2026-04-01 14:04:33 -07:00
Jinjing 5b3f132519 feat: prevent branch name reuse across PR history (#250)
- Reject worktree creation if the computed branch name already exists locally, on a remote, or in PR history. This prevents a fresh worktree from inheriting a stale/merged PR immediately after creation.
- Wrap getPRForBranch in try/catch so GitHub API failures don't block worktree creation
- Fix remote branch matching to compare full branch name after refs/remotes/<remote>/ prefix, preventing false positives
- Wrap updateWorktreeMeta in try/catch so meta-update failures don't leave the dialog in an error state for an already-created worktree
2026-04-01 13:24:07 -07:00
Colin ChambachanandClaude Opus 4.6 86799b4793 feat: add file actions to file explorer (#235)
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-01 09:36:52 -07:00
Jinjing 894f1bb6aa feat: show ShieldAlert icon for conflict-review tabs (#249)
* feat: show ShieldAlert icon for conflict-review tabs

Display a distinct orange ShieldAlert icon for tabs opened in
conflict-review mode, differentiating them from regular diff tabs.

* fix: clear stale Rebasing/Merging badge on non-active worktrees

The git status polling only runs for the active worktree. When a
non-active worktree finishes rebasing, its conflict operation was
never updated to 'unknown', leaving the badge stuck.

Add a lightweight git:conflictOperation IPC (fs-only, no git subprocess)
and poll it for non-active worktrees that have a non-unknown operation.
Once the operation clears, the worktree drops out of the poll list.
2026-03-31 21:47:59 -07:00
Jinjing 617f0c3487 feat: add jump-to-file button in diff view and improve tab styling (#248)
Add a "Open file" button in the diff editor header that opens the
modified-side file in a regular edit tab — useful for accessing
markdown preview from a diff. The button is disabled when the diff
target is deleted.

Also refine tab bar styling: active tabs now use accent background
with bold text, and file explorer rows get consistent hover colors.
2026-03-31 19:23:57 -07:00
Jinjing 2dd8954468 feat: add find in markdown preview (#247) 2026-03-31 19:22:24 -07:00
NeilandClaude Opus 4.6 9fa7aec27a feat: show hover tooltip for OSC 8 and file path links (#246)
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-31 19:07:14 -07:00
Jinjing 8d44edcda9 fix: harden updater version comparisons (#245) 2026-03-31 16:31:04 -07:00
Jinwoo HongandClaude Opus 4.6 12344a51cf fix: capture terminal buffers before quitAndInstall (#241)
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-31 15:34:14 -07:00
Jinjing 12dc676209 feat: allow search for hidden files in quick-open (#239)
Enable --hidden flag for ripgrep so dotfiles users commonly edit
(.env, .github/*, .eslintrc, etc.) appear in quick-open results.
Use a blocklist of tool-generated hidden dirs instead of blocking
all dot-prefixed paths.

Key changes:
- Add --hidden to rg and filter via HIDDEN_DIR_BLOCKLIST
- Add second rg call with --no-ignore-vcs to surface .env* files
- Use fast string-slice prefix stripping with path.relative() fallback
- Guard against path traversal in the fallback path
- Handle Windows path separators via --path-separator and normalization
- Collect into shared Set to avoid duplicate array spread
2026-03-31 13:09:56 -07:00
Jinjing 4497d3adf5 feat: add isMainWorktree field to GitWorktreeInfo (#237)
Expose whether a worktree is the repo's main working tree (the first
entry from `git worktree list`). This lets consumers distinguish the
main worktree from linked worktrees created via `git worktree add`.
2026-03-31 09:24:13 -07:00
d13d59ac40 fix: show correct keyboard shortcuts on Windows in terminal context menu (#233)
* fix: show correct keyboard shortcuts on Windows in terminal context menu

The terminal right-click menu was hardcoded to show macOS shortcuts
(⌘C, ⌘V, etc.) regardless of platform. Now detects the OS via
navigator.userAgent and shows Ctrl+ on Windows/Linux.

Follows the same pattern used in ShortcutsPane and WorktreeMetaDialog.

Fixes #230

* fix: use template literals for compound shortcuts to avoid JSX whitespace

Multi-line JSX expressions insert a space between modifier tokens
(e.g. "⌘ ⇧D" instead of "⌘⇧D"). Template literals avoid this.

---------

Co-authored-by: niklasmarderx <niklasmarderx@users.noreply.github.com>
Co-authored-by: Jinjing <6427696+AmethystLiang@users.noreply.github.com>
2026-03-31 08:56:41 -07:00
Jinjing e0e01cd687 feat: configurable worktree cards with property toggles (#232)
- fix: stay under max-lines lint limit after merge with main

Extract restoreScrollbackBuffers into layout-serialization.ts to reduce
use-terminal-pane-lifecycle.ts below the 300-line limit. Also filter
stale leaf IDs from persisted scrollback buffers and remove design doc.

- fix: polish worktree card controls

- feat: configurable worktree cards with property toggles
2026-03-31 08:49:00 -07:00
Jinjing f2eb119c62 feat: display CI conflict details and improve merge-conflict UX (#234)
- Add PRConflictSummary type and derive conflict metadata (base ref,
  commits behind, conflicting files) via local git merge-tree
- Fix parseUnmergedEntry to use space-separated parsing (porcelain v2
  unmerged entries are not tab-separated)
- Enhance rebase detection by checking rebase-merge/ and rebase-apply/
  directories in addition to REBASE_HEAD
- Show conflicting files list and commits-behind count in ChecksPanel
- Disable merge button with tooltip when PR has conflicts
- Add operation banners (merge/rebase/cherry-pick) in SourceControl
  and WorktreeCard
- Reorder section list so unstaged changes appear above staged
- Extract conflict-summary, issues, and gh-utils into separate modules
- Add 10s timeout to git fetch in conflict summary derivation
- Fix test fixtures to match real porcelain v2 format
2026-03-31 01:27:39 -07:00
Jinjing 86ea7ad719 feat: improve updater flow with auto-restart after download (#231)
* improve the updater

* fix: extract restoreScrollbackBuffers to fix max-lines lint error
2026-03-30 22:58:17 -07:00
Yax Patel c6481d8b64 feat: improve terminal font settings with weight control and keyboard navigation (#228) 2026-03-30 20:47:21 -07:00
Jinwoo HongandClaude Opus 4.6 831b65fe65 feat: restore terminal scrollback on app restart (#224)
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-30 20:11:35 -07:00
Jinjing 240df66365 fix: display image files in editor instead of "Binary file — cannot display" (#222)
Wire up ImageViewer and ImageDiffViewer components by passing file path
through bufferToBlob/buildDiffResult and returning base64 content + MIME
type for recognized image formats (PNG, JPG, GIF, SVG, WebP, BMP, ICO).
2026-03-30 00:00:32 -07:00
Jinjing f7eaf2e5e0 fix: restore markdown preview list markers (#223)
* fix: restore list markers in markdown preview

The app-wide CSS reset removes list-style from all elements, which
strips bullet points and numbers from markdown preview content.
Add scoped overrides for .markdown-body to restore disc/circle/square
markers for unordered lists and decimal markers for ordered lists.

* fix: restore markdown preview list markers
2026-03-30 00:00:03 -07:00
Jinjing 414b7e8cd5 fix: restore list markers in markdown preview (#221)
The app-wide CSS reset removes list-style from all elements, which
strips bullet points and numbers from markdown preview content.
Add scoped overrides for .markdown-body to restore disc/circle/square
markers for unordered lists and decimal markers for ordered lists.
2026-03-29 23:55:08 -07:00
Jinjing d45ead3682 fix: use inline-flex to stabilize find widget buttons (#220) 2026-03-29 23:14:42 -07:00
Jinjing affa73bcd3 fix: Windows compatibility — CRLF line endings and cross-drive path traversal (#217)
* fix: Windows compatibility — handle CRLF line endings and cross-drive path traversal

- Replace literal '\n' splits with /\r?\n/ regex across git output parsers
  (status, worktree, hooks, file listing) to handle Windows CRLF line endings
- Fix path traversal security check in isDescendantOrEqual using isAbsolute()
  instead of sep+sep prefix check, preventing cross-drive bypasses on Windows
- Strip trailing \r from ripgrep output in quick-open file listing

* fix(test): align updater test with user-initiated not-available behavior

The test expected 'idle' for a user-initiated check hitting a missing
latest-mac.yml, but the code correctly sends 'not-available' to give
the user explicit feedback that they're on the latest version.
2026-03-29 22:06:59 -07:00
Jinjing c625ce882e fix(updater): show feedback when check-for-update hits a mid-release draft (#215)
During a mid-release (draft version on GitHub), clicking "Check for Updates"
would silently return to idle with no user feedback. Now shows "You're on the
latest version" when the fallback confirms no published update is available.
2026-03-29 20:26:06 -07:00
Jinjing 91cf221786 fix(ui): prevent sidebar reordering on click (#214) 2026-03-29 20:05:36 -07:00
Neil 4c9ce5d230 Add View Changes action to update notifications (#210) 2026-03-29 19:54:48 -07:00
Jinjing aaece3483b fix: quick-open file search returns no results (#213)
The ripgrep command used --hidden with positive re-inclusion globs
('.github', '.github/**') to keep .github files visible.  However,
positive globs in ripgrep act as a whitelist — once present, only files
matching those positive patterns are returned, which excluded every
non-dotfile (including CLAUDE.md and all source files).

Drop --hidden entirely so rg uses its default behavior: skip hidden
dirs, respect .gitignore, and return all normal files.
2026-03-29 19:09:33 -07:00
Jinjing 774a405e58 fix(ui): show initial file list in quick-open and reduce empty padding (#212)
The conditional render guard hid the results container when there was
no query and loading was complete, which prevented the default 50-file
list from appearing.  Include filtered.length > 0 in the condition so
the initial results are visible.

Also removes the outer pb-2 so there is no empty space below the input
when no results are present, and reduces inner padding to pb-1.
2026-03-29 19:03:47 -07:00
Jinjing 2ea48cd96b fix(ui): allow Cmd/Ctrl+P when terminal is focused (#211)
* fix(ui): allow Cmd/Ctrl+P when terminal is focused

xterm.js uses a hidden <textarea class="xterm-helper-textarea"> for
keyboard capture.  isEditableTarget() was treating it as a real editable
field, which suppressed all global shortcuts (Cmd+P, Cmd+N, etc.) when
the terminal had focus.

Exclude that element so app-level keybindings remain reachable.

* fix(ui): hide empty quick-open results area and reduce bottom padding

The results container was always rendered with pb-2, leaving visible
empty space below the search input when there were no results.
Conditionally render the results div only when there is content, and
reduce padding from pb-2 to pb-1.
2026-03-29 19:02:19 -07:00
Jinjing b70ab2c4f7 fix(ui): prevent sidebar reordering on click and mark timed-out searches as truncated (#209)
Introduce sortEpoch to decouple sort recomputation from click-triggered
state changes (clearing isUnread, GitHub refresh). Use synchronous useMemo
instead of useEffect so the sort order is available before the first render.

Also fix timeout-killed ripgrep searches resolving with truncated: false,
which misled the UI into showing partial results as complete.
2026-03-29 18:14:14 -07:00
Neil efd9c72a76 fix: speed up sidebar file search (#208) 2026-03-29 17:21:06 -07:00
Jinjing 818a315bc9 fix(ui): increase active worktree card background contrast (#207)
The previous bg-accent/80 was too subtle to distinguish the active
worktree at a glance. Use bg-black/[0.06] (light) and bg-white/[0.10]
(dark) for a more obvious selection highlight.
2026-03-29 16:37:16 -07:00
Jinjing e2bb60339f feat: surface merge conflict warning in checks panel (#206) 2026-03-29 16:27:18 -07:00
Jinjing 193c6b96d1 fix(ui): fix scrolling in markdown preview and use editor scrollbar (#205)
- Update flex and height classes in MarkdownPreview, EditorContent, DiffViewer, and CombinedDiffViewer to ensure min-h-0 and flex-1 bubble down properly.
- Apply `scrollbar-editor` class to MarkdownPreview to match Monaco's scrollbar style.
2026-03-29 16:21:43 -07:00
Jinjing 333023fb67 feat: show merge conflicts in source control sidebar (#204)
* Squashed commits

- refactor

- commit design doc

* docs: add why-comments to conflict resolution code and track conflicts on open

- Add explanatory comments throughout conflict resolution code covering
  safety constraints, architectural boundaries, and compatibility choices
- Track unresolved conflicts in openConflictFile so Resolved locally
  state works for conflict-safe entry point
- Add CLAUDE.md/AGENTS.md guideline for documenting the "why"
- Add test for conflict tracking through openConflictFile
2026-03-29 15:40:23 -07:00
Jinjing ba7634ed0a fix: reduce Gemini terminal flashing (#203) 2026-03-29 15:26:09 -07:00
Jinjing ca1d9c5779 feat: extract file explorer entry filter logic (#200)
- feat: extract file explorer entry filter logic
2026-03-29 13:16:43 -07:00
Jinjing 1ba8cda4d9 fix: prevent stale PR cache overwrites on force refresh (#198) 2026-03-29 12:55:14 -07:00
Jinjing 7b69790311 style: make squash and merge button smaller with xs size (#199) 2026-03-29 12:54:36 -07:00
Jinjing a7ae905a97 fix: add updater fallback for GitHub release transitions (#197) 2026-03-29 12:50:36 -07:00
Jinjing 2840ff98c1 feat: allow deleting files and folders from file explorer (#196)
Add file/folder deletion via right-click context menu using Electron's
shell.trashItem (moves to OS trash, not permanent delete). Includes a
confirmation dialog, reveal-in-explorer support, and refactors the file
explorer into smaller composable modules.
2026-03-29 12:44:11 -07:00
Jinjing 98cbfcabfa fix: hide branch empty state on Uncommitted tab to avoid duplicate (#195)
The generic "No changes on this branch" empty state was showing on both
tabs. Scope it to the All tab so only "No uncommitted changes" shows on
the Uncommitted tab.
2026-03-29 09:56:46 -07:00
Jinjing 94fbbdbbd2 style: remove PR title from source control tab switcher (#192) 2026-03-29 09:44:01 -07:00
Jinjing 6622dfac11 style: use PR icon+link style matching WorktreeCard (#191)
Replace the colored badge with the same PR display style used in
WorktreeCard: state-colored PullRequestIcon, clickable PR number link,
and truncated title text.
2026-03-29 09:42:06 -07:00
Jinjing 86c64e9005 feat: move PR badge to tab switcher and make it clickable (#190)
Move the PR badge from CompareSummary into the tab switcher bar so it's
always visible. Clicking it opens the PR on GitHub.
2026-03-29 09:40:13 -07:00