FAQ accordion
Questions and answers, in one column or split beside the heading.
Installation
npx shadcn@latest add http://localhost:3000/r/faq-accordion.jsonMKT UI is not published yet, so this points at your local development server. Set NEXT_PUBLIC_REGISTRY_URL to the deployed origin to show the public command.
Also installs: accordion, container, section, section-heading.
Usage
import { FaqAccordion } from "@/components/faq-accordion";
<FaqAccordion
eyebrow="Questions"
title="Before you get in touch"
items={[
{ id: "fee", question: "Do you charge a call-out fee?", answer: "Emergency call-outs start at $149, which covers the first hour on site." },
{ id: "speed", question: "How quickly will I hear back?", answer: "Requests before 3pm on a weekday get a reply the same day." },
]}
defaultOpen={["fee"]}
footnote="Still not sure? Call us and ask."
/>Props
| Prop | Type | Default | Description |
|---|---|---|---|
| title (required) | ReactNode | — | Section heading. |
| items | FaqItem[] | — | The questions. Ignored when `categories` is supplied. |
| categories | FaqCategory[] | — | Grouped questions, for a long list that needs headings. |
| layout | "single" | "split" | "single" | `split` puts the heading in a sticky left column, which reads better past about eight questions. |
| allowMultiple | boolean | false | Let more than one answer stay open at a time. |
| defaultOpen | string[] | — | Ids to open on load. Use it for the question everyone asks. |
| footnote | ReactNode | — | Shown under the questions. |
| surface | "default" | "muted" | "brand" | "inverted" | "default" | Background treatment. |
Behaviour
Keyboard operation, focus management, and aria-expanded come from the shadcn
accordion. The client boundary lives in that component, so this section itself renders
on the server.
Collapsed text has real costs
An answer that is collapsed is not found by the browser's in-page search, and it is
not read by someone skimming. Keep the list to questions that genuinely block a
decision, and put anything a visitor must see in the page itself rather than
behind a click. Use defaultOpen for the one question everybody asks.
Categories
<FaqAccordion
title="Common questions"
layout="split"
categories={[
{ id: "pricing", title: "Pricing", items: [/* … */] },
{ id: "scheduling", title: "Scheduling", items: [/* … */] },
]}
/>Limitations
- No search or filtering within the list.
- No FAQ structured data. Add JSON-LD yourself if you want rich results, and only for questions genuinely shown on the page.