Files
kandev/apps/web/components/task/workflow-step-marker.tsx
T
2026-09-13 12:07:49 +01:00

68 lines
1.8 KiB
TypeScript

"use client";
import { IconLoader2 } from "@tabler/icons-react";
export type StepMarkerState = "current" | "completed" | "upcoming" | "pending";
export function StepCircleIndicator({
isCurrent,
isCompleted,
isPending = false,
pendingLabel,
}: {
isCurrent: boolean;
isCompleted: boolean;
isPending?: boolean;
pendingLabel?: string;
}) {
let state: StepMarkerState = "upcoming";
if (isPending) state = "pending";
else if (isCurrent) state = "current";
else if (isCompleted) state = "completed";
if (isPending) {
return (
<span
data-marker-state={state}
role={pendingLabel ? "img" : undefined}
aria-label={pendingLabel}
className="relative flex h-2 w-2 items-center justify-center shrink-0"
>
<IconLoader2
aria-hidden="true"
data-marker-visual-size={isCurrent ? "14" : "8"}
className={[
"absolute animate-spin text-primary motion-reduce:animate-none",
isCurrent ? "h-3.5 w-3.5" : "h-2 w-2",
].join(" ")}
/>
</span>
);
}
if (isCurrent) {
return (
<span
data-marker-state={state}
className="relative flex items-center justify-center shrink-0"
>
<span className="absolute h-3.5 w-3.5 rounded-full border-2 border-primary/40" />
<span className="h-2 w-2 rounded-full bg-primary" />
</span>
);
}
if (isCompleted) {
return (
<span
data-marker-state={state}
className="relative flex items-center justify-center shrink-0"
>
<span className="h-2 w-2 rounded-full bg-muted-foreground/60" />
</span>
);
}
return (
<span data-marker-state={state} className="relative flex items-center justify-center shrink-0">
<span className="h-2 w-2 rounded-full border border-muted-foreground/40" />
</span>
);
}