/* Rinx Default Theme
 * A modern, premium documentation theme for Rinx.
 */

@import url('https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&family=Outfit:wght@600;700&family=JetBrains+Mono:wght@400;500&display=swap');

:root {
  --primary: #2563eb;
  --primary-hover: #1d4ed8;
  --bg-main: #ffffff;
  --bg-sidebar: #f8fafc;
  --text-main: #1e293b;
  --text-muted: #64748b;
  --text-header: #0f172a;
  --border: #e2e8f0;
  --sidebar-width: 280px;
  --radius: 8px;
  --shadow-sm: 0 1px 2px 0 rgb(0 0 0 / 0.05);
  --shadow: 0 1px 3px 0 rgb(0 0 0 / 0.1), 0 1px 2px -1px rgb(0 0 0 / 0.1);
}

/* ── Reset & Base ──────────────────────────────────────────────────── */

*, *::before, *::after {
  box-sizing: border-box;
  margin: 0;
  padding: 0;
}

html {
  font-size: 16px;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  scroll-behavior: smooth;
}

body {
  font-family: 'Inter', system-ui, -apple-system, sans-serif;
  color: var(--text-main);
  background: var(--bg-main);
}

hr {
  border: none;
  border-top: 1px solid var(--border);
  margin: 2rem 0;
}

/* ── Layout ────────────────────────────────────────────────────────── */

.document-wrapper {
  display: flex;
  min-height: 100vh;
}

/* ── Sidebar ───────────────────────────────────────────────────────── */

.sidebar {
  width: var(--sidebar-width);
  flex-shrink: 0;
  padding: 2rem 1.5rem;
  background: var(--bg-sidebar);
  border-right: 1px solid var(--border);
  position: sticky;
  top: 0;
  height: 100vh;
  overflow-y: auto;
  transition: all 0.3s ease;
}

.sidebar-header {
  margin-bottom: 2rem;
  padding-bottom: 1.5rem;
  border-bottom: 1px solid var(--border);
}

