/* Shared typography, loaded AFTER the section styles, also by source readers.
   Roles, not page numbers, choose the size. No downloaded or optional Inter font.
   SVG map labels keep their own logical pixel sizes because their viewBox zooms. */
:root {
  --font-ui: ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
  --font-editorial: Georgia, "Times New Roman", serif;
  --font-code: ui-monospace, SFMono-Regular, Consolas, monospace;
  --type-body: 1rem;
  --type-ui: .9375rem;
  --type-small: .875rem;
  --type-meta: .8125rem;
  --type-caption: .75rem;
  --type-quote: 1rem;
  --type-inline-chip: clamp(.875rem, .94em, .9375rem);
  --type-page-title: clamp(1.5rem, 2.15vw, 2.25rem);
  --type-detail-title: clamp(1.5rem, 2.3vw, 2rem);
  --type-section-title: 1.25rem;
  --type-card-title: 1.125rem;
  --type-leading: 1.7;
  --type-ui-leading: 1.4;
  font-family: var(--font-ui);
}
body { font-family: var(--font-ui); font-size: var(--type-body); line-height: var(--type-leading); }
button, input, select, textarea { font-family: var(--font-ui); }
.primary-nav > a { font-size: var(--type-ui); line-height: var(--type-ui-leading); }

/* Normal explanation, field values, and lists: the same readable base in every
   reading surface. Special roles below are explicit; contents are never hidden. */
:is(#routeContent, .inspector-body, .protection-records-dialog) :is(p, ul, ol, li, dd) {
  font-family: var(--font-ui);
  font-size: var(--type-body);
  line-height: var(--type-leading);
}
:is(#routeContent, .inspector-body) :is(p, li, dd) { overflow-wrap: anywhere; }
:is(#routeContent, .inspector-body) :is(.inter-summary, .walk-summary, .rules-chapter > header p, .obj-lead) {
  font-size: var(--type-body);
  line-height: var(--type-leading);
}
/* The overview is an intentional large-format opening, not an article. */
#routeContent .hero p { font-size: clamp(1rem, 1.7vw, 1.22rem); line-height: 1.55; }

/* Sections 02–15 share the compact atlas proportions, without clipped descenders
   or abbreviated introductory copy. These are heading roles, not body prose. */
body[data-route]:not([data-route="overview"]) #routeContent > .page-head .page-title {
  font: 800 var(--type-page-title)/1.2 var(--font-editorial);
}
body[data-route]:not([data-route="overview"]) #routeContent > .page-head .page-kicker {
  font: 850 var(--type-caption)/1.4 var(--font-ui);
}
body[data-route]:not([data-route="overview"]) #routeContent > .page-head .page-lead {
  font: 400 var(--type-small)/1.5 var(--font-ui);
}

/* Article titles, subsection titles, compact card titles and register headings
   are different roles from the common compact page header. */
:is(#routeContent, .inspector-body) :is(
  .register-content > h2, .room-reading-head h2, .obj-head h2, .walk-chapter-head h2, .walk-panel > header h2,
  .inter-detail h2, .culture-title, .rules-chapter > header h2,
  .worldflow-hero h2, .protection-primer h2, .relation-reading-head h2, .research-detail-head h2
  , .dialogue-reading-head h2, .worldflow-collection h2
) { font: 700 var(--type-detail-title)/1.25 var(--font-editorial); overflow-wrap: anywhere; }
:is(#routeContent, .inspector-body) :is(
  .inter-panel h3, .culture-reading h3, .walk-reading h3, .walk-panel h3,
  .obj-view h3, .obj-mini h3, .rules-topic > header h3,
  .dialogue-group-head h3, .protection-context h2, .media-video h2,
  .section-title h2, .culture-detail-section h3, .room-inventory h3,
  .protection-detail-section h3
  , .dialogue-condition-card h3
) { font: 700 var(--type-section-title)/1.3 var(--font-editorial); overflow-wrap: anywhere; }
.inspector-body > h3, .room-reading-body > h3, #actorRegisterContent > h3 { font: 700 var(--type-section-title)/1.3 var(--font-editorial); }
:is(#routeContent, .inspector-body) :is(
  .card h3, .actor-capability h4, .dialogue-branch h4, .protection-card h3,
  .graphics-guide h3, .walk-phase h4, .walk-step h4, .walk-reading h4, .walk-panel h4, .inter-step-body h3,
  .obj-view h4, .obj-mini h4, .inter-panel h4, .culture-reading h4,
  .worldflow-outcome h3, .room-environment h4, .trust-guide h3
) { font: 700 var(--type-card-title)/1.35 var(--font-editorial); overflow-wrap: anywhere; }
:is(#routeContent, .inspector-body) :is(
  .obj-index h2, .walk-index h2, .culture-index h2, .inter-index h2,
  .inter-choice-index > header h3, .worldflow-index h3
) { font: 700 var(--type-body)/1.4 var(--font-editorial); overflow-wrap: anywhere; }

/* Original game passages have the editorial face; paraphrases and explanations
   do not become 'originals' simply because their older CSS used Georgia. */
:is(#routeContent, .inspector-body) :is(
  .quote, .dialogue-node blockquote, .dialogue-action blockquote,
  .dialogue-story-preview p, .worldflow-dialogues blockquote,
  .walk-dialogue blockquote,
  .culture-text-block blockquote, .culture-manual-ref blockquote,
  .culture-card blockquote, .obj-texts .quote
) { font: 400 var(--type-quote)/var(--type-leading) var(--font-editorial); }
:is(#routeContent, .inspector-body) :is(.protection-detail-lead, .protection-metaphor p, .protection-primer-copy blockquote, .culture-reader-context) {
  font-family: var(--font-ui); font-size: var(--type-body); line-height: var(--type-leading);
}

/* Smaller supporting text, not body copy. Fixed rem sizes prevent repeated
   nesting from shrinking notes, chips and labels further on some pages. */
:is(#routeContent, .inspector-body) :is(
  .small, .actor-state-note, .actor-sex-details, .actor-sex-details p,
  .capability-availability, .capability-live,
  .inter-caution, .inter-caution p, .inter-intro > p, .inter-count,
  .rules-limits, .rules-limits p, .obj-count, .obj-aliases, .walk-count,
  #triviaResultCount, .walk-index > header > span,
  .culture-ai-boundary p, .research-detail-meta,
  .worldflow-collection p, .dialogue-open-note, .dialogue-probability,
  .dialogue-rng p, .dialogue-count, .combat-field-help, .combat-object-facts p,
  .trust-guide > header p, .trust-thresholds p, .trust-limit, .actor-aliases
) { font-size: var(--type-small); line-height: 1.6; }
:is(#routeContent, .inspector-body) :is(
  .key-values dt, .meta-grid dt, .obj-facts dt, .walk-facts dt,
  .inter-facts dt, .worldflow-facts dt, .media-quickfacts dt,
  .artifact-card dt, .walk-event dt, .relation-mobile-picker label,
  .dialogue-mobile-picker label, .walk-filter > span, .walk-mobile-picker label, .actor-stat-grid dt
) { font: 650 var(--type-small)/1.5 var(--font-ui); overflow-wrap: anywhere; }
.actor-stat-grid dt span { font: 400 var(--type-meta)/1.5 var(--font-ui); }
#routeContent .actor-stat-grid dd { font: 650 var(--type-section-title)/1.4 var(--font-ui); }
.actor-view .tab-count { font: 650 var(--type-caption)/1.4 var(--font-ui); }
:is(#routeContent, .inspector-body) :is(
  .dialogue-source, .media-provenance, .culture-detail-id,
  .source-note code, .walk-source, .media-image-provenance
) { font: 400 var(--type-meta)/1.5 var(--font-code); overflow-wrap: anywhere; }
:is(#routeContent, .inspector-body) :is(
  figcaption, .dialogue-node-meta .small, .culture-card-date,
  .external-source span, .document-list small, .research-documents small,
  .image-zoom > span small, .inter-holders > li > .small,
  .obj-children > li > .small
) { font-size: var(--type-meta); line-height: 1.5; }
:is(#routeContent, .inspector-body) :is(
  .badge, .page-kicker, .artifact-type, .protection-kind,
  .combatant-statline span,
  .combat-result-metrics > div > span, .metric-grid > div > span
) { font-size: var(--type-caption); line-height: 1.4; }

