Fix #192: collapsed Claude Code input in face-remapped popups#201
Merged
Conversation
There was a problem hiding this comment.
Pull request overview
This PR fixes issue #192 where Claude Code’s TUI input can render collapsed when ghostel runs in face-remapped popup windows by aligning ghostel’s initial/captured terminal row calculations with Emacs’s standard window-adjust-process-window-size-* machinery (using floor(window-screen-lines)), eliminating a startup SIGWINCH size correction.
Changes:
- Switch terminal height capture to
floor(window-screen-lines)across ghostel startup/exec/compile sizing paths. - Remove now-redundant
ghostel--reconcile-display-sizeand itswindow-buffer-change-functionsregistration. - Update
ghostel-debug-info“Size sync” diagnostics and adjust tests accordingly.
Reviewed changes
Copilot reviewed 4 out of 4 changed files in this pull request and generated 4 comments.
| File | Description |
|---|---|
| test/ghostel-test.el | Updates resize-related tests for window-screen-lines and removes tests for deleted reconcile logic. |
| lisp/ghostel.el | Uses floor(window-screen-lines) for sizing; removes ghostel--reconcile-display-size hook/function. |
| lisp/ghostel-debug.el | Fixes “Size sync” diagnostics to compare against floor(window-screen-lines) and adds face-height context. |
| lisp/ghostel-compile.el | Aligns compile-terminal height capture with floor(window-screen-lines) to avoid face-remap row mismatches. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
d817181 to
0e4e113
Compare
ghostel captured terminal height via `(window-body-height)' — which divides the window's pixel height by frame char height. But the standard `window-adjust-process-window-size-smallest' (and term.el, vterm, eat all do likewise) divides by `default-line-height' via `(window-screen-lines)', which respects `face-remapping-alist' and `:height' on the default face. When a theme remaps the buffer's default face — `nano-light' / `nano-dark' bump it ~7% higher than frame default — the two metrics disagree. Concrete report (#192): body 1307 px / 27 px frame char = 48 (window-body-height); 1307 px / 29 px default-line = 45.069 (window-screen-lines). Init captures 48, libghostty + PTY spawn at 48 rows; first redisplay fires `window-configuration-change-hook' (because body-pixel differs from the freshly-zeroed `old_body_pixel'), the standard adjust-fn runs, returns 45, and we issue an immediate startup SIGWINCH down to 45. Claude Code's /tui fullscreen sometimes mishandles the SIGWINCH-during-startup case and ends up with a collapsed input box. Switch every height-capture site to `floor(window-screen-lines)': - `ghostel--init-buffer' and `ghostel-exec' (the spawn paths). - `ghostel--commit-cropped-size' (minibuffer focus return). - `ghostel-compile.el' init/reconcile (3 sites) — same bug class. Add the `(max 1 …)' guard on the init-buffer height that `ghostel-exec' already had, since `floor' of a sub-1 value is a real (if unlikely) source of a 0-row terminal. Remove `ghostel--reconcile-display-size' and its `window-buffer-change-functions' registration (added in b9c12ca). Now redundant: with init capturing the right metric, the standard machinery (`window-configuration-change-hook' → `window--adjust-process-windows' → `--window-adjust-process-window-size') catches every transition the helper tried to catch — chrome reshuffles via `init_iterator''s body-pixel comparison (xdisp.c:3443-3474), buffer migration via `set_window_buffer' setting `FRAME_WINDOW_CHANGE'. Fix the "Size sync" block in `ghostel-debug-info' (added in 0b19011): compare `term-rows' against `(floor (window-screen-lines))' instead of `window-body-height', and surface the frame-vs-default line-height delta directly so a face-remap shows up in the report. Update affected tests to mock `window-screen-lines'.
0e4e113 to
ce966eb
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
/tui fullscreensometimes renders with the input box missing/collapsed when ghostel runs in a Doom popup with a theme that remaps the default face height (e.g.nano-light).ghostel--init-buffercaptured terminal height withwindow-body-height(units = frame char height) while the standardwindow-adjust-process-window-size-smallestuseswindow-screen-lines(units =default-line-height). When a theme remaps the default face height, the two disagree, init captures the wrong number, and the very next redisplay fireswindow-configuration-change-hook→ resize → SIGWINCH at startup. Claude Code's TUI sometimes mishandles a SIGWINCH-during-startup and never re-renders the input box.Approach
floor(window-screen-lines)— same metricterm.el,vterm,eat, and the standard adjust-fn use. With init capturing the right value from the start, the SIGWINCH-during-startup goes away.ghostel--init-buffer,ghostel-exec,ghostel--commit-cropped-size, plus 3 sites inghostel-compile.el.(max 1 …)guard on init-buffer height (parity withghostel-exec).ghostel--reconcile-display-sizeand itswindow-buffer-change-functionsregistration (added in b9c12ca). Now redundant: with init using the right metric, the standard machinery catches every transition the helper tried to catch (chrome reshuffles viainit_iterator's body-pixel comparison inxdisp.c:3443-3474, buffer migration viaset_window_buffersettingFRAME_WINDOW_CHANGE).ghostel-debug-info(added in 0b19011) which compared againstwindow-body-heightand cried wolf for any face-remapped buffer.--reconcile-display-sizemachinery.Test plan
make -j4 all— 184 elisp + 97 native + 39 evil all green/tui fullscreenM-x ghostel-debug-infoSize sync block still reads "in sync" in non-face-remapped setups (verified locally)