.project-name {
  font-family: 'Outfit', sans-serif;
  font-size: 1.4rem;
  font-weight: 700;
  color: var(--text-header);
  background: linear-gradient(135deg, #1e293b 0%, #334155 100%);
  -webkit-background-clip: text;
  -webkit-text-fill-color: transparent;
  margin: 0;
}

.project-version {
  display: inline-block;
  font-size: 0.75rem;
  font-weight: 600;
  color: var(--primary);
  background: #eff6ff;
  padding: 0.1rem 0.5rem;
  border-radius: 9999px;
  margin-top: 0.5rem;
  border: 1px solid #dbeafe;
}

.sidebar-nav ul {
  list-style: none;
  padding: 0;
  margin: 0;
}

.sidebar-nav ul ul {
  padding-left: 1.25rem;
  margin-top: 0.25rem;
  border-left: 1px solid var(--border);
}

.sidebar-nav li {
  margin: 0.25rem 0;
}

.sidebar-nav a {
  display: block;
  padding: 0.4rem 0.75rem;
  color: var(--text-muted);
  text-decoration: none;
  font-size: 0.925rem;
  font-weight: 500;
  border-radius: var(--radius);
  transition: all 0.2s cubic-bezier(0.4, 0, 0.2, 1);
}

.sidebar-nav a:hover {
  background: #f1f5f9;
  color: var(--primary);
  transform: translateX(2px);
}

.sidebar-placeholder {
  color: var(--text-muted);
  font-size: 0.9rem;
  font-style: italic;
  padding: 1rem;
  background: #f1f5f9;
  border-radius: var(--radius);
  text-align: center;
}

/* ── Main Content ──────────────────────────────────────────────────── */

.document {
  flex: 1;
  max-width: 64rem;
  padding: 4rem 5rem;
  margin: 0 auto;
}

.document h1 {
  font-family: 'Outfit', sans-serif;
  font-size: 2.5rem;
  font-weight: 700;
  color: var(--text-header);
  margin-bottom: 2rem;
  letter-spacing: -0.025em;
  line-height: 1.2;
}

.document h2 {
  font-family: 'Outfit', sans-serif;
  font-size: 1.75rem;
  font-weight: 600;
  color: var(--text-header);
  margin-top: 3rem;
  margin-bottom: 1.25rem;
  padding-bottom: 0.5rem;
  border-bottom: 1px solid var(--border);
}

.document h3 {
  font-size: 1.5rem;
  margin-top: 2.5rem;
  margin-bottom: 1rem;
}

.document p {
  margin-bottom: 1.25rem;
  color: #334155;
  font-size: 1.05rem;
}

.document a {
  color: var(--primary);
  text-decoration: none;
  border-bottom: 1px solid transparent;
  transition: border-color 0.2s;
}

.document a:hover {
  border-bottom-color: var(--primary);
}

.document ul, .document ol {
  margin-bottom: 1.5rem;
  padding-left: 2rem;
}

.document li {
  margin-bottom: 0.5rem;
}

/* Enumerated lists carry two classes: the enumeration sequence and the
   punctuation format. The sequence picks the glyphs. */
.document ol.arabic { list-style-type: decimal; }
.document ol.loweralpha { list-style-type: lower-alpha; }
.document ol.upperalpha { list-style-type: upper-alpha; }
.document ol.lowerroman { list-style-type: lower-roman; }
.document ol.upperroman { list-style-type: upper-roman; }

/* The period format is what a browser's own marker already renders, so only
   the two parenthesised formats need counters. Sphinx drops the punctuation
   entirely, rendering `(a)` and `a.` identically; these rules are what keep
   the author's own notation visible. The `counter-reset` seeding a list that
   does not start at 1 is emitted inline by the renderer. */
.document ol.rparen,
.document ol.parens {
  list-style: none;
  counter-reset: rsl;
  padding-left: 3rem;
}

.document ol.rparen > li,
.document ol.parens > li {
  position: relative;
  counter-increment: rsl;
}

/* Absolutely positioned so the marker leaves the item's normal flow. An item's
   content is a block `<p>`, so an in-flow marker — however it is displayed —
   would push that block onto the next line. `right: 100%` puts the marker's
   right edge at the content edge, which right-aligns markers of any width
   without reserving a fixed one; leaving `top` unset keeps the marker on the
   static position, level with the first line of text. */
.document ol.rparen > li::before,
.document ol.parens > li::before {
  position: absolute;
  right: 100%;
  margin-right: 0.4rem;
  white-space: nowrap;
}

.document ol.arabic.rparen > li::before { content: counter(rsl, decimal) ")"; }
.document ol.loweralpha.rparen > li::before { content: counter(rsl, lower-alpha) ")"; }
.document ol.upperalpha.rparen > li::before { content: counter(rsl, upper-alpha) ")"; }
.document ol.lowerroman.rparen > li::before { content: counter(rsl, lower-roman) ")"; }
.document ol.upperroman.rparen > li::before { content: counter(rsl, upper-roman) ")"; }

.document ol.arabic.parens > li::before { content: "(" counter(rsl, decimal) ")"; }
.document ol.loweralpha.parens > li::before { content: "(" counter(rsl, lower-alpha) ")"; }
.document ol.upperalpha.parens > li::before { content: "(" counter(rsl, upper-alpha) ")"; }
.document ol.lowerroman.parens > li::before { content: "(" counter(rsl, lower-roman) ")"; }
.document ol.upperroman.parens > li::before { content: "(" counter(rsl, upper-roman) ")"; }

.document code {
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.9em;
  background: #f1f5f9;
  color: #0f172a;
  padding: 0.2em 0.4em;
  border-radius: 4px;
  border: 1px solid var(--border);
}

.document pre {
  background: #0f172a;
  color: #f8fafc;
  padding: 1.5rem;
  border-radius: var(--radius);
  overflow-x: auto;
  margin-bottom: 1.5rem;
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.9rem;
  line-height: 1.6;
  box-shadow: var(--shadow);
}

/* Reset inline code styles inside literal blocks */
.document pre > code {
  background: none;
  color: inherit;
  padding: 0;
  border: none;
  border-radius: 0;
  font-size: inherit;
}

/* ── Syntax highlighting ───────────────────────────────────────────── */

/* The wrapper a `.. code-block::` renders; `.highlight` is the `<pre>`'s own
   parent, matching the shape Sphinx emits so page-level rules can target
   either the block or just its code. */
.document div[class^="highlight-"] {
  margin-bottom: 1.5rem;
}

.document div[class^="highlight-"] pre {
  margin-bottom: 0;
}

/* The generated theme owns the code area's palette (it styles `.hl-code`),
   so the generic `.document pre` colours step aside inside a highlighted
   block. Without this the two disagree: tokens the theme colours would sit
   on its background while tokens it leaves alone kept the page's. */
.document .highlight.hl-code {
  border-radius: var(--radius);
  overflow-x: auto;
  margin-bottom: 1.5rem;
  box-shadow: var(--shadow);
}

.document .highlight.hl-code > pre {
  background: transparent;
  color: inherit;
  box-shadow: none;
  border-radius: 0;
  margin-bottom: 0;
  overflow-x: visible;
}

.document .code-block-caption {
  font-size: 0.85rem;
  font-weight: 600;
  color: var(--text-muted);
  padding: 0.5rem 0.75rem;
  border-bottom: 1px solid var(--border);
}

/* `:linenos:` — a non-selectable gutter, so copying a block copies the code
   and not the numbers with it. */
.document .linenos {
  display: inline-block;
  width: 2.5em;
  margin-right: 1em;
  text-align: right;
  color: #65737e;
  user-select: none;
  -webkit-user-select: none;
}

/* `:emphasize-lines:` — a band across the full width of the block, which is
   why the newline is emitted inside the span rather than after it. */
.document .hll {
  display: block;
  background: #3b4252;
  margin: 0 -1.5rem;
  padding: 0 1.5rem;
}

/* Token colours below are GENERATED — do not edit by hand.
   They come from `css_for_theme_with_class_style` over the theme named by
   `crates/renderer/src/highlight.rs`'s `THEME`, using the same `ClassStyle`
   the renderer emits its classes with, so the two cannot disagree about what
   a token is called. `css_drift_test` regenerates them and fails if this
   block has gone stale. To change the palette, change `THEME` and copy the
   test's expected output back in here. */
/* ── BEGIN generated syntax-highlighting theme ─────────────────────── */
/*
 * theme "Base16 Ocean Dark" generated by syntect
 */

.hl-code {
 color: #c0c5ce;
 background-color: #2b303b;
}

.hl-variable.hl-parameter.hl-function {
 color: #c0c5ce;
}
.hl-comment, .hl-punctuation.hl-definition.hl-comment {
 color: #65737e;
}
.hl-punctuation.hl-definition.hl-string, .hl-punctuation.hl-definition.hl-variable, .hl-punctuation.hl-definition.hl-string, .hl-punctuation.hl-definition.hl-parameters, .hl-punctuation.hl-definition.hl-string, .hl-punctuation.hl-definition.hl-array {
 color: #c0c5ce;
}
.hl-none {
 color: #c0c5ce;
}
.hl-keyword.hl-operator {
 color: #c0c5ce;
}
.hl-keyword {
 color: #b48ead;
}
.hl-variable, .hl-variable.hl-other.hl-dollar.hl-only.hl-js {
 color: #bf616a;
}
.hl-entity.hl-name.hl-function, .hl-meta.hl-require, .hl-support.hl-function.hl-any-method, .hl-variable.hl-function {
 color: #8fa1b3;
}
.hl-support.hl-class, .hl-entity.hl-name.hl-class, .hl-entity.hl-name.hl-type.hl-class {
 color: #ebcb8b;
}
.hl-meta.hl-class {
 color: #eff1f5;
}
.hl-keyword.hl-other.hl-special-method {
 color: #8fa1b3;
}
.hl-storage {
 color: #b48ead;
}
.hl-support.hl-function {
 color: #96b5b4;
}
.hl-string, .hl-constant.hl-other.hl-symbol, .hl-entity.hl-other.hl-inherited-class {
 color: #a3be8c;
}
.hl-constant.hl-numeric {
 color: #d08770;
}
.hl-none {
 color: #d08770;
}
.hl-none {
 color: #d08770;
}
.hl-constant {
 color: #d08770;
}
.hl-entity.hl-name.hl-tag {
 color: #bf616a;
}
.hl-entity.hl-other.hl-attribute-name {
 color: #d08770;
}
.hl-entity.hl-other.hl-attribute-name.hl-id, .hl-punctuation.hl-definition.hl-entity {
 color: #8fa1b3;
}
.hl-meta.hl-selector {
 color: #b48ead;
}
.hl-none {
 color: #d08770;
}
.hl-markup.hl-heading .hl-punctuation.hl-definition.hl-heading, .hl-entity.hl-name.hl-section {
 color: #8fa1b3;
}
.hl-keyword.hl-other.hl-unit {
 color: #d08770;
}
.hl-markup.hl-bold, .hl-punctuation.hl-definition.hl-bold {
 color: #ebcb8b;
font-weight: bold;
}
.hl-markup.hl-italic, .hl-punctuation.hl-definition.hl-italic {
 color: #b48ead;
font-style: italic;
}
.hl-markup.hl-raw.hl-inline {
 color: #a3be8c;
}
.hl-string.hl-other.hl-link {
 color: #bf616a;
}
.hl-meta.hl-link {
 color: #d08770;
}
.hl-meta.hl-image {
 color: #d08770;
}
.hl-markup.hl-list {
 color: #bf616a;
}
.hl-markup.hl-quote {
 color: #d08770;
}
.hl-meta.hl-separator {
 color: #c0c5ce;
 background-color: #4f5b66;
}
.hl-markup.hl-inserted, .hl-markup.hl-inserted.hl-git_gutter {
 color: #a3be8c;
}
.hl-markup.hl-deleted, .hl-markup.hl-deleted.hl-git_gutter {
 color: #bf616a;
}
.hl-markup.hl-changed, .hl-markup.hl-changed.hl-git_gutter {
 color: #b48ead;
}
.hl-markup.hl-ignored, .hl-markup.hl-ignored.hl-git_gutter {
 color: #4f5b66;
}
.hl-markup.hl-untracked, .hl-markup.hl-untracked.hl-git_gutter {
 color: #4f5b66;
}
.hl-constant.hl-other.hl-color {
 color: #96b5b4;
}
.hl-string.hl-regexp {
 color: #96b5b4;
}
.hl-constant.hl-character.hl-escape {
 color: #96b5b4;
}
.hl-punctuation.hl-section.hl-embedded, .hl-variable.hl-interpolation {
 color: #ab7967;
}
.hl-invalid.hl-illegal {
 color: #2b303b;
 background-color: #bf616a;
}
.hl-markup.hl-deleted.hl-git_gutter {
 color: #f92672;
}
.hl-markup.hl-inserted.hl-git_gutter {
 color: #a6e22e;
}
.hl-markup.hl-changed.hl-git_gutter {
 color: #967efb;
}
.hl-markup.hl-ignored.hl-git_gutter {
 color: #565656;
}
.hl-markup.hl-untracked.hl-git_gutter {
 color: #565656;
}
/* ── END generated syntax-highlighting theme ───────────────────────── */

/* ── Admonitions ───────────────────────────────────────────────────── */

.admonition {
  margin: 2rem 0;
  padding: 1.25rem 1.5rem;
  border-radius: var(--radius);
  border-left: 5px solid var(--border);
  background: var(--bg-sidebar);
  box-shadow: var(--shadow-sm);
}

.admonition-title {
  margin: 0 0 0.75rem 0;
  font-weight: 700;
  font-size: 1.1rem;
  display: flex;
  align-items: center;
  color: var(--text-header);
}

.admonition.note { border-left-color: #3b82f6; background: #eff6ff; }
.admonition.warning { border-left-color: #eab308; background: #fefce8; }
.admonition.danger { border-left-color: #ef4444; background: #fef2f2; }
.admonition.tip { border-left-color: #22c55e; background: #f0fdf4; }
.admonition.important { border-left-color: #a855f7; background: #faf5ff; }
.admonition.caution { border-left-color: #f97316; background: #fff7ed; }
.admonition.seealso { border-left-color: #06b6d4; background: #ecfeff; }

details.admonition summary {
  cursor: pointer;
  outline: none;
  list-style: none;
  font-weight: 700;
  font-size: 1.1rem;
  color: var(--text-header);
}

details.admonition summary::-webkit-details-marker { display: none; }

details.admonition summary::before {
  content: '▶';
  display: inline-block;
  margin-right: 0.75rem;
  transition: transform 0.2s;
  font-size: 0.8rem;
  color: var(--text-muted);
}

details.admonition[open] summary::before {
  transform: rotate(90deg);
}

details.admonition[open] summary {
  border-bottom: 1px solid rgba(0,0,0,0.05);
  padding-bottom: 0.5rem;
  margin-bottom: 1rem;
}

/* ── Dropdowns (sphinx-design's `.. dropdown::`) ────────────────────── */

/* The class names below are sphinx-design's, so a page written for that
   extension keeps its structure here; the rules themselves are this build's
   own — sphinx-design's stylesheet is not vendored. */

.sd-dropdown {
  margin: 1.5rem 0;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  background: var(--bg-sidebar);
  box-shadow: var(--shadow-sm);
  overflow: hidden;
}

.sd-dropdown > .sd-summary-title {
  display: flex;
  align-items: center;
  gap: 0.6rem;
  cursor: pointer;
  outline: none;
  list-style: none;
  padding: 0.85rem 1.25rem;
  font-weight: 700;
  color: var(--text-header);
}

.sd-dropdown > .sd-summary-title::-webkit-details-marker { display: none; }

.sd-summary-text { flex: 1 1 auto; }

.sd-summary-icon,
.sd-summary-state-marker {
  display: inline-flex;
  align-items: center;
  flex: 0 0 auto;
}

/* The marker is the *closed* half of the chevron pair; opening rotates it,
   which is why only one icon is ever embedded. */
.sd-summary-state-marker {
  color: var(--text-muted);
  transition: transform 0.2s;
}

.sd-dropdown[open] > .sd-summary-title > .sd-summary-chevron-right {
  transform: rotate(90deg);
}

.sd-dropdown[open] > .sd-summary-title > .sd-summary-chevron-down {
  transform: rotate(180deg);
}

.sd-summary-content {
  padding: 1rem 1.25rem 1.25rem;
  border-top: 1px solid var(--border);
}

.sd-card-text:first-child { margin-top: 0; }
.sd-card-text:last-child { margin-bottom: 0; }

/* `:color:` — the eleven semantic colours, each a background/foreground pair. */
.sd-bg-primary { background: #0d6efd; }
.sd-bg-secondary { background: #6c757d; }
.sd-bg-success { background: #198754; }
.sd-bg-info { background: #0dcaf0; }
.sd-bg-warning { background: #ffc107; }
.sd-bg-danger { background: #dc3545; }
.sd-bg-light { background: #f8f9fa; }
.sd-bg-muted { background: #6c757d; }
.sd-bg-dark { background: #212529; }
.sd-bg-white { background: #ffffff; }
.sd-bg-black { background: #000000; }

/* Scoped to the summary they were written for: sphinx-design puts the pair on
   one element, and an unscoped `.sd-bg-text-*` would recolour anything else
   that happened to carry the class. */
.sd-dropdown > .sd-bg-text-primary,
.sd-dropdown > .sd-bg-text-secondary,
.sd-dropdown > .sd-bg-text-success,
.sd-dropdown > .sd-bg-text-danger,
.sd-dropdown > .sd-bg-text-muted,
.sd-dropdown > .sd-bg-text-dark,
.sd-dropdown > .sd-bg-text-black { color: #ffffff; }

.sd-dropdown > .sd-bg-text-info,
.sd-dropdown > .sd-bg-text-warning,
.sd-dropdown > .sd-bg-text-light,
.sd-dropdown > .sd-bg-text-white { color: #212529; }

/* On a painted bar the marker takes the title's colour; left to its own muted
   grey it disappears into a dark background. */
.sd-dropdown > [class*="sd-bg-"] .sd-summary-state-marker { color: inherit; }

/* `:margin:` — one step per side on sphinx-design's 0-5 spacing scale. */
.sd-m-0 { margin: 0; }
.sd-m-1 { margin: 0.25rem; }
.sd-m-2 { margin: 0.5rem; }
.sd-m-3 { margin: 1rem; }
.sd-m-4 { margin: 1.5rem; }
.sd-m-5 { margin: 3rem; }
.sd-m-auto { margin: auto; }

.sd-mt-0 { margin-top: 0; }
.sd-mt-1 { margin-top: 0.25rem; }
.sd-mt-2 { margin-top: 0.5rem; }
.sd-mt-3 { margin-top: 1rem; }
.sd-mt-4 { margin-top: 1.5rem; }
.sd-mt-5 { margin-top: 3rem; }
.sd-mt-auto { margin-top: auto; }

.sd-mb-0 { margin-bottom: 0; }
.sd-mb-1 { margin-bottom: 0.25rem; }
.sd-mb-2 { margin-bottom: 0.5rem; }
.sd-mb-3 { margin-bottom: 1rem; }
.sd-mb-4 { margin-bottom: 1.5rem; }
.sd-mb-5 { margin-bottom: 3rem; }
.sd-mb-auto { margin-bottom: auto; }

.sd-ml-0 { margin-left: 0; }
.sd-ml-1 { margin-left: 0.25rem; }
.sd-ml-2 { margin-left: 0.5rem; }
.sd-ml-3 { margin-left: 1rem; }
.sd-ml-4 { margin-left: 1.5rem; }
.sd-ml-5 { margin-left: 3rem; }
.sd-ml-auto { margin-left: auto; }

.sd-mr-0 { margin-right: 0; }
.sd-mr-1 { margin-right: 0.25rem; }
.sd-mr-2 { margin-right: 0.5rem; }
.sd-mr-3 { margin-right: 1rem; }
.sd-mr-4 { margin-right: 1.5rem; }
.sd-mr-5 { margin-right: 3rem; }
.sd-mr-auto { margin-right: auto; }

/* `:padding:` — the same 0-5 scale as `:margin:` above, inside the box
   rather than around it. `auto` is deliberately absent: sphinx-design's
   `padding_option` leaves it off the scale, and the parser refuses it. */
.sd-p-0 { padding: 0; }
.sd-p-1 { padding: 0.25rem; }
.sd-p-2 { padding: 0.5rem; }
.sd-p-3 { padding: 1rem; }
.sd-p-4 { padding: 1.5rem; }
.sd-p-5 { padding: 3rem; }

.sd-pt-0 { padding-top: 0; }
.sd-pt-1 { padding-top: 0.25rem; }
.sd-pt-2 { padding-top: 0.5rem; }
.sd-pt-3 { padding-top: 1rem; }
.sd-pt-4 { padding-top: 1.5rem; }
.sd-pt-5 { padding-top: 3rem; }

.sd-pb-0 { padding-bottom: 0; }
.sd-pb-1 { padding-bottom: 0.25rem; }
.sd-pb-2 { padding-bottom: 0.5rem; }
.sd-pb-3 { padding-bottom: 1rem; }
.sd-pb-4 { padding-bottom: 1.5rem; }
.sd-pb-5 { padding-bottom: 3rem; }

.sd-pl-0 { padding-left: 0; }
.sd-pl-1 { padding-left: 0.25rem; }
.sd-pl-2 { padding-left: 0.5rem; }
.sd-pl-3 { padding-left: 1rem; }
.sd-pl-4 { padding-left: 1.5rem; }
.sd-pl-5 { padding-left: 3rem; }

.sd-pr-0 { padding-right: 0; }
.sd-pr-1 { padding-right: 0.25rem; }
.sd-pr-2 { padding-right: 0.5rem; }
.sd-pr-3 { padding-right: 1rem; }
.sd-pr-4 { padding-right: 1.5rem; }
.sd-pr-5 { padding-right: 3rem; }

/* ── Buttons (sphinx-design's `.. button-link::`) ────────────────────── */

/* The class names below are sphinx-design's, so a page written for that
   extension keeps its structure here; the rules themselves are this build's
   own. The eleven `:color:` values reuse the palette the dropdown section
   above defines, as `sd-btn-<name>` fills and `sd-btn-outline-<name>`
   borders. */

.sd-btn {
  display: inline-block;
  padding: 0.375rem 0.85rem;
  border: 1px solid transparent;
  border-radius: var(--radius);
  font-size: 0.95rem;
  line-height: 1.5;
  text-align: center;
  text-decoration: none;
  cursor: pointer;
  color: var(--text);
  background: var(--bg-sidebar);
  border-color: var(--border);
  transition: filter 0.15s ease-in-out;
}

.sd-btn:hover { filter: brightness(0.94); text-decoration: none; }

/* `:expand:` — the button fills the width its container offers. The wrapper
   is what carries the width, so the button itself only has to fill it. */
.sd-d-grid { display: grid; }
.sd-d-grid > .sd-btn { width: 100%; }

/* `:shadow:` */
.sd-shadow-sm { box-shadow: var(--shadow-sm); }

/* `:click-parent:` — the button's hit area covers its whole positioned
   ancestor, which is how a card becomes clickable through the button in it. */
.sd-stretched-link::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 1;
}

/* `:align:` — written on the paragraph containing the button, not on the
   button, which is why these align *text* rather than a box. */
.sd-text-left { text-align: left; }
.sd-text-right { text-align: right; }
.sd-text-center { text-align: center; }
.sd-text-justify { text-align: justify; }

/* Long labels wrap rather than stretching the button off the line. */
.sd-text-wrap { white-space: normal; }

/* `:color:` — a filled button per semantic colour. The foreground is the same
   split the dropdown's `sd-bg-text-*` pairs make: white on the dark seven,
   near-black on the light four. */
.sd-btn-primary { background: #0d6efd; border-color: #0d6efd; color: #ffffff; }
.sd-btn-secondary { background: #6c757d; border-color: #6c757d; color: #ffffff; }
.sd-btn-success { background: #198754; border-color: #198754; color: #ffffff; }
.sd-btn-danger { background: #dc3545; border-color: #dc3545; color: #ffffff; }
.sd-btn-muted { background: #6c757d; border-color: #6c757d; color: #ffffff; }
.sd-btn-dark { background: #212529; border-color: #212529; color: #ffffff; }
.sd-btn-black { background: #000000; border-color: #000000; color: #ffffff; }
.sd-btn-info { background: #0dcaf0; border-color: #0dcaf0; color: #212529; }
.sd-btn-warning { background: #ffc107; border-color: #ffc107; color: #212529; }
.sd-btn-light { background: #f8f9fa; border-color: #f8f9fa; color: #212529; }
.sd-btn-white { background: #ffffff; border-color: #dee2e6; color: #212529; }

/* `:outline:` — the same colour as a border and text on no fill. */
.sd-btn-outline-primary { background: transparent; border-color: #0d6efd; color: #0d6efd; }
.sd-btn-outline-secondary { background: transparent; border-color: #6c757d; color: #6c757d; }
.sd-btn-outline-success { background: transparent; border-color: #198754; color: #198754; }
.sd-btn-outline-info { background: transparent; border-color: #0dcaf0; color: #0aa2c0; }
.sd-btn-outline-warning { background: transparent; border-color: #ffc107; color: #997404; }
.sd-btn-outline-danger { background: transparent; border-color: #dc3545; color: #dc3545; }
.sd-btn-outline-light { background: transparent; border-color: #f8f9fa; color: #6c757d; }
.sd-btn-outline-muted { background: transparent; border-color: #6c757d; color: #6c757d; }
.sd-btn-outline-dark { background: transparent; border-color: #212529; color: #212529; }
.sd-btn-outline-white { background: transparent; border-color: #dee2e6; color: #6c757d; }
.sd-btn-outline-black { background: transparent; border-color: #000000; color: #000000; }

/* ── Grids (sphinx-design's `.. grid::` / `.. grid-item::`) ─────────── */

/* A twelve-column flex layout, in sphinx-design's class names so a page
   written for that extension keeps its structure; the rules themselves are
   this build's own. The breakpoints are Bootstrap's, which sphinx-design's
   grid derives from: xs is the unqualified base and the three below are
   min-width queries.

   Every width rule below is deliberately kept to *one* class of specificity
   (`> *`, not `> .sd-col`), so that an item's own `:columns:` — written later
   in this file — can override the count its row asked for. */

.sd-container-fluid {
  width: 100%;
}

.sd-row {
  display: flex;
  flex-wrap: wrap;
  margin-left: calc(-0.5 * var(--sd-gutter-x, 1.5rem));
  margin-right: calc(-0.5 * var(--sd-gutter-x, 1.5rem));
  margin-top: calc(-1 * var(--sd-gutter-y, 0rem));
}

.sd-row > * {
  box-sizing: border-box;
  flex-shrink: 0;
  padding-left: calc(0.5 * var(--sd-gutter-x, 1.5rem));
  padding-right: calc(0.5 * var(--sd-gutter-x, 1.5rem));
  margin-top: var(--sd-gutter-y, 0rem);
}

.sd-col {
  display: flex;
  min-width: 0;
}

/* `:child-direction:` — always present on an item, since an omitted value
   means `column`. */
.sd-d-flex-column { flex-direction: column; }
.sd-d-flex-row { flex-direction: row; flex-wrap: wrap; }

/* `:child-align:` — along the item's own major axis. */
.sd-align-major-start { justify-content: flex-start; }
.sd-align-major-end { justify-content: flex-end; }
.sd-align-major-center { justify-content: center; }
.sd-align-major-justify { justify-content: space-between; }
.sd-align-major-spaced { justify-content: space-evenly; }

/* `:reverse:` on a `.. grid::`. */
.sd-flex-row-reverse { flex-direction: row-reverse; }

/* `:outline:`, on a grid and on an item alike. */
.sd-border-1 {
  border: 1px solid var(--border);
  border-radius: var(--radius);
}

/* A cell should not inherit the page's block margins at its own edges, or a
   one-paragraph cell sits off-centre in its box. */
.sd-col > :first-child { margin-top: 0; }
.sd-col > :last-child { margin-bottom: 0; }

/* `:gutter:` — the 0-5 scale again, as the gap between cells. Set as
   custom properties so the row's negative margins stay in step. */
.sd-g-0 { --sd-gutter-x: 0rem; --sd-gutter-y: 0rem; }
.sd-g-1 { --sd-gutter-x: 0.25rem; --sd-gutter-y: 0.25rem; }
.sd-g-2 { --sd-gutter-x: 0.5rem; --sd-gutter-y: 0.5rem; }
.sd-g-3 { --sd-gutter-x: 1rem; --sd-gutter-y: 1rem; }
.sd-g-4 { --sd-gutter-x: 1.5rem; --sd-gutter-y: 1.5rem; }
.sd-g-5 { --sd-gutter-x: 3rem; --sd-gutter-y: 3rem; }

/* A `.. grid::` argument — how many cells fit on a row. The unqualified
   class and the `-xs-` one name the same breakpoint; both are emitted,
   as sphinx-design's `_media_option` emits them. */
.sd-row-cols-1 > * { flex: 0 0 auto; width: 100%; }
.sd-row-cols-2 > * { flex: 0 0 auto; width: 50%; }
.sd-row-cols-3 > * { flex: 0 0 auto; width: 33.333333%; }
.sd-row-cols-4 > * { flex: 0 0 auto; width: 25%; }
.sd-row-cols-5 > * { flex: 0 0 auto; width: 20%; }
.sd-row-cols-6 > * { flex: 0 0 auto; width: 16.666667%; }
.sd-row-cols-7 > * { flex: 0 0 auto; width: 14.285714%; }
.sd-row-cols-8 > * { flex: 0 0 auto; width: 12.5%; }
.sd-row-cols-9 > * { flex: 0 0 auto; width: 11.111111%; }
.sd-row-cols-10 > * { flex: 0 0 auto; width: 10%; }
.sd-row-cols-11 > * { flex: 0 0 auto; width: 9.090909%; }
.sd-row-cols-12 > * { flex: 0 0 auto; width: 8.333333%; }
.sd-row-cols-auto > * { flex: 0 0 auto; width: auto; }

.sd-row-cols-xs-1 > * { flex: 0 0 auto; width: 100%; }
.sd-row-cols-xs-2 > * { flex: 0 0 auto; width: 50%; }
.sd-row-cols-xs-3 > * { flex: 0 0 auto; width: 33.333333%; }
.sd-row-cols-xs-4 > * { flex: 0 0 auto; width: 25%; }
.sd-row-cols-xs-5 > * { flex: 0 0 auto; width: 20%; }
.sd-row-cols-xs-6 > * { flex: 0 0 auto; width: 16.666667%; }
.sd-row-cols-xs-7 > * { flex: 0 0 auto; width: 14.285714%; }
.sd-row-cols-xs-8 > * { flex: 0 0 auto; width: 12.5%; }
.sd-row-cols-xs-9 > * { flex: 0 0 auto; width: 11.111111%; }
.sd-row-cols-xs-10 > * { flex: 0 0 auto; width: 10%; }
.sd-row-cols-xs-11 > * { flex: 0 0 auto; width: 9.090909%; }
.sd-row-cols-xs-12 > * { flex: 0 0 auto; width: 8.333333%; }
.sd-row-cols-xs-auto > * { flex: 0 0 auto; width: auto; }

/* A `.. grid-item::`'s `:columns:` — how many of twelve one cell spans. */
.sd-col-1 { flex: 0 0 auto; width: 8.333333%; }
.sd-col-2 { flex: 0 0 auto; width: 16.666667%; }
.sd-col-3 { flex: 0 0 auto; width: 25%; }
.sd-col-4 { flex: 0 0 auto; width: 33.333333%; }
.sd-col-5 { flex: 0 0 auto; width: 41.666667%; }
.sd-col-6 { flex: 0 0 auto; width: 50%; }
.sd-col-7 { flex: 0 0 auto; width: 58.333333%; }
.sd-col-8 { flex: 0 0 auto; width: 66.666667%; }
.sd-col-9 { flex: 0 0 auto; width: 75%; }
.sd-col-10 { flex: 0 0 auto; width: 83.333333%; }
.sd-col-11 { flex: 0 0 auto; width: 91.666667%; }
.sd-col-12 { flex: 0 0 auto; width: 100%; }
.sd-col-auto { flex: 0 0 auto; width: auto; }

.sd-col-xs-1 { flex: 0 0 auto; width: 8.333333%; }
.sd-col-xs-2 { flex: 0 0 auto; width: 16.666667%; }
.sd-col-xs-3 { flex: 0 0 auto; width: 25%; }
.sd-col-xs-4 { flex: 0 0 auto; width: 33.333333%; }
.sd-col-xs-5 { flex: 0 0 auto; width: 41.666667%; }
.sd-col-xs-6 { flex: 0 0 auto; width: 50%; }
.sd-col-xs-7 { flex: 0 0 auto; width: 58.333333%; }
.sd-col-xs-8 { flex: 0 0 auto; width: 66.666667%; }
.sd-col-xs-9 { flex: 0 0 auto; width: 75%; }
.sd-col-xs-10 { flex: 0 0 auto; width: 83.333333%; }
.sd-col-xs-11 { flex: 0 0 auto; width: 91.666667%; }
.sd-col-xs-12 { flex: 0 0 auto; width: 100%; }
.sd-col-xs-auto { flex: 0 0 auto; width: auto; }

@media (min-width: 576px) {
  .sd-row-cols-sm-1 > * { flex: 0 0 auto; width: 100%; }
  .sd-row-cols-sm-2 > * { flex: 0 0 auto; width: 50%; }
  .sd-row-cols-sm-3 > * { flex: 0 0 auto; width: 33.333333%; }
  .sd-row-cols-sm-4 > * { flex: 0 0 auto; width: 25%; }
  .sd-row-cols-sm-5 > * { flex: 0 0 auto; width: 20%; }
  .sd-row-cols-sm-6 > * { flex: 0 0 auto; width: 16.666667%; }
  .sd-row-cols-sm-7 > * { flex: 0 0 auto; width: 14.285714%; }
  .sd-row-cols-sm-8 > * { flex: 0 0 auto; width: 12.5%; }
  .sd-row-cols-sm-9 > * { flex: 0 0 auto; width: 11.111111%; }
  .sd-row-cols-sm-10 > * { flex: 0 0 auto; width: 10%; }
  .sd-row-cols-sm-11 > * { flex: 0 0 auto; width: 9.090909%; }
  .sd-row-cols-sm-12 > * { flex: 0 0 auto; width: 8.333333%; }
  .sd-row-cols-sm-auto > * { flex: 0 0 auto; width: auto; }

  .sd-col-sm-1 { flex: 0 0 auto; width: 8.333333%; }
  .sd-col-sm-2 { flex: 0 0 auto; width: 16.666667%; }
  .sd-col-sm-3 { flex: 0 0 auto; width: 25%; }
  .sd-col-sm-4 { flex: 0 0 auto; width: 33.333333%; }
  .sd-col-sm-5 { flex: 0 0 auto; width: 41.666667%; }
  .sd-col-sm-6 { flex: 0 0 auto; width: 50%; }
  .sd-col-sm-7 { flex: 0 0 auto; width: 58.333333%; }
  .sd-col-sm-8 { flex: 0 0 auto; width: 66.666667%; }
  .sd-col-sm-9 { flex: 0 0 auto; width: 75%; }
  .sd-col-sm-10 { flex: 0 0 auto; width: 83.333333%; }
  .sd-col-sm-11 { flex: 0 0 auto; width: 91.666667%; }
  .sd-col-sm-12 { flex: 0 0 auto; width: 100%; }
  .sd-col-sm-auto { flex: 0 0 auto; width: auto; }
}

@media (min-width: 768px) {
  .sd-row-cols-md-1 > * { flex: 0 0 auto; width: 100%; }
  .sd-row-cols-md-2 > * { flex: 0 0 auto; width: 50%; }
  .sd-row-cols-md-3 > * { flex: 0 0 auto; width: 33.333333%; }
  .sd-row-cols-md-4 > * { flex: 0 0 auto; width: 25%; }
  .sd-row-cols-md-5 > * { flex: 0 0 auto; width: 20%; }
  .sd-row-cols-md-6 > * { flex: 0 0 auto; width: 16.666667%; }
  .sd-row-cols-md-7 > * { flex: 0 0 auto; width: 14.285714%; }
  .sd-row-cols-md-8 > * { flex: 0 0 auto; width: 12.5%; }
  .sd-row-cols-md-9 > * { flex: 0 0 auto; width: 11.111111%; }
  .sd-row-cols-md-10 > * { flex: 0 0 auto; width: 10%; }
  .sd-row-cols-md-11 > * { flex: 0 0 auto; width: 9.090909%; }
  .sd-row-cols-md-12 > * { flex: 0 0 auto; width: 8.333333%; }
  .sd-row-cols-md-auto > * { flex: 0 0 auto; width: auto; }

  .sd-col-md-1 { flex: 0 0 auto; width: 8.333333%; }
  .sd-col-md-2 { flex: 0 0 auto; width: 16.666667%; }
  .sd-col-md-3 { flex: 0 0 auto; width: 25%; }
  .sd-col-md-4 { flex: 0 0 auto; width: 33.333333%; }
  .sd-col-md-5 { flex: 0 0 auto; width: 41.666667%; }
  .sd-col-md-6 { flex: 0 0 auto; width: 50%; }
  .sd-col-md-7 { flex: 0 0 auto; width: 58.333333%; }
  .sd-col-md-8 { flex: 0 0 auto; width: 66.666667%; }
  .sd-col-md-9 { flex: 0 0 auto; width: 75%; }
  .sd-col-md-10 { flex: 0 0 auto; width: 83.333333%; }
  .sd-col-md-11 { flex: 0 0 auto; width: 91.666667%; }
  .sd-col-md-12 { flex: 0 0 auto; width: 100%; }
  .sd-col-md-auto { flex: 0 0 auto; width: auto; }
}

@media (min-width: 992px) {
  .sd-row-cols-lg-1 > * { flex: 0 0 auto; width: 100%; }
  .sd-row-cols-lg-2 > * { flex: 0 0 auto; width: 50%; }
  .sd-row-cols-lg-3 > * { flex: 0 0 auto; width: 33.333333%; }
  .sd-row-cols-lg-4 > * { flex: 0 0 auto; width: 25%; }
  .sd-row-cols-lg-5 > * { flex: 0 0 auto; width: 20%; }
  .sd-row-cols-lg-6 > * { flex: 0 0 auto; width: 16.666667%; }
  .sd-row-cols-lg-7 > * { flex: 0 0 auto; width: 14.285714%; }
  .sd-row-cols-lg-8 > * { flex: 0 0 auto; width: 12.5%; }
  .sd-row-cols-lg-9 > * { flex: 0 0 auto; width: 11.111111%; }
  .sd-row-cols-lg-10 > * { flex: 0 0 auto; width: 10%; }
  .sd-row-cols-lg-11 > * { flex: 0 0 auto; width: 9.090909%; }
  .sd-row-cols-lg-12 > * { flex: 0 0 auto; width: 8.333333%; }
  .sd-row-cols-lg-auto > * { flex: 0 0 auto; width: auto; }

  .sd-col-lg-1 { flex: 0 0 auto; width: 8.333333%; }
  .sd-col-lg-2 { flex: 0 0 auto; width: 16.666667%; }
  .sd-col-lg-3 { flex: 0 0 auto; width: 25%; }
  .sd-col-lg-4 { flex: 0 0 auto; width: 33.333333%; }
  .sd-col-lg-5 { flex: 0 0 auto; width: 41.666667%; }
  .sd-col-lg-6 { flex: 0 0 auto; width: 50%; }
  .sd-col-lg-7 { flex: 0 0 auto; width: 58.333333%; }
  .sd-col-lg-8 { flex: 0 0 auto; width: 66.666667%; }
  .sd-col-lg-9 { flex: 0 0 auto; width: 75%; }
  .sd-col-lg-10 { flex: 0 0 auto; width: 83.333333%; }
  .sd-col-lg-11 { flex: 0 0 auto; width: 91.666667%; }
  .sd-col-lg-12 { flex: 0 0 auto; width: 100%; }
  .sd-col-lg-auto { flex: 0 0 auto; width: auto; }
}

/* `:animate:` — applied to the body, which is what appears when it opens. */
.sd-fade-in[open] > .sd-summary-content {
  animation: sd-fade-in 0.4s ease-in-out;
}

.sd-fade-in-slide-down[open] > .sd-summary-content {
  animation: sd-fade-in 0.4s ease-in-out, sd-slide-down 0.4s ease-in-out;
}

@keyframes sd-fade-in {
  from { opacity: 0; }
  to { opacity: 1; }
}

@keyframes sd-slide-down {
  from { transform: translateY(-0.5rem); }
  to { transform: translateY(0); }
}

/* ── Block quotes ──────────────────────────────────────────────────── */

blockquote {
  margin: 1.5rem 0;
  padding: 0.5rem 1.5rem;
  border-left: 5px solid var(--border);
  color: var(--text-muted);
  font-style: italic;
}

blockquote > :first-child { margin-top: 0; }
blockquote > :last-child { margin-bottom: 0; }

blockquote blockquote {
  margin: 1rem 0;
}

blockquote p.attribution {
  margin-top: 0.75rem;
  text-align: right;
  font-style: normal;
}

/* ── Line blocks ────────────────────────────────────────────────────── */

.line-block {
  margin: 1em 0;
}

.line-block .line-block {
  margin: 0 0 0 1.5rem;
}

/* ── Images and figures ─────────────────────────────────────────────── */

/* An image must never overflow the page, whatever its intrinsic size — but a
   :width: the author wrote is honoured as an inline style, which wins. */
img {
  max-width: 100%;
  height: auto;
}

figure {
  margin: 2rem 0;
}

figure img {
  display: block;
}

figcaption {
  margin-top: 0.75rem;
  font-size: 0.9rem;
  color: var(--text-muted);
}

figcaption > p:first-child {
  margin-top: 0;
  font-weight: 600;
  color: var(--text);
}

/* Everything after a figure's caption. Set back to body colour and weight so
   a legend reads as prose rather than as a continuation of the caption. */
figcaption .legend {
  margin-top: 0.75rem;
  font-weight: 400;
}

figcaption .legend > :first-child { margin-top: 0; }
figcaption .legend > :last-child { margin-bottom: 0; }

/* The three alignments both image directives share, transcribed from Sphinx's
   own `basic.css` rather than re-derived: `align-left`/`align-right` float so
   text flows beside them, and `align-center` is a block centred in the flow.

   The `clear` on each float is the part that is easy to leave out and hard to
   diagnose. Without it a float only avoids *content*, not earlier floats on
   its own side, so two aligned images in a row sit side by side instead of one
   below the other — and a centred image between them, being an ordinary block,
   rides up alongside the float rather than starting below it. The rendered
   order then bears no relation to the source order.

   Deliberately element-qualified, where Sphinx also has bare `.align-*` rules.
   Those would reach the `align-*` classes the table directives emit and centre
   a centred table's text as a side effect, which is a change to tables rather
   than to images. `figure.align-center` is spelled out because there the
   caption *should* follow the picture it belongs to. */
img.align-left,
figure.align-left {
  clear: left;
  float: left;
  margin-right: 1em;
}

img.align-right,
figure.align-right {
  clear: right;
  float: right;
  margin-left: 1em;
}

img.align-center,
figure.align-center {
  display: block;
  margin-left: auto;
  margin-right: auto;
}

figure.align-center {
  text-align: center;
}

/* A heading must not ride up beside a floated image: each section here starts
   below whatever the previous one floated. */
.document h1,
.document h2,
.document h3 {
  clear: both;
}

/* ── PlantUML Diagrams ─────────────────────────────────────────────── */

.plantuml-diagram {
  margin: 2.5rem 0;
  padding: 1rem;
  background: #f8fafc;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  text-align: center;
  transition: transform 0.3s ease;
}

.plantuml-diagram:hover {
  transform: translateY(-2px);
  box-shadow: var(--shadow);
}

.plantuml-diagram img {
  max-width: 100%;
  height: auto;
}

/* The notice under a sequence diagram `:max-items:` cut short. Set apart from
   the caption above it, since it says what the picture leaves out rather than
   what it shows. */
.entity-sequence-truncated {
  margin: -1.75rem 0 2.5rem;
  font-size: 0.85rem;
  font-style: italic;
  color: var(--text-muted);
  text-align: center;
}

/* ── Version-Change Directives ─────────────────────────────────────── */

.versionadded,
.versionchanged,
.deprecated {
  margin: 1.5rem 0;
  padding: 0.75rem 1rem;
  border-radius: var(--radius);
  border-left: 4px solid;
  font-size: 0.95rem;
}

.versionadded {
  background: #f0fdf4;
  border-color: #22c55e;
  color: #14532d;
}

.versionchanged {
  background: #eff6ff;
  border-color: #3b82f6;
  color: #1e3a8a;
}

.deprecated {
  background: #fefce8;
  border-color: #eab308;
  color: #713f12;
}

.versionmodified-label {
  font-weight: 600;
}

/* ── Glossary ──────────────────────────────────────────────────────── */

dl.glossary {
  margin: 2rem 0;
  display: block;
}

dl.glossary dt {
  font-family: 'Outfit', sans-serif;
  font-size: 1.15rem;
  font-weight: 600;
  color: var(--text-header);
  margin-top: 1.75rem;
  padding: 0.25rem 0.5rem;
  display: inline-block;
  position: relative;
  scroll-margin-top: 2rem;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
  border-radius: var(--radius);
}

dl.glossary dt:first-of-type {
  margin-top: 0.5rem;
}

dl.glossary dd {
  margin-left: 1.5rem;
  margin-bottom: 1.75rem;
  padding-left: 1rem;
  border-left: 2px solid var(--border);
  color: #475569;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
}

dl.glossary dd p:last-child {
  margin-bottom: 0;
}

/* Hover effect on glossary terms to show link anchor */
dl.glossary dt::after {
  content: ' #';
  color: var(--primary);
  opacity: 0;
  font-size: 0.85em;
  font-weight: 400;
  transition: opacity 0.2s ease, transform 0.2s ease;
  display: inline-block;
  transform: translateX(-4px);
  pointer-events: none;
}

dl.glossary dt:hover::after {
  opacity: 0.6;
  transform: translateX(2px);
}

/* Active targeted term via #term-xyz in URL */
dl.glossary dt:target {
  color: var(--primary);
  background-color: #eff6ff;
  padding-left: 0.75rem;
  padding-right: 0.75rem;
}

dl.glossary dt:target + dd {
  border-left-color: var(--primary);
  background: linear-gradient(90deg, #eff6ff 0%, transparent 100%);
  padding-top: 0.5rem;
  padding-bottom: 0.5rem;
  border-radius: 0 var(--radius) var(--radius) 0;
}

/* Inline term references (:term:) */
a.reference.internal .xref.std-term {
  border-bottom: 1px dashed var(--primary);
  padding-bottom: 1px;
  transition: border-color 0.2s, color 0.2s;
}

a.reference.internal:hover .xref.std-term {
  border-bottom-style: solid;
  border-bottom-color: var(--primary-hover);
  color: var(--primary-hover);
}

a.reference.internal {
  border-bottom: none !important;
}

/* Broken glossary term references */
a.broken-link {
  color: #ef4444 !important;
  border-bottom: 1px dashed #ef4444 !important;
  cursor: help;
  text-decoration: none;
  transition: all 0.2s;
}

a.broken-link:hover {
  border-bottom-style: solid !important;
  border-bottom-color: #dc2626 !important;
  color: #dc2626 !important;
}

/* ── Domain Objects (py:*, c:*) ───────────────────────────────────────── */

dl.py, dl.c {
  margin: 1.5rem 0;
  display: block;
}

dl.py dt, dl.c dt {
  font-weight: 600;
  color: var(--text-header);
  padding: 0.5rem 0.75rem;
  background: var(--bg-sidebar);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  scroll-margin-top: 2rem;
  position: relative;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
}

/* Hover-reveal permalink, mirrors dl.glossary dt::after */
dl.py dt::after, dl.c dt::after {
  content: ' #';
  color: var(--primary);
  opacity: 0;
  font-size: 0.85em;
  font-weight: 400;
  transition: opacity 0.2s ease, transform 0.2s ease;
  display: inline-block;
  transform: translateX(-4px);
  pointer-events: none;
}

dl.py dt:hover::after, dl.c dt:hover::after {
  opacity: 0.6;
  transform: translateX(2px);
}

/* Active targeted definition via #py:... in the URL, mirrors dl.glossary */
dl.py dt:target, dl.c dt:target {
  color: var(--primary);
  background-color: #eff6ff;
  border-color: var(--primary);
}

dl.py dt:target + dd, dl.c dt:target + dd {
  border-left-color: var(--primary);
  background: linear-gradient(90deg, #eff6ff 0%, transparent 100%);
  border-radius: 0 var(--radius) var(--radius) 0;
}

dl.py dd, dl.c dd {
  margin-left: 1.5rem;
  margin-top: 0.75rem;
  margin-bottom: 1.25rem;
  padding: 0.25rem 0 0.25rem 1rem;
  border-left: 2px solid var(--border);
  color: #475569;
}

dl.py dd > :first-child, dl.c dd > :first-child { margin-top: 0; }
dl.py dd > :last-child, dl.c dd > :last-child { margin-bottom: 0; }

/* Nested domain-object dl's cascade automatically via normal block flow —
 * each level of class/method/attribute nesting adds another indent and
 * border-left with no depth-tracking needed on the Rust side. Tighten
 * spacing so a nested definition reads as "inside" its parent rather than
 * as a new top-level section. */
dl.py dd dl.py, dl.py dd dl.c,
dl.c dd dl.py, dl.c dd dl.c {
  margin: 0.75rem 0;
}

/* Prefix labels: classmethod / staticmethod / abstractmethod / async / final / class */
dl.py em.property, dl.c em.property {
  font-style: normal;
  font-weight: 600;
  font-size: 0.8em;
  color: var(--primary);
  text-transform: uppercase;
  letter-spacing: 0.03em;
  margin-right: 0.35em;
}

/* Signature name/params sit inline in a heading-like <dt>, not as inline
 * code in body text — override the generic pill-style `.document code`. */
dl.py dt code.sig-name, dl.c dt code.sig-name {
  background: none;
  border: none;
  padding: 0;
  font-size: 1em;
  color: inherit;
  font-weight: 600;
}

/* Type-specific option paragraphs: py:module's platform/synopsis/deprecated,
 * py:data/py:attribute's type/value/canonical */
dl.py dd > p.type,
dl.py dd > p.value,
dl.py dd > p.canonical,
dl.py dd > p.platform,
dl.py dd > p.synopsis {
  font-size: 0.9rem;
  color: var(--text-muted);
  font-family: 'JetBrains Mono', monospace;
  margin-bottom: 0.5rem;
}

dl.py dd > p.deprecated {
  font-size: 0.9rem;
  font-weight: 600;
  color: #b45309;
  margin-bottom: 0.5rem;
}

/* ── Entities (project-declared types) ─────────────────────────────── */

/* A card, like an admonition, since an entity is a self-contained block that
   interrupts the prose around it. The accent is on the left edge for the same
   reason, and the type badge repeats the colour so the two read as one unit. */
.entity {
  margin: 2rem 0;
  border: 1px solid var(--border);
  border-left: 5px solid var(--primary);
  border-radius: var(--radius);
  background: var(--bg-sidebar);
  box-shadow: var(--shadow-sm);
  overflow: hidden;
}

/* The header is a flex row so its three parts separate on their own, and the
   id can sit at the far end without markup that says so. `wrap` keeps it
   readable when the title is long or the viewport narrow. */
.entity-header {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.75rem;
  margin: 0;
  padding: 0.875rem 1.25rem;
  background: var(--bg-main);
  border-bottom: 1px solid var(--border);
}

.entity-type {
  flex: none;
  padding: 0.15rem 0.6rem;
  border-radius: 999px;
  background: var(--primary);
  color: #fff;
  font-size: 0.75rem;
  font-weight: 700;
  letter-spacing: 0.03em;
  text-transform: uppercase;
  white-space: nowrap;
}

.entity-title {
  flex: 1 1 auto;
  min-width: 0;
  font-size: 1.05rem;
  font-weight: 700;
  color: var(--text-header);
}

/* Monospace and muted: an id is a token to copy, not prose to read. */
.entity-id {
  flex: none;
  margin-left: auto;
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.8rem;
  color: var(--text-muted);
}

/* Hover-reveal permalink, mirroring dl.glossary dt::after. */
.entity:hover > .entity-header > .entity-id::after {
  content: " ¶";
  color: var(--primary);
}

/* A key/value list rather than tabular data, so it opts out of the page's
   table styling: no grid, no zebra stripes, no full-bleed width. */
.document table.entity-attributes {
  width: auto;
  margin: 1rem 1.25rem;
  font-size: 0.9rem;
}

.document table.entity-attributes tbody tr:nth-child(even) {
  background: none;
}

.document table.entity-attributes th,
.document table.entity-attributes td {
  padding: 0.3rem 0.75rem 0.3rem 0;
  text-align: left;
  vertical-align: top;
  border: none;
}

.document table.entity-attributes th {
  width: 1%;
  white-space: nowrap;
  font-weight: 600;
  color: var(--text-muted);
}

.entity-content,
.entity-section {
  padding: 0 1.25rem;
}

.entity-content > :first-child,
.entity-section > .entity-section-label + * {
  margin-top: 0;
}

/* A section is a labelled sub-part, so it gets a rule above it and a heading
   that is unmistakably a heading — the complaint the built-in rendering
   originally invited was that this looked like ordinary body text. */
.entity-section {
  margin-top: 1rem;
  padding-top: 0.875rem;
  border-top: 1px solid var(--border);
}

.entity-section-label {
  margin: 0 0 0.5rem 0;
  font-size: 0.78rem;
  font-weight: 700;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--primary);
}

.entity-links {
  margin-top: 1rem;
  padding: 0.875rem 1.25rem 1rem;
  border-top: 1px solid var(--border);
  background: var(--bg-main);
}

.entity-link-label {
  margin: 0.5rem 0 0.25rem;
  font-size: 0.78rem;
  font-weight: 700;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--text-muted);
}

.entity-link-label:first-child {
  margin-top: 0;
}

/* Inline, comma-free: these are short id tokens, and a bulleted column of them
   wastes a lot of vertical space on an entity with several relations. */
.entity-link-list {
  margin: 0;
  padding: 0;
  list-style: none;
  display: flex;
  flex-wrap: wrap;
  gap: 0.4rem;
}

.entity-link-list li {
  margin: 0;
}

.entity-link-list a,
.entity-link-list .broken-link {
  display: inline-block;
  padding: 0.1rem 0.5rem;
  border: 1px solid var(--border);
  border-radius: 999px;
  background: var(--bg-sidebar);
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.8rem;
  text-decoration: none;
}

.entity-link-list .broken-link {
  border-style: dashed;
  border-color: #ef4444;
  color: #ef4444;
}

/* An anchored entity is highlighted, as a targeted glossary term is. */
.entity:target {
  border-left-color: #f59e0b;
}

.entity:target > .entity-header {
  background: #fffbeb;
}

/* ── Entity tables (`.. entity-table::` / `.. needtable::`) ────────── */

/* A listing is a *report* about the entities, not one of them, so it is
   deliberately not styled as an entity card: it reads as a table, like every
   other table on the site. What it adds is a monospace id column, so a column
   of ids scans as ids, and a full-width layout, since a listing is usually the
   widest thing on its page.

   `.document` prefixes the rules that fight `table th`/`td`'s own selectors,
   which are specific enough to win otherwise. */
.document table.entity-table {
  width: 100%;
  font-size: 0.9rem;
}

.document table.entity-table th.head {
  white-space: nowrap;
}

.document table.entity-table td {
  vertical-align: top;
}

/* An id is an identifier, so it is set as one — and the first column is the id
   column in every table this build's default columns produce. */
.document table.entity-table td:first-child a {
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.9em;
}

/* An empty cell is a field this entity's type does not declare. Left blank on
   purpose: a placeholder would read as a value. */

/* Inline references produced by an entity role. */
.document a .xref.entity {
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.9em;
}


/* The disclosure a collapsible type folds its detail into. Collapsed, only the
   header and the leading prose remain — everything a reader needs to scan a
   long page of entities. */
.entity-more {
  border-top: 1px solid var(--border);
}

.entity-more-toggle {
  cursor: pointer;
  padding: 0.55rem 1.25rem;
  font-size: 0.78rem;
  font-weight: 700;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--text-muted);
  background: var(--bg-main);
  outline: none;
}

.entity-more-toggle:hover {
  color: var(--primary);
}

/* The disclosure's own children already carry the dividers, so the summary
   must not add a second rule directly above the first of them. */
.entity-more[open] > .entity-more-toggle {
  border-bottom: 1px solid var(--border);
}

.entity-more > .entity-attributes {
  margin-top: 0.875rem;
}

.entity-more > .entity-section:first-of-type,
.entity-more > .entity-links {
  border-top: none;
}

/* ── Audit events ──────────────────────────────────────────────────── */

/* The counter-example to the entity box: `audit-event` reads as prose, so it
   gets a rule and an indent rather than a card. Enough to group each event
   with the description that follows it — without which a page of them is an
   undifferentiated run of paragraphs — and no more. */
.audit-event {
  margin: 1.5rem 0;
  padding-left: 1rem;
  border-left: 3px solid var(--border);
}

.audit-event:first-of-type {
  margin-top: 2rem;
}

.audit-event > p:first-child {
  margin-top: 0;
}

.audit-event > :last-child {
  margin-bottom: 0;
}

/* The event's name is the thing a reader scans for, so it carries the accent;
   its arguments are supporting detail and stay muted.
   `.document` is on both selectors because `.document code` already sets a
   colour at that specificity — the bare class silently lost to it. */
.document .audit-event-name {
  font-weight: 600;
  color: var(--primary);
}

.document .audit-event-args {
  color: var(--text-muted);
}

.audit-event-version {
  font-size: 0.9em;
  color: var(--text-muted);
}

/* Anchored by a reference, highlighted the same way an entity is. */
.audit-event:target {
  border-left-color: #f59e0b;
  background: #fffbeb;
}

/* ── Option Lists ──────────────────────────────────────────────────── */

dl.option-list {
  margin: 1.5rem 0;
  display: block;
}

dl.option-list dt {
  margin-top: 1rem;
}

dl.option-list dt:first-of-type {
  margin-top: 0;
}

dl.option-list dt kbd {
  font-family: 'JetBrains Mono', monospace;
  font-size: 0.9em;
  background: #f1f5f9;
  color: var(--text-header);
  padding: 0.2em 0.5em;
  border-radius: 4px;
  border: 1px solid var(--border);
}

dl.option-list dt var {
  font-style: normal;
  color: var(--primary);
}

dl.option-list dd {
  margin-left: 1.5rem;
  margin-top: 0.5rem;
  margin-bottom: 1.25rem;
  padding-left: 1rem;
  border-left: 2px solid var(--border);
  color: #475569;
}

dl.option-list dd > :first-child { margin-top: 0; }
dl.option-list dd > :last-child { margin-bottom: 0; }

/* ── Tables ────────────────────────────────────────────────────────── */

table {
  border-collapse: collapse;
  margin: 1.75rem 0;
  width: 100%;
  font-size: 0.95rem;
}

/* `--border` (#e2e8f0) is tuned for subtle single-line dividers elsewhere on
 * the page; against a full grid of table lines it reads as nearly invisible,
 * so tables use a darker, clearly-visible line of their own. */
table th,
table td {
  border: 1px solid #94a3b8;
  padding: 0.6rem 0.85rem;
  text-align: left;
  vertical-align: top;
}

table thead th {
  background: var(--bg-sidebar);
  font-family: 'Outfit', sans-serif;
  font-weight: 600;
  color: var(--text-header);
  border-bottom: 2px solid var(--text-muted);
}

table tbody tr:nth-child(even) {
  background: var(--bg-sidebar);
}

table th p:last-child,
table td p:last-child {
  margin-bottom: 0;
}

/* `.. list-table::`'s `:align:` option only has a visible effect once the
 * table is narrower than the page, so list-tables size to their content by
 * default instead of inheriting the 100%-width rule above; `:width:` (an
 * inline `style` attribute) always wins over this when given. */
table.list-table {
  width: auto;
}

table.list-table.align-left {
  margin-right: auto;
}

table.list-table.align-center {
  margin-left: auto;
  margin-right: auto;
}

table.list-table.align-right {
  margin-left: auto;
}

table.list-table caption {
  caption-side: top;
  text-align: left;
  font-style: italic;
  color: var(--text-muted);
  margin-bottom: 0.5rem;
  font-size: 0.9rem;
}

/* ── Math ──────────────────────────────────────────────────────── */

/* Equations are MathML, rendered natively by the browser — no script is
   loaded for them, and no webfont is downloaded. Correct rendering of the
   stretchy constructs (matrices, `cases`) does depend on a math font being
   installed locally; the `math` rule below names the common ones. */

.math {
  /* A long equation scrolls inside its own box rather than widening the page. */
  overflow-x: auto;
  overflow-y: hidden;
}

span.math {
  /* Inline math sits in the run of text; only a block gets its own box. */
  display: inline;
}

div.math {
  display: flex;
  align-items: center;
  margin: 1.75rem 0;
}

div.math math {
  /* The equation takes the middle, so it stays centred whether or not the
     block carries a number. */
  flex: 1 1 auto;
  text-align: center;
}

math {
  /* The stretchy brackets a `cases` or a matrix grows to fit are drawn from an
     OpenType MATH table's glyph variants. A text font has no such table, so
     without naming a math font here the browser has nothing to stretch with
     and draws `(` at its ordinary character size. The `math` generic family
     (CSS Fonts 4) defers to the browser's own default math font where it is
     supported; the names before it cover the common installs. */
  font-family: "Latin Modern Math", "STIX Two Math", "XITS Math",
    "Cambria Math", "TeX Gyre Termes Math", "DejaVu Math TeX Gyre",
    "Noto Sans Math", math;
  font-size: 1.05em;
}

div.math .eqno {
  /* The number sits at the right margin, as in a printed paper. */
  order: 2;
  flex: 0 0 auto;
  margin-left: 1rem;
  color: #6b7280;
  white-space: nowrap;
}

div.math .eqno .headerlink {
  opacity: 0;
  margin-left: 0.35rem;
  text-decoration: none;
  transition: opacity 0.15s ease-in-out;
}

div.math:hover .eqno .headerlink,
div.math .eqno .headerlink:focus {
  opacity: 1;
}

/* An `:eq:` reference shows the number it points at. */
a .eqno {
  color: inherit;
}

/* LaTeX the math backend could not read: the source is shown as written, so
   the page still says what the author meant. */
.math-error {
  color: #b91c1c;
  background: #fef2f2;
  border: 1px solid #fecaca;
  border-radius: 4px;
  padding: 0.15rem 0.4rem;
  font-size: 0.95em;
}

/* A directive this build could not turn into content — an unrecognized name,
   or a recognized one whose content it had to refuse. Loud on purpose: the
   directive's body never reaches the page any other way, so a quiet style
   would leave the reader with silently missing content. */
.directive-error {
  margin: 1rem 0;
  border: 1px solid #fecaca;
  border-left: 5px solid #b91c1c;
  border-radius: 4px;
  background: #fef2f2;
  padding: 0.6rem 0.9rem;
}

.directive-error-message {
  margin: 0 0 0.5rem;
  color: #b91c1c;
  font-style: italic;
  font-weight: 600;
}

.directive-error-source {
  margin: 0;
  overflow-x: auto;
  background: none;
  border: 0;
  padding: 0;
  color: #7f1d1d;
  font-size: 0.9em;
  white-space: pre;
}

/* ── Responsive ────────────────────────────────────────────────────── */

@media (max-width: 1024px) {
  .document {
    padding: 3rem 2rem;
  }
}

@media (max-width: 768px) {
  .document-wrapper {
    flex-direction: column;
  }

  .sidebar {
    width: 100%;
    height: auto;
    position: static;
    border-right: none;
    border-bottom: 1px solid var(--border);
    padding: 1.5rem;
  }

  .document {
    padding: 2rem 1.5rem;
  }
}