/* Equivalent menu rows: stable weight, multiline labels inside their control.
   Selection/hover colors and scroll ownership stay in their existing modules. */
:is(#routeContent, .inspector-body) :is(
  .register-list button, .obj-choice, .walk-choice, .culture-choice,
  .inter-list button, .inter-list a.inter-choice, .rules-contents a,
  .rules-nav a, .research-group, .worldflow-item, .worldflow-topic
) { font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui); }
:is(#routeContent, .inspector-body) :is(
  .register-list button, .obj-choice, .walk-choice, .culture-choice,
  .inter-list button, .inter-list a.inter-choice, .research-group,
  .worldflow-item, .worldflow-topic
) strong { min-width: 0; font-size: inherit; font-weight: 650; line-height: inherit; overflow-wrap: anywhere; }
:is(#routeContent, .inspector-body) :is(.worldflow-item, .worldflow-topic) small {
  font-size: var(--type-meta); line-height: 1.5;
}
:is(#routeContent, .inspector-body) :is(
  .inter-tabs a, .walk-nav a, .obj-tabs a, .culture-tabs a,
  .inspector-tabs button, .filter-row input, .filter-row select,
  .inter-filter input, .inter-filter select, .inter-mobile-picker select,
  .obj-filter input, .obj-filter select, .obj-mobile-picker select,
  .walk-mobile-picker select, .walk-filter input, .walk-filter select, .culture-filter-row input,
  .culture-filter-row select, .culture-mobile-picker select, .research-picker select,
  .worldflow-index-filter input, .worldflow-index-filter select, .relation-mobile-picker select,
  .dialogue-mobile-picker select, .actor-mobile-picker select, .register-search
) { font: 600 var(--type-ui)/var(--type-ui-leading) var(--font-ui); }
/* Cultural details reuse the room-reader roles, including their source controls. */
:is(body[data-route="trivia"] #routeContent, body.culture-inspector-open #inspectorBody) .culture-text-block summary {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
}
:is(body[data-route="trivia"] #routeContent, body.culture-inspector-open #inspectorBody) .culture-text-block header code {
  font: 400 var(--type-meta)/1.5 var(--font-code);
}

/* Absent/unknown values and passive labels are not made clickable by this CSS.
   Link/button size is independent of its containing table or helper paragraph. */
:is(#routeContent, .inspector-body, .document-dialog-actions, .protection-records-dialog) :is(
  a.chip, button.chip, a.button, button.button, .actor-state-link.chip,
  .inter-links a, .inter-links button, .obj-links a, .obj-links button,
  .walk-links a, .walk-links button, .culture-links a, .culture-links button,
  .rules-related a, .rules-related button, button[data-open-doc], .walk-copy
) {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
  min-width: 0; max-width: 100%; white-space: normal; overflow-wrap: anywhere;
}
:is(#routeContent, .inspector-body) :is(a.inter-ref, a.obj-ref, a.walk-ref, a.culture-ref) {
  font-family: var(--font-ui); font-size: var(--type-inline-chip); font-weight: 650; line-height: 1.35;
}
:is(#routeContent, .inspector-body) :is(
  a.inter-holder-link, a.inter-holder-room, .obj-chain a, .obj-children a,
  .obj-state-list a, .walk-anchors a, .culture-card-anchors a
) { font-size: var(--type-ui); line-height: var(--type-ui-leading); }

