Summary
Ctrl+V does nothing on GTK. It doesn't freeze (that was fixed on the #587 branch by d50d624) — it silently no-ops, in every context tested.
Two independent faults compound:
- quadraui's runner swallows the key.
quadraui/src/gtk/run.rs intercepts Ctrl+V, reads the system clipboard, emits UiEvent::ClipboardPaste(text), and unconditionally returns glib::Propagation::Stop — so the keypress never reaches anything else.
- vimcode never handles
UiEvent::ClipboardPaste. There is no match arm for it anywhere in src/. The only paste plumbing is vimcode's own Msg::ClipboardPasteToInput (src/gtk/mod.rs:1137, :2137, :7484), fed by an async GDK clipboard read (:2655-2667, :2865) that belongs to the pre-ShellApp Relm4 widget world.
So quadraui hands over an event vimcode ignores, having already consumed the key that vimcode's own path would have needed.
Reproduction (verified interactively, X11 + XTEST)
printf 'PASTED_CLIPBOARD_TEXT' | xclip -selection clipboard
./target/debug/vimcode
Command line: press :, then Ctrl+V, then type LIVE.
Result: command line shows :LIVE. The pasted text is absent. LIVE renders, proving the app is alive and processing input — this is a no-op, not a hang.
Editor, insert mode: press i, then Ctrl+V, then type LIVE.
Result: buffer shows LIVE. Pasted text absent.
Liveness confirmed both times — process in Sl on poll_schedule_timeout (normal GTK idle), window queryable, exits cleanly on SIGTERM.
Relationship to #587
Not a regression from #587's branch. Before d50d624, pasting froze the whole app (fork()-based x11_fork::ClipboardContext deadlocking a multithreaded GTK4 process), so paste never worked either. d50d624 correctly removes the deadlock hazard by using the non-forking X11ClipboardContext directly — it just reveals that the paste path underneath was never wired.
Worth stating plainly so the #587 branch isn't over-credited: "paste no longer freezes" is true; "paste works" is not.
Relationship to #592
Same family. Msg::ClipboardPasteToInput's live producers are GDK-widget callbacks from the Relm4 era, i.e. another orphan of the #540 Relm4→ShellApp migration, the same root cause as #592's 13 dropped overlay fields and #587's unpainted palette. Filed separately because the fix is different: #592 is about paint call sites, this is about an event handler that was never ported.
Suggested fix
Add a UiEvent::ClipboardPaste(text) arm to vimcode's GTK handle that routes to the focused input — command line, find/replace field, tree inline-edit, or the editor buffer — mirroring how TUI treats bracketed paste (TUI gets ClipboardPaste from crossterm for free, which is why paste works there). Routing to the focused input is explicitly the app's job per quadraui's own comment in run.rs.
Then either delete the dead Msg::ClipboardPasteToInput GDK path or reduce it to a thin producer of the same event, so there is one paste route rather than two.
Verification note (superseded — see re-scope below)
No GTK acceptance harness exists yet (quadraui#301 GtkDriver unbuilt), so this needs
live smoke on a display-capable machine (not dellserver). Working loop: set the clipboard
with xclip, drive with xdotool key --clearmodifiers ctrl+v (XTEST — --window is
ignored by GTK4), then type a sentinel string to prove liveness, and screenshot with
import -window.
Found while verifying #587's smoke checklist in a human-attended session on 2026-07-19.
Re-scope 2026-09-01 — unblocked, and the verification plan has changed
The hold is lifted. GOALS.md said to hold this until #592-D landed. #672 closed
2026-08-28 (2505786) and src/gtk/draw.rs is deleted. Nothing gates this issue now.
The "needs live smoke" note above is stale. #646 shipped GtkDriver
(src/gtk/testing.rs), which paints into in-memory Cairo ImageSurfaces and runs
headlessly with no DISPLAY. Per CLAUDE.md, black-box driver coverage is the
acceptance bar and there is no "no harness here" excuse on either backend. Write the
test; do not plan a manual smoke session around a harness that now exists.
The xclip/xdotool loop stays useful for a final on-screen confirmation, but it is no
longer the verification plan and must not be the only evidence.
One correction to the fix section. It proposes deleting or thinning the dead
Msg::ClipboardPasteToInput GDK path. That path's producers are the async GDK clipboard
reads at mod.rs:2655-2667 / :2865, which sit behind self.drawing_area — one of 22
Relm4-era widget handles that are initialised None and assigned nowhere in the
crate (audited 2026-09-01; see #592's audit comment). So that path is not merely
"orphaned in spirit", it is provably unreachable: there is nothing to thin, only to
delete. Do not attempt to revive it as a producer.
Acceptance criteria
Ctrl+V pastes into the command line, the find/replace field, tree inline-edit, and
the editor buffer on GTK.
- A
UiEvent::ClipboardPaste arm exists in GTK's ShellApp::handle; Msg::ClipboardPasteToInput
and its dead GDK producers are gone.
- A
GtkDriver black-box test asserts the rendered result of a paste — not that a
state field was populated (CLAUDE.md rule 1).
- The PR states the test was verified RED against unfixed
develop (rule 2).
cargo build && cargo test && cargo clippy -- -D warnings && cargo fmt --check EXIT=0.
Files
src/gtk/mod.rs (the UiEvent::ClipboardPaste arm; deletion of Msg::ClipboardPasteToInput
and its dead GDK producers at :2655-2667 / :2865)
src/gtk/testing.rs (GtkDriver coverage)
Overlaps #731 (which deletes the drawing_area handle those dead producers sit behind) and
#734 slice 5 (the clipboard-paste rung of the shared key router). Sequenced ahead of both:
this is the smallest of the three and the only one a user can see.
Summary
Ctrl+Vdoes nothing on GTK. It doesn't freeze (that was fixed on the #587 branch byd50d624) — it silently no-ops, in every context tested.Two independent faults compound:
quadraui/src/gtk/run.rsinterceptsCtrl+V, reads the system clipboard, emitsUiEvent::ClipboardPaste(text), and unconditionallyreturnsglib::Propagation::Stop— so the keypress never reaches anything else.UiEvent::ClipboardPaste. There is no match arm for it anywhere insrc/. The only paste plumbing is vimcode's ownMsg::ClipboardPasteToInput(src/gtk/mod.rs:1137,:2137,:7484), fed by an async GDK clipboard read (:2655-2667,:2865) that belongs to the pre-ShellApp Relm4 widget world.So quadraui hands over an event vimcode ignores, having already consumed the key that vimcode's own path would have needed.
Reproduction (verified interactively, X11 + XTEST)
Command line: press
:, thenCtrl+V, then typeLIVE.Result: command line shows
:LIVE. The pasted text is absent.LIVErenders, proving the app is alive and processing input — this is a no-op, not a hang.Editor, insert mode: press
i, thenCtrl+V, then typeLIVE.Result: buffer shows
LIVE. Pasted text absent.Liveness confirmed both times — process in
Slonpoll_schedule_timeout(normal GTK idle), window queryable, exits cleanly onSIGTERM.Relationship to #587
Not a regression from #587's branch. Before
d50d624, pasting froze the whole app (fork()-basedx11_fork::ClipboardContextdeadlocking a multithreaded GTK4 process), so paste never worked either.d50d624correctly removes the deadlock hazard by using the non-forkingX11ClipboardContextdirectly — it just reveals that the paste path underneath was never wired.Worth stating plainly so the #587 branch isn't over-credited: "paste no longer freezes" is true; "paste works" is not.
Relationship to #592
Same family.
Msg::ClipboardPasteToInput's live producers are GDK-widget callbacks from the Relm4 era, i.e. another orphan of the #540 Relm4→ShellApp migration, the same root cause as #592's 13 dropped overlay fields and #587's unpainted palette. Filed separately because the fix is different: #592 is about paint call sites, this is about an event handler that was never ported.Suggested fix
Add a
UiEvent::ClipboardPaste(text)arm to vimcode's GTKhandlethat routes to the focused input — command line, find/replace field, tree inline-edit, or the editor buffer — mirroring how TUI treats bracketed paste (TUI getsClipboardPastefrom crossterm for free, which is why paste works there). Routing to the focused input is explicitly the app's job per quadraui's own comment inrun.rs.Then either delete the dead
Msg::ClipboardPasteToInputGDK path or reduce it to a thin producer of the same event, so there is one paste route rather than two.Verification note (superseded — see re-scope below)
No GTK acceptance harness exists yet (quadraui#301
GtkDriverunbuilt), so this needslive smoke on a display-capable machine (not dellserver). Working loop: set the clipboard
with
xclip, drive withxdotool key --clearmodifiers ctrl+v(XTEST —--windowisignored by GTK4), then type a sentinel string to prove liveness, and screenshot with
import -window.Found while verifying #587's smoke checklist in a human-attended session on 2026-07-19.
Re-scope 2026-09-01 — unblocked, and the verification plan has changed
The hold is lifted.
GOALS.mdsaid to hold this until #592-D landed. #672 closed2026-08-28 (
2505786) andsrc/gtk/draw.rsis deleted. Nothing gates this issue now.The "needs live smoke" note above is stale. #646 shipped
GtkDriver(
src/gtk/testing.rs), which paints into in-memory CairoImageSurfaces and runsheadlessly with no
DISPLAY. PerCLAUDE.md, black-box driver coverage is theacceptance bar and there is no "no harness here" excuse on either backend. Write the
test; do not plan a manual smoke session around a harness that now exists.
The
xclip/xdotoolloop stays useful for a final on-screen confirmation, but it is nolonger the verification plan and must not be the only evidence.
One correction to the fix section. It proposes deleting or thinning the dead
Msg::ClipboardPasteToInputGDK path. That path's producers are the async GDK clipboardreads at
mod.rs:2655-2667/:2865, which sit behindself.drawing_area— one of 22Relm4-era widget handles that are initialised
Noneand assigned nowhere in thecrate (audited 2026-09-01; see #592's audit comment). So that path is not merely
"orphaned in spirit", it is provably unreachable: there is nothing to thin, only to
delete. Do not attempt to revive it as a producer.
Acceptance criteria
Ctrl+Vpastes into the command line, the find/replace field, tree inline-edit, andthe editor buffer on GTK.
UiEvent::ClipboardPastearm exists in GTK'sShellApp::handle;Msg::ClipboardPasteToInputand its dead GDK producers are gone.
GtkDriverblack-box test asserts the rendered result of a paste — not that astate field was populated (
CLAUDE.mdrule 1).develop(rule 2).cargo build && cargo test && cargo clippy -- -D warnings && cargo fmt --checkEXIT=0.Files
src/gtk/mod.rs(theUiEvent::ClipboardPastearm; deletion ofMsg::ClipboardPasteToInputand its dead GDK producers at
:2655-2667/:2865)src/gtk/testing.rs(GtkDrivercoverage)Overlaps #731 (which deletes the
drawing_areahandle those dead producers sit behind) and#734 slice 5 (the clipboard-paste rung of the shared key router). Sequenced ahead of both:
this is the smallest of the three and the only one a user can see.