Repository navigation
feat(studio): cancel element picking with Escape and show hover labels - #6900
Conversation
Preview approval requiredThis pull request comes from a fork, so Mintlify won't build a preview until someone with write access approves commit |
jrusso1020
left a comment
There was a problem hiding this comment.
Reviewed at 004ba4763187d351da64087a7f1a8a00202c49d4.
Cancellation restores the selection captured when picking began, and hover labels render outside the preview. Switching the active iframe disables the previous picker before enabling the next.
No blocking issue found in the selection restoration, message validation or cleanup paths. Label animation frames and listeners are released on clear/dispose/unmount. Existing source-patching behavior is retained.
Read the picker session and hover-label implementation, runtime additions and their callers. The standard package configuration ran useElementPicker.test.ts and elementPickerHoverLabel.test.ts: 31 passed. A fresh independent source pass found no blocker. No real-browser label placement or iframe navigation claim.
Need: yes · Size: ok · Reuse: existing runtime protocol, picker API and source patching · Simpler: already minimal · Structure: fine
Risk: medium — picker session and iframe lifecycle.
— hf-review
Verdict: APPROVE
Reasoning: Escape restoration and hover feedback are implemented through the existing picker contract with explicit lifecycle cleanup.
…-com#7336-heygen-com#7358 Adopt heygen-com#7304 (without CLI renderDiagnostic, needs heygen-com#6725), heygen-com#7331, heygen-com#7332, heygen-com#7334, heygen-com#7337, heygen-com#7336, heygen-com#7339, heygen-com#7289, heygen-com#5594, heygen-com#6900, heygen-com#7322, heygen-com#7342, heygen-com#7343, heygen-com#7350 (onProgress only), heygen-com#7352, heygen-com#7348, heygen-com#7344, heygen-com#7353, heygen-com#7356 and heygen-com#7355. Defer heygen-com#5708 (needs heygen-com#6911) and heygen-com#7345 (READ_VERSION 4 vs 7); heygen-com#7307 not applicable. Re-read 14 moved pins, pin 6 new PRs (monitored 126). Make checkReportFile module-private and suppress the cross-package closeTestChrome duplicate for fallow. Co-authored-by: Miguel Ángel <miguel.sierra@heygen.com> Co-authored-by: SophiaHuangCc <129631224+SophiaHuangCc@users.noreply.github.com> Co-authored-by: Dante <duanjl.china@gmail.com> Co-authored-by: Muzzy5150 <muzzy5150yt@gmail.com> Co-authored-by: ump45nose <52391318+ump45nose@users.noreply.github.com> Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com> Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
What
Studio's element picker now cancels with Escape when focus is in the Studio chrome, restores the selection that existed before pick mode began, and shows a compact identifier beside the hovered preview element.
The identifier uses
tag#id, thentag.first-class, then the tag name alone. It stays inside the visible preview/viewport, follows preview zoom and scrolling, ignores pointer input, and clears on cancellation, selection, iframe replacement, and unmount.Why
The preview runtime already handled Escape inside its iframe and emitted
pick-mode-cancelled, butuseElementPickerhad no Studio-window keyboard path and did not remember the pre-pick selection. It also ignored the existing validatedelement-hoveredmessages. As a result, Escape depended on which frame held focus, candidate selection could survive cancellation, and nested targets had no visible identity.Untouched upstream at
47fe68562f39d91b4d9280dff41ae43d67805faereproduced all three gaps: the initial regression run had 12 passing tests and 3 failures (Studio Escape remained active, no hover label was rendered, and cancellation retained the candidate instead of the original selection).Related work
Fixes #5585.
#4727 changes the runtime's human-readable element
labelpriority; this change does not alter that label and only adds optional class metadata for the picker identifier.How
element-hoveredonly from the active validated preview, reject malformed geometry, and ignore stale replaced-frame messages.classNameto picker element info. The runtime refreshes hover geometry after preview scroll/resize so the host label remains aligned.textContentin Studio's document with theme tokens andpointer-events: none; no hover state is written to project source.Before
The highlighted target had no visible identifier.
After
The same target shows
h1#hero-title; Escape restores the prior selection.Test plan
bun run --cwd packages/studio test src/hooks/useElementPicker.test.ts src/hooks/elementPickerHoverLabel.test.ts src/hooks/elementPickerHoverLabel.browser.test.ts(32 passed)bun run --cwd packages/core test src/runtime/picker.test.ts(52 passed)bun run --cwd packages/core test(262 files, 5,645 passed)bun run --filter '*' typecheckbun run lintbun run format:checkbun run buildbunx fallow audit --base upstream/main --fail-on-issues(no changed-file issues)The full Studio run completed 8,235 tests successfully. Its existing
useTimelineGroupEditingGSAP backup test still fails withUnknown encoding: base64url; the identical failure reproduces at the untouched upstream SHA. One unrelated filesystem-watch timing case also flaked during the patched full run and passed immediately when rerun alone. The picker-focused, browser, typecheck, lint, format, build, and full Core gates are green.Compatibility
Existing iframe Escape handling and normal element picks remain in place.
classNameis optional on the shared picker info type, so older runtime messages still fall back to a tag-only identifier. Source patching, selection trust, and zoom iframe behavior are preserved, and the change adds no dependency or persisted project state.AI assistance
Codex assisted with repository review, implementation, regression tests, and command execution. I reviewed the complete diff and validated the behavior and results above.