/* Technical notation is a separate role. Nested code inside a chip/command
   inherits its size instead of multiplying .88em again and again. */
:is(#routeContent, .inspector-body) :is(code, kbd, .code, .inter-code, .inter-command) {
  font-family: var(--font-code);
}
:is(#routeContent, .inspector-body) :is(pre, .json-block, .command-box, .walk-command-input) {
  font: 500 var(--type-small)/1.6 var(--font-code); overflow-wrap: anywhere;
}
:is(#routeContent, .inspector-body) :is(pre, .command-box, .walk-command-input, .inter-ref, .obj-ref, .walk-ref, .culture-ref) :is(code, kbd) {
  font-family: var(--font-code); font-size: 1em; line-height: inherit;
}
:is(.evidence-tooltip, .inter-tooltip) { font: 500 var(--type-small)/1.5 var(--font-ui); }

/* 15 shares the room-reader controls; source notation and evidence stay distinct. */
body:is([data-route="internals"],[data-route="method"],[data-route="glossary"]) #routeContent :is(.inter-technical, .inter-holder-details) summary {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
}
body:is([data-route="internals"],[data-route="method"],[data-route="glossary"]) #routeContent :is(.inter-count-badge, .inter-step-number) {
  font: 800 var(--type-caption)/1 var(--font-ui);
  font-variant-numeric: tabular-nums;
}
/* Same number/name roles as #roomRegisterList; IDs are not count badges. */
body:is([data-route="internals"],[data-route="method"],[data-route="glossary"]) #routeContent .inter-row-number {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-code);
  font-variant-numeric: tabular-nums;
}
body:is([data-route="internals"],[data-route="method"],[data-route="glossary"]) #routeContent .inter-list button > strong {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
  color: inherit;
}

/* Inspector controls need the same type as main-page controls even when the
   inspector is a sibling of #routeContent. Width stays responsive, not fixed. */
.inspector-tabs button { font: 600 var(--type-ui)/var(--type-ui-leading) var(--font-ui); }
.relation-table { font: 400 var(--type-ui)/var(--type-ui-leading) var(--font-ui); }
.inspector-head h2 { font: 700 1.5rem/1.25 var(--font-editorial); overflow-wrap: anywhere; }
.atlas-tooltip p { font: 400 var(--type-small)/1.6 var(--font-ui); }
.media-image-provenance { font: 400 var(--type-meta)/1.5 var(--font-code); }

/* 12: handbook coordinates are readable table values, not tiny metadata. */
body[data-route="protection"] .protection-records-table :is(th, td) {
  font: 400 var(--type-ui)/1.5 var(--font-ui);
}
body[data-route="protection"] .protection-records-table thead th { font-weight: 650; }
body[data-route="protection"] .protection-records-table code {
  font: 500 var(--type-small)/1.5 var(--font-code);
}
body[data-route="protection"] #routeContent .protection-step h3 {
  font: 700 var(--type-card-title)/1.35 var(--font-editorial); overflow-wrap: anywhere;
}
body[data-route="protection"] .protection-records-dialog :is(.small, .protection-records-head p) {
  font: 400 var(--type-small)/1.6 var(--font-ui); overflow-wrap: anywhere;
}
body[data-route="protection"] .protection-records-foot {
  font: 400 var(--type-meta)/1.5 var(--font-ui);
}

/* 09: explicit roles also cover the calculator's previously undersized fields. */
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(
  .rules-contents a, .combat-lab-tabs button, .combat-target-switch button,
  input[type="search"], input[type="number"], select, select option
) { font: 600 var(--type-ui)/var(--type-ui-leading) var(--font-ui); }
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.rules-related a, .inter-links a, .inter-links button, .combat-ranking-grid li button) {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.rules-filter label, .combat-field > span, .combat-adjustment-grid label > span, .combat-run-toolbar > label > span) {
  font: 650 var(--type-small)/1.5 var(--font-ui); letter-spacing: normal; text-transform: none;
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(#rulesCount, .combat-result-metrics small, .combat-run-readout > div > span, .combat-live-actor > div span, .combat-live-object > div span) {
  font: 400 var(--type-small)/1.6 var(--font-ui); text-transform: none;
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.combat-log li > span, .combat-result-divider span, .combat-ranking-grid li strong) {
  font: 600 var(--type-meta)/1.5 var(--font-ui); letter-spacing: normal;
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.rules-sources > summary, .combat-adjustments > summary, .combat-rankings > summary, .combat-simulator-evidence > summary) {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.rules-topic p, .rules-steps > li > strong, .combat-log li strong, .combat-flow strong) {
  font-size: var(--type-body); line-height: var(--type-leading);
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.rules-chapter-body p, .rules-chapter-body li) { font-size: var(--type-body); line-height: var(--type-leading); }
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.rules-limits p, .combat-object-facts p) { font-size: var(--type-small); line-height: 1.6; }
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent :is(.combat-stats h2, .combat-melee h2, .combat-weapons h2, .combat-outcomes h2, .shoot-card h2, .shoot-notes h2) {
  font: 700 var(--type-section-title)/1.3 var(--font-editorial);
}
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent .combat-open-label { font: 600 var(--type-ui)/1.4 var(--font-ui); text-transform: none; }
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent .combat-atlas[open] .combat-open-label { font-size: 0; }
body:is([data-route="mechanics"],[data-route="combat"]) #routeContent .combat-atlas[open] .combat-open-label::after { font-size: var(--type-ui); }

/* 11: same type roles as the room readers, including comparison captions and
   expanded technical details. Native audio/video controls retain browser UI. */
body[data-route="media"] #routeContent .media-audio-card h2 {
  font: 700 var(--type-section-title)/1.3 var(--font-editorial); overflow-wrap: anywhere;
}
body[data-route="media"] #routeContent .media-disclosure-body h3 {
  font: 700 var(--type-card-title)/1.35 var(--font-editorial); text-transform: none; letter-spacing: normal;
}
body[data-route="media"] #routeContent :is(.media-disclosure summary, .image-zoom > span strong) {
  font: 650 var(--type-ui)/var(--type-ui-leading) var(--font-ui);
}
body[data-route="media"] #routeContent .media-quickfacts dt { letter-spacing: normal; text-transform: none; }
body[data-route="media"] #routeContent .data-table { font: 400 var(--type-body)/1.7 var(--font-ui); }
body[data-route="media"] #routeContent .data-table thead th { font: 650 var(--type-ui)/1.4 var(--font-ui); }
body[data-route="media"] #routeContent .media-picture-table tbody th strong { font: 650 var(--type-meta)/1.5 var(--font-code); }
body[data-route="media"] #routeContent :is(.media-picture-table tbody th small, .missing-media span) { font: 400 var(--type-small)/1.6 var(--font-ui); }
body[data-route="media"] .media-image-head strong { font: 700 var(--type-card-title)/1.35 var(--font-editorial); }
body[data-route="media"] .media-image-head #mediaImageMeta { font: 400 var(--type-meta)/1.5 var(--font-ui); }
body[data-route="media"] .document-dialog-actions :is(a.button, button.button) { font: 650 var(--type-ui)/1.4 var(--font-ui); }

/* The atlas selection strip is intentionally compact. Longer labels wrap;
   unlike article controls, its graph-scaled labels are not enlarged here. */

@media (max-width: 680px) {
  /* No shrinking the menu type to conceal overflow on narrow screens. */
  :is(#routeContent, .inspector-body) :is(.inter-tabs, .rules-nav, .walk-nav, .obj-tabs, .culture-tabs) {
    min-width: 0; max-width: 100%;
  }
}
