perf(expose): lightweight entry + pre-paint flash mask; keep tile colors, opt-in inactive dimming#170
Conversation
Add src/popup-expose.ts exposing registerExposeCommand / buildExposeProgram / runExpose — a minimal commander program that imports only runTmuxExpose, not the full 4.5M CLI graph (importing it loads in ~40ms vs ~110ms for main.js). main.ts now registers the expose command via the shared registerExposeCommand (single source of truth). Inert until bin/aimux routes to it next. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
bin/aimux and bin/aimux-dev now route the `expose` subcommand to the lightweight popup entry via runRoutedCli(), instead of always loading the full CLI. Cuts exposé cold-start from ~110ms to ~40ms (near the raw-node floor), shrinking the residual open-blank. Other commands are unchanged. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The popup now paints the pre-popup screen snapshot instantly (printf home + cat) before exec-ing exposé, so the ~40ms node cold-start no longer shows a blank — your screen holds, then exposé atomically repaints it dimmed with the panel (its first render is already synchronized output). No shell-side dimming. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Exposé previews now render in the captured pane's real colors by default instead of being flattened to gray, and the active tile is never dimmed. Dimming non-selected tiles (gray preview + dim border) is now gated behind a new expose.dimInactive config option, default off. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
|
Warning Review limit reached
More reviews will be available in 3 hours and 30 minutes. Learn how PR review limits work. Your organization has used up its prepaid credits, and credit purchases are no longer available. Enable the review add-on in the billing tab to keep reviews running — you're only billed for reviews past your plan's rate limits ($0.25/file). ⌛ How to resolve this issue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based credits. 🚦 How do rate limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan refill rate. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, the refill rate gradually slows as usage increases. The highest same-day bursts are limited more strictly. Please see our Fair Usage Limits Policy for further information. ℹ️ Review info⚙️ Run configurationConfiguration used: defaults Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (2)
📝 WalkthroughWalkthroughThe PR splits the ChangesExpose routing split + dimInactive UI feature
Sequence Diagram(s)sequenceDiagram
participant bin as bin/aimux
participant env as launcher-env.ts
participant pe as popup-expose.ts
participant expose as expose.ts (runTmuxExpose)
participant main as main.ts
bin->>env: prepareStableCliEnv()
bin->>env: runRoutedCli()
env->>env: cliEntryFor(process.argv)
alt argv[2] === "expose"
env->>pe: dynamic import → runExpose()
pe->>pe: buildExposeProgram().parse()
pe->>expose: runTmuxExpose(toExposeOptions(opts))
expose->>expose: read+delete backdropFile
expose->>expose: drawTile(…, config.expose.dimInactive)
else other subcommand
env->>main: dynamic import main.js
end
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
Poem
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
Move the launcher backdrop-file read and unlink to before terminal setup and the SIGINT/SIGTERM handlers, so a fatal signal during exposé startup can't leak the temp file (the shell-side rm only fires when display-popup itself fails). Add a config-merge test for expose.dimInactive. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@src/launcher-env.ts`:
- Around line 89-94: The runRoutedCli() function has dynamic imports that lack
explicit error handling, which means rejected promises could become unhandled
rejections. Add .catch() handlers to both the
import("./popup-expose.js").then(...) chain in the expose condition and the
import("./main.js") in the else branch to explicitly catch and handle any import
rejections. Log the errors appropriately when they occur to align with error
handling patterns used in other parts of the codebase.
In `@src/popup-expose.ts`:
- Around line 69-70: In the runExpose function, the call to
buildExposeProgram().parse() needs to be changed to
buildExposeProgram().parseAsync() because registerExposeCommand defines async
action handlers that need to be properly awaited. Since async handlers are
present, using parseAsync is required by Commander.js to ensure proper execution
flow and error handling. Additionally, update the runExpose function signature
from void to return a Promise so that the async operation can be properly
awaited by callers.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro
Run ID: 538bede7-c0ca-4b07-ac95-841cbcef1f8c
📒 Files selected for processing (13)
bin/aimuxbin/aimux-devscripts/tmux-control.shsrc/config.test.tssrc/config.tssrc/launcher-env.test.tssrc/launcher-env.tssrc/main.tssrc/popup-expose.test.tssrc/popup-expose.tssrc/tmux/control-script.test.tssrc/tmux/expose-tile.test.tssrc/tmux/expose.ts
runExpose now uses parseAsync so commander awaits the async expose action (parse() would exit before runTmuxExpose settled). runRoutedCli catches a rejected dynamic import / runExpose and exits non-zero instead of relying on unhandled-rejection behavior. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Summary
Continues the exposé polish work (follows #169). Four focused changes:
src/popup-expose.tsexposesregisterExposeCommand/buildExposeProgram/runExpose: a minimal commander program that imports onlyrunTmuxExpose, not the full ~4.5M CLI graph (~40ms vs ~110ms).main.tsnow registers the expose command through the sharedregisterExposeCommand(single source of truth).bin/aimux/bin/aimux-devroute theexposesubcommand viarunRoutedCli(), cutting exposé cold-start from ~110ms to ~40ms (near the raw-node floor). Other commands unchanged.printfhome +cat) before exec-ing exposé, so the residual node cold-start no longer shows a blank: the screen holds, then exposé atomically repaints it dimmed (its first render is already synchronized output). No shell-side dimming.expose.dimInactiveconfig option, default off.Test plan
yarn typecheck,yarn lint, fullyarn vitest(1431 passing),yarn build— all clean.0.1.21-tui-ia; verifieddimInactivepresent in installeddist/config.jsand exposé routing through the lightweight entry.🤖 Generated with Claude Code
Summary by CodeRabbit
New Features
dimInactiveconfiguration option to control whether inactive tiles are dimmed in the exposé popup.Performance