Showcase Contract
The showcase is a composition chain, not a page-by-page metadata copy:
flowchart LR Registry["registry.ts"] --> Shell["ComponentPage.svelte"] Registry --> Route["components slug +page.svelte"] Route --> Shell Route --> Demo["Demo.svelte"] DemoSource["Demo component source"] --> Raw["Vite ?raw import"] Raw --> Demo Demo --> Code["CodeBlock.svelte"]
Every Mermaid label containing . or + is quoted above; the diagram represents source relationships, not deployment state.
1. Registry authority
src/lib/showcase/registry.ts is the single source of truth for:
- route slug;
- display name;
- category and category order;
- one-line blurb;
- optional Bits UI namespace; and
- whether an entry is a utility.
bySlug supplies lookup, grouped() supplies ordered navigation groups, neighbours() supplies previous and next entries, and docsUrl() maps every showcase entry to its local wiki guide at https://wiki.bits.loca.zone/components/<slug>.
2. Shared component page
ComponentPage.svelte accepts slug, optional anatomy, optional notes, and child content. It looks up the registry entry, writes title and description metadata, renders category/name/blurb/import guidance, exposes the anatomy list, and derives previous/next navigation from registry order.
A route page supplies component-specific demos and notes; it does not duplicate the registry record.
3. Demo shell and source handoff
Demo.svelte accepts this interface:
type Props = {
title: string;
description?: string;
/** raw source of the demo component, imported with `?raw` */
src?: string;
/** extra vertical room for overlay-heavy demos */
tall?: boolean;
children: Snippet;
};The source disclosure exists only when src is truthy. Importing a raw string without passing it to Demo is not sufficient. tall adds vertical room but does not change overlay behavior.
Reference composition
This is the canonical route shape. The explicit src={basicSrc} handoff is the contract that activates the source disclosure:
<script lang="ts">
import ComponentPage from '$lib/showcase/ComponentPage.svelte';
import Demo from '$lib/showcase/Demo.svelte';
import BasicDemo from '$lib/demos/accordion/BasicDemo.svelte';
import basicSrc from '$lib/demos/accordion/BasicDemo.svelte?raw';
</script>
<ComponentPage
slug="accordion"
anatomy={[
'Accordion.Root',
'Accordion.Item',
'Accordion.Header',
'Accordion.Trigger',
'Accordion.Content'
]}
>
<Demo
title="Single"
description={'type="single" keeps at most one section open'}
src={basicSrc}
>
<BasicDemo />
</Demo>
{#snippet notes()}
<p>Document required props, value shape, form behavior, portals, CSS variables, or accessibility details here.</p>
{/snippet}
</ComponentPage>Invariants
- A component route slug must resolve in the registry.
- Registry order, not filesystem discovery, controls category navigation.
- A demo stays self-contained under
src/lib/demos/<slug>/. - Source reveal requires a
?rawimport passed throughsrc. - Component-specific, non-obvious API guidance belongs in the
notessnippet. - Primary guide URLs come from
docsUrland stay on the local wiki; upstream references are secondary links inside the generated guide. bun run generate:component-guidesderives all 46 guides, their index, and the reference catalog from this registry; never hand-maintain a parallel component list.
loca.zone · bits.loca.zone · Bits UI · Vite