fix(ui): thème, textes et lisibilité restants de la revue
All checks were successful
CI / Lint, Unit Tests & Build (push) Successful in 6m57s
CI / Deploy production (on server) (push) Successful in 24s

Les boutons suivent la couleur d’apparence, les libellés trop petits ou trop techniques sont clarifiés, et le catalogue des fournisseurs se met à jour tout seul.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
Antigravity
2026-08-30 21:13:07 +00:00
parent ebf6f16fde
commit afbb0dfc2d
77 changed files with 2842 additions and 1546 deletions

View File

@@ -10,6 +10,7 @@ import {
import { useLanguage } from '@/lib/i18n'
import { DashboardWidgetTitleRow } from '@/components/dashboard-widget-title-row'
import { MEMORY_ECHO_LEGACY_EN_FALLBACKS } from '@/lib/ai/memory-echo-i18n'
import { pathNoteTitle } from '@/lib/dashboard/path-title'
// ─── Types ─────────────────────────────────────────────
@@ -104,14 +105,14 @@ function ConnectionDiagram({
className="flex-1 min-w-0 p-2.5 rounded-xl border border-border/30 bg-white/80 dark:bg-zinc-900/60 text-start"
style={{ borderColor: `${color}30` }}
>
<p className="text-[10px] font-semibold text-ink dark:text-dark-ink truncate leading-tight">
<p className="text-sm font-semibold text-ink dark:text-dark-ink line-clamp-2 leading-tight" title={note1Title}>
{note1Title}
</p>
</div>
<div className="shrink-0 flex flex-col items-center gap-0.5 px-1">
<div className="w-8 h-px" style={{ background: `linear-gradient(90deg, transparent, ${color}, transparent)` }} />
<span
className="text-[9px] font-mono font-bold px-2 py-0.5 rounded-full"
className="text-[13px] font-medium px-2 py-0.5 rounded-full"
style={{ color, backgroundColor: `${color}14`, border: `1px solid ${color}25` }}
>
{Math.round(score * 100)}%
@@ -122,7 +123,7 @@ function ConnectionDiagram({
className="flex-1 min-w-0 p-2.5 rounded-xl border border-border/30 bg-white/80 dark:bg-zinc-900/60 text-start"
style={{ borderColor: `${color}30` }}
>
<p className="text-[10px] font-semibold text-ink dark:text-dark-ink truncate leading-tight">
<p className="text-sm font-semibold text-ink dark:text-dark-ink line-clamp-2 leading-tight" title={note2Title}>
{note2Title}
</p>
</div>
@@ -153,6 +154,7 @@ export interface IntelligenceHubProps {
dismissingInsightId: string | null
actingBridgeSuggestionKey: string | null
prefersReducedMotion: boolean
excludeBridgeSuggestionKeys?: string[]
}
// ─── Component ─────────────────────────────────────────
@@ -178,6 +180,7 @@ export function IntelligenceHub({
dismissingInsightId,
actingBridgeSuggestionKey,
prefersReducedMotion,
excludeBridgeSuggestionKeys,
}: IntelligenceHubProps) {
const router = useRouter()
const { t } = useLanguage()
@@ -226,10 +229,13 @@ export function IntelligenceHub({
})
}
const hiddenSuggestions = new Set(excludeBridgeSuggestionKeys ?? [])
for (const suggestion of bridgeSuggestions) {
const key = `${suggestion.clusterAId}-${suggestion.clusterBId}`
if (hiddenSuggestions.has(key)) continue
items.push({
kind: 'suggestion',
id: `suggestion-${suggestion.clusterAId}-${suggestion.clusterBId}`,
id: `suggestion-${key}`,
priority: 80,
suggestion,
})
@@ -245,7 +251,7 @@ export function IntelligenceHub({
}
return items.sort((a, b) => b.priority - a.priority).slice(0, 10)
}, [insights, bridgeNotes, bridgeSuggestions, agentActions])
}, [insights, bridgeNotes, bridgeSuggestions, agentActions, excludeBridgeSuggestionKeys])
const counts = useMemo(() => ({
all: allItems.length,
@@ -302,32 +308,32 @@ export function IntelligenceHub({
return (
<div className="flex flex-col h-full">
<div className="flex items-center gap-2 mb-3">
<Sparkles size={12} className="text-indigo-500" />
<span className="text-[9px] font-mono font-bold uppercase tracking-wider text-indigo-600 dark:text-indigo-400">
<Sparkles size={12} className="text-brand-accent" />
<span className="text-[13px] font-medium text-brand-accent">
{t('homeDashboard.semanticConnection')}
</span>
{!insight.viewed && (
<span className="w-1.5 h-1.5 rounded-full bg-ochre animate-pulse" />
<span className="w-1.5 h-1.5 rounded-full bg-brand-accent animate-pulse" />
)}
</div>
<ConnectionDiagram
note1Title={insight.note1.title || t('homeDashboard.untitled')}
note2Title={insight.note2.title || t('homeDashboard.untitled')}
note1Title={pathNoteTitle(insight.note1.title, insight.note1Excerpt) || t('homeDashboard.untitled')}
note2Title={pathNoteTitle(insight.note2.title, insight.note2Excerpt) || t('homeDashboard.untitled')}
score={insight.score}
/>
<p className="text-[11px] text-ink/75 dark:text-dark-ink/75 font-serif italic leading-relaxed line-clamp-3 px-1">
<p className="text-sm text-ink/75 dark:text-dark-ink/75 font-serif italic leading-relaxed line-clamp-3 px-1">
« {text} »
</p>
{excerpt && (
<p className="text-[9px] text-concrete/80 line-clamp-2 mt-2 px-1 border-s-2 border-indigo-500/20 ps-2">
<p className="text-sm text-concrete/80 line-clamp-2 mt-2 px-1 border-s-2 border-brand-accent/20 ps-2">
{excerpt}
</p>
)}
<div className="flex items-center gap-1.5 mt-auto pt-3 flex-wrap">
<div className="flex items-center gap-1.5 mt-auto pt-3 flex-wrap shrink-0">
<button
type="button"
onClick={() => onOpenInsightNote(insight, insight.note1.id)}
className="inline-flex items-center gap-1 text-[8.5px] font-mono uppercase font-bold px-2.5 py-1.5 rounded-lg bg-indigo-600 text-white hover:bg-indigo-700 transition-colors"
className="inline-flex items-center gap-1 text-[13px] font-medium px-2.5 py-1.5 rounded-lg bg-brand-accent text-white hover:bg-brand-accent/90 transition-colors"
>
<ExternalLink size={9} />
{t('homeDashboard.intelOpenNote')}
@@ -335,7 +341,7 @@ export function IntelligenceHub({
<button
type="button"
onClick={() => onOpenInsightNote(insight, insight.note1.id, insight.note2.id)}
className="inline-flex items-center gap-1 text-[8.5px] font-mono uppercase font-bold px-2.5 py-1.5 rounded-lg border border-border/40 hover:border-indigo-400/40 transition-colors"
className="inline-flex items-center gap-1 text-[13px] font-medium px-2.5 py-1.5 rounded-lg border border-border/40 hover:border-brand-accent/40 transition-colors"
>
<GitCompare size={9} />
{t('homeDashboard.intelCompare')}
@@ -358,19 +364,19 @@ export function IntelligenceHub({
case 'bridge': {
const { bridge } = item
const title = bridge.note?.title || t('homeDashboard.untitled')
const title = pathNoteTitle(bridge.note?.title, bridge.note?.content) || t('homeDashboard.untitled')
const excerpt = bridge.note?.content ? stripHtml(bridge.note.content).slice(0, 160) : ''
const names = bridge.clusterNames ?? []
return (
<div className="flex flex-col h-full">
<div className="flex items-center justify-between gap-2 mb-3">
<div className="flex items-center gap-2">
<Zap size={12} className="text-ochre" />
<span className="text-[9px] font-mono font-bold uppercase tracking-wider text-ochre">
<Zap size={12} className="text-brand-accent" />
<span className="text-[13px] font-medium text-brand-accent">
{t('homeDashboard.bridgeNote')}
</span>
</div>
<span className="text-[9px] font-mono font-bold text-ochre bg-ochre/10 px-2 py-0.5 rounded-full">
<span className="text-[13px] font-medium text-brand-accent bg-brand-accent/10 px-2 py-0.5 rounded-full">
{Math.round(bridge.bridgeScore * 100)}%
</span>
</div>
@@ -379,11 +385,11 @@ export function IntelligenceHub({
onClick={() => onNoteSelect(bridge.noteId)}
className="text-start group flex-1"
>
<p className="text-sm font-semibold text-ink dark:text-dark-ink group-hover:text-ochre transition-colors mb-2 leading-snug">
<p className="text-sm font-semibold text-ink dark:text-dark-ink group-hover:text-brand-accent transition-colors mb-2 leading-snug">
{title}
</p>
{excerpt && (
<p className="text-[10px] text-concrete leading-relaxed line-clamp-3 mb-3">{excerpt}</p>
<p className="text-sm text-concrete leading-relaxed line-clamp-3 mb-3">{excerpt}</p>
)}
{names.length > 0 && (
<div className="flex flex-wrap gap-1.5">
@@ -396,7 +402,7 @@ export function IntelligenceHub({
className="w-1.5 h-1.5 rounded-full"
style={{ backgroundColor: CLUSTER_COLORS[i % CLUSTER_COLORS.length] }}
/>
<span className="text-[8px] font-mono uppercase text-concrete">{name}</span>
<span className="text-[13px] text-concrete">{name}</span>
</span>
))}
</div>
@@ -405,7 +411,7 @@ export function IntelligenceHub({
<button
type="button"
onClick={() => onNoteSelect(bridge.noteId)}
className="mt-3 inline-flex items-center gap-1 text-[8.5px] font-mono uppercase font-bold px-2.5 py-1.5 rounded-lg bg-ochre/90 text-white hover:bg-ochre transition-colors w-fit"
className="mt-3 inline-flex items-center gap-1 text-[13px] font-medium px-2.5 py-1.5 rounded-lg bg-brand-accent/90 text-white hover:bg-brand-accent transition-colors w-fit"
>
<ExternalLink size={9} />
{t('homeDashboard.intelOpenNote')}
@@ -421,28 +427,28 @@ export function IntelligenceHub({
return (
<div className="flex flex-col h-full">
<div className="flex items-center gap-2 mb-3">
<Lightbulb size={12} className="text-violet-500" />
<span className="text-[9px] font-mono font-bold uppercase tracking-wider text-violet-600 dark:text-violet-400 truncate">
<Lightbulb size={12} className="text-brand-accent" />
<span className="text-[13px] font-medium text-brand-accent truncate">
{t('homeDashboard.intelMissingLink')}
</span>
</div>
<div className="flex items-center gap-2 mb-3">
<span className="px-2 py-1 rounded-lg bg-violet-500/10 text-[9px] font-mono font-bold text-violet-700 dark:text-violet-300 truncate max-w-[45%]">
<span className="px-2 py-1 rounded-lg bg-brand-accent/10 text-[13px] font-medium text-brand-accent truncate max-w-[45%]" title={suggestion.clusterAName}>
{suggestion.clusterAName}
</span>
<div className="flex-1 h-px bg-gradient-to-r from-violet-400/40 via-ochre/60 to-violet-400/40" />
<span className="px-2 py-1 rounded-lg bg-ochre/10 text-[9px] font-mono font-bold text-ochre truncate max-w-[45%]">
<div className="flex-1 h-px bg-gradient-to-r from-brand-accent/40 via-brand-accent/60 to-brand-accent/40" />
<span className="px-2 py-1 rounded-lg bg-brand-accent/10 text-[13px] font-medium text-brand-accent truncate max-w-[45%]" title={suggestion.clusterBName}>
{suggestion.clusterBName}
</span>
</div>
<p className="text-sm font-semibold text-ink dark:text-dark-ink mb-1.5">{suggestion.suggestedTitle}</p>
<p className="text-[10px] text-concrete leading-relaxed line-clamp-2 flex-1">{suggestion.suggestedContent}</p>
<div className="flex items-center gap-1.5 mt-3 pt-3 border-t border-border/15">
<p className="text-sm text-concrete leading-relaxed line-clamp-2 flex-1">{suggestion.suggestedContent}</p>
<div className="flex items-center gap-1.5 mt-3 pt-3 border-t border-border/15 shrink-0">
<button
type="button"
disabled={busy}
onClick={() => onCreateBridgeSuggestion(suggestion)}
className="inline-flex items-center gap-1 text-[8.5px] font-mono uppercase font-bold px-2.5 py-1.5 rounded-lg bg-violet-600 text-white hover:bg-violet-700 transition-colors disabled:opacity-40"
className="inline-flex items-center gap-1 text-[13px] font-medium px-2.5 py-1.5 rounded-lg bg-brand-accent text-white hover:bg-brand-accent/90 transition-colors disabled:opacity-40"
>
{busy ? <Loader2 size={9} className="animate-spin" /> : <Link2 size={9} />}
{t('homeDashboard.createBridgeNote')}
@@ -451,7 +457,7 @@ export function IntelligenceHub({
type="button"
disabled={busy}
onClick={() => onDismissBridgeSuggestion(suggestion)}
className="text-[8.5px] font-mono uppercase px-2 py-1.5 rounded-lg border border-border/30 text-concrete hover:text-rose-500 disabled:opacity-40"
className="text-[13px] font-medium px-2 py-1.5 rounded-lg border border-border/30 text-concrete hover:text-rose-500 disabled:opacity-40"
>
{t('homeDashboard.dismiss')}
</button>
@@ -465,25 +471,25 @@ export function IntelligenceHub({
return (
<div className="flex flex-col h-full">
<div className="flex items-center gap-2 mb-3">
<Bot size={12} className="text-ochre" />
<span className="text-[9px] font-mono font-bold uppercase tracking-wider text-ochre">
<Bot size={12} className="text-brand-accent" />
<span className="text-[13px] font-medium text-brand-accent">
{agent.agentName}
</span>
<span className="text-[8px] font-mono text-concrete/60 ms-auto">
<span className="text-[13px] text-concrete/60 ms-auto">
{formatRelativeTime(agent.createdAt, t)}
</span>
</div>
{agent.result ? (
<p className="text-[11px] text-concrete leading-relaxed line-clamp-4 flex-1">
<p className="text-sm text-concrete leading-relaxed line-clamp-4 flex-1">
{agent.result}
</p>
) : (
<p className="text-[11px] text-concrete/60 italic flex-1">{t('homeDashboard.intelAgentNoResult')}</p>
<p className="text-sm text-concrete/60 italic flex-1">{t('homeDashboard.intelAgentNoResult')}</p>
)}
<button
type="button"
onClick={() => router.push('/agents')}
className="mt-3 inline-flex items-center gap-1 text-[8.5px] font-mono uppercase font-bold px-2.5 py-1.5 rounded-lg border border-ochre/30 text-ochre hover:bg-ochre/10 transition-colors w-fit"
className="mt-3 inline-flex items-center gap-1 text-[13px] font-medium px-2.5 py-1.5 rounded-lg border border-brand-accent/30 text-brand-accent hover:bg-brand-accent/10 transition-colors w-fit"
>
{t('homeDashboard.intelViewAgent')}
<ArrowRight size={9} />
@@ -497,10 +503,10 @@ export function IntelligenceHub({
const spotlightAccent = (item: IntelItem | null) => {
if (!item) return 'from-stone-100/50 to-transparent border-border/30'
switch (item.kind) {
case 'insight': return 'from-indigo-500/[0.06] via-transparent to-transparent border-indigo-400/25'
case 'bridge': return 'from-ochre/[0.06] via-transparent to-transparent border-ochre/25'
case 'suggestion': return 'from-violet-500/[0.06] via-transparent to-transparent border-violet-400/25'
case 'agent': return 'from-ochre/[0.04] via-transparent to-transparent border-border/30'
case 'insight': return 'from-brand-accent/[0.06] via-transparent to-transparent border-brand-accent/25'
case 'bridge': return 'from-brand-accent/[0.06] via-transparent to-transparent border-brand-accent/25'
case 'suggestion': return 'from-brand-accent/[0.06] via-transparent to-transparent border-brand-accent/25'
case 'agent': return 'from-brand-accent/[0.04] via-transparent to-transparent border-border/30'
}
}
@@ -518,7 +524,7 @@ export function IntelligenceHub({
actions={(
<>
{newCount > 0 && (
<span className="text-[8px] font-mono font-bold text-brand-accent bg-brand-accent/10 px-2 py-0.5 rounded uppercase">
<span className="text-[13px] font-medium text-brand-accent bg-brand-accent/10 px-2 py-0.5 rounded">
{newCount} {t('homeDashboard.new')}
</span>
)}
@@ -543,7 +549,7 @@ export function IntelligenceHub({
<div className="h-[220px] rounded-2xl bg-stone-50 dark:bg-zinc-950/30 animate-pulse" />
) : !aiActive ? (
<div className="p-5 rounded-2xl border border-dashed border-border/40 bg-stone-50/50 dark:bg-zinc-950/30 text-center space-y-3 min-h-[180px] flex flex-col justify-center">
<p className="text-xs text-concrete leading-relaxed">
<p className="text-sm text-concrete leading-relaxed">
{!hasAiConsent
? t('homeDashboard.aiConsentRequired')
: !providerReady
@@ -554,7 +560,7 @@ export function IntelligenceHub({
<button
type="button"
onClick={onEnableAi}
className="text-[9px] font-mono uppercase font-bold px-3 py-1.5 rounded-lg bg-ink text-white dark:bg-white dark:text-black hover:opacity-90 transition-opacity mx-auto"
className="text-[13px] font-medium px-3 py-1.5 rounded-lg bg-brand-accent text-white hover:bg-brand-accent/90 transition-colors mx-auto"
>
{t('homeDashboard.enableAi')}
</button>
@@ -563,12 +569,12 @@ export function IntelligenceHub({
) : allItems.length === 0 ? (
<div className="p-5 rounded-2xl border border-dashed border-border/40 bg-stone-50/50 dark:bg-zinc-950/30 text-center space-y-3 min-h-[180px] flex flex-col justify-center">
<Brain size={22} className="mx-auto text-concrete/40" strokeWidth={1.25} />
<p className="text-xs text-concrete leading-relaxed">{t('homeDashboard.noConnections')}</p>
<p className="text-sm text-concrete leading-relaxed">{t('homeDashboard.noConnections')}</p>
<button
type="button"
onClick={onRefreshEcho}
disabled={echoRefreshing}
className="inline-flex items-center gap-1.5 text-[9px] font-mono uppercase font-bold px-3 py-1.5 rounded-lg border border-ochre/30 text-ochre hover:bg-ochre/10 transition-all disabled:opacity-40 mx-auto"
className="inline-flex items-center gap-1.5 text-[13px] font-medium px-3 py-1.5 rounded-lg border border-brand-accent/30 text-brand-accent hover:bg-brand-accent/10 transition-all disabled:opacity-40 mx-auto"
>
{echoRefreshing ? <Loader2 size={11} className="animate-spin" /> : <Sparkles size={11} />}
{t('homeDashboard.analyzeNotes')}
@@ -587,15 +593,15 @@ export function IntelligenceHub({
key={f.key}
type="button"
onClick={() => setFilter(f.key)}
className={`shrink-0 inline-flex items-center gap-1.5 px-2.5 py-1 rounded-full text-[8.5px] font-mono font-bold uppercase tracking-wider transition-all ${
className={`shrink-0 inline-flex items-center gap-1.5 px-2.5 py-1 rounded-full text-[13px] font-medium transition-all ${
active
? 'bg-ink text-white dark:bg-white dark:text-black shadow-sm'
? 'bg-brand-accent text-white shadow-sm'
: 'bg-stone-100 dark:bg-zinc-800 text-concrete hover:text-ink dark:hover:text-dark-ink'
}`}
>
{f.label}
{count > 0 && (
<span className={`text-[7px] px-1 py-px rounded-full ${active ? 'bg-white/20' : 'bg-black/5 dark:bg-white/10'}`}>
<span className={`text-[13px] px-1.5 py-0.5 rounded-full ${active ? 'bg-white/20' : 'bg-black/5 dark:bg-white/10'}`}>
{count}
</span>
)}
@@ -605,7 +611,7 @@ export function IntelligenceHub({
</div>
{filteredItems.length === 0 ? (
<p className="text-xs text-concrete italic text-center py-8">{t('homeDashboard.intelFilterEmpty')}</p>
<p className="text-sm text-concrete italic text-center py-8">{t('homeDashboard.intelFilterEmpty')}</p>
) : (
<>
{/* Spotlight carousel */}
@@ -616,7 +622,7 @@ export function IntelligenceHub({
type="button"
onClick={goPrev}
disabled={activeIndex === 0}
className="absolute start-0 top-1/2 -translate-y-1/2 -translate-x-1 z-10 p-1 rounded-full border border-border/40 bg-white/90 dark:bg-zinc-900/90 shadow-sm disabled:opacity-25 hover:border-ochre/40 transition-all"
className="absolute start-0 top-1/2 -translate-y-1/2 -translate-x-1 z-10 p-1 rounded-full border border-border/40 bg-white/90 dark:bg-zinc-900/90 shadow-sm disabled:opacity-25 hover:border-brand-accent/40 transition-all"
aria-label={t('homeDashboard.intelPrev')}
>
<ChevronLeft size={14} />
@@ -625,7 +631,7 @@ export function IntelligenceHub({
type="button"
onClick={goNext}
disabled={activeIndex >= filteredItems.length - 1}
className="absolute end-0 top-1/2 -translate-y-1/2 translate-x-1 z-10 p-1 rounded-full border border-border/40 bg-white/90 dark:bg-zinc-900/90 shadow-sm disabled:opacity-25 hover:border-ochre/40 transition-all"
className="absolute end-0 top-1/2 -translate-y-1/2 translate-x-1 z-10 p-1 rounded-full border border-border/40 bg-white/90 dark:bg-zinc-900/90 shadow-sm disabled:opacity-25 hover:border-brand-accent/40 transition-all"
aria-label={t('homeDashboard.intelNext')}
>
<ChevronRight size={14} />
@@ -664,14 +670,14 @@ export function IntelligenceHub({
onClick={() => setActiveIndex(idx)}
className={`rounded-full transition-all ${
idx === activeIndex
? 'w-5 h-1.5 bg-ochre'
? 'w-5 h-1.5 bg-brand-accent'
: 'w-1.5 h-1.5 bg-concrete/25 hover:bg-concrete/50'
}`}
aria-label={t('homeDashboard.intelGoTo', { index: idx + 1 })}
/>
))}
</div>
<span className="text-[8px] font-mono text-concrete/60 uppercase">
<span className="text-[13px] text-concrete/60">
{t('homeDashboard.intelPosition', { current: activeIndex + 1, total: filteredItems.length })}
</span>
</div>
@@ -684,37 +690,39 @@ export function IntelligenceHub({
const isActive = idx === activeIndex
let label = ''
let Icon = Sparkles
let accent = 'text-indigo-500'
let accent = 'text-brand-accent'
if (item.kind === 'insight') {
label = item.insight.note1.title?.slice(0, 28) || t('homeDashboard.untitled')
label = pathNoteTitle(item.insight.note1.title, item.insight.note1Excerpt) || t('homeDashboard.untitled')
Icon = Sparkles
accent = 'text-indigo-500'
accent = 'text-brand-accent'
} else if (item.kind === 'bridge') {
label = item.bridge.note?.title?.slice(0, 28) || t('homeDashboard.untitled')
label = pathNoteTitle(item.bridge.note?.title, item.bridge.note?.content) || t('homeDashboard.untitled')
Icon = Zap
accent = 'text-ochre'
accent = 'text-brand-accent'
} else if (item.kind === 'suggestion') {
label = item.suggestion.suggestedTitle.slice(0, 28)
label = item.suggestion.suggestedTitle
Icon = Lightbulb
accent = 'text-violet-500'
accent = 'text-brand-accent'
} else {
label = item.agent.agentName
Icon = Bot
accent = 'text-ochre'
accent = 'text-brand-accent'
}
return (
<button
key={item.id}
type="button"
onClick={() => setActiveIndex(idx)}
className={`shrink-0 flex items-center gap-1.5 px-2 py-1.5 rounded-lg border text-start max-w-[130px] transition-all ${
title={label}
aria-label={label}
className={`shrink-0 flex items-center gap-1.5 px-2 py-1.5 rounded-lg border text-start max-w-[180px] transition-all ${
isActive
? 'border-ochre/40 bg-ochre/5 shadow-sm'
? 'border-brand-accent/40 bg-brand-accent/5 shadow-sm'
: 'border-border/25 bg-stone-50/50 dark:bg-zinc-950/30 hover:border-border/50'
}`}
>
<Icon size={9} className={`shrink-0 ${accent}`} />
<span className="text-[8px] font-medium text-ink dark:text-dark-ink truncate">{label}</span>
<span className="text-[13px] font-medium text-ink dark:text-dark-ink truncate">{label}</span>
</button>
)
})}