Skip to content

fix(desktop): restore hidden tab bar from sidebar row menu - #81638

Open
12312ewqdq wants to merge 1 commit into
NousResearch:mainfrom
12312ewqdq:fix/restore-tab-bar
Open

fix(desktop): restore hidden tab bar from sidebar row menu#81638
12312ewqdq wants to merge 1 commit into
NousResearch:mainfrom
12312ewqdq:fix/restore-tab-bar

Conversation

@12312ewqdq

@12312ewqdq 12312ewqdq commented Aug 8, 2026

Copy link
Copy Markdown

What does this PR do?

The main tab's context menu offers "Hide tab bar" — but once the bar is hidden, that menu disappears with it, and the session tile swallows right-clicks on the chat body (stopPropagation in session-tile.tsx), so the zone menu's "Show header" is unreachable too. The only escape was Ctrl+T (a new tab force-pins the header back on), which is undiscoverable.

This PR adds the symmetrical restore: the sidebar session row menu (kebab ⋮ + right-click — always reachable, independent of the tab bar) shows "Show tab bar" whenever the workspace zone's header is explicitly hidden, and clicking it flips headerHidden back off.

Why the sidebar: it is the only menu surface that does not depend on the tab bar existing. The menu item reads isWorkspaceTabBarHidden() lazily at menu-open time (.get(), no $layoutTree render subscription — that is a documented perf red line, see tree-group.tsx), and only surfaces for an explicit hide (headerHidden === true); a lone pane's auto-hide default is not treated as user state to restore.

Related Issue

No existing issue filed — this is a trapped-state bug found while using the desktop app. Happy to file one if maintainers prefer.

Type of Change

  • 🐛 Bug fix (non-breaking change that fixes an issue)

Changes Made

  • apps/desktop/src/components/pane-shell/tree/store.ts — add isWorkspaceTabBarHidden() (read-only, .get()-based) and showWorkspaceTabBar() (symmetrical restore via setTreeGroupHeaderHidden(false)).
  • apps/desktop/src/app/chat/sidebar/session-actions-menu.tsx — render "Show tab bar" item (icon eye) in the session menu when the workspace header is explicitly hidden; calls showWorkspaceTabBar().
  • apps/desktop/src/i18n/{types,en,zh,ar}.ts — add showTabBar string (en/zh/ar translated; ja/zh-hant fall back to English via defineLocale).
  • apps/desktop/src/app/chat/sidebar/session-actions-menu.test.tsx — 2 new tests: item appears only while hidden + click restores; absent while visible.

How to Test

  1. Open a session. Right-click the main tab → "Hide tab bar". The tab strip disappears.
  2. In the left sidebar, open any session row's ⋮ menu (or right-click the row).
  3. "Show tab bar" is present. Click it → the tab strip returns.
  4. With the bar visible, reopen the row menu → "Show tab bar" is absent.

Checklist

Code

  • I've read the Contributing Guide
  • My commit messages follow Conventional Commits (fix(scope):, feat(scope):, etc.)
  • I searched for existing PRs to make sure this isn't a duplicate
  • My PR contains only changes related to this fix/feature (no unrelated commits)
  • I've run pytest tests/ -q and all tests pass (n/a — renderer-only change)
  • I've added tests for my changes
  • I've tested on my platform: Windows 11

Documentation & Housekeeping

  • I've updated relevant documentation — or N/A
  • I've updated cli-config.yaml.example if I added/changed config keys — or N/A
  • I've updated CONTRIBUTING.md or AGENTS.md if I changed architecture or workflows — or N/A
  • I've considered cross-platform impact (Windows, macOS) per the compatibility guide — or N/A
  • I've updated tool descriptions/schemas if I changed tool behavior — or N/A

Verification (local, Windows 11)

  • npm run test:ui -- src/app/chat/sidebar/session-actions-menu.test.tsx → 3/3 pass
  • npx tsc -p . --noEmit → no errors
  • npx eslint on changed files → no issues
  • npx prettier --check on changed files → all formatted
  • Rebased onto latest origin/main (no conflicts; upstream did not touch these files)

Known limitations

  • ja/zh-hant locales lack the new key and fall back to English via defineLocale merge (consistent with how hideTabBar is handled there today).
  • The item renders on any session menu while the bar is hidden (surface-agnostic); calling showWorkspaceTabBar() when already visible is a guarded no-op.

@alt-glitch alt-glitch added type/bug Something isn't working comp/desktop Electron desktop app (apps/desktop/*) area/sessions Session lifecycle, resume, persistence, history P3 Low — cosmetic, nice to have sweeper:risk-session-state Sweeper risk: may lose/corrupt/mis-associate session or context state labels Aug 8, 2026
@alt-glitch

Copy link
Copy Markdown
Collaborator

This was generated by AI during triage.

Related: #79520 also addresses #79518 by force-showing the session tab strip during reveal/adoption. This PR instead adds a sidebar recovery action; maintainers should choose the preferred UX model.

@matebenyovszky

Copy link
Copy Markdown

Ran into the same trap from a different direction, and your diagnosis matches mine exactly — the hide takes the strip, and the strip is the only host of the zone menu.

One gap worth flagging: isWorkspaceTabBarHidden() is workspace-specific, and the sidebar session row is the surface this hangs off. A preview or Browser zone has neither. I hit it with two file previews docked in their own zones, both double-tap-hidden — no tab, no ✕, no menu, and no sidebar row to reach for. ⌘W works (closeFocusedSessionTab keys on isMainStripPane, so it covers preview tiles), but ⌃Tab doesn't (it needs ≥2 tabs in the zone), and neither is discoverable from a zone showing no chrome at all.

I've opened #84458 for that case: a top-edge reveal strip on the zone itself, so it doesn't depend on any other surface existing. It's the gesture model.ts has documented since the flag was added ("double-click the zone's top edge to bring it back") but which was never implemented.

I think they're complementary rather than competing — yours gives the chat case a discoverable menu item, mine gives every other zone class an affordance. But if maintainers would rather have one mechanism, mine is zone-agnostic and would cover the workspace too; happy to adapt or fold it in whichever way is preferred.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area/sessions Session lifecycle, resume, persistence, history comp/desktop Electron desktop app (apps/desktop/*) P3 Low — cosmetic, nice to have sweeper:risk-session-state Sweeper risk: may lose/corrupt/mis-associate session or context state type/bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants