Skip to content

Fix tab-bar gap after shell exit with hide-if-single#1518

Closed
0x0aa wants to merge 22 commits into
raphamorim:mainfrom
0x0aa:fix-hiding
Closed

Fix tab-bar gap after shell exit with hide-if-single#1518
0x0aa wants to merge 22 commits into
raphamorim:mainfrom
0x0aa:fix-hiding

Conversation

@0x0aa
Copy link
Copy Markdown
Contributor

@0x0aa 0x0aa commented Apr 15, 2026

Summary

Fixes #1514 — with navigation.hide_if_single = true and two tabs open, exiting the shell in one tab leaves a single tab but keeps an empty strip reserved at the top where the tab bar used to be. The terminal content stays shifted down until the next event triggers a re-layout.

Reproduced on Arch Linux / Sway (Wayland). The affected handler in application.rs runs on Linux and Windows, so the fix should apply equally on both.

The bug

There are two ways to go from two tabs to one with hide_if_single on:

  • Closing the tab via the close-tab shortcut — handled by Screen::close_tab in screen/mod.rs, which already calls resize_top_or_bottom_line(1) followed by current_grid_mut().update_dimensions(&mut self.sugarloaf) and render(). This path works.
  • The shell exiting on its own (e.g. typing exit) — handled by the RioEvent::CloseTerminal branch in application.rs. This path only called resize_top_or_bottom_line(size). The margin was recomputed, but update_dimensions was never invoked, so sugarloaf.set_position kept the old origin and the freed tab-bar strip stayed empty until something else forced a re-layout.

The fix

In application.rs, mirror what Screen::close_tab already does for the shortcut path: after resize_top_or_bottom_line, call current_grid_mut().update_dimensions(&mut sugarloaf) and screen.render() so the new scaled margin is pushed to sugarloaf and the frame is redrawn immediately.

Test plan

  • With navigation.hide_if_single = true and two tabs open, type exit in one tab — the remaining tab's content moves up to the top of the window with no empty strip.
  • Same config, two tabs open, close one tab via the close-tab shortcut — behavior unchanged (still no gap).
  • With hide_if_single = false and multiple tabs, exit a shell — the tab bar remains visible and laid out as before.

Debugging and the proposed fix were generated with the assistance of Claude — please review critically.

raphamorim and others added 15 commits April 18, 2026 10:26
Switch `set_system_backdrop` from the Windows 11 22H2+ DWM backdrop
attribute (`DWMWA_SYSTEMBACKDROP_TYPE`) to the legacy `SetWindow
CompositionAttribute` path with `ACCENT_ENABLE_BLURBEHIND`. The DWM
path requires Windows 11 build 22523+; the legacy path works on
Windows 10 v1809+ and every Windows 11 build, giving a consistent
blur across all supported Windows versions.

Dynamic-loads `SetWindowCompositionAttribute` from user32.dll via
`GetProcAddress`; the symbol isn't in the public SDK. Falls back to
a no-op when the function isn't present.

Uses `AccentFlags = 2` (undocumented "use gradient color") so the
tint renders properly — matches Tauri's `window-vibrancy` crate.
Without it, blur ignores the gradient color and picks a washed-out
default.

Co-authored-by: NSPC911 <NSPC911@users.noreply.github.com>
Flake lock file updates:

• Updated input 'flake-parts':
    'github:hercules-ci/flake-parts/f20dc5d' (2026-03-01)
  → 'github:hercules-ci/flake-parts/3107b77' (2026-04-01)
• Updated input 'flake-parts/nixpkgs-lib':
    'github:nix-community/nixpkgs.lib/c185c7a' (2026-03-01)
  → 'github:nix-community/nixpkgs.lib/333c4e0' (2026-03-29)
• Updated input 'nixpkgs':
    'github:NixOS/nixpkgs/b40629e' (2026-03-18)
  → 'github:NixOS/nixpkgs/4bd9165' (2026-04-14)
• Updated input 'rust-overlay':
    'github:oxalica/rust-overlay/c807e83' (2026-03-21)
  → 'github:oxalica/rust-overlay/e611106' (2026-04-18)
@0x0aa 0x0aa changed the title Remove margin at the top when left with a single tab and hide-if-single is on Fix tab-bar gap after shell exit with hide-if-single Apr 20, 2026
@shiena
Copy link
Copy Markdown
Contributor

shiena commented Apr 23, 2026

Thanks for this — I ran into one additional transition that the PR as written doesn't cover, so I put the follow-up on top of your branch for reference:

The extra case:

Screen::resize_top_or_bottom_line gates its margin update behind a comparison against Context::dimension.margin, but ContextGrid::apply_taffy_layout zeroes dimension.margin on every run (frontends/rioterm/src/layout/mod.rs:917). After
the first layout pass, that "previous margin" is always (0, 0, 0, 0). Walking 1 → 2 → 1 tabs with hide_if_single = true:

  1. 1 → 2: previous_margin.top = 0, padding_y_top = 34 → predicate is true, update_scaled_margin runs. The subsequent apply_taffy_layout zeroes dimension.margin.
  2. 2 → 1: previous_margin.top = 0 (zeroed in step 1), padding_y_top = 0 (hide-if-single + 1 tab) → predicate is false, update_scaled_margin is skipped, and the grid's scaled_margin.top stays at 34 * scale.

The update_dimensions call this PR adds in CloseTerminal then runs apply_taffy_layout, which computes rich-text position as (abs_y + scaled_margin.top) / scale = 34. The island is hidden but the rich text still starts ~34 px down — the
same visual gap this PR is trying to close.

The same early-exit also catches the close-tab shortcut path. On Windows 11 with hide_if_single = true, opening a second tab and closing it via the close-tab shortcut leaves the top strip blank even with this PR applied.

The extra commit switches the comparison to the grid's own scaled_margin (which apply_taffy_layout does not clear), and with it the update_dimensions + render this PR adds starts seeing a correctly-updated scaled_margin. The existing 22
tests in layout/compute_tests.rs still pass.

Lai Jia Yang and others added 2 commits April 23, 2026 20:42
* docs: add documentation to test_poll.rs

* chore: remove test_echo_server.rs (fully commented out, no functional tests)

* chore: remove test_close_on_drop.rs (fully commented out, no functional tests)

* chore: remove test_double_register.rs (fully commented out, no functional tests)

* chore: remove test_broken_pipe.rs (uses deprecated corcovado::deprecated module that no longer exists)
@0x0aa
Copy link
Copy Markdown
Contributor Author

0x0aa commented May 5, 2026

Fixed in main

@0x0aa 0x0aa closed this May 5, 2026
@0x0aa 0x0aa deleted the fix-hiding branch May 5, 2026 21:48
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Hide-if-single leaves margin at the top

3 participants