diff --git a/src/renderer/src/components/tab-bar/BrowserTab.tsx b/src/renderer/src/components/tab-bar/BrowserTab.tsx index 3d960dc40..47cc893a7 100644 --- a/src/renderer/src/components/tab-bar/BrowserTab.tsx +++ b/src/renderer/src/components/tab-bar/BrowserTab.tsx @@ -149,9 +149,14 @@ export default function BrowserTab({ }} > {isActive && } - + {/* Why: the browser tab icon is the only non-terminal, non-editor + surface in the tab strip. Coloring the Globe blue (matching the + in-app browser's identity and the default tab insertion bar) + gives it a distinct, recognizable anchor so users can spot + browser tabs at a glance even when the strip is saturated. We + keep full color on both active and inactive tabs — dimming to + muted-foreground made the icon read as "disabled" in practice. */} + {getBrowserTabLabel(tab)} {tab.loading && !tab.loadError && !isBlankBrowserTab(tab) && ( diff --git a/src/renderer/src/components/tab-bar/SortableTab.tsx b/src/renderer/src/components/tab-bar/SortableTab.tsx index d5ab25826..79c99c223 100644 --- a/src/renderer/src/components/tab-bar/SortableTab.tsx +++ b/src/renderer/src/components/tab-bar/SortableTab.tsx @@ -1,6 +1,6 @@ import { useCallback, useEffect, useRef, useState } from 'react' import { useSortable } from '@dnd-kit/sortable' -import { X, Terminal as TerminalIcon, Minimize2, Columns2, Rows2 } from 'lucide-react' +import { X, Minimize2, Columns2, Rows2 } from 'lucide-react' import { ShellIcon } from './shell-icons' import { DropdownMenu, @@ -81,6 +81,16 @@ export default function SortableTab({ // because the slice returns a fresh object reference on each mark/clear. const hasUnreadActivity = useAppStore((s) => s.unreadTerminalTabs[tab.id] === true) + // Why: on Windows, tabs created before the per-tab shell override landed (or + // created via the default Ctrl+T path without picking a specific shell) + // don't carry a shellOverride. We still want the tab-strip icon to reflect + // the shell actually running, so fall back to the user's configured default + // Windows shell. On mac/linux this resolves to undefined and the ShellIcon + // generic-terminal fallback renders. + const defaultWindowsShell = useAppStore((s) => s.settings?.terminalWindowsShell) + const isWindows = navigator.userAgent.includes('Windows') + const shellForIcon = tab.shellOverride ?? (isWindows ? defaultWindowsShell : undefined) + // Why: intentionally no transform/transition/opacity here. The PR's // design is that tabs stay visually anchored during a drag — only the // blue insertion bar moves. Siblings also don't shift (see @@ -255,25 +265,21 @@ export default function SortableTab({ - ) : tab.shellOverride ? ( - // Why: when the tab was explicitly opened with a specific Windows - // shell (PowerShell / CMD / WSL via the "+" menu), render the - // matching brand-style glyph so the strip shows at a glance which - // shell this tab is running. Falls back to the generic lucide - // TerminalIcon below for mac/linux shells and for Windows tabs - // that were spawned before the per-tab shell override landed - // (shellOverride absent → same neutral glyph as before, no visual - // regression for existing sessions). + ) : ( + // Why: ShellIcon renders a colored brand-style tile for PowerShell, + // CMD, and WSL so Windows users can distinguish shells at a glance. + // On mac/linux (or Windows tabs without a resolved shell) it falls + // back to a matching colored generic-terminal tile — keeping every + // tab's leading glyph in the same visual idiom instead of mixing a + // flat lucide chevron with the brand tiles. Opacity dims the icon + // on inactive tabs to match the existing text treatment without + // desaturating the brand colors beyond recognition. - + - ) : ( - )} {isEditing ? ( + + + + + ) +} + export function ShellIcon({ shell, size = 14 @@ -92,7 +128,5 @@ export function ShellIcon({ if (normalized === 'wsl.exe' || normalized.startsWith('wsl')) { return } - // Fallback: generic terminal glyph for mac/linux shells and anything - // unrecognized. Inherits currentColor so it matches the surrounding tab. - return + return }