/* ============================================================
   Scrived — UI styles
   Inspired by classic book-design aesthetics: warm cream paper,
   serif typography, restrained accent color, three-pane editor.
   ============================================================ */

:root {
  --bg-page:        #f5f3ee;
  --bg-card:        #ffffff;
  --bg-paper:       #fdfbf6;
  --bg-rail:        #efece4;
  --bg-rail-hover:  #e6e2d6;
  --bg-topbar:      #1d1b18;
  --bg-topbar-soft: #2a2723;

  --ink-1:    #1a1a1a;
  --ink-2:    #3a3733;
  --ink-3:    #6a665e;
  --ink-4:    #98948a;
  --ink-5:    #c8c3b6;

  --line:     #e2dcd0;
  --line-soft:#ece8dc;
  --line-strong:#d4cdba;
  /* Alias used across marketing.css (blog, articles, landing tables). It was
     referenced 20+ times but never defined, so it always fell back to the
     light #e2dcd0 — borders never darkened in dark mode. Aliasing it to
     --line makes every one of those borders theme-aware in a single place
     (same value in light mode, so nothing changes there). */
  --line-1:   var(--line);

  --accent:        #8b6914;   /* old gold */
  --accent-soft:   #b58a2f;
  --accent-bg:     #f6efdb;
  --danger:        #a93b2a;
  --success:       #4d7a2e;

  --font-sans:  'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
  --font-serif: 'Lora', Georgia, 'Times New Roman', serif;
  --font-display: 'Playfair Display', Georgia, serif;

  --radius-sm: 4px;
  --radius:    8px;
  --radius-lg: 12px;

  --shadow-1: 0 1px 2px rgba(0,0,0,.04), 0 2px 8px rgba(0,0,0,.04);
  --shadow-2: 0 2px 6px rgba(0,0,0,.06), 0 12px 36px rgba(0,0,0,.08);
  --shadow-paper: 0 1px 0 rgba(0,0,0,.02), 0 12px 28px rgba(60,52,32,.08);

  --topbar-h: 56px;
}

/* ============================================================
   Dark theme — applied via [data-theme="dark"] on <html>.
   Set before render by an inline script in layout.php so there's
   no flash of light theme on cold loads.
   Only the editor chrome + writing-view manuscript darken; the
   preview / print / EPUB views still use the book's saved theme
   colors (via --pv-* vars), so WYSIWYG stays accurate.
   ============================================================ */
:root[data-theme="dark"] {
  --bg-page:        #1c1a17;
  --bg-card:        #26221d;
  --bg-paper:       #26221d;
  --bg-rail:        #1a1815;
  --bg-rail-hover:  #2a2722;
  --bg-topbar:      #131210;
  --bg-topbar-soft: #1d1b18;

  --ink-1: #ebe6d8;
  --ink-2: #c8c2b3;
  --ink-3: #968f80;
  --ink-4: #6c655a;
  --ink-5: #45403a;

  --line:        #3a342c;
  --line-soft:   #2d2823;
  --line-strong: #4d4538;

  --accent:      #c8a042;
  --accent-soft: #d4a64f;
  --accent-bg:   #322816;
  --danger:      #d36456;
  --success:     #84b66a;

  --shadow-1: 0 1px 2px rgba(0,0,0,.35), 0 2px 8px rgba(0,0,0,.25);
  --shadow-2: 0 2px 6px rgba(0,0,0,.4),  0 12px 36px rgba(0,0,0,.5);
  --shadow-paper: 0 1px 0 rgba(0,0,0,.25), 0 12px 28px rgba(0,0,0,.4);
}

/* A handful of literal-colored values can't ride the var system
   directly (they're either inline styles set by JS or were typed as
   literal hex codes). Override them per-component in dark mode. */
:root[data-theme="dark"] body { background: var(--bg-page); }
:root[data-theme="dark"] .editor-topbar { background: var(--bg-topbar); }
:root[data-theme="dark"] .topbar-iconbtn:hover { background: rgba(255,255,255,.06); }
:root[data-theme="dark"] .ql-toolbar.ql-snow {
  background: var(--bg-paper);
  border-color: var(--line);
}
:root[data-theme="dark"] .ql-toolbar.ql-snow .ql-stroke { stroke: var(--ink-2); }
:root[data-theme="dark"] .ql-toolbar.ql-snow .ql-fill   { fill:   var(--ink-2); }
:root[data-theme="dark"] .ql-toolbar.ql-snow .ql-picker-label { color: var(--ink-2); }
:root[data-theme="dark"] .ql-toolbar.ql-snow button:hover .ql-stroke,
:root[data-theme="dark"] .ql-toolbar.ql-snow button.ql-active .ql-stroke { stroke: var(--accent); }
:root[data-theme="dark"] .ql-toolbar.ql-snow button:hover .ql-fill,
:root[data-theme="dark"] .ql-toolbar.ql-snow button.ql-active .ql-fill   { fill:   var(--accent); }
:root[data-theme="dark"] .ql-snow .ql-picker-options {
  background: var(--bg-card);
  border-color: var(--line);
  color: var(--ink-1);
}
:root[data-theme="dark"] .ql-editor blockquote { color: var(--ink-2); }
:root[data-theme="dark"] .ql-editor::before { color: var(--ink-4); } /* placeholder */
:root[data-theme="dark"] input,
:root[data-theme="dark"] textarea,
:root[data-theme="dark"] select {
  background: var(--bg-paper);
  color: var(--ink-1);
  border-color: var(--line);
}
:root[data-theme="dark"] input::placeholder,
:root[data-theme="dark"] textarea::placeholder { color: var(--ink-4); }
:root[data-theme="dark"] input[type=checkbox],
:root[data-theme="dark"] input[type=radio] { accent-color: var(--accent); }

/* Modal / panel backgrounds were hardcoded to white in places. */
:root[data-theme="dark"] .preset-pop,
:root[data-theme="dark"] .timer-popover,
:root[data-theme="dark"] .tts-popover,
:root[data-theme="dark"] .find-modal,
:root[data-theme="dark"] .prose-panel,
:root[data-theme="dark"] .bible-mention-popover,
:root[data-theme="dark"] .res-link-composer,
:root[data-theme="dark"] .chapter-settings-popover,
:root[data-theme="dark"] .resource-detail,
:root[data-theme="dark"] .bible-form,
:root[data-theme="dark"] .corkboard-card,
:root[data-theme="dark"] .diff-chapter,
:root[data-theme="dark"] .bible-sidebar,
:root[data-theme="dark"] .resources-sidebar {
  background: var(--bg-card);
  color: var(--ink-1);
}

/* Find-modal backdrop should be deeper in dark mode. */
:root[data-theme="dark"] .find-backdrop { background: rgba(0,0,0,.55); }

/* Diff page row colors: tweak the green/red highlights so they read on dark. */
:root[data-theme="dark"] .diff-row-add { background: rgba(80, 160, 80, 0.12); }
:root[data-theme="dark"] .diff-row-del { background: rgba(200, 70, 70, 0.12); }
:root[data-theme="dark"] .diff-row-del .diff-row-text { color: #d49591; }
:root[data-theme="dark"] .diff-row-mod { background: rgba(200, 160, 60, 0.10); }

/* Prose-check and find-match highlights stay legible. */
:root[data-theme="dark"] ::highlight(prose-weasel) { background-color: rgba(200,160,60,.25); }
:root[data-theme="dark"] ::highlight(prose-wordy)  { background-color: rgba(90,130,210,.22); }
:root[data-theme="dark"] ::highlight(prose-repeat) { background-color: rgba(200,80,80,.22); }
:root[data-theme="dark"] ::highlight(prose-flash)  { background-color: rgba(70,135,255,.85); color: #fff; }
:root[data-theme="dark"] ::highlight(find-match)   { background-color: rgba(255,200,80,.30); }
:root[data-theme="dark"] ::highlight(find-current) { background-color: rgba(255,160,60,.55); }

/* TOC dotted leader and page-sheet borders use ink colors that need
   to stay on the dark page. The fallbacks via CSS vars cover most. */
:root[data-theme="dark"] .save-status { color: var(--ink-3); }
:root[data-theme="dark"] .preset-pop-row:hover { background: var(--bg-rail-hover); }

/* Library cards + admin pages use the same vars, so they pick up
   dark mode automatically. Cover fallbacks need a lighter tint. */
:root[data-theme="dark"] .cover-fallback { background: var(--bg-rail); color: var(--ink-2); }

*, *::before, *::after { box-sizing: border-box; }
html, body { height: 100%; }

/* The browser's default `[hidden] { display: none }` rule loses to any
   class-based display rule (e.g. `.field { display: block }`). Force
   it to win — most "hidden" elements in this app are toggled via the
   HTML `hidden` attribute and we want that to actually work. */
[hidden] { display: none !important; }
body {
  margin: 0;
  background: var(--bg-page);
  color: var(--ink-1);
  font-family: var(--font-sans);
  font-size: 14px;
  line-height: 1.5;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

a { color: var(--accent); text-decoration: none; }
a:hover { color: var(--accent-soft); }

/* ---------- Buttons ---------- */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 6px;
  padding: 9px 18px;
  border-radius: var(--radius-sm);
  border: 1px solid transparent;
  font-family: var(--font-sans);
  font-size: 13.5px;
  font-weight: 500;
  letter-spacing: .01em;
  cursor: pointer;
  background: #fff;
  color: var(--ink-1);
  border-color: var(--line);
  transition: all .15s ease;
  text-decoration: none;
  line-height: 1;
}
.btn:hover { background: var(--bg-rail); border-color: var(--line-strong); }
.btn-primary {
  background: var(--ink-1);
  color: #fff;
  border-color: var(--ink-1);
}
.btn-primary:hover { background: #000; border-color: #000; color: #fff; }
.btn-ghost { background: transparent; border-color: transparent; }
.btn-ghost:hover { background: var(--bg-rail); border-color: var(--line); }
.btn-block { width: 100%; }
.btn-lg { padding: 12px 24px; font-size: 14px; }
.btn-sm { padding: 6px 12px; font-size: 12.5px; }
.btn-link {
  background: none; border: none; padding: 0;
  color: var(--ink-3); font-size: 13px; cursor: pointer;
  font-family: inherit;
}
.btn-link:hover { color: var(--ink-1); }
.btn-icon {
  width: 26px; height: 26px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: #fff;
  color: var(--ink-2);
  font-size: 18px;
  line-height: 1;
  cursor: pointer;
  display: inline-flex; align-items: center; justify-content: center;
  padding: 0;
}
.btn-icon:hover { background: var(--bg-rail); border-color: var(--line-strong); color: var(--ink-1); }

/* ---------- Form fields ---------- */
.field { display: block; margin-bottom: 14px; }
.field-label {
  display: block;
  font-size: 12px;
  font-weight: 500;
  color: var(--ink-3);
  margin-bottom: 5px;
  letter-spacing: .03em;
  text-transform: uppercase;
}
.field input,
.field select,
.field textarea,
.select {
  width: 100%;
  padding: 9px 11px;
  border: 1px solid var(--line);
  background: var(--bg-paper);
  border-radius: var(--radius-sm);
  font-family: var(--font-sans);
  font-size: 14px;
  color: var(--ink-1);
  transition: border-color .12s ease, box-shadow .12s ease;
}
.field input:focus,
.field select:focus,
.field textarea:focus,
.select:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
  background: #fff;
}
/* Radios and checkboxes inside a .field (e.g. inline pickers) should keep
   their native size — without this they inherit the text-input width:100%. */
.field input[type="radio"],
.field input[type="checkbox"] {
  width: auto;
  padding: 0;
  margin: 0;
  background: transparent;
  border: 0;
  box-shadow: none;
}
.field-toggle {
  display: flex; align-items: center; gap: 8px;
  font-size: 13px; color: var(--ink-2);
  margin: 8px 0;
  cursor: pointer;
}
.field-toggle-tight {
  margin: 2px 0 4px;
  font-size: 12px;
  color: var(--ink-3);
}
.req { color: var(--danger); }

.alert {
  padding: 10px 14px;
  border-radius: var(--radius-sm);
  font-size: 13px;
  margin-bottom: 16px;
}
.alert-error {
  background: #fdf0ed;
  color: #8a2c1d;
  border-left: 3px solid var(--danger);
}

.inline-form { display: inline; }

/* ============================================================
   AUTH (login)
   ============================================================ */
.auth-body { background: var(--bg-page); }
.auth-shell {
  min-height: 100vh;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 40px 20px;
}
.auth-card {
  width: 100%;
  max-width: 400px;
  background: var(--bg-card);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-2);
  padding: 40px 36px;
  border: 1px solid var(--line);
}
.auth-brand { text-align: center; margin-bottom: 28px; }
.brand-mark {
  font-family: var(--font-display);
  font-size: 32px;
  font-weight: 600;
  margin: 0;
  letter-spacing: .02em;
  color: var(--ink-1);
}
/* The wordmark links back to the homepage — keep the heading look,
   hint at clickability on hover. */
.brand-mark a {
  color: inherit;
  text-decoration: none;
}
.brand-mark a:hover { color: var(--accent); }
.brand-tag {
  font-family: var(--font-serif);
  font-style: italic;
  font-size: 13px;
  color: var(--ink-3);
  margin: 4px 0 0;
}
.auth-form { margin-top: 8px; }
.auth-form .btn { margin-top: 8px; }
.auth-footer {
  text-align: center;
  font-size: 12px;
  color: var(--ink-4);
  margin: 24px 0 0;
}
/* Trust line under the register submit — same quiet tone as .auth-footer,
   sitting inside the form so it reads as part of the decision moment. */
.auth-trust-line {
  text-align: center;
  font-size: 12px;
  color: var(--ink-4);
  margin: 12px 0 0;
}
/* Buyer-intent note (?plan=lifetime): slightly more present than the
   trust line — it explains what the submit button will do next. */
.auth-plan-note {
  text-align: center;
  font-size: 12.5px;
  line-height: 1.5;
  color: var(--ink-3);
  margin: 12px 0 0;
}

/* Show/hide toggle for password inputs. Wrap the input in
   .field-reveal and add a .field-reveal-btn button after it. */
.field-reveal { position: relative; display: block; }
.field-reveal input { padding-right: 40px; }
.field-reveal-btn {
  position: absolute;
  right: 6px;
  top: 50%;
  transform: translateY(-50%);
  border: 0;
  background: transparent;
  padding: 4px;
  line-height: 0;
  color: var(--ink-4);
  cursor: pointer;
  border-radius: var(--radius-sm);
}
.field-reveal-btn:hover { color: var(--ink-1); }
.field-reveal-btn .eye-closed { display: none; }
.field-reveal-btn.is-showing .eye-open { display: none; }
.field-reveal-btn.is-showing .eye-closed { display: inline; }

/* ============================================================
   APP shell + topbar
   ============================================================ */
.app-body { background: var(--bg-page); min-height: 100vh; }
.app-shell { min-height: 100vh; display: flex; flex-direction: column; }

.topbar {
  height: var(--topbar-h);
  background: var(--bg-topbar);
  color: #fff;
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 0 24px;
}
.topbar-left, .topbar-right { display: flex; align-items: center; gap: 14px; }
.brand {
  font-family: var(--font-display);
  font-size: 20px;
  font-weight: 600;
  color: #fff;
  letter-spacing: .02em;
}
.brand:hover { color: #fff; opacity: .85; }
.user-chip {
  font-size: 12.5px;
  color: #c8c3b6;
  padding: 4px 10px;
  border: 1px solid #3a3733;
  border-radius: 999px;
}
.topbar .btn-link { color: #c8c3b6; }
.topbar .btn-link:hover { color: #fff; }

/* Library / shell topbar wordmark next to the gold S logo */
.topbar-wordmark {
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
  color: #fff;
  letter-spacing: .12em;
}
.topbar-signout {
  font-size: 12.5px;
  letter-spacing: .01em;
}

/* ============================================================
   LIBRARY
   ============================================================ */
.library {
  flex: 1;
  padding: 40px 48px 80px;
  max-width: 1400px;
  margin: 0 auto;
  width: 100%;
}
.library-hero {
  display: flex;
  align-items: end;
  justify-content: space-between;
  margin-bottom: 32px;
  gap: 16px;
}
.library-title {
  font-family: var(--font-display);
  font-size: 36px;
  font-weight: 600;
  margin: 0 0 4px;
  letter-spacing: .01em;
}
.library-sub {
  margin: 0;
  color: var(--ink-3);
  font-size: 14px;
}
.library-actions { display: flex; gap: 10px; align-items: center; flex-wrap: wrap; justify-content: flex-end; }
.library-search-input {
  width: 220px;
  padding: 8px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13.5px;
  color: var(--ink-1);
  background: var(--bg-paper);
  transition: border-color .12s, box-shadow .12s, background .12s;
}
.library-search-input:focus {
  outline: none;
  border-color: var(--accent);
  background: #fff;
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
}

/* ---- Cross-book search results panel ---- */
.library-search-results {
  margin: 0 0 32px;
}
.library-search-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 14px;
}
.library-search-title {
  margin: 0;
  font-family: var(--font-display);
  font-size: 22px;
  font-weight: 500;
  color: var(--ink-1);
}
.library-search-empty {
  padding: 18px 0;
  color: var(--ink-3);
  font-style: italic;
}
.library-search-body {
  display: flex;
  flex-direction: column;
  gap: 18px;
}
.lsr-book {
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 16px 20px 14px;
}
.lsr-book-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 10px;
  border-bottom: 1px solid var(--line-soft);
  padding-bottom: 8px;
}
.lsr-book-title {
  margin: 0;
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 500;
  color: var(--ink-1);
}
.lsr-book-meta {
  font-size: 12px;
  color: var(--ink-3);
  letter-spacing: .02em;
}
.lsr-chapters {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.lsr-chapter {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: 4px 10px;
}
.lsr-chapter-title {
  background: transparent;
  border: none;
  padding: 0;
  font: inherit;
  font-size: 13.5px;
  color: var(--accent);
  cursor: pointer;
  text-align: left;
  font-weight: 500;
  text-decoration: none;
}
.lsr-chapter-title:hover { text-decoration: underline; }
.lsr-chapter-count {
  font-size: 11px;
  color: var(--ink-3);
  background: var(--bg-rail);
  padding: 1px 8px;
  border-radius: 999px;
  align-self: start;
  font-variant-numeric: tabular-nums;
}
.lsr-snippets {
  list-style: none;
  margin: 4px 0 0;
  padding: 0;
  grid-column: 1 / -1;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.lsr-snippet {
  font-family: var(--font-serif, Georgia, serif);
  font-size: 13px;
  line-height: 1.55;
  color: var(--ink-2);
}
.lsr-snippet mark {
  background: rgba(255,235,170,.7);
  color: var(--ink-1);
  padding: 0 2px;
  border-radius: 2px;
  font-weight: 500;
}
.lsr-ctx { color: var(--ink-3); }
.lsr-truncated {
  margin: 4px 0 0;
  font-size: 11.5px;
  color: var(--ink-3);
  font-style: italic;
  grid-column: 1 / -1;
}

/* Streak + goal stats. Four pills under the "13 books · 868,884 words"
   line — populated client-side from /api/writing-sessions/stats. The
   .is-empty state mutes them so a brand new user (or one between
   sessions) sees a calmer row instead of four zeros at full contrast. */
.library-stats {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  margin-top: 14px;
}
.library-stats[hidden] { display: none; }
.library-stat {
  display: inline-flex;
  align-items: baseline;
  gap: 6px;
  padding: 7px 12px 7px 10px;
  background: var(--bg-card);
  border: 1px solid var(--line-soft);
  border-radius: 999px;
  font-size: 13px;
  color: var(--ink-2);
  transition: opacity .15s ease;
}
.library-stat-icon {
  font-size: 14px;
  line-height: 1;
}
.library-stat-value {
  font-weight: 600;
  color: var(--ink-1);
  font-variant-numeric: tabular-nums;
}
.library-stat-label {
  font-size: 12px;
  color: var(--ink-3);
}
.library-stats.is-empty .library-stat { opacity: .55; }
.library-actions .select { width: 200px; }

.book-grid {
  list-style: none;
  margin: 0; padding: 0;
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(190px, 1fr));
  gap: 32px 24px;
}
.book-card {
  position: relative;
  display: flex;
  flex-direction: column;
}
/* Drag-reorder visuals kick in on grids marked .is-draggable — every
   series grid, plus the standalone grid when in Manual sort. Cards stay
   [draggable=true] everywhere (so they can be dragged into a series),
   but the grab cursor + drop styling only show where a drop sticks. */
.book-grid.is-draggable .book-card { cursor: grab; }
.book-card.is-dragging { opacity: .55; cursor: grabbing; }
.book-grid.is-draggable .book-card.drag-over {
  outline: 2px dashed var(--accent);
  outline-offset: 4px;
}

/* Drag handle — six-dot grip in the top-left corner of each card.
   Hidden by default; revealed when the grid is in Manual sort.
   Positioned outside the cover-link so a click on the handle never
   navigates into the editor. */
.book-drag-handle {
  position: absolute;
  top: 6px;
  left: 6px;
  width: 26px;
  height: 26px;
  display: none;
  align-items: center;
  justify-content: center;
  background: rgba(255,255,255,.92);
  border: 1px solid var(--line);
  border-radius: 6px;
  color: var(--ink-2);
  cursor: grab;
  padding: 0;
  z-index: 2;
  box-shadow: 0 1px 3px rgba(0,0,0,.08);
  transition: background .12s ease, color .12s ease;
}
.book-grid.is-draggable .book-drag-handle { display: inline-flex; }
.book-drag-handle:hover { background: #fff; color: var(--ink-1); }
.book-drag-handle:active { cursor: grabbing; }

/* Series selector in the Book details modal: select + inline "New". */
.series-select-row { display: flex; gap: 8px; align-items: stretch; }
.series-select-row select { flex: 1 1 auto; }
.series-select-row .btn-sm { flex: 0 0 auto; white-space: nowrap; }

/* ----- Series shelves ----- */
.series-shelf { margin-bottom: 38px; }
.series-head {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 18px;
  padding-bottom: 8px;
  border-bottom: 1px solid var(--line);
}
.series-toggle {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 26px; height: 26px;
  padding: 0;
  border: 1px solid var(--line);
  border-radius: 6px;
  background: var(--paper-2, #fff);
  color: var(--ink-2);
  cursor: pointer;
  flex: 0 0 auto;
}
.series-toggle:hover { color: var(--ink-1); background: #fff; }
.series-caret { transition: transform .15s ease; }
.series-shelf.is-collapsed .series-caret { transform: rotate(-90deg); }
.series-title {
  margin: 0;
  font-size: 1.15rem;
  font-weight: 600;
  color: var(--ink-1);
}
.series-count {
  font-size: .8rem;
  color: var(--ink-3, var(--ink-2));
  background: var(--paper-2, #f3efe6);
  border: 1px solid var(--line);
  border-radius: 999px;
  padding: 2px 10px;
  white-space: nowrap;
}
.series-actions {
  margin-left: auto;
  display: flex;
  gap: 8px;
}
.series-delete { color: var(--danger, #b3261e); }
.series-delete:hover { color: var(--danger, #b3261e); }

/* Collapsed → hide the grid but keep the header (and its drop target
   for dragging a book in, via the count badge / header zone).
   .book-grid (not .series-grid) so the standalone shelf collapses too. */
.series-shelf.is-collapsed .book-grid { display: none; }

/* The standalone shelf header is lighter — it's a catch-all, not a
   user-named series, so no rename/delete chrome (it does collapse). */
.series-shelf.is-standalone .series-title { color: var(--ink-2); font-weight: 500; }

/* Empty grids still need height so they're a reachable drop target.
   `.is-empty` is toggled by library.js (a CSS :empty selector wouldn't
   match because the PHP-rendered <ul> contains whitespace). */
.book-grid.is-empty {
  min-height: 90px;
  border: 1px dashed var(--line);
  border-radius: 8px;
  display: grid;
  place-items: center;
}
.book-grid.is-empty::after {
  content: 'Drag a book here';
  color: var(--ink-3, var(--ink-2));
  font-size: .85rem;
}
/* Highlight the shelf a dragged card is hovering over. */
.book-grid.drag-target {
  outline: 2px dashed var(--accent);
  outline-offset: 6px;
  border-radius: 8px;
}
.book-cover-link { display: block; }
.book-cover {
  position: relative;
  aspect-ratio: 2 / 3;
  background: var(--ink-1);
  border-radius: 3px;
  overflow: hidden;
  box-shadow: var(--shadow-paper);
  transition: transform .2s ease, box-shadow .2s ease;
}
.book-card:hover .book-cover {
  transform: translateY(-3px);
  box-shadow: 0 4px 0 rgba(0,0,0,.04), 0 16px 36px rgba(60,52,32,.16);
}
/* Show the full cover (no cropping) inside the uniform 2:3 grid frame.
   Anything narrower or taller than 2:3 letterboxes against the dark frame. */
.book-cover img { width: 100%; height: 100%; object-fit: contain; display: block; }
.book-cover-fallback {
  position: absolute; inset: 0;
  background: linear-gradient(155deg, #2c2820 0%, #1a1715 100%);
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
  text-align: center;
  padding: 20px 14px;
  border-left: 4px solid var(--accent);
}
.book-cover-title {
  font-family: var(--font-display);
  font-size: 16px;
  line-height: 1.25;
  color: #f1ead2;
  font-weight: 500;
}
.book-cover-author {
  font-family: var(--font-serif);
  font-style: italic;
  font-size: 11px;
  color: rgba(241,234,210,.6);
  margin-top: 12px;
  letter-spacing: .04em;
}
.book-meta { padding: 12px 4px 0; }
.book-title {
  font-family: var(--font-display);
  font-size: 15px;
  font-weight: 500;
  margin: 0 0 2px;
  color: var(--ink-1);
  line-height: 1.3;
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
}
.book-info {
  margin: 0;
  font-size: 12px;
  color: var(--ink-3);
}

/* Book-stage pill — author-only writing-stage marker shown beneath the
   word count on each library card. Click cycles draft → revising →
   complete → live → draft. Complete (manuscript finished) is blue;
   Live (published) takes the green. */
.book-status-pill {
  display: inline-block;
  margin-top: 6px;
  padding: 3px 9px;
  border-radius: 999px;
  border: 1px solid var(--line);
  background: var(--bg-paper);
  color: var(--ink-2);
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease, transform .12s ease;
}
.book-status-pill:hover { transform: translateY(-1px); }
.book-status-pill[data-current="draft"]    { background: #eceef1; color: #4b5560; border-color: #d6dae0; }
.book-status-pill[data-current="revising"] { background: #fbe4cb; color: #8a4d18; border-color: #efc99a; }
.book-status-pill[data-current="complete"] { background: #dbe6f5; color: #2d5583; border-color: #bcd0ec; }
.book-status-pill[data-current="live"]     { background: #d8ebd8; color: #2f6633; border-color: #b8d8b8; }
.book-status-pill.is-saving { opacity: .55; cursor: progress; }

/* Per-book word-target progress. Rendered only when word_target > 0
   on the book row. Color is keyed to the same status palette as the
   pill above so the card reads as a single colored unit. */
.book-progress {
  position: relative;
  height: 6px;
  margin: 6px 0 8px;
  background: var(--bg-rail);
  border-radius: 999px;
  overflow: hidden;
  border: 1px solid var(--line-soft);
}
.book-progress-fill {
  position: absolute;
  inset: 0 auto 0 0;
  background: #b6bcc3;
  transition: width .25s ease;
  border-radius: inherit;
}
.book-progress[data-status="draft"]    .book-progress-fill { background: #b6bcc3; }
.book-progress[data-status="revising"] .book-progress-fill { background: #f0a253; }
.book-progress[data-status="complete"] .book-progress-fill { background: #6f9bd8; }
.book-progress[data-status="live"]     .book-progress-fill { background: #6cba6c; }
.book-progress-label {
  position: absolute;
  right: 6px;
  top: 50%;
  transform: translateY(-50%);
  font-size: 9.5px;
  font-weight: 600;
  letter-spacing: .04em;
  color: var(--ink-3);
  background: rgba(255,255,255,.85);
  padding: 0 4px;
  border-radius: 3px;
  pointer-events: none;
}

/* ---------- /settings page ---------- */
.topbar-back-link {
  color: rgba(241,234,210,.78);
  text-decoration: none;
  font-size: 13px;
  letter-spacing: .04em;
  margin-left: 8px;
  transition: color .12s ease;
}
.topbar-back-link:hover { color: #f1ead2; }

.settings-main {
  max-width: 720px;
  margin: 0 auto;
  padding: 36px 28px 80px;
}
.settings-hero {
  position: relative;
  padding-bottom: 22px;
  border-bottom: 1px solid var(--line-soft);
  margin-bottom: 28px;
}
.settings-title {
  font-family: var(--font-display);
  font-size: 30px;
  font-weight: 500;
  margin: 0 0 6px;
  color: var(--ink-1);
}
.settings-sub {
  margin: 0;
  font-size: 13px;
  color: var(--ink-3);
  line-height: 1.55;
  max-width: 560px;
}
.settings-save-status {
  position: absolute;
  top: 4px;
  right: 0;
  font-size: 11px;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: var(--ink-3);
}
.settings-save-status[data-state="busy"]  { color: var(--ink-2); }
.settings-save-status[data-state="idle"]  { color: var(--success, #2f6633); }
.settings-save-status[data-state="error"] { color: var(--danger, #b04646); }

.settings-form {
  display: flex;
  flex-direction: column;
  gap: 18px;
}
.settings-card {
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius-lg);
  overflow: hidden;
}
.settings-card-head {
  padding: 18px 22px 12px;
  border-bottom: 1px solid var(--line-soft);
}
.settings-card-head h2 {
  font-family: var(--font-display);
  font-size: 17px;
  font-weight: 500;
  margin: 0 0 4px;
  color: var(--ink-1);
}
.settings-card-sub {
  margin: 0;
  font-size: 12.5px;
  color: var(--ink-3);
  line-height: 1.5;
}
.settings-card-body { padding: 20px 22px 6px; }
.settings-card-body .field { margin-bottom: 18px; }

/* ----- Settings › Page templates management list ----- */
.mt-list { padding-bottom: 14px; }
.mt-group + .mt-group { margin-top: 18px; }
.mt-group-head {
  margin: 0 0 8px;
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
.mt-rows { list-style: none; margin: 0; padding: 0; }
.mt-row {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 10px 0;
  border-bottom: 1px solid var(--line);
}
.mt-row:last-child { border-bottom: none; }
.mt-row-label {
  flex: 1 1 auto;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  font-size: 14px;
  color: var(--ink-1);
  cursor: text;
  padding: 3px 6px;
  margin: -3px -6px;
  border-radius: 5px;
  border: 1px solid transparent;
}
.mt-row-label:hover,
.mt-row-label:focus {
  background: var(--bg-rail);
  border-color: var(--line);
  outline: none;
}
.mt-row-input {
  flex: 1 1 auto;
  min-width: 0;
  font: inherit;
  font-size: 14px;
  color: var(--ink-1);
  padding: 3px 6px;
  margin: -1px 0;
  border: 1px solid var(--accent);
  border-radius: 5px;
  background: var(--bg-1, #fff);
}
.mt-row-input:focus { outline: none; }
.mt-row-actions {
  flex: 0 0 auto;
  display: inline-flex;
  gap: 6px;
}
.mt-row-delete:hover,
.mt-row-delete:focus { color: var(--danger, #c0392b); }

/* ----- Settings › Membership card ----- */
.membership-state { font-size: 14px; line-height: 1.5; color: var(--ink-1); }
.membership-state.is-member strong { color: var(--accent); }
.membership-price {
  display: flex;
  align-items: baseline;
  gap: 10px;
  flex-wrap: wrap;
}
.membership-price-was {
  font-size: 18px;
  color: var(--ink-3);
  text-decoration: line-through;
}
.membership-price-now {
  font-family: var(--font-display);
  font-size: 30px;
  font-weight: 700;
  color: var(--ink-1);
  line-height: 1;
}
.membership-price-note { font-size: 12.5px; color: var(--ink-3); }

/* ----- Authenticated app footer (library, etc.) ----- */
.app-foot {
  border-top: 1px solid var(--line);
  margin-top: 48px;
}
.app-foot-inner {
  max-width: 1180px;
  margin: 0 auto;
  padding: 26px 32px 34px;
  display: flex;
  align-items: center;
  gap: 18px 26px;
  flex-wrap: wrap;
}
.app-foot-brand {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  text-decoration: none;
}
.app-foot-brand .logo-mark {
  width: 28px; height: 28px;
  display: inline-flex; align-items: center; justify-content: center;
  background: var(--accent);
  color: #fff;
  border-radius: 6px;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 16px;
}
/* Uploaded-logo variant: drop the accent tile, contain the image. */
.app-foot-brand img.logo-mark { background: transparent; object-fit: contain; }
.app-foot-name {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 16px;
  color: var(--ink-1);
}
.app-foot-links {
  display: flex;
  gap: 22px;
  flex-wrap: wrap;
  margin-left: auto;
}
.app-foot-links a {
  color: var(--ink-2);
  text-decoration: none;
  font-size: 14px;
}
.app-foot-links a:hover,
.app-foot-links a:focus { color: var(--accent); }
.app-foot-fineprint {
  flex-basis: 100%;
  margin: 2px 0 0;
  font-size: 12.5px;
  color: var(--ink-3);
}

.settings-card-body .field:last-child { margin-bottom: 14px; }
.settings-card-body .select { width: 100%; }
.field-hint {
  display: block;
  font-size: 11.5px;
  color: var(--ink-3);
  margin-top: 6px;
  line-height: 1.45;
}
.book-delete {
  position: absolute;
  top: 8px; right: 8px;
  width: 26px; height: 26px;
  border-radius: 50%;
  border: none;
  background: rgba(255,255,255,.92);
  color: var(--ink-2);
  font-size: 18px;
  line-height: 1;
  cursor: pointer;
  opacity: 0;
  transition: opacity .15s ease, background .15s ease, color .15s ease;
  box-shadow: 0 1px 4px rgba(0,0,0,.16);
}
.book-card:hover .book-delete { opacity: 1; }
.book-delete:hover { background: var(--danger); color: #fff; }

.book-duplicate {
  position: absolute;
  top: 8px; right: 40px;
  width: 26px; height: 26px;
  border-radius: 50%;
  border: none;
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(255,255,255,.92);
  color: var(--ink-2);
  cursor: pointer;
  opacity: 0;
  transition: opacity .15s ease, background .15s ease, color .15s ease;
  box-shadow: 0 1px 4px rgba(0,0,0,.16);
}
.book-card:hover .book-duplicate { opacity: 1; }
.book-duplicate:hover { background: var(--accent); color: #fff; }
.book-duplicate:disabled { cursor: default; opacity: .5; }

.empty-state {
  text-align: center;
  padding: 80px 24px;
  background: var(--bg-card);
  border: 1px dashed var(--line-strong);
  border-radius: var(--radius-lg);
}
.empty-illustration {
  font-size: 56px;
  margin-bottom: 16px;
  filter: grayscale(.2);
}
.empty-state h2 {
  font-family: var(--font-display);
  font-size: 22px;
  margin: 0 0 8px;
}
.empty-state p {
  color: var(--ink-3);
  max-width: 460px;
  margin: 0 auto 24px;
}

/* ============================================================
   CONFIRMATION DIALOG (Scrived.confirm replacement for window.confirm)
   ============================================================ */
.sc-confirm {
  position: fixed;
  inset: 0;
  z-index: 260; /* above toasts and overlays so it's the only thing
                   demanding the user's attention */
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 24px;
  opacity: 0;
  transition: opacity .15s ease;
  pointer-events: none;
}
.sc-confirm.is-open { opacity: 1; pointer-events: auto; }
.sc-confirm[hidden] { display: none; }
.sc-confirm-backdrop {
  position: absolute; inset: 0;
  background: rgba(20, 18, 14, .50);
}
.sc-confirm-card {
  position: relative;
  width: min(440px, 100%);
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 10px;
  box-shadow: 0 24px 60px rgba(0,0,0,.32);
  padding: 22px 24px 18px;
}
.sc-confirm-title {
  margin: 0 0 6px;
  font-family: var(--font-display);
  font-size: 17px;
  font-weight: 500;
  color: var(--ink-1);
  line-height: 1.35;
}
.sc-confirm-msg {
  margin: 0 0 18px;
  font-size: 13.5px;
  color: var(--ink-2);
  line-height: 1.5;
  white-space: pre-line;
}
.sc-confirm-actions {
  display: flex;
  justify-content: flex-end;
  gap: 8px;
}
.sc-confirm-cancel,
.sc-confirm-ok {
  border: 1px solid var(--line);
  background: #fff;
  color: var(--ink-2);
  padding: 8px 16px;
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13px;
  cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.sc-confirm-cancel:hover { background: var(--bg-rail); color: var(--ink-1); }
.sc-confirm-ok.is-primary {
  background: var(--accent);
  border-color: var(--accent);
  color: #fff;
  font-weight: 600;
}
.sc-confirm-ok.is-primary:hover { filter: brightness(.92); }
.sc-confirm-ok.is-danger {
  background: var(--danger, #b04646);
  border-color: var(--danger, #b04646);
  color: #fff;
  font-weight: 600;
}
.sc-confirm-ok.is-danger:hover { filter: brightness(.92); }
.sc-confirm-ok:focus-visible,
.sc-confirm-cancel:focus-visible {
  outline: none;
  box-shadow: 0 0 0 3px rgba(139,105,20,.20);
}
:root[data-theme="dark"] .sc-confirm-card {
  background: var(--bg-card);
  border-color: var(--line);
}

/* ============================================================
   KEYBOARD SHORTCUT HELP OVERLAY (?)
   ============================================================ */
.kbd-help {
  position: fixed;
  inset: 0;
  z-index: 240;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 32px 16px;
  opacity: 0;
  transition: opacity .15s ease;
  pointer-events: none;
}
.kbd-help.is-open { opacity: 1; pointer-events: auto; }
.kbd-help[hidden] { display: none; }
.kbd-backdrop {
  position: absolute; inset: 0;
  background: rgba(20, 18, 14, .42);
}
.kbd-card {
  position: relative;
  width: min(720px, 100%);
  max-height: calc(100vh - 64px);
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 10px;
  box-shadow: 0 24px 60px rgba(0,0,0,.28);
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
.kbd-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 20px;
  border-bottom: 1px solid var(--line);
}
.kbd-title {
  margin: 0;
  font-family: var(--font-display);
  font-size: 18px;
  font-weight: 500;
  color: var(--ink-1);
}
.kbd-close {
  width: 28px; height: 28px;
  border: none; background: transparent;
  color: var(--ink-3);
  font-size: 22px; line-height: 1;
  cursor: pointer; padding: 0;
  border-radius: 4px;
}
.kbd-close:hover { color: var(--ink-1); background: var(--bg-rail); }
.kbd-body {
  flex: 1;
  overflow-y: auto;
  padding: 18px 20px;
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 22px 32px;
}
.kbd-group { min-width: 0; }
.kbd-group-title {
  margin: 0 0 8px;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: var(--ink-3);
}
.kbd-list { margin: 0; padding: 0; }
.kbd-row {
  display: grid;
  grid-template-columns: auto 1fr;
  gap: 10px;
  align-items: baseline;
  padding: 5px 0;
  font-size: 13px;
}
.kbd-keys {
  margin: 0;
  flex-shrink: 0;
  white-space: nowrap;
}
.kbd-desc {
  margin: 0;
  color: var(--ink-2);
  line-height: 1.4;
}
.kbd-plus {
  display: inline-block;
  margin: 0 2px;
  color: var(--ink-3);
  font-size: 11px;
}
.kbd-help kbd,
.kbd-foot kbd {
  display: inline-block;
  min-width: 22px;
  padding: 1px 6px;
  border: 1px solid var(--line);
  border-radius: 3px;
  background: var(--bg-paper);
  font-family: var(--font-sans);
  font-size: 11.5px;
  font-weight: 600;
  color: var(--ink-1);
  text-align: center;
  box-shadow: 0 1px 0 var(--line);
}
.kbd-foot {
  padding: 10px 20px;
  border-top: 1px solid var(--line-soft);
  background: var(--bg-rail);
  font-size: 11.5px;
  color: var(--ink-3);
  text-align: center;
}
:root[data-theme="dark"] .kbd-card {
  background: var(--bg-card);
  border-color: var(--line);
}
:root[data-theme="dark"] .kbd-help kbd,
:root[data-theme="dark"] .kbd-foot kbd {
  background: var(--bg-rail);
}
@media (max-width: 640px) {
  .kbd-body { grid-template-columns: 1fr; }
}

/* ============================================================
   COMMAND PALETTE (Cmd/Ctrl+K)
   ============================================================ */
.cmd-palette {
  position: fixed;
  inset: 0;
  z-index: 250; /* above toasts so it can be dismissed cleanly */
  display: flex;
  align-items: flex-start;
  justify-content: center;
  padding-top: 12vh;
  opacity: 0;
  transition: opacity .14s ease;
  pointer-events: none;
}
.cmd-palette.is-open { opacity: 1; pointer-events: auto; }
.cmd-palette[hidden] { display: none; }
.cmd-backdrop {
  position: absolute; inset: 0;
  background: rgba(20, 18, 14, .42);
}
.cmd-card {
  position: relative;
  width: min(640px, calc(100vw - 32px));
  max-height: calc(100vh - 24vh);
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 10px;
  box-shadow: 0 24px 60px rgba(0,0,0,.28);
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
.cmd-input {
  width: 100%;
  padding: 16px 18px;
  font-family: inherit;
  font-size: 15px;
  color: var(--ink-1);
  border: none;
  border-bottom: 1px solid var(--line);
  background: transparent;
  outline: none;
}
.cmd-input::placeholder { color: var(--ink-3); }
.cmd-list {
  list-style: none;
  margin: 0;
  padding: 6px 0;
  overflow-y: auto;
  flex: 1;
}
.cmd-item {
  display: grid;
  grid-template-columns: 28px 1fr auto;
  align-items: center;
  gap: 10px;
  padding: 8px 16px;
  cursor: pointer;
  font-size: 14px;
}
.cmd-item.is-active {
  background: var(--accent-soft, rgba(139,105,20,.12));
}
.cmd-icon {
  font-size: 16px;
  text-align: center;
  flex-shrink: 0;
  line-height: 1;
}
.cmd-title {
  color: var(--ink-1);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.cmd-meta {
  font-size: 11.5px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .08em;
  white-space: nowrap;
}
.cmd-empty {
  padding: 16px;
  text-align: center;
  color: var(--ink-3);
  font-style: italic;
}
.cmd-foot {
  display: flex;
  gap: 16px;
  padding: 8px 16px;
  border-top: 1px solid var(--line-soft);
  background: var(--bg-rail);
  font-size: 11.5px;
  color: var(--ink-3);
}
.cmd-foot kbd {
  display: inline-block;
  min-width: 20px;
  padding: 1px 5px;
  margin: 0 2px;
  border: 1px solid var(--line);
  border-radius: 3px;
  background: #fff;
  font-family: inherit;
  font-size: 11px;
  color: var(--ink-2);
}
:root[data-theme="dark"] .cmd-card {
  background: var(--bg-card);
  border-color: var(--line);
}
:root[data-theme="dark"] .cmd-foot kbd { background: var(--bg-rail); }

/* ============================================================
   TOAST NOTIFICATIONS
   ============================================================ */
.toast-container {
  position: fixed;
  top: 16px;
  right: 16px;
  z-index: 200; /* above modals, popovers, the rail panel */
  display: flex;
  flex-direction: column;
  gap: 8px;
  pointer-events: none; /* let clicks fall through the gaps */
  max-width: 360px;
}
.toast {
  display: flex;
  align-items: flex-start;
  gap: 10px;
  padding: 10px 10px 10px 14px;
  background: #fff;
  border: 1px solid var(--line);
  border-left: 3px solid var(--ink-3);
  border-radius: var(--radius-sm);
  box-shadow: 0 8px 24px rgba(0,0,0,.12);
  font-size: 13.5px;
  line-height: 1.45;
  color: var(--ink-1);
  pointer-events: auto;
  opacity: 0;
  transform: translateY(-6px);
  transition: opacity .18s ease, transform .18s ease;
}
.toast.is-visible { opacity: 1; transform: translateY(0); }
.toast.is-leaving { opacity: 0; transform: translateY(-6px); }
.toast-msg { flex: 1; min-width: 0; word-break: break-word; }
.toast-close {
  flex-shrink: 0;
  width: 22px; height: 22px;
  border: none; background: transparent;
  color: var(--ink-3);
  font-size: 18px; line-height: 1;
  cursor: pointer; padding: 0;
  border-radius: 4px;
}
.toast-close:hover { color: var(--ink-1); background: var(--bg-rail); }
.toast-info    { border-left-color: var(--accent); }
.toast-success { border-left-color: #4a8b4d; }
.toast-warn    { border-left-color: #d18a3d; }
.toast-error   { border-left-color: var(--danger, #b04646); }
:root[data-theme="dark"] .toast {
  background: var(--bg-card);
  color: var(--ink-1);
  border-color: var(--line);
}

/* ============================================================
   MODAL
   ============================================================ */
.modal {
  position: fixed; inset: 0;
  z-index: 100;
  display: flex; align-items: center; justify-content: center;
  opacity: 0; pointer-events: none;
  transition: opacity .18s ease;
}
.modal.is-open { opacity: 1; pointer-events: auto; }
.modal-backdrop {
  position: absolute; inset: 0;
  background: rgba(20,17,12,.55);
}
.modal-card {
  position: relative;
  width: 100%;
  max-width: 440px;
  background: var(--bg-card);
  border-radius: var(--radius-lg);
  padding: 28px 32px 24px;
  box-shadow: var(--shadow-2);
  transform: translateY(8px);
  transition: transform .18s ease;
}
.modal.is-open .modal-card { transform: translateY(0); }
.modal-title {
  font-family: var(--font-display);
  font-size: 22px;
  margin: 0 0 18px;
}
.modal-actions {
  display: flex;
  justify-content: flex-end;
  gap: 8px;
  margin-top: 18px;
}

/* ============================================================
   EDITOR — Atticus-style layout
   ============================================================ */
.editor-body {
  height: 100vh;
  overflow: hidden;
  background: var(--bg-page);
}
.editor-shell {
  height: 100vh;
  display: flex;
  flex-direction: column;
}

/* ----- Top bar ----- */
.editor-topbar {
  height: var(--topbar-h);
  background: var(--bg-topbar);
  color: #fff;
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  padding: 0 18px;
  gap: 16px;
}
.editor-topbar .topbar-left   { justify-self: start; gap: 12px; }
.editor-topbar .topbar-center { justify-self: center; }
.editor-topbar .topbar-right  { justify-self: end; gap: 14px; }

.topbar-logo {
  width: 30px; height: 30px;
  background: var(--accent);
  border-radius: 6px;
  display: inline-flex; align-items: center; justify-content: center;
  color: #fff;
  font-family: var(--font-display);
  font-size: 18px;
  font-weight: 700;
  text-decoration: none;
}
.topbar-logo:hover { color: #fff; opacity: .92; }

/* ----- Uploaded brand logo (replaces the lettered "P" mark) -----
   The <img> keeps the .logo-mark class so each context's existing box
   sizing still applies; these rules drop the accent tile behind it and
   make it sit as a contained image. The context is baked into the
   selector so it out-specifies the base `.<ctx> .logo-mark { background:
   accent }` rules. */
.topbar-logo img.logo-mark,
.admin-logo img.logo-mark {
  background: transparent;
  object-fit: contain;
}
/* Main + snapshot-diff topbars paint the accent tile on the *wrapper*;
   blank it when it holds an uploaded logo and let the image fill the slot. */
.topbar-logo:has(img.logo-mark) { background: transparent; }
.topbar-logo img.logo-mark { width: 100%; height: 100%; border-radius: 6px; }
.topbar-home {
  width: 30px; height: 30px;
  display: inline-flex; align-items: center; justify-content: center;
  color: #c8c3b6;
  border-radius: 6px;
  border: 1px solid transparent;
}
.topbar-home:hover { color: #fff; background: var(--bg-topbar-soft); border-color: #3a3733; }

.topbar-title-block {
  display: flex; align-items: center; gap: 14px;
  min-width: 0;
}
.topbar-title-text {
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
  color: #fff;
  letter-spacing: .12em;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 320px;
}
.btn-edit-details {
  background: transparent;
  border: 1px solid #3a3733;
  color: #c8c3b6;
  font-family: inherit;
  font-size: 12.5px;
  padding: 5px 12px;
  border-radius: 999px;
  cursor: pointer;
  letter-spacing: .01em;
  transition: background .15s ease, color .15s ease, border-color .15s ease;
  white-space: nowrap;
}
.btn-edit-details:hover { background: var(--bg-topbar-soft); color: #fff; border-color: #555048; }

.view-tabs {
  display: flex;
  gap: 2px;
  background: var(--bg-topbar-soft);
  border-radius: 999px;
  padding: 3px;
}
.view-tab {
  background: transparent;
  border: none;
  color: #c8c3b6;
  padding: 7px 22px;
  font-size: 13px;
  font-weight: 500;
  border-radius: 999px;
  cursor: pointer;
  font-family: inherit;
  letter-spacing: .02em;
  transition: all .15s ease;
}
.view-tab:hover { color: #fff; }
.view-tab.is-active {
  background: #fff;
  color: var(--ink-1);
}

.topbar-iconbtn {
  width: 30px; height: 30px;
  display: inline-flex; align-items: center; justify-content: center;
  background: transparent;
  border: 1px solid transparent;
  border-radius: 6px;
  color: #c8c3b6;
  cursor: pointer;
  padding: 0;
}
.topbar-iconbtn:hover { color: #fff; background: var(--bg-topbar-soft); border-color: #3a3733; }

/* ============================================================
   Custom tooltips (assets/js/tooltips.js).
   The JS shim copies [title] onto opted-in icon buttons into a
   [data-tip] attribute and removes the native title (so the
   browser's slow grey OS tooltip doesn't double up). This rule
   surfaces a styled tooltip below the button on hover/focus.
   ============================================================ */
[data-tip] {
  position: relative;
}
[data-tip]::after {
  content: attr(data-tip);
  position: absolute;
  top: calc(100% + 6px);
  left: 50%;
  transform: translateX(-50%) translateY(-2px);
  background: #1d1b18;
  color: #f5f1e6;
  padding: 5px 10px;
  border-radius: 5px;
  font-family: var(--font-sans);
  font-size: 11.5px;
  font-weight: 500;
  letter-spacing: .01em;
  white-space: nowrap;
  pointer-events: none;
  opacity: 0;
  z-index: 1100;
  box-shadow: 0 4px 14px rgba(0,0,0,.25);
  transition: opacity .12s ease, transform .12s ease;
}
[data-tip]:hover::after,
[data-tip]:focus-visible::after {
  opacity: 1;
  transform: translateX(-50%) translateY(0);
}

/* Compact export pills in the topbar (next to the Export view icon).
   Single click triggers a download via export.js. */
.topbar-export-pill {
  height: 28px;
  padding: 0 12px;
  display: inline-flex;
  align-items: center;
  gap: 6px;
  border-radius: 999px;
  background: var(--bg-topbar-soft);
  border: 1px solid #3a3733;
  color: #d8d3c5;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .05em;
  text-transform: uppercase;
  cursor: pointer;
  white-space: nowrap;
}
.topbar-export-pill:hover {
  color: #fff;
  background: var(--accent);
  border-color: var(--accent);
}
.topbar-export-pill[aria-busy="true"] {
  opacity: .65;
  pointer-events: none;
  cursor: progress;
}

/* Export dropdown (topbar). The toggle reuses .topbar-export-pill; the menu
   drops below it, anchored to the wrapper. */
.topbar-export { position: relative; display: inline-flex; }
.topbar-export-toggle .export-caret { transition: transform .15s ease; opacity: .85; }
.topbar-export-toggle[aria-expanded="true"] {
  color: #fff;
  background: var(--accent);
  border-color: var(--accent);
}
.topbar-export-toggle[aria-expanded="true"] .export-caret { transform: rotate(180deg); }
.topbar-export-menu {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  z-index: 250;
  min-width: 210px;
  padding: 6px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-sm);
  box-shadow: 0 12px 32px rgba(0,0,0,.18);
  display: flex;
  flex-direction: column;
  gap: 1px;
}
.topbar-export-menu[hidden] { display: none; }
.export-menu-item {
  display: flex;
  align-items: center;
  gap: 10px;
  width: 100%;
  padding: 8px 10px;
  background: transparent;
  border: 0;
  border-radius: 6px;
  color: var(--ink-1);
  font-family: var(--font-sans);
  font-size: 13px;
  text-align: left;
  cursor: pointer;
}
.export-menu-item:hover { background: var(--bg-rail); }
.export-menu-item svg { color: var(--ink-3); flex: none; }
.export-menu-item[aria-busy="true"] { opacity: .6; pointer-events: none; cursor: progress; }
.topbar-export-sep { height: 1px; background: var(--line); margin: 5px 4px; }

.topbar-divider { width: 1px; height: 22px; background: #3a3733; display: inline-block; }
.user-avatar {
  width: 30px; height: 30px;
  border-radius: 50%;
  background: var(--accent);
  color: #fff;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: .03em;
  display: inline-flex; align-items: center; justify-content: center;
}

/* Account menu — avatar button + sign-out dropdown (in-book topbars). */
.user-menu { position: relative; display: inline-flex; }
.user-avatar-btn {
  border: none;
  padding: 0;
  cursor: pointer;
  font-family: inherit;
}
.user-avatar-btn:hover { filter: brightness(1.08); }
.user-menu-dropdown {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  z-index: 250;
  min-width: 190px;
  padding: 6px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-sm);
  box-shadow: 0 12px 32px rgba(0,0,0,.18);
}
.user-menu-dropdown[hidden] { display: none; }
.user-menu-identity {
  padding: 6px 10px 8px;
  margin-bottom: 4px;
  border-bottom: 1px solid var(--line);
}
.user-menu-name {
  display: block;
  font-size: 13px;
  font-weight: 600;
  color: var(--ink-1);
  word-break: break-word;
}
.user-menu-form { margin: 0; }
.user-menu-item {
  display: block;
  width: 100%;
  padding: 8px 10px;
  border: 0;
  border-radius: 6px;
  background: transparent;
  color: var(--ink-1);
  font-family: var(--font-sans);
  font-size: 13px;
  text-align: left;
  text-decoration: none;
  cursor: pointer;
}
.user-menu-item:hover { background: var(--bg-rail); }
.user-menu-signout { color: var(--danger); }
.user-menu-signout:hover { background: var(--danger); color: #fff; }

.save-status {
  font-size: 12.5px;
  color: #d4cfc1;
  font-weight: 500;
  letter-spacing: .03em;
  margin-right: 4px;
}
.save-status[data-state=dirty]   { color: #e6c876; }
.save-status[data-state=busy]    { color: #e6c876; }
.save-status[data-state=error]   { color: #f08c7c; }
.save-status[data-state=idle]    { color: #b8d6a3; }
.save-status[data-state=idle]::before {
  content: '✓ ';
  color: #8bc56a;
  font-weight: 700;
}

/* ----- Three-pane layout (sidebar | manuscript | rail-panel | rail) ----- */
.editor-body-grid {
  flex: 1;
  display: grid;
  grid-template-columns: 268px 1fr 56px;
  overflow: hidden;
  background: var(--bg-page);
}
.editor-body-grid.is-panel-open {
  grid-template-columns: 268px 1fr 280px 56px;
}

/* ----- Sidebar (sectioned chapter list) ----- */
.chapter-sidebar {
  background: var(--bg-rail);
  border-right: 1px solid var(--line);
  display: flex; flex-direction: column;
  overflow: hidden;
}
.sidebar-scroll {
  flex: 1;
  overflow-y: auto;
  padding: 14px 8px 14px;
}
.sidebar-section { margin-bottom: 14px; }
.sidebar-section-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 4px 8px 4px 6px;
  border-radius: var(--radius-sm);
}
.sidebar-section-toggle {
  flex: 1;
  display: inline-flex;
  align-items: center;
  gap: 8px;
  background: transparent;
  border: none;
  padding: 4px 4px;
  cursor: pointer;
  font-family: inherit;
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-3);
}
.sidebar-section-toggle:hover { color: var(--ink-1); }
.sidebar-section-toggle .chev {
  color: var(--ink-4);
  transition: transform .15s ease;
}
.sidebar-section.is-collapsed .sidebar-section-toggle .chev { transform: rotate(-90deg); }
.sidebar-section.is-collapsed .chapter-list { display: none; }
.sidebar-section-add {
  width: 22px; height: 22px;
  border: 1px solid transparent;
  background: transparent;
  color: var(--ink-3);
  font-size: 16px;
  line-height: 1;
  border-radius: 4px;
  cursor: pointer;
  padding: 0;
}
.sidebar-section-add:hover { color: var(--ink-1); border-color: var(--line-strong); background: #fff; }

/* Status filter chip row — sits above the chapter sections. Reuses
   .res-chip from the corkboard, slightly tightened for the narrow
   sidebar. Wraps to a second row on smaller widths rather than
   horizontally scrolling. */
.sidebar-filter {
  display: flex;
  flex-wrap: wrap;
  gap: 4px;
  padding: 10px 10px 6px;
  border-bottom: 1px solid var(--line-soft);
}
.sidebar-filter .res-chip {
  padding: 3px 9px;
  font-size: 11px;
  letter-spacing: .02em;
}

/* Per-section status distribution. Lives inside the section toggle so
   the dots+numbers float to the right edge of the section heading. */
.sidebar-section-counts {
  margin-left: auto;
  display: inline-flex;
  align-items: center;
  gap: 8px;
  font-weight: 500;
  font-size: 10px;
  letter-spacing: 0;
  text-transform: none;
  color: var(--ink-3);
}
.sidebar-section-counts .sc-pill {
  display: inline-flex;
  align-items: center;
  gap: 3px;
  font-variant-numeric: tabular-nums;
}
.sidebar-section-counts .sc-dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: #b6bcc3;
}
.sidebar-section-counts .sc-dot[data-status="draft"]    { background: #b6bcc3; }
.sidebar-section-counts .sc-dot[data-status="revising"] { background: #f0a253; }
.sidebar-section-counts .sc-dot[data-status="revised"]  { background: #b27dd8; }
.sidebar-section-counts .sc-dot[data-status="final"]    { background: #6cba6c; }

/* Filter hide rules. The active chapter is always kept visible
   (`:not(.is-active)`) so the author can't lose track of where they
   are by toggling a filter that excludes their current document. */
.chapter-sidebar[data-filter="draft"]    .chapter-item:not([data-status="draft"]):not(.is-active),
.chapter-sidebar[data-filter="revising"] .chapter-item:not([data-status="revising"]):not(.is-active),
.chapter-sidebar[data-filter="revised"]  .chapter-item:not([data-status="revised"]):not(.is-active),
.chapter-sidebar[data-filter="final"]    .chapter-item:not([data-status="final"]):not(.is-active) {
  display: none;
}
/* When any non-"all" filter is active, hide the front-matter
   placeholder row too — its data-status is undefined so it would
   otherwise sit there during a filtered view. */
.chapter-sidebar:not([data-filter="all"]) .sidebar-empty-row { display: none; }

/* Empty-state for the status filter. Lives at the top of the
   .sidebar-scroll region so it's always visible, even when sections
   below it scroll. Italics + muted color so it reads as guidance
   rather than a section. */
.sidebar-no-matches {
  margin: 12px 8px;
  padding: 12px 14px;
  text-align: center;
  font-size: 12px;
  font-style: italic;
  color: var(--ink-3);
  background: var(--bg-paper);
  border: 1px dashed var(--line);
  border-radius: var(--radius-sm);
}

.chapter-list {
  list-style: none;
  margin: 4px 0 0;
  padding: 0;
}
.chapter-item {
  display: grid;
  /* number | name | status-dot | comments-badge? | words | delete
     — items are pinned to columns explicitly below so an empty badge
     row still keeps words+delete aligned with neighbouring rows. */
  grid-template-columns: 22px 1fr auto auto auto auto;
  align-items: center;
  gap: 8px;
  padding: 7px 10px 7px 8px;
  margin: 1px 0;
  border-radius: var(--radius-sm);
  cursor: pointer;
  font-size: 13.5px;
  color: var(--ink-2);
  position: relative;
  transition: background .12s ease;
}
.chapter-item > .chapter-number,
.chapter-item > .chapter-bullet { grid-column: 1; }
.chapter-item > .chapter-name { grid-column: 2; }
.chapter-item > .chapter-status-dot { grid-column: 3; }
.chapter-item > .chapter-comments-badge { grid-column: 4; }
.chapter-item > .chapter-words { grid-column: 5; }
.chapter-item > .chapter-delete { grid-column: 6; }
.chapter-item:hover { background: var(--bg-rail-hover); }
/* Find-in-book match count — a leading accent pill (Atticus-style) shown
   on each chapter while a whole-book search is active. Absolutely placed in
   the gutter; .has-find-badge shifts the row's grid content right for it. */
.chapter-item.has-find-badge { padding-left: 30px; }
.chapter-find-badge {
  position: absolute;
  left: 4px;
  top: 50%;
  transform: translateY(-50%);
  min-width: 17px;
  height: 17px;
  padding: 0 4px;
  border-radius: 9px;
  background: var(--accent);
  color: #fff;
  font-size: 10.5px;
  font-weight: 700;
  font-style: normal;
  line-height: 1;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  box-sizing: border-box;
  z-index: 1;
}
.chapter-item.is-active {
  background: #fff;
  color: var(--ink-1);
  font-weight: 500;
  box-shadow: 0 1px 2px rgba(0,0,0,.04);
}
.chapter-item.is-active::before {
  content: '';
  position: absolute;
  left: -8px;
  top: 6px;
  bottom: 6px;
  width: 3px;
  background: var(--accent);
  border-radius: 0 2px 2px 0;
}
.chapter-number {
  font-family: var(--font-serif);
  font-style: italic;
  color: var(--ink-4);
  font-size: 12px;
  text-align: right;
  font-variant-numeric: tabular-nums;
}
.chapter-bullet {
  color: var(--ink-4);
  font-size: 14px;
  text-align: center;
  line-height: 1;
}
.chapter-item.is-active .chapter-number,
.chapter-item.is-active .chapter-bullet { color: var(--accent); }
.chapter-name {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.chapter-name-input {
  width: 100%;
  font-family: inherit;
  font-size: inherit;
  color: var(--ink-1);
  background: #fff;
  border: 1px solid var(--accent);
  border-radius: 3px;
  padding: 2px 6px;
  margin: -3px 0;
  outline: none;
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
}
.chapter-words {
  font-size: 11px;
  color: var(--ink-4);
  font-variant-numeric: tabular-nums;
}
/* Sidebar comment-count bubble. Neutral = author's own unresolved notes;
   .has-beta = at least one beta-reader comment in the bunch (gold tint). */
.chapter-comments-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 18px;
  height: 18px;
  padding: 0 5px;
  margin-left: 4px;
  border-radius: 999px;
  font-size: 10px;
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  letter-spacing: 0;
  background: var(--bg-rail);
  color: var(--ink-2);
  border: 1px solid var(--line-soft);
  flex-shrink: 0;
}
.chapter-comments-badge.has-beta {
  background: rgba(139,105,20,.16);
  color: var(--accent);
  border-color: rgba(139,105,20,.32);
}
.chapter-item.is-active .chapter-comments-badge {
  background: rgba(255,255,255,.18);
  color: #fff;
  border-color: rgba(255,255,255,.25);
}
.chapter-item.is-active .chapter-comments-badge.has-beta {
  background: rgba(255,235,150,.85);
  color: #6e4f14;
  border-color: rgba(255,235,150,1);
}

/* Writing-stage indicator. Same color vocabulary as the corkboard pill;
   click cycles through none → draft → revising → revised → final. */
.chapter-status-dot {
  width: 14px;
  height: 14px;
  border-radius: 50%;
  border: 1.5px solid var(--ink-4);
  background: transparent;
  padding: 0;
  cursor: pointer;
  flex-shrink: 0;
  opacity: .55;
  transition: opacity .12s ease, transform .12s ease, box-shadow .12s ease, background .12s ease, border-color .12s ease;
}
.chapter-status-dot:hover {
  opacity: 1;
  transform: scale(1.2);
  box-shadow: 0 0 0 2px var(--accent-soft);
}
/* Keyboard focus must be visible — the dot is an interactive control that
   cycles the writing stage. */
.chapter-status-dot:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
  opacity: 1;
}
/* State is signalled by colour AND a filled/outlined shape so it doesn't
   rely on hue alone: unset stages stay hollow, set stages fill. Draft is
   darkened for contrast against the pale sidebar. */
.chapter-status-dot[data-current="draft"]    { background: #9aa1ac; border-color: #656e7a; opacity: 1; }
.chapter-status-dot[data-current="revising"] { background: #f0a253; border-color: #b3670f; opacity: 1; }
.chapter-status-dot[data-current="revised"]  { background: #b27dd8; border-color: #6c4494; opacity: 1; }
.chapter-status-dot[data-current="final"]    { background: #6cba6c; border-color: #337333; opacity: 1; }
.chapter-item.is-active .chapter-status-dot[data-current="none"] { border-color: var(--accent); }
.chapter-delete {
  width: 22px; height: 22px;
  border: none;
  background: transparent;
  color: var(--ink-4);
  font-size: 18px;
  line-height: 1;
  border-radius: 3px;
  cursor: pointer;
  opacity: 0;
  padding: 0;
}
/* Reveal on hover, but also on keyboard focus and whenever anything in the
   row is focused — otherwise the control is mouse-only and unreachable by
   keyboard or touch. */
.chapter-item:hover .chapter-delete,
.chapter-item:focus-within .chapter-delete,
.chapter-delete:focus-visible { opacity: 1; }
.chapter-delete:focus-visible {
  outline: 2px solid var(--danger);
  outline-offset: 1px;
}
.chapter-delete:hover { background: var(--danger); color: #fff; }
.chapter-item.is-dragging { opacity: .5; }
.chapter-item.drag-over { box-shadow: 0 -2px 0 var(--accent); }

.sidebar-empty-row {
  list-style: none;
  padding: 6px 12px;
  font-size: 11.5px;
  color: var(--ink-4);
  font-style: italic;
}

.sidebar-footer {
  padding: 10px;
  border-top: 1px solid var(--line);
  background: var(--bg-rail);
}
.btn-add-chapter {
  width: 100%;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 6px;
  padding: 9px 12px;
  background: var(--ink-1);
  color: #fff;
  border: none;
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 13px;
  font-weight: 500;
  cursor: pointer;
  transition: background .12s ease;
}
.btn-add-chapter:hover { background: #000; }
.btn-add-chapter .plus {
  font-size: 16px; line-height: 1; font-weight: 600;
}
.btn-renumber-chapters {
  width: 100%;
  margin-top: 6px;
  padding: 7px 12px;
  background: transparent;
  color: var(--ink-3);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 12.5px;
  font-weight: 500;
  cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.btn-renumber-chapters:hover { background: var(--bg-1); color: var(--ink-1); border-color: var(--ink-4); }
.btn-renumber-chapters:disabled { opacity: .5; cursor: default; }

/* ----- Preset popover (opens off the section "+" buttons) ----- */
.preset-popover {
  position: absolute;
  z-index: 250;
  min-width: 240px;
  max-width: 300px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  font-size: 13px;
  overflow: hidden;
  animation: preset-pop-in .12s ease-out;
}
@keyframes preset-pop-in {
  from { opacity: 0; transform: translateY(-4px); }
  to   { opacity: 1; transform: translateY(0); }
}
.preset-popover-head {
  padding: 9px 14px;
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-3);
  background: var(--bg-rail);
  border-bottom: 1px solid var(--line);
}
.preset-popover-list {
  list-style: none;
  margin: 0;
  padding: 4px 0;
  max-height: 380px;
  overflow-y: auto;
}
.preset-popover-item {
  display: block;
  padding: 8px 14px;
  cursor: pointer;
  border-left: 3px solid transparent;
}
.preset-popover-item:hover,
.preset-popover-item:focus {
  background: var(--bg-rail);
  border-left-color: var(--accent);
  outline: none;
}
.preset-popover-label {
  display: block;
  font-weight: 500;
  color: var(--ink-1);
  line-height: 1.3;
}
.preset-popover-desc {
  display: block;
  font-size: 11.5px;
  color: var(--ink-3);
  margin-top: 2px;
  line-height: 1.3;
}
/* "My templates" sub-heading — a second labelled group under the presets. */
.preset-popover-subhead {
  border-top: 1px solid var(--line);
}
/* Saved-template rows carry an inline delete (×); lay them out as a row. */
.preset-popover-item[data-template-id] {
  display: flex;
  align-items: center;
  gap: 8px;
}
.preset-popover-item[data-template-id] .preset-popover-label {
  flex: 1 1 auto;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.preset-popover-del {
  flex: 0 0 auto;
  border: none;
  background: transparent;
  color: var(--ink-3);
  font-size: 16px;
  line-height: 1;
  width: 22px;
  height: 22px;
  border-radius: 4px;
  cursor: pointer;
  opacity: .55;
}
.preset-popover-del:hover,
.preset-popover-del:focus {
  opacity: 1;
  color: var(--danger, #c0392b);
  background: rgba(0, 0, 0, .06);
  outline: none;
}

/* ----- "Save as template" in the Chapter-properties rail panel ----- */
.inspector-template-tools {
  margin-top: 14px;
  padding-top: 14px;
  border-top: 1px solid var(--line);
}
.btn-save-template {
  display: inline-block;
  padding: 7px 12px;
  font-size: 13px;
  font-weight: 500;
  color: var(--ink-1);
  background: var(--bg-rail);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  cursor: pointer;
}
.btn-save-template:hover,
.btn-save-template:focus {
  border-color: var(--accent);
  color: var(--accent);
  outline: none;
}

/* ----- Email verification status chips (settings + admin users) ----- */
.email-status {
  display: inline-flex;
  align-items: center;
  margin-left: 6px;
  padding: 1px 7px;
  border-radius: 999px;
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: .04em;
  vertical-align: middle;
}
.email-status-ok {
  background: #e6f5ea;
  color: #1e6b35;
  border: 1px solid #c4e4cf;
}
.email-status-pending {
  background: #fbf1cf;
  color: #6b5210;
  border: 1px solid #efdf95;
}
:root[data-theme="dark"] .email-status-ok      { background: rgba(80,160,80,.18); color: #84b66a; border-color: rgba(80,160,80,.35); }
:root[data-theme="dark"] .email-status-pending { background: rgba(200,160,60,.18); color: #d4a64f; border-color: rgba(200,160,60,.35); }

/* ----- Auth-page extras (forgot/reset) ----- */
.auth-prose {
  font-family: var(--font-serif);
  font-size: 14.5px;
  line-height: 1.55;
  color: var(--ink-2);
  margin: 8px 0 18px;
}
.auth-link {
  color: var(--accent);
  text-decoration: none;
  font-weight: 500;
}
.auth-link:hover { text-decoration: underline; }
.auth-footer-sep {
  margin: 0 8px;
  color: var(--ink-4);
}
.alert-ok {
  background: #e6f5ea;
  color: #1e6b35;
  border: 1px solid #c4e4cf;
  padding: 10px 14px;
  border-radius: 6px;
  font-size: 13.5px;
}
:root[data-theme="dark"] .alert-ok { background: rgba(80,160,80,.12); color: #b6dca0; border-color: rgba(80,160,80,.3); }

/* ----- Settings page inline form bits (account / email) ----- */
.settings-inline-form { display: flex; flex-direction: column; gap: 12px; }
.settings-inline-actions { display: flex; gap: 8px; flex-wrap: wrap; }

/* ----- Manuscript (center) ----- */
.manuscript {
  display: flex;
  flex-direction: column;
  overflow: hidden;
  background: var(--bg-page);
  --editor-zoom: 1;
}
.page-stage {
  flex: 1;
  overflow-y: auto;
  padding: 0 40px 80px;
  display: flex;
  flex-direction: column;
  align-items: center;
}

/* Quill toolbar host — pinned at the top of the manuscript area */
.editor-toolbar-host {
  position: sticky;
  top: 0;
  z-index: 6;
  width: 100%;
  max-width: 760px;
  background: var(--bg-page);
  padding: 10px 0 8px;
}
.editor-toolbar-host .ql-toolbar.ql-snow {
  position: static;
  margin: 0;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 6px 10px;
  box-shadow: 0 1px 3px rgba(0,0,0,.04);
}

.page-sheet {
  width: 100%;
  max-width: 760px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: 2px;
  box-shadow: var(--shadow-paper);
  padding: 56px 72px 80px;
  /* `.page-stage` is a flex column. Default `flex-shrink: 1` would
     compress the page-sheet when content exceeds the visible area,
     which makes the cream background end mid-chapter. Pin it open. */
  flex-shrink: 0;
  height: auto;
  min-height: 100%;
  margin-top: 14px;
  transform: scale(var(--editor-zoom));
  transform-origin: top center;
}
.page-sheet[hidden] { display: none; }
.page-sheet-header { margin-bottom: 12px; position: relative; }

/* ---------- Chapter display gear (top-right of the page sheet) ---------- */
.chapter-settings-btn {
  position: absolute;
  top: -6px;
  right: -6px;
  width: 30px;
  height: 30px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: 1px solid transparent;
  border-radius: 50%;
  color: var(--ink-3);
  cursor: pointer;
  padding: 0;
  z-index: 4;
}
.chapter-settings-btn:hover { color: var(--ink-1); background: var(--bg-rail); border-color: var(--line); }
.chapter-settings-popover {
  position: absolute;
  top: 32px;
  right: -6px;
  z-index: 220;
  width: 270px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  font-size: 13px;
  animation: preset-pop-in .12s ease-out;
}
.chapter-settings-popover[hidden] { display: none; }
.chapter-settings-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 12px 14px 10px;
  border-bottom: 1px solid var(--line);
}
.chapter-settings-title {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
  margin: 0;
}
.chapter-settings-body {
  padding: 12px 14px 14px;
  display: flex;
  flex-direction: column;
  gap: 6px;
}

/* Opening background image block in the gear popover (migration 103). */
.chapter-opening-image {
  margin-top: 10px;
  padding-top: 10px;
  border-top: 1px solid var(--line-soft);
}
.chapter-opening-row {
  display: flex;
  align-items: center;
  gap: 10px;
}
.chapter-opening-thumb {
  width: 48px;
  height: 64px;
  object-fit: cover;
  border-radius: 4px;
  border: 1px solid var(--line);
  flex: 0 0 auto;
}
.chapter-opening-actions { display: flex; gap: 6px; flex-wrap: wrap; }

/* Sidebar glyph for full-page image chapters — replaces the word count. */
.chapter-plate-glyph { font-size: 12px; }

/* ---------- Per-chapter display overrides ---------- */
/* Live editor preview — hide heading not relevant (heading lives outside Quill),
   but invert and smaller-title can be felt in the editor too. */
.page-sheet.is-invert-colors {
  background: #1a1715;
  color: #f1ead2;
  border-color: #2a2723;
}
.page-sheet.is-invert-colors .chapter-title-input,
.page-sheet.is-invert-colors .chapter-subtitle-input,
.page-sheet.is-invert-colors .ql-editor {
  color: #f1ead2;
}
.page-sheet.is-invert-colors .ql-editor blockquote { color: #d6cdac; }
.page-sheet.is-invert-colors .chapter-settings-btn { color: #c8c3b6; }
.page-sheet.is-smaller-title .chapter-title-input { font-size: 18px; }

/* Hide-chapter-heading: dim the title + subtitle inputs so the author
   sees at-a-glance that they won't appear in the published book.
   (Inputs stay editable — this is purely visual feedback.) */
.page-sheet.is-hide-heading .chapter-title-input,
.page-sheet.is-hide-heading .chapter-subtitle-input {
  opacity: .35;
}

/* Faux drop cap inside the editor, mirroring what the published theme
   will render. Gated by data-theme-drop-cap (set from the theme's
   drop_cap setting) so turning the drop cap off in Formatting removes it
   here too — and by :not(.is-hide-drop-cap) so a single chapter can still
   suppress it. Uses the theme's drop-cap font when one is set. */
.page-sheet[data-theme-drop-cap="1"]:not(.is-hide-drop-cap) .ql-editor p:first-child::first-letter {
  font-family: var(--editor-drop-cap-font, var(--editor-heading-font, var(--font-display)));
  font-weight: 600;
  font-size: 2.6em;
  line-height: .85;
  float: left;
  padding: .04em .1em 0 0;
  color: inherit;
}
.page-sheet.is-hide-drop-cap .ql-editor p:first-child::first-letter { font-size: inherit; float: none; padding: 0; color: inherit; }

/* Preview view */
.preview-page.is-invert-colors {
  background: #1a1715;
  color: #f1ead2;
  --pv-text-color: #f1ead2;
  --pv-bg-color: #1a1715;
}
.preview-page.is-invert-colors .chapter-title,
.preview-page.is-invert-colors .chapter-num-label { color: #f1ead2; }
.preview-stage[data-drop-cap="1"] .preview-page.is-hide-drop-cap[data-kind="chapter"] .chapter-body p:first-of-type::first-letter {
  font-family: inherit;
  font-size: inherit;
  line-height: inherit;
  float: none;
  padding: 0;
  color: inherit;
  font-weight: inherit;
}

body[data-page-width="narrow"]   .page-sheet { max-width: 620px; }
body[data-page-width="wide"]     .page-sheet { max-width: 880px; }
body[data-page-width="narrow"]   .editor-toolbar-host { max-width: 620px; }
body[data-page-width="wide"]     .editor-toolbar-host { max-width: 880px; }

.page-sheet-empty {
  width: 100%;
  max-width: 720px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: 2px;
  box-shadow: var(--shadow-paper);
  padding: 80px 72px;
  min-height: 70vh;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  text-align: center;
}
.page-sheet-empty[hidden] { display: none; }

/* ----- Auto title-page panel (replaces Quill for auto front_matter title_page) ----- */
.page-sheet-auto[hidden] { display: none; }
.page-sheet-auto {
  /* Inherits .page-sheet width / shadow / radius — just override the inner
     padding so the banner can hug the top edge. */
  padding: 0;
}
.auto-page-banner {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  padding: 14px 24px;
  background: #fff8e6;
  border-bottom: 1px solid #f1e3b8;
  border-top-left-radius: 2px;
  border-top-right-radius: 2px;
}
.auto-page-banner-text {
  margin: 0;
  font-size: 13px;
  color: #6e5818;
  line-height: 1.5;
  flex: 1;
  min-width: 0;
}
.auto-page-banner .btn { flex-shrink: 0; white-space: nowrap; }
.auto-page-body { padding: 56px 72px; }
.auto-page-title {
  font-family: var(--font-display);
  font-size: 28px;
  font-weight: 600;
  margin: 0 0 32px;
  color: var(--ink-1);
}
.auto-page-fields {
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 22px;
}
.auto-page-field {
  display: flex;
  flex-direction: column;
  gap: 4px;
  border-bottom: 1px solid var(--line-soft);
  padding-bottom: 14px;
}
.auto-page-field:last-child { border-bottom: none; padding-bottom: 0; }
.auto-page-field dt {
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .08em;
  color: var(--ink-3);
  margin: 0;
}
.auto-page-field dd {
  margin: 0;
  font-size: 16px;
  color: var(--ink-1);
  font-family: var(--font-sans);
  word-break: break-word;
}
.auto-page-field dd:empty::before {
  content: '—';
  color: var(--ink-4);
}
.auto-page-help {
  font-size: 14px;
  color: var(--ink-3);
  margin: 0 0 18px;
}
.auto-page-hint {
  font-size: 13px;
  color: var(--ink-4);
  font-style: italic;
  margin: 18px 0 0;
}
.auto-page-toc-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.auto-page-toc-item {
  padding: 8px 0;
  border-bottom: 1px dotted var(--line-soft);
  font-size: 15px;
  color: var(--ink-1);
}
.auto-page-toc-item:last-child { border-bottom: none; }
.auto-page-toc-item.is-front-matter,
.auto-page-toc-item.is-back-matter { font-style: italic; color: var(--ink-2); }
.auto-page-toc-item.is-part {
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .08em;
  color: var(--ink-1);
}
.empty-mark {
  font-family: var(--font-serif);
  font-size: 36px;
  color: var(--accent);
  margin-bottom: 18px;
  opacity: .85;
}
.empty-heading {
  font-family: var(--font-display);
  font-size: 26px;
  font-weight: 500;
  color: var(--ink-1);
  margin: 0 0 10px;
  letter-spacing: .01em;
}
.empty-sub {
  font-family: var(--font-serif);
  font-size: 15px;
  color: var(--ink-3);
  max-width: 380px;
  margin: 0 0 28px;
  line-height: 1.6;
}
.chapter-title-input {
  width: 100%;
  border: none;
  background: transparent;
  font-family: var(--editor-heading-font, var(--font-display));
  font-size: 28px;
  font-weight: 600;
  color: var(--ink-1);
  margin-bottom: 4px;
  padding: 4px 0;
  letter-spacing: .01em;
}
.chapter-title-input::placeholder { color: var(--ink-4); font-style: italic; font-weight: 400; }
.chapter-title-input:focus { outline: none; }
.chapter-subtitle-input {
  width: 100%;
  border: none;
  background: transparent;
  font-family: var(--font-serif);
  font-style: italic;
  font-size: 15px;
  color: var(--ink-3);
  padding: 0 0 8px;
}
.chapter-subtitle-input::placeholder { color: var(--ink-4); }
.chapter-subtitle-input:focus { outline: none; }

/* Quill overrides — paper-like reading area.
   Quill's snow theme gives .ql-editor `height: 100%; overflow-y: auto` so
   it scrolls inside its own container. We don't want that — we want the
   editor to grow with its content and let the outer .page-stage handle
   all scrolling. Otherwise long chapters render below the cream paper
   sheet boundary. */
.ql-container.ql-snow {
  border: none;
  /* Body text follows the theme's body font (falls back to the editor
     default) so the writing surface previews the published typeface. */
  font-family: var(--editor-body-font, var(--font-serif));
  font-size: 17px;
  line-height: 1.65;
  color: var(--ink-1);
  height: auto;
}
.ql-editor {
  padding: 0;
  min-height: 60vh;
  height: auto;
  overflow: visible;
}
.ql-editor p { margin: 0 0 .8em; text-indent: 0; }
.ql-editor p + p { text-indent: 1.5em; margin-top: 0; }
/* A paragraph that follows a scene break (dinkus) or page break is still a
   continuing body paragraph, not the start of a new section, so it keeps its
   first-line indent — matching print/export, the main preview, and the share
   reader (which indent every paragraph except the chapter's very first). The
   break's <div>/<hr> otherwise breaks the `p + p` chain above and the next
   paragraph would wrongly lose its indent. */
.ql-editor .scene-break + p,
.ql-editor hr.page-break + p { text-indent: 1.5em; }
/* Per-chapter "Indent first paragraph" override — when the chapter gear
   toggle is on, restore the indent on the first paragraph so the editor
   matches what print/EPUB will render. */
.page-sheet.is-indent-first .ql-editor p:first-child { text-indent: 1.5em; }
/* Theme-level default: indent every chapter's first paragraph. Mirrors the
   per-chapter override above but is driven by the theme, so it carries to
   all chapters without ticking the box on each one. */
.page-sheet[data-theme-indent-first="1"] .ql-editor p:first-child { text-indent: 1.5em; }
.ql-editor h1, .ql-editor h2, .ql-editor h3 {
  font-family: var(--editor-heading-font, var(--font-display));
  font-weight: 600;
  color: var(--ink-1);
  margin: 1.4em 0 .5em;
}
.ql-editor h1 { font-size: 28px; }
.ql-editor h2 { font-size: 22px; }
.ql-editor h3 { font-size: 18px; }
.ql-editor blockquote {
  border-left: 3px solid var(--accent);
  padding: 4px 18px;
  margin: 1em 0;
  font-family: var(--font-serif);
  font-style: italic;
  color: var(--ink-2);
}
/* ---------- Scene break (visual divider in the editor) ----------
 * The saved HTML is just <div class="scene-break"></div>. The visual
 * (asterisks / flourish / etc.) is rendered via a ::before pseudo-
 * element whose content depends on the page-sheet's
 * data-scene-break-style attribute. Editor.js syncs that attribute
 * with the book's current scene_break_style on init and on changes
 * from the formatting tab.
 */
.ql-editor .scene-break {
  display: block;
  text-align: center;
  margin: 1.4em 0;
  color: var(--accent);
  font-family: var(--font-display);
  font-size: 1.1em;
  letter-spacing: .25em;
  user-select: none;
  cursor: default;
  min-height: 1.5em;
  position: relative;
}
.ql-editor .scene-break::before { content: '*  *  *'; } /* asterisks default */
.page-sheet[data-scene-break-style="asterisks"] .ql-editor .scene-break::before { content: '*  *  *'; letter-spacing: .25em; }
.page-sheet[data-scene-break-style="flourish"]  .ql-editor .scene-break::before { content: '❦'; font-size: 1.5em; letter-spacing: 0; }
.page-sheet[data-scene-break-style="rune"]      .ql-editor .scene-break::before { content: '✦'; font-size: 1.4em; letter-spacing: 0; }
.page-sheet[data-scene-break-style="dingbat"]   .ql-editor .scene-break::before { content: '❧'; font-size: 1.5em; letter-spacing: 0; }
.page-sheet[data-scene-break-style="thin-line"] .ql-editor .scene-break {
  letter-spacing: 0;
}
.page-sheet[data-scene-break-style="thin-line"] .ql-editor .scene-break::before {
  content: '';
  display: block;
  height: 1px;
  background: currentColor;
  width: 80px;
  margin: .8em auto;
  opacity: .35;
}

/* Floating trash icon — appears on hover over a scene-break in the editor.
 * Positioned absolutely against the document; editor.js sets top/left.
 * Stays clear of Quill's content tree so saved HTML stays clean.
 */
.scene-break-delete-floater {
  position: absolute;
  z-index: 200;
  width: 28px;
  height: 28px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 999px;
  color: var(--danger);
  cursor: pointer;
  box-shadow: var(--shadow-1);
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.scene-break-delete-floater:hover {
  background: var(--danger);
  color: #fff;
  border-color: var(--danger);
}
.scene-break-delete-floater[hidden] { display: none; }

/* Chapter images uploaded via the toolbar — keep them within the page width. */
.ql-editor img {
  max-width: 100%;
  height: auto;
  display: block;
  margin: 0.6em auto;
  border-radius: 2px;
}

/* ---------- Comment anchor highlight (in the editor) ---------- */
.ql-editor .cmt {
  background: rgba(252, 236, 176, 0.55);
  border-bottom: 2px solid var(--accent-soft);
  border-radius: 2px;
  padding: 0 1px;
  cursor: help;
  transition: background .15s ease;
}
.ql-editor .cmt:hover { background: rgba(252, 236, 176, 0.85); }
.ql-editor .cmt.is-flashing {
  animation: cmt-flash 1.1s ease-out;
}
@keyframes cmt-flash {
  0%   { background: var(--accent); color: #fff; }
  100% { background: rgba(252, 236, 176, 0.55); color: inherit; }
}
.ql-snow .ql-stroke { stroke: var(--ink-2); }
.ql-snow .ql-fill { fill: var(--ink-2); }
.ql-snow .ql-picker { color: var(--ink-2); }
.ql-snow .ql-picker-label:hover, .ql-snow button:hover { color: var(--accent) !important; }
.ql-snow button:hover .ql-stroke { stroke: var(--accent); }
.ql-snow button:hover .ql-fill { fill: var(--accent); }

/* Custom toolbar buttons (page-break / undo / redo) */
.ql-toolbar .ql-page-break,
.ql-toolbar .ql-undo,
.ql-toolbar .ql-redo {
  font-size: 16px !important;
  line-height: 1 !important;
  color: var(--ink-2) !important;
}
.ql-toolbar .ql-page-break:hover,
.ql-toolbar .ql-undo:hover,
.ql-toolbar .ql-redo:hover { color: var(--accent) !important; }

/* Page break renders as a labeled pill in the editor.
 * Invisible in the published output — the print/EPUB pipelines
 * convert this into an actual page break (CSS page-break-before).
 * The hr is a void element, so the pill is built from ::before/::after
 * pseudo-elements: ::after draws the dim horizontal line, ::before
 * paints the centered "PAGE BREAK ↓" badge over it.
 */
.ql-editor hr.page-break {
  border: none;
  background: transparent;
  height: 28px;
  margin: 1.6em 0;
  position: relative;
  overflow: visible;
  padding: 0;
}
.ql-editor hr.page-break::after {
  content: '';
  position: absolute;
  top: 50%;
  left: 0;
  right: 0;
  height: 1px;
  background: var(--accent);
  opacity: .25;
}
.ql-editor hr.page-break::before {
  content: 'PAGE BREAK ↓';
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  background: var(--bg-paper);
  border: 1px solid var(--accent);
  color: var(--accent);
  padding: 4px 14px;
  font-family: var(--font-sans);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: .14em;
  border-radius: 999px;
  z-index: 2;
}

.manuscript-footer {
  height: 40px;
  border-top: 1px solid var(--line);
  background: #fff;
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 0 18px;
  font-size: 12px;
  color: var(--ink-3);
}
.manuscript-footer strong { color: var(--ink-1); font-weight: 600; }
.footer-btn {
  background: transparent;
  border: none;
  color: var(--ink-3);
  font-family: inherit;
  font-size: 12.5px;
  padding: 4px 10px;
  border-radius: var(--radius-sm);
  cursor: pointer;
}
.footer-btn:hover { background: var(--bg-rail); color: var(--ink-1); }

/* ----- Writing-timer footer button + popover ----- */
.footer-timer {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  font-variant-numeric: tabular-nums;
}
.footer-timer.is-running {
  background: var(--accent-bg);
  color: var(--accent);
  border: 1px solid var(--accent-soft);
}
.footer-timer.is-paused {
  background: var(--bg-rail);
  color: var(--ink-2);
}
.footer-timer.is-goal-met {
  animation: footer-timer-pulse 1.6s ease-in-out infinite;
}
@keyframes footer-timer-pulse {
  0%, 100% { box-shadow: 0 0 0 0 rgba(139,105,20,.4); }
  50%      { box-shadow: 0 0 0 6px rgba(139,105,20,0); }
}
.timer-icon { font-size: 14px; line-height: 1; }

.timer-popover {
  position: absolute;
  right: 18px;
  bottom: 50px;
  z-index: 240;
  width: 280px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  font-size: 13.5px;
  animation: preset-pop-in .12s ease-out;
}
.timer-popover[hidden] { display: none; }
.timer-pop-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 12px 14px 10px;
  border-bottom: 1px solid var(--line);
}
.timer-pop-title {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
  margin: 0;
}
.timer-pop-body {
  padding: 14px 16px 16px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.timer-elapsed {
  display: flex;
  align-items: baseline;
  gap: 8px;
  padding: 10px 0 4px;
  border-bottom: 1px solid var(--line-soft);
}
.timer-elapsed-secondary { padding: 0 0 8px; border-bottom: none; }
.timer-elapsed-num {
  font-family: var(--font-display);
  font-size: 28px;
  font-weight: 600;
  color: var(--ink-1);
  font-variant-numeric: tabular-nums;
  line-height: 1;
}
.timer-elapsed-num.is-goal-met { color: var(--accent); }
.timer-elapsed-secondary .timer-elapsed-num { font-size: 18px; color: var(--accent); }
.timer-elapsed-label {
  font-size: 11px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .08em;
}
.timer-controls {
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.timer-discard {
  margin-top: 4px;
  font-size: 12px;
  color: var(--ink-4);
  text-align: center;
}
.timer-discard:hover { color: var(--danger); }
.timer-today {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding-top: 10px;
  border-top: 1px solid var(--line-soft);
  font-size: 12.5px;
  color: var(--ink-3);
}
.timer-today-label {
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .08em;
  font-size: 10.5px;
}
.timer-today-value { font-variant-numeric: tabular-nums; color: var(--ink-1); }

/* ---------- Timer mode toggle (Time / Sprint) ---------- */
.timer-mode-toggle {
  display: flex;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: 999px;
  padding: 3px;
  margin-bottom: 4px;
}
.timer-mode-btn {
  flex: 1;
  background: transparent;
  border: none;
  padding: 6px 10px;
  font: inherit;
  font-size: 12px;
  font-weight: 500;
  color: var(--ink-3);
  cursor: pointer;
  border-radius: 999px;
  transition: background .12s ease, color .12s ease;
}
.timer-mode-btn:hover { color: var(--ink-1); }
.timer-mode-btn.is-active {
  background: var(--accent);
  color: #fff;
}

/* ---------- Sprint progress bar + status ---------- */
.timer-sprint-fields { display: flex; flex-direction: column; gap: 8px; }
.timer-sprint-fields[hidden] { display: none; }
.timer-sprint-progress {
  padding: 6px 0 2px;
}
.timer-sprint-progress[hidden] { display: none; }
.timer-sprint-bar {
  height: 8px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: 999px;
  overflow: hidden;
}
.timer-sprint-bar > span {
  display: block;
  height: 100%;
  width: 0;
  background: linear-gradient(90deg, var(--accent), var(--accent-soft));
  transition: width .3s ease;
}
.timer-sprint-status {
  margin-top: 4px;
  font-family: var(--font-sans);
  font-size: 11.5px;
  color: var(--ink-3);
  font-variant-numeric: tabular-nums;
}

/* Sprint completion toast (also reused for "typing locked" hits) */
.timer-sprint-toast {
  position: fixed;
  bottom: 60px;
  left: 50%;
  transform: translateX(-50%) translateY(8px);
  padding: 10px 18px;
  background: #1d1b18;
  color: #fff;
  border-radius: 999px;
  font-family: var(--font-sans);
  font-size: 13px;
  letter-spacing: .03em;
  z-index: 500;
  pointer-events: none;
  opacity: 0;
  transition: opacity .15s ease, transform .15s ease;
  box-shadow: 0 6px 20px rgba(0, 0, 0, .25);
}
.timer-sprint-toast.is-visible {
  opacity: 1;
  transform: translateX(-50%) translateY(0);
}

/* ---------- Streak counter + heatmap ---------- */
.timer-streak {
  margin-top: 10px;
  padding-top: 10px;
  border-top: 1px solid var(--line-soft);
}
.timer-streak-row {
  display: flex;
  align-items: baseline;
  gap: 8px;
  margin-bottom: 8px;
}
.timer-streak-num {
  font-family: var(--font-display);
  font-size: 20px;
  font-weight: 700;
  color: var(--accent);
  line-height: 1;
}
.timer-streak-label {
  font-family: var(--font-sans);
  font-size: 11.5px;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-2);
}
.timer-streak-best {
  margin-left: auto;
  font-size: 11px;
  color: var(--ink-3);
}
.timer-streak-best strong { color: var(--ink-1); font-weight: 600; }

.timer-streak-heatmap {
  display: grid;
  grid-template-rows: repeat(7, 8px);
  grid-auto-flow: column;
  grid-auto-columns: 8px;
  gap: 2px;
  overflow-x: auto;
  padding: 2px 0;
  scrollbar-width: thin;
}
.heatmap-cell {
  display: block;
  background: var(--line-soft);
  border-radius: 1.5px;
}
.heatmap-cell[data-level="1"] { background: #d9c98a; }
.heatmap-cell[data-level="2"] { background: #c1a85a; }
.heatmap-cell[data-level="3"] { background: var(--accent-soft); }
.heatmap-cell[data-level="4"] { background: var(--accent); }

/* ---------- Read-aloud popover ---------- */
.tts-popover {
  position: fixed;
  top: 60px;
  right: 96px;
  z-index: 240;
  width: 300px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  font-size: 13.5px;
  animation: preset-pop-in .12s ease-out;
}
.tts-popover[hidden] { display: none; }
.tts-pop-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 12px 14px 10px;
  border-bottom: 1px solid var(--line);
}
.tts-pop-title {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
  margin: 0;
}
.tts-pop-body {
  padding: 14px 16px 16px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.tts-controls {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  padding: 4px 0 6px;
}
.tts-btn {
  width: 34px;
  height: 34px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: 50%;
  color: var(--ink-2);
  cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.tts-btn:hover { background: var(--accent-soft); color: var(--ink-1); border-color: var(--accent-soft); }
.tts-btn-primary {
  width: 42px;
  height: 42px;
  background: var(--accent);
  border-color: var(--accent);
  color: #fff;
}
.tts-btn-primary:hover { background: #a37a17; border-color: #a37a17; color: #fff; }
.tts-rate-label {
  margin-left: 6px;
  font-variant-numeric: tabular-nums;
  color: var(--ink-3);
  font-weight: 500;
}
.tts-divider { border: none; border-top: 1px solid var(--line); margin: 4px 0 6px; }
.tts-status {
  margin: 0 0 10px;
  padding: 8px 10px;
  background: #fdf3e0;
  border: 1px solid #e3c98a;
  border-radius: var(--radius-sm);
  font-size: 12px;
  color: #6f4f0e;
  line-height: 1.4;
}
.tts-status[hidden] { display: none; }

/* Inter-chunk loading indicator. Sits below the speed slider in
   the read-aloud popover; shows only when Kokoro is mid-generation
   and the gap has crossed the show-after-N-ms threshold set in
   read-aloud.js. The spinner uses the existing accent color so it
   reads as "system is working" rather than an error. */
.tts-loading {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  margin: 10px 0 0;
  padding: 6px 12px;
  background: var(--accent-bg);
  border: 1px solid color-mix(in srgb, var(--accent) 35%, transparent);
  border-radius: 999px;
  font-size: 12px;
  color: var(--ink-2);
}
.tts-loading[hidden] { display: none; }
.tts-loading-spinner {
  width: 12px;
  height: 12px;
  border-radius: 50%;
  border: 2px solid var(--line);
  border-top-color: var(--accent);
  animation: tts-spin 0.7s linear infinite;
  flex-shrink: 0;
}
@keyframes tts-spin {
  to { transform: rotate(360deg); }
}

/* The currently-spoken paragraph (editor + preview): a faint backdrop +
   accent bar marking the paragraph being read, kept subtle so the brighter
   current-sentence band below is the clear focal point. */
.ql-editor .tts-highlight {
  background: rgba(139,105,20,.13);
  border-radius: 3px;
  box-shadow: inset 3px 0 0 var(--accent);
  padding-left: 8px !important;
  transition: background .15s ease;
}
.preview-page .tts-highlight {
  background: rgba(139,105,20,.11);
  border-radius: 3px;
  box-shadow: inset 3px 0 0 var(--accent);
  transition: background .15s ease;
}

/* The exact sentence being spoken — read-along aid for focused reading.
   Painted via the CSS Custom Highlight API (a styled Range, no wrapper
   element), so it's safe over the live Quill editor. Browsers without the
   API simply ignore this rule and fall back to the paragraph backdrop.
   A warm highlighter band so the moving sentence is unmistakable. */
::highlight(tts-sentence) {
  background-color: rgba(255, 209, 71, .60);
  color: inherit;
}
:root[data-theme="dark"] ::highlight(tts-sentence) {
  background-color: rgba(232, 196, 92, .42);
  color: inherit;
}

/* ============================================================
   Reading aid — a personal on-screen reading lens (dyslexia / low-vision).
   Toggled by reading-aid.js via classes + CSS vars on <body>. Scoped to the
   editor surface and the in-app Preview only; never affects saved content or
   the PDF/EPUB exports.
   ============================================================ */

/* OpenDyslexic (weighted-bottom dyslexia typeface) — served from the
   fontsource CDN, consistent with how the app loads Google Fonts / Quill.
   Atkinson Hyperlegible and Lexend come from Google Fonts (see layout.php). */
@font-face {
  font-family: 'OpenDyslexic';
  src: url('https://cdn.jsdelivr.net/fontsource/fonts/opendyslexic@latest/latin-400-normal.woff2') format('woff2');
  font-weight: 400; font-style: normal; font-display: swap;
}
@font-face {
  font-family: 'OpenDyslexic';
  src: url('https://cdn.jsdelivr.net/fontsource/fonts/opendyslexic@latest/latin-700-normal.woff2') format('woff2');
  font-weight: 700; font-style: normal; font-display: swap;
}

/* --- The lens itself: spacing + line-height over editor & preview text --- */
body.reading-aid .ql-editor,
body.reading-aid .preview-page .chapter-body {
  letter-spacing: var(--ra-letter, 0) !important;
  word-spacing: var(--ra-word, 0) !important;
  line-height: var(--ra-line, 1.6) !important;
}
/* Optional narrower measure (shorter lines are easier to track). Centered in
   the page; preview keeps its own page width to avoid layout surprises. */
body.reading-aid .ql-editor {
  max-width: var(--ra-width, none);
  margin-left: auto;
  margin-right: auto;
}

/* --- Reading fonts --- */
body.reading-aid.ra-font-opendyslexic .ql-editor,
body.reading-aid.ra-font-opendyslexic .preview-page .chapter-body {
  font-family: 'OpenDyslexic', 'Comic Sans MS', sans-serif !important;
}
body.reading-aid.ra-font-atkinson .ql-editor,
body.reading-aid.ra-font-atkinson .preview-page .chapter-body {
  font-family: 'Atkinson Hyperlegible', sans-serif !important;
}
body.reading-aid.ra-font-lexend .ql-editor,
body.reading-aid.ra-font-lexend .preview-page .chapter-body {
  font-family: 'Lexend', sans-serif !important;
}

/* --- Background tints (Irlen-style overlay). Light theme only — in dark mode
   a cream page would clash, so the user turns the tint off there. --- */
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-cream .page-sheet,
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-cream .preview-page { background-color: #faf3e1 !important; }
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-peach .page-sheet,
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-peach .preview-page { background-color: #fbeee0 !important; }
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-mint .page-sheet,
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-mint .preview-page { background-color: #e8f3e8 !important; }
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-blue .page-sheet,
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-blue .preview-page { background-color: #e7eef6 !important; }
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-grey .page-sheet,
:root:not([data-theme="dark"]) body.reading-aid.ra-bg-grey .preview-page { background-color: #ecebe8 !important; }

/* --- The control popover (mirrors the read-aloud popover) --- */
.reading-popover {
  position: fixed;
  top: 60px;
  right: 96px;
  z-index: 240;
  width: 300px;
  /* The panel is tall (fonts, spacing, tint, ruler) — cap it to the viewport
     and let the body scroll so nothing runs off the bottom of the screen. */
  max-height: calc(100vh - 76px);
  display: flex;
  flex-direction: column;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: 0 12px 40px rgba(0,0,0,.18);
}
.reading-popover[hidden] { display: none; }
.reading-popover .tts-pop-head { flex: 0 0 auto; }   /* header stays put */
.reading-popover .tts-pop-body {
  flex: 1 1 auto;
  min-height: 0;        /* allow the flex child to shrink so overflow scrolls */
  overflow-y: auto;
}

.ra-swatches { display: flex; gap: 6px; }
.ra-swatch {
  width: 28px;
  height: 28px;
  border-radius: 50%;
  border: 1px solid var(--line-strong);
  background: #fff;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 13px;
  color: var(--ink-3);
}
.ra-swatch.is-active {
  box-shadow: 0 0 0 2px var(--accent);
  border-color: var(--accent);
}
.ra-reset {
  margin-top: 2px;
  align-self: flex-start;
  background: none;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 6px 12px;
  font-size: 12.5px;
  color: var(--ink-2);
  cursor: pointer;
}
.ra-reset:hover { background: var(--bg-paper); }

/* --- Reading ruler: a clear band that follows the mouse, dimming the rest of
   the page so one line stays in focus. The overlay never blocks interaction
   (pointer-events:none) and sits below the control popovers (z 240) so the
   panel itself isn't dimmed while you adjust it. --- */
.ra-ruler {
  position: fixed;
  inset: 0;
  z-index: 200;
  pointer-events: none;
}
.ra-ruler[hidden] { display: none; }
.ra-ruler-dim {
  position: fixed;
  left: 0;
  right: 0;
  background: rgba(12, 14, 22, var(--ra-ruler-dim, .18));
}
.ra-ruler-top    { top: 0; height: 0; }       /* height set inline from JS */
.ra-ruler-bottom { bottom: 0; top: 0; }       /* top set inline from JS */
.ra-ruler-band {
  position: fixed;
  left: 0;
  right: 0;
  border-top: 1.5px solid rgba(139, 105, 20, .55);
  border-bottom: 1.5px solid rgba(139, 105, 20, .55);
}

/* ---------- Typewriter focus mode ---------- */
.editor-shell.is-typewriter-focus .ql-editor {
  /* Generous top/bottom padding so any line can scroll to vertical center */
  padding-top: 40vh !important;
  padding-bottom: 40vh !important;
}
.editor-shell.is-typewriter-focus .ql-editor > * {
  transition: opacity .25s ease;
  opacity: .35;
}
/* The active block is tagged from JS on every selection-change. */
.editor-shell.is-typewriter-focus .ql-editor > .is-typewriter-active,
.editor-shell.is-typewriter-focus .ql-editor > .tts-highlight {
  opacity: 1;
}

/* ---------- Smart typography toast (transient feedback) ---------- */
.smart-typo-toast {
  position: fixed;
  top: 64px;
  left: 50%;
  transform: translateX(-50%) translateY(-12px);
  padding: 9px 18px;
  background: #1d1b18;
  color: #fff;
  border-radius: 999px;
  font-family: var(--font-sans);
  font-size: 12.5px;
  letter-spacing: .04em;
  z-index: 500;
  pointer-events: none;
  opacity: 0;
  transition: opacity .15s ease, transform .15s ease;
  box-shadow: 0 6px 20px rgba(0,0,0,.18);
}
.smart-typo-toast.is-visible {
  opacity: 1;
  transform: translateX(-50%) translateY(0);
}

/* ---------- Prose checker (CSS Highlight API + side panel) ---------- */
::highlight(prose-weasel) {
  background-color: #fff4d4;
  text-decoration: underline wavy #c2a644;
  text-underline-offset: 2px;
}
::highlight(prose-wordy) {
  background-color: #e2ecff;
  text-decoration: underline wavy #5a7fd6;
  text-underline-offset: 2px;
}
::highlight(prose-repeat) {
  background-color: #fde2e2;
  text-decoration: underline wavy #c25555;
  text-underline-offset: 2px;
}
/* Transient flash applied for ~1.5s after clicking a panel entry, so
   the user can spot the clicked finding among many same-colored
   weasel/repeat highlights. Sits on top of the persistent layers. */
::highlight(prose-flash) {
  background-color: #2c70f5;
  color: #fff;
}
.prose-panel {
  position: fixed;
  top: 56px;
  right: 16px;
  width: 360px;
  max-height: calc(100vh - 80px);
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  z-index: 230;
  display: flex;
  flex-direction: column;
  animation: preset-pop-in .12s ease-out;
}
.prose-panel[hidden] { display: none; }
.prose-panel-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 12px 14px;
  border-bottom: 1px solid var(--line);
}
.prose-panel-title {
  margin: 0;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
}
.prose-panel-actions { display: flex; align-items: center; gap: 6px; }
.prose-panel-actions .btn-link {
  font-size: 14px;
  background: transparent;
  border: none;
  color: var(--ink-3);
  cursor: pointer;
  padding: 2px 6px;
}
.prose-panel-actions .btn-link:hover { color: var(--accent); }
.prose-panel-summary {
  display: flex;
  gap: 16px;
  padding: 10px 14px;
  border-bottom: 1px solid var(--line-soft);
  font-family: var(--font-sans);
  font-size: 12px;
  color: var(--ink-2);
}
.prose-stat strong {
  font-weight: 600;
  color: var(--ink-1);
  font-variant-numeric: tabular-nums;
}
.prose-panel-list {
  list-style: none;
  margin: 0;
  padding: 0;
  overflow-y: auto;
  flex: 1;
}
.prose-empty,
.prose-degraded {
  padding: 18px 14px;
  margin: 0;
  font-size: 12.5px;
  color: var(--ink-3);
  font-style: italic;
}
.prose-row {
  padding: 10px 14px;
  border-bottom: 1px solid var(--line-soft);
  cursor: pointer;
  display: flex;
  gap: 10px;
  align-items: flex-start;
  transition: background .12s ease;
}
.prose-row:hover { background: var(--bg-paper); }
.prose-row-badge {
  font-family: var(--font-sans);
  font-size: 9.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .1em;
  padding: 2px 6px;
  border-radius: 999px;
  flex-shrink: 0;
}
.prose-row-weasel .prose-row-badge { background: #fff4d4; color: #6a4d0a; }
.prose-row-wordy  .prose-row-badge { background: #e2ecff; color: #1d3a6a; }
.prose-row-repeat .prose-row-badge { background: #fde2e2; color: #6a1d1d; }
.prose-row-text {
  font-family: var(--font-serif, Georgia, serif);
  font-size: 13px;
  line-height: 1.5;
  color: var(--ink-1);
}
.prose-ctx { color: var(--ink-3); }
.prose-row-text strong { color: var(--ink-1); background: rgba(255,235,170,.5); padding: 0 2px; border-radius: 2px; }
/* Suggested tighter replacement on a wordy-phrase row ("→ because"). */
.prose-suggest {
  display: block;
  margin-top: 3px;
  font-family: var(--font-sans);
  font-size: 11.5px;
  font-weight: 600;
  color: var(--accent);
}

/* ---------- Find & Replace (rail panel) ----------
 * The find UI lives inside the writing-view's right rail panel
 * (.rail-panel-body[data-panel="find"]). Layout is column-flow,
 * narrow column, so input rows and action buttons stack tightly.
 */
.rail-find-body {
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.find-tabs {
  display: flex;
  gap: 4px;
  border-bottom: 1px solid var(--line);
  margin: -4px -4px 6px;
  padding: 0 4px;
}
.find-tab {
  background: transparent;
  border: none;
  padding: 8px 14px;
  font: inherit;
  font-family: var(--font-sans);
  font-size: 13px;
  font-weight: 500;
  color: var(--ink-3);
  cursor: pointer;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
  transition: color .12s ease, border-color .12s ease;
}
.find-tab:hover { color: var(--ink-2); }
.find-tab.is-active {
  color: var(--ink-1);
  border-bottom-color: var(--accent);
}
.find-tab-context {
  margin: 0;
  font-family: var(--font-sans);
  font-size: 11.5px;
  color: var(--ink-3);
  font-style: italic;
}
.find-input-row {
  display: flex;
  align-items: center;
  gap: 6px;
}
.find-input-row input {
  flex: 1;
  padding: 9px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 14px;
  background: var(--bg-paper);
}
.find-input-row input:focus { outline: none; border-color: var(--accent); background: #fff; }
.find-nav-btn {
  width: 32px;
  height: 32px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  color: var(--ink-2);
  cursor: pointer;
  flex-shrink: 0;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.find-nav-btn:hover:not(:disabled) {
  background: var(--accent-soft);
  color: var(--ink-1);
  border-color: var(--accent-soft);
}
.find-nav-btn:disabled {
  opacity: .35;
  cursor: not-allowed;
}
.find-options {
  display: flex;
  align-items: center;
  gap: 14px;
  flex-wrap: wrap;
}
.find-options label {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 13px;
  color: var(--ink-2);
  cursor: pointer;
}
.find-actions {
  display: flex;
  gap: 6px;
  align-items: center;
  flex-wrap: wrap;
}
.find-actions .btn { padding: 6px 12px; font-size: 12.5px; }

/* Inline highlights for chapter-mode matches (CSS Custom Highlight API). */
::highlight(find-match) {
  background-color: rgba(255, 220, 100, 0.55);
  border-radius: 2px;
}
/* The match the author is currently on (since the editor cursor no longer
   moves to it) — a stronger tint so it stands out from the other matches. */
::highlight(find-current) {
  background-color: rgba(255, 150, 40, 0.75);
  border-radius: 2px;
}
.find-summary {
  font-family: var(--font-sans);
  font-size: 12.5px;
  color: var(--ink-3);
  min-height: 18px;
}
.find-summary[data-kind="ok"]    { color: #2d5a1f; }
.find-summary[data-kind="error"] { color: var(--danger); }
.find-summary[data-kind="busy"]  { color: var(--accent); font-style: italic; }
.find-results {
  overflow-y: auto;
  max-height: 50vh;
  border-top: 1px solid var(--line-soft);
  padding-top: 10px;
}

/* Quick-replacements section under the regular find/replace controls.
   Honors the Chapter / Book scope tabs at the top of the panel. */
.find-quick-replacements {
  margin-top: 16px;
  padding-top: 14px;
  border-top: 1px solid var(--line-soft);
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.find-quick-label {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-3);
}
.find-quick-status {
  font-size: 12px;
  color: var(--ink-3);
  min-height: 16px;
}
.find-empty {
  padding: 14px;
  margin: 0;
  color: var(--ink-3);
  font-style: italic;
}
.find-chapter { margin-bottom: 18px; }
.find-chapter-head {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 6px 0;
  border-bottom: 1px solid var(--line-soft);
  flex-wrap: wrap;
}
.find-chapter-title {
  background: transparent;
  border: none;
  padding: 0;
  font: inherit;
  font-family: var(--font-display);
  font-size: 13.5px;
  font-weight: 600;
  color: var(--ink-1);
  cursor: pointer;
  text-align: left;
  flex: 1;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.find-chapter-title:hover { color: var(--accent); }
.find-chapter-count {
  margin-left: auto;
  font-family: var(--font-sans);
  font-size: 11px;
  color: var(--ink-3);
  font-variant-numeric: tabular-nums;
}
.find-truncated {
  margin: 6px 0;
  color: var(--ink-3);
  font-size: 11.5px;
  font-style: italic;
}
.find-snippets { list-style: none; padding: 0; margin: 6px 0 0; }
.find-snippet {
  font-family: var(--font-serif, Georgia, serif);
  font-size: 13.5px;
  line-height: 1.55;
  color: var(--ink-2);
  padding: 4px 0;
}
.find-snippet mark {
  background: rgba(255,235,170,.7);
  color: var(--ink-1);
  padding: 0 2px;
  border-radius: 2px;
  font-weight: 500;
}
.find-ctx { color: var(--ink-3); }
/* Book-mode snippets are clickable — each jumps to its specific occurrence. */
.find-snippet.is-jumpable { cursor: pointer; border-radius: 4px; padding: 4px 6px; margin: 0 -6px; transition: background .12s ease; }
.find-snippet.is-jumpable:hover { background: var(--accent-soft); }

/* Replacement preview inside book-mode snippets — pre [old → new] post.
   Old gets the same yellow tint as a regular match, new gets a green
   tint so the user reads it as additive at a glance. */
.find-snippets.has-preview .find-snippet { font-size: 13px; }
.find-old {
  background: rgba(255,235,170,.7);
  color: var(--ink-2);
  text-decoration: line-through;
  padding: 0 2px;
  border-radius: 2px;
}
.find-arrow {
  display: inline-block;
  margin: 0 4px;
  color: var(--ink-3);
  font-weight: 600;
}
.find-new {
  background: rgba(170, 220, 170, .55);
  color: #1f4a1f;
  padding: 0 2px;
  border-radius: 2px;
  text-decoration: none;
  font-weight: 500;
}

/* Book-mode "Where" select — sub-scope under the Book tab. Hidden by
   the [hidden] attribute when in chapter mode. */
.find-kind-scope {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 6px 0 8px;
}
.find-kind-scope-label {
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
#find-kind-scope-select {
  flex: 1;
  padding: 4px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  font: inherit;
  font-size: 12.5px;
  color: var(--ink-1);
}

/* Disabled visual state on the whole-word label when regex mode is on
   (the input itself is also disabled via JS). */
.find-options label.is-disabled { opacity: .55; cursor: not-allowed; }
.find-options label.is-disabled input { pointer-events: none; }

/* Undo-last-replace bar. Sits between the summary and the results so
   the user sees it immediately after a successful replace. */
.find-undo-row {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 8px 0;
  border-top: 1px dashed var(--line);
  border-bottom: 1px dashed var(--line);
  margin: 6px 0;
}
.find-undo-meta { font-size: 11.5px; color: var(--ink-3); }

/* ---------- Distraction-free focus mode ----------
 *
 * Strategy:
 *   - Keep the topbar visible but compress it into a small floating
 *     horizontal pill at the top-right with only the action icons
 *     (exit focus, find, prose, TTS, preview, export). The book title,
 *     view tabs, save status, admin link, and avatar are hidden.
 *   - Hide the chapter sidebar, manuscript footer, page-sheet gear,
 *     and all transient popovers / floaters.
 *   - Center the manuscript and remove the page-sheet's paper border
 *     for a cleaner reading frame.
 */
.editor-shell.is-focus-mode .chapter-sidebar,
.editor-shell.is-focus-mode .icon-rail,
.editor-shell.is-focus-mode .rail-panel,
.editor-shell.is-focus-mode .manuscript-footer,
.editor-shell.is-focus-mode .comment-floater,
.editor-shell.is-focus-mode .comment-composer,
.editor-shell.is-focus-mode .chapter-settings-btn,
.editor-shell.is-focus-mode .chapter-settings-popover,
.editor-shell.is-focus-mode .tts-popover,
.editor-shell.is-focus-mode .timer-popover,
.editor-shell.is-focus-mode .bible-mention-popover,
.editor-shell.is-focus-mode .topbar-left,
.editor-shell.is-focus-mode .topbar-center,
.editor-shell.is-focus-mode .save-status,
.editor-shell.is-focus-mode .topbar-admin-link,
.editor-shell.is-focus-mode .topbar-divider,
.editor-shell.is-focus-mode .user-avatar,
.editor-shell.is-focus-mode .user-menu {
  display: none !important;
}
/* Compress the topbar into a floating horizontal pill of action icons. */
.editor-shell.is-focus-mode .editor-topbar {
  position: fixed;
  top: 14px;
  right: 14px;
  left: auto;
  width: auto;
  background: transparent;
  border: none;
  box-shadow: none;
  padding: 0;
  z-index: 240;
  pointer-events: none; /* the wrapper doesn't catch clicks; the pill does */
}
.editor-shell.is-focus-mode .topbar-right {
  display: inline-flex;
  align-items: center;
  gap: 2px;
  padding: 4px;
  background: rgba(255, 255, 255, 0.94);
  backdrop-filter: blur(8px);
  -webkit-backdrop-filter: blur(8px);
  border: 1px solid var(--line);
  border-radius: 999px;
  box-shadow: 0 6px 18px rgba(0, 0, 0, 0.08);
  pointer-events: auto;
}
.editor-shell.is-focus-mode .topbar-iconbtn {
  width: 32px;
  height: 32px;
}
.editor-shell.is-focus-mode .editor-body-grid {
  grid-template-columns: 1fr !important;
}
.editor-shell.is-focus-mode .manuscript {
  padding-top: 36px;
}
.editor-shell.is-focus-mode .page-stage {
  max-width: 820px;
  margin: 0 auto;
}
.editor-shell.is-focus-mode .page-sheet {
  box-shadow: none !important;
  border: none !important;
}
.topbar-iconbtn.is-active {
  color: var(--accent);
  background: var(--accent-soft);
}
/* Theme toggle: show the icon that represents the *target* theme. In
   light mode, show the moon (click to go dark). In dark mode, show
   the sun (click to go light). The button stores the *current* theme
   in data-theme so we just CSS-swap which child SVG is visible. */
.theme-toggle .icon-sun  { display: none; }
.theme-toggle .icon-moon { display: inline-block; }
.theme-toggle[data-theme="dark"] .icon-sun  { display: inline-block; }
.theme-toggle[data-theme="dark"] .icon-moon { display: none; }

.manuscript { position: relative; } /* anchor for the absolute-positioned popover */
.footer-meta { display: flex; align-items: center; gap: 22px; }
.footer-stat { font-variant-numeric: tabular-nums; }
/* Genre-aware "Novel-length" chip in the footer. Click opens the modal
   below with the standard word-count buckets for the book's genre. */
.footer-length-chip {
  display: inline-flex;
  align-items: center;
  padding: 3px 10px;
  border-radius: 999px;
  background: rgba(139,105,20,.14);
  color: var(--accent);
  border: 1px solid rgba(139,105,20,.28);
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .04em;
  text-transform: uppercase;
  cursor: pointer;
  font-family: var(--font-sans);
  line-height: 1.4;
}
.footer-length-chip:hover { background: rgba(139,105,20,.22); }

/* Variant tints for the additional footer chips. Each gets a unique
   hue so the row reads as a row of distinct stats rather than four
   identical pills. Hover state inherits the deeper tint. */
.footer-length-chip.is-today {
  background: rgba(46,125,50,.14);
  color: #2e7d32;
  border-color: rgba(46,125,50,.30);
}
.footer-length-chip.is-today:hover { background: rgba(46,125,50,.22); }
.footer-length-chip.is-pages {
  background: rgba(48,79,154,.12);
  color: #304f9a;
  border-color: rgba(48,79,154,.28);
}
.footer-length-chip.is-pages:hover { background: rgba(48,79,154,.20); }
.footer-length-chip.is-readtime {
  background: rgba(120,55,160,.12);
  color: #783aa0;
  border-color: rgba(120,55,160,.28);
}
.footer-length-chip.is-readtime:hover { background: rgba(120,55,160,.20); }

/* The shared chip modal re-uses .length-modal-card chrome but its body
   is dynamic so it doesn't need a fixed table. Just give it some
   breathing room and let length-modal-* styles handle the rest. */
.chip-modal-body {
  padding: 0 0 18px;
}
.chip-modal-body > .length-modal-sub:first-child { margin-top: 16px; }

/* Length-info modal */
.length-modal-card { max-width: 460px; padding: 0; }
.length-modal-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 18px 22px 10px;
  border-bottom: 1px solid var(--line-soft);
}
.length-modal-head .modal-title { margin: 0; }
.length-modal-sub {
  margin: 14px 22px 8px;
  font-size: 13px;
  color: var(--ink-3);
  line-height: 1.5;
}
.length-modal-table {
  width: calc(100% - 44px);
  margin: 8px 22px 0;
  border-collapse: collapse;
  font-size: 14px;
}
.length-modal-table th,
.length-modal-table td {
  text-align: left;
  padding: 8px 10px;
  border-bottom: 1px solid var(--line-soft);
}
.length-modal-table th {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--ink-3);
}
.length-modal-table td:last-child {
  text-align: right;
  font-variant-numeric: tabular-nums;
  color: var(--ink-2);
}
.length-modal-table tr.is-current td {
  background: rgba(139,105,20,.10);
  color: var(--accent);
  font-weight: 600;
}
.length-modal-foot {
  margin: 16px 22px 22px;
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
}
.goal-progress { display: flex; align-items: center; gap: 10px; }
.goal-bar {
  width: 160px;
  height: 4px;
  background: var(--line);
  border-radius: 2px;
  overflow: hidden;
}
.goal-fill {
  display: block;
  height: 100%;
  background: var(--accent);
  transition: width .25s ease;
}
.goal-label { font-variant-numeric: tabular-nums; }

/* ----- Right icon rail ----- */
.icon-rail {
  background: #fff;
  border-left: 1px solid var(--line);
  display: flex;
  flex-direction: column;
  align-items: center;
  padding: 14px 0;
  gap: 6px;
  order: 2; /* always rightmost — rail-panel slides in to its left */
}
.chapter-sidebar { order: 0; }
.manuscript      { order: 1; }
.rail-panel      { order: 1; } /* sits between manuscript and icon-rail when shown */
.rail-btn {
  width: 36px; height: 36px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: 1px solid transparent;
  border-radius: var(--radius-sm);
  color: var(--ink-3);
  cursor: pointer;
  padding: 0;
}
.rail-btn:hover { background: var(--bg-rail); color: var(--ink-1); }
/* Divider between the panel rail buttons and the reading/checking tools. */
.rail-sep { width: 20px; height: 1px; background: var(--line); margin: 4px 0; flex: none; }
.rail-btn.is-active {
  background: var(--accent-bg);
  color: var(--accent);
  border-color: var(--accent-soft);
}
.rail-glyph {
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 700;
  line-height: 1;
}

/* ----- Right rail slide-out panel ----- */
.rail-panel {
  background: #fff;
  border-left: 1px solid var(--line);
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
.rail-panel[hidden] { display: none; }
.rail-panel-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 14px 16px 12px;
  border-bottom: 1px solid var(--line);
}
.rail-panel-title {
  font-family: var(--font-sans);
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
  margin: 0;
}
.rail-panel-close {
  width: 24px; height: 24px;
  border: none; background: transparent;
  font-size: 20px; line-height: 1;
  color: var(--ink-3); cursor: pointer; padding: 0;
  border-radius: 4px;
}
.rail-panel-close:hover { background: var(--bg-rail); color: var(--ink-1); }
.rail-panel-body {
  flex: 1;
  overflow-y: auto;
  padding: 16px 16px 24px;
}

/* Per-chapter notes panel. The textarea fills the panel below the
   help line so the author has as much room as possible without the
   panel itself scrolling. */
.chapter-notes-panel-body {
  display: flex;
  flex-direction: column;
}
.chapter-notes-head {
  display: flex;
  align-items: flex-start;
  gap: 8px;
  margin-bottom: 8px;
}
.chapter-notes-head .rail-panel-help { flex: 1; min-width: 0; }
.chapter-notes-clear {
  flex-shrink: 0;
  width: 26px;
  height: 26px;
  padding: 0;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: 1px solid transparent;
  border-radius: 4px;
  color: var(--ink-3);
  cursor: pointer;
  transition: color .12s ease, background .12s ease, border-color .12s ease;
}
.chapter-notes-clear:hover {
  color: var(--danger, #b04646);
  background: rgba(176, 70, 70, .08);
  border-color: rgba(176, 70, 70, .25);
}
.chapter-notes-textarea {
  flex: 1;
  width: 100%;
  min-height: 240px;
  resize: none;
  padding: 12px 14px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  font-family: var(--font-serif, Georgia, serif);
  font-size: 14px;
  line-height: 1.55;
  color: var(--ink-1);
  outline: none;
  transition: border-color .12s ease, box-shadow .12s ease;
}
.chapter-notes-textarea:focus {
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
  background: #fff;
}
.chapter-notes-textarea::placeholder {
  color: var(--ink-3);
  font-style: italic;
}

/* Small dot on the rail's Notes icon — only shown when the current
   chapter has notes, so the author can spot it from across the
   editor without opening the panel. */
.rail-btn { position: relative; }
.rail-notes-dot {
  position: absolute;
  top: 4px;
  right: 4px;
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: var(--accent);
  box-shadow: 0 0 0 2px var(--bg-rail);
}
.rail-panel-help {
  font-size: 12.5px;
  color: var(--ink-3);
  line-height: 1.55;
  margin: 0 0 14px;
}

.find-results { margin-top: 6px; font-size: 12.5px; color: var(--ink-3); }
.find-status { color: var(--ink-3); }
.find-status.find-empty { color: var(--danger); }

/* ---------- Comments rail icon + count badge ---------- */
.rail-comments-wrap {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}
.rail-comments-count {
  position: absolute;
  top: -6px;
  right: -8px;
  min-width: 16px;
  height: 16px;
  padding: 0 4px;
  background: var(--accent);
  color: #fff;
  border-radius: 999px;
  font-size: 10px;
  font-weight: 700;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  letter-spacing: 0;
}

/* ---------- Comments rail panel ---------- */
.comments-toolbar {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 12px;
  padding: 0 0 8px;
  border-bottom: 1px solid var(--line-soft);
  margin-bottom: 10px;
}
.comments-nav {
  display: inline-flex;
  gap: 2px;
}
.comments-nav-btn {
  width: 26px;
  height: 26px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: 4px;
  font-size: 14px;
  line-height: 1;
  color: var(--ink-2);
  font-weight: 600;
  padding: 0;
}
.comments-nav-btn:hover { background: var(--bg-rail); color: var(--accent); }
.comments-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.comments-empty {
  padding: 14px 0;
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
  text-align: center;
}
.comment-row {
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 10px 12px;
  background: #fff;
  font-size: 13px;
}
.comment-row.is-resolved { background: var(--bg-rail); opacity: .75; }
.comment-meta {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: 8px;
  font-size: 11px;
  color: var(--ink-3);
  margin-bottom: 4px;
}
.comment-author { font-weight: 600; color: var(--ink-2); }
.comment-time   { font-variant-numeric: tabular-nums; }
.comment-badge {
  display: inline-block;
  font-size: 10px;
  font-weight: 600;
  letter-spacing: .06em;
  text-transform: uppercase;
  padding: 2px 7px;
  border-radius: 999px;
  line-height: 1.4;
}
.comment-badge-beta {
  background: rgba(139,105,20,.14);
  color: var(--accent);
  border: 1px solid rgba(139,105,20,.25);
}
.comment-row.is-from-share { border-left: 3px solid var(--accent); }
.comment-quote {
  margin: 4px 0 6px;
  padding: 6px 10px;
  background: rgba(139,105,20,.06);
  border-left: 2px solid var(--accent);
  font-style: italic;
  font-size: 13px;
  color: var(--ink-2);
  line-height: 1.4;
  max-height: 5.5em;
  overflow: hidden;
}
.comment-body   {
  color: var(--ink-1);
  line-height: 1.45;
  white-space: pre-wrap;
  word-break: break-word;
}
.comment-row.is-resolved .comment-body { text-decoration: line-through; color: var(--ink-3); }
.comment-row.is-editing { border-color: var(--accent); box-shadow: 0 0 0 3px rgba(139,105,20,.10); }
.comment-edit-body {
  width: 100%;
  min-height: 60px;
  padding: 6px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 13px;
  resize: vertical;
  background: var(--bg-paper);
  margin-top: 2px;
}
.comment-edit-body:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
  background: #fff;
}
.comment-actions {
  display: flex;
  gap: 12px;
  margin-top: 8px;
  align-items: center;
}
.comment-row.is-editing .comment-actions { justify-content: flex-end; }
.comment-actions .btn-link {
  font-size: 12px;
  color: var(--ink-3);
}
.comment-actions .btn-link:hover { color: var(--ink-1); }
.comment-danger:hover { color: var(--danger) !important; }

/* Author reply on a beta-reader comment. Indented + accent-tinted to
   read as a response to the body above, not as a sibling note. */
.comment-reply {
  margin: 8px 0 0 8px;
  padding: 8px 10px;
  border-left: 2px solid var(--accent);
  background: var(--bg-rail);
  border-radius: 0 4px 4px 0;
}
.comment-reply-meta {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 11px;
  color: var(--ink-3);
  margin-bottom: 4px;
}
.comment-reply-from {
  font-weight: 600;
  color: var(--accent);
  letter-spacing: .04em;
}
.comment-reply-remove {
  margin-left: auto;
  font-size: 11px;
  color: var(--ink-3);
}
.comment-reply-remove:hover { color: var(--danger); }
.comment-reply-body {
  color: var(--ink-1);
  font-size: 13px;
  line-height: 1.45;
  white-space: pre-wrap;
  word-break: break-word;
}
.comment-reply-composer {
  margin-top: 8px;
  padding: 8px 10px 10px;
  border-left: 2px solid var(--accent);
  background: var(--bg-rail);
  border-radius: 0 4px 4px 0;
}
.comment-reply-edit {
  width: 100%;
  min-height: 60px;
  padding: 6px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 13px;
  resize: vertical;
  background: #fff;
}
.comment-reply-edit:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
}
.comment-reply-composer .comment-actions { margin-top: 6px; justify-content: flex-end; }

/* ---------- Floating comment button + composer ---------- */
.comment-floater {
  position: absolute;
  z-index: 220;
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 5px 10px;
  background: var(--ink-1);
  color: #fff;
  border: 1px solid var(--ink-1);
  border-radius: 6px;
  font-family: inherit;
  font-size: 12px;
  font-weight: 500;
  cursor: pointer;
  box-shadow: 0 2px 8px rgba(0,0,0,.2);
  animation: preset-pop-in .12s ease-out;
}
.comment-floater:hover { background: #000; }
.comment-floater[hidden] { display: none; }

.comment-composer {
  position: absolute;
  z-index: 230;
  width: 280px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  padding: 12px;
  animation: preset-pop-in .12s ease-out;
}
.comment-composer[hidden] { display: none; }
.comment-composer textarea {
  width: 100%;
  min-height: 70px;
  padding: 8px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 13px;
  resize: vertical;
  background: var(--bg-paper);
}
.comment-composer textarea:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
  background: #fff;
}
.comment-composer-actions {
  display: flex;
  align-items: center;
  justify-content: flex-end;
  gap: 12px;
  margin-top: 10px;
}

/* Reused: section headings inside any inspector-style panel */
.section-heading {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
  margin: 0 0 12px;
}
.inspector-section {
  padding-bottom: 18px;
  margin-bottom: 18px;
  border-bottom: 1px solid var(--line-soft);
}
.inspector-section:last-child { border-bottom: none; padding-bottom: 0; margin-bottom: 0; }

/* ============================================================
   PHASE 2 — View switching shell
   ============================================================ */
.editor-view {
  flex: 1;
  overflow: hidden;
}
.editor-view[hidden] { display: none; }
.editor-view.is-active { display: flex; }
.editor-view.editor-body-grid {
  display: grid;
}
.editor-view.editor-body-grid[hidden] { display: none; }

/* ============================================================
   PHASE 2 — Format view
   ============================================================ */
.format-view {
  background: var(--bg-page);
  overflow: auto;
}
.format-shell {
  flex: 1;
  display: flex;
  flex-direction: column;
  width: 100%;
}
.format-hero {
  padding: 28px 48px 16px;
  border-bottom: 1px solid var(--line);
  background: #fff;
  display: flex;
  align-items: end;
  justify-content: space-between;
  gap: 16px;
  flex-wrap: wrap;
}
.format-hero-title {
  font-family: var(--font-display);
  font-size: 22px;
  font-weight: 500;
  margin: 0 0 4px;
  letter-spacing: .01em;
  color: var(--ink-2);
}
.format-hero-title #current-theme-name {
  font-weight: 600;
  color: var(--ink-1);
}
.format-hero-sub {
  margin: 0;
  color: var(--ink-3);
  font-size: 13.5px;
}
.format-hero-actions { display: flex; gap: 10px; }
.select-sm { width: auto; min-width: 130px; padding: 7px 10px; font-size: 13px; }

/* Gallery mode: theme gallery + device preview side-by-side.
   Editor mode: header bar (top) + left nav + main pane (with sections) + device preview. */
.format-body {
  display: grid;
  gap: 28px;
  padding: 28px 48px 60px;
  align-items: start;
}
.format-body[data-mode="gallery"] {
  grid-template-columns: 1fr 380px;
  grid-template-areas:
    "gallery   side";
}
.format-body[data-mode="editor"] {
  /* minmax(0, 1fr) keeps the middle column from sizing to its content's
     intrinsic min-width — without this, switching sections would shift
     the column wider or narrower based on what's inside. */
  grid-template-columns: 200px minmax(0, 1fr) 380px;
  grid-template-areas:
    "bar  bar      side"
    "nav  editor   side";
}
.format-body[data-mode="editor"] > .format-editor {
  min-width: 0;
  width: 100%;
}
.format-body > .theme-gallery       { grid-area: gallery; }
.format-body > .format-editor       { grid-area: editor; margin-top: 0; }
.format-body > .format-editor-bar   { grid-area: bar; }
.format-body > .format-editor-nav   { grid-area: nav; }
.format-body > .format-side         { grid-area: side; }

/* Hide gallery + the editor pieces depending on the active mode. */
.format-body[data-mode="gallery"] > .format-editor,
.format-body[data-mode="gallery"] > .format-editor-bar,
.format-body[data-mode="gallery"] > .format-editor-nav {
  display: none;
}
.format-body[data-mode="editor"] > .theme-gallery {
  display: none;
}

/* Editor breadcrumb bar */
.format-editor-bar {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 6px 0 12px;
  border-bottom: 1px solid var(--line-soft);
  font-family: var(--font-sans);
  font-size: 13px;
}
.format-editor-back {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  background: transparent;
  border: 1px solid var(--line);
  padding: 6px 12px 6px 8px;
  border-radius: var(--radius-sm);
  color: var(--ink-2);
  cursor: pointer;
  font: inherit;
  font-size: 13px;
}
.format-editor-back:hover { background: var(--bg-paper); color: var(--ink-1); }
.format-editor-bar-divider { color: var(--ink-3); }
.format-editor-bar-title { color: var(--ink-3); }
.format-editor-bar-title strong { color: var(--ink-1); font-weight: 600; }
.format-editor-bar-spacer { flex: 1 1 auto; }

/* Save status pill in the customize bar. Color follows the lifecycle:
   gray (idle/saved), accent (dirty/saving), red (error). */
.format-save-status {
  font-size: 12px;
  color: var(--ink-3);
  padding: 4px 10px;
  border-radius: 999px;
  background: var(--bg-rail);
  border: 1px solid var(--line-soft);
  white-space: nowrap;
}
.format-save-status[data-state="dirty"]  { color: var(--accent); border-color: rgba(139,105,20,.30); background: rgba(139,105,20,.08); }
.format-save-status[data-state="saving"] { color: var(--accent); border-color: rgba(139,105,20,.30); background: rgba(139,105,20,.08); font-style: italic; }
.format-save-status[data-state="saved"]  { color: #2a7d2a; border-color: rgba(42,125,42,.25); background: rgba(42,125,42,.08); }
.format-save-status[data-state="error"]  { color: #b03030; border-color: rgba(176,48,48,.30); background: rgba(176,48,48,.08); }

/* Editor left nav */
.format-editor-nav {
  position: sticky;
  top: 16px;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 8px 0;
  align-self: start;
}
.format-editor-nav ul { list-style: none; margin: 0; padding: 0; }
.format-editor-nav li { margin: 0; }
.format-editor-nav-btn {
  display: block;
  width: 100%;
  text-align: left;
  background: transparent;
  border: none;
  padding: 9px 16px;
  font: inherit;
  font-size: 13.5px;
  color: var(--ink-2);
  cursor: pointer;
  border-left: 3px solid transparent;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.format-editor-nav-btn:hover { background: var(--bg-paper); color: var(--ink-1); }
.format-editor-nav-btn.is-active {
  background: var(--accent-bg);
  color: var(--ink-1);
  border-left-color: var(--accent);
  font-weight: 500;
}

/* In editor mode, only the active section is visible inside the
   format-advanced-body container. The grid layout collapses since we
   only ever show one section at a time. */
.format-body[data-mode="editor"] .format-advanced-body {
  display: block;
}
.format-body[data-mode="editor"] .inspector-section[data-section] {
  display: none;
}
.format-body[data-mode="editor"] .inspector-section.is-active-section {
  display: block;
  /* Even sections that span both columns in 2-column mode show as a
     single block here. */
  grid-column: auto;
}

/* Theme gallery */
.theme-gallery {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: 18px;
}
.theme-card {
  position: relative;
  display: flex;
  flex-direction: column;
  border: 2px solid var(--line);
  border-radius: var(--radius);
  background: #fff;
  padding: 0;
  cursor: pointer;
  overflow: hidden;
  transition: border-color .15s ease, transform .15s ease, box-shadow .15s ease;
  font-family: inherit;
  text-align: left;
}
.theme-card:hover {
  border-color: var(--accent-soft);
  transform: translateY(-2px);
  box-shadow: 0 6px 18px rgba(60,52,32,.10);
}
.theme-card.is-selected {
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.15);
}
.theme-card-preview {
  display: block;
  padding: 22px 22px 18px;
  min-height: 130px;
  border-bottom: 1px solid var(--line-soft);
}
.theme-card-heading {
  display: block;
  font-size: 16px;
  font-weight: 600;
  margin-bottom: 8px;
  letter-spacing: .02em;
}
.theme-card-body {
  display: block;
  font-size: 12px;
  line-height: 1.5;
}
.theme-card-dropcap {
  font-size: 28px;
  line-height: .9;
  font-weight: 700;
  float: left;
  margin: 2px 6px 0 0;
  font-family: var(--font-display);
}
.theme-card-name {
  display: block;
  padding: 10px 16px;
  font-size: 13.5px;
  font-weight: 500;
  color: var(--ink-2);
  letter-spacing: .02em;
}
.theme-card-check {
  position: absolute;
  top: 10px; right: 10px;
  width: 22px; height: 22px;
  background: var(--accent);
  color: #fff;
  border-radius: 50%;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 12px;
  font-weight: 700;
  opacity: 0;
  transition: opacity .15s ease;
}
.theme-card.is-selected .theme-card-check { opacity: 1; }

/* Theme card wrapper holds the card itself + the kebab menu button.
 * The wrapper participates in the gallery grid the same way a bare
 * card did before, so layout is unchanged. */
.theme-card-wrap {
  position: relative;
  display: flex;
}
.theme-card-wrap .theme-card { flex: 1; }

/* "Default for new books" badge — shows on the user's chosen default
   theme so they can see at a glance which one new books inherit from.
   Pinned to the bottom-left so it doesn't compete with the selected
   check (top-right) or the kebab menu. */
.theme-card-wrap.is-default::after {
  content: 'Default';
  position: absolute;
  bottom: 38px;
  left: 8px;
  padding: 2px 7px;
  border-radius: 999px;
  background: var(--accent);
  color: #fff;
  font-family: var(--font-sans);
  font-size: 9.5px;
  font-weight: 700;
  letter-spacing: .12em;
  text-transform: uppercase;
  pointer-events: none;
  box-shadow: 0 1px 3px rgba(0,0,0,.15);
}
.theme-card-menu {
  position: absolute;
  top: 8px;
  right: 8px;
  width: 26px;
  height: 26px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: rgba(255, 255, 255, .92);
  border: 1px solid var(--line);
  border-radius: 999px;
  color: var(--ink-3);
  cursor: pointer;
  opacity: 0;
  transition: opacity .12s ease, background .12s ease, color .12s ease;
}
.theme-card-wrap:hover .theme-card-menu,
.theme-card-menu:focus-visible { opacity: 1; }
.theme-card-menu:hover {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}

/* "+ Create new theme" card — accent-tinted call-to-action at the
 * start of the gallery. */
.theme-card-new {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 8px;
  background: var(--accent);
  border-color: var(--accent);
  color: #fff;
  text-align: center;
  cursor: pointer;
  min-height: 200px;
}
.theme-card-new:hover {
  background: var(--accent-soft);
  border-color: var(--accent-soft);
  color: #fff;
}
.theme-card-new-icon {
  font-size: 36px;
  font-weight: 300;
  line-height: 1;
}
.theme-card-new-label {
  font-family: var(--font-sans);
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  line-height: 1.4;
}

/* Theme actions popover (anchored next to the kebab button) */
.theme-action-pop {
  position: absolute;
  z-index: 240;
  min-width: 180px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  padding: 4px;
  display: flex;
  flex-direction: column;
  animation: preset-pop-in .12s ease-out;
}
.theme-action-pop[hidden] { display: none; }
.theme-action-pop-item {
  background: transparent;
  border: none;
  font: inherit;
  font-size: 13px;
  text-align: left;
  padding: 8px 12px;
  color: var(--ink-1);
  cursor: pointer;
  border-radius: var(--radius-sm);
}
.theme-action-pop-item:hover { background: var(--accent-soft); color: var(--ink-1); }
.theme-action-pop-item.theme-action-pop-danger { color: var(--danger); }
.theme-action-pop-item.theme-action-pop-danger:hover { background: var(--danger); color: #fff; }
/* On a built-in theme, only "Duplicate" is meaningful — hide the rest. */
.theme-action-pop.is-built-in .theme-action-pop-user { display: none; }

/* Format side column (device preview + export + advanced typography) */
.format-side {
  position: sticky;
  top: 16px;
  display: flex;
  flex-direction: column;
  gap: 16px;
}

/* Device shell centers and bounds the frame so it doesn't stretch with content. */
.device-shell {
  display: flex;
  justify-content: center;
}

/* ---- Device frame: realistic device chrome with a fixed-size scrollable screen. ---- */
.device-frame {
  position: relative;
  background: #1d1b18;
  box-shadow: 0 6px 24px rgba(0,0,0,.18);
  flex-shrink: 0;
  /* Per-device dimensions live below — these are reasonable defaults. */
  width: 320px;
  height: 460px;
  border-radius: 22px;
  padding: 14px;
}
/* iPad: rounded corners, even bezel, tiny camera dot at the top */
.device-frame[data-device="ipad"] {
  width: 340px;
  height: 460px;
  border-radius: 22px;
  padding: 18px 14px;
  background: #1d1b18;
}
.device-frame[data-device="ipad"]::before {
  content: '';
  position: absolute;
  top: 7px; left: 50%;
  width: 5px; height: 5px;
  background: #3a3733;
  border-radius: 50%;
  transform: translateX(-50%);
}
/* Kindle Oasis: thicker bezel on the left for the page-turn buttons */
.device-frame[data-device="kindle"] {
  width: 320px;
  height: 460px;
  border-radius: 8px;
  padding: 14px 14px 14px 38px;
  background: #2a2723;
}
.device-frame[data-device="kindle"]::before,
.device-frame[data-device="kindle"]::after {
  content: '';
  position: absolute;
  left: 12px;
  width: 14px;
  height: 4px;
  background: #555048;
  border-radius: 2px;
}
.device-frame[data-device="kindle"]::before { top: 38%; }
.device-frame[data-device="kindle"]::after  { top: 56%; }

/* Phone: tall, very rounded corners, a notch at the top */
.device-frame[data-device="phone"] {
  width: 240px;
  height: 470px;
  border-radius: 28px;
  padding: 36px 12px;
  background: #1d1b18;
}
.device-frame[data-device="phone"]::before {
  content: '';
  position: absolute;
  top: 10px; left: 50%;
  width: 70px; height: 14px;
  background: #000;
  border-radius: 0 0 10px 10px;
  transform: translateX(-50%);
}

/* Paperback: tan cover with a flat spine */
.device-frame[data-device="paperback"] {
  width: 320px;
  height: 460px;
  background: #c9bfa5;
  border-radius: 4px;
  padding: 8px 8px 8px 14px;
  box-shadow: 0 6px 24px rgba(60,52,32,.22), inset 6px 0 0 rgba(0,0,0,.12);
}

.device-screen {
  width: 100%;
  height: 100%;
  background: #fdfbf6;
  border-radius: 4px;
  overflow-y: auto;
  font-family: var(--font-serif);
}
/* Inset of the rendered page within the screen — slightly different per device */
.device-page {
  font-size: 12px;
  line-height: 1.55;
  color: var(--ink-1);
  padding: 24px 22px 28px;
}
.device-frame[data-device="kindle"] .device-page    { padding: 24px 18px 28px; background: #f4ecd8; }
.device-frame[data-device="kindle"] .device-screen  { background: #f4ecd8; }
.device-frame[data-device="phone"] .device-page     { padding: 18px 14px 22px; font-size: 11px; }
.device-frame[data-device="paperback"] .device-page { padding: 28px 26px 32px; }

/* Subtle scrollbar inside the screen */
.device-screen::-webkit-scrollbar       { width: 6px; }
.device-screen::-webkit-scrollbar-thumb { background: rgba(0,0,0,.18); border-radius: 3px; }
.device-screen::-webkit-scrollbar-track { background: transparent; }
.device-page {
  font-size: 12px;
  line-height: 1.55;
  color: var(--ink-1);
}
.device-chapter-title {
  font-family: var(--font-display);
  font-size: 14px;
  font-weight: 600;
  margin: 0 0 12px;
  text-align: center;
  letter-spacing: .02em;
}

/* Real chapter-head used inside the device frame — same styles as the
   live preview, scaled down to the device-page's smaller base font. */
.device-chapter-head { margin-bottom: 14px; padding-top: 4px; }
/* Title sizes scale from the user's chapter_title_size setting. Each
   chapter style has a base device-scale multiplier (1.4 for classic,
   0.9 for banner, etc.) — we scale that by (user_size / 1.9) so a
   default value (1.9) matches the original, while user overrides
   live-update the preview. Same pattern applies to subtitle. */
.device-chapter-head .chapter-title { font-size: calc(1.5em * var(--pv-chapter-title-size, 1.9) / 1.9); line-height: 1.15; }
.device-chapter-head.chapter-head-banner .chapter-title {
  font-size: calc(0.9em * var(--pv-chapter-title-size, 1.9) / 1.9);
  padding: 8px 18px;
  letter-spacing: .12em;
}
.device-chapter-head.chapter-head-classic .chapter-title { font-size: calc(1.4em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head.chapter-head-ornate  .chapter-title { font-size: calc(1.4em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head.chapter-head-modern  .chapter-title { font-size: calc(1.25em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head.chapter-head-minimal .chapter-title { font-size: calc(1.1em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head.chapter-head-caps      .chapter-title { font-size: calc(1.35em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head.chapter-head-framed    .chapter-title { font-size: calc(1.4em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head.chapter-head-editorial .chapter-title { font-size: calc(1.4em * var(--pv-chapter-title-size, 1.9) / 1.9); }
.device-chapter-head .chapter-subtitle    { font-size: calc(0.9em * var(--pv-chapter-subtitle-size, 1.1) / 1.1); margin-top: .35em; }
.device-chapter-subtitle {
  font-family: var(--font-serif);
  font-style: italic;
  font-size: 11px;
  color: var(--ink-3);
  text-align: center;
  margin: -8px 0 14px;
}
.device-chapter-body {
  /* font_size (pt) is multiplied by 1.05 to land near the px values
     used at default 11pt body. line_height + paragraph_spacing come
     directly from the user's theme settings. text_align + hyphens are
     pushed via separate CSS vars set by format.js's preview update. */
  font-size: calc(var(--pv-body-pt, 11) * 1.05px);
  line-height: var(--pv-line-height, 1.55);
  margin: 0 0 calc(0.5em + var(--pv-paragraph-spacing, 0em));
  text-align: var(--pv-text-align, justify);
  hyphens: var(--pv-hyphens, auto);
  -webkit-hyphens: var(--pv-hyphens, auto);
  color: var(--pv-text-color, var(--ink-1));
}
.device-chapter-body:last-child { margin-bottom: 0; }
.device-chapter-heading {
  font-family: var(--font-display);
  font-weight: 600;
  margin: 1em 0 0.4em;
  font-size: 13px;
}
.device-chapter-quote {
  border-left: 2px solid var(--accent);
  padding: 0 0.6em;
  margin: 0.6em 0;
  font-style: italic;
  color: var(--ink-2);
  text-indent: 0;
}
.device-nav {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 8px;
  padding: 4px 0 0;
}
.device-nav-btn {
  background: #fff;
  color: var(--ink-2);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 8px 12px;
  font-family: inherit;
  font-size: 12px;
  cursor: pointer;
}
.device-nav-btn:hover { background: var(--bg-rail); color: var(--ink-1); border-color: var(--line-strong); }

.format-export-row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 8px;
}
.btn-block { width: 100%; }

/* Cleanup tools row in the format view sidebar — sits below export
   buttons. Single column; the small label sets it apart from the
   export grid above. */
.format-cleanup-row {
  margin-top: 14px;
  padding-top: 12px;
  border-top: 1px solid var(--line-soft);
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.format-cleanup-label {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-3);
}

/* Disabled state on export anchors during generation. <a> doesn't honor
   the `disabled` attribute, so this gives us the visual + pointer cue. */
.btn[aria-busy="true"] {
  opacity: .65;
  pointer-events: none;
  cursor: progress;
}
.btn[aria-busy="true"]::after {
  content: "";
  display: inline-block;
  width: 12px;
  height: 12px;
  margin-left: 8px;
  vertical-align: -2px;
  border-radius: 50%;
  border: 2px solid currentColor;
  border-right-color: transparent;
  animation: scrived-spin .7s linear infinite;
}

/* Bottom-right toast that stays visible across view tabs while a PDF /
   EPUB build is running. Plain progress feedback — no real percent
   because the server doesn't stream Content-Length until the file is
   finished, but the spinner + reassuring sub-line is what's missing. */
.export-toast {
  position: fixed;
  right: 24px;
  bottom: 24px;
  z-index: 60;
  display: flex;
  align-items: center;
  gap: 14px;
  padding: 14px 18px;
  border-radius: 10px;
  background: var(--ink-1, #1a1a1a);
  color: #fff;
  box-shadow: 0 14px 36px rgba(0,0,0,.28);
  font-family: var(--font-sans);
  max-width: 360px;
}
.export-toast.is-error {
  background: #b03030;
}
.export-toast-spinner {
  flex-shrink: 0;
  width: 22px;
  height: 22px;
  border-radius: 50%;
  border: 3px solid rgba(255,255,255,.25);
  border-top-color: #fff;
  animation: scrived-spin .8s linear infinite;
}
.export-toast.is-error .export-toast-spinner { display: none; }
.export-toast-text {
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.export-toast-text strong { font-size: 14px; font-weight: 600; }
.export-toast-sub {
  font-size: 12px;
  color: rgba(255,255,255,.75);
  line-height: 1.35;
}

@keyframes scrived-spin { to { transform: rotate(360deg); } }

/* ----- Format editor (the inspector, now in the main column) ----- */
.format-editor {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  margin-top: 24px;
  box-shadow: var(--shadow-paper);
  overflow: hidden;
  /* Hold a minimum height so switching from a tall section (e.g.
     Chapter heading) to a short one (Notes & footnotes) doesn't
     reflow the page or shift the device-preview column up. The
     value is roughly the height of the device preview at default
     viewport size — they stay shoulder-to-shoulder either way. */
  min-height: 540px;
}
.format-editor-head {
  padding: 16px 22px;
  border-bottom: 1px solid var(--line-soft);
  background: var(--bg-paper);
}
.format-editor-title {
  margin: 0 0 4px;
  font-family: var(--font-display);
  font-size: 17px;
  font-weight: 600;
  color: var(--ink-1);
}
.format-editor-sub {
  margin: 0;
  font-size: 12.5px;
  color: var(--ink-3);
}
.format-advanced-body {
  padding: 22px 22px 26px;
  display: grid;
  /* Two-column form layout when the main area is wide enough,
     single column when it isn't. */
  grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
  gap: 24px 32px;
}
.format-advanced-body .inspector-section {
  margin: 0;
  /* Sections that contain wide controls (radio grids) span both columns
     so options aren't squeezed. Mark them by adding class .inspector-section-wide
     in the markup if needed; default keeps one column. */
}
.format-advanced-body .inspector-section .section-heading {
  margin-top: 0;
}
/* Print layout has lots of toggles; let it span full width by default. */
.format-advanced-body .inspector-section:has(input[name="fmt-layout-priority"]),
.format-advanced-body .inspector-section.inspector-section-wide {
  grid-column: 1 / -1;
}
/* Header / Footer 2-column inner grid for the dropdowns */
.header-footer-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
  gap: 14px 18px;
  margin-bottom: 14px;
}

/* Chapter heading "Fine-tune" details + nested subtitle/title blocks */
.format-subsection > summary {
  font-family: var(--font-sans);
  font-size: 12px;
  font-weight: 600;
  color: var(--ink-2);
  text-transform: uppercase;
  letter-spacing: .12em;
  cursor: pointer;
  padding: 6px 0;
  list-style: revert;
}
.format-subsection > summary::marker { color: var(--ink-3); }
.ch-heading-block { margin-top: 14px; }
.ch-heading-block-title {
  margin: 0 0 8px;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .12em;
}

/* Inline footnote reference (rendered by Quill's FootnoteBlot).
   In the editor we show a tiny pill that hints at footnote presence;
   the actual text lives in data-fn-text. */
.ql-editor sup.fn-ref {
  background: var(--accent-soft);
  color: #fff;
  font-size: 0.7em;
  padding: 0 5px;
  border-radius: 999px;
  cursor: help;
  font-weight: 600;
  vertical-align: super;
}
.ql-editor sup.fn-ref:hover {
  background: var(--accent);
}

/* In the published view, the Quill marker gets replaced with a
   numbered superscript by the renderer. The inline pill style is
   editor-only; print/EPUB use a plain superscript number. */
.preview-page .chapter-body sup.fn-ref,
.print-page .chapter-body sup.fn-ref {
  background: transparent;
  color: var(--accent);
  padding: 0;
  border-radius: 0;
  font-weight: 600;
}

/* Footnotes block at end of chapter / end of book */
.footnotes-section {
  margin-top: 2em;
  padding-top: 1em;
  border-top: 1px solid var(--line);
  font-size: var(--pv-fn-size, 0.85em);
  color: var(--ink-2);
}
.footnotes-section .footnotes-heading {
  font-family: var(--pv-heading-font);
  font-size: 1em;
  font-weight: 600;
  margin: 0 0 .8em;
  text-transform: uppercase;
  letter-spacing: .1em;
}
.footnotes-list { list-style: decimal; padding-left: 2em; margin: 0; }
.footnotes-list li { margin-bottom: .4em; line-height: 1.45; }

/* Scene-break ornament image upload + preview */
.scene-break-image-row {
  margin-top: 10px;
  padding: 12px;
  background: var(--bg-paper);
  border: 1px solid var(--line-soft);
  border-radius: var(--radius-sm);
}
.scene-break-image-row[hidden] { display: none; }
.scene-break-image-preview {
  background: #fff;
  border: 1px dashed var(--line);
  border-radius: var(--radius-sm);
  min-height: 60px;
  padding: 12px;
  display: flex;
  align-items: center;
  justify-content: center;
  margin-bottom: 8px;
}
.scene-break-image-preview img {
  max-width: 240px;
  max-height: 80px;
  display: block;
}
.scene-break-image-empty {
  color: var(--ink-3);
  font-size: 12px;
  font-style: italic;
}
.scene-break-image-actions {
  display: flex;
  align-items: center;
  gap: 10px;
}

/* When the rendered scene-break uses an image, the ::before glyph
   should not show; the <img> is the visual instead. */
.scene-break-image .scene-break-img {
  display: block;
  margin: 0 auto;
  max-width: 60%;
  max-height: 60px;
  height: auto;
}
.scene-break.scene-break-image::before { content: none !important; }
.preview-page .scene-break.scene-break-image::before { content: none !important; }

/* H2-H6 subheading rows: badge | font dropdown | size number */
.subheading-grid {
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.subheading-row {
  display: grid;
  grid-template-columns: 40px 1fr 130px;
  align-items: end;
  gap: 12px;
}
.subheading-label {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 13px;
  color: var(--ink-2);
  height: 36px;
}
.subheading-row .field { margin: 0; }
@media (max-width: 720px) {
  .subheading-row {
    grid-template-columns: 40px 1fr;
  }
  .subheading-row .subheading-size { grid-column: 2; }
}

.radio-grid {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  gap: 8px;
}
.radio-grid-sm { grid-template-columns: repeat(5, 1fr); }
.radio-card {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 4px;
  padding: 10px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  cursor: pointer;
  background: var(--bg-paper);
  transition: border-color .12s ease, background .12s ease;
}
.radio-card:hover { border-color: var(--accent-soft); }
.radio-card.is-selected {
  border-color: var(--accent);
  background: #fdf7e8;
  box-shadow: inset 0 0 0 1px var(--accent);
}
.radio-card input[type=radio] { position: absolute; opacity: 0; pointer-events: none; }
.radio-card-preview {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 14px;
  color: var(--ink-2);
}
.radio-card-label {
  font-size: 11px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .08em;
}
.radio-card-glyph {
  font-size: 18px;
  color: var(--accent);
}

/* Mini chapter heading previews */
.chapter-preview-classic { letter-spacing: .14em; text-transform: uppercase; font-size: 11px; }
.chapter-preview-modern  { font-size: 13px; font-weight: 500; }
.chapter-preview-ornate  { font-style: italic; font-family: var(--font-serif); font-size: 13px; }
.chapter-preview-banner  { font-weight: 700; font-size: 14px; padding: 4px 8px; background: var(--ink-1); color: #fff; border-radius: 2px; }
.chapter-preview-minimal { font-weight: 400; font-size: 13px; color: var(--ink-3); }
.chapter-preview-caps    { text-transform: uppercase; letter-spacing: .12em; font-weight: 600; font-size: 11px; }
.chapter-preview-framed  { font-style: italic; font-size: 13px; border-top: 1px solid var(--accent); border-bottom: 1px solid var(--accent); padding: 2px 0; }
.chapter-preview-editorial { font-weight: 600; font-size: 13px; border-bottom: 1px solid var(--accent); padding-bottom: 2px; }

/* ============================================================
   PHASE 2 — Preview view
   ============================================================ */
.preview-view {
  background: #e7e2d6;
  display: flex !important;
  flex-direction: column;
  overflow: hidden;
}
.preview-view[hidden] { display: none !important; }

/* ============================================================
   Story bible view
   ============================================================ */
/* The .editor-view.is-active rule above forces display:flex on the
   active view (specificity 0,2,0). To keep this view as a grid
   container we match its specificity with .editor-view.bible-view
   so the later-defined rule wins. */
.editor-view.bible-view {
  display: grid;
  grid-template-columns: 320px 1fr;
  /* Auto top row holds the Resources/Bible sub-tab strip; 1fr below
     gives the sidebar + main pane the same height they had before. */
  grid-template-rows: auto 1fr;
  background: var(--bg-page);
  overflow: hidden;
}
.bible-view[hidden] { display: none !important; }
.bible-view > .subview-tabs { grid-column: 1 / -1; }

.bible-sidebar {
  display: flex;
  flex-direction: column;
  background: #fff;
  border-right: 1px solid var(--line);
  overflow: hidden;
}
.bible-sidebar-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 18px 10px;
  border-bottom: 1px solid var(--line);
}
.bible-sidebar-title {
  margin: 0;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
}
.bible-sidebar-search {
  padding: 10px 14px;
  border-bottom: 1px solid var(--line-soft);
}
.bible-sidebar-search input {
  width: 100%;
  padding: 8px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13px;
  background: var(--bg-paper);
}
.bible-sidebar-search input:focus { outline: none; border-color: var(--accent); }
.bible-sidebar-scroll {
  flex: 1;
  overflow-y: auto;
  padding: 8px 0 16px;
}
.bible-empty {
  padding: 18px 16px;
  margin: 0;
  font-size: 13px;
  color: var(--ink-3);
  font-style: italic;
}
.bible-group { margin: 12px 0 6px; }
.bible-group-head {
  margin: 0;
  padding: 6px 18px;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
  display: flex;
  align-items: center;
  gap: 6px;
}
.bible-group-head .bible-count {
  margin-left: auto;
  font-weight: 500;
  color: var(--ink-3);
  font-size: 10.5px;
}
.bible-group-list {
  list-style: none;
  margin: 4px 0;
  padding: 0;
}
.bible-row {
  padding: 8px 16px 8px 18px;
  border-left: 3px solid transparent;
  cursor: pointer;
  transition: background .12s ease;
}
.bible-row:hover { background: var(--bg-paper); }
.bible-row.is-selected {
  background: #fdf7e8;
  border-left-color: var(--accent);
}
.bible-row-name {
  font-weight: 500;
  color: var(--ink-1);
  font-size: 13.5px;
}
.bible-row-aliases {
  font-size: 11.5px;
  color: var(--ink-3);
  font-style: italic;
  margin-top: 2px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* ----- Bible main / form ----- */
.bible-main {
  overflow-y: auto;
  padding: 32px 48px;
}
.bible-empty-state {
  max-width: 520px;
  margin: 80px auto;
  text-align: center;
}
.bible-empty-state .empty-mark {
  font-size: 36px;
  color: var(--accent);
  margin-bottom: 12px;
}
.bible-empty-state .empty-heading {
  font-family: var(--font-display);
  font-size: 28px;
  margin: 0 0 12px;
}
.bible-empty-state .empty-sub {
  color: var(--ink-3);
  margin: 0 0 24px;
  line-height: 1.55;
}

.bible-form {
  max-width: 820px;
  margin: 0 auto;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  box-shadow: var(--shadow-paper);
  overflow: hidden;
}
.bible-form-head {
  display: grid;
  grid-template-columns: 96px 1fr auto;
  gap: 16px;
  align-items: start;
  padding: 18px 22px;
  border-bottom: 1px solid var(--line);
  background: var(--bg-paper);
}
.bible-form-image {
  width: 96px;
  height: 96px;
  border-radius: 8px;
  background: #f0eadb;
  border: 1px solid var(--line);
  display: flex;
  align-items: center;
  justify-content: center;
  overflow: hidden;
  position: relative;
}
.bible-form-image img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}
.bible-image-placeholder {
  font-size: 11px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .1em;
}
.bible-form-head-fields {
  display: flex;
  flex-direction: column;
  gap: 10px;
  min-width: 0;
}
.bible-name-input {
  width: 100%;
  border: none;
  outline: none;
  background: transparent;
  font-family: var(--font-display);
  font-size: 22px;
  font-weight: 600;
  color: var(--ink-1);
  padding: 4px 0;
  border-bottom: 1px solid transparent;
  transition: border-color .12s ease;
}
.bible-name-input:focus { border-bottom-color: var(--accent-soft); }
.bible-name-input::placeholder { color: var(--ink-3); font-weight: 400; }
.bible-form-row {
  display: flex;
  gap: 14px;
  flex-wrap: wrap;
}
.bible-mini-field {
  display: flex;
  flex-direction: column;
  gap: 4px;
  font-size: 11px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .08em;
}
.bible-mini-field select,
.bible-mini-field input[type=color] {
  font: inherit;
  font-size: 13px;
  text-transform: none;
  letter-spacing: 0;
  padding: 4px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  color: var(--ink-1);
  background: #fff;
}
.bible-mini-field input[type=color] {
  width: 50px;
  padding: 2px;
  height: 30px;
}
.bible-image-buttons {
  display: flex;
  gap: 6px;
  align-items: center;
}
.bible-form-delete {
  width: 36px;
  height: 36px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  color: var(--ink-3);
  cursor: pointer;
  align-self: start;
}
.bible-form-delete:hover { color: var(--danger); border-color: var(--danger); }

.bible-form-body {
  padding: 22px;
  display: flex;
  flex-direction: column;
  gap: 16px;
}
.bible-field { display: flex; flex-direction: column; gap: 6px; }
.bible-field-label {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-2);
}
.bible-field-hint {
  font-weight: 400;
  text-transform: none;
  letter-spacing: 0;
  color: var(--ink-3);
  margin-left: 6px;
  font-size: 11px;
}
.bible-field input,
.bible-field textarea {
  font: inherit;
  font-size: 14px;
  padding: 9px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  color: var(--ink-1);
  resize: vertical;
}
.bible-field input:focus,
.bible-field textarea:focus { outline: none; border-color: var(--accent); background: #fff; }
.bible-field textarea {
  font-family: var(--font-serif, Georgia, serif);
  line-height: 1.5;
  min-height: 240px;
}

.bible-form-foot {
  padding: 12px 22px;
  border-top: 1px solid var(--line);
  background: var(--bg-paper);
  display: flex;
  justify-content: flex-end;
}
.bible-save-status {
  font-size: 12px;
  color: var(--ink-3);
  font-style: italic;
}

/* ----- Bible mention popover (writing view hover) ----- */
/* Codex mentions in the manuscript: every entry name/alias gets a quiet
   dotted underline so the writer can see what's in the codex at a glance.
   Painted by bible.js via the CSS Custom Highlight API — pure ranges,
   no markup injected into Quill's document. Only color/decoration
   properties are valid inside ::highlight. */
::highlight(codex-mentions) {
  text-decoration: underline dotted 1px;
  text-decoration-color: color-mix(in srgb, var(--accent) 60%, transparent);
}

.bible-mention-popover {
  position: fixed;
  z-index: 260;
  width: 280px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-left: 4px solid var(--accent);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  padding: 12px 14px;
  font-family: var(--font-sans);
  font-size: 13px;
  color: var(--ink-1);
  pointer-events: auto;
  animation: preset-pop-in .12s ease-out;
}
.bible-mention-popover[hidden] { display: none; }
.bible-mention-head {
  display: flex;
  align-items: baseline;
  gap: 8px;
  margin-bottom: 8px;
}
.bible-mention-kind {
  font-size: 10.5px;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--accent);
  font-weight: 600;
}
.bible-mention-name {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 15px;
  color: var(--ink-1);
}
.bible-mention-body {
  display: flex;
  gap: 10px;
  align-items: flex-start;
}
.bible-mention-image {
  width: 56px;
  height: 56px;
  object-fit: cover;
  border-radius: 6px;
  flex-shrink: 0;
  border: 1px solid var(--line);
}
.bible-mention-text { flex: 1; min-width: 0; }
.bible-mention-summary {
  margin: 0 0 6px;
  line-height: 1.5;
  color: var(--ink-2);
  font-size: 12.5px;
}
.bible-mention-summary.is-empty { color: var(--ink-3); font-style: italic; }
.bible-mention-open {
  font-size: 12px;
  color: var(--accent);
  background: none;
  border: none;
  padding: 0;
  cursor: pointer;
  font-family: inherit;
}
.bible-mention-open:hover { text-decoration: underline; }

/* ============================================================
   Resources view
   ============================================================ */
/* See .editor-view.bible-view above — same trick to keep the active
   resources view rendering as a grid instead of being flipped to flex
   by the .editor-view.is-active rule earlier in this file. */
.editor-view.resources-view {
  display: grid;
  grid-template-columns: 320px 1fr;
  /* Mirror of .bible-view: top row for the sub-tab strip, then the
     existing sidebar + main 320 / 1fr layout below. */
  grid-template-rows: auto 1fr;
  background: var(--bg-page);
  overflow: hidden;
  position: relative;
}
.resources-view[hidden] { display: none !important; }
.resources-view > .subview-tabs { grid-column: 1 / -1; }

/* Resources / Bible sub-tab strip. Two pills inside a thin bar that
   spans both the sidebar and main columns — the user can flip between
   the two views from either side. */
.subview-tabs {
  display: flex;
  gap: 4px;
  padding: 8px 14px;
  background: #fff;
  border-bottom: 1px solid var(--line);
}
.subview-tab {
  background: transparent;
  border: 1px solid transparent;
  border-radius: 999px;
  padding: 5px 14px;
  font: inherit;
  font-size: 12.5px;
  font-weight: 500;
  color: var(--ink-3);
  cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.subview-tab:hover { color: var(--ink-1); background: var(--bg-rail); }
.subview-tab.is-active {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}

.resources-sidebar {
  display: flex;
  flex-direction: column;
  background: #fff;
  border-right: 1px solid var(--line);
  overflow: hidden;
}
.resources-sidebar-head {
  padding: 16px 18px 8px;
  border-bottom: 1px solid var(--line);
}
.resources-sidebar-title {
  margin: 0;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
}
.resources-actions {
  padding: 12px 14px 8px;
  display: flex;
  flex-direction: column;
  gap: 6px;
  border-bottom: 1px solid var(--line-soft);
}
.res-action-btn {
  width: 100%;
  justify-content: center;
}
.resources-filter {
  display: flex;
  gap: 6px;
  padding: 10px 14px 8px;
  flex-wrap: wrap;
}
.res-chip {
  background: var(--bg-paper);
  color: var(--ink-2);
  border: 1px solid var(--line);
  border-radius: 999px;
  padding: 4px 12px;
  font: inherit;
  font-size: 12px;
  cursor: pointer;
  transition: background .12s ease, color .12s ease;
}
.res-chip:hover { background: var(--accent-soft); }
.res-chip.is-active {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}
.resources-search {
  padding: 0 14px 10px;
  border-bottom: 1px solid var(--line-soft);
}
.resources-search input {
  width: 100%;
  padding: 8px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13px;
  background: var(--bg-paper);
}
.resources-search input:focus { outline: none; border-color: var(--accent); }
.resources-sidebar-scroll {
  flex: 1;
  overflow-y: auto;
  padding: 8px 0 16px;
}
.res-empty {
  padding: 18px 16px;
  margin: 0;
  font-size: 13px;
  color: var(--ink-3);
  font-style: italic;
}
.res-group { margin: 12px 0 6px; }
.res-group-head {
  margin: 0;
  padding: 6px 18px;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
  display: flex;
  align-items: center;
  gap: 6px;
}
.res-group-head .res-count { margin-left: auto; font-weight: 500; font-size: 10.5px; }
.res-group-list { list-style: none; margin: 4px 0; padding: 0; }
.res-row {
  padding: 8px 16px 8px 18px;
  border-left: 3px solid transparent;
  cursor: pointer;
  display: flex;
  gap: 10px;
  align-items: flex-start;
  transition: background .12s ease;
}
.res-row:hover { background: var(--bg-paper); }
.res-row.is-selected {
  background: #fdf7e8;
  border-left-color: var(--accent);
}
.res-row-icon { font-size: 18px; flex-shrink: 0; line-height: 1.2; }
.res-row-text { flex: 1; min-width: 0; }
.res-row-title {
  font-weight: 500;
  color: var(--ink-1);
  font-size: 13.5px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.res-row-sub {
  font-size: 11.5px;
  color: var(--ink-3);
  margin-top: 2px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* Publisher Rocket companion panels (migrations 081/083, admin test phase). */
.kdp-rocket-runs,
.eaz-harvested {
  margin-top: 28px;
  padding-top: 18px;
  border-top: 1px solid var(--line);
}
.eaz-harvested .publishing-head { margin-bottom: 10px; }
.eaz-harv-group td {
  padding-top: 14px;
  border-bottom: 1px solid var(--line-strong);
  background: var(--bg-rail);
}
.eaz-harv-group .snap-link { margin-left: 10px; }

/* Rocket pane (083): queue harvests from the app. */
.kdp-rocket-form {
  margin-top: 20px;
  padding-top: 16px;
  border-top: 1px solid var(--line);
}
.kdp-rocket-form:first-of-type { border-top: none; padding-top: 0; }
.kdp-rocket-controls { align-items: end; gap: 12px; }
.kdp-rocket-controls .btn { margin-bottom: 2px; }
#rocket-keywords { font-family: var(--mono, monospace); font-size: 13px; }
.kdp-rocket-job {
  margin-top: 20px;
  padding: 14px 16px;
  border: 1px solid var(--line-strong);
  border-radius: 10px;
  background: var(--bg-rail);
}
.kdp-rocket-job-row { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.kdp-rocket-elapsed { font-size: 12px; color: var(--ink-3); }
.kdp-rocket-progress {
  margin: 10px 0 0;
  font-family: var(--mono, monospace);
  /* Wraps instead of truncating — a cut-off progress line is unreadable,
     and this text is the only live view of what the agent is doing. */
  font-size: 14px;
  line-height: 1.5;
  color: var(--ink-2);
  overflow-wrap: anywhere;
}
.kdp-rocket-error { margin: 8px 0 0; font-size: 13px; line-height: 1.5; color: var(--danger, #c0392b); overflow-wrap: anywhere; }
/* Running job whose agent heartbeat has gone quiet — visibly "not fine"
   without claiming failure yet. Same amber family as .pub-pill-paused. */
.kdp-rocket-stale {
  background: #fbf1cf;
  color: #6b5210;
  border-color: #efdf95;
}
.kdp-rocket-agent-hint { font-size: 12px; color: var(--ink-3); margin-left: 8px; }

/* Tool-pushed report chip (Publisher Rocket companion, migration 081). */
.res-rocket-chip {
  display: inline-block;
  margin-left: 6px;
  padding: 0 6px;
  border: 1px solid var(--line-strong);
  border-radius: 999px;
  font-size: 10px;
  font-weight: 600;
  color: var(--ink-2);
  background: var(--bg-rail);
  vertical-align: 1px;
}

/* In-flight upload row. Subdued so it doesn't compete with finished
   files; the spinner gives unambiguous "I'm working on it" feedback. */
.res-row.is-uploading {
  cursor: progress;
  opacity: .85;
  background: var(--bg-rail);
}
.res-row.is-uploading:hover { background: var(--bg-rail); }
.res-row.is-uploading .res-row-title { color: var(--ink-2); font-style: italic; }
.res-row-spinner {
  display: inline-block;
  width: 16px;
  height: 16px;
  border-radius: 50%;
  border: 2px solid var(--line-strong);
  border-top-color: var(--accent);
  animation: res-spinner-rot .9s linear infinite;
}
@keyframes res-spinner-rot { to { transform: rotate(360deg); } }

/* ----- Resources main pane ----- */
.resources-main {
  overflow-y: auto;
  padding: 32px 48px;
  position: relative;
}
.resources-empty-state {
  max-width: 560px;
  margin: 80px auto;
  text-align: center;
}
.resources-empty-state .empty-mark {
  font-size: 36px;
  margin-bottom: 12px;
}
.resources-empty-state .empty-heading {
  font-family: var(--font-display);
  font-size: 28px;
  margin: 0 0 12px;
}
.resources-empty-state .empty-sub {
  color: var(--ink-3);
  margin: 0 0 24px;
  line-height: 1.55;
}

.resource-detail {
  max-width: 880px;
  margin: 0 auto;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  box-shadow: var(--shadow-paper);
  overflow: hidden;
}
.resource-detail-head {
  display: grid;
  grid-template-columns: auto 1fr auto;
  gap: 14px;
  align-items: center;
  padding: 16px 22px;
  border-bottom: 1px solid var(--line);
  background: var(--bg-paper);
}
.resource-kind-badge {
  display: inline-block;
  padding: 3px 10px;
  border-radius: 999px;
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  background: var(--accent);
  color: #fff;
}
.resource-kind-badge[data-kind="link"] { background: #4a78c0; }
.resource-kind-badge[data-kind="note"] { background: #6b7a4a; }
.resource-title-input {
  width: 100%;
  border: none;
  outline: none;
  background: transparent;
  font-family: var(--font-display);
  font-size: 22px;
  font-weight: 600;
  color: var(--ink-1);
  padding: 4px 0;
  border-bottom: 1px solid transparent;
  transition: border-color .12s ease;
}
.resource-title-input:focus { border-bottom-color: var(--accent-soft); }
.resource-detail-delete {
  width: 36px;
  height: 36px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  color: var(--ink-3);
  cursor: pointer;
}
.resource-detail-delete:hover { color: var(--danger); border-color: var(--danger); }

.resource-detail-body {
  padding: 22px;
  display: flex;
  flex-direction: column;
  gap: 14px;
}

.resource-preview {
  background: #f8f5ec;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 12px;
  display: flex;
  align-items: center;
  justify-content: center;
  min-height: 120px;
}
.resource-preview-image {
  max-width: 100%;
  max-height: 520px;
  object-fit: contain;
  display: block;
}
.resource-preview-pdf {
  width: 100%;
  height: 600px;
  border: none;
  background: #fff;
}
.resource-preview-audio,
.resource-preview-video {
  width: 100%;
  max-height: 480px;
}
.resource-preview-text {
  width: 100%;
  max-height: 480px;
  overflow: auto;
  background: #fff;
  border: 1px solid var(--line);
  padding: 12px 14px;
  font-family: var(--font-mono, ui-monospace, Menlo, Consolas, monospace);
  font-size: 12.5px;
  line-height: 1.55;
  white-space: pre-wrap;
  word-wrap: break-word;
  color: var(--ink-1);
  margin: 0;
  border-radius: var(--radius-sm);
}
.resource-preview-generic {
  text-align: center;
  padding: 24px 10px;
}
.resource-icon { font-size: 48px; margin-bottom: 8px; }
.resource-preview-msg { color: var(--ink-3); margin: 0; font-size: 13px; }

.resource-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  font-size: 12px;
  color: var(--ink-3);
}
.resource-meta .dot { opacity: .5; }

.resource-file-actions {
  display: flex;
  gap: 8px;
}

.resource-link-block,
.resource-note-block {
  display: flex;
  flex-direction: column;
  gap: 8px;
}

.resource-detail-foot {
  padding: 12px 22px;
  border-top: 1px solid var(--line);
  background: var(--bg-paper);
  display: flex;
  justify-content: flex-end;
}

/* ----- Drag-and-drop overlay ----- */
.resource-drop-overlay {
  position: absolute;
  inset: 0;
  background: rgba(139, 105, 20, 0.08);
  border: 3px dashed var(--accent);
  z-index: 50;
  display: flex;
  align-items: center;
  justify-content: center;
  pointer-events: none;
  border-radius: 0;
}
.resource-drop-overlay[hidden] { display: none; }
.resource-drop-card {
  background: #fff;
  border: 1px solid var(--accent);
  border-radius: var(--radius);
  padding: 28px 40px;
  text-align: center;
  box-shadow: var(--shadow-2);
}
.resource-drop-icon {
  font-size: 36px;
  color: var(--accent);
  margin-bottom: 8px;
}
.resource-drop-msg {
  font-family: var(--font-display);
  font-size: 18px;
  font-weight: 600;
  color: var(--ink-1);
}

/* ----- Link composer popover ----- */
.res-link-composer {
  position: fixed;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  z-index: 280;
  width: 420px;
  background: #fff;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
  box-shadow: var(--shadow-2);
  animation: preset-pop-in .12s ease-out;
}
.res-link-composer[hidden] { display: none; }
.res-link-composer-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 14px 18px;
  border-bottom: 1px solid var(--line);
}
.res-link-composer-head h3 {
  margin: 0;
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
}
.res-link-composer-body {
  padding: 18px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.res-link-composer-actions {
  display: flex;
  justify-content: flex-end;
  gap: 8px;
  margin-top: 6px;
}

/* ============================================================
   Corkboard view
   ============================================================ */
.corkboard-view {
  display: flex;
  flex-direction: column;
  background: var(--bg-page);
  overflow: hidden;
}
.corkboard-view[hidden] { display: none !important; }

.corkboard-toolbar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 18px 32px;
  background: #fff;
  border-bottom: 1px solid var(--line);
  gap: 24px;
  flex-wrap: wrap;
}
.corkboard-title {
  font-family: var(--font-display);
  margin: 0 0 2px;
  font-size: 22px;
  font-weight: 600;
  color: var(--ink-1);
}
.corkboard-sub { color: var(--ink-3); font-size: 12.5px; }
.corkboard-toolbar-right {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 12px;
  /* When the toolbar wraps onto two lines, the filter rows should stack
     left-aligned instead of justifying to the right edge. */
  justify-content: flex-end;
}
.corkboard-filter { display: flex; gap: 6px; flex-wrap: wrap; }

/* Second-row filters (POV / Location) — same accent palette as the
   status chips, but using compact <select>s since the values are
   free text and can have many distinct entries. */
.corkboard-filter-extra {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10px;
}
.corkboard-filter-group {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
.corkboard-filter-label {
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
.corkboard-filter-select {
  padding: 4px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  font: inherit;
  font-size: 12.5px;
  color: var(--ink-1);
  max-width: 160px;
}
.corkboard-filter-reset {
  font-size: 12px;
  color: var(--ink-3);
}
.corkboard-filter-reset:hover { color: var(--accent); }

.corkboard-stage {
  flex: 1;
  overflow-y: auto;
  padding: 24px 32px 60px;
}

.corkboard-empty {
  max-width: 480px;
  margin: 80px auto;
  text-align: center;
}
.corkboard-empty .empty-mark { font-size: 36px; margin-bottom: 12px; }
.corkboard-empty .empty-heading {
  font-family: var(--font-display);
  font-size: 24px;
  margin: 0 0 8px;
}
.corkboard-empty .empty-sub { color: var(--ink-3); }

.corkboard-section { margin-bottom: 28px; }
.corkboard-section-head {
  display: flex;
  align-items: baseline;
  gap: 12px;
  margin: 0 0 12px;
  padding-bottom: 8px;
  border-bottom: 1px solid var(--line-soft);
}
.corkboard-section-head h3 {
  margin: 0;
  font-family: var(--font-sans);
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
}
.corkboard-section-count { font-size: 11.5px; color: var(--ink-3); }
.corkboard-section-empty {
  color: var(--ink-3);
  font-style: italic;
  font-size: 13px;
  padding: 8px 0;
  margin: 0;
  grid-column: 1 / -1;
}

.corkboard-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(260px, 1fr));
  gap: 14px;
}

.corkboard-card {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 0;
  display: flex;
  flex-direction: column;
  box-shadow: var(--shadow-paper);
  cursor: grab;
  transition: transform .12s ease, box-shadow .12s ease, border-color .12s ease;
  /* Pinned to a corkboard look — subtle paper texture */
  background-image:
    linear-gradient(180deg, rgba(255,255,255,1), rgba(252,247,232,.4));
  position: relative;
  border-top-width: 3px;
  border-top-color: var(--line);
}
.corkboard-card:hover {
  transform: translateY(-1px);
  box-shadow: 0 6px 18px rgba(0,0,0,.06);
}
.corkboard-card.is-dragging { opacity: .5; }
.corkboard-card.drag-over { outline: 2px dashed var(--accent); outline-offset: 2px; }

/* Bulk-edit selection. The checkbox sits in the top-right corner so it
   doesn't fight with the chapter number on the left of the header.
   Hover surfaces it; once any card is selected, every checkbox stays
   visible site-wide so the user can keep building / pruning the set. */
.corkboard-card-select {
  position: absolute;
  top: 8px;
  right: 8px;
  width: 18px;
  height: 18px;
  border: 1.5px solid var(--ink-4);
  border-radius: 4px;
  background: rgba(255,255,255,.92);
  cursor: pointer;
  padding: 0;
  opacity: .35;
  transition: opacity .12s ease, background .12s ease, border-color .12s ease;
  z-index: 2;
}
.corkboard-card:hover .corkboard-card-select { opacity: 1; }
.corkboard-card-select:hover { border-color: var(--accent); }
.corkboard-card.is-selected .corkboard-card-select {
  opacity: 1;
  background: var(--accent);
  border-color: var(--accent);
}
.corkboard-card.is-selected .corkboard-card-select::after {
  content: '';
  position: absolute;
  inset: 0;
  background: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'><path d='M3.5 8l3 3 6-6.5' fill='none' stroke='%23fff' stroke-width='2.2' stroke-linecap='round' stroke-linejoin='round'/></svg>") center / 12px 12px no-repeat;
}
.corkboard-card.is-selected {
  outline: 2px solid var(--accent);
  outline-offset: 1px;
}

/* When any card is selected, hint that all the others are pickable too
   by raising the checkboxes globally. */
.corkboard-stage:has(.corkboard-card.is-selected) .corkboard-card-select { opacity: 1; }

/* ---------- Bulk action bar ---------- */
.corkboard-bulk-bar {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10px;
  padding: 10px 18px;
  background: var(--bg-card);
  border-bottom: 1px solid var(--line-soft);
  position: sticky;
  top: 0;
  z-index: 5;
  box-shadow: 0 1px 3px rgba(0,0,0,.04);
}
.corkboard-bulk-bar.is-busy { opacity: .7; pointer-events: none; }
.corkboard-bulk-count {
  font-weight: 600;
  font-size: 13px;
  color: var(--ink-1);
  letter-spacing: .02em;
}
.corkboard-bulk-group {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
.corkboard-bulk-label {
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
  margin-right: 2px;
}
.corkboard-bulk-divider {
  width: 1px;
  height: 18px;
  background: var(--line);
  margin: 0 4px;
}
.corkboard-bulk-spacer { flex: 1; }
.corkboard-bulk-btn {
  background: var(--bg-paper);
  color: var(--ink-2);
  border: 1px solid var(--line);
  border-radius: 999px;
  padding: 4px 11px;
  font: inherit;
  font-size: 12px;
  cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.corkboard-bulk-btn:hover { background: var(--accent-soft); border-color: var(--line-strong); }
.corkboard-bulk-danger { color: var(--danger); border-color: var(--danger); }
.corkboard-bulk-danger:hover { background: var(--danger); color: #fff; border-color: var(--danger); }
.corkboard-bulk-close {
  width: 24px; height: 24px;
  border: none;
  background: transparent;
  color: var(--ink-3);
  font-size: 18px;
  line-height: 1;
  cursor: pointer;
  border-radius: 4px;
  padding: 0;
}
.corkboard-bulk-close:hover { color: var(--ink-1); background: var(--bg-rail); }

/* Status-coded top edge */
.corkboard-card[data-status="draft"]    { border-top-color: #6b7480; }
.corkboard-card[data-status="revising"] { border-top-color: #d18a3d; }
.corkboard-card[data-status="revised"]  { border-top-color: #7a52a3; }
.corkboard-card[data-status="final"]    { border-top-color: #4a8b4d; }

.corkboard-card-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 8px;
  /* Right padding reserves room for the corner checkbox so the
     status pill never sits underneath it. The checkbox lives at
     top:8/right:8/width:18, so it occupies roughly the rightmost
     26px of the card. 32px right padding gives the pill clearance. */
  padding: 12px 32px 6px 14px;
}
.corkboard-card-head-left {
  display: flex;
  /* flex-start so the chapter number lines up with the first row
     (title) rather than centering between title + subtitle. */
  align-items: flex-start;
  gap: 8px;
  flex: 1;
  min-width: 0;
}
.corkboard-card-num {
  font-family: var(--font-display);
  font-weight: 600;
  color: var(--accent);
  font-size: 13px;
  flex-shrink: 0;
  padding: 4px 4px 0;
}
.corkboard-card-titles {
  display: flex;
  flex-direction: column;
  gap: 2px;
  flex: 1;
  min-width: 0;
}
.corkboard-card-title {
  border: none;
  background: transparent;
  font-family: var(--font-display);
  font-size: 15px;
  font-weight: 600;
  color: var(--ink-1);
  padding: 2px 0;
  border-bottom: 1px solid transparent;
  transition: border-color .12s ease;
  min-width: 0;
  outline: none;
}
.corkboard-card-title:focus { border-bottom-color: var(--accent-soft); }
.corkboard-card-subtitle {
  border: none;
  background: transparent;
  font-family: var(--font-serif, Georgia, serif);
  font-style: italic;
  font-size: 12px;
  color: var(--ink-3);
  padding: 1px 0;
  border-bottom: 1px solid transparent;
  transition: border-color .12s ease, color .12s ease;
  outline: none;
  min-width: 0;
}
.corkboard-card-subtitle::placeholder { color: var(--ink-4); font-style: italic; }
.corkboard-card-subtitle:focus { border-bottom-color: var(--accent-soft); color: var(--ink-2); }

.corkboard-status-pill {
  background: var(--bg-paper);
  color: var(--ink-2);
  border: 1px solid var(--line);
  border-radius: 999px;
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .1em;
  padding: 3px 9px;
  cursor: pointer;
  white-space: nowrap;
  flex-shrink: 0;
}
.corkboard-status-pill:hover { background: var(--accent-soft); }
.corkboard-status-pill[data-current="draft"]    { background: #eceef1; color: #4b5560; }
.corkboard-status-pill[data-current="revising"] { background: #fbe4cb; color: #8a4d18; }
.corkboard-status-pill[data-current="revised"]  { background: #ece1f2; color: #5b3680; }
.corkboard-status-pill[data-current="final"]    { background: #d8ebd8; color: #2f6633; }

.corkboard-card-body {
  padding: 6px 14px 10px;
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.corkboard-synopsis {
  border: none;
  background: transparent;
  font: inherit;
  font-family: var(--font-serif, Georgia, serif);
  font-size: 13px;
  line-height: 1.5;
  color: var(--ink-1);
  resize: none;
  padding: 0;
  outline: none;
  min-height: 60px;
}
.corkboard-synopsis::placeholder { color: var(--ink-3); font-style: italic; }
.corkboard-synopsis:focus {
  background: #fffefa;
  outline: 1px solid var(--accent-soft);
  outline-offset: 4px;
  border-radius: 2px;
}

.corkboard-meta-row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 8px;
  min-width: 0;
}
.corkboard-mini-field {
  display: flex;
  flex-direction: column;
  gap: 2px;
  font-size: 10.5px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .08em;
  /* Grid items default to min-content; allow shrinking so the input
     doesn't push past the card edge. */
  min-width: 0;
}
.corkboard-mini-field input {
  font: inherit;
  font-size: 12.5px;
  text-transform: none;
  letter-spacing: 0;
  padding: 4px 6px;
  border: 1px solid var(--line-soft);
  border-radius: var(--radius-sm);
  color: var(--ink-1);
  background: #fff;
  outline: none;
  transition: border-color .12s ease;
  width: 100%;
  min-width: 0;
  box-sizing: border-box;
}
.corkboard-mini-field input:focus { border-color: var(--accent); }
.corkboard-mini-field input::placeholder { color: var(--ink-3); }

.corkboard-card-foot {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  padding: 8px 14px;
  border-top: 1px solid var(--line-soft);
  background: rgba(0,0,0,.015);
  font-size: 11.5px;
  color: var(--ink-3);
}
.corkboard-card-stat strong {
  color: var(--ink-1);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
}
.corkboard-card-open {
  background: transparent;
  color: var(--accent);
  border: none;
  font-family: var(--font-sans);
  font-size: 12px;
  font-weight: 500;
  cursor: pointer;
  padding: 2px 4px;
}
.corkboard-card-open:hover { text-decoration: underline; }

/* ============================================================
   Snapshot diff page
   ============================================================ */
.diff-body {
  background: var(--bg-page);
  min-height: 100vh;
}
.diff-shell {
  display: flex;
  flex-direction: column;
  min-height: 100vh;
}
.diff-topbar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 14px 28px;
  background: #1d1b18;
  color: #fff;
  gap: 16px;
}
.diff-topbar .topbar-logo {
  background: var(--accent);
  width: 32px;
  height: 32px;
  border-radius: 6px;
  display: flex;
  align-items: center;
  justify-content: center;
  text-decoration: none;
  color: #fff;
  font-weight: 700;
}
.diff-topbar-left { display: flex; align-items: center; gap: 14px; }
.diff-back {
  color: #d4cfc1;
  text-decoration: none;
  font-size: 13px;
  transition: color .12s ease;
}
.diff-back:hover { color: #fff; }
.diff-page-title {
  margin: 0;
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
  letter-spacing: .02em;
}
.diff-topbar-right { min-width: 60px; }

.diff-controls {
  display: flex;
  align-items: center;
  gap: 14px;
  padding: 18px 32px;
  background: #fff;
  border-bottom: 1px solid var(--line);
  flex-wrap: wrap;
}
.diff-control {
  display: flex;
  align-items: center;
  gap: 8px;
  font-family: var(--font-sans);
  font-size: 11px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .12em;
}
.diff-control select {
  font: inherit;
  font-size: 13px;
  text-transform: none;
  letter-spacing: 0;
  color: var(--ink-1);
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: #fff;
  min-width: 220px;
}
.diff-swap-btn {
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: 50%;
  width: 32px;
  height: 32px;
  font-size: 14px;
  color: var(--ink-2);
  cursor: pointer;
}
.diff-swap-btn:hover { background: var(--accent-soft); color: var(--ink-1); }
.diff-summary {
  margin-left: auto;
  font-size: 13px;
  color: var(--ink-2);
  font-variant-numeric: tabular-nums;
}

.diff-body-main {
  padding: 24px 32px 60px;
  max-width: 1080px;
  margin: 0 auto;
  width: 100%;
  box-sizing: border-box;
}
.diff-loading {
  text-align: center;
  padding: 80px 0;
  color: var(--ink-3);
  font-style: italic;
}
.diff-empty {
  text-align: center;
  padding: 60px 0;
  color: var(--ink-3);
}
.diff-empty-chapter {
  padding: 14px 18px;
  color: var(--ink-3);
  font-style: italic;
  font-size: 13px;
}

.diff-chapter {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  margin-bottom: 16px;
  box-shadow: var(--shadow-paper);
  overflow: hidden;
}
.diff-chapter-summary {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 14px 20px;
  cursor: pointer;
  background: var(--bg-paper);
  font-family: var(--font-sans);
  list-style: none;
  user-select: none;
}
.diff-chapter-summary::-webkit-details-marker { display: none; }
.diff-chapter-summary::before {
  content: '▸';
  color: var(--ink-3);
  font-size: 12px;
  transition: transform .12s ease;
}
.diff-chapter[open] > .diff-chapter-summary::before { transform: rotate(90deg); }
.diff-chapter-badge {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--ink-3);
  flex-shrink: 0;
}
.diff-chapter.is-added    .diff-chapter-badge { background: #2f7c34; }
.diff-chapter.is-removed  .diff-chapter-badge { background: #b53b3b; }
.diff-chapter.is-changed  .diff-chapter-badge { background: var(--accent); }
.diff-chapter.is-unchanged .diff-chapter-badge { background: #cfcabd; }
.diff-chapter-title {
  flex: 1;
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
  color: var(--ink-1);
}
.diff-title-renamed {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 500;
  color: var(--ink-3);
  font-style: italic;
  margin-left: 8px;
}
.diff-chapter-sub {
  font-family: var(--font-sans);
  font-size: 12px;
  color: var(--ink-3);
  font-variant-numeric: tabular-nums;
}
.diff-chapter-body {
  padding: 16px 20px;
  font-family: var(--font-serif, Georgia, serif);
  font-size: 14.5px;
  line-height: 1.6;
  color: var(--ink-1);
}

.diff-row {
  position: relative;
  padding: 6px 12px 6px 32px;
  margin: 2px 0;
  border-radius: 3px;
  text-indent: 0;
}
.diff-row-text { white-space: pre-wrap; word-wrap: break-word; }
.diff-row-marker {
  position: absolute;
  left: 8px;
  top: 6px;
  font-family: var(--font-mono, ui-monospace, Menlo, Consolas, monospace);
  font-size: 14px;
  color: var(--ink-3);
  font-weight: 600;
}
.diff-row-eq {
  color: var(--ink-2);
}
.diff-row-add {
  background: rgba(46, 124, 52, 0.08);
  border-left: 3px solid #2f7c34;
}
.diff-row-add .diff-row-marker { color: #2f7c34; }
.diff-row-del {
  background: rgba(181, 59, 59, 0.08);
  border-left: 3px solid #b53b3b;
}
.diff-row-del .diff-row-marker { color: #b53b3b; }
.diff-row-del .diff-row-text {
  text-decoration: line-through;
  text-decoration-color: rgba(181, 59, 59, .5);
  color: #6f4444;
}
.diff-row-mod {
  border-left: 3px solid var(--accent);
  background: rgba(139, 105, 20, 0.05);
  padding: 4px 0;
}
.diff-row-mod-old,
.diff-row-mod-new {
  position: relative;
  padding: 4px 12px 4px 32px;
}
.diff-row-mod-old { color: #6f4444; }
.diff-row-mod-old .diff-row-marker { color: #b53b3b; }
.diff-row-mod-new .diff-row-marker { color: #2f7c34; }
.diff-row-mod-old del {
  background: rgba(181, 59, 59, 0.18);
  text-decoration: line-through;
  text-decoration-color: rgba(181, 59, 59, .6);
  border-radius: 2px;
  padding: 0 1px;
}
.diff-row-mod-new ins {
  background: rgba(46, 124, 52, 0.18);
  text-decoration: none;
  border-radius: 2px;
  padding: 0 1px;
}

.diff-collapsed-toggle {
  display: block;
  width: 100%;
  text-align: center;
  background: var(--bg-paper);
  border: 1px dashed var(--line);
  border-radius: var(--radius-sm);
  padding: 8px;
  margin: 8px 0;
  color: var(--ink-3);
  font-family: var(--font-sans);
  font-size: 12px;
  cursor: pointer;
}
.diff-collapsed-toggle:hover { background: var(--accent-soft); color: var(--ink-2); }
.diff-collapsed-body[hidden] { display: none; }

.preview-toolbar {
  background: #fff;
  border-bottom: 1px solid var(--line);
  padding: 10px 24px;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  font-size: 12.5px;
  color: var(--ink-3);
}
.preview-meta strong { color: var(--ink-1); font-weight: 600; }

/* Toolbar pager — N / total + Prev / Next buttons */
.preview-pager {
  display: flex;
  align-items: center;
  gap: 10px;
  font-size: 12.5px;
  color: var(--ink-3);
}
.preview-pager-btn {
  background: #fff;
  border: 1px solid var(--line);
  color: var(--ink-2);
  padding: 5px 12px;
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 12.5px;
  cursor: pointer;
  font-variant-numeric: tabular-nums;
}
.preview-pager-btn:hover:not(:disabled) {
  background: var(--bg-rail);
  border-color: var(--line-strong);
  color: var(--ink-1);
}
.preview-pager-btn:disabled {
  opacity: .4;
  cursor: not-allowed;
}
/* "Full book preview" is an <a> reusing the pager-button look — kill the
   link underline and let the lock badge sit inline. Solid ink so the
   print-proof entry point reads as the toolbar's one primary action.
   Compound selector on purpose: the generic `:hover:not(:disabled)` rule
   above is (0,3,0), so a bare `.preview-fullbook:hover` would lose to it
   and flash back to the rail background. */
.preview-pager-btn.preview-fullbook {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin-left: 14px;
  text-decoration: none;
  background: var(--ink-1);
  border-color: var(--ink-1);
  color: #fff;
}
.preview-pager-btn.preview-fullbook:hover {
  background: var(--ink-2);
  border-color: var(--ink-2);
  color: #fff;
}
.preview-pager-label strong { color: var(--ink-1); font-weight: 600; }
.preview-pager-title {
  color: var(--ink-3);
  font-style: italic;
  max-width: 220px;
  display: inline-block;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  vertical-align: middle;
}

.preview-stage {
  flex: 1;
  overflow-y: auto;
  padding: 32px 24px 80px;
  display: flex;
  justify-content: center;
  position: relative; /* anchor for the side arrows */

  /* Theme variables, set by preview.js */
  --pv-body-font: 'Lora', serif;
  --pv-heading-font: 'Playfair Display', serif;
  --pv-font-size: 12pt;
  --pv-line-height: 1.45;
  --pv-indent: 0.3in;
  --pv-text-color: #1a1a1a;
  --pv-accent-color: #8b6914;
  --pv-bg-color: #fdfbf6;
}
.preview-pages {
  width: 100%;
  max-width: 720px;
  display: block;
}

/* Show only the active chapter — paginated, not infinite-scrolling */
.preview-page { display: none; }
.preview-page.is-active { display: flex; flex-direction: column; }

/* Big side arrows for click-to-flip page turns */
.preview-side-arrow {
  position: sticky;
  top: 50%;
  z-index: 5;
  align-self: center;
  width: 44px;
  height: 44px;
  border-radius: 50%;
  border: 1px solid var(--line-strong);
  background: rgba(255,255,255,.92);
  color: var(--ink-2);
  font-size: 22px;
  line-height: 1;
  font-family: inherit;
  cursor: pointer;
  box-shadow: 0 2px 8px rgba(0,0,0,.08);
  flex-shrink: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  transition: transform .12s ease, background .12s ease;
}
.preview-side-arrow:hover:not(:disabled) {
  background: #fff;
  transform: scale(1.06);
  color: var(--ink-1);
}
.preview-side-arrow:disabled {
  opacity: .25;
  cursor: not-allowed;
}
.preview-side-prev { margin-right: 8px; }
.preview-side-next { margin-left: 8px; }
.preview-loading {
  text-align: center;
  padding: 60px 0;
  color: var(--ink-3);
  font-style: italic;
}

.preview-page {
  background: var(--pv-bg-color);
  color: var(--pv-text-color);
  font-family: var(--pv-body-font);
  font-size: var(--pv-font-size);
  line-height: var(--pv-line-height);
  border: 1px solid var(--line);
  box-shadow: var(--shadow-paper);
  padding: 0.875in 0.875in 1in;
  border-radius: 1px;
  min-height: var(--pv-page-min-height, 1000px);
}
/* Active page uses column flex (set on .is-active above) so the body/auto-* fills the page. */
.preview-page.is-active > * { flex: 0 0 auto; }
.preview-page.is-active > .chapter-body,
.preview-page.is-active > .auto-toc,
.preview-page.is-active > .auto-titlepage { flex: 1 1 auto; }

/* Chapter body paragraph styling */
.preview-page .chapter-body p {
  margin: 0 0 .35em;
  text-indent: var(--pv-indent);
  text-align: var(--pv-text-align, justify);
  hyphens: var(--pv-hyphens, auto);
  -webkit-hyphens: var(--pv-hyphens, auto);
}
.preview-page .chapter-body p:first-child { text-indent: 0; }
/* Per-paragraph alignment from the editor (Quill writes these classes; its
   own CSS is scoped to .ql-editor, so the preview needs its own copy). */
.preview-page .chapter-body .ql-align-center  { text-align: center !important; text-indent: 0 !important; }
.preview-page .chapter-body .ql-align-right   { text-align: right !important; text-indent: 0 !important; }
.preview-page .chapter-body .ql-align-justify { text-align: justify !important; }
.preview-page.is-indent-first .chapter-body p:first-child { text-indent: var(--pv-indent); }
/* Theme-level default: indent the first paragraph across every chapter
   (set via the stage's data-indent-first). The per-chapter override above
   still wins on its own; both resolve to the same indent. */
.preview-stage[data-indent-first="1"] .preview-page .chapter-body p:first-child { text-indent: var(--pv-indent); }
.device-page p,
.device-chapter-body {
  text-align: var(--pv-text-align, justify);
  hyphens: var(--pv-hyphens, auto);
  -webkit-hyphens: var(--pv-hyphens, auto);
}
/* Auto-rendered front matter (title page, copyrights, etc.) is centered
   by design; the broad `.device-page p` rule above otherwise wins for
   the per-line <p> children inside it and pulls them off-center, even
   though the export path renders them centered. Explicit override here
   keeps the device-frame preview matching the export. */
.device-page .auto-titlepage,
.device-page .auto-titlepage p,
.device-page .auto-titlepage h1,
.device-page .auto-copyrights,
.device-page .auto-copyrights p {
  text-align: center;
  hyphens: manual;
  -webkit-hyphens: manual;
}
.preview-page .chapter-body h1,
.preview-page .chapter-body h2,
.preview-page .chapter-body h3,
.preview-page .chapter-body h4,
.preview-page .chapter-body h5,
.preview-page .chapter-body h6 {
  font-family: var(--pv-heading-font);
  color: var(--pv-text-color);
  margin: 1.4em 0 .5em;
  text-indent: 0;
}
/* H2-H6 size + font overrides driven by theme settings.
   --pv-hN-size is a multiplier of body font-size; --pv-hN-font is an
   optional font-family override. Both fall back to the heading font
   and a typographic default scale when not set. */
.preview-page .chapter-body h2 { font-size: calc(var(--pv-font-size, 12pt) * var(--pv-h2-size, 1.5));  font-family: var(--pv-h2-font, var(--pv-heading-font)); }
.preview-page .chapter-body h3 { font-size: calc(var(--pv-font-size, 12pt) * var(--pv-h3-size, 1.25)); font-family: var(--pv-h3-font, var(--pv-heading-font)); }
.preview-page .chapter-body h4 { font-size: calc(var(--pv-font-size, 12pt) * var(--pv-h4-size, 1.10)); font-family: var(--pv-h4-font, var(--pv-heading-font)); }
.preview-page .chapter-body h5 { font-size: calc(var(--pv-font-size, 12pt) * var(--pv-h5-size, 1.00)); font-family: var(--pv-h5-font, var(--pv-heading-font)); }
.preview-page .chapter-body h6 { font-size: calc(var(--pv-font-size, 12pt) * var(--pv-h6-size, 0.90)); font-family: var(--pv-h6-font, var(--pv-heading-font)); }
.preview-page .chapter-body blockquote {
  border-left: 2px solid var(--pv-accent-color);
  padding: 4px 16px;
  margin: 1em 0;
  font-style: italic;
  color: var(--ink-2);
  text-indent: 0;
}

/* ----- Drop cap ----- */
.preview-stage[data-drop-cap="1"] .preview-page[data-kind="chapter"] .chapter-body p:first-of-type::first-letter {
  font-family: var(--pv-drop-cap-font, var(--pv-body-font));
  font-size: 3.4em;
  line-height: .85;
  float: left;
  padding: .05em .08em 0 0;
  color: var(--pv-accent-color);
  font-weight: 600;
}
/* Drop cap on the paragraph after each scene break, when the
   "every-break" first-sentence mode is selected. */
.preview-stage[data-drop-cap="1"][data-first-sentence-when="every-break"] .preview-page[data-kind="chapter"] .chapter-body .scene-break + p::first-letter {
  font-family: var(--pv-drop-cap-font, var(--pv-body-font));
  font-size: 3.4em;
  line-height: .85;
  float: left;
  padding: .05em .08em 0 0;
  color: var(--pv-accent-color);
  font-weight: 600;
}

/* Drop cap inside the formatting-tab device-frame preview. Mirrors the
   eyeball-preview rules above; uses the data-drop-cap attribute set by
   format.js when the "Show a decorative first letter" toggle is on. */
.device-page[data-drop-cap="1"] .device-chapter-body:first-of-type::first-letter {
  font-family: var(--pv-drop-cap-font, var(--pv-body-font));
  font-size: 3.2em;
  line-height: .85;
  float: left;
  padding: .05em .08em 0 0;
  color: var(--pv-accent-color);
  font-weight: 600;
}
.device-page[data-drop-cap="1"][data-first-sentence-when="every-break"] .device-chapter-body.after-scene-break::first-letter {
  font-family: var(--pv-drop-cap-font, var(--pv-body-font));
  font-size: 3.2em;
  line-height: .85;
  float: left;
  padding: .05em .08em 0 0;
  color: var(--pv-accent-color);
  font-weight: 600;
}
/* Lead-in span (rendered server-side / by preview.js when
   drop_cap_lead_small_caps is on). Small-caps + slight letter-spacing
   gives the classic novel-opener look. */
.preview-page .chapter-body .lead-in,
.device-page .lead-in {
  font-variant: small-caps;
  font-variant-caps: all-small-caps;
  letter-spacing: 0.04em;
}

/* Chapter heading granular overrides — apply on top of the chapter_style preset.
   These read CSS vars set by preview.js / format.js; when not set they
   fall back to the preset's defaults. */
.preview-page .chapter-title {
  font-family: var(--pv-chapter-title-font, var(--pv-heading-font));
  text-align:  var(--pv-chapter-title-align, center);
  font-size:   calc(var(--pv-font-size, 12pt) * var(--pv-chapter-title-size, 1.9));
}
.preview-stage[data-chapter-title-style="italic"]     .preview-page .chapter-title { font-style: italic; font-weight: 500; }
.preview-stage[data-chapter-title-style="bold"]       .preview-page .chapter-title { font-style: normal; font-weight: 700; }
.preview-stage[data-chapter-title-style="small-caps"] .preview-page .chapter-title { font-variant: small-caps; font-variant-caps: all-small-caps; }
.preview-stage[data-chapter-title-style="regular"]    .preview-page .chapter-title { font-style: normal; font-weight: 600; }
/* Width controls the underline / banner width on relevant presets */
.preview-page .chapter-style-classic .chapter-title { width: var(--pv-chapter-title-width, 100%); }
.preview-page .chapter-style-banner  .chapter-title { width: var(--pv-chapter-title-width, 100%); }

.preview-page .chapter-subtitle {
  font-family: var(--pv-chapter-subtitle-font, var(--pv-heading-font));
  text-align:  var(--pv-chapter-subtitle-align, center);
  font-size:   calc(var(--pv-font-size, 12pt) * var(--pv-chapter-subtitle-size, 1.1));
  width:       var(--pv-chapter-subtitle-width, 100%);
}
.preview-stage[data-chapter-subtitle-style="italic"]     .preview-page .chapter-subtitle { font-style: italic; font-weight: 400; }
.preview-stage[data-chapter-subtitle-style="bold"]       .preview-page .chapter-subtitle { font-style: normal; font-weight: 700; }
.preview-stage[data-chapter-subtitle-style="small-caps"] .preview-page .chapter-subtitle { font-variant: small-caps; font-variant-caps: all-small-caps; font-style: normal; }
.preview-stage[data-chapter-subtitle-style="regular"]    .preview-page .chapter-subtitle { font-style: normal; font-weight: 400; }

/* Hide the auto chapter-number prefix when chapter_number_show is off */
.preview-stage[data-chapter-number-show="0"] .preview-page .chapter-num-label { display: none; }

/* ----- Device-frame preview: same hooks, scoped to .device-page -----
   The eyeball preview (`.preview-stage` / `.preview-page`) and the
   formatting-tab device frame (`.device-page`) ship the same CSS vars
   from format.js, so duplicate the consume rules here. Without this
   the chapter-title font/align/size/style/width and chapter-subtitle
   variants set in the inspector silently no-op in the device frame. */
/* Font / align / width come from the user's settings; font-size is
   handled by the per-chapter-style rules above so the chosen
   chapter_style preset still influences the device-frame scale. */
.device-page .chapter-title {
  font-family: var(--pv-chapter-title-font, var(--pv-heading-font));
  text-align:  var(--pv-chapter-title-align, center);
  width:       var(--pv-chapter-title-width, 100%);
}
.device-page[data-chapter-title-style="italic"]     .chapter-title { font-style: italic; font-weight: 500; }
.device-page[data-chapter-title-style="bold"]       .chapter-title { font-style: normal; font-weight: 700; }
.device-page[data-chapter-title-style="small-caps"] .chapter-title { font-variant: small-caps; font-variant-caps: all-small-caps; }
.device-page[data-chapter-title-style="regular"]    .chapter-title { font-style: normal; font-weight: 600; }

.device-page .chapter-subtitle {
  font-family: var(--pv-chapter-subtitle-font, var(--pv-heading-font));
  text-align:  var(--pv-chapter-subtitle-align, center);
  width:       var(--pv-chapter-subtitle-width, 100%);
}
.device-page[data-chapter-subtitle-style="italic"]     .chapter-subtitle { font-style: italic; font-weight: 400; }
.device-page[data-chapter-subtitle-style="bold"]       .chapter-subtitle { font-style: normal; font-weight: 700; }
.device-page[data-chapter-subtitle-style="small-caps"] .chapter-subtitle { font-variant: small-caps; font-variant-caps: all-small-caps; font-style: normal; }
.device-page[data-chapter-subtitle-style="regular"]    .chapter-subtitle { font-style: normal; font-weight: 400; }

/* Hide the auto chapter-number prefix when chapter_number_show is off */
.device-page[data-chapter-number-show="0"] .chapter-num-label { display: none; }

/* H2-H6 in device preview. Same multiplier-of-body pattern; the body
   size is `--pv-body-pt` (in pt units, multiplied by 1.05 for px). */
.device-chapter-body h2,
.device-page .device-chapter-heading[data-tag="h2"],
.device-page h2 { font-size: calc(var(--pv-body-pt, 11) * 1.05px * var(--pv-h2-size, 1.5)); font-family: var(--pv-h2-font, var(--pv-heading-font)); }
.device-page h3 { font-size: calc(var(--pv-body-pt, 11) * 1.05px * var(--pv-h3-size, 1.25)); font-family: var(--pv-h3-font, var(--pv-heading-font)); }
.device-page h4 { font-size: calc(var(--pv-body-pt, 11) * 1.05px * var(--pv-h4-size, 1.10)); font-family: var(--pv-h4-font, var(--pv-heading-font)); }
.device-page h5 { font-size: calc(var(--pv-body-pt, 11) * 1.05px * var(--pv-h5-size, 1.00)); font-family: var(--pv-h5-font, var(--pv-heading-font)); }
.device-page h6 { font-size: calc(var(--pv-body-pt, 11) * 1.05px * var(--pv-h6-size, 0.90)); font-family: var(--pv-h6-font, var(--pv-heading-font)); }

/* ----- Chapter heading styles ----- */
.chapter-head {
  margin-bottom: 1.6em;
  text-indent: 0;
}
.chapter-num-label {
  display: block;
  font-family: var(--pv-heading-font);
  text-transform: uppercase;
  letter-spacing: .25em;
  font-size: .8em;
  color: var(--pv-accent-color);
  margin-bottom: .8em;
}
.chapter-title {
  font-family: var(--pv-heading-font);
  font-weight: 600;
  font-size: 1.9em;
  margin: 0;
  letter-spacing: .01em;
  color: var(--pv-text-color);
}
.chapter-subtitle {
  font-family: var(--pv-heading-font);
  font-style: italic;
  font-size: 1.1em;
  margin: .4em 0 0;
  color: var(--pv-accent-color);
  text-indent: 0;
}

/* Classic — centered, italic large serif title with a thin underline */
.chapter-head-classic { text-align: center; padding-top: 1em; }
.chapter-head-classic .chapter-title {
  font-size: 2em;
  font-style: italic;
  font-weight: 500;
  letter-spacing: .04em;
  display: inline-block;
  padding-bottom: .35em;
  border-bottom: 1px solid var(--pv-accent-color);
}

/* Modern — left-aligned, sans-serif feel, small accent block before */
.chapter-head-modern { text-align: left; padding-top: .4em; }
.chapter-head-modern::before {
  content: '';
  display: block;
  width: 38px;
  height: 3px;
  background: var(--pv-accent-color);
  margin-bottom: .6em;
}
.chapter-head-modern .chapter-title { font-size: 1.6em; font-weight: 600; letter-spacing: -.005em; }

/* Ornate — flourishes above and below the italic title */
.chapter-head-ornate { text-align: center; padding-top: 1.5em; }
.chapter-head-ornate::before {
  content: '❦';
  display: block;
  font-size: 1.4em;
  color: var(--pv-accent-color);
  margin-bottom: 1em;
}
.chapter-head-ornate .chapter-title {
  font-style: italic;
  font-size: 2em;
  font-weight: 500;
}
.chapter-head-ornate::after {
  content: '';
  display: block;
  width: 60px;
  height: 1px;
  background: var(--pv-accent-color);
  margin: .9em auto 0;
}

/* Banner — title rendered as a dark inline-block block (the namesake) */
.chapter-head-banner { text-align: center; padding-top: .5em; }
.chapter-head-banner .chapter-title {
  background: var(--pv-text-color);
  color: var(--pv-bg-color);
  display: inline-block;
  padding: 12px 32px;
  font-size: 1.4em;
  font-weight: 700;
  letter-spacing: .15em;
  text-transform: uppercase;
}

/* Minimal — title only, small + left-aligned */
.chapter-head-minimal { text-align: left; }
.chapter-head-minimal .chapter-title { font-size: 1.4em; font-weight: 500; }

/* Uppercase — centered, all-caps, letter-spaced, no rule */
.chapter-head-caps { text-align: center; padding-top: 1em; }
.chapter-head-caps .chapter-title {
  text-transform: uppercase;
  letter-spacing: .16em;
  font-weight: 600;
  font-size: 1.45em;
}

/* Framed — centered italic title bracketed by hairline rules above + below */
.chapter-head-framed { text-align: center; padding-top: 1em; }
.chapter-head-framed .chapter-title {
  display: inline-block;
  font-style: italic;
  font-weight: 500;
  font-size: 1.7em;
  padding: .3em 0;
  border-top: 1px solid var(--pv-accent-color);
  border-bottom: 1px solid var(--pv-accent-color);
}

/* Editorial — left-aligned title over a full-width hairline rule */
.chapter-head-editorial { text-align: left; padding-top: .4em; border-bottom: 1px solid var(--pv-accent-color); padding-bottom: .4em; }
.chapter-head-editorial .chapter-title { font-size: 1.7em; font-weight: 600; }

/* Divider rule under the heading — suppressed when chapter_heading_rule
   is off. Two presets draw one: Ornate (the short ::after line beneath
   the title/subtitle) and Classic (the underline on the title). Scoped to
   each preview surface's data attribute so the toggle is a live preview. */
.preview-stage[data-chapter-heading-rule="0"] .chapter-head-ornate::after,
.device-page[data-chapter-heading-rule="0"] .chapter-head-ornate::after { display: none; }
.preview-stage[data-chapter-heading-rule="0"] .chapter-head-classic .chapter-title,
.device-page[data-chapter-heading-rule="0"] .chapter-head-classic .chapter-title { border-bottom: none; padding-bottom: 0; }

/* Part / section */
.chapter-head-part { text-align: center; padding: 3em 0 2em; }
.chapter-head-part .part-label {
  display: block;
  font-family: var(--pv-heading-font);
  text-transform: uppercase;
  letter-spacing: .35em;
  font-size: .9em;
  color: var(--pv-accent-color);
  margin-bottom: .6em;
}
.chapter-head-part .chapter-title { font-size: 2.6em; font-weight: 600; }

/* ----- Scene breaks ----- */
.scene-break {
  text-align: center;
  margin: 1.4em 0;
  color: var(--pv-accent-color);
  font-family: var(--pv-heading-font);
  text-indent: 0;
}
.scene-break-asterisks::before { content: '*  *  *'; letter-spacing: .25em; }
.scene-break-thin-line {
  display: block;
  border: none;
  height: 1px;
  background: var(--pv-text-color);
  width: 80px;
  margin: 1.4em auto;
  opacity: .35;
}
.scene-break-flourish::before { content: '❦'; font-size: 1.4em; }
.scene-break-rune::before { content: '✦'; font-size: 1.3em; }
.scene-break-dingbat::before { content: '❧'; font-size: 1.4em; }

/* Empty preview state */
.preview-empty {
  margin: 0 auto;
}

/* ---------- Auto title page (preview, format, EPUB share class names) ---------- */
.auto-titlepage {
  text-align: center;
  padding: 2.4em 1em 1.4em;
}
.auto-titlepage-title {
  font-family: var(--pv-heading-font, var(--font-display));
  font-size: 2em;
  font-weight: 600;
  margin: 0 0 0.4em;
  line-height: 1.1;
  letter-spacing: .01em;
}
.auto-titlepage-subtitle {
  font-style: italic;
  color: var(--pv-accent-color, var(--accent));
  margin: 0 0 1.4em;
  font-size: 1.05em;
}
.auto-titlepage-author {
  font-family: var(--pv-heading-font, var(--font-display));
  font-size: 1.05em;
  font-weight: 500;
  letter-spacing: .12em;
  margin: 0 0 2.2em;
}
.auto-titlepage-publisher-logo {
  margin: 1.4em auto 0.6em;
  max-width: 60%;
}
.auto-titlepage-publisher-logo img {
  max-width: 100%;
  max-height: 130px;
  height: auto;
  display: block;
  margin: 0 auto;
}
.auto-titlepage-publisher-name {
  font-family: var(--pv-heading-font, var(--font-display));
  font-size: 0.78em;
  letter-spacing: .14em;
  text-transform: uppercase;
  margin: 0;
  color: var(--pv-text-color, var(--ink-1));
}

/* ---------- Auto Copyrights ---------- */
.auto-copyrights {
  padding: 1em;
  max-width: 36em;
  margin: 0 auto;
}
.auto-copyrights .auto-copyrights-line {
  font-size: 0.92em;
  line-height: 1.5;
  margin: 0 0 0.85em;
  text-indent: 0;
  text-align: left;
}
.auto-copyrights .auto-copyrights-line a {
  color: inherit;
  text-decoration: underline;
}

/* ---------- Auto TOC ---------- */
.auto-toc {
  list-style: none;
  margin: 1em 0;
  padding: 0 0.5em;
}
.auto-toc-item {
  padding: 0.4em 0;
  font-size: 0.95em;
  text-indent: 0;
  cursor: pointer;
}
.auto-toc-item:hover .auto-toc-text { color: var(--pv-accent-color, var(--accent)); }
.auto-toc-num {
  display: inline-block;
  min-width: 1.6em;
  color: var(--pv-accent-color, var(--accent));
  font-family: var(--pv-heading-font, var(--font-display));
}
.auto-toc-front { font-style: italic; }
.auto-toc-back  { font-style: italic; }
.auto-toc-part  { font-weight: 700; text-transform: uppercase; letter-spacing: .08em; }

/* TOC style: Classic — dotted leader between title and (no page) */
.auto-toc-classic .auto-toc-item {
  border-bottom: 1px dotted var(--pv-accent-color, var(--accent));
}

/* TOC style: Plain — no decorations, generous spacing */
.auto-toc-plain .auto-toc-item {
  padding: 0.55em 0;
  border: 0;
}
.auto-toc-plain .auto-toc-num { color: var(--pv-text-color); opacity: .55; }

/* TOC style: Lined — solid hairline rule under each row */
.auto-toc-lined .auto-toc-item {
  border-bottom: 1px solid color-mix(in srgb, var(--pv-text-color) 18%, transparent);
}
.auto-toc-lined .auto-toc-part { border-bottom-width: 2px; }

/* TOC style: Decorative — ornament between rows, centered titles */
.auto-toc-decorative {
  text-align: center;
  padding: 0;
}
.auto-toc-decorative .auto-toc-item {
  padding: 0.55em 0 0.85em;
  border: 0;
  position: relative;
}
.auto-toc-decorative .auto-toc-item + .auto-toc-item::before {
  content: "❦";
  position: absolute;
  top: -0.15em;
  left: 50%;
  transform: translateX(-50%);
  color: var(--pv-accent-color, var(--accent));
  font-size: .8em;
  opacity: .7;
}
.auto-toc-decorative .auto-toc-num {
  display: block;
  min-width: 0;
  font-size: .75em;
  letter-spacing: .12em;
  text-transform: uppercase;
  margin-bottom: 0.15em;
}
.auto-toc-decorative .auto-toc-text { font-style: italic; }

/* TOC style: Centered — entries centered, no rules */
.auto-toc-centered { text-align: center; }
.auto-toc-centered .auto-toc-item { border: 0; padding: 0.5em 0; justify-content: center; }
.auto-toc-centered .auto-toc-num { margin-right: .4em; }

/* TOC style: Modern — clean, uppercase spaced numbers, airy, no rules */
.auto-toc-modern .auto-toc-item { border: 0; padding: 0.6em 0; }
.auto-toc-modern .auto-toc-num {
  text-transform: uppercase;
  letter-spacing: .1em;
  font-size: .8em;
  opacity: .6;
}
.auto-toc-modern .auto-toc-text { font-weight: 500; }

/* TOC style: Numbered — accent-colored, prominent chapter numbers */
.auto-toc-numbered .auto-toc-item { border: 0; padding: 0.45em 0; }
.auto-toc-numbered .auto-toc-num {
  color: var(--pv-accent-color, var(--accent));
  font-weight: 700;
  min-width: 1.8em;
}

/* Mini TOC heading previews (inspector radio cards) */
.toc-preview-classic   { font-size: 11px; border-bottom: 1px dotted var(--accent); padding: 2px 6px; min-width: 60px; text-align: left; }
.toc-preview-plain     { font-size: 11px; padding: 2px 6px; min-width: 60px; text-align: left; }
.toc-preview-lined     { font-size: 11px; border-bottom: 1px solid var(--ink-3); padding: 2px 6px; min-width: 60px; text-align: left; }
.toc-preview-decorative { font-size: 11px; font-style: italic; padding: 2px 6px; min-width: 60px; text-align: center; }
.toc-preview-decorative::before { content: "❦ "; color: var(--accent); font-style: normal; font-size: .8em; }
.toc-preview-centered  { font-size: 11px; padding: 2px 6px; min-width: 60px; text-align: center; }
.toc-preview-modern    { font-size: 11px; padding: 2px 6px; min-width: 60px; text-align: left; text-transform: uppercase; letter-spacing: .08em; }
.toc-preview-numbered  { font-size: 11px; padding: 2px 6px; min-width: 60px; text-align: left; font-weight: 700; color: var(--accent); }

/* Inside the device-frame preview the auto blocks need smaller spacing. */
.device-page .auto-titlepage { padding: 1.4em 0.4em 0.6em; }
.device-page .auto-titlepage-title { font-size: 1.4em; }
.device-page .auto-titlepage-subtitle { font-size: 0.85em; margin-bottom: 1em; }
.device-page .auto-titlepage-author { font-size: 0.85em; margin-bottom: 1.4em; }
.device-page .auto-titlepage-publisher-logo { max-width: 90px; margin: 0.8em auto 0.4em; }
.device-page .auto-titlepage-publisher-logo img { max-height: 70px; }
.device-page .auto-titlepage-publisher-name { font-size: 0.6em; }
.device-page .auto-toc { padding: 0; }
.device-page .auto-toc-item { font-size: 0.78em; padding: 3px 0; }

/* ============================================================
   PHASE 3 — Export view
   ============================================================ */
.export-view {
  background: var(--bg-page);
  overflow: auto;
}
.export-view[hidden] { display: none !important; }
.export-shell {
  flex: 1;
  display: flex;
  flex-direction: column;
  width: 100%;
}
.export-hero {
  padding: 32px 48px 18px;
  border-bottom: 1px solid var(--line);
  background: #fff;
}
.export-hero-title {
  font-family: var(--font-display);
  font-size: 26px;
  font-weight: 600;
  margin: 0 0 4px;
  letter-spacing: .01em;
}
.export-hero-sub {
  margin: 0;
  color: var(--ink-3);
  font-size: 14px;
  max-width: 720px;
}
.export-grid {
  display: grid;
  grid-template-columns: 280px 1fr;
  gap: 32px;
  padding: 32px 48px 64px;
  align-items: start;
  max-width: 1200px;
  width: 100%;
  margin: 0 auto;
}

/* ---- Cover + summary ---- */
.export-summary {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 22px 22px 24px;
}
.export-cover {
  position: relative;
  border-radius: 3px;
  overflow: hidden;
  margin-bottom: 14px;
  /* No fixed ratio — sizes to image's intrinsic aspect. */
}
.export-cover:has(img) { background: var(--ink-1); box-shadow: var(--shadow-paper); }
.export-cover img { width: 100%; height: auto; display: block; }
.export-cover.is-uploading::after {
  content: 'Uploading…';
  position: absolute; inset: 0;
  background: rgba(0,0,0,.55); color: #fff;
  display: flex; align-items: center; justify-content: center;
  font-size: 13px; letter-spacing: .04em;
}
.cover-fallback {
  /* When no cover is uploaded, render a 2:3 placeholder. */
  aspect-ratio: 2 / 3;
  background: linear-gradient(155deg, #2c2820 0%, #1a1715 100%);
  border-radius: 3px;
  box-shadow: var(--shadow-paper);
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
  text-align: center;
  padding: 24px 18px;
  border-left: 4px solid var(--accent);
}
.cover-fallback .cover-title {
  font-family: var(--font-display);
  font-size: 17px;
  line-height: 1.25;
  color: #f1ead2;
  font-weight: 500;
}
.cover-fallback .cover-author {
  font-family: var(--font-serif);
  font-style: italic;
  font-size: 11px;
  color: rgba(241,234,210,.6);
  margin-top: 12px;
  letter-spacing: .04em;
}
.export-cover-actions {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 20px;
  flex-wrap: wrap;
}
.export-cover-actions label.btn { cursor: pointer; }

.export-book-title {
  font-family: var(--font-display);
  font-size: 18px;
  font-weight: 600;
  margin: 0 0 2px;
  color: var(--ink-1);
  line-height: 1.3;
}
.export-book-author {
  font-family: var(--font-serif);
  font-style: italic;
  color: var(--ink-3);
  margin: 0 0 16px;
  font-size: 13px;
}
.export-stats {
  list-style: none;
  margin: 0;
  padding: 14px 0 0;
  border-top: 1px solid var(--line-soft);
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.export-stats li {
  font-size: 13px;
  color: var(--ink-3);
}
.export-stats strong { color: var(--ink-1); font-weight: 600; }

/* Right column on the export view: action cards on top, advisory
   preflight beneath. Stacked vertically so each takes the full
   width of the 1fr column. */
.export-main {
  display: flex;
  flex-direction: column;
  gap: 22px;
  min-width: 0;
}

/* ---- Pre-flight checks card ---- */
.export-preflight {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 18px 22px 14px;
}
.export-preflight-head {
  display: flex;
  align-items: baseline;
  gap: 12px;
  margin-bottom: 8px;
}
.export-preflight-title {
  margin: 0;
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 500;
  color: var(--ink-1);
}
.export-preflight-summary {
  font-size: 12px;
  color: var(--ink-3);
}
.export-preflight-summary[data-tone="pass"] { color: #2f6633; }
.export-preflight-summary[data-tone="warn"] { color: #8a4d18; }
.export-preflight-summary[data-tone="fail"] { color: var(--danger, #b04646); font-weight: 600; }
.export-preflight-list {
  list-style: none;
  margin: 6px 0 0;
  padding: 0;
}
.export-preflight-item {
  display: grid;
  grid-template-columns: 14px auto 1fr;
  align-items: baseline;
  gap: 10px;
  padding: 5px 0;
  font-size: 13px;
  color: var(--ink-2);
  line-height: 1.45;
}
.export-preflight-dot {
  width: 9px;
  height: 9px;
  border-radius: 50%;
  background: var(--ink-4);
  display: inline-block;
}
.export-preflight-item[data-level="pass"] .export-preflight-dot { background: #4a8b4d; }
.export-preflight-item[data-level="warn"] .export-preflight-dot { background: #d18a3d; }
.export-preflight-item[data-level="fail"] .export-preflight-dot { background: var(--danger, #b04646); }
.export-preflight-item[data-level="info"] .export-preflight-dot { background: #6b7480; }
.export-preflight-level {
  font-size: 10.5px;
  font-weight: 700;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: var(--ink-3);
  white-space: nowrap;
}
.export-preflight-item[data-level="fail"] .export-preflight-level { color: var(--danger, #b04646); }
.export-preflight-item[data-level="warn"] .export-preflight-level { color: #8a4d18; }
.export-preflight-item[data-level="pass"] .export-preflight-level { color: #2f6633; }
.export-preflight-msg { color: var(--ink-1); }

/* ---- Export options ---- */
.export-options {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 22px;
}
.export-card {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 28px 26px;
  display: flex;
  flex-direction: column;
}
.export-card-icon {
  font-size: 28px;
  margin-bottom: 14px;
}
/* "Members" pill on export buttons for free accounts — the click opens
   the unlock dialog (export.js) instead of downloading. */
.export-lock-badge {
  display: inline-block;
  margin-left: 8px;
  padding: 2px 7px;
  font-size: 10px;
  font-weight: 600;
  letter-spacing: .06em;
  text-transform: uppercase;
  border-radius: 999px;
  background: rgba(255,255,255,.22);
  border: 1px solid rgba(255,255,255,.45);
  vertical-align: 2px;
}
.btn-link .export-lock-badge,
.export-menu-item .export-lock-badge {
  background: var(--bg-rail);
  border-color: var(--line);
  color: var(--ink-3);
}
.export-card-title {
  font-family: var(--font-display);
  font-size: 20px;
  font-weight: 600;
  margin: 0 0 10px;
  color: var(--ink-1);
}
.export-card-desc {
  margin: 0 0 14px;
  color: var(--ink-2);
  font-size: 14px;
  line-height: 1.55;
}
.export-card-meta {
  list-style: none;
  margin: 0 0 22px;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.export-card-meta li {
  font-size: 12.5px;
  color: var(--ink-3);
  padding-left: 18px;
  position: relative;
}
.export-card-meta li::before {
  content: '✓';
  position: absolute;
  left: 0;
  top: 0;
  color: var(--accent);
  font-weight: 700;
  font-size: 12px;
}
.export-card .btn { align-self: flex-start; margin-top: auto; }

/* ---- Audiobook export card ---- */
.audiobook-controls {
  display: flex;
  flex-direction: column;
  gap: 10px;
  margin: 4px 0 16px;
}
.audiobook-field {
  display: flex;
  flex-direction: column;
  gap: 4px;
  font-size: 13px;
  color: var(--ink-3);
}
.audiobook-field select {
  width: 100%;
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  color: var(--ink-1);
  font-size: 14px;
}
.audiobook-check {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 13px;
  color: var(--ink-2);
  cursor: pointer;
}
.audiobook-check input { accent-color: var(--accent); }
#audiobook-card .btn { align-self: stretch; margin-top: 0; }
#ab-cancel { margin-top: 8px; }
.audiobook-progress { margin-top: 14px; }
.audiobook-progress-track {
  height: 8px;
  border-radius: 99px;
  background: var(--bg-rail);
  overflow: hidden;
}
.audiobook-progress-track > span {
  display: block;
  height: 100%;
  width: 0;
  background: var(--accent);
  border-radius: 99px;
  transition: width .25s ease;
}
.audiobook-progress-label {
  margin: 8px 0 0;
  font-size: 12.5px;
  color: var(--ink-3);
}
.audiobook-note {
  margin: 0 0 12px;
  font-size: 12px;
  color: var(--ink-4);
}
.audiobook-chapters-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 8px;
}
.audiobook-chapters-actions { display: flex; gap: 8px; }
.audiobook-chapters-actions .btn-link { font-size: 12px; }
.audiobook-chapters {
  margin-top: 6px;
  max-height: 200px;
  overflow-y: auto;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  padding: 4px;
}
.audiobook-chapter-row {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 5px 6px;
  border-radius: var(--radius-sm);
  font-size: 13px;
  color: var(--ink-1);
  cursor: pointer;
}
.audiobook-chapter-row:hover { background: var(--bg-rail); }
.audiobook-chapter-row input { accent-color: var(--accent); flex: none; }
.audiobook-chapter-title {
  flex: 1 1 auto;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.audiobook-chapter-badge {
  flex: none;
  font-size: 10.5px;
  text-transform: uppercase;
  letter-spacing: .04em;
  color: var(--ink-4);
  background: var(--bg-rail);
  padding: 1px 6px;
  border-radius: 99px;
}
.audiobook-pron > summary {
  cursor: pointer;
  font-size: 13px;
  color: var(--ink-2);
  padding: 2px 0;
}
.audiobook-pron-help {
  margin: 6px 0 6px;
  font-size: 12px;
  color: var(--ink-4);
}
.audiobook-pron-help code {
  background: var(--bg-rail);
  padding: 1px 4px;
  border-radius: 3px;
  font-size: 11.5px;
}
.audiobook-pron textarea {
  width: 100%;
  resize: vertical;
  padding: 8px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  color: var(--ink-1);
  font-size: 13px;
  font-family: var(--font-sans);
}

@media (max-width: 1100px) {
  .export-grid { grid-template-columns: 1fr; padding: 24px 28px 60px; }
  .export-options { grid-template-columns: 1fr; }
}

/* ============================================================
   Modal — Edit book details (tabbed)
   ============================================================ */
.modal-card-wide {
  max-width: 880px;
  padding: 0;
  overflow: hidden;
}
.modal-tabs {
  display: flex;
  align-items: center;
  border-bottom: 1px solid var(--line);
  padding: 0 6px;
  position: relative;
}
.modal-tab {
  background: transparent;
  border: none;
  padding: 16px 22px 14px;
  font-family: inherit;
  font-size: 13.5px;
  font-weight: 500;
  color: var(--ink-3);
  cursor: pointer;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}
.modal-tab:hover { color: var(--ink-1); }
.modal-tab.is-active {
  color: var(--accent);
  border-bottom-color: var(--accent);
}
.modal-close {
  position: absolute;
  top: 10px; right: 12px;
  width: 32px; height: 32px;
  border: none; background: transparent;
  font-size: 22px; line-height: 1;
  color: var(--ink-3); cursor: pointer; padding: 0;
  border-radius: 50%;
}
.modal-close:hover { background: var(--bg-rail); color: var(--ink-1); }

.modal-tab-body {
  padding: 28px 32px 32px;
}
.modal-tab-body[hidden] { display: none; }
.modal-help {
  font-size: 13px;
  color: var(--ink-3);
  margin: 0 0 20px;
  line-height: 1.55;
}
.modal-grid {
  display: grid;
  grid-template-columns: 1fr 200px;
  gap: 28px;
  align-items: start;
}
.modal-grid-main { min-width: 0; }
.modal-cover {
  aspect-ratio: 2 / 3;
  background: var(--ink-1);
  border-radius: 4px;
  overflow: hidden;
  box-shadow: var(--shadow-paper);
}
.modal-cover img { width: 100%; height: 100%; object-fit: cover; display: block; }
.modal-cover-fallback {
  width: 100%; height: 100%;
  background: linear-gradient(155deg, #2c2820 0%, #1a1715 100%);
  border-left: 4px solid var(--accent);
  display: flex; align-items: center; justify-content: center;
  text-align: center;
  padding: 16px;
  color: #f1ead2;
  font-family: var(--font-display);
  font-size: 14px;
}
.modal-cover-hint {
  margin: 12px 0 0;
  font-size: 12px;
  color: var(--ink-3);
}

.field-row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 14px;
}
.field-coming {
  font-size: 11px;
  color: var(--ink-4);
  font-weight: 400;
  text-transform: none;
  letter-spacing: 0;
  font-style: italic;
}
.field-help {
  display: block;
  margin-top: 4px;
  font-size: 11px;
  color: var(--ink-4);
  letter-spacing: 0;
  text-transform: none;
}
.field-help code {
  background: var(--bg-rail);
  padding: 1px 5px;
  border-radius: 3px;
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-size: 10.5px;
}

/* ============================================================
   PHASE B — Book details page
   ============================================================ */
.details-body { background: var(--bg-page); min-height: 100vh; }
.details-shell { min-height: 100vh; display: flex; flex-direction: column; }

.btn-back-editor {
  display: inline-flex; align-items: center;
  background: transparent;
  border: 1px solid #3a3733;
  color: #c8c3b6;
  font-size: 12.5px;
  padding: 5px 12px;
  border-radius: 999px;
  text-decoration: none;
  letter-spacing: .01em;
  transition: background .15s ease, color .15s ease;
}
.btn-back-editor:hover { background: var(--bg-topbar-soft); color: #fff; }

.details-main {
  flex: 1;
  padding: 32px 48px 80px;
  max-width: 1280px;
  margin: 0 auto;
  width: 100%;
}
.details-grid {
  display: grid;
  grid-template-columns: 1fr 320px;
  gap: 28px;
  align-items: start;
}

/* ----- Left: tabbed form card ----- */
.details-card {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  overflow: hidden;
}
.details-tabs {
  display: flex;
  gap: 4px;
  border-bottom: 1px solid var(--line);
  padding: 0 24px;
  background: #fff;
}
.details-tab {
  background: transparent;
  border: none;
  padding: 18px 4px 14px;
  margin: 0 14px 0 0;
  font-family: inherit;
  font-size: 14px;
  font-weight: 500;
  color: var(--ink-3);
  cursor: pointer;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}
.details-tab:hover { color: var(--ink-1); }
.details-tab.is-active {
  color: var(--accent);
  border-bottom-color: var(--accent);
}
.details-tab-pane { padding: 32px 36px 36px; }
.details-tab-pane[hidden] { display: none; }

.details-form-grid {
  display: grid;
  grid-template-columns: 1fr 220px;
  gap: 36px;
  align-items: start;
}
.details-form-main { min-width: 0; }
.details-form-side {
  display: flex;
  flex-direction: column;
  align-items: stretch;
}

.details-cover, .details-logo {
  position: relative;
  background: var(--ink-1);
  border-radius: 4px;
  overflow: hidden;
  box-shadow: var(--shadow-paper);
  margin-bottom: 12px;
}
/* Cover container has no fixed ratio — it sizes to the image's natural ratio.
   Only the fallback (when no cover uploaded) uses a 2:3 placeholder. */
.details-cover { background: transparent; box-shadow: none; }
.details-cover:has(img) { background: var(--ink-1); box-shadow: var(--shadow-paper); }
.details-logo  {
  background: #fafaf6;
  border: 1px solid var(--line);
  aspect-ratio: 1 / 1;
  box-shadow: none;
  display: flex;
  align-items: center;
  justify-content: center;
}
.details-cover img {
  width: 100%;
  height: auto;
  display: block;
  /* No object-fit — the box flexes to the image's intrinsic aspect ratio. */
}
.details-logo img  { max-width: 80%; max-height: 80%; object-fit: contain; display: block; }
.details-cover.is-uploading::after,
.details-logo.is-uploading::after {
  content: 'Uploading…';
  position: absolute; inset: 0;
  background: rgba(0,0,0,.55); color: #fff;
  display: flex; align-items: center; justify-content: center;
  font-size: 13px; letter-spacing: .04em;
}
.details-cover-fallback {
  /* Render as a 2:3 block when no cover is uploaded. */
  aspect-ratio: 2 / 3;
  background: linear-gradient(155deg, #2c2820 0%, #1a1715 100%);
  border-left: 4px solid var(--accent);
  border-radius: 4px;
  box-shadow: var(--shadow-paper);
  display: flex; align-items: center; justify-content: center;
  text-align: center;
  padding: 16px;
  color: #f1ead2;
  font-family: var(--font-display);
  font-size: 16px;
  line-height: 1.3;
}
.details-cover-title { color: #f1ead2; font-weight: 500; }
.details-logo-fallback {
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
}
.details-cover-btn {
  align-self: stretch;
  text-align: center;
}
.cover-remove {
  position: absolute;
  top: 8px; right: 8px;
  width: 26px; height: 26px;
  border-radius: 50%;
  border: none;
  background: rgba(255,255,255,.92);
  color: var(--ink-2);
  cursor: pointer;
  display: inline-flex; align-items: center; justify-content: center;
  padding: 0;
  box-shadow: 0 1px 4px rgba(0,0,0,.2);
}
.cover-remove:hover { background: var(--danger); color: #fff; }

/* Chip input (Author shows as chip in Atticus) */
.chip-input {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  padding: 6px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  margin-bottom: 6px;
  min-height: 32px;
}
.chip-input:empty { display: none; }
.chip {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 3px 8px 3px 10px;
  background: var(--accent-bg);
  border: 1px solid var(--accent-soft);
  border-radius: 4px;
  font-size: 12.5px;
  color: var(--ink-1);
}
.chip-x { color: var(--ink-3); cursor: pointer; font-weight: 600; }
.chip-x:hover { color: var(--danger); }

/* ----- Right rail of stat cards ----- */
.details-rail {
  display: flex;
  flex-direction: column;
  gap: 18px;
  position: sticky;
  top: 16px;
}
.rail-card {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 18px 20px 20px;
}
.rail-card-title {
  font-family: var(--font-sans);
  font-size: 13px;
  font-weight: 600;
  color: var(--ink-1);
  margin: 0 0 14px;
  display: flex;
  align-items: center;
  gap: 6px;
}
.info-pill {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 14px; height: 14px;
  border-radius: 50%;
  background: var(--ink-5);
  color: #fff;
  font-size: 9px;
  font-style: italic;
  font-weight: 700;
  font-family: var(--font-display);
}
.stat-block {
  display: flex;
  align-items: baseline;
  gap: 8px;
  margin-bottom: 10px;
}
.stat-num {
  font-family: var(--font-display);
  font-size: 32px;
  font-weight: 600;
  color: var(--accent);
  line-height: 1;
}
.stat-label {
  color: var(--ink-3);
  font-size: 13px;
}
.rail-card-meta {
  list-style: none;
  margin: 6px 0 0;
  padding: 12px 0 0;
  border-top: 1px solid var(--line-soft);
  display: flex;
  flex-direction: column;
  gap: 6px;
  font-size: 13px;
  color: var(--ink-3);
}
.rail-card-meta li {
  display: flex;
  justify-content: space-between;
}
.rail-card-meta strong { color: var(--ink-1); font-weight: 600; }

.rail-export-grid {
  display: grid;
  grid-template-columns: 1fr 1fr 1fr;
  gap: 8px;
}
.btn-success {
  background: #16a34a;
  border-color: #16a34a;
  color: #fff;
}
.btn-success:hover { background: #15803d; border-color: #15803d; color: #fff; }
.btn-success:disabled,
.btn-success[disabled] {
  background: #c8c3b6;
  border-color: #c8c3b6;
  color: #fff;
  cursor: not-allowed;
}

.rail-card-help {
  margin: 10px 0 0;
  font-size: 12px;
  color: var(--ink-4);
  line-height: 1.55;
}

/* ----- Snapshot timeline (book details right rail) -----
   Vertical commit-history-style spine with a dot per snapshot. The
   spine is a pseudo-element on the <ol> so it draws between dots even
   if rows have variable height; each .snap-dot is absolutely-positioned
   over the spine. */
.snap-card-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
}
.snapshot-empty {
  padding: 14px 0 4px;
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
  text-align: center;
}
.snap-timeline {
  list-style: none;
  margin: 12px 0 0;
  padding: 4px 0 4px 0;
  position: relative;
}
.snap-timeline::before {
  content: '';
  position: absolute;
  left: 7px;
  top: 12px;
  bottom: 12px;
  width: 2px;
  background: var(--line);
  border-radius: 1px;
}
.snap-node {
  position: relative;
  display: grid;
  grid-template-columns: 22px 1fr auto;
  align-items: start;
  gap: 10px;
  padding: 10px 0;
}
.snap-dot {
  position: relative;
  display: block;
  width: 12px; height: 12px;
  margin: 4px 0 0 1px;
  background: var(--accent);
  border: 2px solid var(--bg-page, #fff);
  border-radius: 50%;
  box-shadow: 0 0 0 1px var(--line);
}
.snap-body { min-width: 0; }
.snap-line {
  display: flex;
  align-items: baseline;
  flex-wrap: wrap;
  gap: 8px;
}
.snap-rel {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-3);
  cursor: help;
}
.snap-label {
  font-size: 13.5px;
  font-weight: 500;
  color: var(--ink-1);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 100%;
}
.snap-label-empty {
  font-style: italic;
  font-weight: 400;
  color: var(--ink-3);
}
.snap-stats {
  font-size: 11.5px;
  color: var(--ink-3);
  margin-top: 3px;
}
.snap-actions {
  display: flex;
  gap: 4px;
  align-items: flex-start;
  flex-shrink: 0;
}
.snap-link {
  width: 26px; height: 26px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--line);
  background: #fff;
  color: var(--ink-2);
  border-radius: var(--radius-sm);
  cursor: pointer;
  font-size: 14px;
  text-decoration: none;
  padding: 0;
  font-family: inherit;
  transition: background .12s, color .12s, border-color .12s;
}
.snap-link:hover { background: var(--bg-rail); border-color: var(--line-strong); color: var(--ink-1); }
.snap-link-danger:hover { background: var(--danger); border-color: var(--danger); color: #fff; }

/* ----- Beta-reader share rail card + modal ----- */
.share-list {
  list-style: none;
  margin: 14px 0 0;
  padding: 0;
  border-top: 1px solid var(--line-soft);
}
.share-empty {
  padding: 14px 0 4px;
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
  text-align: center;
}
.share-row {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 10px;
  padding: 12px 0;
  border-bottom: 1px solid var(--line-soft);
}
.share-row:last-child { border-bottom: none; }
.share-meta { display: flex; flex-direction: column; gap: 4px; min-width: 0; }
.share-label {
  font-size: 13px;
  color: var(--ink-1);
  font-weight: 500;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 220px;
}
.share-sub { font-size: 11px; color: var(--ink-3); }
.share-chips { display: flex; gap: 4px; flex-wrap: wrap; margin-top: 2px; }
.share-chip {
  display: inline-flex;
  align-items: center;
  font-size: 10.5px;
  padding: 2px 8px;
  border-radius: 999px;
  background: var(--bg-rail);
  color: var(--ink-3);
  border: 1px solid var(--line-soft);
  white-space: nowrap;
}
.share-chip-danger { background: #fde6e6; color: #8a1f1f; border-color: #f4c4c4; }
.share-actions { display: flex; gap: 4px; flex-shrink: 0; }

.share-modal-card { max-width: 520px; }

/* ----- Releases rail card (KDP / IngramSpark / etc.) -----
   Mirrors the share-list look so the two rail cards feel uniform —
   same row chrome, same chip pill, same right-side action buttons. */
.release-list {
  list-style: none;
  margin: 14px 0 0;
  padding: 0;
  border-top: 1px solid var(--line-soft);
}
.release-empty {
  padding: 14px 0 4px;
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
  text-align: center;
}
.release-row {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 10px;
  padding: 12px 0;
  border-bottom: 1px solid var(--line-soft);
}
.release-row:last-child { border-bottom: none; }
.release-meta { display: flex; flex-direction: column; gap: 4px; min-width: 0; }
.release-label {
  font-size: 13px;
  color: var(--ink-1);
  font-weight: 500;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 220px;
}
.release-sub { font-size: 11px; color: var(--ink-3); }
.release-chips { display: flex; gap: 4px; flex-wrap: wrap; margin-top: 2px; }
.release-chip {
  display: inline-flex;
  align-items: center;
  font-size: 10.5px;
  padding: 2px 8px;
  border-radius: 999px;
  background: var(--bg-rail);
  color: var(--ink-3);
  border: 1px solid var(--line-soft);
  white-space: nowrap;
}
/* Status-tinted chips. "live" gets the affirmative green tone, "delisted"
   gets the danger tone — quick visual scan of what's actually selling. */
.release-chip-live     { background: #e6f5ea; color: #1e6b35; border-color: #c4e4cf; }
.release-chip-delisted { background: #fde6e6; color: #8a1f1f; border-color: #f4c4c4; }
.release-chip-paused   { background: #fbf1cf; color: #6b5210; border-color: #efdf95; }
.release-actions { display: flex; gap: 4px; flex-shrink: 0; }

.release-modal-card { max-width: 540px; }

/* ----- Editor sub-tab views: Releases + Marketing ("Publishing").
   Single-column layout (no left sidebar, unlike Resources/Bible) —
   header bar on top, a full-width table below. Lives under the
   "Resources" top tab via the shared .subview-tabs strip. */
.editor-view.publishing-view {
  flex-direction: column;
  background: var(--bg-page);
  overflow: hidden;
}
.publishing-view[hidden] { display: none !important; }

.publishing-main {
  flex: 1;
  min-height: 0;
  overflow-y: auto;
  padding: 28px 36px 48px;
}
.publishing-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 24px;
  margin-bottom: 22px;
  max-width: 1200px;
}
.publishing-title {
  margin: 0 0 6px;
  font-size: 22px;
  font-weight: 600;
  color: var(--ink-1);
}
.publishing-sub {
  margin: 0;
  font-size: 13px;
  color: var(--ink-3);
  max-width: 720px;
  line-height: 1.5;
}

.publishing-table-wrap {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 6px;
  overflow: hidden;
  max-width: 1200px;
}
.publishing-table {
  width: 100%;
  border-collapse: collapse;
  font-size: 13px;
}
.publishing-table th {
  text-align: left;
  padding: 10px 12px;
  background: var(--bg-rail);
  color: var(--ink-2);
  font-weight: 600;
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .08em;
  border-bottom: 1px solid var(--line);
  white-space: nowrap;
}
.publishing-table td {
  padding: 10px 12px;
  border-bottom: 1px solid var(--line-soft);
  vertical-align: middle;
  color: var(--ink-2);
}
.publishing-table tbody tr:last-child td { border-bottom: none; }
.publishing-table tbody tr:hover td { background: var(--bg-rail); }
.publishing-cell-strong { color: var(--ink-1); font-weight: 500; }
.publishing-actions-col { width: 72px; }
.publishing-actions { text-align: right; white-space: nowrap; }
.publishing-actions .snap-link { margin-left: 4px; }
.publishing-empty-row td {
  text-align: center;
  padding: 28px 12px;
  color: var(--ink-4);
  font-style: italic;
}

/* Member-gate panel shown in a publishing sub-tab when a free user
   opens a paid feature (e.g. Beta readers). Centered, calm upsell. */
.publishing-locked {
  max-width: 560px;
  margin: 32px auto;
  padding: 40px 32px;
  text-align: center;
  background: var(--bg-rail);
  border: 1px solid var(--line);
  border-radius: var(--radius);
}
.publishing-locked-icon { font-size: 34px; line-height: 1; margin-bottom: 14px; }
.publishing-locked-title { margin: 0 0 10px; font-size: 1.2rem; }
.publishing-locked-text {
  margin: 0 0 22px;
  color: var(--ink-2);
  line-height: 1.55;
}

/* Status pills shared between releases and campaigns. The base pill is
   the neutral "planned" look; status-tinted variants override. */
.pub-pill {
  display: inline-flex;
  align-items: center;
  font-size: 11px;
  padding: 2px 9px;
  border-radius: 999px;
  background: var(--bg-rail);
  color: var(--ink-3);
  border: 1px solid var(--line-soft);
  white-space: nowrap;
}
.pub-pill-live,
.pub-pill-active,
.pub-pill-completed  { background: #e6f5ea; color: #1e6b35; border-color: #c4e4cf; }
.pub-pill-delisted,
.pub-pill-cancelled  { background: #fde6e6; color: #8a1f1f; border-color: #f4c4c4; }
.pub-pill-paused     { background: #fbf1cf; color: #6b5210; border-color: #efdf95; }

.pub-dash { color: var(--ink-4); }

/* ---------- Book details: cover actions ---------- */
.details-cover-actions {
  display: flex;
  flex-direction: column;
  gap: 6px;
  margin-top: 8px;
}
.share-chapter-picker {
  list-style: none;
  margin: 8px 0 0;
  padding: 8px 10px;
  max-height: 240px;
  overflow-y: auto;
  border: 1px solid var(--line-soft);
  border-radius: var(--radius-sm);
  background: var(--bg-rail);
}
.share-chapter-picker li { padding: 2px 0; }
.share-chapter-picker .field-toggle { display: flex; align-items: center; gap: 8px; }
.share-chapter-kind {
  font-size: 10.5px;
  color: var(--ink-4);
  text-transform: uppercase;
  letter-spacing: .06em;
  margin-left: 6px;
}

/* ----- Public beta-reader unlock page ----- */
.share-unlock-body {
  background: #1d1b18;
  color: #e8e3d6;
  min-height: 100vh;
  margin: 0;
  display: flex;
  align-items: center;
  justify-content: center;
}
.share-unlock-shell { width: 100%; padding: 24px; }
.share-unlock-card {
  max-width: 380px;
  margin: 0 auto;
  background: #25221e;
  border: 1px solid #3a3733;
  border-radius: 10px;
  padding: 28px;
  box-shadow: 0 12px 36px rgba(0,0,0,.4);
}
.share-unlock-title {
  font-family: 'Playfair Display', Georgia, serif;
  font-size: 22px;
  font-weight: 600;
  margin: 0 0 8px;
  color: #fff;
}
.share-unlock-help {
  margin: 0 0 16px;
  color: #b8b3a6;
  font-size: 13px;
  line-height: 1.5;
}
.share-unlock-form .field-label { color: #c8c3b6; }
.share-unlock-form input[type="password"] {
  width: 100%;
  background: #1d1b18;
  border: 1px solid #3a3733;
  color: #e8e3d6;
  padding: 10px 12px;
  border-radius: 6px;
  font-size: 14px;
}
.share-unlock-form input[type="password"]:focus {
  outline: none;
  border-color: #8b6914;
  box-shadow: 0 0 0 2px rgba(139,105,20,.25);
}

/* ----- Public beta-reader main view ----- */
.share-reader-body {
  background: var(--reader-bg, #fdfbf6);
  color: var(--reader-text, #1a1a1a);
  margin: 0;
  min-height: 100vh;
}
.share-reader-shell {
  display: flex;
  flex-direction: column;
  min-height: 100vh;
}
.share-reader-topbar {
  position: sticky;
  top: 0;
  z-index: 20;
  background: rgba(29,27,24,.96);
  color: #e8e3d6;
  border-bottom: 1px solid #2a2723;
  backdrop-filter: blur(8px);
}
.share-reader-topbar-inner {
  max-width: 1100px;
  margin: 0 auto;
  padding: 12px 24px;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
}
.share-reader-brand { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.share-reader-brand-name {
  font-family: 'Playfair Display', Georgia, serif;
  font-size: 16px;
  font-weight: 600;
  color: #fff;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.share-reader-brand-author { color: #b8b3a6; font-size: 12px; }
.share-reader-topbar-actions { display: flex; gap: 12px; align-items: center; }
.share-reader-label {
  font-size: 11.5px;
  color: #b8b3a6;
  border: 1px solid #3a3733;
  padding: 3px 10px;
  border-radius: 999px;
}
.share-reader-toc-toggle {
  display: none;
  background: transparent;
  border: 1px solid #3a3733;
  color: #d4cfc1;
  padding: 6px 10px;
  border-radius: 6px;
  cursor: pointer;
  font-size: 14px;
}

.share-reader-grid {
  flex: 1;
  display: grid;
  grid-template-columns: 240px minmax(0, 1fr);
  max-width: 1100px;
  width: 100%;
  margin: 0 auto;
  padding: 0 24px 48px;
  gap: 32px;
  box-sizing: border-box;
}

.share-reader-toc {
  position: sticky;
  top: 60px;
  align-self: start;
  max-height: calc(100vh - 80px);
  overflow-y: auto;
  padding: 22px 0;
  border-right: 1px solid rgba(0,0,0,.06);
}
.share-reader-toc-title {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: 13px;
  font-weight: 600;
  margin: 0 0 14px;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--reader-accent, #8b6914);
}
.share-reader-toc-empty { font-size: 13px; color: #888; font-style: italic; }
.share-reader-toc-list { list-style: none; padding: 0; margin: 0; }
.share-reader-toc-list li { margin: 0; }
.share-reader-toc-item {
  width: 100%;
  display: flex;
  align-items: baseline;
  gap: 8px;
  padding: 8px 12px 8px 0;
  background: transparent;
  border: 0;
  border-left: 2px solid transparent;
  text-align: left;
  cursor: pointer;
  font: inherit;
  color: inherit;
  font-size: 13.5px;
  line-height: 1.4;
}
.share-reader-toc-item:hover { color: var(--reader-accent, #8b6914); }
.share-reader-toc-item.is-active {
  border-left-color: var(--reader-accent, #8b6914);
  padding-left: 10px;
  color: var(--reader-accent, #8b6914);
  font-weight: 600;
}
/* Per-chapter count of THIS reader's notes. Decorative — fades in once
   the counts API resolves; hidden when the chapter has zero notes. */
.share-reader-toc-badge {
  margin-left: auto;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 18px;
  height: 18px;
  padding: 0 6px;
  border-radius: 999px;
  background: var(--reader-accent, #8b6914);
  color: #fff;
  font-size: 10px;
  font-weight: 600;
  line-height: 1;
  font-variant-numeric: tabular-nums;
  font-family: inherit;
}
.share-reader-toc-num {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  color: var(--reader-accent, #8b6914);
  font-size: 12px;
  flex-shrink: 0;
  min-width: 1.6em;
}

.share-reader-main {
  padding: 32px 0 24px;
  display: flex;
  flex-direction: column;
  gap: 20px;
  min-width: 0;
}

/* First-visit orientation card for beta readers — dismissable, shown
   once per share link (localStorage). UI-sans on purpose: it's chrome,
   not part of the manuscript. */
.share-reader-intro {
  background: #faf7ef;
  border: 1px solid #e9e2d0;
  border-left: 3px solid var(--reader-accent, #8b6914);
  border-radius: 8px;
  padding: 20px 24px;
  font-family: var(--font-sans, -apple-system, sans-serif);
  color: #3a3630;
}
/* Whole header doubles as the open/close toggle — the card is
   collapsible (never dismissed) so readers can re-check the
   instructions whenever they forget how commenting works. */
.share-reader-intro-toggle {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  width: 100%;
  background: none;
  border: 0;
  padding: 0;
  cursor: pointer;
  text-align: left;
  color: inherit;
}
.share-reader-intro-title {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: 19px;
  font-weight: 600;
  margin: 0;
  color: var(--reader-text, #1a1a1a);
}
.share-reader-intro-chevron {
  font-size: 14px;
  color: var(--reader-accent, #8b6914);
  transition: transform .15s ease;
}
.share-reader-intro-toggle[aria-expanded="false"] .share-reader-intro-chevron {
  transform: rotate(-90deg);
}
.share-reader-intro-body {
  margin-top: 10px;
}
.share-reader-intro-list {
  margin: 0 0 14px;
  padding-left: 20px;
  font-size: 14px;
  line-height: 1.6;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.share-reader-intro-actions {
  display: flex;
  justify-content: flex-end;
}

/* "Powered by …" line under the reader — quiet, but present on every
   share page (beta readers are prospective authors). */
.share-reader-powered {
  text-align: center;
  font-family: var(--font-sans, -apple-system, sans-serif);
  font-size: 12.5px;
  color: #8a857a;
  padding: 8px 0 4px;
}
.share-reader-powered a {
  color: var(--reader-accent, #8b6914);
  text-decoration: none;
  font-weight: 600;
}
.share-reader-powered a:hover { text-decoration: underline; }
.share-reader-page {
  background: var(--reader-bg, #fdfbf6);
  font-family: var(--reader-body-font, 'Lora', Georgia, serif);
  font-size: var(--reader-font-size, 12pt);
  line-height: var(--reader-line-height, 1.65);
  color: var(--reader-text, #1a1a1a);
  padding: 56px 64px;
  border: 1px solid rgba(0,0,0,.06);
  border-radius: 6px;
  box-shadow: 0 2px 24px rgba(0,0,0,.06), 0 1px 2px rgba(0,0,0,.04);
  min-height: 60vh;
}
.share-reader-page p {
  margin: 0 0 0.7em;
  text-indent: var(--reader-indent, 0.3in);
  text-align: var(--reader-text-align, justify);
  hyphens: auto;
  -webkit-hyphens: auto;
}
.share-reader-page .share-reader-content p:first-child { text-indent: 0; }
/* Per-paragraph alignment from the editor (Quill writes these classes). */
.share-reader-page .ql-align-center  { text-align: center !important; text-indent: 0 !important; }
.share-reader-page .ql-align-right   { text-align: right !important; text-indent: 0 !important; }
.share-reader-page .ql-align-justify { text-align: justify !important; }
/* Theme-level default: indent every chapter's first paragraph. */
.share-reader-page.is-indent-first .share-reader-content p:first-child { text-indent: var(--reader-indent, 0.3in); }
.share-reader-head {
  text-align: center;
  margin: 0 0 1.8em;
  padding-bottom: 1.2em;
  border-bottom: 1px solid rgba(0,0,0,.06);
}
/* Auto-rendered title page + TOC inside the share reader — look more
   like a real book page rather than a stub list. */
.share-reader-page .auto-titlepage { padding: 2em 0 1.4em; }
.share-reader-page .auto-titlepage-title {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: 2.2em;
  font-weight: 600;
  margin: 0 0 .35em;
  line-height: 1.15;
  color: var(--reader-text);
}
.share-reader-page .auto-titlepage-subtitle {
  font-style: italic;
  color: var(--reader-accent, #8b6914);
  margin: 0 0 1.6em;
  text-indent: 0;
  text-align: center;
}
.share-reader-page .auto-titlepage-author {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  letter-spacing: .12em;
  margin: 0 0 2.4em;
  text-indent: 0;
  text-align: center;
}
.share-reader-page .auto-titlepage-publisher-logo {
  margin: 1.6em auto 0.4em;
  max-width: 50%;
}
.share-reader-page .auto-titlepage-publisher-logo img {
  max-width: 100%;
  max-height: 120px;
  height: auto;
  display: block;
  margin: 0 auto;
}
.share-reader-page .auto-titlepage-publisher-name {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: .8em;
  letter-spacing: .14em;
  text-transform: uppercase;
  margin: 0;
  text-indent: 0;
  text-align: center;
}
.share-reader-page .auto-toc { list-style: none; margin: 0; padding: 0; }
.share-reader-page .auto-toc-item {
  padding: 10px 0;
  border-bottom: 1px dotted rgba(0,0,0,.18);
  text-indent: 0;
}
.share-reader-page .auto-toc-item:last-child { border-bottom: 0; }
.share-reader-page .auto-toc-item a {
  color: var(--reader-text);
  text-decoration: none;
  display: flex;
  gap: 10px;
  align-items: baseline;
}
.share-reader-page .auto-toc-item a:hover { color: var(--reader-accent, #8b6914); }
.share-reader-page .auto-toc-num {
  color: var(--reader-accent, #8b6914);
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: .9em;
  min-width: 1.8em;
}
.share-reader-page .auto-toc-front,
.share-reader-page .auto-toc-back  { font-style: italic; }
.share-reader-page .auto-toc-part {
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .08em;
}
.share-reader-title {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: 1.9em;
  font-weight: 600;
  margin: 0;
  color: var(--reader-text, #1a1a1a);
}
.share-reader-subtitle {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-style: italic;
  margin: 0.4em 0 0;
  color: var(--reader-accent, #8b6914);
  text-indent: 0;
}
.share-reader-page h1, .share-reader-page h2, .share-reader-page h3,
.share-reader-page h4, .share-reader-page h5, .share-reader-page h6 {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
}
.share-reader-page blockquote {
  border-left: 2px solid var(--reader-accent, #8b6914);
  padding: 0.2em 1em;
  margin: 1em 0;
  font-style: italic;
}
.share-reader-page img { max-width: 100%; height: auto; display: block; margin: 0.6em auto; }
.share-reader-page hr {
  border: 0;
  text-align: center;
  margin: 1.6em 0;
  color: var(--reader-accent, #8b6914);
}
.share-reader-page hr::before { content: '*  *  *'; letter-spacing: .25em; }
.share-reader-loading {
  text-align: center;
  padding: 60px 0;
  color: #999;
  font-style: italic;
}
.share-reader-page .placeholder-line { color: #aaa; font-style: italic; text-align: center; }

.share-reader-nav {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 12px;
  padding: 16px 0 8px;
  border-top: 1px solid rgba(0,0,0,.08);
}

/* ---------- Beta-reader comments ---------- */
.share-comments {
  margin: 32px 0 8px;
  padding: 28px 32px;
  background: rgba(0,0,0,.02);
  border: 1px solid rgba(0,0,0,.08);
  border-radius: 8px;
  font-family: var(--reader-body-font, Georgia, serif);
}
.share-comments-head { margin-bottom: 18px; }
.share-comments-title {
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  font-size: 20px;
  margin: 0 0 6px;
  color: var(--reader-text, #1a1a1a);
}
.share-comments-help {
  font-size: 13px;
  color: rgba(0,0,0,.55);
  margin: 0;
  line-height: 1.45;
}
.share-comments-list {
  list-style: none;
  margin: 0 0 22px;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.share-comments-empty {
  font-size: 13px;
  color: rgba(0,0,0,.45);
  font-style: italic;
  padding: 8px 0;
}
.share-comment {
  background: rgba(255,255,255,.6);
  padding: 12px 14px;
  border-radius: 6px;
  border: 1px solid rgba(0,0,0,.06);
}
.share-comment-meta {
  display: flex;
  align-items: baseline;
  gap: 10px;
  margin-bottom: 6px;
}
.share-comment-author {
  font-weight: 600;
  font-size: 13px;
  color: var(--reader-text, #1a1a1a);
}
.share-comment-time {
  font-size: 11px;
  color: rgba(0,0,0,.45);
  letter-spacing: .04em;
}
.share-comment-body {
  font-size: 14px;
  line-height: 1.5;
  color: var(--reader-text, #1a1a1a);
  white-space: pre-wrap;
  word-break: break-word;
}

/* Acknowledgement badges on the reader side. The author can mark a
   comment resolved or post a short reply; both surface here so the
   reader can see what the author has done with their feedback. */
.share-comment-resolved {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .04em;
  color: #2f6633;
  background: #d8ebd8;
  padding: 1px 7px;
  border-radius: 999px;
  border: 1px solid #b8d8b8;
}
.share-comment.is-resolved {
  background: rgba(255,255,255,.4);
}
.share-comment.is-resolved .share-comment-body {
  color: rgba(0,0,0,.55);
}
.share-comment-reply {
  margin: 10px 0 0 10px;
  padding: 8px 10px;
  background: rgba(0,0,0,.04);
  border-left: 2px solid var(--reader-accent, #8b6914);
  border-radius: 0 6px 6px 0;
}
.share-comment-reply-meta {
  display: flex;
  align-items: baseline;
  gap: 10px;
  margin-bottom: 4px;
}
.share-comment-reply-from {
  font-weight: 700;
  font-size: 11px;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--reader-accent, #8b6914);
}
.share-comment-reply-body {
  font-size: 13.5px;
  line-height: 1.5;
  color: var(--reader-text, #1a1a1a);
  white-space: pre-wrap;
  word-break: break-word;
}
.share-comments-form {
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.share-comments-name {
  display: flex;
  flex-direction: column;
  gap: 4px;
  font-size: 12px;
  color: rgba(0,0,0,.6);
}
.share-comments-name-label {
  font-weight: 600;
  letter-spacing: .04em;
  text-transform: uppercase;
  font-size: 11px;
}
.share-comments-form input[type="text"],
.share-comments-form textarea {
  font-family: inherit;
  font-size: 14px;
  padding: 9px 12px;
  border: 1px solid rgba(0,0,0,.18);
  border-radius: 6px;
  background: #fff;
  color: var(--reader-text, #1a1a1a);
  width: 100%;
  box-sizing: border-box;
}
.share-comments-form textarea {
  resize: vertical;
  min-height: 70px;
  line-height: 1.45;
}
.share-comments-form input[type="text"]:focus,
.share-comments-form textarea:focus {
  outline: none;
  border-color: var(--reader-accent, #8b6914);
  box-shadow: 0 0 0 3px rgba(139,105,20,.15);
}
.share-comments-form-actions {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
}
.share-comments-error {
  font-size: 12px;
  color: #b03030;
}
.share-comments-disabled {
  font-size: 13px;
  color: rgba(0,0,0,.55);
  font-style: italic;
  margin: 0;
  padding: 12px 0 0;
  border-top: 1px dashed rgba(0,0,0,.1);
}

/* Floating "Comment on selection" button. position: absolute against the
   document — JS sets top/left to hover above the user's text selection. */
.share-comment-floater {
  position: absolute;
  z-index: 50;
  transform: translateX(-50%);
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 12px;
  background: var(--reader-text, #1a1a1a);
  color: #fff;
  border: 0;
  border-radius: 999px;
  font-family: var(--reader-body-font, Georgia, serif);
  font-size: 12px;
  font-weight: 500;
  cursor: pointer;
  box-shadow: 0 6px 18px rgba(0,0,0,.18);
}
.share-comment-floater:hover { background: var(--reader-accent, #8b6914); }

/* Staged-quote preview shown above the form once a selection has been
   adopted. The blockquote keeps the reader oriented while they type. */
.share-comments-staged {
  background: rgba(255,235,150,.35);
  border-left: 3px solid var(--reader-accent, #8b6914);
  padding: 10px 14px;
  border-radius: 4px;
  font-size: 13px;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.share-comments-staged-label {
  font-weight: 600;
  font-size: 11px;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: rgba(0,0,0,.6);
}
.share-comments-staged-quote {
  margin: 0;
  font-style: italic;
  color: var(--reader-text, #1a1a1a);
  line-height: 1.45;
  max-height: 6.5em;
  overflow: hidden;
}
.share-comments-staged-clear {
  align-self: flex-start;
  font-size: 12px;
}

/* Per-comment quoted snippet (shown alongside the body in the reader's
   own list of posted notes). Visually parallel to .share-comments-staged. */
.share-comment-quote {
  margin: 0 0 6px;
  padding: 6px 10px;
  background: rgba(0,0,0,.03);
  border-left: 2px solid var(--reader-accent, #8b6914);
  font-style: italic;
  font-size: 13px;
  color: rgba(0,0,0,.65);
  line-height: 1.4;
}
.share-reader-pos {
  font-size: 12px;
  color: #888;
  font-family: var(--reader-heading-font, 'Playfair Display', Georgia, serif);
  letter-spacing: .08em;
  text-transform: uppercase;
}

@media (max-width: 800px) {
  .share-reader-toc-toggle { display: inline-flex; }
  .share-reader-grid {
    grid-template-columns: 1fr;
    padding: 0 18px 40px;
    gap: 0;
  }
  .share-reader-toc {
    position: fixed;
    top: 56px; left: 0; right: 0; bottom: 0;
    z-index: 30;
    background: var(--reader-bg, #fdfbf6);
    padding: 20px 24px;
    border-right: 0;
    border-top: 1px solid rgba(0,0,0,.08);
    transform: translateY(-110%);
    transition: transform .22s ease;
    max-height: none;
  }
  .share-reader-toc.is-open { transform: translateY(0); }
  .share-reader-main { padding-top: 24px; }
  .share-reader-page { padding: 32px 22px; }
}

/* ============================================================
   PHASE D — Admin area
   ============================================================ */
.admin-body { background: var(--bg-page); min-height: 100vh; }
.admin-shell {
  min-height: 100vh;
  display: grid;
  grid-template-columns: 256px 1fr;
}

/* ----- Topbar Admin pill (visible across editor/library/details) ----- */
.topbar-admin-link {
  display: inline-flex;
  align-items: center;
  padding: 5px 12px;
  border: 1px solid #3a3733;
  color: #c8c3b6;
  font-size: 12.5px;
  border-radius: 999px;
  text-decoration: none;
  letter-spacing: .04em;
  transition: background .15s ease, color .15s ease;
}
.topbar-admin-link:hover { background: var(--bg-topbar-soft); color: #fff; }
.topbar .topbar-admin-link {
  border-color: #3a3733;
  color: #c8c3b6;
}

/* ----- "Upgrade" CTA (free-tier users only, see partials/upgrade_button.php) -----
   Solid accent fill so it visibly outranks the plain outlined pills
   (Support/Settings/Admin) sitting next to it — this is the one thing in
   the topbar we actually want the user's eye to land on. */
.topbar-upgrade-btn {
  display: inline-flex;
  align-items: center;
  padding: 6px 14px;
  border-radius: 999px;
  background: var(--accent);
  color: #fff;
  font-size: 12.5px;
  font-weight: 700;
  letter-spacing: .02em;
  text-decoration: none;
  white-space: nowrap;
  transition: background .15s ease;
}
.topbar-upgrade-btn:hover { background: var(--accent-soft); color: #fff; }

/* "?" keyboard-help button. Lives in the topbar-right next to
   Settings / Admin. Same dark-bar palette as the admin link, but
   round so it reads as a glyph rather than text. */
.topbar-help-btn {
  width: 26px;
  height: 26px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 1px solid #3a3733;
  background: transparent;
  color: #c8c3b6;
  font-size: 13px;
  font-weight: 600;
  border-radius: 50%;
  cursor: pointer;
  padding: 0;
  transition: background .15s ease, color .15s ease, border-color .15s ease;
}
.topbar-help-btn:hover { background: var(--bg-topbar-soft); color: #fff; }
.topbar-help-btn:focus-visible {
  outline: none;
  box-shadow: 0 0 0 2px rgba(200,195,182,.45);
}

/* ----- Sidebar nav ----- */
.admin-nav {
  background: #1d1b18;
  color: #c8c3b6;
  display: flex;
  flex-direction: column;
  padding: 18px 0 14px;
  /* The nav is taller than most pages now (6 groups); pin it so the
     rail scrolls independently instead of scrolling away with long
     tables. Reset to static in the 900px mobile block. */
  position: sticky;
  top: 0;
  height: 100vh;
  overflow-y: auto;
  align-self: start;
  scrollbar-width: thin;
  scrollbar-color: #3a3733 transparent;
}
.admin-nav-head {
  padding: 0 18px 18px;
  border-bottom: 1px solid #2e2a26;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.admin-logo {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  color: #fff;
  text-decoration: none;
}
.admin-logo .logo-mark {
  width: 26px; height: 26px;
  background: var(--accent);
  border-radius: 6px;
  display: inline-flex; align-items: center; justify-content: center;
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 700;
  color: #fff;
}

/* ----- Admin › Branding: brand-logo manager (preview + upload) ----- */
.admin-logo-manage {
  display: flex;
  align-items: center;
  gap: 20px;
  flex-wrap: wrap;
}
.admin-logo-preview {
  flex: 0 0 auto;
  width: 72px; height: 72px;
  border-radius: 10px;
  background: var(--bg-topbar);
  border: 1px solid var(--line, #ddd);
  display: inline-flex; align-items: center; justify-content: center;
  padding: 10px;
}
.admin-logo-preview img { max-width: 100%; max-height: 100%; object-fit: contain; }
.admin-logo-preview-mark {
  width: 40px; height: 40px;
  border-radius: 8px;
  background: var(--accent);
  color: #fff;
  display: inline-flex; align-items: center; justify-content: center;
  font-family: var(--font-display);
  font-size: 22px; font-weight: 700;
}
.admin-logo-forms {
  display: flex;
  align-items: flex-end;
  gap: 16px;
  flex-wrap: wrap;
}
.admin-logo-label {
  font-family: var(--font-display);
  font-size: 18px;
  letter-spacing: .02em;
}
.admin-section {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--accent);
  margin-left: 36px;
}
.admin-nav-list {
  list-style: none;
  margin: 14px 0 0;
  padding: 0;
  flex: 1;
}
.admin-nav-link {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 18px;
  color: #c8c3b6;
  text-decoration: none;
  font-size: 13.5px;
}
.admin-nav-link:hover { color: #fff; background: rgba(255,255,255,.04); }
.admin-nav-link:hover .admin-nav-icon { opacity: 1; }
.admin-nav-link.is-active {
  background: #2a2723;
  color: #fff;
  font-weight: 500;
  box-shadow: inset 2px 0 0 var(--accent);
}
.admin-nav-link.is-active .admin-nav-icon { opacity: 1; color: var(--accent); }
.admin-nav-icon {
  flex-shrink: 0;
  display: inline-flex;
  opacity: .65;
  transition: opacity .12s ease;
}
.admin-nav-icon svg { width: 16px; height: 16px; display: block; }
.admin-nav-label {
  flex: 1;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.admin-nav-link-muted { color: #8a857a; font-size: 12.5px; }

/* "Jump to…" quick filter between the head and the group list.
   Pure client-side: typing hides non-matching links (see the inline
   script in admin_nav.php); it never touches collapse state. */
.admin-nav-filter { padding: 12px 18px 0; }
.admin-nav-filter input {
  width: 100%;
  background: #26231f;
  border: 1px solid #35312b;
  color: #e8e4da;
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 12.5px;
  padding: 6px 10px;
}
.admin-nav-filter input::placeholder { color: #6c655a; }
.admin-nav-filter input:focus {
  outline: none;
  border-color: #55503f;
}
/* While filtering: collapse is overridden so matches in collapsed
   groups still show; groups with zero matches disappear entirely. */
.admin-nav-list.is-filtering .admin-nav-group-items { max-height: none !important; }
.admin-nav-section.is-empty { display: none; }
.admin-nav-foot {
  padding: 14px 18px 0;
  border-top: 1px solid #2e2a26;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.admin-nav-user {
  font-size: 11px;
  color: #6a665e;
  letter-spacing: .04em;
  padding: 0 0 0 6px;
}
/* Sign out under the logo in the admin rail header — a real button
   (logout is a CSRF-protected POST). Indented to line up under the
   wordmark, matching the "Admin" label's alignment. */
.admin-nav-head-signout-form { margin: 8px 0 0 36px; }
.admin-nav-signout-btn {
  cursor: pointer;
  font-family: inherit;
  font-size: 12px;
  font-weight: 500;
  color: #d8d3c7;
  background: #2e2a26;
  border: 1px solid #423d37;
  border-radius: 6px;
  padding: 5px 14px;
  transition: background .12s ease, border-color .12s ease, color .12s ease;
}
.admin-nav-signout-btn:hover {
  background: #3a352f;
  border-color: #55504a;
  color: #fff;
}

/* ----- Main pane ----- */
.admin-main {
  padding: 32px 40px 80px;
  max-width: 1100px;
  width: 100%;
}
/* Wide-table pages (e.g. the Users list) need more than the standard
   1100px reading-width cap so columns don't fight each other for
   space and force a horizontal scrollbar. */
.admin-main.admin-main-wide {
  max-width: 1500px;
}
.admin-page-head {
  margin-bottom: 24px;
  padding-bottom: 18px;
  border-bottom: 1px solid var(--line-soft);
}
/* Title/sub on the left, page-level action buttons on the right.
   Emitted by partials/admin_page_start.php — the one shared header. */
.admin-page-head-row {
  display: flex;
  justify-content: space-between;
  align-items: flex-start;
  gap: 16px;
  flex-wrap: wrap;
}
.admin-page-head-main { min-width: 0; }
.admin-page-actions {
  display: flex;
  gap: 8px;
  align-items: center;
  flex-shrink: 0;
  /* Optical alignment with the Playfair title's cap height. */
  margin-top: 4px;
}
.admin-page-backlink {
  display: inline-block;
  font-size: 12.5px;
  color: var(--ink-3);
  text-decoration: none;
  margin-bottom: 6px;
}
.admin-page-backlink:hover { color: var(--ink-1); }
.admin-page-title {
  font-family: var(--font-display);
  font-size: 28px;
  font-weight: 600;
  margin: 0 0 6px;
  letter-spacing: .01em;
  color: var(--ink-1);
}
.admin-page-sub {
  margin: 0;
  color: var(--ink-3);
  font-size: 14px;
  max-width: 720px;
  line-height: 1.55;
}

/* ----- The one count-badge component -----
   Replaces both .admin-nav-badge (sidebar/dashboard) and the
   .admin-tier-chip count usage on tab rails. -accent = "needs you"
   (gold), -muted = neutral count. */
.admin-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 20px;
  height: 18px;
  padding: 0 6px;
  border-radius: 999px;
  font-size: 11px;
  font-weight: 700;
  line-height: 1;
}
.admin-badge-accent { background: var(--accent); color: #fff; }
.admin-badge-muted  { background: var(--bg-rail); color: var(--ink-3); }
.admin-nav-link .admin-badge { margin-left: auto; }
.admin-tab-rail-link .admin-badge { margin-left: 6px; }

.admin-alert {
  padding: 10px 14px;
  border-radius: var(--radius-sm);
  font-size: 13px;
  margin-bottom: 18px;
}
.admin-alert-ok    { background: #ecf5e3; color: #2f5a1e; border-left: 3px solid var(--success); }
.admin-alert-error { background: #fdf0ed; color: #8a2c1d; border-left: 3px solid var(--danger); }

.admin-card {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 20px 22px 22px;
  margin-bottom: 22px;
}
.admin-card-title {
  font-family: var(--font-sans);
  font-size: 13px;
  font-weight: 600;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: var(--ink-3);
  margin: 0 0 16px;
}

.admin-form-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 14px 18px;
  align-items: end;
}
.admin-form-grid > .field-toggle {
  grid-column: 1 / -1;
}
.admin-form-actions {
  grid-column: 1 / -1;
  display: flex;
  justify-content: flex-end;
}
.admin-form-inline {
  margin-top: 10px;
  padding: 14px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  display: flex;
  flex-direction: column;
  gap: 10px;
}

/* ----- Stat grid (dashboard) ----- */
.admin-stat-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: 16px;
}
.admin-stat {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 18px 20px 16px;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.admin-stat-wide { grid-column: 1 / -1; }
.admin-stat-num {
  font-family: var(--font-display);
  font-size: 32px;
  font-weight: 600;
  color: var(--accent);
  line-height: 1;
}
.admin-stat-label {
  font-size: 14px;
  font-weight: 500;
  color: var(--ink-1);
  margin-top: 4px;
}
.admin-stat-meta {
  font-size: 12px;
  color: var(--ink-3);
}

/* ----- Dashboard launchpad ----- */
/* "Needs attention" card gets a gold left edge only while there is
   actually something to do — all-clear renders as a plain card. */
.admin-attention-card.has-items { border-left: 3px solid var(--accent); }
.admin-attention-list { list-style: none; margin: 0; padding: 0; }
.admin-attention-row {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 12px;
  padding: 10px 0;
  border-bottom: 1px solid var(--line-soft);
}
.admin-attention-row:last-child { border-bottom: none; }
.admin-attention-row:first-child { padding-top: 0; }
.admin-attention-label {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  font-size: 14px;
  color: var(--ink-1);
}
.admin-attention-clear {
  margin: 0;
  font-size: 14px;
  color: var(--ink-3);
}
.admin-quick-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}
.admin-quick-actions .btn svg {
  width: 15px;
  height: 15px;
  display: block;
  opacity: .7;
}
.admin-recent-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 18px;
  align-items: start;
}
.admin-recent-grid .admin-card { margin-bottom: 0; }
.admin-recent-list { list-style: none; margin: 0; padding: 0; }
.admin-recent-list li {
  padding: 9px 0;
  border-bottom: 1px solid var(--line-soft);
  font-size: 13.5px;
}
.admin-recent-list li:last-child { border-bottom: none; }
.admin-recent-list li:first-child { padding-top: 0; }
.admin-recent-meta {
  display: block;
  font-size: 12px;
  color: var(--ink-3);
  margin-top: 2px;
}

/* ----- Tables ----- */
.admin-table-wrap {
  /* Belt-and-suspenders: if a row's content ever forces the table wider
     than the card (e.g. a long email), scroll horizontally inside the
     card instead of spilling out past its border. */
  overflow-x: auto;
}
.admin-table {
  width: 100%;
  border-collapse: collapse;
  font-size: 13.5px;
}
.admin-table th,
.admin-table td {
  text-align: left;
  padding: 10px 12px;
  border-bottom: 1px solid var(--line-soft);
  vertical-align: top;
}
.admin-table th {
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
.admin-table tr:last-child td { border-bottom: none; }
.admin-pagination {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 16px;
  padding-top: 16px;
  margin-top: 4px;
}
.admin-pagination-label { font-size: 13px; color: var(--ink-3); }
.admin-pagination .is-disabled {
  opacity: .4;
  pointer-events: none;
}
.admin-table-actions {
  text-align: right;
  white-space: nowrap;
  display: flex;
  flex-wrap: wrap;
  gap: 6px 8px;
  justify-content: flex-end;
  align-items: center;
}
/* Utility actions (resend verification / email) tucked inside the
   expanded Edit panel, below Save — keeps the collapsed row down to
   just "Edit" + "Delete" so the actions column stays narrow. */
.admin-row-edit-secondary {
  display: flex;
  flex-wrap: wrap;
  gap: 4px 14px;
  margin-top: 8px;
  padding-top: 8px;
  border-top: 1px dashed var(--line-soft);
}
.admin-pill {
  display: inline-block;
  padding: 2px 8px;
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  border-radius: 999px;
  background: var(--bg-rail);
  color: var(--ink-3);
  margin-left: 4px;
}
.admin-pill-on  { background: var(--accent-bg); color: var(--accent); }
.admin-pill-off { background: var(--bg-rail);   color: var(--ink-3);  }

.admin-row-edit summary {
  list-style: none;
  cursor: pointer;
  padding: 4px 0;
}
.admin-row-edit summary::-webkit-details-marker { display: none; }
.admin-row-edit[open] summary::after { content: ' (close)'; color: var(--ink-4); font-size: 11px; }
.admin-row-edit:not([open]) summary::after { content: ' ›'; color: var(--ink-4); }

.admin-danger { color: var(--danger) !important; }
.admin-danger:hover { color: #7f2618 !important; }

.admin-empty {
  color: var(--ink-3);
  font-size: 14px;
  font-style: italic;
}

/* ---------- Preset list (admin/presets) ---------- */
.preset-list { list-style: none; margin: 0; padding: 0; }
.preset-row {
  border-bottom: 1px solid var(--line-soft);
}
.preset-row:last-child { border-bottom: none; }
.preset-details summary {
  list-style: none;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 14px;
  padding: 12px 4px;
}
.preset-details summary::-webkit-details-marker { display: none; }
.preset-details[open] summary { border-bottom: 1px dashed var(--line-soft); }
.preset-summary-main { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.preset-summary-label { color: var(--ink-1); font-weight: 500; }
.preset-summary-desc {
  font-size: 12px;
  color: var(--ink-3);
}
.preset-summary-meta { display: flex; gap: 4px; flex-shrink: 0; }
.preset-edit-form { padding: 14px 4px 0; }
.preset-edit-form textarea.admin-html {
  width: 100%;
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-size: 12.5px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 10px 12px;
  resize: vertical;
}
.preset-edit-form textarea.admin-html:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
  background: #fff;
}
.preset-edit-actions {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-top: 6px;
  padding: 0 4px 14px;
}

/* The same admin-html textarea on the create form too */
.admin-card .admin-html {
  width: 100%;
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-size: 12.5px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 10px 12px;
  resize: vertical;
}
.admin-card .admin-html:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
  background: #fff;
}

/* Disabled buttons in the admin must LOOK disabled — the app has no
   global .btn:disabled on purpose (app-side disabled buttons get
   bespoke treatment), but in admin a full-strength disabled button
   reads as clickable and fails silently (the Auto-poster scan button
   taught us that). */
.admin-main .btn:disabled {
  opacity: .45;
  cursor: not-allowed;
}

/* ------------------------------------------------------------
   Admin styles consolidated here from marketing.css (2026-07 admin
   redesign) so the whole admin surface lives in one place and shares
   ONE responsive breakpoint (900px). marketing.css keeps only truly
   public-facing rules.
   ------------------------------------------------------------ */

/* Horizontal underline tabs (support queue filter, etc.) */
.admin-tab-strip {
  display: flex;
  gap: 4px;
  margin-bottom: 18px;
  border-bottom: 1px solid var(--line-soft);
}
.admin-tab-link {
  padding: 10px 18px;
  color: var(--ink-3);
  text-decoration: none;
  font-size: 14px;
  font-weight: 500;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
  display: inline-flex;
  align-items: center;
  gap: 8px;
}
.admin-tab-link:hover { color: var(--ink-1); }
.admin-tab-link.is-active {
  color: var(--ink-1);
  border-bottom-color: var(--accent);
}
.admin-tab-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 18px;
  height: 18px;
  padding: 0 6px;
  border-radius: 999px;
  background: var(--accent);
  color: #fff;
  font-size: 11px;
  font-weight: 600;
}

.admin-row-unread { background: rgba(139, 105, 20, 0.04); }
.admin-row-unread strong { color: var(--ink-1); font-weight: 600; }
.admin-unread-dot {
  display: inline-block;
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--accent);
}
.admin-row-sub {
  display: block;
  font-size: 12px;
  color: var(--ink-3);
  margin-top: 2px;
}
.admin-link { color: var(--ink-1); text-decoration: none; }
.admin-link:hover { color: var(--accent); }
/* Legacy back-link (pre-redesign pages); superseded by
   .admin-page-backlink in the shared header partial. */
.admin-back-link {
  display: inline-block;
  margin-bottom: 8px;
  color: var(--ink-3);
  text-decoration: none;
  font-size: 13px;
}
.admin-back-link:hover { color: var(--ink-1); }

.admin-message-body {
  font-family: var(--font-serif);
  font-size: 15.5px;
  line-height: 1.65;
  color: var(--ink-1);
  background: var(--bg-page);
  border: 1px solid var(--line-soft);
  border-radius: 8px;
  padding: 24px;
  margin: 18px 0;
  white-space: pre-wrap;
  word-wrap: break-word;
}
.admin-card-foot {
  display: flex;
  flex-direction: column;
  gap: 14px;
  padding-top: 18px;
  border-top: 1px solid var(--line-soft);
}
.admin-message-meta {
  display: flex;
  gap: 24px;
  font-size: 12px;
  color: var(--ink-3);
  flex-wrap: wrap;
}
.admin-message-meta code {
  background: var(--bg-rail);
  padding: 1px 6px;
  border-radius: 3px;
  font-size: 11.5px;
}

.admin-h3 {
  font-family: var(--font-sans);
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-2);
  margin: 24px 0 10px;
}
.admin-h3:first-child { margin-top: 0; }
.admin-help-strong {
  font-size: 13.5px;
  font-weight: 500;
  color: var(--ink-2);
  margin: 12px 0 6px;
}
.admin-help {
  font-size: 12.5px;
  color: var(--ink-3);
  margin: 6px 0 0;
}

.admin-code-block {
  background: #1a1815;
  color: #ebe6d8;
  padding: 12px 14px;
  border-radius: 6px;
  font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
  font-size: 12px;
  line-height: 1.5;
  margin: 0 0 14px;
  overflow-x: auto;
  white-space: pre;
  word-wrap: normal;
}

.admin-cron-wire {
  padding: 18px;
  background: var(--bg-page);
  border: 1px solid var(--line-soft);
  border-radius: 8px;
  margin: 18px 0;
}
.admin-cron-url-row {
  display: flex;
  gap: 8px;
  align-items: center;
  margin: 6px 0 4px;
}
.admin-cron-url {
  flex: 1;
  padding: 8px 10px;
  font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
  font-size: 12px;
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: 6px;
  color: var(--ink-1);
}
.admin-cron-status {
  padding: 18px;
  background: var(--bg-page);
  border: 1px solid var(--line-soft);
  border-radius: 8px;
}
.admin-cron-status-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  grid-template-columns: 1fr;
  gap: 10px;
}
.admin-cron-status-list li {
  display: grid;
  grid-template-columns: 110px 1fr;
  align-items: baseline;
  gap: 12px;
  font-size: 13.5px;
  color: var(--ink-1);
}
.admin-cron-label {
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
.admin-cron-error {
  font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
  font-size: 12px;
  color: var(--danger);
  word-break: break-word;
}

/* Compact admin card variant (Email/SMTP, test-send). */
.admin-card-tight { padding-top: 18px; padding-bottom: 18px; }

/* Logs viewer (Site settings → Logs) */
.admin-log-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 18px;
  font-size: 12.5px;
  color: var(--ink-3);
  padding: 10px 14px;
  background: var(--bg-rail);
  border: 1px solid var(--line-soft);
  border-radius: 6px;
  margin: 0 0 14px;
}
.admin-log-meta code {
  background: var(--bg-card);
  padding: 1px 6px;
  border-radius: 3px;
  font-size: 11.5px;
}
.admin-log-meta strong { color: var(--ink-1); font-weight: 600; }
.admin-log-truncated {
  background: #fbf1cf;
  color: #6b5210;
  border: 1px solid #efdf95;
  padding: 8px 12px;
  border-radius: 6px;
  font-size: 12.5px;
  margin-bottom: 10px;
}
.admin-log {
  background: #1a1815;
  color: #ebe6d8;
  padding: 16px 18px;
  border-radius: 6px;
  font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
  font-size: 12px;
  line-height: 1.6;
  margin: 0;
  max-height: 70vh;
  overflow: auto;
  white-space: pre-wrap;
  word-break: break-word;
}
:root[data-theme="dark"] .admin-log { background: #0e0d0b; }

/* Settings-page vertical tab rail (plain ?tab= anchors, no JS). */
.admin-tabs {
  display: grid;
  grid-template-columns: 200px 1fr;
  gap: 24px;
  align-items: flex-start;
}
.admin-tabs-rail {
  display: flex;
  flex-direction: column;
  gap: 2px;
  position: sticky;
  top: 24px;
}
.admin-tab-rail-link {
  display: block;
  padding: 10px 14px;
  border-radius: 6px;
  color: var(--ink-2);
  text-decoration: none;
  font-size: 14px;
  font-weight: 500;
  background: transparent;
  border: 1px solid transparent;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.admin-tab-rail-link:hover {
  background: var(--bg-card);
  color: var(--ink-1);
}
.admin-tab-rail-link.is-active {
  background: var(--accent);
  color: #ffffff;
  border-color: var(--accent);
}
.admin-tabs-pane { min-width: 0; }

/* Collapsible sidebar groups */
.admin-nav-section { margin-top: 2px; }
.admin-nav-section:first-child { margin-top: 0; }
.admin-nav-group-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  background: transparent;
  border: none;
  padding: 14px 18px 6px;
  font-size: 10.5px;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: #6c655a;
  font-weight: 600;
  text-align: left;
  cursor: pointer;
  font-family: inherit;
  transition: color .12s ease;
}
.admin-nav-section:first-child .admin-nav-group-header { padding-top: 12px; }
.admin-nav-group-header:hover { color: #8a857a; }
.admin-nav-chevron {
  font-size: 11px;
  color: #6c655a;
  transition: transform .15s ease;
}
.admin-nav-section.is-collapsed .admin-nav-chevron { transform: rotate(-90deg); }
.admin-nav-group-items {
  list-style: none;
  margin: 0;
  padding: 0;
  max-height: 600px;
  overflow: hidden;
  transition: max-height .2s ease;
}
.admin-nav-section.is-collapsed .admin-nav-group-items { max-height: 0; }

/* Legacy sidebar count badge — superseded by .admin-badge; kept only
   until every view stops referencing it (cleanup pass). */
.admin-nav-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 20px;
  height: 18px;
  padding: 0 6px;
  margin-left: 8px;
  border-radius: 999px;
  background: var(--accent);
  color: #fff;
  font-size: 11px;
  font-weight: 700;
  line-height: 1;
}
.admin-nav-badge-inline { margin-left: 8px; }

/* ------------------------------------------------------------
   Admin — the ONE responsive breakpoint. Sidebar becomes a wrapping
   pill row: filter + group headers hidden, collapse disabled (the
   sections and lists flatten via display:contents so every link is
   a direct flex item of .admin-nav-list).
   ------------------------------------------------------------ */
@media (max-width: 900px) {
  .admin-shell { grid-template-columns: 1fr; }
  .admin-nav {
    position: static;
    height: auto;
    overflow: visible;
    flex-direction: row;
    padding: 10px;
    gap: 8px;
    flex-wrap: wrap;
  }
  .admin-nav-head { border-bottom: none; padding: 0 8px; flex-direction: row; align-items: center; gap: 8px; flex-wrap: wrap; }
  /* On mobile the header is a row and the footer (its old home) is
     hidden, so let the sign-out button sit inline without the desktop
     indent — and push it to the far right. */
  .admin-nav-head-signout-form { margin: 0 0 0 auto; }
  .admin-nav-filter { display: none; }
  .admin-nav-list { display: flex; gap: 4px; flex: 1; flex-wrap: wrap; margin: 0; }
  .admin-nav-section,
  .admin-nav-group-items,
  .admin-nav-group-items li { display: contents; }
  /* display:contents would defeat the UA's [hidden] rule — keep
     filtered-out links hidden if the viewport shrinks mid-filter. */
  .admin-nav-group-items li[hidden] { display: none; }
  .admin-nav-group-header { display: none; }
  .admin-nav-link { padding: 6px 12px; border-radius: 999px; gap: 6px; }
  .admin-nav-link.is-active {
    background: var(--accent);
    color: #fff;
    box-shadow: none;
  }
  .admin-nav-link.is-active .admin-nav-icon { color: #fff; }
  .admin-nav-foot { display: none; }
  .admin-main { padding: 18px 16px 60px; }
  .admin-form-grid { grid-template-columns: 1fr; }
  .admin-tabs { grid-template-columns: 1fr; gap: 16px; }
  .admin-tabs-rail { position: static; flex-direction: row; flex-wrap: wrap; }
  .admin-recent-grid { grid-template-columns: 1fr; }
}

/* ============================================================
   Responsive
   ============================================================ */
@media (max-width: 1180px) {
  .editor-body-grid { grid-template-columns: 244px 1fr 56px; }
  .editor-body-grid.is-panel-open { grid-template-columns: 244px 1fr 260px 56px; }
  .page-sheet { padding: 40px 48px 60px; }
  .format-body[data-mode="gallery"] {
    grid-template-columns: 1fr;
    grid-template-areas:
      "gallery"
      "side";
    gap: 24px;
  }
  .format-body[data-mode="editor"] {
    grid-template-columns: 1fr;
    grid-template-areas:
      "bar"
      "nav"
      "editor"
      "side";
    gap: 16px;
  }
  .format-side { position: static; }
  .format-editor-nav { position: static; }
  .format-editor-nav ul { display: flex; flex-wrap: wrap; }
  .format-editor-nav li { flex: 1 1 auto; }
  .format-editor-nav-btn { padding: 8px 12px; }
}
@media (max-width: 900px) {
  .editor-body-grid { grid-template-columns: 220px 1fr 48px; }
  .editor-body-grid.is-panel-open { grid-template-columns: 220px 1fr 260px 48px; }
  .editor-topbar { grid-template-columns: 1fr auto auto; gap: 8px; }
  .topbar-title-text { max-width: 160px; font-size: 14px; }
  .btn-edit-details { display: none; }
  .editor-topbar .topbar-right { gap: 8px; }
}
@media (max-width: 1100px) {
  .details-grid { grid-template-columns: 1fr; }
  .details-rail { position: static; }
  .details-form-grid { grid-template-columns: 1fr; }
}
@media (max-width: 680px) {
  .editor-body-grid { grid-template-columns: 1fr; }
  .editor-body-grid.is-panel-open { grid-template-columns: 1fr; }
  .chapter-sidebar { display: none; }
  .icon-rail { display: none; }
  .rail-panel { display: none; }
  .page-sheet { padding: 28px 22px 48px; }
  .library { padding: 24px 16px 60px; }
  .library-hero { flex-direction: column; align-items: flex-start; }
  .book-grid { grid-template-columns: repeat(auto-fill, minmax(140px, 1fr)); gap: 24px 16px; }
  .modal-grid { grid-template-columns: 1fr; }
  .details-main { padding: 16px 16px 60px; }
  .details-tab-pane { padding: 22px 18px 24px; }
  .details-form-grid { gap: 24px; }
}

/* ============================================================
   Scratchpad — persistent right-edge notes panel.

   A vertical "SCRATCHPAD" tab is always visible. Clicking slides
   a panel in from the right (translateX on .scratchpad-panel).
   The whole thing is position:fixed at z:1000 so it overlays
   every sticky toolbar, modal, dropdown, and confirm dialog the
   app uses (topmost in-app layer is z:500 for toasts).

   Markup is rendered in layout.php only when Auth::check(), so
   public pages (marketing/share/auth/maintenance) never see it.
   ============================================================ */
#scratchpad {
  position: fixed;
  top: 0;
  right: 0;
  height: 100vh;
  z-index: 1000;
  display: flex;
  align-items: flex-start;
  pointer-events: none; /* panel + tab each opt-in below */
  font-family: var(--font-sans);
}
.scratchpad-tab,
.scratchpad-panel { pointer-events: auto; }

.scratchpad-tab {
  position: absolute;
  /* Anchored to the lower-right corner rather than vertical-center so it
     clears the editor's icon-rail (whose buttons cluster at the top) and
     sits above the bottom status bar — covering nothing on any page. */
  top: auto;
  bottom: 72px;
  right: 0;
  /* vertical-rl + rotate(180deg) makes the label read bottom-to-top */
  writing-mode: vertical-rl;
  transform-origin: center;
  -webkit-appearance: none;
  appearance: none;
  background: var(--bg-topbar);
  color: #f5f1e6;
  border: 1px solid var(--bg-topbar);
  border-right: none;
  border-radius: var(--radius) 0 0 var(--radius);
  padding: 18px 6px;
  font-size: 11.5px;
  font-weight: 600;
  letter-spacing: .22em;
  cursor: pointer;
  box-shadow: -2px 2px 10px rgba(0,0,0,.18);
  transition: background .15s ease, color .15s ease, transform .15s ease;
}
.scratchpad-tab:hover { background: #000; }
.scratchpad-tab:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}
.scratchpad-tab-label {
  writing-mode: vertical-rl;
  transform: rotate(180deg);
  display: inline-block;
}

/* Panel sits offscreen by default; .is-open slides it in. */
.scratchpad-panel {
  width: 360px;
  height: 100vh;
  background: var(--bg-card);
  border-left: 1px solid var(--line);
  box-shadow: -8px 0 24px rgba(0,0,0,.12);
  display: flex;
  flex-direction: column;
  transform: translateX(100%);
  /* .scratchpad-ready is added one frame after load so the initial
     paint doesn't animate when the panel was already open on reload. */
}
#scratchpad.scratchpad-ready .scratchpad-panel {
  transition: transform 260ms ease;
}
#scratchpad.is-open .scratchpad-panel {
  transform: translateX(0);
}
/* When open, the tab rides the panel's left edge. */
#scratchpad.is-open .scratchpad-tab {
  right: 360px;
}
#scratchpad.scratchpad-ready .scratchpad-tab {
  transition: right 260ms ease, background .15s ease;
}

.scratchpad-head {
  display: flex;
  align-items: center;
  gap: 10px;
  background: var(--bg-topbar);
  color: #f5f1e6;
  padding: 10px 14px;
  border-bottom: 1px solid var(--bg-topbar-soft);
}
.scratchpad-title {
  font-family: var(--font-display);
  font-size: 14px;
  font-weight: 600;
  letter-spacing: .02em;
  flex: 1;
  /* min-width:0 lets the flex item shrink so the active pad name can
     ellipsize instead of shoving the status pill + Clear off the edge. */
  min-width: 0;
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}
.scratchpad-title-brand { flex: 0 0 auto; }
/* The active pad's name, appended after "Scratchpad ·". Slightly lighter
   than the brand so the two read as label + value. */
.scratchpad-title-pad { font-weight: 500; opacity: .82; }
.scratchpad-status {
  font-size: 11.5px;
  letter-spacing: .04em;
  opacity: .7;
  font-variant-numeric: tabular-nums;
}
.scratchpad-status[data-state="loading"] { color: var(--accent-soft); opacity: 1; }
.scratchpad-status[data-state="saving"]  { color: var(--accent-soft); opacity: 1; }
.scratchpad-status[data-state="saved"]   { color: #cfe6b5; opacity: .9; }
.scratchpad-status[data-state="empty"]   { opacity: .5; }
.scratchpad-status[data-state="error"]   { color: #f0a99d; opacity: 1; }
.scratchpad-clear {
  background: transparent;
  border: 1px solid rgba(255,255,255,.18);
  color: #f5f1e6;
  border-radius: var(--radius-sm);
  padding: 4px 10px;
  font-size: 12px;
  font-family: inherit;
  cursor: pointer;
  transition: background .12s ease, border-color .12s ease;
}
.scratchpad-clear:hover {
  background: rgba(255,255,255,.08);
  border-color: rgba(255,255,255,.32);
}

/* Rich-text scratchpad (contenteditable). Sans-serif by default — the
   point of preserving paste formatting is that the source typography
   carries through, so a monospace base font fights it. The mono font
   is reused only for code-ish content via <code>/<pre> below. */
.scratchpad-content {
  flex: 1;
  width: 100%;
  border: none;
  outline: none;
  padding: 14px 16px;
  background: var(--bg-paper);
  color: var(--ink-1);
  font-family: var(--font-sans, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif);
  font-size: 13.5px;
  line-height: 1.55;
  /* pre-wrap preserves whitespace from plaintext pastes (legacy data
     stored as raw text still reads correctly); overflow-wrap: anywhere
     handles long URLs / unbreakable tokens. */
  white-space: pre-wrap;
  overflow-wrap: anywhere;
  overflow: auto;
  cursor: text;
}
/* CSS-only placeholder. :empty matches when the contenteditable has
   nothing in it; the load handler in scratchpad.js sets innerHTML=""
   for empty state so this kicks in cleanly. */
.scratchpad-content:empty::before {
  content: attr(data-placeholder);
  color: var(--ink-4);
  font-family: var(--font-sans);
  font-size: 12.5px;
  line-height: 1.5;
  pointer-events: none;
}
.scratchpad-content:focus {
  background: var(--bg-card);
}
/* While loading, scratchpad.js sets contenteditable="false". We lean
   on that attribute for the disabled visual cue (consistent with
   form controls). */
.scratchpad-content[contenteditable="false"] {
  cursor: progress;
  opacity: .55;
}
/* Rich-text formatting inside the scratchpad — keep it readable in
   the narrow panel. Headings step down in size relative to a normal
   article so an H1 paste doesn't blow out the panel. */
.scratchpad-content h1,
.scratchpad-content h2,
.scratchpad-content h3,
.scratchpad-content h4 {
  font-family: var(--font-sans);
  font-weight: 600;
  margin: 12px 0 6px;
  line-height: 1.25;
  color: var(--ink-1);
}
.scratchpad-content h1 { font-size: 15.5px; }
.scratchpad-content h2 { font-size: 14.5px; }
.scratchpad-content h3 { font-size: 13.8px; }
.scratchpad-content h4 { font-size: 13.3px; }
.scratchpad-content p { margin: 0 0 8px; }
.scratchpad-content ul,
.scratchpad-content ol { margin: 4px 0 8px; padding-left: 1.4em; }
.scratchpad-content li { margin: 2px 0; }
/* Some sources (Google Docs, rendered markdown) wrap each list item's
   text in its own <p>. Without this the <p>'s bottom margin stacks on
   top of the <li> margin and every bullet gets a blank line under it. */
.scratchpad-content li > p { margin: 0; }
.scratchpad-content a { color: var(--accent); text-decoration: underline; }
.scratchpad-content blockquote {
  border-left: 2px solid var(--line);
  padding-left: 10px;
  margin: 6px 0;
  color: var(--ink-2);
}
.scratchpad-content code,
.scratchpad-content pre {
  font-family: var(--font-mono, ui-monospace, SFMono-Regular, Menlo, Consolas, monospace);
  background: rgba(0,0,0,0.04);
  border-radius: 3px;
}
.scratchpad-content code { padding: 1px 4px; font-size: 12.5px; }
.scratchpad-content pre {
  padding: 8px 10px;
  overflow-x: auto;
  font-size: 12.5px;
  line-height: 1.5;
}
.scratchpad-content img {
  max-width: 100%;
  height: auto;
  border-radius: 4px;
}

/* Pad tabs (migration 072) — the strip of pills under the header that
   switches between up to 4 independent pads. Same pill idiom as the
   KDP pane tabs, on its own class names: these must NOT be
   .scratchpad-tab (that's the drawer's edge toggle, and todo.js's
   one-drawer-at-a-time clicks the first .scratchpad-tab:not(.todo-tab)).
   The To-Do drawer shares .scratchpad-panel/.scratchpad-head but never
   renders a .scratchpad-pads node, so none of this leaks into it. */
.scratchpad-pads {
  display: flex;
  align-items: center;
  gap: 6px;
  padding: 8px 10px 6px;
  border-bottom: 1px solid var(--line);
  background: var(--bg-card);
  overflow-x: auto;
  flex: 0 0 auto;
}
.scratchpad-pad-tab {
  font: inherit;
  font-size: 12px;
  line-height: 1.4;
  padding: 3px 10px;
  border: 1px solid var(--line);
  border-radius: 999px;
  background: var(--bg-card);
  color: var(--ink-3);
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  gap: 6px;
  max-width: 118px;
  flex: 0 0 auto;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.scratchpad-pad-tab .scratchpad-pad-label {
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}
.scratchpad-pad-tab:hover { color: var(--ink-1); border-color: var(--ink-4); }
.scratchpad-pad-tab.is-active {
  background: var(--accent-bg);
  border-color: var(--accent-soft);
  color: var(--ink-1);
  font-weight: 600;
}
.scratchpad-pad-del {
  opacity: .55;
  font-weight: 400;
  padding: 0 1px;
}
.scratchpad-pad-del:hover { opacity: 1; color: var(--danger, #c0392b); }
.scratchpad-pad-add {
  font: inherit;
  font-size: 13px;
  line-height: 1;
  width: 24px;
  height: 24px;
  border: 1px dashed var(--line);
  border-radius: 999px;
  background: none;
  color: var(--ink-3);
  cursor: pointer;
  flex: 0 0 auto;
}
.scratchpad-pad-add:hover { color: var(--ink-1); border-color: var(--ink-4); }
.scratchpad-pad-rename {
  font: inherit;
  font-size: 12px;
  width: 92px;
  padding: 1px 6px;
  border: 1px solid var(--accent-soft);
  border-radius: 999px;
  background: var(--bg-paper);
  color: var(--ink-1);
  outline: none;
}

@media (max-width: 820px) {
  .scratchpad-panel { width: 80vw; }
  #scratchpad.is-open .scratchpad-tab { right: 80vw; }
}

/* Dark theme — the cream paper feel reads wrong on the dark app
   shell. Swap to the inky surfaces so the panel sits naturally
   above the editor and admin pages. Everything else in the drawer
   (content, pad pills) is var()-driven and needs no override. */
:root[data-theme="dark"] .scratchpad-panel {
  background: var(--bg-card);
  border-left-color: var(--line);
  box-shadow: -8px 0 24px rgba(0,0,0,.45);
}

/* ============================================================
   Codex drawer — left-edge slideout for the story codex.

   The mirror image of the scratchpad: a vertical "CODEX" tab pinned
   to the LEFT edge slides a panel in from the left (translateX). It
   hosts the same .bible-* sidebar/form that bible.js drives, so the
   codex is available while writing without leaving the page. Only
   rendered inside the editor (see editor.php); position:fixed at
   z:1000 so it overlays the editor chrome, matching the scratchpad.

   Left edge is deliberate — the scratchpad owns the right edge, so
   the two never collide and can be open at the same time.
   ============================================================ */
.codex-drawer {
  position: fixed;
  top: 0;
  left: 0;
  height: 100vh;
  z-index: 1000;
  display: flex;
  align-items: flex-start;
  pointer-events: none; /* tab + panel each opt-in below */
  font-family: var(--font-sans);
}
.codex-drawer-tab,
.codex-drawer-panel { pointer-events: auto; }

.codex-drawer-tab {
  position: absolute;
  /* Sit clear of the left chapter-sidebar's footer cluster (the tall
     "Add new chapter" + auto-number + recalc stack, ~115px), so the tab
     floats over the scrollable chapter list rather than on top of those
     buttons. That footer is why this sits higher than the scratchpad tab
     (bottom:72px), which only has to clear the 40px manuscript footer. */
  top: auto;
  bottom: 132px;
  left: 0;
  writing-mode: vertical-rl;
  -webkit-appearance: none;
  appearance: none;
  background: var(--bg-topbar);
  color: #f5f1e6;
  border: 1px solid var(--bg-topbar);
  border-left: none;
  border-radius: 0 var(--radius) var(--radius) 0;
  padding: 18px 6px;
  font-size: 11.5px;
  font-weight: 600;
  letter-spacing: .22em;
  cursor: pointer;
  box-shadow: 2px 2px 10px rgba(0,0,0,.18);
  transition: background .15s ease, color .15s ease;
}
.codex-drawer-tab:hover { background: #000; }
.codex-drawer-tab:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}
.codex-drawer-tab-label {
  writing-mode: vertical-rl;
  transform: rotate(180deg);
  display: inline-block;
}

/* Panel sits offscreen to the left by default; .is-open slides it in. */
.codex-drawer-panel {
  width: 720px;
  max-width: 96vw;
  height: 100vh;
  background: var(--bg-card);
  border-right: 1px solid var(--line);
  box-shadow: 8px 0 24px rgba(0,0,0,.12);
  display: flex;
  flex-direction: column;
  transform: translateX(-100%);
  /* .codex-drawer-ready is added one frame after load so a drawer that
     was open on the last visit doesn't animate on the initial paint. */
}
#codex-drawer.codex-drawer-ready .codex-drawer-panel {
  transition: transform 260ms ease;
}
#codex-drawer.is-open .codex-drawer-panel {
  transform: translateX(0);
}
/* When open, the tab rides the panel's right edge. min() keeps it glued
   to that edge even when the 96vw max-width clamps the panel narrower. */
#codex-drawer.is-open .codex-drawer-tab {
  left: min(720px, 96vw);
}
#codex-drawer.codex-drawer-ready .codex-drawer-tab {
  transition: left 260ms ease, background .15s ease;
}

.codex-drawer-head {
  display: flex;
  align-items: center;
  gap: 10px;
  background: var(--bg-topbar);
  color: #f5f1e6;
  padding: 10px 14px;
  border-bottom: 1px solid var(--bg-topbar-soft);
  flex: 0 0 auto;
}
.codex-drawer-title {
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .18em;
}
.codex-drawer-close {
  margin-left: auto;
  -webkit-appearance: none;
  appearance: none;
  background: transparent;
  border: none;
  color: #f5f1e6;
  font-size: 22px;
  line-height: 1;
  cursor: pointer;
  padding: 0 4px;
  opacity: .8;
  transition: opacity .12s ease;
}
.codex-drawer-close:hover { opacity: 1; }

/* Body hosts the existing .bible-sidebar + .bible-main as a two-pane
   grid. min-height:0 lets the panes scroll internally instead of
   pushing the panel taller than the viewport. */
.codex-drawer-body {
  flex: 1 1 auto;
  min-height: 0;
  display: grid;
  grid-template-columns: 300px 1fr;
  overflow: hidden;
}
/* The main pane's full-page padding is too generous inside the narrower
   drawer — tighten it so the form fields have room to breathe. */
.codex-drawer .bible-main { padding: 24px 28px; }
.codex-drawer .bible-empty-state { margin: 56px auto; }

@media (max-width: 640px) {
  .codex-drawer-panel { width: 100vw; max-width: 100vw; }
  /* At full width the left-anchored tab would vanish offscreen, so when
     open, flip it to the right edge where it stays reachable. */
  #codex-drawer.is-open .codex-drawer-tab {
    left: auto;
    right: 0;
    border-radius: var(--radius) 0 0 var(--radius);
    border-left: 1px solid var(--bg-topbar);
    border-right: none;
  }
  /* Stack the two panes vertically on phones — a 300px sidebar would
     leave the form almost no room. */
  .codex-drawer-body {
    grid-template-columns: 1fr;
    grid-template-rows: minmax(120px, 38%) 1fr;
  }
  .codex-drawer .bible-sidebar {
    border-right: none;
    border-bottom: 1px solid var(--line);
  }
}

/* Dark theme — same treatment as the scratchpad panel. */
:root[data-theme="dark"] .codex-drawer-panel {
  border-right-color: var(--line);
  box-shadow: 8px 0 24px rgba(0,0,0,.45);
}

/* ============================================================
   Admin-broadcast announcement banner.
   Renders at the top of every authenticated page until dismissed.
   Three tints (info/success/warning) match the kinds in the
   announcements table. Banner flows with the page (not sticky) so
   it doesn't permanently steal vertical space in the editor.
   ============================================================ */
.app-announcement {
  display: flex;
  align-items: flex-start;
  justify-content: center;
  gap: 14px;
  padding: 12px 22px;
  font-family: var(--font-sans);
  font-size: 14px;
  line-height: 1.5;
  border-bottom: 1px solid var(--line);
  transition: opacity .2s ease, transform .2s ease;
  /* z-index keeps it above any sticky topbar that might cover it */
  position: relative;
  z-index: 80;
}
.app-announcement.is-dismissing {
  opacity: 0;
  transform: translateY(-6px);
}
.app-announcement-content {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: center;
  gap: 6px 14px;
  flex: 1;
  max-width: 1100px;
  text-align: center;
}
.app-announcement-title {
  font-weight: 600;
  color: var(--ink-1);
}
.app-announcement-body {
  color: var(--ink-2);
}
.app-announcement-cta {
  font-weight: 600;
  text-decoration: none;
  white-space: nowrap;
  padding: 2px 0;
  border-bottom: 1px solid currentColor;
  transition: opacity .12s ease;
}
.app-announcement-cta:hover { opacity: .75; }
.app-announcement-dismiss {
  flex: 0 0 auto;
  width: 28px;
  height: 28px;
  border-radius: 50%;
  border: none;
  background: transparent;
  color: var(--ink-3);
  font-size: 20px;
  line-height: 1;
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  margin-top: -2px;
  transition: background .12s ease, color .12s ease;
}
.app-announcement-dismiss:hover {
  background: rgba(0, 0, 0, .08);
  color: var(--ink-1);
}
.app-announcement-dismiss:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}

/* Kind tints. Backgrounds picked to read clearly in both light
   and dark themes (dark-theme overrides further down). */
.app-announcement-info {
  background: #eef4f9;
  border-bottom-color: #cfdee9;
}
.app-announcement-info .app-announcement-cta { color: #1f4a6a; }

.app-announcement-success {
  background: #eef7ec;
  border-bottom-color: #cfe2c4;
}
.app-announcement-success .app-announcement-cta { color: #2d5a1f; }

.app-announcement-warning {
  background: var(--accent-bg);
  border-bottom-color: color-mix(in srgb, var(--accent) 40%, transparent);
}
.app-announcement-warning .app-announcement-cta { color: var(--accent); }

/* Snooze controls inside the Amazon ad-campaign reminder banner. The
   "Snooze" button reuses .app-announcement-cta but is a <button>, so
   strip the native chrome to match the adjacent link CTA. */
button.app-announcement-cta {
  background: none;
  border: none;
  border-bottom: 1px solid currentColor;
  cursor: pointer;
  font: inherit;
}
.app-campaign-reminder-snooze {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  white-space: nowrap;
}
.app-campaign-reminder-snooze-label {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  color: var(--ink-2);
  font-size: .92em;
}
.app-campaign-reminder-date {
  font: inherit;
  padding: 2px 6px;
  border: 1px solid color-mix(in srgb, var(--ink-3) 50%, transparent);
  border-radius: 6px;
  background: var(--surface-1, #fff);
  color: var(--ink-1);
}

:root[data-theme="dark"] .app-announcement-info {
  background: #1d2934;
  border-bottom-color: #2f4253;
}
:root[data-theme="dark"] .app-announcement-info .app-announcement-cta { color: #82b3da; }
:root[data-theme="dark"] .app-announcement-success {
  background: #1f2c1f;
  border-bottom-color: #3a4f3a;
}
:root[data-theme="dark"] .app-announcement-success .app-announcement-cta { color: #93c777; }
:root[data-theme="dark"] .app-announcement-warning {
  background: #2c2516;
  border-bottom-color: color-mix(in srgb, var(--accent) 50%, transparent);
}
:root[data-theme="dark"] .app-announcement-dismiss:hover {
  background: rgba(255, 255, 255, .08);
}

@media (max-width: 640px) {
  .app-announcement { padding: 10px 14px; font-size: 13px; gap: 10px; }
  .app-announcement-content { text-align: left; justify-content: flex-start; }
}

/* ============================================================
   Sources view (Workshop → Sources: bibliography manager)
   Two-pane layout mirroring the Bible view: a grouped source
   list on the left, an edit form on the right.
   ============================================================ */
.editor-view.sources-view {
  display: grid;
  grid-template-columns: 320px 1fr;
  grid-template-rows: auto 1fr;
  background: var(--bg-page);
  overflow: hidden;
}
.sources-view[hidden] { display: none !important; }
.sources-view > .subview-tabs { grid-column: 1 / -1; }

/* ----- Sidebar ----- */
.sources-sidebar {
  display: flex;
  flex-direction: column;
  background: #fff;
  border-right: 1px solid var(--line);
  overflow: hidden;
}
.sources-sidebar-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 18px 10px;
  border-bottom: 1px solid var(--line);
}
.sources-sidebar-title {
  margin: 0;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .14em;
  color: var(--ink-2);
}
.sources-sidebar-search {
  padding: 10px 14px;
  border-bottom: 1px solid var(--line-soft);
}
.sources-sidebar-search input {
  width: 100%;
  padding: 8px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13px;
  background: var(--bg-paper);
}
.sources-sidebar-search input:focus { outline: none; border-color: var(--accent); }
.sources-sidebar-scroll {
  flex: 1;
  overflow-y: auto;
  padding: 8px 0 16px;
}
.sources-empty {
  padding: 18px 16px;
  margin: 0;
  font-size: 13px;
  color: var(--ink-3);
  font-style: italic;
}
.sources-group { margin: 12px 0 6px; }
.sources-group-head {
  margin: 0;
  padding: 6px 18px;
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
  display: flex;
  align-items: center;
  gap: 6px;
}
.sources-group-head .sources-count {
  margin-left: auto;
  font-weight: 500;
  color: var(--ink-3);
  font-size: 10.5px;
}
.sources-group-list { list-style: none; margin: 4px 0; padding: 0; }
.sources-row {
  padding: 8px 16px 8px 18px;
  border-left: 3px solid transparent;
  cursor: pointer;
  transition: background .12s ease;
}
.sources-row:hover { background: var(--bg-paper); }
.sources-row.is-selected {
  background: #fdf7e8;
  border-left-color: var(--accent);
}
.sources-row-title {
  font-weight: 500;
  color: var(--ink-1);
  font-size: 13.5px;
}
.sources-row-meta {
  font-size: 11.5px;
  color: var(--ink-3);
  margin-top: 2px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* ----- Main / form ----- */
.sources-main { overflow-y: auto; padding: 32px 48px; }
.sources-empty-state {
  max-width: 520px;
  margin: 80px auto;
  text-align: center;
}
.sources-empty-state .empty-mark {
  font-size: 36px;
  color: var(--accent);
  margin-bottom: 12px;
}
.sources-empty-state .empty-heading {
  font-family: var(--font-display);
  font-size: 28px;
  margin: 0 0 12px;
}
.sources-empty-state .empty-sub {
  color: var(--ink-3);
  margin: 0 0 24px;
  line-height: 1.55;
}

.sources-form {
  max-width: 820px;
  margin: 0 auto;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  box-shadow: var(--shadow-paper);
  overflow: hidden;
}
.sources-form-head {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: 16px;
  align-items: start;
  padding: 18px 22px;
  border-bottom: 1px solid var(--line);
  background: var(--bg-paper);
}
.sources-form-head-fields { display: flex; flex-direction: column; gap: 10px; min-width: 0; }
.sources-title-input {
  width: 100%;
  font-family: var(--font-display);
  font-size: 21px;
  font-weight: 600;
  padding: 4px 0;
  border: none;
  border-bottom: 1px solid transparent;
  background: transparent;
  color: var(--ink-1);
}
.sources-title-input:focus { outline: none; border-bottom-color: var(--accent); }
.sources-form-row { display: flex; gap: 14px; flex-wrap: wrap; }
.sources-mini-field { display: flex; flex-direction: column; gap: 4px; }
.sources-mini-field > span {
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .1em;
  color: var(--ink-3);
}
.sources-mini-field select,
.sources-mini-field input {
  padding: 6px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13px;
  background: #fff;
}
.sources-mini-field select:focus,
.sources-mini-field input:focus { outline: none; border-color: var(--accent); }
.sources-mini-field #src-year { width: 80px; }
.sources-key-field { flex: 1; min-width: 140px; }
.sources-key-field input { width: 100%; }

.sources-form-delete {
  width: 34px;
  height: 34px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: #fff;
  color: var(--ink-3);
  cursor: pointer;
}
.sources-form-delete:hover { color: var(--danger); border-color: var(--danger); }

.sources-form-body {
  padding: 22px;
  display: flex;
  flex-direction: column;
  gap: 16px;
}
.sources-field { display: flex; flex-direction: column; gap: 6px; }
.sources-field-label {
  font-family: var(--font-sans);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .1em;
  color: var(--ink-2);
}
.sources-field-hint {
  font-weight: 400;
  text-transform: none;
  letter-spacing: 0;
  color: var(--ink-3);
  font-style: italic;
}
.sources-field input,
.sources-field textarea {
  padding: 8px 11px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13.5px;
  background: var(--bg-paper);
  resize: vertical;
}
.sources-field input:focus,
.sources-field textarea:focus { outline: none; border-color: var(--accent); background: #fff; }
.sources-field-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 16px;
}
.sources-field-grid-3 { grid-template-columns: 1fr 1fr 1fr; }

.sources-preview {
  margin-top: 6px;
  padding: 14px 16px;
  background: var(--bg-paper);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.sources-preview-label {
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
.sources-preview-text {
  margin: 0;
  font-family: var(--font-serif, Georgia, serif);
  font-size: 14px;
  line-height: 1.5;
  color: var(--ink-1);
  text-indent: -1.6em;
  padding-left: 1.6em;
}
.sources-preview-muted { color: var(--ink-3); font-style: italic; }
.sources-preview-note { font-size: 11px; color: var(--ink-3); font-style: italic; }
.sources-form-foot {
  padding: 12px 22px;
  border-top: 1px solid var(--line);
  background: var(--bg-paper);
}
.sources-save-status { font-size: 12px; color: var(--ink-3); }

@media (max-width: 720px) {
  .sources-field-grid,
  .sources-field-grid-3 { grid-template-columns: 1fr; }
}

/* ----- Dark mode ----- */
:root[data-theme="dark"] .sources-sidebar,
:root[data-theme="dark"] .sources-form { background: var(--bg-rail, #1f1d1a); }
:root[data-theme="dark"] .sources-title-input,
:root[data-theme="dark"] .sources-mini-field select,
:root[data-theme="dark"] .sources-mini-field input,
:root[data-theme="dark"] .sources-field input,
:root[data-theme="dark"] .sources-field textarea { background: var(--bg-page); color: var(--ink-1); }
:root[data-theme="dark"] .sources-row.is-selected { background: rgba(255, 255, 255, .05); }

/* ============================================================
   In-text citations (citation Quill embed + picker modal)
   ============================================================ */
/* The atomic citation token inside the editor. Renders as a subtly
   tinted, non-editable chip so it's clearly one unit. In print/EPUB it
   falls back to plain text (those pipelines don't load this CSS). */
.ql-editor .cite-ref {
  background: color-mix(in srgb, var(--accent) 14%, transparent);
  color: var(--ink-1);
  border-radius: 4px;
  padding: 0 3px;
  cursor: default;
  white-space: nowrap;
  box-decoration-break: clone;
  -webkit-box-decoration-break: clone;
}
.ql-editor .cite-ref:hover {
  background: color-mix(in srgb, var(--accent) 24%, transparent);
}

/* The “＂” glyph the citation toolbar button uses reads small; nudge it. */
.ql-toolbar .ql-citation { font-size: 15px; }

/* ----- Picker modal ----- */
.cite-modal { position: fixed; inset: 0; z-index: 1000; }
.cite-modal[hidden] { display: none; }
.cite-modal-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(20, 18, 15, .45);
}
.cite-modal-card {
  position: relative;
  width: min(520px, calc(100vw - 32px));
  max-height: calc(100vh - 80px);
  margin: 56px auto 0;
  display: flex;
  flex-direction: column;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  box-shadow: 0 16px 48px rgba(0, 0, 0, .28);
  overflow: hidden;
}
.cite-modal-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 20px;
  border-bottom: 1px solid var(--line);
}
.cite-modal-title { margin: 0; font-family: var(--font-display); font-size: 18px; }
.cite-modal-close {
  border: none;
  background: none;
  font-size: 24px;
  line-height: 1;
  color: var(--ink-3);
  cursor: pointer;
}
.cite-modal-close:hover { color: var(--ink-1); }
.cite-modal-search { padding: 12px 20px 8px; }
.cite-modal-search input {
  width: 100%;
  padding: 8px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13.5px;
  background: var(--bg-paper);
}
.cite-modal-search input:focus { outline: none; border-color: var(--accent); }
.cite-modal-list {
  flex: 1;
  overflow-y: auto;
  padding: 4px 12px;
  min-height: 80px;
  max-height: 320px;
}
.cite-list-empty { padding: 16px; margin: 0; font-size: 13px; color: var(--ink-3); font-style: italic; }
.cite-source-row {
  display: flex;
  flex-direction: column;
  gap: 2px;
  width: 100%;
  text-align: left;
  padding: 9px 12px;
  border: 1px solid transparent;
  border-radius: var(--radius-sm);
  background: none;
  cursor: pointer;
}
.cite-source-row:hover { background: var(--bg-paper); }
.cite-source-row.is-selected {
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  border-color: var(--accent);
}
.cite-source-title { font-size: 13.5px; font-weight: 500; color: var(--ink-1); }
.cite-source-meta { font-size: 11.5px; color: var(--ink-3); }
.cite-modal-empty { padding: 28px 20px; text-align: center; color: var(--ink-3); }
.cite-modal-empty p { margin: 0 0 12px; font-size: 13.5px; }
.cite-modal-options {
  padding: 12px 20px;
  border-top: 1px solid var(--line-soft);
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.cite-opt-field { display: flex; flex-direction: column; gap: 5px; }
.cite-opt-field > span {
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .1em;
  color: var(--ink-3);
}
.cite-opt-field input {
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13.5px;
  background: var(--bg-paper);
}
.cite-opt-field input:focus { outline: none; border-color: var(--accent); }
.cite-opt-check {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 13px;
  color: var(--ink-1);
  cursor: pointer;
}
.cite-hint { font-weight: 400; text-transform: none; letter-spacing: 0; color: var(--ink-3); font-style: italic; }
.cite-modal-preview {
  padding: 12px 20px;
  border-top: 1px solid var(--line-soft);
  display: flex;
  align-items: baseline;
  gap: 10px;
}
.cite-preview-label {
  font-family: var(--font-sans);
  font-size: 10.5px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--ink-3);
}
.cite-preview-text {
  font-family: var(--font-serif, Georgia, serif);
  font-size: 14.5px;
  color: var(--ink-1);
}
.cite-modal-foot {
  display: flex;
  justify-content: flex-end;
  gap: 8px;
  padding: 14px 20px;
  border-top: 1px solid var(--line);
  background: var(--bg-paper);
}

:root[data-theme="dark"] .cite-modal-card { background: var(--bg-rail, #1f1d1a); }
:root[data-theme="dark"] .cite-modal-search input,
:root[data-theme="dark"] .cite-opt-field input { background: var(--bg-page); color: var(--ink-1); }

/* ============================================================
   Rich footnote editor (footnotes.js popover + mini Quill)
   ============================================================ */
/* Existing footnotes are clickable to re-open the editor. */
.ql-editor sup.fn-ref { cursor: pointer; }
.ql-editor sup.fn-ref:hover { background: color-mix(in srgb, var(--accent) 22%, transparent); border-radius: 3px; }

.fn-modal { position: fixed; inset: 0; z-index: 950; }
.fn-modal[hidden] { display: none; }
.fn-modal-backdrop { position: absolute; inset: 0; background: rgba(20, 18, 15, .45); }
.fn-modal-card {
  position: relative;
  width: min(560px, calc(100vw - 32px));
  margin: 64px auto 0;
  display: flex;
  flex-direction: column;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  box-shadow: 0 16px 48px rgba(0, 0, 0, .28);
  overflow: hidden;
}
.fn-modal-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 20px;
  border-bottom: 1px solid var(--line);
}
.fn-modal-title { margin: 0; font-family: var(--font-display); font-size: 18px; }
.fn-modal-close {
  border: none; background: none; font-size: 24px; line-height: 1;
  color: var(--ink-3); cursor: pointer;
}
.fn-modal-close:hover { color: var(--ink-1); }

/* Mini Quill — keep the toolbar compact and the editing area modest. */
.fn-mini-wrap { padding: 12px 20px; }
.fn-mini-wrap .ql-toolbar.ql-snow {
  border: 1px solid var(--line);
  border-bottom: none;
  border-radius: var(--radius-sm) var(--radius-sm) 0 0;
  padding: 5px 8px;
}
.fn-mini-wrap .ql-container.ql-snow {
  border: 1px solid var(--line);
  border-radius: 0 0 var(--radius-sm) var(--radius-sm);
  font-family: var(--font-serif, Georgia, serif);
  font-size: 14.5px;
}
.fn-mini-wrap .ql-editor {
  min-height: 110px;
  max-height: 260px;
  overflow-y: auto;
}
.fn-mini-wrap .ql-editor.ql-blank::before { font-style: italic; color: var(--ink-3); }
.fn-mini-wrap .ql-citation { font-size: 15px; }

.fn-modal-foot {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 14px 20px;
  border-top: 1px solid var(--line);
  background: var(--bg-paper);
}
.fn-foot-spacer { flex: 1; }
.fn-delete { color: var(--danger); }

:root[data-theme="dark"] .fn-modal-card { background: var(--bg-rail, #1f1d1a); }

/* Bibliography (preview + editor) — hanging indent per convention. */
.bibliography .bib-entry { margin: 0 0 0.7em; padding-left: 1.6em; text-indent: -1.6em; line-height: 1.5; text-align: left; }
.bibliography .bib-empty { font-style: italic; color: var(--ink-3); }

/* ============================================================
   Skip-to-content link. Visually hidden until focused, then drops in at
   the top-left as the first Tab stop so keyboard users can jump past the
   topbar/nav straight to the page's <main>. High z-index so it sits over
   sticky topbars and announcement banners.
   ============================================================ */
.skip-link {
  position: fixed;
  top: 8px;
  left: 8px;
  z-index: 100000;
  padding: 10px 16px;
  background: #111;
  color: #fff;
  border-radius: 6px;
  text-decoration: none;
  font-weight: 600;
  font-size: 14px;
  transform: translateY(-160%);
  transition: transform .15s ease;
}
.skip-link:focus {
  transform: translateY(0);
  outline: 2px solid #fff;
  outline-offset: 2px;
}
/* A container focused programmatically via the skip link shouldn't show a
   persistent focus box around the whole region. */
[tabindex="-1"]:focus { outline: none; }

/* ============================================================
   Reduced motion. Honour the OS "reduce motion" setting across the
   whole app — near-instant transitions/animations, no infinite
   spinners, no smooth-scroll. Loaded on every page (scrived.css is
   global) so it also covers marketing.css / cover-maker.css rules.
   The tiny non-zero duration keeps transitionend/animationend
   listeners firing so JS that waits on them still resolves.
   ============================================================ */
@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
}

/* ============================================================
   Help center (public /help pages). Sits inside .app-shell like
   library/settings; a sidebar (categories + search) plus a main pane
   that renders either a category grid, an article list, one article's
   prose, or search results. .help-prose mirrors .legal-prose's
   treatment of the same markdown-lite renderer output.
   ============================================================ */
.help-shell {
  display: grid;
  grid-template-columns: 260px 1fr;
  gap: 32px;
  max-width: 1160px;
  margin: 0 auto;
  padding: 32px 24px 96px;
  align-items: start;
}
@media (max-width: 860px) {
  .help-shell { grid-template-columns: 1fr; }
}

.help-nav {
  position: sticky;
  top: 24px;
  display: flex;
  flex-direction: column;
  gap: 4px;
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 16px;
}
.help-nav-home {
  font-family: var(--font-display);
  font-size: 15px;
  font-weight: 600;
  color: var(--ink-1);
  text-decoration: none;
  padding: 4px 8px 10px;
  border-bottom: 1px solid var(--line-soft);
  margin-bottom: 6px;
}
.help-nav-home.is-active { color: var(--accent); }
.help-nav-search { margin-bottom: 10px; }
.help-search-input {
  width: 100%;
  box-sizing: border-box;
  padding: 8px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  font: inherit;
  font-size: 13.5px;
  background: var(--bg-page);
  color: var(--ink-1);
}
.help-search-input:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(139,105,20,.12);
}
.help-search-live {
  position: relative;
}
.help-search-live:not([hidden]) {
  display: block;
  margin: -4px 0 10px;
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  box-shadow: var(--shadow-1);
  overflow: hidden;
  max-height: 320px;
  overflow-y: auto;
}
.help-search-live-item {
  display: block;
  padding: 8px 10px;
  text-decoration: none;
  border-bottom: 1px solid var(--line-soft);
}
.help-search-live-item:last-child { border-bottom: none; }
.help-search-live-item:hover,
.help-search-live-item:focus { background: var(--bg-page); }
.help-search-live-title { display: block; font-size: 13px; font-weight: 600; color: var(--ink-1); }
.help-search-live-cat { display: block; font-size: 11.5px; color: var(--ink-3); }
.help-search-live-empty { padding: 10px; font-size: 13px; color: var(--ink-3); font-style: italic; }

.help-nav-group { margin-top: 8px; }
.help-nav-group-label {
  display: block;
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-3);
  padding: 8px 8px 4px;
}
.help-nav-list { list-style: none; margin: 0; padding: 0; }
.help-nav-link {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 7px 8px;
  border-radius: var(--radius-sm);
  color: var(--ink-2);
  text-decoration: none;
  font-size: 13.5px;
}
.help-nav-link:hover { background: var(--bg-page); color: var(--ink-1); }
.help-nav-link.is-active { background: var(--bg-page); color: var(--accent); font-weight: 600; }
.help-nav-icon { font-size: 14px; }
.help-nav-back {
  display: block;
  margin-top: 14px;
  padding-top: 12px;
  border-top: 1px solid var(--line-soft);
  color: var(--ink-3);
  text-decoration: none;
  font-size: 13px;
}
.help-nav-back:hover { color: var(--ink-1); }

.help-main { min-width: 0; width: 100%; }
.help-hero { margin-bottom: 24px; }
.help-page-title {
  font-family: var(--font-display);
  font-size: 28px;
  font-weight: 600;
  margin: 0 0 8px;
  color: var(--ink-1);
}
.help-page-sub { margin: 0 0 18px; color: var(--ink-3); font-size: 14.5px; }
.help-hero-search {
  display: flex;
  gap: 10px;
  max-width: 640px;
  width: 100%;
}
.help-hero-search-input { flex: 1; width: 100%; padding: 10px 14px; font-size: 14.5px; }
.help-empty {
  color: var(--ink-3);
  font-style: italic;
  padding: 20px 0;
}

.help-crumb {
  font-size: 13px;
  color: var(--ink-3);
  margin-bottom: 12px;
}
.help-crumb a { color: var(--ink-3); }
.help-crumb a:hover { color: var(--accent); }

.help-category-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: 16px;
}
.help-category-card {
  display: flex;
  flex-direction: column;
  gap: 4px;
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 18px;
  text-decoration: none;
  transition: border-color .15s ease, box-shadow .15s ease;
}
.help-category-card:hover {
  border-color: var(--accent);
  box-shadow: var(--shadow-1);
}
.help-category-icon { font-size: 22px; }
.help-category-label {
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
  color: var(--ink-1);
}
.help-category-desc { font-size: 13px; color: var(--ink-3); line-height: 1.4; }
.help-category-count { margin-top: 6px; font-size: 11.5px; color: var(--ink-3); text-transform: uppercase; letter-spacing: .04em; }

.help-article-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 2px; }
.help-article-link {
  display: flex;
  flex-direction: column;
  gap: 3px;
  padding: 14px 16px;
  border-radius: var(--radius-sm);
  text-decoration: none;
  border-bottom: 1px solid var(--line-soft);
}
.help-article-link:hover { background: var(--bg-card); }
.help-article-title { font-size: 15px; font-weight: 600; color: var(--ink-1); }
.help-article-summary { font-size: 13px; color: var(--ink-3); }
.help-admin-badge {
  display: inline-block;
  margin-left: 6px;
  padding: 1px 6px;
  border-radius: 999px;
  background: var(--accent);
  color: #fff;
  font-size: 10px;
  font-weight: 600;
  text-transform: uppercase;
  vertical-align: middle;
}

.help-article {
  background: var(--bg-card);
  border: 1px solid var(--line-soft);
  border-radius: var(--radius);
  padding: 40px 48px;
  box-shadow: var(--shadow-1);
}
.help-article-h1 {
  font-family: var(--font-display);
  font-size: 26px;
  font-weight: 600;
  margin: 0 0 20px;
  color: var(--ink-1);
}
.help-prose {
  font-family: var(--font-serif);
  font-size: 16px;
  line-height: 1.7;
  color: var(--ink-2);
}
.help-prose h2 {
  font-family: var(--font-display);
  font-size: 20px;
  font-weight: 600;
  color: var(--ink-1);
  margin: 30px 0 12px;
}
.help-prose h2:first-child { margin-top: 0; }
.help-prose h3 {
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 600;
  color: var(--ink-1);
  margin: 24px 0 8px;
}
.help-prose p { margin: 0 0 16px; }
.help-prose ul { margin: 0 0 18px; padding-left: 24px; }
.help-prose li { margin-bottom: 8px; }
.help-prose strong { color: var(--ink-1); font-weight: 600; }
.help-prose a { color: var(--accent); text-decoration: underline; text-underline-offset: 2px; }
.help-prose a:hover { color: var(--accent-soft); }
.help-prose hr { border: none; border-top: 1px solid var(--line); margin: 28px 0; }

/* Rich-text media embeds — output of SiteSetting::renderRichText(),
   shared by help articles and the legal pages, so these rules are
   intentionally not scoped under .help-prose/.legal-prose. */
.rt-media { margin: 20px 0; }
.rt-media img { max-width: 100%; height: auto; border-radius: var(--radius-sm); display: block; }
.rt-video {
  position: relative;
  width: 100%;
  padding-top: 56.25%; /* 16:9 */
  border-radius: var(--radius-sm);
  overflow: hidden;
  background: #000;
}
.rt-video iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }

/* Admin help-article editor toolbar (image upload, YouTube embed). */
.help-editor-toolbar {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 8px;
  margin-bottom: 6px;
}
.help-editor-toolbar-divider {
  width: 1px;
  align-self: stretch;
  background: var(--line);
  margin: 0 2px;
}

.help-editor-tabs {
  display: flex;
  gap: 4px;
  margin-bottom: 8px;
  border-bottom: 1px solid var(--line);
}
.help-editor-tab {
  padding: 7px 14px;
  border: none;
  background: none;
  font: inherit;
  font-size: 13px;
  font-weight: 500;
  color: var(--ink-3);
  cursor: pointer;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}
.help-editor-tab:hover { color: var(--ink-1); }
.help-editor-tab.is-active { color: var(--ink-1); border-bottom-color: var(--accent); }

.help-editor-preview {
  min-height: 200px;
  max-height: 520px;
  overflow-y: auto;
  padding: 16px 18px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-card);
}
.help-editor-preview-loading,
.help-editor-preview-empty {
  color: var(--ink-3);
  font-style: italic;
}

/* Help/legal admin textareas default to white-space: pre (no wrap) so
   hand-wrapped legal prose renders exactly as typed. Help articles are
   flowing paragraphs instead, so force wrapping here without touching
   the shared .admin-legal-textarea rule other admin pages rely on. */
/* #id, not .class: .admin-legal-textarea's white-space:pre lives in
   marketing.css, which <link>s in after scrived.css in layout.php's
   <head> — with equal class-selector specificity, that later rule
   would otherwise win regardless of source order in this file. */
#help-article-body {
  white-space: pre-wrap;
  overflow-x: hidden;
}

/* Media strip — actual thumbnails (not raw markdown) for every image
   embedded in the help-article textarea above, with a per-image size
   dropdown and remove button. See help_article_editor.js. */
.help-media-strip {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  padding: 10px;
  margin-bottom: 8px;
  background: var(--bg-page);
  border: 1px solid var(--line-soft);
  border-radius: var(--radius-sm);
}
.help-media-card {
  display: flex;
  align-items: center;
  gap: 8px;
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: 6px 8px;
}
.help-media-thumb {
  width: 56px;
  height: 56px;
  object-fit: cover;
  border-radius: 4px;
  background: var(--bg-page);
  flex-shrink: 0;
}
.help-media-meta { display: flex; flex-direction: column; gap: 4px; }
.help-media-alt {
  font-size: 12px;
  color: var(--ink-2);
  max-width: 160px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.help-media-size { font-size: 12px; padding: 2px 4px; }
.help-media-remove {
  align-self: flex-start;
  font-size: 11px;
  color: var(--danger);
  background: none;
  border: none;
  cursor: pointer;
  padding: 0;
}
.help-media-remove:hover { text-decoration: underline; }

.help-pager {
  display: flex;
  justify-content: space-between;
  gap: 16px;
  margin-top: 20px;
}
.help-pager-link {
  flex: 1;
  padding: 14px 16px;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  color: var(--ink-2);
  text-decoration: none;
  font-size: 13.5px;
}
.help-pager-link:hover { border-color: var(--accent); color: var(--ink-1); }
.help-pager-next { text-align: right; }

.help-search-results-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 18px; }
.help-search-result {
  background: var(--bg-card);
  border: 1px solid var(--line-soft);
  border-radius: var(--radius);
  padding: 16px 18px;
}
.help-search-result-title {
  display: block;
  font-size: 15.5px;
  font-weight: 600;
  color: var(--ink-1);
  text-decoration: none;
}
.help-search-result-title:hover { color: var(--accent); }
.help-search-result-cat {
  display: inline-block;
  margin: 2px 0 8px;
  font-size: 11.5px;
  color: var(--ink-3);
  text-transform: uppercase;
  letter-spacing: .04em;
}
.help-search-snippet {
  margin: 4px 0 0;
  font-size: 13.5px;
  color: var(--ink-3);
  line-height: 1.5;
}
.help-search-snippet mark {
  background: rgba(139,105,20,.22);
  color: var(--ink-1);
  padding: 0 2px;
  border-radius: 2px;
}

/* Admin help-editor form fields that need to span both grid columns. */
.field-wide { grid-column: 1 / -1; }


/* ============================================================
   KDP keywords (Workshop → KDP Keywords, migration 066)

   Seven slot rows, each a chip input with a byte meter. The meter's
   three tones are local tokens so the dark override lives in one
   place: green with headroom, amber as the 50-byte budget fills,
   red once KDP would reject the box.
   ============================================================ */
:root {
  --kdp-ok:   #4d7a2e;
  --kdp-near: #8a6d13;
  --kdp-over: #a93b2a;
}
:root[data-theme="dark"] {
  --kdp-ok:   #7fae5c;
  --kdp-near: #cba85a;
  --kdp-over: #d36456;
}

/* Seven stacked slots across a full-width editor read as an overwhelming wall
   of empty boxes — a keyword box is ~50 characters, so the content never needs
   more than a comfortable reading measure. The cap goes on the CHILDREN, not
   on .publishing-main: that's the scroll container, and capping it shoves the
   whole pane (scrollbar included) to the left edge of a wide screen with dead
   space beside it. Children capped + auto-margined = centered column,
   scrollbar stays at the viewport edge. */
/* The cap sits on the individual sections, NOT on .kdp-body: the description
   pane needs a wider measure (1200px, set with the pane styles) for its
   side-by-side editor+preview, and a cap on the common parent would win. */
#view-kdp .publishing-head,
#view-kdp .kdp-guide,
#view-kdp .kdp-empty-wrap,
#view-kdp .kdp-listing-bar,
#view-kdp .kdp-pane-tabs,
#view-kdp .kdp-pane {
  max-width: 860px;
  margin-left: auto;
  margin-right: auto;
}

/* The keyword library is a fixed drawer on the right edge; reserve its width so
   the centered column slides clear of it instead of sitting underneath. */
#view-kdp.has-library-open .publishing-main {
  padding-right: 396px;
  transition: padding-right .18s ease;
}
@media (max-width: 1400px) {
  /* Not enough room to do both — the drawer overlays, as drawers do. */
  #view-kdp.has-library-open .publishing-main { padding-right: 36px; }
}

.kdp-head-actions {
  display: flex;
  gap: 8px;
  align-items: center;
  flex-shrink: 0;           /* never crush the buttons into two-line pills */
}
.kdp-head-actions .btn { white-space: nowrap; }

.field-optional { color: var(--ink-4); font-weight: 400; }

/* ---------- walkthrough ---------- */
.kdp-guide {
  border: 1px solid var(--line);
  border-left: 3px solid var(--accent-soft);
  border-radius: var(--radius);
  background: var(--bg-card);
  margin-bottom: 22px;
}
.kdp-guide-summary {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  padding: 10px 14px;
  cursor: pointer;
  list-style: none;           /* Firefox */
  user-select: none;
}
.kdp-guide-summary::-webkit-details-marker { display: none; }
.kdp-guide-summary:hover { background: var(--bg-rail); }
.kdp-guide[open] .kdp-guide-summary { border-bottom: 1px solid var(--line-soft); }
.kdp-guide-title {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--ink-3);
}
/* Chevron: points down when closed, up when open. */
.kdp-guide-toggle {
  width: 8px; height: 8px;
  border-right: 1.5px solid var(--ink-4);
  border-bottom: 1.5px solid var(--ink-4);
  transform: rotate(45deg);
  transition: transform .15s ease;
  margin-bottom: 3px;
}
.kdp-guide[open] .kdp-guide-toggle { transform: rotate(-135deg); margin-bottom: -3px; }

.kdp-guide-steps {
  margin: 0;
  padding: 12px 14px 14px 34px;
  counter-reset: kdp-step;
  list-style: none;
}
.kdp-guide-steps li {
  position: relative;
  font-size: 12.5px;
  line-height: 1.6;
  color: var(--ink-2);
  margin-bottom: 9px;
}
.kdp-guide-steps li:last-child { margin-bottom: 0; }
.kdp-guide-steps li::before {
  counter-increment: kdp-step;
  content: counter(kdp-step);
  position: absolute;
  left: -26px;
  top: 1px;
  width: 18px; height: 18px;
  border-radius: 50%;
  background: var(--accent-bg);
  border: 1px solid var(--accent-soft);
  color: var(--accent);
  font-size: 10.5px;
  font-weight: 700;
  display: flex;
  align-items: center;
  justify-content: center;
}
.kdp-guide-steps strong { color: var(--ink-1); font-weight: 600; }
.kdp-guide-steps em { font-style: normal; color: var(--ink-1); font-weight: 500; }
/* The app only styles kbd inside .kbd-foot / .cmd-foot, so give ours a look. */
.kdp-guide-steps kbd {
  display: inline-block;
  padding: 0 5px;
  border: 1px solid var(--line);
  border-bottom-width: 2px;
  border-radius: 3px;
  background: var(--bg-paper);
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 11px;
  color: var(--ink-2);
}

/* The shared .snap-link is a fixed 26x26 icon button — right for a bare ✎ or ✕,
   wrong for a worded action. This is its text sibling: same quiet treatment,
   sized to its label. */
.kdp-linkbtn {
  display: inline-flex;
  align-items: center;
  white-space: nowrap;
  border: 1px solid var(--line);
  background: var(--bg-card);
  color: var(--ink-2);
  border-radius: var(--radius-sm);
  cursor: pointer;
  font: inherit;
  font-size: 12px;
  padding: 4px 9px;
  transition: background .12s, color .12s, border-color .12s;
}
.kdp-linkbtn:hover { background: var(--bg-rail); border-color: var(--line-strong); color: var(--ink-1); }
.kdp-linkbtn-danger:hover { background: var(--danger); border-color: var(--danger); color: #fff; }

/* The app defines no global .btn:disabled, so a disabled primary button still
   reads as clickable. Scoped here rather than globally to avoid restyling
   every other view. */
#view-kdp .btn:disabled,
#view-kdp .kdp-linkbtn:disabled {
  opacity: .45;
  cursor: not-allowed;
}
#view-kdp .btn:disabled:hover { background: var(--accent); }
#view-kdp .btn-ghost:disabled:hover { background: transparent; }

/* ---------- empty state ---------- */
.kdp-empty {
  max-width: 520px;
  margin: 48px auto;
  text-align: center;
}
.kdp-empty-title { font-size: 15px; color: var(--ink-1); margin: 0 0 6px; }
.kdp-empty-hint  { font-size: 13px; color: var(--ink-3); line-height: 1.55; margin: 0 0 18px; }

/* ---------- listing bar ---------- */
.kdp-listing-bar {
  display: flex;
  align-items: flex-end;
  gap: 16px;
  padding: 0 0 16px;
  border-bottom: 1px solid var(--line-soft);
  margin-bottom: 20px;
  flex-wrap: wrap;
}
.kdp-listing-picker { min-width: 240px; margin: 0; }
.kdp-listing-meta { display: flex; gap: 8px; flex-wrap: wrap; flex: 1; padding-bottom: 6px; }
.kdp-meta-bit {
  font-size: 11px;
  color: var(--ink-3);
  background: var(--bg-rail);
  border: 1px solid var(--line-soft);
  border-radius: 999px;
  padding: 2px 9px;
  white-space: nowrap;
}
.kdp-listing-tools { display: flex; gap: 6px; padding-bottom: 4px; }

/* ---------- editor ---------- */
.kdp-editor-head {
  display: flex;
  justify-content: space-between;
  align-items: flex-start;
  gap: 16px;
  margin-bottom: 14px;
}
.kdp-section-title { font-size: 14px; font-weight: 600; color: var(--ink-1); margin: 0 0 4px; }
.kdp-section-sub   { font-size: 12px; color: var(--ink-3); margin: 0; line-height: 1.5; max-width: 70ch; }
.kdp-editor-actions { display: flex; gap: 8px; align-items: center; flex-shrink: 0; }

.kdp-slots { display: flex; flex-direction: column; gap: 10px; }

.kdp-slot {
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-left: 3px solid var(--kdp-ok);
  border-radius: var(--radius);
  padding: 10px 12px;
}
.kdp-slot.is-near { border-left-color: var(--kdp-near); }
.kdp-slot.is-over { border-left-color: var(--kdp-over); }

.kdp-slot-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 6px;
}
.kdp-slot-label { font-size: 11px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; color: var(--ink-3); }
.kdp-slot-meter { display: flex; align-items: center; gap: 8px; }
.kdp-meter-bar {
  width: 90px;
  height: 4px;
  border-radius: 999px;
  background: var(--bg-rail);
  overflow: hidden;
}
.kdp-meter-fill {
  display: block;
  height: 100%;
  border-radius: 999px;
  background: var(--kdp-ok);
  transition: width .12s linear;
}
.kdp-slot.is-near .kdp-meter-fill { background: var(--kdp-near); }
.kdp-slot.is-over .kdp-meter-fill { background: var(--kdp-over); }
.kdp-meter-count { font-size: 11px; color: var(--ink-3); font-variant-numeric: tabular-nums; min-width: 92px; text-align: right; }
.kdp-slot.is-over .kdp-meter-count { color: var(--kdp-over); font-weight: 600; }

/* The shared .chip-input hides itself when empty; these boxes always show,
   because an empty slot still needs a click target and a text entry. */
.kdp-chip-input,
.kdp-chip-input:empty {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  align-items: center;
  min-height: 34px;
  cursor: text;
}
.kdp-chip-entry {
  flex: 1;
  min-width: 140px;
  border: none;
  background: transparent;
  font: inherit;
  font-size: 13px;
  color: var(--ink-1);
  padding: 2px 0;
  outline: none;
}
.kdp-chip-entry::placeholder { color: var(--ink-4); }

/* A read-only slot (no draft open) must not impersonate a text field — the
   borderless, tinted box plus the hint tells you to click to start editing. */
.kdp-slot.is-readonly .kdp-chip-input {
  border-style: dashed;
  background: transparent;
  cursor: pointer;
}
.kdp-slot.is-readonly .kdp-chip-input:hover { background: var(--bg-rail); border-color: var(--line-strong); }
/* Nothing to measure and nothing to copy: collapse the row to its essentials. */
.kdp-slot.is-bare { padding: 8px 12px; border-left-color: var(--line); }
.kdp-slot.is-bare .kdp-slot-head { margin-bottom: 4px; }
.kdp-slot.is-bare .kdp-chip-input { margin-bottom: 0; min-height: 30px; }
.kdp-slot-hint {
  font-size: 12.5px;
  color: var(--ink-4);
  font-style: italic;
  align-self: center;
}

/* Elsewhere .chip-x is a <span role="button">; here it's a real <button> so it
   is keyboard-reachable, which means its UA chrome needs clearing. */
.kdp-chip-input .chip-x {
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  font: inherit;
  font-size: 14px;
  line-height: 1;
}

.kdp-slot-foot {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 12px;
  margin-top: 6px;
  padding-top: 6px;
  border-top: 1px dashed var(--line-soft);
}
.kdp-slot-rendered {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 11.5px;
  color: var(--ink-3);
  overflow-x: auto;
  white-space: nowrap;
}

/* ---------- submit-ready block ---------- */
.kdp-submit-block {
  margin-top: 18px;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  background: var(--bg-paper);
  overflow: hidden;
}
.kdp-submit-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 8px 12px;
  background: var(--bg-rail);
  border-bottom: 1px solid var(--line-soft);
}
.kdp-submit-label { font-size: 11px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; color: var(--ink-3); }
.kdp-submit-tools { display: flex; align-items: center; gap: 12px; }
.kdp-total { font-size: 11px; color: var(--ink-4); font-variant-numeric: tabular-nums; }
.kdp-submit-pre {
  margin: 0;
  padding: 12px;
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 12px;
  line-height: 1.7;
  color: var(--ink-2);
  white-space: pre;
  overflow-x: auto;
  min-height: 40px;
}
.kdp-submit-pre.is-empty { color: var(--ink-4); font-style: italic; white-space: normal; }

/* ---------- validator output ---------- */
.kdp-warnings { margin-top: 16px; display: flex; flex-direction: column; gap: 10px; }
.kdp-warn-group {
  border: 1px solid var(--line);
  border-left-width: 3px;
  border-radius: var(--radius-sm);
  padding: 10px 12px;
  background: var(--bg-card);
}
.kdp-warn-group.is-error { border-left-color: var(--kdp-over); }
.kdp-warn-group.is-warn  { border-left-color: var(--kdp-near); }
.kdp-warn-heading {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: .04em;
  text-transform: uppercase;
  margin: 0 0 6px;
  color: var(--ink-3);
}
.kdp-warn-group.is-error .kdp-warn-heading { color: var(--kdp-over); }
.kdp-warn-list { margin: 0; padding-left: 18px; }
.kdp-warn-list li { font-size: 12.5px; color: var(--ink-2); line-height: 1.6; margin-bottom: 3px; }
.kdp-warn-clean { font-size: 12.5px; color: var(--kdp-ok); margin: 0; }

/* ---------- history ---------- */
.kdp-history { margin-top: 32px; }
.kdp-history .kdp-section-sub { margin-bottom: 12px; }
.publishing-row.is-current { background: var(--accent-bg); }

/* ---------- inner pane pills (Keywords | Description | Categories) ---------- */
.kdp-pane-tabs {
  display: flex;
  gap: 6px;
  margin: 0 0 18px;
}
.kdp-pane-tab {
  font: inherit;
  font-size: 13px;
  padding: 6px 14px;
  border: 1px solid var(--line);
  border-radius: 999px;
  background: var(--bg-card);
  color: var(--ink-3);
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s;
}
.kdp-pane-tab:hover { background: var(--bg-rail); color: var(--ink-1); }
.kdp-pane-tab.is-active {
  background: var(--accent-bg);
  border-color: var(--accent-soft);
  color: var(--ink-1);
  font-weight: 600;
}

/* The description pane runs its editor and preview side by side, which the
   860px column can't fit — it alone gets a wider measure (overrides the
   shared .kdp-pane cap above; same specificity, declared later). */
#view-kdp .kdp-pane.kdp-pane-wide { max-width: 1200px; }
.kdp-pane-loading { font-size: 13px; color: var(--ink-4); padding: 24px 0; }

/* ---------- verdicts (good / bad keyword) ---------- */
.kdp-dot {
  display: inline-block;
  width: 8px; height: 8px;
  border-radius: 50%;
  margin-right: 5px;
  vertical-align: baseline;
  flex-shrink: 0;
}
.kdp-dot-testing         { background: var(--kdp-near); }
.kdp-dot-working         { background: var(--kdp-ok); }
.kdp-dot-underperforming { background: var(--kdp-over); }

.kdp-verdict-select {
  font: inherit;
  font-size: 11.5px;
  padding: 2px 4px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-card);
  color: var(--ink-2);
  max-width: 132px;
}

/* Segmented verdict picker in the performance modal. */
.kdp-obs-verdict { display: flex; gap: 6px; margin: 4px 0 10px; }
.kdp-verdict-btn {
  display: inline-flex;
  align-items: center;
  font: inherit;
  font-size: 12px;
  padding: 4px 10px;
  border: 1px solid var(--line);
  border-radius: 999px;
  background: var(--bg-card);
  color: var(--ink-2);
  cursor: pointer;
}
.kdp-verdict-btn:hover { background: var(--bg-rail); }
.kdp-verdict-btn.is-active { border-color: var(--ink-3); background: var(--bg-rail); color: var(--ink-1); font-weight: 600; }

/* ---------- description pane ---------- */
.kdpd-workbench {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: 16px;
  /* start + a height-capped sticky preview: the preview re-renders on every
     keystroke, and if its column can grow the page reflows under the caret. */
  align-items: start;
}
@media (max-width: 980px) {
  .kdpd-workbench { grid-template-columns: 1fr; }
}
.kdpd-toolbar {
  display: flex;
  gap: 6px;
  flex-wrap: wrap;
  margin-bottom: 8px;
}
.kdpd-body {
  width: 100%;
  min-height: 320px;
  resize: vertical;
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 12.5px;
  line-height: 1.6;
  padding: 10px 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  background: var(--bg-paper);
  color: var(--ink-1);
}
.kdpd-body:disabled { opacity: .65; cursor: not-allowed; }
.kdpd-meter {
  display: flex;
  align-items: baseline;
  gap: 10px;
  margin-top: 6px;
}
#kdpd-counter {
  font-variant-numeric: tabular-nums;
  font-size: 12.5px;
  font-weight: 600;
  color: var(--kdp-ok);
}
#kdpd-counter.is-near { color: var(--kdp-near); }
#kdpd-counter.is-over { color: var(--kdp-over); }
.kdpd-meter-note { font-size: 11.5px; color: var(--ink-4); }

.kdpd-preview-col {
  display: flex;
  flex-direction: column;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  background: var(--bg-card);
  overflow: hidden;
  /* Capped so a long blurb scrolls INSIDE the preview instead of growing the
     page; sticky keeps it beside the textarea while the author scrolls. */
  position: sticky;
  top: 12px;
  max-height: min(70vh, 560px);
}
.kdpd-preview-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 8px 12px;
  background: var(--bg-rail);
  border-bottom: 1px solid var(--line-soft);
}
.kdpd-preview {
  flex: 1;
  padding: 14px 16px;
  overflow-y: auto;
  font-size: 13.5px;
  line-height: 1.6;
  color: var(--ink-2);
  min-height: 200px;
}
.kdpd-preview h4, .kdpd-preview h5, .kdpd-preview h6 { margin: 0 0 8px; color: var(--ink-1); }
.kdpd-preview p  { margin: 0 0 10px; }
.kdpd-preview hr { border: none; border-top: 1px solid var(--line); margin: 12px 0; }
.kdpd-preview ul, .kdpd-preview ol { margin: 0 0 10px; padding-left: 22px; }
.kdpd-preview-empty { color: var(--ink-4); font-style: italic; }
.kdpd-fold {
  display: inline-block;
  margin: 0 4px;
  padding: 0 8px;
  border: 1px dashed var(--kdp-near);
  border-radius: 999px;
  font-size: 10.5px;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--kdp-near);
  white-space: nowrap;
  user-select: none;
}

/* ---------- categories pane ---------- */
.kdpc-slots { display: flex; flex-direction: column; gap: 10px; }
.kdpc-slot {
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 10px 12px;
}
.kdpc-slot-meta { display: flex; align-items: center; gap: 8px; }
.kdpc-bsr { font-size: 11.5px; color: var(--ink-2); font-variant-numeric: tabular-nums; }
.kdpc-slot-input {
  width: 100%;
  font: inherit;
  font-size: 13px;
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-paper);
  color: var(--ink-1);
}
.kdpc-slot-path {
  font-size: 13px;
  color: var(--ink-1);
  padding: 7px 2px;
}
.kdpc-slot-path.is-empty { color: var(--ink-4); font-style: italic; }
.kdpc-slot-hint { margin: 4px 2px 0; font-size: 11.5px; color: var(--kdp-near); }

/* "Shown on Amazon" — the display categories the product page actually lists. */
.kdpc-shown { margin-top: 22px; }
.kdpc-shown-list { display: flex; flex-direction: column; gap: 8px; margin-top: 10px; }
.kdpc-shown-empty { font-size: 12.5px; color: var(--ink-4); font-style: italic; margin: 6px 0 0; }
.kdpc-shown-row {
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 9px 12px;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.kdpc-shown-main { display: flex; align-items: center; gap: 8px; min-width: 0; flex-wrap: wrap; }
.kdpc-shown-path { font-size: 13px; color: var(--ink-1); }
.kdpc-shown-meta {
  display: flex;
  align-items: center;
  gap: 10px;
  flex-wrap: wrap;
  font-size: 11.5px;
  color: var(--ink-3);
}
.kdpc-shown-checked { color: var(--ink-4); }
.kdpc-shown-meta .snap-link { margin-left: auto; }
.kdpc-shown-add { display: flex; gap: 8px; margin-top: 10px; }
.kdpc-shown-add input {
  flex: 1;
  font: inherit;
  font-size: 13px;
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  background: var(--bg-paper);
  color: var(--ink-1);
}

/* ---------- keyword library drawer ---------- */
.kdp-library {
  position: fixed;
  top: var(--topbar-h);
  right: 0;
  bottom: 0;
  width: 380px;
  max-width: 92vw;
  background: var(--bg-card);
  border-left: 1px solid var(--line);
  box-shadow: var(--shadow-2);
  z-index: 60;
  display: flex;
  flex-direction: column;
  transform: translateX(100%);
  transition: transform .18s ease;
}
.kdp-library.is-open { transform: translateX(0); }
.kdp-library-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 14px 16px 10px;
  border-bottom: 1px solid var(--line-soft);
}
.kdp-library-close {
  background: none;
  border: none;
  font-size: 20px;
  line-height: 1;
  color: var(--ink-3);
  cursor: pointer;
  padding: 0 4px;
}
.kdp-library-close:hover { color: var(--ink-1); }
.kdp-library-search { padding: 12px 16px 6px; }
.kdp-library-search input {
  width: 100%;
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--bg-page);
  color: var(--ink-1);
  font: inherit;
  font-size: 13px;
}
.kdp-library-hint { font-size: 11.5px; color: var(--ink-4); margin: 0; padding: 4px 16px 10px; line-height: 1.5; }
/* Bulk-select bar — count on the left, select-all / clear / delete on the
   right. Shown whenever the list has rows; Delete enables at 1+ selected. */
.kdp-library-bulkbar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  padding: 6px 16px 8px;
  border-bottom: 1px solid var(--line);
  font-size: 12px;
}
.kdp-library-bulkcount { color: var(--ink-3); white-space: nowrap; }
.kdp-library-bulk-actions { display: inline-flex; gap: 12px; flex-wrap: wrap; }
.kdp-library-bulkbar .kdp-linkbtn:disabled { opacity: .4; cursor: not-allowed; }
/* Per-row select checkbox, leading the phrase on its row. */
.kdp-lib-check { display: inline-flex; align-items: center; }
.kdp-lib-check input { margin: 0; cursor: pointer; accent-color: var(--accent); }
/* Admin-only library view tabs (All phrases / From Publisher Rocket). */
.kdp-library-tabs { display: flex; gap: 6px; padding: 8px 16px 0; }
/* Scope toggle (085) — same pill look, slightly subdued. */
.kdp-library-scope { display: flex; gap: 6px; padding: 8px 16px 0; }
.kdp-library-scope .kdp-library-tab { font-size: 11.5px; }
.kdp-library-tab {
  font: inherit; font-size: 12px; padding: 4px 10px;
  border: 1px solid var(--line); border-radius: 999px;
  background: var(--bg-card); color: var(--ink-3); cursor: pointer;
  transition: background .12s ease, color .12s ease, border-color .12s ease;
}
.kdp-library-tab:hover { color: var(--ink-1); border-color: var(--ink-4); }
.kdp-library-tab.is-active { background: var(--accent-bg); border-color: var(--accent-soft); color: var(--ink-1); font-weight: 600; }
.kdp-lib-group {
  font-size: 11px; text-transform: uppercase; letter-spacing: .06em;
  color: var(--ink-4); margin: 12px 8px 4px; font-weight: 600;
}
.kdp-lib-group:first-child { margin-top: 4px; }
.kdp-lib-imported { font-size: 11px; color: var(--ink-4); font-style: italic; }
.kdp-lib-row-slot { background: var(--accent-bg); }
.kdp-lib-row-slot .kdp-lib-phrase { font-family: var(--font-mono, ui-monospace, Menlo, Consolas, monospace); font-size: 12px; }
.kdp-library-list { flex: 1; overflow-y: auto; padding: 0 8px 12px; }
.kdp-library-foot { border-top: 1px solid var(--line-soft); padding: 10px 16px; }
.kdp-lib-empty { font-size: 12.5px; color: var(--ink-4); padding: 16px 8px; line-height: 1.6; }

.kdp-lib-row {
  padding: 9px 8px;
  border-radius: var(--radius-sm);
  border-bottom: 1px solid var(--line-soft);
}
.kdp-lib-row:hover { background: var(--bg-rail); }
.kdp-lib-main { display: flex; align-items: baseline; gap: 8px; flex-wrap: wrap; }
.kdp-lib-phrase {
  background: none;
  border: none;
  padding: 0;
  font: inherit;
  font-size: 13px;
  font-weight: 500;
  color: var(--ink-1);
  cursor: pointer;
  text-align: left;
}
.kdp-lib-phrase:hover { color: var(--accent); text-decoration: underline; }
.kdp-lib-count { font-size: 11px; color: var(--ink-4); font-variant-numeric: tabular-nums; }
.kdp-lib-obs   { font-size: 11px; color: var(--accent-soft); }
.kdp-lib-books { font-size: 11.5px; color: var(--ink-3); }
.kdp-lib-sub   { margin-top: 2px; }
.kdp-lib-actions { display: flex; gap: 6px; margin-top: 6px; }

@media (max-width: 700px) {
  .kdp-slot-head { flex-wrap: wrap; gap: 6px; }
  .kdp-meter-bar { width: 60px; }
  .kdp-editor-head { flex-direction: column; }
  .kdp-listing-bar { flex-direction: column; align-items: stretch; }
}

/* ==========================================================================
   Workshop dashboard (Workshop → Dashboard)
   Card grid summarizing every Workshop tab. All colors via vars — dark mode
   needs no extra rules here.
   ========================================================================== */
.wd-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(260px, 100%), 1fr));
  /* dense: the 2-column KDP card wraps; let later cards backfill the hole */
  grid-auto-flow: dense;
  gap: 16px;
  max-width: 1200px;
}
.wd-card {
  display: flex;
  flex-direction: column;
  gap: 10px;
  min-width: 0;                    /* long labels ellipsize instead of overflowing */
  padding: 16px 18px;
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  cursor: pointer;
  text-align: left;
}
.wd-card:hover,
.wd-card:focus-visible {
  border-color: var(--line-strong);
  box-shadow: var(--shadow-1);
}
.wd-card-head {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: 8px;
}
.wd-card-title {
  margin: 0;
  font-size: 13px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .05em;
  color: var(--ink-3);
}
.wd-card-arrow { color: var(--ink-4); font-size: 14px; }
.wd-card:hover .wd-card-arrow { color: var(--accent); }

.wd-stat { display: flex; align-items: baseline; gap: 8px; }
.wd-stat-num {
  font-family: var(--font-display);
  font-size: 30px;
  line-height: 1;
  color: var(--ink-1);
}
.wd-stat-label { font-size: 12.5px; color: var(--ink-3); }
.wd-pills { display: flex; flex-wrap: wrap; gap: 6px; }
.wd-meta { margin: 0; font-size: 12.5px; color: var(--ink-3); }
.wd-next { margin: 0; font-size: 12.5px; color: var(--ink-2); }
.wd-next.wd-due { color: var(--danger); font-weight: 600; }

/* KDP small multiples — one series per spark, accent hue, lower-is-better
   axis is inverted in JS so up always means improving. */
.wd-sparks {
  display: flex;
  flex-direction: column;
  gap: 8px;
  margin-top: 2px;
  padding-top: 10px;
  border-top: 1px solid var(--line-soft);
}
.wd-sparks-title { margin: 0; font-size: 11px; color: var(--ink-4); }
.wd-spark-row { display: flex; align-items: center; gap: 8px; min-width: 0; }
.wd-spark-label {
  flex: 1 1 40%;
  min-width: 0;
  font-size: 12px;
  color: var(--ink-2);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.wd-spark { flex: 0 0 100px; }
.wd-spark svg { display: block; width: 100%; height: 30px; }
.wd-spark-hint { flex: 1; font-size: 11.5px; color: var(--ink-4); font-style: italic; }
.wd-spark-latest {
  font-size: 12px;
  font-variant-numeric: tabular-nums;
  color: var(--ink-1);
  white-space: nowrap;
}
.wd-delta { font-size: 11.5px; font-variant-numeric: tabular-nums; color: var(--ink-3); white-space: nowrap; }
.wd-delta.is-up   { color: var(--success); }
.wd-delta.is-down { color: var(--danger); }

/* To-do card — interactive checkboxes, same strikethrough as the drawer. */
.wd-todos { display: flex; flex-direction: column; gap: 6px; }
.wd-todo {
  display: flex;
  align-items: flex-start;
  gap: 8px;
  font-size: 13px;
  color: var(--ink-1);
  line-height: 1.4;
  cursor: pointer;
}
.wd-todo input { margin-top: 2px; accent-color: var(--accent); cursor: pointer; flex: 0 0 auto; }
.wd-todo span { overflow-wrap: anywhere; }
.wd-todo.is-done span { text-decoration: line-through; color: var(--ink-4); }

/* Cover checklist */
.wd-check { display: flex; align-items: center; gap: 8px; margin: 0; font-size: 13px; color: var(--ink-3); }
.wd-check.is-done { color: var(--ink-1); }
.wd-check-mark { color: var(--ink-4); }
.wd-check.is-done .wd-check-mark { color: var(--success); font-weight: 700; }

/* Empty / error / skeleton states */
.wd-card-empty { border-style: dashed; }
.wd-empty-text { margin: 0; font-size: 13px; color: var(--ink-4); }
.wd-setup { font-size: 13px; font-weight: 500; color: var(--accent); }
.wd-card-error { cursor: default; }
.wd-card-error .btn { align-self: flex-start; }
.wd-card-skeleton { cursor: default; }
.wd-skel-line {
  height: 12px;
  border-radius: 6px;
  background: var(--bg-rail);
  animation: wd-skel 1.2s ease-in-out infinite alternate;
}
.wd-skel-wide { height: 26px; width: 55%; }
.wd-skel-short { width: 35%; }
@keyframes wd-skel { from { opacity: .55; } to { opacity: 1; } }

/* The KDP card carries the sparkline block — give it room at wide widths. */
@media (min-width: 900px) {
  .wd-card[data-target="kdp"] { grid-column: span 2; }
}

/* ==========================================================================
   Final cover files (Workshop → Cover → Final Files)
   ========================================================================== */
.cvf-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(320px, 100%), 1fr));
  gap: 16px;
  margin-top: 14px;
}
.cvf-card {
  background: var(--bg-card);
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 16px 18px;
  display: flex;
  flex-direction: column;
  gap: 10px;
  min-width: 0;
}
.cvf-title { margin: 0; font-size: 15px; color: var(--ink-1); }
.cvf-spec { margin: 0; font-size: 12px; color: var(--ink-4); }
.cvf-none { margin: 0; font-size: 13px; color: var(--ink-4); font-style: italic; }
.cvf-thumb img {
  display: block;
  max-width: 120px;
  max-height: 180px;
  border: 1px solid var(--line);
  border-radius: 4px;
}
/* TIFF (or otherwise unrenderable) covers get a file badge, not a broken img. */
.cvf-thumb-file {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 6px;
  width: 120px;
  height: 150px;
  border: 1px dashed var(--line-strong);
  border-radius: 4px;
  background: var(--bg-rail);
  text-decoration: none;
  padding: 8px;
  text-align: center;
}
.cvf-thumb-ext {
  font-size: 16px;
  font-weight: 700;
  letter-spacing: .08em;
  color: var(--ink-2);
}
.cvf-thumb-note { font-size: 10.5px; color: var(--ink-4); line-height: 1.4; }
.cvf-fileline { margin: 0; font-size: 13px; overflow-wrap: anywhere; }
.cvf-fileline a { color: var(--accent); }
.cvf-meta { display: block; font-size: 11.5px; color: var(--ink-4); margin-top: 2px; }
.cvf-checks { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 5px; }
.cvf-check { font-size: 12.5px; color: var(--ink-2); display: flex; gap: 7px; align-items: baseline; }
.cvf-check-glyph { flex: 0 0 auto; }
.cvf-check.is-ok   .cvf-check-glyph { color: var(--success); font-weight: 700; }
.cvf-check.is-warn { color: var(--danger); }
.cvf-check.is-info { color: var(--ink-3); }
.cvf-actions { display: flex; gap: 10px; align-items: center; margin-top: auto; }
.cvf-limit { margin: 12px 0 0; font-size: 11.5px; color: var(--ink-4); }

/* ==========================================================================
   To-Do drawer — rides the scratchpad's slide mechanics (#todo-drawer reuses
   .scratchpad-tab/.scratchpad-panel classes); only the tab position and the
   list content are its own.
   ========================================================================== */
#todo-drawer {
  position: fixed;
  top: 0;
  right: 0;
  height: 100vh;
  z-index: 1000;
  display: flex;
  align-items: flex-start;
  pointer-events: none;
  font-family: var(--font-sans);
}
#todo-drawer .scratchpad-tab,
#todo-drawer .scratchpad-panel { pointer-events: auto; }
/* Above the SCRATCHPAD tab (which is anchored at bottom: 72px). */
#todo-drawer .todo-tab { bottom: 220px; }
#todo-drawer .scratchpad-panel { transform: translateX(100%); }
#todo-drawer.scratchpad-ready .scratchpad-panel { transition: transform 260ms ease; }
#todo-drawer.is-open .scratchpad-panel { transform: translateX(0); }
#todo-drawer.is-open .todo-tab { right: 360px; }
#todo-drawer.scratchpad-ready .todo-tab { transition: right 260ms ease, background .15s ease; }

.todo-count { font-size: 11.5px; opacity: .75; }
.todo-add {
  display: flex;
  gap: 8px;
  padding: 12px 14px;
  border-bottom: 1px solid var(--line-soft);
}
.todo-add input {
  flex: 1;
  font: inherit;
  font-size: 13px;
  padding: 7px 10px;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  background: var(--bg-paper);
  color: var(--ink-1);
}
.todo-list {
  list-style: none;
  margin: 0;
  padding: 8px 6px;
  overflow-y: auto;
  flex: 1;
}
.todo-empty { padding: 10px 10px; font-size: 12.5px; color: var(--ink-4); font-style: italic; }
.todo-item {
  display: flex;
  align-items: flex-start;
  gap: 9px;
  padding: 8px 8px;
  border-radius: 6px;
}
.todo-item:hover { background: var(--bg-rail); }
.todo-check { margin-top: 3px; accent-color: var(--accent); cursor: pointer; flex: 0 0 auto; }
.todo-text {
  flex: 1;
  font-size: 13.5px;
  color: var(--ink-1);
  line-height: 1.45;
  overflow-wrap: anywhere;
}
.todo-item.is-done .todo-text {
  text-decoration: line-through;
  color: var(--ink-4);
}
.todo-delete {
  background: none;
  border: none;
  cursor: pointer;
  font-size: 13px;
  line-height: 1;
  padding: 3px 4px;
  border-radius: 4px;
  opacity: .45;
  flex: 0 0 auto;
}
.todo-item:hover .todo-delete { opacity: 1; }
.todo-delete:hover { background: var(--bg-card); }

@media (max-width: 480px) {
  #todo-drawer.is-open .todo-tab { right: 80vw; }
}
