refactor: streamline ExtensionStoreView layout and enhance UnreadCommentsBadge styling

- Adjusted layout in ExtensionStoreView for improved structure and readability.
- Updated UnreadCommentsBadge component to refine styling and enhance visual clarity.
- Consolidated tooltip and button elements for better user interaction.
This commit is contained in:
iliya 2026-03-11 22:17:39 +02:00
parent 5abd8a0ceb
commit e440042c2b
3 changed files with 190 additions and 208 deletions

View file

@ -103,129 +103,131 @@ export const ExtensionStoreView = (): React.JSX.Element => {
return ( return (
<div className="flex flex-1 flex-col overflow-hidden"> <div className="flex flex-1 flex-col overflow-hidden">
{/* Header */} <div className="flex-1 overflow-y-auto">
<div className="flex items-center justify-between border-b border-border px-6 py-4"> {/* Header */}
<div className="flex items-center gap-3"> <div className="flex items-center justify-between border-b border-border px-6 py-4">
<Puzzle className="size-5 text-text-muted" /> <div className="flex items-center gap-3">
<h1 className="text-lg font-semibold text-text">Extensions</h1> <Puzzle className="size-5 text-text-muted" />
<h1 className="text-lg font-semibold text-text">Extensions</h1>
</div>
<TooltipProvider>
<Tooltip>
<TooltipTrigger asChild>
<Button variant="ghost" size="icon" onClick={handleRefresh} disabled={isRefreshing}>
<RefreshCw className={`size-4 ${isRefreshing ? 'animate-spin' : ''}`} />
</Button>
</TooltipTrigger>
<TooltipContent>Refresh catalog</TooltipContent>
</Tooltip>
</TooltipProvider>
</div> </div>
<TooltipProvider>
<Tooltip>
<TooltipTrigger asChild>
<Button variant="ghost" size="icon" onClick={handleRefresh} disabled={isRefreshing}>
<RefreshCw className={`size-4 ${isRefreshing ? 'animate-spin' : ''}`} />
</Button>
</TooltipTrigger>
<TooltipContent>Refresh catalog</TooltipContent>
</Tooltip>
</TooltipProvider>
</div>
{/* Sub-tabs */} {/* Sub-tabs */}
<div className="flex-1 overflow-y-auto px-6 py-4"> <div className="px-6 py-4">
{/* CLI not installed warning */} {/* CLI not installed warning */}
{!cliInstalled && ( {!cliInstalled && (
<div className="mb-4 flex items-center gap-2 rounded-md border border-amber-500/30 bg-amber-500/5 px-4 py-3 text-sm text-amber-400"> <div className="mb-4 flex items-center gap-2 rounded-md border border-amber-500/30 bg-amber-500/5 px-4 py-3 text-sm text-amber-400">
<AlertTriangle className="size-4 shrink-0" /> <AlertTriangle className="size-4 shrink-0" />
Claude CLI is required to install or uninstall extensions. Install it from Settings. Claude CLI is required to install or uninstall extensions. Install it from Settings.
</div> </div>
)} )}
{/* Active sessions warning */} {/* Active sessions warning */}
{hasOngoingSessions && ( {hasOngoingSessions && (
<div className="mb-4 flex items-center gap-2 rounded-md border border-blue-500/30 bg-blue-500/5 px-4 py-3 text-sm text-blue-400"> <div className="mb-4 flex items-center gap-2 rounded-md border border-blue-500/30 bg-blue-500/5 px-4 py-3 text-sm text-blue-400">
<Info className="size-4 shrink-0" /> <Info className="size-4 shrink-0" />
Running sessions won&apos;t pick up extension changes until restarted. Running sessions won&apos;t pick up extension changes until restarted.
</div> </div>
)} )}
<Tabs <Tabs
value={tabState.activeSubTab} value={tabState.activeSubTab}
onValueChange={(v) => onValueChange={(v) =>
tabState.setActiveSubTab(v as 'plugins' | 'mcp-servers' | 'skills' | 'api-keys') tabState.setActiveSubTab(v as 'plugins' | 'mcp-servers' | 'skills' | 'api-keys')
} }
> >
<div className="mb-4 flex items-center justify-between"> <div className="mb-4 flex items-center justify-between">
<TabsList> <TabsList>
<TabsTrigger value="plugins" className="gap-1.5"> <TabsTrigger value="plugins" className="gap-1.5">
<Puzzle className="size-3.5" /> <Puzzle className="size-3.5" />
Plugins Plugins
</TabsTrigger> </TabsTrigger>
<TabsTrigger value="mcp-servers" className="gap-1.5"> <TabsTrigger value="mcp-servers" className="gap-1.5">
<Server className="size-3.5" /> <Server className="size-3.5" />
MCP Servers MCP Servers
</TabsTrigger> </TabsTrigger>
<TabsTrigger value="skills" className="gap-1.5"> <TabsTrigger value="skills" className="gap-1.5">
<BookOpen className="size-3.5" /> <BookOpen className="size-3.5" />
Skills Skills
</TabsTrigger> </TabsTrigger>
<TabsTrigger value="api-keys" className="gap-1.5"> <TabsTrigger value="api-keys" className="gap-1.5">
<Key className="size-3.5" /> <Key className="size-3.5" />
API Keys API Keys
</TabsTrigger> </TabsTrigger>
</TabsList> </TabsList>
{tabState.activeSubTab === 'mcp-servers' && ( {tabState.activeSubTab === 'mcp-servers' && (
<Button <Button
variant="outline" variant="outline"
size="sm" size="sm"
onClick={() => setCustomMcpDialogOpen(true)} onClick={() => setCustomMcpDialogOpen(true)}
className="whitespace-nowrap" className="whitespace-nowrap"
> >
<Plus className="mr-1 size-3.5" /> <Plus className="mr-1 size-3.5" />
Add Custom Add Custom
</Button> </Button>
)} )}
</div> </div>
<TabsContent value="plugins"> <TabsContent value="plugins">
<PluginsPanel <PluginsPanel
pluginFilters={tabState.pluginFilters} pluginFilters={tabState.pluginFilters}
pluginSort={tabState.pluginSort} pluginSort={tabState.pluginSort}
selectedPluginId={tabState.selectedPluginId} selectedPluginId={tabState.selectedPluginId}
updatePluginSearch={tabState.updatePluginSearch} updatePluginSearch={tabState.updatePluginSearch}
toggleCategory={tabState.toggleCategory} toggleCategory={tabState.toggleCategory}
toggleCapability={tabState.toggleCapability} toggleCapability={tabState.toggleCapability}
toggleInstalledOnly={tabState.toggleInstalledOnly} toggleInstalledOnly={tabState.toggleInstalledOnly}
setSelectedPluginId={tabState.setSelectedPluginId} setSelectedPluginId={tabState.setSelectedPluginId}
clearFilters={tabState.clearFilters} clearFilters={tabState.clearFilters}
hasActiveFilters={tabState.hasActiveFilters} hasActiveFilters={tabState.hasActiveFilters}
setPluginSort={tabState.setPluginSort} setPluginSort={tabState.setPluginSort}
/> />
</TabsContent> </TabsContent>
<TabsContent value="mcp-servers"> <TabsContent value="mcp-servers">
<McpServersPanel <McpServersPanel
mcpSearchQuery={tabState.mcpSearchQuery} mcpSearchQuery={tabState.mcpSearchQuery}
mcpSearch={tabState.mcpSearch} mcpSearch={tabState.mcpSearch}
mcpSearchResults={tabState.mcpSearchResults} mcpSearchResults={tabState.mcpSearchResults}
mcpSearchLoading={tabState.mcpSearchLoading} mcpSearchLoading={tabState.mcpSearchLoading}
mcpSearchWarnings={tabState.mcpSearchWarnings} mcpSearchWarnings={tabState.mcpSearchWarnings}
selectedMcpServerId={tabState.selectedMcpServerId} selectedMcpServerId={tabState.selectedMcpServerId}
setSelectedMcpServerId={tabState.setSelectedMcpServerId} setSelectedMcpServerId={tabState.setSelectedMcpServerId}
/> />
</TabsContent> </TabsContent>
<TabsContent value="api-keys"> <TabsContent value="api-keys">
<ApiKeysPanel /> <ApiKeysPanel />
</TabsContent> </TabsContent>
<TabsContent value="skills"> <TabsContent value="skills">
<SkillsPanel <SkillsPanel
projectPath={projectPath} projectPath={projectPath}
projectLabel={projectLabel} projectLabel={projectLabel}
skillsSearchQuery={tabState.skillsSearchQuery} skillsSearchQuery={tabState.skillsSearchQuery}
setSkillsSearchQuery={tabState.setSkillsSearchQuery} setSkillsSearchQuery={tabState.setSkillsSearchQuery}
skillsSort={tabState.skillsSort} skillsSort={tabState.skillsSort}
setSkillsSort={tabState.setSkillsSort} setSkillsSort={tabState.setSkillsSort}
selectedSkillId={tabState.selectedSkillId} selectedSkillId={tabState.selectedSkillId}
setSelectedSkillId={tabState.setSelectedSkillId} setSelectedSkillId={tabState.setSelectedSkillId}
/> />
</TabsContent> </TabsContent>
</Tabs> </Tabs>
{/* Custom MCP server dialog (lifted to store view level) */} {/* Custom MCP server dialog (lifted to store view level) */}
<CustomMcpServerDialog <CustomMcpServerDialog
open={customMcpDialogOpen} open={customMcpDialogOpen}
onClose={() => setCustomMcpDialogOpen(false)} onClose={() => setCustomMcpDialogOpen(false)}
/> />
</div>
</div> </div>
</div> </div>
); );

View file

@ -15,13 +15,13 @@ export const UnreadCommentsBadge = ({
return ( return (
<Tooltip> <Tooltip>
<TooltipTrigger asChild> <TooltipTrigger asChild>
<span className="relative inline-flex size-8 shrink-0 items-center justify-center rounded-full border border-[var(--color-border)] bg-[var(--color-surface)] text-[var(--color-text-muted)] shadow-sm transition-colors hover:bg-[var(--color-surface-raised)]"> <span className="relative inline-flex size-6 shrink-0 items-center justify-center text-[var(--color-text-muted)] transition-colors hover:text-[var(--color-text)]">
<MessageSquare size={14} /> <MessageSquare size={13} />
<span className="absolute -bottom-0.5 -right-0.5 flex h-3.5 min-w-[14px] items-center justify-center rounded-full bg-slate-200 px-1 text-[7px] font-bold leading-none text-slate-700 shadow-sm dark:bg-slate-200 dark:text-slate-900"> <span className="absolute -bottom-0.5 -right-0.5 flex h-3 min-w-3 items-center justify-center rounded-full bg-slate-200 px-0.5 text-[7px] font-bold leading-none text-slate-700 dark:bg-slate-200 dark:text-slate-900">
{totalCount} {totalCount}
</span> </span>
{unreadCount > 0 ? ( {unreadCount > 0 ? (
<span className="absolute -right-1.5 -top-1.5 flex h-5 min-w-[20px] items-center justify-center rounded-full bg-blue-500 px-1.5 text-[9px] font-bold leading-none text-white shadow-sm ring-2 ring-[var(--color-surface-raised)]"> <span className="absolute -right-1 -top-1 flex h-4 min-w-4 items-center justify-center rounded-full bg-blue-500 px-1 text-[8px] font-bold leading-none text-white shadow-sm">
{unreadCount} {unreadCount}
</span> </span>
) : null} ) : null}

View file

@ -3,64 +3,64 @@
@tailwind utilities; @tailwind utilities;
/* Theme CSS Custom Properties */ /* Theme CSS Custom Properties */
:root { :root {
/* Dark theme (default) - Midnight Slate palette (cool indigo undertone) */ /* Dark theme (default) - Midnight Slate palette (cool indigo undertone) */
--color-surface: #12131a; /* Main background — deep midnight */ --color-surface: #12131a;
--color-surface-raised: #1c1d26; /* Active/Selected items — cool slate */ /* Main background — deep midnight */
--color-surface-overlay: #1c1d26; /* Overlay surfaces */ --color-surface-raised: #1c1d26;
--color-surface-sidebar: #0c0d13; /* Sidebar — deepest navy-black */ /* Active/Selected items — cool slate */
--color-border: rgba(148, 163, 184, 0.07); /* Borders — slate-tinted */ --color-surface-overlay: #1c1d26;
--color-border-subtle: rgba(148, 163, 184, 0.05); /* Subtle borders */ /* Overlay surfaces */
--color-border-emphasis: rgba(148, 163, 184, 0.12); /* Emphasis borders */ --color-surface-sidebar: #0c0d13;
/* Sidebar — deepest navy-black */
--color-border: rgba(148, 163, 184, 0.07);
/* Borders — slate-tinted */
--color-border-subtle: rgba(148, 163, 184, 0.05);
/* Subtle borders */
--color-border-emphasis: rgba(148, 163, 184, 0.12);
/* Emphasis borders */
--color-text: #f1f5f9; --color-text: #f1f5f9;
--color-text-secondary: #94a3b8; --color-text-secondary: #94a3b8;
--color-text-muted: #64748b; --color-text-muted: #64748b;
--color-accent: #818cf8; /* Accent — indigo-400, visible on dark surfaces */ --color-accent: #818cf8;
/* Accent — indigo-400, visible on dark surfaces */
/* Scrollbar colors */ /* Scrollbar colors */
--scrollbar-thumb: rgba(148, 163, 184, 0.15); --scrollbar-thumb: rgba(148, 163, 184, 0.15);
--scrollbar-thumb-hover: rgba(148, 163, 184, 0.25); --scrollbar-thumb-hover: rgba(148, 163, 184, 0.25);
--scrollbar-thumb-active: rgba(148, 163, 184, 0.35); --scrollbar-thumb-active: rgba(148, 163, 184, 0.35);
/* Search highlights */ /* Search highlights */
--highlight-bg: rgba(202, 138, 4, 0.7); --highlight-bg: rgba(202, 138, 4, 0.7);
--highlight-bg-inactive: rgba(113, 63, 18, 0.5); --highlight-bg-inactive: rgba(113, 63, 18, 0.5);
--highlight-text: #fef9c3; --highlight-text: #fef9c3;
--highlight-text-inactive: #fef08a; --highlight-text-inactive: #fef08a;
--highlight-ring: #facc15; --highlight-ring: #facc15;
/* User chat bubble — orange (Claude Code) */ /* User chat bubble — orange (Claude Code) */
--chat-user-bg: #1c1d26; --chat-user-bg: #1c1d26;
--chat-user-text: #94a3b8; --chat-user-text: #94a3b8;
--chat-user-border: rgba(249, 115, 22, 0.2); --chat-user-border: rgba(249, 115, 22, 0.2);
--chat-user-shadow: 0 1px 0 0 rgba(249, 115, 22, 0.06); --chat-user-shadow: 0 1px 0 0 rgba(249, 115, 22, 0.06);
/* User bubble inline tags */ /* User bubble inline tags */
--chat-user-tag-bg: rgba(249, 115, 22, 0.12); --chat-user-tag-bg: rgba(249, 115, 22, 0.12);
--chat-user-tag-text: #fb923c; --chat-user-tag-text: #fb923c;
--chat-user-tag-border: rgba(249, 115, 22, 0.2); --chat-user-tag-border: rgba(249, 115, 22, 0.2);
/* Tool items */ /* Tool items */
--tool-item-name: #e2e8f0; --tool-item-name: #e2e8f0;
--tool-item-summary: #94a3b8; --tool-item-summary: #94a3b8;
--tool-item-muted: #64748b; --tool-item-muted: #64748b;
--tool-item-hover-bg: rgba(28, 29, 38, 0.6); --tool-item-hover-bg: rgba(28, 29, 38, 0.6);
/* System chat bubble */ /* System chat bubble */
--chat-system-bg: rgba(28, 29, 38, 0.6); --chat-system-bg: rgba(28, 29, 38, 0.6);
--chat-system-text: #cbd5e1; --chat-system-text: #cbd5e1;
/* AI message styling */ /* AI message styling */
--chat-ai-border: rgba(148, 163, 184, 0.06); --chat-ai-border: rgba(148, 163, 184, 0.06);
--chat-ai-icon: #64748b; --chat-ai-icon: #64748b;
/* Code blocks — midnight slate */ /* Code blocks — midnight slate */
--code-bg: #171822; --code-bg: #171822;
--code-header-bg: #171822; --code-header-bg: #171822;
--code-border: rgba(148, 163, 184, 0.1); --code-border: rgba(148, 163, 184, 0.1);
--code-line-number: #475569; --code-line-number: #475569;
--code-filename: #818cf8; --code-filename: #818cf8;
/* Syntax highlighting — cooler accents */ /* Syntax highlighting — cooler accents */
--syntax-string: #4ade80; --syntax-string: #4ade80;
--syntax-comment: #64748b; --syntax-comment: #64748b;
@ -69,11 +69,9 @@
--syntax-type: #fbbf24; --syntax-type: #fbbf24;
--syntax-operator: #94a3b8; --syntax-operator: #94a3b8;
--syntax-function: #818cf8; --syntax-function: #818cf8;
/* Inline code */ /* Inline code */
--inline-code-bg: rgba(148, 163, 184, 0.08); --inline-code-bg: rgba(148, 163, 184, 0.08);
--inline-code-text: #e2e8f0; --inline-code-text: #e2e8f0;
/* Diff viewer */ /* Diff viewer */
--diff-added-bg: rgba(34, 197, 94, 0.15); --diff-added-bg: rgba(34, 197, 94, 0.15);
--diff-added-text: #4ade80; --diff-added-text: #4ade80;
@ -101,7 +99,6 @@
--diff-expand-active-bg: rgba(255, 255, 255, 0.1); --diff-expand-active-bg: rgba(255, 255, 255, 0.1);
--diff-expand-all-hover-bg: rgba(255, 255, 255, 0.04); --diff-expand-all-hover-bg: rgba(255, 255, 255, 0.04);
--diff-expand-all-active-bg: rgba(255, 255, 255, 0.08); --diff-expand-all-active-bg: rgba(255, 255, 255, 0.08);
/* Markdown prose */ /* Markdown prose */
--prose-heading: #f8fafc; --prose-heading: #f8fafc;
--prose-body: #f1f5f9; --prose-body: #f1f5f9;
@ -114,7 +111,6 @@
--prose-blockquote-border: rgba(148, 163, 184, 0.1); --prose-blockquote-border: rgba(148, 163, 184, 0.1);
--prose-table-border: rgba(148, 163, 184, 0.06); --prose-table-border: rgba(148, 163, 184, 0.06);
--prose-table-header-bg: #1c1d26; --prose-table-header-bg: #1c1d26;
/* Thinking blocks — slightly more vibrant purple */ /* Thinking blocks — slightly more vibrant purple */
--thinking-bg: rgba(88, 28, 135, 0.22); --thinking-bg: rgba(88, 28, 135, 0.22);
--thinking-border: rgba(107, 33, 168, 0.4); --thinking-border: rgba(107, 33, 168, 0.4);
@ -122,14 +118,12 @@
--thinking-text-muted: #e9d5ff; --thinking-text-muted: #e9d5ff;
--thinking-content-border: rgba(107, 33, 168, 0.3); --thinking-content-border: rgba(107, 33, 168, 0.3);
--thinking-content-text: #f3e8ff; --thinking-content-text: #f3e8ff;
/* Tool call blocks */ /* Tool call blocks */
--tool-call-bg: rgba(120, 53, 15, 0.2); --tool-call-bg: rgba(120, 53, 15, 0.2);
--tool-call-border: rgba(146, 64, 14, 0.4); --tool-call-border: rgba(146, 64, 14, 0.4);
--tool-call-text: #fcd34d; --tool-call-text: #fcd34d;
--tool-call-code-bg: rgba(69, 26, 3, 0.5); --tool-call-code-bg: rgba(69, 26, 3, 0.5);
--tool-call-content-border: rgba(146, 64, 14, 0.3); --tool-call-content-border: rgba(146, 64, 14, 0.3);
/* Tool result blocks */ /* Tool result blocks */
--tool-result-success-bg: rgba(20, 83, 45, 0.2); --tool-result-success-bg: rgba(20, 83, 45, 0.2);
--tool-result-success-border: rgba(22, 101, 52, 0.4); --tool-result-success-border: rgba(22, 101, 52, 0.4);
@ -137,13 +131,11 @@
--tool-result-error-bg: rgba(127, 29, 29, 0.2); --tool-result-error-bg: rgba(127, 29, 29, 0.2);
--tool-result-error-border: rgba(153, 27, 27, 0.4); --tool-result-error-border: rgba(153, 27, 27, 0.4);
--tool-result-error-text: #fca5a5; --tool-result-error-text: #fca5a5;
/* Output blocks */ /* Output blocks */
--output-bg: rgba(23, 24, 34, 0.5); --output-bg: rgba(23, 24, 34, 0.5);
--output-border: #2d3044; --output-border: #2d3044;
--output-text: #e2e8f0; --output-text: #e2e8f0;
--output-content-border: rgba(45, 48, 68, 0.5); --output-content-border: rgba(45, 48, 68, 0.5);
/* Badges */ /* Badges */
--badge-error-bg: #dc2626; --badge-error-bg: #dc2626;
--badge-error-text: #ffffff; --badge-error-text: #ffffff;
@ -155,43 +147,35 @@
--badge-info-text: #ffffff; --badge-info-text: #ffffff;
--badge-neutral-bg: #2a2c38; --badge-neutral-bg: #2a2c38;
--badge-neutral-text: #e2e8f0; --badge-neutral-text: #e2e8f0;
/* Language/tag badges */ /* Language/tag badges */
--tag-bg: #1c1d26; --tag-bg: #1c1d26;
--tag-text: #94a3b8; --tag-text: #94a3b8;
--tag-border: rgba(148, 163, 184, 0.06); --tag-border: rgba(148, 163, 184, 0.06);
/* Highlighted text (skills, paths) */ /* Highlighted text (skills, paths) */
--skill-highlight-bg: rgba(148, 163, 184, 0.08); --skill-highlight-bg: rgba(148, 163, 184, 0.08);
--skill-highlight-text: #e2e8f0; --skill-highlight-text: #e2e8f0;
--path-highlight-bg: rgba(148, 163, 184, 0.08); --path-highlight-bg: rgba(148, 163, 184, 0.08);
--path-highlight-text: #e2e8f0; --path-highlight-text: #e2e8f0;
/* Interruption badge */ /* Interruption badge */
--interruption-bg: rgba(127, 29, 29, 0.3); --interruption-bg: rgba(127, 29, 29, 0.3);
--interruption-border: #b91c1c; --interruption-border: #b91c1c;
--interruption-text: #fca5a5; --interruption-text: #fca5a5;
/* Warning/Amber colors (for interruption banner) */ /* Warning/Amber colors (for interruption banner) */
--warning-bg: rgba(245, 158, 11, 0.15); --warning-bg: rgba(245, 158, 11, 0.15);
--warning-border: rgba(245, 158, 11, 0.4); --warning-border: rgba(245, 158, 11, 0.4);
--warning-text: #fbbf24; --warning-text: #fbbf24;
/* Plan exit/Green colors (for ExitPlanMode) */ /* Plan exit/Green colors (for ExitPlanMode) */
--plan-exit-bg: rgba(34, 197, 94, 0.05); --plan-exit-bg: rgba(34, 197, 94, 0.05);
--plan-exit-header-bg: rgba(34, 197, 94, 0.1); --plan-exit-header-bg: rgba(34, 197, 94, 0.1);
--plan-exit-border: rgba(34, 197, 94, 0.25); --plan-exit-border: rgba(34, 197, 94, 0.25);
--plan-exit-text: #4ade80; --plan-exit-text: #4ade80;
/* Error highlight (pulsing) */ /* Error highlight (pulsing) */
--error-highlight-ring: #ef4444; --error-highlight-ring: #ef4444;
--error-highlight-bg: rgba(239, 68, 68, 0.2); --error-highlight-bg: rgba(239, 68, 68, 0.2);
/* Keyboard hints */ /* Keyboard hints */
--kbd-bg: #1c1d26; --kbd-bg: #1c1d26;
--kbd-border: rgba(148, 163, 184, 0.1); --kbd-border: rgba(148, 163, 184, 0.1);
--kbd-text: #cbd5e1; --kbd-text: #cbd5e1;
/* Subagent/Card styling */ /* Subagent/Card styling */
--card-bg: #0f1018; --card-bg: #0f1018;
--card-bg-zebra: #14151f; --card-bg-zebra: #14151f;
@ -202,39 +186,32 @@
--card-text-light: #cbd5e1; --card-text-light: #cbd5e1;
--card-text-lighter: #e2e8f0; --card-text-lighter: #e2e8f0;
--card-separator: #2a2c38; --card-separator: #2a2c38;
/* System activity messages */ /* System activity messages */
--system-activity-bg: rgba(59, 130, 246, 0.06); --system-activity-bg: rgba(59, 130, 246, 0.06);
--system-activity-border: rgba(59, 130, 246, 0.12); --system-activity-border: rgba(59, 130, 246, 0.12);
--system-activity-accent: rgba(96, 165, 250, 0.5); --system-activity-accent: rgba(96, 165, 250, 0.5);
/* Cross-team communication */ /* Cross-team communication */
--cross-team-bg: rgba(168, 85, 247, 0.06); --cross-team-bg: rgba(168, 85, 247, 0.06);
--cross-team-border: rgba(168, 85, 247, 0.12); --cross-team-border: rgba(168, 85, 247, 0.12);
--cross-team-accent: rgba(192, 132, 252, 0.5); --cross-team-accent: rgba(192, 132, 252, 0.5);
/* Info style — banners, status indicators */ /* Info style — banners, status indicators */
--info-bg: rgba(59, 130, 246, 0.08); --info-bg: rgba(59, 130, 246, 0.08);
--info-border: rgba(59, 130, 246, 0.25); --info-border: rgba(59, 130, 246, 0.25);
--info-text: #60a5fa; --info-text: #60a5fa;
/* Assessment severity colors (badges, health indicators) */ /* Assessment severity colors (badges, health indicators) */
--assess-good: #4ade80; --assess-good: #4ade80;
--assess-warning: #fbbf24; --assess-warning: #fbbf24;
--assess-danger: #f87171; --assess-danger: #f87171;
--assess-neutral: #a1a1aa; --assess-neutral: #a1a1aa;
/* Sticky Context button — indigo glass */ /* Sticky Context button — indigo glass */
--context-btn-bg: rgba(148, 163, 184, 0.08); --context-btn-bg: rgba(148, 163, 184, 0.08);
--context-btn-bg-hover: rgba(148, 163, 184, 0.14); --context-btn-bg-hover: rgba(148, 163, 184, 0.14);
--context-btn-active-bg: rgba(99, 102, 241, 0.5); --context-btn-active-bg: rgba(99, 102, 241, 0.5);
--context-btn-active-text: #e0e7ff; --context-btn-active-text: #e0e7ff;
/* Skeleton — cool midnight */ /* Skeleton — cool midnight */
--skeleton-base: #1a1c28; --skeleton-base: #1a1c28;
--skeleton-base-light: #23252f; --skeleton-base-light: #23252f;
--skeleton-base-dim: rgba(26, 28, 40, 0.6); --skeleton-base-dim: rgba(26, 28, 40, 0.6);
/* Provisioning step badges */ /* Provisioning step badges */
--step-done-bg: rgba(16, 185, 129, 0.1); --step-done-bg: rgba(16, 185, 129, 0.1);
--step-done-border: rgba(52, 211, 153, 0.6); --step-done-border: rgba(52, 211, 153, 0.6);
@ -248,13 +225,11 @@
--step-warning-text: #fde68a; --step-warning-text: #fde68a;
--step-warning-border: rgba(245, 158, 11, 0.4); --step-warning-border: rgba(245, 158, 11, 0.4);
--step-warning-bg: rgba(245, 158, 11, 0.1); --step-warning-bg: rgba(245, 158, 11, 0.1);
/* Collapsible section backgrounds (sidebar) */ /* Collapsible section backgrounds (sidebar) */
--color-section-bg: rgba(255, 255, 255, 0.04); --color-section-bg: rgba(255, 255, 255, 0.04);
--color-section-bg-open: rgba(255, 255, 255, 0.07); --color-section-bg-open: rgba(255, 255, 255, 0.07);
--color-section-hover: rgba(255, 255, 255, 0.08); --color-section-hover: rgba(255, 255, 255, 0.08);
--color-section-hover-open: rgba(255, 255, 255, 0.1); --color-section-hover-open: rgba(255, 255, 255, 0.1);
/* Compact boundary — phase badge */ /* Compact boundary — phase badge */
--compact-phase-bg: rgba(99, 102, 241, 0.15); --compact-phase-bg: rgba(99, 102, 241, 0.15);
--compact-phase-text: #818cf8; --compact-phase-text: #818cf8;
@ -307,7 +282,6 @@
from { from {
opacity: 0; opacity: 0;
} }
to { to {
opacity: 1; opacity: 1;
} }
@ -380,74 +354,77 @@
} }
/* File icon glow — halo so dark icons stay visible on dark backgrounds */ /* File icon glow — halo so dark icons stay visible on dark backgrounds */
.file-icon-glow { .file-icon-glow {
filter: drop-shadow(0 0 6px rgba(255, 255, 255, 0.45)); filter: drop-shadow(0 0 6px rgba(255, 255, 255, 0.45));
} }
/* Light theme overrides - Warm neutral palette for eye comfort */ /* Light theme overrides - Warm neutral palette for eye comfort */
:root.light {
--color-surface: #f9f9f7; /* Warm off-white (not pure white) */
--color-surface-raised: #e8e6e3; /* Warm raised surface — stronger contrast for visible hover */
--color-surface-overlay: #e8e7e4; /* Warm overlay */
--color-surface-sidebar: #f1f0ee; /* Warm sidebar, distinct from main */
--color-border: #d5d3cf; /* Warm neutral border */
--color-border-subtle: #e3e1dd; /* Warm subtle border */
--color-border-emphasis: #a8a5a0; /* Warm emphasis border */
--color-text: #1c1b19; /* Warm near-black text */
--color-text-secondary: #4d4b46; /* Warm secondary text */
--color-text-muted: #6d6b65; /* Warm muted text */
--color-accent: #4f46e5; /* Accent — indigo-600, visible on light surfaces */
:root.light {
--color-surface: #f9f9f7;
/* Warm off-white (not pure white) */
--color-surface-raised: #e8e6e3;
/* Warm raised surface — stronger contrast for visible hover */
--color-surface-overlay: #e8e7e4;
/* Warm overlay */
--color-surface-sidebar: #f1f0ee;
/* Warm sidebar, distinct from main */
--color-border: #d5d3cf;
/* Warm neutral border */
--color-border-subtle: #e3e1dd;
/* Warm subtle border */
--color-border-emphasis: #a8a5a0;
/* Warm emphasis border */
--color-text: #1c1b19;
/* Warm near-black text */
--color-text-secondary: #4d4b46;
/* Warm secondary text */
--color-text-muted: #6d6b65;
/* Warm muted text */
--color-accent: #4f46e5;
/* Accent — indigo-600, visible on light surfaces */
/* Assessment severity colors - darker for light backgrounds */ /* Assessment severity colors - darker for light backgrounds */
--assess-good: #16a34a; --assess-good: #16a34a;
--assess-warning: #d97706; --assess-warning: #d97706;
--assess-danger: #dc2626; --assess-danger: #dc2626;
--assess-neutral: #57534e; --assess-neutral: #57534e;
/* Scrollbar colors for light mode */ /* Scrollbar colors for light mode */
--scrollbar-thumb: rgba(0, 0, 0, 0.15); --scrollbar-thumb: rgba(0, 0, 0, 0.15);
--scrollbar-thumb-hover: rgba(0, 0, 0, 0.28); --scrollbar-thumb-hover: rgba(0, 0, 0, 0.28);
--scrollbar-thumb-active: rgba(0, 0, 0, 0.4); --scrollbar-thumb-active: rgba(0, 0, 0, 0.4);
/* Search highlights - High saturation yellow */ /* Search highlights - High saturation yellow */
--highlight-bg: #facc15; --highlight-bg: #facc15;
--highlight-bg-inactive: #fef08a; --highlight-bg-inactive: #fef08a;
--highlight-text: #1c1917; --highlight-text: #1c1917;
--highlight-text-inactive: #422006; --highlight-text-inactive: #422006;
--highlight-ring: #ca8a04; --highlight-ring: #ca8a04;
/* User chat bubble - orange (Claude Code) */ /* User chat bubble - orange (Claude Code) */
--chat-user-bg: #eae9e6; --chat-user-bg: #eae9e6;
--chat-user-text: #5a5955; --chat-user-text: #5a5955;
--chat-user-border: rgba(249, 115, 22, 0.35); --chat-user-border: rgba(249, 115, 22, 0.35);
--chat-user-shadow: 0 1px 2px 0 rgba(249, 115, 22, 0.08); --chat-user-shadow: 0 1px 2px 0 rgba(249, 115, 22, 0.08);
/* User bubble inline tags */ /* User bubble inline tags */
--chat-user-tag-bg: rgba(249, 115, 22, 0.12); --chat-user-tag-bg: rgba(249, 115, 22, 0.12);
--chat-user-tag-text: #c2410c; --chat-user-tag-text: #c2410c;
--chat-user-tag-border: rgba(249, 115, 22, 0.25); --chat-user-tag-border: rgba(249, 115, 22, 0.25);
/* Tool items - Warm high contrast */ /* Tool items - Warm high contrast */
--tool-item-name: #1c1b19; --tool-item-name: #1c1b19;
--tool-item-summary: #4d4b46; --tool-item-summary: #4d4b46;
--tool-item-muted: #6d6b65; --tool-item-muted: #6d6b65;
--tool-item-hover-bg: #eae9e6; --tool-item-hover-bg: #eae9e6;
/* System chat bubble */ /* System chat bubble */
--chat-system-bg: #eae9e6; --chat-system-bg: #eae9e6;
--chat-system-text: #3a3935; --chat-system-text: #3a3935;
/* AI message styling */ /* AI message styling */
--chat-ai-border: #d5d3cf; --chat-ai-border: #d5d3cf;
--chat-ai-icon: #6d6b65; --chat-ai-icon: #6d6b65;
/* Code blocks - Warm light theme */ /* Code blocks - Warm light theme */
--code-bg: #f0efed; --code-bg: #f0efed;
--code-header-bg: #eae9e6; --code-header-bg: #eae9e6;
--code-border: #d5d3cf; --code-border: #d5d3cf;
--code-line-number: #a8a5a0; --code-line-number: #a8a5a0;
--code-filename: #2563eb; --code-filename: #2563eb;
/* Syntax highlighting - GitHub Light inspired */ /* Syntax highlighting - GitHub Light inspired */
--syntax-string: #0a3069; --syntax-string: #0a3069;
--syntax-comment: #6e7781; --syntax-comment: #6e7781;
@ -456,11 +433,9 @@
--syntax-type: #8250df; --syntax-type: #8250df;
--syntax-operator: #24292f; --syntax-operator: #24292f;
--syntax-function: #8250df; --syntax-function: #8250df;
/* Inline code - Warm neutral */ /* Inline code - Warm neutral */
--inline-code-bg: rgba(0, 0, 0, 0.05); --inline-code-bg: rgba(0, 0, 0, 0.05);
--inline-code-text: #3a3935; --inline-code-text: #3a3935;
/* Diff viewer - Light mode */ /* Diff viewer - Light mode */
--diff-added-bg: rgba(34, 197, 94, 0.18); --diff-added-bg: rgba(34, 197, 94, 0.18);
--diff-added-text: #14532d; --diff-added-text: #14532d;
@ -488,7 +463,6 @@
--diff-expand-active-bg: rgba(0, 0, 0, 0.08); --diff-expand-active-bg: rgba(0, 0, 0, 0.08);
--diff-expand-all-hover-bg: rgba(0, 0, 0, 0.03); --diff-expand-all-hover-bg: rgba(0, 0, 0, 0.03);
--diff-expand-all-active-bg: rgba(0, 0, 0, 0.06); --diff-expand-all-active-bg: rgba(0, 0, 0, 0.06);
/* Markdown prose - Warm tones */ /* Markdown prose - Warm tones */
--prose-heading: #1c1b19; --prose-heading: #1c1b19;
--prose-body: #2a2925; --prose-body: #2a2925;
@ -501,7 +475,6 @@
--prose-blockquote-border: #d5d3cf; --prose-blockquote-border: #d5d3cf;
--prose-table-border: #e3e1dd; --prose-table-border: #e3e1dd;
--prose-table-header-bg: #eae9e6; --prose-table-header-bg: #eae9e6;
/* Thinking blocks - Warm purple */ /* Thinking blocks - Warm purple */
--thinking-bg: #f9f5fe; --thinking-bg: #f9f5fe;
--thinking-border: #d8b4fe; --thinking-border: #d8b4fe;
@ -509,14 +482,12 @@
--thinking-text-muted: #7c3aed; --thinking-text-muted: #7c3aed;
--thinking-content-border: #e9d5ff; --thinking-content-border: #e9d5ff;
--thinking-content-text: #581c87; --thinking-content-text: #581c87;
/* Tool call blocks - Warm amber */ /* Tool call blocks - Warm amber */
--tool-call-bg: #fefbf0; --tool-call-bg: #fefbf0;
--tool-call-border: #f0d070; --tool-call-border: #f0d070;
--tool-call-text: #92400e; --tool-call-text: #92400e;
--tool-call-code-bg: #fdf3d0; --tool-call-code-bg: #fdf3d0;
--tool-call-content-border: #f0d888; --tool-call-content-border: #f0d888;
/* Tool result blocks */ /* Tool result blocks */
--tool-result-success-bg: #f0fdf4; --tool-result-success-bg: #f0fdf4;
--tool-result-success-border: #86efac; --tool-result-success-border: #86efac;
@ -524,13 +495,11 @@
--tool-result-error-bg: #fef2f2; --tool-result-error-bg: #fef2f2;
--tool-result-error-border: #fca5a5; --tool-result-error-border: #fca5a5;
--tool-result-error-text: #991b1b; --tool-result-error-text: #991b1b;
/* Output blocks */ /* Output blocks */
--output-bg: #f0efed; --output-bg: #f0efed;
--output-border: #d5d3cf; --output-border: #d5d3cf;
--output-text: #2a2925; --output-text: #2a2925;
--output-content-border: #d5d3cf; --output-content-border: #d5d3cf;
/* Badges - High contrast */ /* Badges - High contrast */
--badge-error-bg: #dc2626; --badge-error-bg: #dc2626;
--badge-error-text: #ffffff; --badge-error-text: #ffffff;
@ -542,43 +511,35 @@
--badge-info-text: #ffffff; --badge-info-text: #ffffff;
--badge-neutral-bg: #e3e1dd; --badge-neutral-bg: #e3e1dd;
--badge-neutral-text: #3a3935; --badge-neutral-text: #3a3935;
/* Language/tag badges - Warm neutral */ /* Language/tag badges - Warm neutral */
--tag-bg: #eae9e6; --tag-bg: #eae9e6;
--tag-text: #4d4b46; --tag-text: #4d4b46;
--tag-border: #d5d3cf; --tag-border: #d5d3cf;
/* Highlighted text (skills, paths) - Warm neutral */ /* Highlighted text (skills, paths) - Warm neutral */
--skill-highlight-bg: rgba(0, 0, 0, 0.05); --skill-highlight-bg: rgba(0, 0, 0, 0.05);
--skill-highlight-text: #3a3935; --skill-highlight-text: #3a3935;
--path-highlight-bg: rgba(0, 0, 0, 0.05); --path-highlight-bg: rgba(0, 0, 0, 0.05);
--path-highlight-text: #3a3935; --path-highlight-text: #3a3935;
/* Interruption badge */ /* Interruption badge */
--interruption-bg: #fef2f2; --interruption-bg: #fef2f2;
--interruption-border: #f87171; --interruption-border: #f87171;
--interruption-text: #b91c1c; --interruption-text: #b91c1c;
/* Warning/Amber colors (for interruption banner) */ /* Warning/Amber colors (for interruption banner) */
--warning-bg: #fef3c7; --warning-bg: #fef3c7;
--warning-border: #f59e0b; --warning-border: #f59e0b;
--warning-text: #b45309; --warning-text: #b45309;
/* Plan exit/Green colors (for ExitPlanMode) */ /* Plan exit/Green colors (for ExitPlanMode) */
--plan-exit-bg: #f0fdf4; --plan-exit-bg: #f0fdf4;
--plan-exit-header-bg: #dcfce7; --plan-exit-header-bg: #dcfce7;
--plan-exit-border: #86efac; --plan-exit-border: #86efac;
--plan-exit-text: #15803d; --plan-exit-text: #15803d;
/* Error highlight (pulsing) */ /* Error highlight (pulsing) */
--error-highlight-ring: #dc2626; --error-highlight-ring: #dc2626;
--error-highlight-bg: rgba(220, 38, 38, 0.15); --error-highlight-bg: rgba(220, 38, 38, 0.15);
/* Keyboard hints */ /* Keyboard hints */
--kbd-bg: #eae9e6; --kbd-bg: #eae9e6;
--kbd-border: #a8a5a0; --kbd-border: #a8a5a0;
--kbd-text: #3a3935; --kbd-text: #3a3935;
/* Subagent/Card styling - Warm light mode */ /* Subagent/Card styling - Warm light mode */
--card-bg: #f9f9f7; --card-bg: #f9f9f7;
--card-bg-zebra: #f2f1ee; --card-bg-zebra: #f2f1ee;
@ -589,33 +550,27 @@
--card-text-light: #3a3935; --card-text-light: #3a3935;
--card-text-lighter: #2a2925; --card-text-lighter: #2a2925;
--card-separator: #d5d3cf; --card-separator: #d5d3cf;
/* System activity messages */ /* System activity messages */
--system-activity-bg: rgba(59, 130, 246, 0.08); --system-activity-bg: rgba(59, 130, 246, 0.08);
--system-activity-border: rgba(59, 130, 246, 0.25); --system-activity-border: rgba(59, 130, 246, 0.25);
--system-activity-accent: rgba(37, 99, 235, 0.7); --system-activity-accent: rgba(37, 99, 235, 0.7);
/* Cross-team communication */ /* Cross-team communication */
--cross-team-bg: rgba(168, 85, 247, 0.08); --cross-team-bg: rgba(168, 85, 247, 0.08);
--cross-team-border: rgba(168, 85, 247, 0.25); --cross-team-border: rgba(168, 85, 247, 0.25);
--cross-team-accent: rgba(124, 58, 237, 0.7); --cross-team-accent: rgba(124, 58, 237, 0.7);
/* Info style — banners, status indicators */ /* Info style — banners, status indicators */
--info-bg: rgba(59, 130, 246, 0.1); --info-bg: rgba(59, 130, 246, 0.1);
--info-border: rgba(37, 99, 235, 0.3); --info-border: rgba(37, 99, 235, 0.3);
--info-text: #2563eb; --info-text: #2563eb;
/* Sticky Context button - transparent glass */ /* Sticky Context button - transparent glass */
--context-btn-bg: rgba(0, 0, 0, 0.06); --context-btn-bg: rgba(0, 0, 0, 0.06);
--context-btn-bg-hover: rgba(0, 0, 0, 0.1); --context-btn-bg-hover: rgba(0, 0, 0, 0.1);
--context-btn-active-bg: rgba(99, 102, 241, 0.35); --context-btn-active-bg: rgba(99, 102, 241, 0.35);
--context-btn-active-text: #3730a3; --context-btn-active-text: #3730a3;
/* Skeleton — tinted cool gray */ /* Skeleton — tinted cool gray */
--skeleton-base: #d6d8de; --skeleton-base: #d6d8de;
--skeleton-base-light: #cdd0d7; --skeleton-base-light: #cdd0d7;
--skeleton-base-dim: rgba(205, 208, 215, 0.6); --skeleton-base-dim: rgba(205, 208, 215, 0.6);
/* Provisioning step badges — dark enough for light backgrounds */ /* Provisioning step badges — dark enough for light backgrounds */
--step-done-bg: rgba(16, 185, 129, 0.12); --step-done-bg: rgba(16, 185, 129, 0.12);
--step-done-border: rgba(5, 150, 105, 0.5); --step-done-border: rgba(5, 150, 105, 0.5);
@ -629,52 +584,59 @@
--step-warning-text: #b45309; --step-warning-text: #b45309;
--step-warning-border: rgba(180, 83, 9, 0.4); --step-warning-border: rgba(180, 83, 9, 0.4);
--step-warning-bg: rgba(245, 158, 11, 0.1); --step-warning-bg: rgba(245, 158, 11, 0.1);
/* Collapsible section backgrounds (sidebar) */ /* Collapsible section backgrounds (sidebar) */
--color-section-bg: rgba(0, 0, 0, 0.04); --color-section-bg: rgba(0, 0, 0, 0.04);
--color-section-bg-open: rgba(0, 0, 0, 0.07); --color-section-bg-open: rgba(0, 0, 0, 0.07);
--color-section-hover: rgba(0, 0, 0, 0.08); --color-section-hover: rgba(0, 0, 0, 0.08);
--color-section-hover-open: rgba(0, 0, 0, 0.1); --color-section-hover-open: rgba(0, 0, 0, 0.1);
/* Compact boundary — phase badge */ /* Compact boundary — phase badge */
--compact-phase-bg: rgba(67, 56, 202, 0.12); --compact-phase-bg: rgba(67, 56, 202, 0.12);
--compact-phase-text: #4338ca; --compact-phase-text: #4338ca;
} }
/* rehype-highlight (highlight.js) — map hljs classes to app theme variables */ /* rehype-highlight (highlight.js) — map hljs classes to app theme variables */
.hljs { .hljs {
color: var(--color-text); color: var(--color-text);
background: transparent; background: transparent;
} }
.hljs-keyword, .hljs-keyword,
.hljs-selector-tag { .hljs-selector-tag {
color: var(--syntax-keyword); color: var(--syntax-keyword);
} }
.hljs-addition { .hljs-addition {
color: var(--diff-added-text); color: var(--diff-added-text);
} }
.hljs-string, .hljs-string,
.hljs-doctag { .hljs-doctag {
color: var(--syntax-string); color: var(--syntax-string);
} }
.hljs-comment, .hljs-comment,
.hljs-quote { .hljs-quote {
color: var(--syntax-comment); color: var(--syntax-comment);
font-style: italic; font-style: italic;
} }
.hljs-number, .hljs-number,
.hljs-literal { .hljs-literal {
color: var(--syntax-number); color: var(--syntax-number);
} }
.hljs-built_in, .hljs-built_in,
.hljs-type, .hljs-type,
.hljs-class .hljs-title { .hljs-class .hljs-title {
color: var(--syntax-type); color: var(--syntax-type);
} }
.hljs-title.function_, .hljs-title.function_,
.hljs-function .hljs-title { .hljs-function .hljs-title {
color: var(--syntax-function); color: var(--syntax-function);
} }
.hljs-params, .hljs-params,
.hljs-attr, .hljs-attr,
.hljs-variable, .hljs-variable,
@ -682,6 +644,7 @@
.hljs-attribute { .hljs-attribute {
color: var(--color-text); color: var(--color-text);
} }
.hljs-symbol, .hljs-symbol,
.hljs-bullet, .hljs-bullet,
.hljs-subst, .hljs-subst,
@ -693,9 +656,11 @@
.hljs-regexp { .hljs-regexp {
color: var(--syntax-operator); color: var(--syntax-operator);
} }
.hljs-deletion { .hljs-deletion {
color: var(--diff-removed-text); color: var(--diff-removed-text);
} }
.hljs-section { .hljs-section {
font-weight: 600; font-weight: 600;
color: var(--syntax-keyword); color: var(--syntax-keyword);
@ -727,6 +692,7 @@ body {
} }
/* macOS window integration */ /* macOS window integration */
.sidebar-header { .sidebar-header {
-webkit-app-region: drag; -webkit-app-region: drag;
-webkit-user-select: none; -webkit-user-select: none;
@ -739,11 +705,13 @@ body {
} }
/* Prevent drag region bleed-through on Windows: all fixed overlays must be no-drag */ /* Prevent drag region bleed-through on Windows: all fixed overlays must be no-drag */
.fixed { .fixed {
-webkit-app-region: no-drag; -webkit-app-region: no-drag;
} }
/* Hide horizontal scrollbar in tab bar */ /* Hide horizontal scrollbar in tab bar */
.scrollbar-none { .scrollbar-none {
scrollbar-width: none; scrollbar-width: none;
-ms-overflow-style: none; -ms-overflow-style: none;
@ -754,6 +722,7 @@ body {
} }
/* Custom scrollbar styling for dark theme */ /* Custom scrollbar styling for dark theme */
::-webkit-scrollbar { ::-webkit-scrollbar {
width: 8px; width: 8px;
height: 8px; height: 8px;
@ -778,12 +747,14 @@ body {
} }
/* Firefox scrollbar */ /* Firefox scrollbar */
* { * {
scrollbar-width: thin; scrollbar-width: thin;
scrollbar-color: var(--scrollbar-thumb) transparent; scrollbar-color: var(--scrollbar-thumb) transparent;
} }
/* Thin scrollbar for narrow panels (sidebar, search) */ /* Thin scrollbar for narrow panels (sidebar, search) */
.scrollbar-thin::-webkit-scrollbar { .scrollbar-thin::-webkit-scrollbar {
width: 6px; width: 6px;
} }
@ -793,6 +764,7 @@ body {
} }
/* Dashboard skeleton shimmer animation */ /* Dashboard skeleton shimmer animation */
@keyframes shimmer { @keyframes shimmer {
0% { 0% {
transform: translateX(-100%); transform: translateX(-100%);
@ -898,6 +870,7 @@ body {
} }
/* Member spawn animations */ /* Member spawn animations */
@keyframes member-spawn-pulse { @keyframes member-spawn-pulse {
0%, 0%,
100% { 100% {
@ -931,6 +904,7 @@ body {
} }
/* Per-element shimmer — fast, high-contrast sweep */ /* Per-element shimmer — fast, high-contrast sweep */
.skeleton-shimmer { .skeleton-shimmer {
position: relative; position: relative;
overflow: hidden; overflow: hidden;
@ -965,11 +939,13 @@ body {
} }
/* Optional field label — muted text for non-required form fields */ /* Optional field label — muted text for non-required form fields */
.label-optional { .label-optional {
color: var(--color-text-muted); color: var(--color-text-muted);
} }
/* Checkerboard background for transparent image previews */ /* Checkerboard background for transparent image previews */
.checkerboard-bg { .checkerboard-bg {
background-image: background-image:
linear-gradient(45deg, #1a1a2e 25%, transparent 25%), linear-gradient(45deg, #1a1a2e 25%, transparent 25%),
@ -986,15 +962,18 @@ body {
} }
/* CLI Logs compact density — reduces item height inside CliLogsRichView */ /* CLI Logs compact density — reduces item height inside CliLogsRichView */
.cli-logs-compact [role='button'] { .cli-logs-compact [role='button'] {
padding-top: 0.2rem; padding-top: 0.2rem;
padding-bottom: 0.2rem; padding-bottom: 0.2rem;
gap: 0.375rem; gap: 0.375rem;
} }
.cli-logs-compact [role='button'] .text-sm { .cli-logs-compact [role='button'] .text-sm {
font-size: 0.75rem; font-size: 0.75rem;
line-height: 1rem; line-height: 1rem;
} }
.cli-logs-compact [role='button'] .text-xs { .cli-logs-compact [role='button'] .text-xs {
font-size: 0.625rem; font-size: 0.625rem;
line-height: 0.875rem; line-height: 0.875rem;
@ -1010,6 +989,7 @@ body {
} }
/* Lightbox toolbar buttons — enlarge hit targets and fix macOS hit-testing */ /* Lightbox toolbar buttons — enlarge hit targets and fix macOS hit-testing */
.yarl__toolbar { .yarl__toolbar {
z-index: 1; z-index: 1;
} }