{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "typography",
  "title": "Typography",
  "description": "Long text, set to be read: it styles plain HTML by element, and punctuation hangs in the margin.",
  "dependencies": [
    "@radix-ui/react-slot"
  ],
  "registryDependencies": [
    "https://thedirectors.agency/ui/r/0nlytype.json"
  ],
  "files": [
    {
      "path": "registry/0nlytype/ui/typography.tsx",
      "content": "import * as React from \"react\"\nimport { Slot } from \"@radix-ui/react-slot\"\n\nimport { cn } from \"@/lib/utils\"\n\ntype ProseProps = React.ComponentProps<\"article\"> & {\n  /** Set the child element (a div, say) instead of rendering an article. */\n  asChild?: boolean\n  /**\n   * swiss (the default): space between paragraphs, punctuation hung in the margin. book: indents instead\n   * of space, justified, the opening line in capitals, a dinkus for a break. run-on: a passage's paragraphs\n   * run on as one block, a pilcrow where each begins.\n   */\n  variant?: \"swiss\" | \"book\" | \"run-on\"\n}\n\n/**\n * Long text, set to be read. Wrap plain HTML (headings, paragraphs, links, quotes, lists,\n * code, tables, rules) and it is styled by element, so rendered markdown needs no classes.\n */\nfunction Prose({ asChild = false, variant = \"swiss\", className, ...props }: ProseProps) {\n  const Comp = asChild ? Slot : \"article\"\n  return <Comp data-slot=\"typography\" data-variant={variant} className={cn(\"ot-prose\", className)} {...props} />\n}\n\n/** An opening paragraph, set at the lead size in ink. */\nfunction ProseLead({ className, ...props }: React.ComponentProps<\"p\">) {\n  return <p data-slot=\"typography-lead\" className={cn(\"ot-prose-lead\", className)} {...props} />\n}\n\nexport { Prose, ProseLead, type ProseProps }\n",
      "type": "registry:ui"
    },
    {
      "path": "registry/0nlytype/styles/typography.css",
      "content": "@layer components {\n  /* ── ot-prose ── long text; punctuation hangs in the margin so the edge stays true */\n  .ot-prose { max-width: var(--ot-measure); color: var(--ot-graphite); hanging-punctuation: first last; }\n  .ot-prose > * + * { margin-top: 1em; }\n  .ot-prose > * + :is(h2, h3, h4, h5, h6) { margin-top: 1.8em; }\n  .ot-prose :is(h1, h2, h3, h4, h5, h6) { font-weight: 300; color: var(--ot-ink); }\n  .ot-prose h1 { font-size: var(--ot-ff); line-height: var(--ot-ff-lh); letter-spacing: var(--ot-ff-tr); }\n  .ot-prose h2 { font-size: var(--ot-f); line-height: var(--ot-f-lh); letter-spacing: var(--ot-f-tr); }\n  .ot-prose h3 { font-size: var(--ot-mf); line-height: var(--ot-mf-lh); letter-spacing: var(--ot-mf-tr); }\n  .ot-prose :is(h4, h5, h6) { font-size: var(--ot-mp); line-height: var(--ot-mp-lh); font-weight: 500; }\n  .ot-prose-lead { font-size: var(--ot-mp); line-height: var(--ot-mp-lh); color: var(--ot-ink); text-wrap: balance; }\n  .ot-prose :is(h1, h2, h3, h4, h5, h6) { text-wrap: balance; }\n  .ot-prose :is(p, li) { text-wrap: pretty; }\n  .ot-prose blockquote { quotes: \"“\" \"”\"; font-family: var(--ot-expression); font-style: italic; font-size: calc(var(--ot-mp) * var(--ot-expression-scale)); line-height: 1.35; color: var(--ot-ink); }\n  .ot-prose blockquote > p { text-indent: -0.4em; } /* the opening mark hangs */\n  .ot-prose blockquote > p::before { content: open-quote; }\n  .ot-prose blockquote > p::after { content: close-quote; }\n  .ot-prose blockquote footer { margin-top: 0.6em; font-family: var(--ot-voice); font-style: normal; font-size: var(--ot-pp); color: var(--ot-pencil); }\n  .ot-prose ul { list-style: none; padding: 0; }\n  .ot-prose ul > li { position: relative; }\n  .ot-prose ul > li::before { content: \"–\" / \"\"; position: absolute; inset-inline-start: -1.1em; color: var(--ot-pencil); }\n  .ot-prose ol { padding: 0; padding-inline-start: 1.6em; list-style: decimal outside; } /* a number is too wide to hang: the list steps in, and the numbers stand on the edge */\n  .ot-prose ol > li::marker { color: var(--ot-pencil); font-variant-numeric: tabular-nums; }\n  .ot-prose li + li { margin-top: 0.5em; } /* half a paragraph's pause, so a long item still reads as one */\n  .ot-prose code { font-family: var(--ot-voice); font-stretch: 78%; font-weight: 500; letter-spacing: 0.01em; color: var(--ot-ink); }\n  .ot-prose small { font-size: var(--ot-pp); color: var(--ot-pencil); }\n  .ot-prose > :first-child { margin-top: 0; }\n  .ot-prose strong { font-weight: 500; color: var(--ot-ink); }\n  .ot-prose :is(em, i) { font-family: var(--ot-expression); font-style: italic; font-size: calc(var(--ot-expression-scale) * 1em); }\n  .ot-prose ul ul, .ot-prose ol ol, .ot-prose ul ol, .ot-prose ol ul { margin-top: 0.35em; }\n  .ot-prose li > ul { padding-inline-start: 1.1em; } /* a nested list steps in by its dash, so the dash hangs under its parent's words */\n  .ot-prose hr { margin-block: 2em; }\n  .ot-prose img { display: block; max-inline-size: 100%; block-size: auto; }\n  .ot-prose figcaption { margin-top: 0.6em; font-size: var(--ot-pp); line-height: var(--ot-pp-lh); color: var(--ot-pencil); }\n  .ot-prose pre {\n    tab-size: 2; white-space: pre-wrap; overflow-wrap: anywhere; /* code wraps: nothing in the page scrolls sideways */\n    font-family: var(--ot-voice); font-stretch: 88%; font-size: 0.9375em; line-height: 1.7; letter-spacing: 0.005em;\n    font-variant-numeric: tabular-nums lining-nums; color: var(--ot-graphite);\n  }\n  .ot-prose pre code { font: inherit; letter-spacing: inherit; color: inherit; }\n  .ot-prose table { width: 100%; border-collapse: collapse; font-variant-numeric: tabular-nums lining-nums; }\n  .ot-prose :is(th, td) { padding: var(--ot-space-3) var(--ot-space-4) var(--ot-space-3) 0; text-align: start; vertical-align: baseline; border-bottom: var(--ot-hairline) solid var(--ot-rule); }\n  .ot-prose :is(th, td):last-child { padding-inline-end: 0; }\n  .ot-prose th { font-weight: 400; font-size: var(--ot-pp); color: var(--ot-pencil); }\n  .ot-prose thead th { padding-top: 0; border-bottom-color: var(--ot-ink); white-space: nowrap; }\n\n  /* book: the page of a book (Tschichold's Penguin rules; Bringhurst: indent or space, never both).\n     Paragraphs follow on without a space, each indented an em and a half, the first after a heading flush;\n     justified and hyphenated; the opening line set in spaced capitals; figures old style; a section break\n     is a dinkus of three dots, not a rule. */\n  .ot-prose[data-variant=\"book\"] > p { text-align: justify; hyphens: auto; font-variant-numeric: oldstyle-nums proportional-nums; }\n  .ot-prose[data-variant=\"book\"] > p + p { margin-top: 0; text-indent: 1.5em; }\n  .ot-prose[data-variant=\"book\"] > :is(h1, h2, h3, h4, h5, h6, hr) + p::first-line,\n  .ot-prose[data-variant=\"book\"] > p:first-child::first-line { text-transform: uppercase; letter-spacing: 0.08em; font-size: 0.84em; color: var(--ot-ink); }\n  .ot-prose[data-variant=\"book\"] > :is(h1, h2, h3, h4, h5, h6) + .ot-prose-lead::first-line { text-transform: none; letter-spacing: inherit; font-size: inherit; }\n  .ot-prose[data-variant=\"book\"] > hr { height: auto; margin-block: 1.6em; background: none; text-align: center; color: var(--ot-pencil); line-height: 1; }\n  .ot-prose[data-variant=\"book\"] > hr::before { content: \"·\\2003·\\2003·\" / \"\"; font-size: var(--ot-mf); }\n  .ot-prose[data-variant=\"book\"] > blockquote { margin-inline: 1.5em; font-size: calc(var(--ot-p) * var(--ot-expression-scale)); }\n\n  /* run-on: the scribe's paragraph. The paragraphs of a passage run on as one block, and where one\n     ends a pilcrow stands in the line: the silence between paragraphs is kept as a single mark. */\n  .ot-prose[data-variant=\"run-on\"] > p:not(.ot-prose-lead) { display: inline; }\n  .ot-prose[data-variant=\"run-on\"] > p:not(.ot-prose-lead) + p:not(.ot-prose-lead)::before {\n    content: \"\\00b6\" / \"\"; margin-inline: 0.35em 0.3em;\n    font-family: var(--ot-expression); font-style: normal; font-size: calc(var(--ot-expression-scale) * 1.1em); line-height: 1; color: var(--ot-ink);\n  }\n  .ot-prose[data-variant=\"run-on\"] > :not(p):has(+ p:not(.ot-prose-lead)) { margin-bottom: 1em; } /* an inline paragraph takes no margin: what stands before it keeps the space */\n  .ot-prose[data-variant=\"run-on\"] > p:not(.ot-prose-lead) + :not(p) { margin-top: 1em; }\n  .ot-prose[data-variant=\"run-on\"] > p:not(.ot-prose-lead) + :is(h2, h3, h4, h5, h6) { margin-top: 1.8em; }\n}\n",
      "type": "registry:file",
      "target": "styles/0nlytype/typography.css"
    }
  ],
  "css": {
    "@import \"../styles/0nlytype/typography.css\"": {}
  },
  "meta": {
    "movement": "X",
    "underneath": "native",
    "contract": "ot-prose"
  },
  "type": "registry:ui"
}
