{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "page-header",
  "type": "registry:ui",
  "title": "Page Header",
  "description": "The header band at the top of admin / docs / settings pages. Carries a breadcrumb (optional), title, optional description, and a right-aligned actions slot (typically a primary CTA + an optional menu). Renders a `<header>` landmark for screen-reader…",
  "author": "ofri-peretz <https://github.com/ofri-peretz>",
  "categories": [
    "navigation",
    "pattern"
  ],
  "dependencies": [],
  "registryDependencies": [
    "https://ds.interlace.tools/r/theme.json",
    "https://ds.interlace.tools/r/cn.json",
    "https://ds.interlace.tools/r/skeleton.json",
    "https://ds.interlace.tools/r/stack.json",
    "https://ds.interlace.tools/r/typography.json"
  ],
  "files": [
    {
      "path": "registry/interlace-ui/patterns/page-header.tsx",
      "target": "components/ui/patterns/page-header.tsx",
      "type": "registry:ui",
      "content": "import * as React from 'react';\n\n// @interlace/page-header v1.1.0 — Interlace design system.\n// Docs, props and live preview: https://ds.interlace.tools/c/page-header\n// What changed since: https://ds.interlace.tools/c/page-header#history\n// Generated banner — keep it, the upgrade diff reads this version.\n\n/**\n * @interlace/ui — PageHeader\n *\n * The header band at the top of admin / docs / settings pages. Carries a\n * breadcrumb (optional), title, optional description, and a right-aligned\n * actions slot (typically a primary CTA + an optional menu). Renders a\n * `<header>` landmark for screen-reader navigation.\n *\n * ## Anatomy\n *\n *   PageHeader                       (header — data-min-viewport=480)\n *     ├─ {breadcrumb}                (optional — Breadcrumb primitive)\n *     ├─ <div>                       (title row — flex justify-between)\n *     │   ├─ Stack                   (left column)\n *     │   │   ├─ Typography h1       (title)\n *     │   │   └─ Typography body     (description — optional)\n *     │   └─ {actions}               (right column — Cluster of Buttons)\n *     └─ {meta}                      (optional — tags / status / dates row)\n *\n * ## MIN_VIEWPORT — 480\n *\n * Page headers expect a breadcrumb + title + actions row, which doesn't fit\n * cleanly below the iPhone-mini-portrait floor; the actions stack vertically\n * below, but the meta strip + breadcrumb crowd the title. Reach for a simpler\n * title-only header on narrower phones.\n *\n * | Rule | Concept                          | Where in this file                                          |\n * | ---- | -------------------------------- | ----------------------------------------------------------- |\n * | R4   | Extends native <header>          | `React.ComponentProps<'header'> & PageHeaderProps`          |\n * | R6   | data-slot on root                | `data-slot=\"page-header\"`                                   |\n * | R10  | Composition seams                | `breadcrumb` + `actions` + `meta` props                     |\n * | R14  | Declares min viewport            | `data-min-viewport={String(MIN_VIEWPORT)}` + exported const |\n * | R19  | Tokens only                      | border/spacing/typography from primitives                   |\n * | R25  | Server component                 | No hooks → no `'use client'`                                |\n * | R26  | A11y landmark                    | `<header>` is the rendered element                          |\n */\n\nimport { cn } from '@/lib/utils';\nimport { Skeleton } from '@/components/ui/skeleton';\nimport { Stack } from '@/components/ui/stack';\nimport { Typography } from '@/components/ui/typography';\n\nexport const MIN_VIEWPORT = 480 as const;\n\ntype PageHeaderProps = React.ComponentProps<'header'> & {\n  title?: React.ReactNode;\n  description?: React.ReactNode;\n  /** Optional <Breadcrumb> above the title. */\n  breadcrumb?: React.ReactNode;\n  /** Optional right-aligned actions cluster — typically Buttons. */\n  actions?: React.ReactNode;\n  /** Optional meta strip below the title — tags / status / dates. */\n  meta?: React.ReactNode;\n  /** When true, render a `<Skeleton variant=\"page-header\" />` placeholder. */\n  loading?: boolean;\n};\n\nexport function PageHeader({\n  className,\n  title,\n  description,\n  breadcrumb,\n  actions,\n  meta,\n  loading,\n  ...props\n}: PageHeaderProps) {\n  if (loading) {\n    return (\n      <Skeleton\n        variant=\"page-header\"\n        data-slot=\"page-header\"\n        data-min-viewport={String(MIN_VIEWPORT)}\n        className={className}\n      />\n    );\n  }\n  return (\n    <header\n      data-slot=\"page-header\"\n      data-min-viewport={String(MIN_VIEWPORT)}\n      className={cn('border-border w-full border-b pb-6', className)}\n      {...props}\n    >\n      <Stack gap=\"md\">\n        {breadcrumb ? <div>{breadcrumb}</div> : null}\n        <div className=\"flex flex-col items-start justify-between gap-4 sm:flex-row sm:items-end\">\n          <div className=\"min-w-0 flex-1\">\n            <Typography as=\"h1\" variant=\"h1\">\n              {title}\n            </Typography>\n            {description ? (\n              <Typography variant=\"body\" tone=\"muted\" className=\"mt-2\">\n                {description}\n              </Typography>\n            ) : null}\n          </div>\n          {actions ? (\n            <div className=\"flex flex-shrink-0 flex-wrap items-center gap-2\">\n              {actions}\n            </div>\n          ) : null}\n        </div>\n        {meta ? (\n          <div className=\"text-muted-foreground flex flex-wrap items-center gap-3 text-sm\">\n            {meta}\n          </div>\n        ) : null}\n      </Stack>\n    </header>\n  );\n}\n"
    }
  ],
  "meta": {
    "tier": "pattern",
    "client": false,
    "minViewport": 480,
    "loading": true,
    "version": "1.1.0",
    "since": "1.0.0"
  },
  "docs": "## @interlace/page-header\n\nInstalled to `components/ui/patterns/page-header.tsx`.\n\n```tsx\nimport { /* … */ } from '@/components/ui/patterns/page-header';\n```\n\nProps, a11y contract, live preview and source: https://ds.interlace.tools/c/page-header\n\nRequires the `@interlace/theme` CSS baseline (installed automatically as a registry dependency)."
}
