fix(ui): Lot A #151 #158 #159 (QA verte)

- #151: chevauchement des boutons dans la barre supérieure pendant une conversation agent

- #158: popup de reprise de conversation intempestive (ajout cellule / changement layout / projet)

- #159: pastille d'activité de projet
This commit is contained in:
2026-08-06 10:23:23 +02:00
parent fb19ee48dc
commit c5d6c3b98e
10 changed files with 351 additions and 6 deletions

View File

@ -12,6 +12,7 @@
import type { TabItem } from "@/shared";
import { Button, Tabs, cn } from "@/shared";
import type { ProjectActivityStatus } from "./projectActivity";
export interface ProjectTabsProps {
items: TabItem[];
@ -22,6 +23,8 @@ export interface ProjectTabsProps {
projectsPanelOpen: boolean;
/** Open the Projects panel (floating) — create/switch project. */
onOpenProjectsPanel: () => void;
/** Per-project custom CLI activity, keyed by project id. Missing = none. */
activityByProjectId?: Record<string, ProjectActivityStatus>;
className?: string;
}
@ -32,8 +35,19 @@ export function ProjectTabs({
onClose,
projectsPanelOpen,
onOpenProjectsPanel,
activityByProjectId = {},
className,
}: ProjectTabsProps) {
const tabs = items.map((item) => ({
...item,
leading: (
<ProjectActivityDot
status={activityByProjectId[item.id] ?? "none"}
label={item.label}
/>
),
}));
return (
<div
className={cn(
@ -45,7 +59,7 @@ export function ProjectTabs({
<p className="px-2 text-sm text-muted">No open tabs.</p>
) : (
<Tabs
items={items}
items={tabs}
value={activeTabId}
onSelect={onSelect}
onClose={onClose}
@ -72,3 +86,32 @@ export function ProjectTabs({
</div>
);
}
function ProjectActivityDot({
status,
label,
}: {
status: ProjectActivityStatus;
label: string;
}) {
const title =
status === "busy"
? `${label} : activité en cours`
: status === "idle"
? `${label} : conversation ouverte`
: `${label} : aucune conversation active`;
return (
<span
data-testid={`project-activity-${label}`}
aria-hidden="true"
title={title}
className={cn(
"h-2.5 w-2.5 shrink-0 rounded-full border",
status === "busy" &&
"animate-pulse border-warning bg-warning shadow-[0_0_0_2px_rgba(212,155,58,0.16)]",
status === "idle" && "border-success bg-success",
status === "none" && "border-border-strong bg-muted",
)}
/>
);
}