A workflow that states one trigger on an inverted full-width panel, then forks into two equally weighted condition branches whose outcomes sit in nested cards carrying the share of cases they account for.
A workflow that states one trigger on an inverted full-width panel, then forks into two equally weighted condition branches whose outcomes sit in nested cards carrying the share of cases they account for.
Upgrade to Pro
Pro blocks install through the shadcn CLI with your license key and ship their full source. Docs and live previews stay open to everyone, so you can read every block's details first.
Swap YOUR_EMAIL and YOUR_KEY for the email and license key on your account. Find your license key on your account page.
Radix flavor
npx shadcn add "https://ui.beste.co/r/workflow49?email=YOUR_EMAIL&license_key=YOUR_KEY"Base UI flavor
npx shadcn add "https://ui.beste.co/r-base/workflow49?email=YOUR_EMAIL&license_key=YOUR_KEY"This installs the block to components/beste/block/workflow49.tsx plus the badge23 and button21 components it uses for the eyebrow and the closing action.
The installed file exports workflow49Demo alongside the block: the exact props behind the preview above. Spread it to get a working flow in one line.
import { Workflow49, workflow49Demo } from "@/components/beste/block/workflow49";
export default function FlowPage() {
return <Workflow49 {...workflow49Demo} />;
}Then replace the demo with your own props. Written out, a trimmed setup looks like this:
import { Workflow49 } from "@/components/beste/block/workflow49";
export default function FlowPage() {
return (
<Workflow49
badge={{ label: "What happens next" }}
heading="A cancellation takes one of two paths, and neither needs a phone call"
description="This is the whole decision. There is no third branch."
triggerLabel="The trigger"
triggerTitle="A member cancels an appointment"
triggerDetail="From their own reminder link, at any hour. The slot is released the moment they confirm."
branches={[
{
condition: "If somebody is waiting",
title: "The slot is offered down the list",
description: "Everyone whose preferences match is offered it at once, in join order.",
outcomes: [
{
title: "Filled without anyone acting",
description: "Median eleven minutes from cancellation to a new confirmed booking.",
share: "84% of cancellations",
},
],
},
{
condition: "If the list is empty",
title: "The hour goes back to the rota",
description: "The slot is released as bookable capacity and the clinician is told.",
outcomes: [
{
title: "Booked by a new member",
description: "Picked up through the public booking page, usually within a day.",
share: "7% of cancellations",
},
],
},
]}
closing="Reception sees all of it happening and can step in at any point."
button={{ label: "See the waiting list rules", href: "/product/waiting-list" }}
/>
);
}| Prop | Type | Default | Description |
|---|---|---|---|
badge | { label: string } | – | Eyebrow above the hairline rule, rendered through Badge23 |
heading | string | – | Section heading in the left column of the header |
description | string | – | Supporting paragraph, right-aligned from md up |
triggerLabel | string | – | Small label on the inverted panel |
triggerTitle | string | – | What starts the flow, set at display scale |
triggerDetail | string | – | Supporting detail, right-aligned on the panel |
branches | Branch[] | [] | The paths the flow can take |
closing | string | – | Paragraph beside the closing action |
button | { label: string; href: string } | – | Outline closing action |
className | string | – | Extra classes for the outer section |
type ActionLink = {
label: string;
href: string;
};
type Outcome = {
title: string;
description: string;
share: string;
};
type Branch = {
condition: string;
title: string;
description: string;
outcomes: Outcome[];
};bg-muted surface, because a decision tree that visually favours one path is arguing rather than describing.bg-foreground panel and the branches are muted, with a mt-4 gap chaining them. There is no connector line.background text tokens, since its surface is fixed.auto-rows-fr inside their grid, so every nested card in a branch is the same height even when one description wraps to two lines and another does not.mt-auto, so the cards align along the bottom of both branch cards regardless of how long each branch's own description is.md up, with md:shrink-0 keeping it on one line so the title wraps instead.share is free text, so it can carry a percentage, a count, or a phrase.workflow26
Horizontal connected process steps with numbered nodes on a continuous rail.
workflow54
An integration map naming every system as a card, inverting the first-party one so it reads as the origin, then listing each crossing on a hairline row with what travels and how often.
workflow48
An approval workflow drawn as a vertical rail of nodes tinted by whether each step is done, waiting, or queued, naming the person and the timestamp, beside a tile floating the live request card.
workflow12
Hero with a full canvas on the right showing a real workflow flow: trigger node, condition node, and two action branches connected with lines.