Testimonial Marquee
Blocks & SlicesA wall of testimonial rows scrolling infinitely in alternating directions via a seamless two-half translateX(-50%) loop; hovering a row or tabbing onto any card pauses just that row, short rows are tiled with aria-hidden passes so the track always outruns the viewport, and cards fall back to a brand-accent initials disc when no avatar is given. Under prefers-reduced-motion it collapses to a static wrapped grid with no scroll and no duplicates.
Inspired by Cult Pro — testimonial walls (pattern) — independently built, not affiliated. Attribution policy
“We swapped three tools for this and shipped a week early.”
Mara EllisonCTO, Fieldnote “Installed one component, kept the whole registry.”
Priya RaghavanFounder, Statlight “It reads like code we wish we had written ourselves.”
Alma ReyesStaff engineer, Driftwood
“The polish out of the box is unreal. Our landing page finally feels alive.”
Devon OkaforDesign lead, Loomline “Accessibility handled by default. Our audit came back spotless.”
Jonas WeberEngineering, Kupfer “Marketing pages went from weeks to an afternoon.”
Theo LindqvistProduct, Norrsken
Installation
npx shadcn@latest add https://parable-three.vercel.app/r/testimonial-marquee.jsonRuns the shadcn CLI — the component source is copied intocomponents/parable/testimonial-marquee.tsx. You own it from there.
Usage
The exact code rendering the preview above.
<div className="w-full max-w-3xl py-2">
<TestimonialMarquee
rows={2}
speed={26}
testimonials={[
{ quote: "We swapped three tools for this and shipped a week early.", name: "Mara Ellison", role: "CTO, Fieldnote" },
{ quote: "The polish out of the box is unreal. Our landing page finally feels alive.", name: "Devon Okafor", role: "Design lead, Loomline" },
{ quote: "Installed one component, kept the whole registry.", name: "Priya Raghavan", role: "Founder, Statlight" },
{ quote: "Accessibility handled by default. Our audit came back spotless.", name: "Jonas Weber", role: "Engineering, Kupfer" },
{ quote: "It reads like code we wish we had written ourselves.", name: "Alma Reyes", role: "Staff engineer, Driftwood" },
{ quote: "Marketing pages went from weeks to an afternoon.", name: "Theo Lindqvist", role: "Product, Norrsken" },
]}
/>
</div>Props
TestimonialMarqueeProps extends React.HTMLAttributes<HTMLElement>
| Prop | Type | Default | Description |
|---|---|---|---|
| testimonials* | Testimonial[] | — | The testimonials, distributed round-robin across the rows. |
| rows | number | 2 | How many scrolling rows to render (clamped to the testimonial count). |
| speed | number | 40 | Seconds one full loop takes. Lower is faster. |