Skip to content

Add keyboard shortcuts for jumping to sidebar threads#1456

Draft
t3dotgg wants to merge 2 commits intomainfrom
t3code/thread-number-shortcuts
Draft

Add keyboard shortcuts for jumping to sidebar threads#1456
t3dotgg wants to merge 2 commits intomainfrom
t3code/thread-number-shortcuts

Conversation

@t3dotgg
Copy link
Copy Markdown
Member

@t3dotgg t3dotgg commented Mar 27, 2026

Summary

  • Added platform-aware thread jump shortcuts for the first nine visible sidebar threads (Cmd+1-Cmd+9 on macOS, Ctrl+1-Ctrl+9 elsewhere).
  • Displayed contextual shortcut hints next to thread rows while the modifier key is held.
  • Extracted jump-key logic into shared sidebar helpers and covered it with unit tests.
  • Reused the existing thread navigation path so shortcut selection behaves the same as clicking a thread.

Testing

  • Not run

Note

Medium Risk
Adds new global window keyboard listeners and expands the supported keybinding command set, which could introduce shortcut conflicts or unexpected navigation if matching logic is wrong.

Overview
Adds default keybindings and contract support for thread.jump.1 through thread.jump.9, enabling Cmd/Ctrl+number shortcuts.

Implements sidebar thread-jump navigation: computes the first 9 visible thread targets, intercepts matching shortcut events to navigate (reusing the existing selection/anchor behavior), and shows inline shortcut hint badges while the modifier key is held. Includes unit tests for jump target selection and command index parsing.

Written by Cursor Bugbot for commit 6aadae6. This will update automatically on new commits. Configure here.

Note

Add keyboard shortcuts for jumping to sidebar threads

  • Pressing mod+1 through mod+9 navigates to the corresponding visible thread in the sidebar, with per-thread hint badges shown while the modifier key is held.
  • Adds getVisibleThreadJumpTargets in Sidebar.logic.ts to compute an ordered list of up to 9 visible thread IDs from the current sidebar state, skipping collapsed projects and those where the thread panel is hidden.
  • Adds parseThreadJumpIndex in keybindings.ts to parse thread.jump.[1-9] commands into zero-based indices.
  • Default keybindings mod+1mod+9 are registered in keybindings.ts and the commands are added to STATIC_KEYBINDING_COMMANDS.

Macroscope summarized 6aadae6.

Summary by CodeRabbit

  • New Features
    • Added keyboard shortcuts to quickly jump between threads using keys 1–9 with a platform-specific modifier (Cmd on macOS, Ctrl on other platforms).
    • Visual hints now display on thread rows indicating which key to press for each thread when the jump modifier is held.

- Map the first nine visible threads to number keys
- Show platform-specific shortcut hints while modifier is held
- Add tests for key mapping and modifier detection
@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Mar 27, 2026

🚥 Pre-merge checks | ✅ 1 | ❌ 2

❌ Failed checks (2 warnings)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Description check ⚠️ Warning PR description includes summary and testing status, but lacks required sections: no 'What Changed' details, missing 'Why' rationale, no UI changes screenshots/videos despite adding visual hints, and checklist incomplete. Add 'What Changed' section with clear scope description, 'Why' section explaining problem and approach, before/after screenshots showing jump hint badges, and complete the checklist items to confirm PR follows guidelines.
✅ Passed checks (1 passed)
Check name Status Explanation
Title check ✅ Passed The pull request title clearly and concisely summarizes the main change: adding keyboard shortcuts for jumping to sidebar threads, which aligns with the primary focus of the changeset.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch t3code/thread-number-shortcuts

Comment @coderabbitai help to get the list of available commands and usage tips.

@github-actions github-actions bot added size:L 100-499 changed lines (additions + deletions). vouch:trusted PR author is trusted by repo permissions or the VOUCHED list. labels Mar 27, 2026
Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
apps/web/src/components/Sidebar.logic.test.ts (1)

110-147: Good platform-aware modifier detection tests.

Tests correctly cover:

  • macOS with metaKey
  • Windows with ctrlKey
  • Rejection when shiftKey is also pressed

Consider adding a test case for altKey: true to verify it's also rejected, matching the implementation requirement.

