Logos Strip Stat
Original · freetrusted-by logo strip (generic marks)
Copy prompt gives Claude Code, Cursor or v0 a ready-to-paste prompt that recreates this exact component.
npx shadcn@latest add https://webinnoventix.com/r/statx-logos-strip.json"use client";
import { useId, useRef, useState } from "react";
import type { KeyboardEvent, ReactElement } from "react";
import { AnimatePresence, motion, useReducedMotion } from "motion/react";
const FILTERS = [
{ id: "all", label: "All" },
{ id: "fintech", label: "Fintech" },
{ id: "health", label: "Health" },
{ id: "logistics", label: "Logistics" },
{ id: "devtools", label: "Dev Tools" },
{ id: "commerce", label: "Commerce" },
] as const;
type FilterId = (typeof FILTERS)[number]["id"];
type Industry = Exclude<FilterId, "all">;
const INDUSTRY_LABEL: Record<Industry, string> = {
fintech: "Fintech",
health: "Health",
logistics: "Logistics",
devtools: "Dev Tools",
commerce: "Commerce",
};
interface Mark {
id: string;
name: string;
industry: Industry;
metric: string;
blurb: string;
glyph: ReactElement;
}
const svgProps = {
viewBox: "0 0 24 24",
fill: "none",
stroke: "currentColor",
strokeWidth: 1.6,
strokeLinecap: "round" as const,
strokeLinejoin: "round" as const,
"aria-hidden": true,
className: "h-6 w-6",
};
const dot = { fill: "currentColor", stroke: "none" as const };
const MARKS: Mark[] = [
{
id: "northwind",
name: "Northwind Labs",
industry: "devtools",
metric: "42% faster builds",
blurb:
"Northwind Labs moved their CI build cache to the platform and cut pipeline times by 42% across 90 repositories.",
glyph: (
<svg {...svgProps}>
<path d="M4 18 12 4l8 14z" />
<path d="M8.5 18 12 11l3.5 7" />
</svg>
),
},
{
id: "corevault",
name: "Corevault",
industry: "fintech",
metric: "SOC 2 in 6 weeks",
blurb:
"Corevault cleared its SOC 2 Type II audit in six weeks using built-in evidence collection instead of a spreadsheet.",
glyph: (
<svg {...svgProps}>
<path d="M12 3 20 6v6c0 5-3.5 7.6-8 9-4.5-1.4-8-4-8-9V6z" />
<circle cx="12" cy="11" r="3" />
</svg>
),
},
{
id: "meridian",
name: "Meridian Health",
industry: "health",
metric: "9.4M records synced",
blurb:
"Meridian Health keeps 9.4M patient records in sync across 60 clinics without a single reconciliation ticket.",
glyph: (
<svg {...svgProps}>
<circle cx="12" cy="12" r="9" />
<path d="M4 12h3.5l1.8-4 3 8 1.8-4H20" />
</svg>
),
},
{
id: "ironclad",
name: "Ironclad Freight",
industry: "logistics",
metric: "18k shipments/day",
blurb:
"Ironclad Freight routes 18,000 shipments a day through one orchestration API, replacing four legacy schedulers.",
glyph: (
<svg {...svgProps}>
<path d="M4 7.5 12 12l8-4.5" />
<path d="M4 12.5 12 17l8-4.5" />
<path d="M4 17 12 21.5 20 17" />
</svg>
),
},
{
id: "palette",
name: "Palette Studio",
industry: "commerce",
metric: "31% faster checkout",
blurb:
"Palette Studio rebuilt its storefront over a weekend and shaved 31% off checkout latency for 1.1M shoppers.",
glyph: (
<svg {...svgProps}>
<rect x="3" y="3" width="18" height="18" rx="5" />
<circle cx="9" cy="9" r="1.5" {...dot} />
<circle cx="15" cy="8.5" r="1.5" {...dot} />
<circle cx="9.5" cy="15" r="1.5" {...dot} />
</svg>
),
},
{
id: "beaconpay",
name: "Beacon Pay",
industry: "fintech",
metric: "0.02% dispute rate",
blurb:
"Beacon Pay holds a 0.02% dispute rate across 4M monthly transactions with real-time risk scoring at the edge.",
glyph: (
<svg {...svgProps}>
<circle cx="12" cy="12" r="2.4" {...dot} />
<path d="M8 16a6 6 0 0 1 0-8" />
<path d="M5 19a10 10 0 0 1 0-14" />
<path d="M16 8a6 6 0 0 1 0 8" />
<path d="M19 5a10 10 0 0 1 0 14" />
</svg>
),
},
{
id: "verdant",
name: "Verdant Bio",
industry: "health",
metric: "3x faster trials",
blurb:
"Verdant Bio onboards clinical trial sites three times faster with automated consent and eligibility flows.",
glyph: (
<svg {...svgProps}>
<path d="M5 19C5 11 11 5 19 5c0 8-6 14-14 14z" />
<path d="M9 15 16 8" />
</svg>
),
},
{
id: "cargolyn",
name: "Cargolyn",
industry: "logistics",
metric: "99.98% on-time",
blurb:
"Cargolyn maintains 99.98% on-time delivery across 38 countries on a single live map with predictive ETAs.",
glyph: (
<svg {...svgProps}>
<path d="M12 2.5 20 7v10l-8 4.5L4 17V7z" />
<path d="M4 7l8 4.5L20 7" />
<path d="M12 21.5V11.5" />
</svg>
),
},
{
id: "forgeline",
name: "Forgeline",
industry: "devtools",
metric: "1.2M deploys/mo",
blurb:
"Forgeline runs 1.2M production deploys a month with zero-downtime rollbacks turned on by default.",
glyph: (
<svg {...svgProps}>
<path d="M9 6 4 12l5 6" />
<path d="M15 6l5 6-5 6" />
<path d="M13 5 11 19" />
</svg>
),
},
{
id: "loomstack",
name: "Loomstack",
industry: "devtools",
metric: "70% less alert noise",
blurb:
"Loomstack cut on-call alert noise by 70% after unifying logs, metrics, and traces into one query surface.",
glyph: (
<svg {...svgProps}>
<rect x="4" y="10" width="3.4" height="10" rx="1.2" {...dot} />
<rect x="10.3" y="5" width="3.4" height="15" rx="1.2" {...dot} />
<rect x="16.6" y="13" width="3.4" height="7" rx="1.2" {...dot} />
</svg>
),
},
{
id: "solstice",
name: "Solstice Retail",
industry: "commerce",
metric: "2.4M peak shoppers",
blurb:
"Solstice Retail scaled to 2.4M monthly shoppers through a Black Friday peak with zero incidents.",
glyph: (
<svg {...svgProps}>
<circle cx="12" cy="12" r="4" />
<path d="M12 2.5v2.2M12 19.3v2.2M2.5 12h2.2M19.3 12h2.2M5.2 5.2l1.6 1.6M17.2 17.2l1.6 1.6M18.8 5.2l-1.6 1.6M6.8 17.2l-1.6 1.6" />
</svg>
),
},
{
id: "atlasledger",
name: "Atlas Ledger",
industry: "fintech",
metric: "Close in 2 days",
blurb:
"Atlas Ledger closes its books in two days instead of nine with continuous reconciliation across 14 entities.",
glyph: (
<svg {...svgProps}>
<path d="M6 20 12 4l6 16" />
<path d="M8.6 14h6.8" />
<path d="M4 20h16" />
</svg>
),
},
];
const STATS: { value: string; label: string }[] = [
{ value: "400+", label: "Product teams" },
{ value: "4.6B", label: "Events / month" },
{ value: "99.98%", label: "Median uptime" },
{ value: "38", label: "Countries served" },
];
const cx = (...c: (string | false | null | undefined)[]) => c.filter(Boolean).join(" ");
const focusRing =
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-indigo-500 focus-visible:ring-offset-2 focus-visible:ring-offset-white dark:focus-visible:ring-offset-zinc-950";
interface MarkCardProps {
mark: Mark;
selected: boolean;
interactive: boolean;
onSelect?: () => void;
}
function MarkCard({ mark, selected, interactive, onSelect }: MarkCardProps) {
const base =
"group flex h-16 shrink-0 select-none items-center gap-3.5 rounded-2xl border px-5 transition-colors duration-200";
const skin = selected
? "border-indigo-400/80 bg-indigo-50/70 ring-2 ring-indigo-500/30 dark:border-indigo-400/60 dark:bg-indigo-500/10"
: "border-zinc-200/80 bg-white/60 hover:border-zinc-300 hover:bg-white dark:border-zinc-800 dark:bg-zinc-900/50 dark:hover:border-zinc-700";
const glyphColor = selected
? "text-indigo-600 dark:text-indigo-400"
: "text-zinc-400 group-hover:text-zinc-900 dark:text-zinc-500 dark:group-hover:text-white";
const nameColor = selected
? "text-zinc-900 dark:text-white"
: "text-zinc-600 group-hover:text-zinc-900 dark:text-zinc-300 dark:group-hover:text-white";
const inner = (
<>
<span className={cx("flex h-9 w-9 items-center justify-center transition-colors duration-200", glyphColor)}>
{mark.glyph}
</span>
<span className="flex flex-col items-start leading-tight">
<span className={cx("text-[15px] font-semibold tracking-tight transition-colors duration-200", nameColor)}>
{mark.name}
</span>
<span className="text-[10.5px] font-medium uppercase tracking-[0.14em] text-zinc-400 dark:text-zinc-500">
{INDUSTRY_LABEL[mark.industry]}
</span>
</span>
</>
);
if (!interactive) {
return (
<div aria-hidden="true" className={cx(base, skin)}>
{inner}
</div>
);
}
return (
<button
type="button"
aria-pressed={selected}
aria-label={`${mark.name}, ${INDUSTRY_LABEL[mark.industry]}. ${selected ? "Hide" : "Show"} details.`}
onClick={onSelect}
className={cx(base, skin, focusRing, "cursor-pointer")}
>
{inner}
</button>
);
}
export default function StatxLogosStrip() {
const shouldReduce = useReducedMotion();
const reduce = shouldReduce === true;
const [active, setActive] = useState<FilterId>("all");
const [selected, setSelected] = useState<string | null>(null);
const [playing, setPlaying] = useState(true);
const filterRefs = useRef<(HTMLButtonElement | null)[]>([]);
const groupLabelId = useId();
const panelId = useId();
const visible = active === "all" ? MARKS : MARKS.filter((m) => m.industry === active);
const activeMark = MARKS.find((m) => m.id === selected) ?? null;
const activeIndex = FILTERS.findIndex((f) => f.id === active);
function pickFilter(index: number) {
const f = FILTERS[index];
setActive(f.id);
setSelected(null);
filterRefs.current[index]?.focus();
}
function onFilterKeyDown(e: KeyboardEvent<HTMLButtonElement>, index: number) {
const last = FILTERS.length - 1;
let next = index;
if (e.key === "ArrowRight" || e.key === "ArrowDown") next = index === last ? 0 : index + 1;
else if (e.key === "ArrowLeft" || e.key === "ArrowUp") next = index === 0 ? last : index - 1;
else if (e.key === "Home") next = 0;
else if (e.key === "End") next = last;
else return;
e.preventDefault();
pickFilter(next);
}
return (
<section className="relative w-full overflow-hidden bg-white text-zinc-900 dark:bg-zinc-950 dark:text-zinc-100">
<style>{`
@keyframes statx-scroll {
from { transform: translateX(0); }
to { transform: translateX(-50%); }
}
.statx-track { animation: statx-scroll 44s linear infinite; will-change: transform; }
.statx-track[data-paused="true"] { animation-play-state: paused; }
.statx-marquee:hover .statx-track,
.statx-marquee:focus-within .statx-track { animation-play-state: paused; }
@media (prefers-reduced-motion: reduce) {
.statx-track { animation: none; }
}
`}</style>
{/* atmosphere */}
<div
aria-hidden="true"
className="pointer-events-none absolute inset-x-0 top-0 h-px bg-gradient-to-r from-transparent via-zinc-300 to-transparent dark:via-zinc-700"
/>
<div
aria-hidden="true"
className="pointer-events-none absolute left-1/2 top-0 h-72 w-[42rem] -translate-x-1/2 rounded-full bg-indigo-500/[0.07] blur-3xl dark:bg-indigo-500/[0.12]"
/>
<div className="relative mx-auto max-w-6xl px-6 py-24 sm:py-28">
{/* header */}
<div className="mx-auto max-w-2xl text-center">
<span className="inline-flex items-center gap-2 rounded-full border border-zinc-200 bg-zinc-50 px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.16em] text-zinc-500 dark:border-zinc-800 dark:bg-zinc-900 dark:text-zinc-400">
<span className="relative flex h-1.5 w-1.5">
<span className="absolute inline-flex h-full w-full animate-ping rounded-full bg-emerald-400 opacity-70" />
<span className="relative inline-flex h-1.5 w-1.5 rounded-full bg-emerald-500" />
</span>
Trusted by builders
</span>
<h2 className="mt-6 text-balance text-3xl font-semibold tracking-tight text-zinc-900 sm:text-4xl dark:text-white">
The infrastructure behind 400+ product teams
</h2>
<p className="mt-4 text-pretty text-base leading-relaxed text-zinc-500 dark:text-zinc-400">
Filter by industry, then select any team to see the number that moved. Real workloads, not logos on a wall.
</p>
</div>
{/* controls */}
<div className="mt-12 flex flex-col items-center gap-5">
<div
role="radiogroup"
aria-labelledby={groupLabelId}
className="flex flex-wrap items-center justify-center gap-1.5 rounded-full border border-zinc-200 bg-zinc-50/80 p-1.5 dark:border-zinc-800 dark:bg-zinc-900/60"
>
<span id={groupLabelId} className="sr-only">
Filter teams by industry
</span>
{FILTERS.map((f, i) => {
const isActive = f.id === active;
return (
<button
key={f.id}
ref={(el) => {
filterRefs.current[i] = el;
}}
type="button"
role="radio"
aria-checked={isActive}
tabIndex={i === activeIndex ? 0 : -1}
onClick={() => pickFilter(i)}
onKeyDown={(e) => onFilterKeyDown(e, i)}
className={cx(
"relative rounded-full px-4 py-1.5 text-sm font-medium transition-colors duration-200",
focusRing,
isActive
? "text-white dark:text-zinc-900"
: "text-zinc-600 hover:text-zinc-900 dark:text-zinc-400 dark:hover:text-white",
)}
>
{isActive && (
<motion.span
layoutId="statx-pill"
className="absolute inset-0 rounded-full bg-zinc-900 shadow-sm dark:bg-white"
transition={reduce ? { duration: 0 } : { type: "spring", stiffness: 420, damping: 34 }}
/>
)}
<span className="relative z-10">{f.label}</span>
</button>
);
})}
</div>
<div className="flex items-center gap-4">
<p aria-live="polite" className="text-sm text-zinc-500 dark:text-zinc-400">
<span className="font-semibold text-zinc-900 tabular-nums dark:text-white">{visible.length}</span>{" "}
{visible.length === 1 ? "team" : "teams"}
{active !== "all" && <> in {INDUSTRY_LABEL[active as Industry]}</>}
</p>
{!reduce && (
<button
type="button"
onClick={() => setPlaying((p) => !p)}
aria-label={playing ? "Pause the scrolling logos" : "Resume the scrolling logos"}
aria-pressed={!playing}
className={cx(
"inline-flex items-center gap-2 rounded-full border border-zinc-200 bg-white px-3 py-1.5 text-xs font-medium text-zinc-600 transition-colors hover:border-zinc-300 hover:text-zinc-900 dark:border-zinc-800 dark:bg-zinc-900 dark:text-zinc-400 dark:hover:border-zinc-700 dark:hover:text-white",
focusRing,
)}
>
<svg viewBox="0 0 24 24" fill="currentColor" aria-hidden="true" className="h-3.5 w-3.5">
{playing ? <path d="M7 5h3v14H7zM14 5h3v14h-3z" /> : <path d="M8 5v14l11-7z" />}
</svg>
{playing ? "Pause" : "Play"}
</button>
)}
</div>
</div>
{/* logo strip */}
<div className="relative mt-12">
{!reduce ? (
<div className="statx-marquee relative overflow-hidden">
<div
aria-hidden="true"
className="pointer-events-none absolute inset-y-0 left-0 z-10 w-16 bg-gradient-to-r from-white to-transparent sm:w-28 dark:from-zinc-950"
/>
<div
aria-hidden="true"
className="pointer-events-none absolute inset-y-0 right-0 z-10 w-16 bg-gradient-to-l from-white to-transparent sm:w-28 dark:from-zinc-950"
/>
<ul
className="statx-track flex w-max items-center gap-4 py-2"
data-paused={!playing}
aria-label="Teams building on the platform"
>
{visible.map((m) => (
<li key={`a-${m.id}`}>
<MarkCard
mark={m}
selected={selected === m.id}
interactive
onSelect={() => setSelected((s) => (s === m.id ? null : m.id))}
/>
</li>
))}
{visible.map((m) => (
<li key={`b-${m.id}`} aria-hidden="true">
<MarkCard mark={m} selected={selected === m.id} interactive={false} />
</li>
))}
</ul>
</div>
) : (
<ul className="flex flex-wrap items-center justify-center gap-3" aria-label="Teams building on the platform">
{visible.map((m) => (
<li key={m.id}>
<MarkCard
mark={m}
selected={selected === m.id}
interactive
onSelect={() => setSelected((s) => (s === m.id ? null : m.id))}
/>
</li>
))}
</ul>
)}
</div>
{/* detail panel */}
<div className="mx-auto mt-8 min-h-[7rem] max-w-2xl">
<AnimatePresence mode="wait">
{activeMark ? (
<motion.div
key={activeMark.id}
id={panelId}
role="status"
aria-live="polite"
initial={reduce ? false : { opacity: 0, y: 10 }}
animate={{ opacity: 1, y: 0 }}
exit={reduce ? { opacity: 0 } : { opacity: 0, y: 8 }}
transition={reduce ? { duration: 0 } : { duration: 0.26, ease: [0.22, 1, 0.36, 1] }}
className="relative overflow-hidden rounded-3xl border border-zinc-200 bg-zinc-50/80 p-6 sm:p-7 dark:border-zinc-800 dark:bg-zinc-900/50"
>
<div className="flex items-start gap-5">
<span className="flex h-12 w-12 shrink-0 items-center justify-center rounded-2xl bg-white text-indigo-600 shadow-sm ring-1 ring-zinc-200 dark:bg-zinc-800 dark:text-indigo-400 dark:ring-zinc-700">
{activeMark.glyph}
</span>
<div className="min-w-0 flex-1">
<div className="flex flex-wrap items-center gap-x-3 gap-y-1">
<span className="text-base font-semibold tracking-tight text-zinc-900 dark:text-white">
{activeMark.name}
</span>
<span className="rounded-full bg-indigo-100 px-2.5 py-0.5 text-[11px] font-semibold uppercase tracking-wide text-indigo-700 dark:bg-indigo-500/15 dark:text-indigo-300">
{INDUSTRY_LABEL[activeMark.industry]}
</span>
</div>
<p className="mt-3 text-2xl font-semibold tracking-tight text-zinc-900 dark:text-white">
{activeMark.metric}
</p>
<p className="mt-2 text-sm leading-relaxed text-zinc-600 dark:text-zinc-400">{activeMark.blurb}</p>
</div>
<button
type="button"
onClick={() => setSelected(null)}
aria-label={`Dismiss details for ${activeMark.name}`}
className={cx(
"shrink-0 rounded-full p-1.5 text-zinc-400 transition-colors hover:bg-zinc-200/70 hover:text-zinc-900 dark:hover:bg-zinc-800 dark:hover:text-white",
focusRing,
)}
>
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth={1.8} aria-hidden="true" className="h-4 w-4">
<path d="M6 6l12 12M18 6 6 18" strokeLinecap="round" />
</svg>
</button>
</div>
</motion.div>
) : (
<p className="flex h-28 items-center justify-center rounded-3xl border border-dashed border-zinc-200 text-center text-sm text-zinc-400 dark:border-zinc-800 dark:text-zinc-500">
Select a team to see the number that moved.
</p>
)}
</AnimatePresence>
</div>
{/* stats */}
<dl className="mt-16 grid grid-cols-2 gap-x-6 gap-y-8 border-t border-zinc-200 pt-10 sm:grid-cols-4 dark:border-zinc-800">
{STATS.map((s) => (
<div key={s.label} className="text-center">
<dt className="sr-only">{s.label}</dt>
<dd className="text-3xl font-semibold tracking-tight text-zinc-900 tabular-nums sm:text-4xl dark:text-white">
{s.value}
</dd>
<p className="mt-1.5 text-xs font-medium uppercase tracking-[0.12em] text-zinc-400 dark:text-zinc-500">
{s.label}
</p>
</div>
))}
</dl>
</div>
</section>
);
}Dependencies
Licence
Built by Web Innoventix. Free for personal and commercial use, no attribution required.
Built by Web Innoventix
Need a custom interface, a full website, or SEO that gets you cited by AI? We design, build and rank it end to end.
Get a free quoteSimilar components
Browse all →
Four Stat Metric Band
OriginalA four-column metric band with gradient figures inside a hairline-divided card, ideal for headline numbers like uptime, latency and growth.

Labelled Stats With Dividers
OriginalThree centred stats separated by responsive dividers, each pairing a headline figure with an uppercase label and supporting detail.

Trusted By Logo Cloud
OriginalA responsive six-up logo strip using simple inline-SVG marks and wordmarks with a grayscale-to-colour hover, for a trusted-by section.

Hero Stat With Supporting Copy
OriginalA two-column layout pairing one oversized hero statistic with a supporting paragraph and a checklist card explaining the number.

Count-up stats reveal
OriginalA four-card stat band whose gradient numbers count up from zero as the section scrolls into view, with staggered blur-in cards, a pulsing eyebrow, floating aurora blobs and a shimmering underline sweep.

Animated SVG progress rings
OriginalFour circular SVG progress rings that draw their gradient arcs and count up to their target percentage the moment they enter view, over a slowly rotating conic halo with a soft glow pulse behind each ring.

Staggered stat band with marquee ticker
OriginalA dark stat band where 3D-tilt cards stagger into view with count-up figures over an animated gradient mesh, finished by an infinite marquee ticker of highlight chips that pauses on hover.

Counter Row Stat
Originalanimated counter stats row

Cards Stat
Originalstat cards with icons

Gradient Stat
Originalgradient stats band

Split Stat
Originalstats beside copy
Icons Stat
Originalicon stat grid