📝 Optional: Add altKey rejection test
expect(
  isThreadJumpModifierPressed(
    {
      key: "Control",
      metaKey: false,
      ctrlKey: true,
      shiftKey: false,
      altKey: true,
    },
    "Win32",
  ),
).toBe(false);
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@apps/web/src/components/Sidebar.logic.test.ts` around lines 110 - 147, Add a
test asserting that isThreadJumpModifierPressed rejects when altKey is true: in
the test "detects the active jump modifier by platform" add a case calling
isThreadJumpModifierPressed with a Windows platform ("Win32") and an event
object where ctrlKey: true, altKey: true (and shiftKey: false, metaKey: false)
and expect the result to be false; this mirrors the existing shiftKey rejection
case and verifies altKey is also treated as an invalid modifier.
apps/web/src/components/Sidebar.logic.ts (1)

81-111: Default navigator.platform may throw in non-browser contexts.

While Sidebar.tsx always passes platform explicitly, the default parameter navigator.platform would throw a ReferenceError if these helpers are ever called without an argument in SSR or test environments where navigator is undefined.

Consider using a safer default or documenting that the argument is required outside browser contexts.

🛡️ Suggested defensive default
 export function isThreadJumpModifierPressed(
   event: ThreadJumpEvent,
-  platform = navigator.platform,
+  platform = typeof navigator !== "undefined" ? navigator.platform : "",
 ): boolean {

Apply the same pattern to resolveThreadJumpIndex and formatThreadJumpHintLabel.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@apps/web/src/components/Sidebar.logic.ts` around lines 81 - 111, Defaulting
parameters to navigator.platform can throw in non-browser environments; update
isThreadJumpModifierPressed, resolveThreadJumpIndex, and
formatThreadJumpHintLabel to use a safe platform default (e.g. const
safePlatform = typeof navigator !== "undefined" ? navigator.platform : "" or
undefined) instead of directly using navigator.platform in the parameter list,
then use safePlatform in calls to isMacPlatform and other logic so these helpers
won’t ReferenceError in SSR/tests.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@apps/web/src/components/Sidebar.logic.test.ts`:
- Around line 110-147: Add a test asserting that isThreadJumpModifierPressed
rejects when altKey is true: in the test "detects the active jump modifier by
platform" add a case calling isThreadJumpModifierPressed with a Windows platform
("Win32") and an event object where ctrlKey: true, altKey: true (and shiftKey:
false, metaKey: false) and expect the result to be false; this mirrors the
existing shiftKey rejection case and verifies altKey is also treated as an
invalid modifier.

In `@apps/web/src/components/Sidebar.logic.ts`:
- Around line 81-111: Defaulting parameters to navigator.platform can throw in
non-browser environments; update isThreadJumpModifierPressed,
resolveThreadJumpIndex, and formatThreadJumpHintLabel to use a safe platform
default (e.g. const safePlatform = typeof navigator !== "undefined" ?
navigator.platform : "" or undefined) instead of directly using
navigator.platform in the parameter list, then use safePlatform in calls to
isMacPlatform and other logic so these helpers won’t ReferenceError in
SSR/tests.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: f3c49538-55ac-433c-86b5-46df99b9e76a

📥 Commits

Reviewing files that changed from the base of the PR and between add5f34 and aa91042.

📒 Files selected for processing (3)
  • apps/web/src/components/Sidebar.logic.test.ts
  • apps/web/src/components/Sidebar.logic.ts
  • apps/web/src/components/Sidebar.tsx

Copy link
Copy Markdown
Contributor

@cursor cursor bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 2 potential issues.

Fix All in Cursor

Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

});
},
[clearSelection, navigate, selectedThreadIds.size, setSelectionAnchor],
);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Duplicated navigation logic in handleThreadClick and navigateToThread

Low Severity

The new navigateToThread callback duplicates the plain-click branch of the existing handleThreadClick callback (clear selection, set anchor, navigate). The plain-click path in handleThreadClick (lines 964–972) performs the exact same sequence — check selectedThreadIds.size, call clearSelection, setSelectionAnchor, and navigate — but was not updated to call navigateToThread. This duplication means a future change to the navigation logic risks being applied in one place but missed in the other.

Additional Locations (1)
Fix in Cursor Fix in Web

- Bind Cmd/Ctrl+1-9 to thread jump commands
- Resolve jump targets from visible sidebar threads
- Show shortcut hints using current keybinding labels
@t3dotgg t3dotgg marked this pull request as draft March 27, 2026 23:37
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size:L 100-499 changed lines (additions + deletions). vouch:trusted PR author is trusted by repo permissions or the VOUCHED list.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant