/* ═══════════════════════════════════════════════════════════════════════
   Lernino — Design System v2
   ───────────────────────────────────────────────────────────────────────
   Aesthetic: warm, friendly, kid-learning — Duolingo/Khan Academy polish.
   White base + orange primary + sky-blue accent. Full-width layouts.
   Modal dialogs for creation flows. Subtle entrance + hover animations.
   ═══════════════════════════════════════════════════════════════════════ */

/* ── Design tokens ─────────────────────────────────────────────────── */
:root {
  /* Neutrals */
  --c-bg:        #fafbfc;
  --c-surface:   #ffffff;
  --c-surface-2: #f8fafc;
  --c-border:    #e2e8f0;
  --c-border-2:  #cbd5e1;
  --c-text:      #0f172a;
  --c-text-2:    #475569;
  --c-text-3:    #94a3b8;

  /* Primary — warm orange */
  --c-primary:    #f97316;
  --c-primary-2:  #ea580c;
  --c-primary-3:  #fff7ed;
  --c-primary-br: #fed7aa;

  /* Accent — sky blue */
  --c-accent:     #0ea5e9;
  --c-accent-2:   #0284c7;
  --c-accent-3:   #f0f9ff;
  --c-accent-br:  #bae6fd;

  /* Semantic */
  --c-ok:     #10b981;
  --c-ok-2:   #059669;
  --c-ok-3:   #ecfdf5;
  --c-ok-br:  #bbf7d0;
  --c-warn:   #f59e0b;
  --c-warn-3: #fffbeb;
  --c-err:    #ef4444;
  --c-err-2:  #dc2626;
  --c-err-3:  #fef2f2;
  --c-err-br: #fecaca;

  /* Gradients for hero surfaces & accents */
  --grad-warm:   linear-gradient(135deg, #fb923c 0%, #f97316 50%, #ea580c 100%);
  --grad-cool:   linear-gradient(135deg, #38bdf8 0%, #0ea5e9 100%);
  --grad-sunset: linear-gradient(135deg, #fb923c 0%, #f472b6 50%, #c084fc 100%);
  --grad-hero:   linear-gradient(135deg, #fff7ed 0%, #ffedd5 50%, #fef3c7 100%);
  --grad-cool-soft: linear-gradient(135deg, #f0f9ff 0%, #e0f2fe 100%);

  /* Radius */
  --r-xs:  6px;
  --r-sm:  10px;
  --r-md:  14px;
  --r-lg:  20px;
  --r-xl:  28px;
  --r-full:9999px;

  /* Shadows */
  --sh-xs: 0 1px 2px 0 rgba(15, 23, 42, 0.04);
  --sh-sm: 0 1px 3px 0 rgba(15, 23, 42, 0.06), 0 1px 2px -1px rgba(15, 23, 42, 0.04);
  --sh-md: 0 4px 6px -1px rgba(15, 23, 42, 0.08), 0 2px 4px -2px rgba(15, 23, 42, 0.04);
  --sh-lg: 0 10px 20px -3px rgba(15, 23, 42, 0.10), 0 4px 8px -4px rgba(15, 23, 42, 0.05);
  --sh-xl: 0 20px 40px -5px rgba(15, 23, 42, 0.12), 0 10px 20px -10px rgba(15, 23, 42, 0.08);
  --sh-warm: 0 12px 28px -8px rgba(249, 115, 22, 0.35);
  --sh-focus: 0 0 0 4px rgba(249, 115, 22, 0.20);
  --sh-focus-blue: 0 0 0 4px rgba(14, 165, 233, 0.20);

  /* Motion */
  --ease:     cubic-bezier(0.22, 0.9, 0.3, 1);
  --ease-bounce: cubic-bezier(0.34, 1.56, 0.64, 1);
  --dur-fast:   140ms;
  --dur-med:    240ms;
  --dur-slow:   380ms;

  /* Layout */
  --wrap-max: 1536px;
}

/* ── Reset & base ──────────────────────────────────────────────────── */
*, *::before, *::after { box-sizing: border-box; }
html, body { margin: 0; padding: 0; }
html { -webkit-text-size-adjust: 100%; }
body {
  font-family: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
  font-feature-settings: "cv11", "ss01", "ss03";
  font-size: 15px;
  line-height: 1.55;
  color: var(--c-text);
  background: var(--c-bg);
  min-height: 100vh;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  letter-spacing: -0.005em;
}
body::before {
  /* Subtle decorative orange blob behind the top */
  content: "";
  position: fixed;
  top: -300px; left: 50%;
  transform: translateX(-50%);
  width: 1200px; height: 600px;
  background: radial-gradient(closest-side, rgba(249, 115, 22, 0.08), transparent 70%);
  pointer-events: none;
  z-index: -1;
}

/* Helper to size a <select> to the same height as a btn-sm, so form rows
   that mix labels + select + small primary button end up visually flush. */
select.h-btn-sm {
  height: 36px;
  padding: 0 32px 0 12px;
  font-size: 14px;
}

/* ── Dictation audio visualiser ──────────────────────────────────────── */
/* Five orange bars that bounce while the TTS audio plays. Pure CSS anim,
   no Web Audio API needed — visually communicates "sound is playing"
   for kids in under 2KB. Goes silent between plays (bars stay at 10%). */
.dict-viz {
  display: inline-flex; align-items: flex-end; gap: 4px;
  height: 28px;
  padding: 0 6px;
}
.dict-viz span {
  display: inline-block;
  width: 4px; height: 10%;
  background: #ff7a3a;
  border-radius: 2px;
  transition: height .15s;
}
.dict-viz.is-active span {
  animation: dict-viz-bounce 0.9s ease-in-out infinite;
}
.dict-viz.is-active span:nth-child(1) { animation-delay: 0.00s; }
.dict-viz.is-active span:nth-child(2) { animation-delay: 0.12s; }
.dict-viz.is-active span:nth-child(3) { animation-delay: 0.24s; }
.dict-viz.is-active span:nth-child(4) { animation-delay: 0.36s; }
.dict-viz.is-active span:nth-child(5) { animation-delay: 0.48s; }
@keyframes dict-viz-bounce {
  0%, 100% { height: 20%; }
  50%      { height: 100%; }
}

/* Dictation action row: make skip button match the primary button height
   so they align cleanly side-by-side regardless of viewport width. */
.dictation-card .row > .btn-lg { min-height: 52px; }

/* ── AI loading overlay ──────────────────────────────────────────────── */
/* Full-screen dim + centered card with an animated sparkle. Shown after
   the parent hits any ✨ Generate button; stays until the page reloads
   with the fresh questions. Pure CSS animation so no dependencies. */
.ai-loading-overlay {
  position: fixed; inset: 0;
  background: rgba(20, 18, 15, 0.55);
  backdrop-filter: blur(3px);
  -webkit-backdrop-filter: blur(3px);
  display: flex; align-items: center; justify-content: center;
  z-index: 9999;
  animation: ai-overlay-in .2s ease;
}
.ai-loading-overlay[hidden] { display: none; }
.ai-loading-card {
  background: #fff;
  border-radius: 16px;
  padding: 32px 40px;
  text-align: center;
  min-width: 280px;
  max-width: 90vw;
  box-shadow: 0 20px 60px rgba(0, 0, 0, 0.25);
  animation: ai-card-in .25s cubic-bezier(.2,.8,.2,1);
}
.ai-loading-sparkle {
  font-size: 56px; line-height: 1;
  margin-bottom: 16px;
  display: inline-block;
  animation: ai-sparkle-pulse 1.2s ease-in-out infinite;
}
.ai-loading-text {
  font-size: 18px; font-weight: 600;
  color: #c2410c;
  margin-bottom: 6px;
}
.ai-loading-sub { margin-bottom: 16px; }
.ai-loading-bar {
  width: 200px;
  height: 6px;
  background: rgba(255, 122, 58, 0.15);
  border-radius: 999px;
  overflow: hidden;
  margin: 0 auto;
  position: relative;
}
.ai-loading-bar-fill {
  position: absolute;
  left: -40%;
  width: 40%;
  height: 100%;
  background: linear-gradient(90deg, transparent, #ff7a3a, transparent);
  animation: ai-bar-slide 1.4s linear infinite;
}
@keyframes ai-overlay-in   { from { opacity: 0 } to { opacity: 1 } }
@keyframes ai-card-in      { from { opacity: 0; transform: translateY(10px) scale(.97) } to { opacity: 1; transform: none } }
@keyframes ai-sparkle-pulse { 0%, 100% { transform: scale(1) rotate(0) } 50% { transform: scale(1.2) rotate(15deg) } }
@keyframes ai-bar-slide    { from { left: -40% } to { left: 100% } }

/* ── Wizard CSV template links (one per question type) ───────────────── */
/* Download tiles inside the "Aus CSV importieren" sub-panel. Styled like
   mini chips so they feel distinct from the big method buttons above. */
.wizard-csv-templates {
  display: flex; flex-wrap: wrap; gap: 8px;
}
.wizard-csv-dl {
  display: inline-flex; align-items: center;
  padding: 8px 14px;
  border: 1.5px solid var(--c-border);
  border-radius: 999px;
  background: var(--c-surface);
  font-size: 13px;
  text-decoration: none;
  color: inherit;
  transition: border-color var(--dur-fast) var(--ease), background var(--dur-fast) var(--ease);
}
.wizard-csv-dl:hover { border-color: var(--c-primary-br); background: rgba(255,122,58,0.05); }

/* ── AI generator cards ───────────────────────────────────────────────── */
/* Every ✨ "Generate with AI" collapsible across the test editor uses this
   styling. Soft orange gradient + sparkle cue signals "magic" without being
   noisy. Collapsed state feels like a subtle banner; expanded state opens
   into a form panel. Scoped via .ai-gen-box / .ai-gen-summary so the same
   look applies to MC, Yes/No, Flashcard, Dictation, and Lesetext. */
.ai-gen-box {
  margin-top: 14px;
  border-radius: 12px;
  background: linear-gradient(135deg, #fff4ec 0%, #ffeedf 100%);
  border: 1.5px solid #ffd4b8;
  overflow: hidden;
  transition: box-shadow .2s var(--ease, ease), border-color .2s var(--ease, ease);
}
.ai-gen-box:hover      { border-color: #ffb38a; }
.ai-gen-box[open]      { box-shadow: 0 2px 10px rgba(255, 122, 58, 0.12); border-color: #ff9a5c; }
.ai-gen-summary {
  cursor: pointer;
  padding: 12px 16px;
  font-weight: 600;
  font-size: 15px;
  color: #b2420c;
  list-style: none;
  display: flex;
  align-items: center;
  gap: 8px;
  transition: background .15s;
  user-select: none;
}
.ai-gen-summary:hover  { background: rgba(255, 122, 58, 0.08); }
.ai-gen-summary::-webkit-details-marker { display: none; }
.ai-gen-summary::marker { content: ""; }
.ai-gen-summary::before {
  content: "▶";
  font-size: 10px;
  transition: transform .2s ease;
  color: #ff7a3a;
  display: inline-block;
}
.ai-gen-box[open] .ai-gen-summary::before { transform: rotate(90deg); }
.ai-gen-form {
  padding: 6px 16px 16px 16px;
  border-top: 1px solid rgba(255, 122, 58, 0.18);
  background: rgba(255, 255, 255, 0.5);
}
.ai-gen-form .field span { color: #7a3510; }

/* ── Auth pages (login, signup) — playful colorful background ─────────── */
/* Applied via body.auth-page, set when hideTopbar is true. Dashboards are
   unaffected. Three soft color blobs match the Lernino logo palette (warm
   orange, playful pink, cool purple-blue) and are heavily blurred so they
   feel like lighting, not shapes. Pseudo-elements use position:fixed so they
   stay put on scroll, and negative z-index so form inputs stay clickable. */
body.auth-page {
  background:
    linear-gradient(135deg,
      #fff7ed 0%,
      #fef3f9 35%,
      #f0f4ff 70%,
      #f5f3ff 100%);
}

/* ── Landing-page override: unified soft-grey canvas ─────────────────
   Login + signup keep the pastel gradient + colourful blobs. The
   marketing landing page uses a single soft-grey (#fafafb, same as
   the footer) so cards, testimonials, and the laptop visually pop
   against it. We target only the landing via :has(.landing-nav) so
   the auth pages stay untouched. Supported in all modern browsers
   since early 2023. */
body.auth-page:has(.landing-nav) {
  background: #fafafb;
}
body.auth-page:has(.landing-nav)::before,
body.auth-page:has(.landing-nav)::after,
body.auth-page:has(.landing-nav) .wrap::before {
  display: none;     /* kill all three coloured blobs on landing */
}
body.auth-page::before {
  /* Override the default body::before with a bigger warm orange blob */
  content: "";
  position: fixed;
  top: -200px; left: -150px;
  width: 700px; height: 700px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(249, 115, 22, 0.35) 0%, rgba(249, 115, 22, 0) 65%);
  filter: blur(40px);
  pointer-events: none;
  z-index: -1;
  transform: none;
  animation: authBlobFloat 14s ease-in-out infinite alternate;
}
body.auth-page::after {
  /* Cool purple-blue blob bottom-right */
  content: "";
  position: fixed;
  bottom: -250px; right: -200px;
  width: 800px; height: 800px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(139, 92, 246, 0.28) 0%, rgba(139, 92, 246, 0) 65%);
  filter: blur(50px);
  pointer-events: none;
  z-index: -1;
  animation: authBlobFloat 18s ease-in-out infinite alternate-reverse;
}

/* A third pink blob injected via a dedicated wrapper pseudo on .wrap.
   We can't chain ::before/::after on body beyond two, so we reuse .wrap. */
body.auth-page .wrap::before {
  content: "";
  position: fixed;
  top: 40%; right: 10%;
  width: 400px; height: 400px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(236, 72, 153, 0.22) 0%, rgba(236, 72, 153, 0) 65%);
  filter: blur(60px);
  pointer-events: none;
  z-index: -1;
  animation: authBlobFloat 12s ease-in-out infinite alternate;
}

@keyframes authBlobFloat {
  0%   { transform: translate(0, 0)     scale(1); }
  100% { transform: translate(40px, -30px) scale(1.08); }
}

/* Lift the auth card above the blobs and give it a slightly stronger shadow
   so it pops on the colorful background. */
body.auth-page .card {
  position: relative;
  z-index: 1;
  box-shadow: 0 20px 60px -20px rgba(49, 46, 129, 0.25),
              0 8px 24px -8px rgba(249, 115, 22, 0.15);
  backdrop-filter: saturate(180%) blur(8px);
  background: rgba(255, 255, 255, 0.92);
}

/* Respect users who prefer reduced motion — no blob animation. */
@media (prefers-reduced-motion: reduce) {
  body.auth-page::before,
  body.auth-page::after,
  body.auth-page .wrap::before { animation: none; }
}

a { color: var(--c-accent-2); text-decoration: none; transition: color var(--dur-fast) var(--ease); }
a:hover { color: var(--c-accent); }

h1, h2, h3, h4 { margin: 0; letter-spacing: -0.022em; font-weight: 700; color: var(--c-text); line-height: 1.2; }
h1 { font-size: 34px; letter-spacing: -0.03em; font-weight: 800; }
h2 { font-size: 22px; }
h3 { font-size: 16px; }
p  { margin: 0; }

button, input, select, textarea { font-family: inherit; font-size: inherit; color: inherit; }

::selection { background: #ffedd5; color: #9a3412; }

/* ── Motion prefs ──────────────────────────────────────────────────── */
@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;
  }
}

/* ── Keyframes ─────────────────────────────────────────────────────── */
@keyframes fadeInUp {
  from { opacity: 0; transform: translateY(14px); }
  to   { opacity: 1; transform: translateY(0); }
}
@keyframes fadeIn {
  from { opacity: 0; }
  to   { opacity: 1; }
}
@keyframes popIn {
  0%   { opacity: 0; transform: scale(0.6); }
  60%  { transform: scale(1.06); }
  100% { opacity: 1; transform: scale(1); }
}
@keyframes slideUp {
  from { opacity: 0; transform: translateY(40px) scale(0.97); }
  to   { opacity: 1; transform: translateY(0) scale(1); }
}
@keyframes shimmer {
  0%   { background-position: -200% 0; }
  100% { background-position: 200% 0; }
}
@keyframes floaty {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-4px); }
}
@keyframes wiggle {
  0%, 100% { transform: rotate(0deg); }
  25%      { transform: rotate(-6deg); }
  75%      { transform: rotate(6deg); }
}

/* ── Layout shell ──────────────────────────────────────────────────── */
.topbar {
  position: sticky;
  top: 0;
  z-index: 50;
  display: flex;
  align-items: center;
  gap: 16px;
  /* Horizontal padding grows on wide viewports so the topbar's content
     (logo on the left, avatar/actions on the right) lines up with the
     1536px .wrap column below. max() keeps padding at 32px minimum on
     narrow screens. The white frosted background still spans the full
     viewport since .topbar itself has no max-width. */
  padding: 16px max(32px, calc((100% - var(--wrap-max)) / 2 + 32px));
  background: rgba(255, 255, 255, 0.88);
  backdrop-filter: saturate(180%) blur(14px);
  -webkit-backdrop-filter: saturate(180%) blur(14px);
  border-bottom: 1px solid var(--c-border);
}
.topbar .brand {
  display: inline-flex;
  align-items: center;
  gap: 12px;
  font-size: 17px;
  font-weight: 800;
  letter-spacing: -0.02em;
  color: var(--c-text);
}
.topbar .brand:hover { text-decoration: none; }
.brand-logo {
  height: 88px;
  width: auto;
  display: block;
  transition: transform var(--dur-med) var(--ease-bounce);
}
.brand:hover .brand-logo { transform: rotate(-2deg) scale(1.04); }

/* Centered logo for auth pages (login, signup, error cards). The wordmark
   crop is ~2.6:1, so 90px tall renders ~234px wide — plenty present
   without dominating the card. */
.brand-logo-hero {
  display: block;
  height: 90px;
  width: auto;
  margin: 0 auto 12px;
  /* Same white-bg blend as .landing-brand-logo — see note there. */
  mix-blend-mode: multiply;
}
.brand-logo {
  mix-blend-mode: multiply;
}

/* Shrink the topbar logo a bit on small screens so it doesn't dominate. */
@media (max-width: 720px) {
  .brand-logo      { height: 60px; }
  .brand-logo-hero { height: 72px; }
}

.topbar .spacer { flex: 1; }
/* "Kaffee"-Unterstuetzen chip in the topbar — a warm, inviting call that
   sits left of the user avatar. Idle state is an outlined orange pill that
   reads as a gentle nudge; hover fills with the warm gradient to turn it
   into a primary action. */
.topbar .coffee-chip {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin-right: 14px;
  padding: 7px 14px 7px 10px;
  border: 1.5px solid rgba(249, 115, 22, 0.45);
  background: #fff8f0;
  border-radius: 999px;
  font-size: 13px;
  font-weight: 700;
  color: var(--c-primary);
  text-decoration: none;
  letter-spacing: 0.01em;
  transition: background var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.topbar .coffee-chip:hover {
  background: var(--grad-warm);
  border-color: transparent;
  color: #fff;
  text-decoration: none;
  transform: translateY(-1px);
  box-shadow: var(--sh-warm);
}
.topbar .coffee-chip-emoji {
  font-size: 16px;
  line-height: 1;
  filter: saturate(1.1);
}
.topbar .coffee-chip:hover .coffee-chip-emoji {
  animation: coffee-chip-wiggle 0.6s var(--ease-bounce);
}
@keyframes coffee-chip-wiggle {
  0%   { transform: rotate(0deg) scale(1); }
  30%  { transform: rotate(-12deg) scale(1.1); }
  60%  { transform: rotate(8deg)  scale(1.05); }
  100% { transform: rotate(0deg) scale(1); }
}
/* On narrow screens keep the icon, drop the label so it stays a tap target
   without stealing room from the user avatar and Abmelden button. */
@media (max-width: 560px) {
  .topbar .coffee-chip { padding: 7px 10px; margin-right: 8px; }
  .topbar .coffee-chip-text { display: none; }
}

/* ── Topbar "⋯" menu: parent tools tucked away ─────────────────────
   Native <details>/<summary> dropdown — zero-JS for the open/close
   mechanics, keyboard-accessible out of the box. We remove the default
   disclosure triangle and anchor the panel to the trigger. */
.topbar-menu {
  position: relative;
  margin-right: 10px;
}
.topbar-menu-trigger {
  list-style: none;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 38px;
  height: 38px;
  border-radius: 50%;
  background: var(--c-surface-2);
  border: 1px solid var(--c-border);
  color: var(--c-text-2);
  font-size: 20px;
  font-weight: 800;
  cursor: pointer;
  line-height: 1;
  user-select: none;
  transition: background var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.topbar-menu-trigger::-webkit-details-marker { display: none; }
.topbar-menu-trigger::marker { content: ""; }
.topbar-menu-trigger:hover,
.topbar-menu[open] .topbar-menu-trigger {
  background: var(--c-primary-3);
  color: var(--c-primary);
  border-color: var(--c-primary-br);
}
.topbar-menu-panel {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  min-width: 220px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  box-shadow: 0 12px 32px -8px rgba(0, 0, 0, 0.18);
  padding: 6px;
  z-index: 60;
  animation: topbar-menu-in 0.12s var(--ease);
}
@keyframes topbar-menu-in {
  from { opacity: 0; transform: translateY(-4px); }
  to   { opacity: 1; transform: translateY(0); }
}
.topbar-menu-item {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 12px;
  border-radius: var(--r-sm);
  font-size: 14px;
  font-weight: 600;
  color: var(--c-text);
  text-decoration: none;
  transition: background var(--dur-fast) var(--ease);
}
.topbar-menu-item:hover {
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  text-decoration: none;
}
.topbar-menu-item > span[aria-hidden] {
  font-size: 16px;
  line-height: 1;
}

/* ── Settings page ──────────────────────────────────────────────────
   Identity row at the top (read-only) + three grouped cards in a grid
   below. Each card has its own submit, so one failing form doesn't
   wipe the others' input. */
.settings-identity {
  display: flex;
  align-items: center;
  gap: 18px;
  padding: 20px 24px;
  background: linear-gradient(135deg, #fff7ed 0%, #fefce8 100%);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  margin-bottom: 28px;
}
.settings-avatar {
  width: 64px;
  height: 64px;
  border-radius: 50%;
  background: var(--grad-warm);
  color: #fff;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 26px;
  font-weight: 800;
  flex-shrink: 0;
  box-shadow: var(--sh-warm);
}
.settings-avatar-emoji {
  background: linear-gradient(135deg, #fff 0%, #fef3f9 100%);
  border: 1px solid rgba(249, 115, 22, 0.18);
  font-size: 36px;
  line-height: 1;
  text-shadow: none;
}
.settings-identity-body { flex: 1; min-width: 0; }
.settings-identity-label {
  font-size: 11px;
  font-weight: 800;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--c-text-3);
  margin-bottom: 4px;
}
.settings-identity-name {
  font-size: 22px;
  font-weight: 800;
  letter-spacing: -0.01em;
  color: var(--c-text);
}
.settings-identity-sub {
  margin-top: 4px;
  display: inline-flex;
  align-items: center;
  flex-wrap: wrap;
}

.settings-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
  gap: 20px;
}
@media (max-width: 860px) {
  .settings-grid { grid-template-columns: 1fr; }
}

.settings-divider {
  height: 1px;
  background: var(--c-border);
  margin: 10px 0 0;
}

.settings-supporter {
  padding: 14px 16px;
  background: #ecfdf5;
  border: 1px solid #a7f3d0;
  border-radius: var(--r-sm);
  margin-top: 4px;
}
.settings-supporter-head {
  display: flex;
  align-items: center;
  gap: 10px;
  color: #047857;
}

/* ── Language switcher ──────────────────────────────────────────────
   Tiny dropdown in the top nav (and landing nav). Native <details> so
   no JS needed — one click to open, click outside to close. Active
   language chip gets a warm highlight. */
.lang-menu { position: relative; margin-right: 8px; }
.lang-trigger {
  list-style: none;
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 10px;
  border-radius: 999px;
  border: 1px solid var(--c-border);
  background: var(--c-surface);
  color: var(--c-text-2);
  font-size: 12px;
  font-weight: 700;
  cursor: pointer;
  user-select: none;
  transition: background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease);
}
.lang-trigger::-webkit-details-marker { display: none; }
.lang-trigger::marker { content: ""; }
.lang-trigger:hover,
.lang-menu[open] .lang-trigger {
  background: var(--c-primary-3);
  border-color: var(--c-primary-br);
  color: var(--c-primary-2);
}
.lang-trigger-code { font-feature-settings: "tnum"; letter-spacing: 0.02em; }
.lang-panel {
  position: absolute;
  top: calc(100% + 6px);
  right: 0;
  min-width: 160px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  box-shadow: 0 12px 32px -8px rgba(0, 0, 0, 0.18);
  padding: 4px;
  z-index: 60;
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.lang-item {
  padding: 8px 12px;
  border-radius: var(--r-sm);
  font-size: 13px;
  font-weight: 600;
  color: var(--c-text);
  text-decoration: none;
  transition: background var(--dur-fast) var(--ease);
}
.lang-item:hover {
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  text-decoration: none;
}
.lang-item-active {
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  font-weight: 800;
}

/* Screen-reader-only helper for accessible labels. */
.visually-hidden {
  position: absolute;
  width: 1px; height: 1px;
  padding: 0; margin: -1px;
  overflow: hidden;
  clip: rect(0, 0, 0, 0);
  white-space: nowrap;
  border: 0;
}
.topbar .who {
  display: flex;
  flex-direction: row;
  align-items: center;
  gap: 10px;
  margin-right: 10px;
}
/* Parent variant: the whole avatar+name cluster is a link to the
   settings page. Subtle hover — just a background blush so the cue
   reads "clickable" without shouting. */
.topbar .who-link {
  padding: 4px 8px;
  border-radius: 999px;
  text-decoration: none;
  color: inherit;
  transition: background var(--dur-fast) var(--ease);
}
.topbar .who-link:hover {
  background: var(--c-primary-3);
  text-decoration: none;
}
.topbar .who-link:hover .who-name {
  color: var(--c-primary);
}
.topbar .who-name { font-size: 14px; font-weight: 600; color: var(--c-text); }
/* Supporter badge — tiny green pill next to the display name for users
   who have backed Lernino via the Unterstuetzen flow. */
.supporter-badge {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 3px 8px;
  background: #ecfdf5;
  color: #047857;
  border: 1px solid #a7f3d0;
  border-radius: 999px;
  font-size: 11px;
  font-weight: 800;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  line-height: 1;
  flex-shrink: 0;
}
.supporter-badge span[aria-hidden] { font-size: 12px; line-height: 1; }
@media (max-width: 560px) {
  .supporter-badge-text { display: none; }
  .supporter-badge { padding: 3px 6px; }
}
/* Avatar circle with first initial OR a gender-role emoji. When showing an
   emoji (.avatar-emoji), we drop the warm gradient background in favor of a
   neutral pastel so the emoji's own colors read clearly. The letter variant
   keeps the warm brand gradient for identity. */
.topbar .avatar {
  width: 38px;
  height: 38px;
  border-radius: 50%;
  background: var(--grad-warm);
  color: #fff;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 14px;
  font-weight: 700;
  flex-shrink: 0;
  box-shadow: var(--sh-warm), inset 0 1px 0 rgba(255, 255, 255, 0.35);
  text-shadow: 0 1px 2px rgba(0, 0, 0, 0.15);
  letter-spacing: 0;
}
.topbar .avatar.avatar-emoji {
  background: linear-gradient(135deg, #fff7ed 0%, #fef3f9 100%);
  box-shadow: 0 2px 8px -2px rgba(249, 115, 22, 0.25), inset 0 1px 0 rgba(255, 255, 255, 0.8);
  border: 1px solid rgba(249, 115, 22, 0.18);
  font-size: 22px;
  text-shadow: none;
  line-height: 1;
}
/* Hide the name on narrow screens — the avatar alone is enough. */
@media (max-width: 720px) {
  .topbar .who-name { display: none; }
}
.inline { display: inline-block; }

.wrap {
  max-width: var(--wrap-max);
  margin: 0 auto;
  padding: 36px 32px 80px;
  animation: fadeInUp var(--dur-slow) var(--ease) both;
}
.wrap-narrow { max-width: 480px; }

/* ── Page header + hero ────────────────────────────────────────────── */
.page-head { margin-bottom: 28px; }
.crumb {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 13px;
  font-weight: 500;
  color: var(--c-text-3);
  margin-bottom: 12px;
  transition: color var(--dur-fast) var(--ease), transform var(--dur-fast) var(--ease);
}
.crumb:hover { color: var(--c-primary); text-decoration: none; transform: translateX(-2px); }

.hero {
  background: var(--grad-hero);
  border: 1px solid var(--c-primary-br);
  border-radius: var(--r-xl);
  padding: 44px 48px;
  margin-bottom: 32px;
  position: relative;
  overflow: hidden;
  animation: fadeInUp 500ms var(--ease) both;
}
.hero::before {
  content: "";
  position: absolute;
  top: -80px; right: -80px;
  width: 280px; height: 280px;
  background: radial-gradient(closest-side, rgba(251, 146, 60, 0.22), transparent 70%);
  pointer-events: none;
}
.hero::after {
  content: "";
  position: absolute;
  bottom: -60px; left: 20%;
  width: 220px; height: 220px;
  background: radial-gradient(closest-side, rgba(14, 165, 233, 0.12), transparent 70%);
  pointer-events: none;
}
.hero > * { position: relative; }
.hero h1 {
  font-size: 42px;
  letter-spacing: -0.035em;
  margin-bottom: 6px;
}
.hero h1 .wave {
  display: inline-block;
  transform-origin: 70% 70%;
  animation: wiggle 1.6s var(--ease) 1;
}
.hero .sub {
  font-size: 17px;
  color: var(--c-text-2);
  max-width: 560px;
  margin-top: 8px;
}
.hero .stats {
  display: flex;
  flex-wrap: wrap;
  gap: 28px;
  margin-top: 24px;
}
.hero .stat {
  display: flex;
  flex-direction: column;
}
.hero .stat-val {
  font-size: 32px;
  font-weight: 800;
  color: var(--c-text);
  line-height: 1;
  font-feature-settings: "tnum";
  letter-spacing: -0.03em;
}
.hero .stat-lbl {
  font-size: 12px;
  font-weight: 600;
  color: var(--c-text-2);
  margin-top: 6px;
  text-transform: uppercase;
  letter-spacing: 0.06em;
}
/* ── Per-kid stat strip (parent dashboard hero) ─────────────────────────── */
/* One card per child, designed to answer "how are they doing?" in a glance
   instead of showing flat inventory counts. Three states: assigned=0 (empty),
   attempted=0 (waiting), or has results (big score + pass ratio). */
.hero .kid-stat-strip {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
  gap: 16px;
  margin-top: 24px;
  max-width: 800px;
}
.kid-stat-card {
  background: rgba(255, 255, 255, 0.7);
  border: 1px solid rgba(249, 115, 22, 0.15);
  border-radius: var(--r-md);
  padding: 18px 20px;
  backdrop-filter: saturate(160%) blur(6px);
  box-shadow: 0 4px 12px -4px rgba(249, 115, 22, 0.12);
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.kid-stat-card:hover {
  transform: translateY(-2px);
  box-shadow: 0 8px 20px -6px rgba(249, 115, 22, 0.2);
}
.kid-stat-head {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 14px;
}
.kid-stat-emoji {
  font-size: 28px;
  line-height: 1;
}
.kid-stat-name {
  font-size: 16px;
  font-weight: 700;
  color: var(--c-text);
}
.kid-stat-score {
  font-size: 38px;
  font-weight: 800;
  line-height: 1;
  letter-spacing: -0.03em;
  font-feature-settings: "tnum";
  display: flex;
  align-items: baseline;
  gap: 8px;
}
.kid-stat-score-good { color: #16a34a; }
.kid-stat-score-mid  { color: #d97706; }
.kid-stat-score-bad  { color: #dc2626; }
.kid-stat-badge {
  font-size: 20px;
  line-height: 1;
}
.kid-stat-sub {
  margin-top: 4px;
  margin-bottom: 10px;
}
.kid-stat-progress {
  font-size: 13px;
  color: var(--c-text-2);
  padding-top: 10px;
  border-top: 1px solid rgba(0, 0, 0, 0.06);
}
.kid-stat-empty {
  display: flex;
  flex-direction: column;
  gap: 6px;
  padding: 8px 0 4px;
  color: var(--c-text-2);
  font-size: 14px;
}
.kid-stat-empty-icon {
  font-size: 28px;
  line-height: 1;
}

/* ── Hero CTA row ───────────────────────────────────────────────────────── */
.hero .hero-cta {
  margin-top: 28px;
  display: flex;
  gap: 12px;
  flex-wrap: wrap;
}

/* Text helpers */
.muted { color: var(--c-text-2); }
.small { font-size: 12px; }
.tiny  { font-size: 11px; }
.count {
  font-size: 12px;
  color: var(--c-text-2);
  font-weight: 600;
  margin-left: 8px;
  background: var(--c-surface-2);
  padding: 3px 10px;
  border-radius: var(--r-full);
  border: 1px solid var(--c-border);
}

/* ── Sections ──────────────────────────────────────────────────────── */
.section { margin-bottom: 40px; animation: fadeInUp var(--dur-slow) var(--ease) both; }
.section:nth-child(2) { animation-delay: 60ms; }
.section:nth-child(3) { animation-delay: 120ms; }
.section:nth-child(4) { animation-delay: 180ms; }
.section-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 16px;
  gap: 16px;
  flex-wrap: wrap;
}
.section-head h2 { display: flex; align-items: center; gap: 8px; }
.section-actions { display: flex; gap: 10px; align-items: center; flex-wrap: wrap; }

/* ── Cards ─────────────────────────────────────────────────────────── */
.card {
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 28px;
  margin-bottom: 16px;
  box-shadow: var(--sh-xs);
  transition: border-color var(--dur-med) var(--ease), box-shadow var(--dur-med) var(--ease), transform var(--dur-med) var(--ease);
}
.card h3 {
  margin: 0 0 16px;
  font-size: 15px;
  font-weight: 700;
  letter-spacing: -0.01em;
}
.card-narrow { max-width: 480px; margin: 72px auto; padding: 40px; animation: slideUp var(--dur-slow) var(--ease) both; }
.card-wide   { max-width: 780px; margin: 36px auto; padding: 40px; }

/* ── Buttons ───────────────────────────────────────────────────────── */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  font-family: inherit;
  font-size: 14px;
  font-weight: 700;
  letter-spacing: -0.005em;
  padding: 12px 20px;
  border: 1px solid transparent;
  border-radius: var(--r-md);
  cursor: pointer;
  text-decoration: none;
  white-space: nowrap;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease);
  user-select: none;
}
.btn:hover { text-decoration: none; }
.btn:active { transform: translateY(1px) scale(0.985); }
.btn:focus-visible { outline: none; box-shadow: var(--sh-focus); }

.btn-primary {
  background: var(--grad-warm);
  color: #ffffff;
  border-color: transparent;
  box-shadow: var(--sh-warm), inset 0 1px 0 rgba(255, 255, 255, 0.25);
}
.btn-primary:hover {
  transform: translateY(-1px);
  box-shadow: 0 16px 34px -10px rgba(249, 115, 22, 0.45), inset 0 1px 0 rgba(255, 255, 255, 0.3);
  color: #ffffff;
}

.btn-accent {
  background: var(--c-accent);
  color: #ffffff;
  border-color: var(--c-accent);
  box-shadow: 0 6px 14px -4px rgba(14, 165, 233, 0.35);
}
.btn-accent:hover {
  background: var(--c-accent-2);
  border-color: var(--c-accent-2);
  transform: translateY(-1px);
  color: #ffffff;
}

.btn-ghost {
  background: var(--c-surface);
  color: var(--c-text);
  border-color: var(--c-border);
}
.btn-ghost:hover {
  background: var(--c-surface-2);
  color: var(--c-text);
  border-color: var(--c-border-2);
}

.btn-soft {
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  border-color: var(--c-primary-br);
}
.btn-soft:hover {
  background: #ffedd5;
  color: var(--c-primary-2);
  border-color: #fdba74;
}

.btn-sm { font-size: 13px; padding: 9px 16px; border-radius: var(--r-sm); }
.btn-lg { font-size: 16px; padding: 15px 28px; border-radius: var(--r-md); font-weight: 700; }
.btn-xl { font-size: 17px; padding: 18px 32px; border-radius: var(--r-md); font-weight: 700; }
.btn-block { width: 100%; }

/* ── Forms ─────────────────────────────────────────────────────────── */
.field { display: block; margin-bottom: 16px; }
.field > span {
  display: block;
  font-size: 12px;
  font-weight: 600;
  color: var(--c-text-2);
  margin-bottom: 7px;
  letter-spacing: 0;
}
.field input,
.field textarea,
.field select,
input[type="text"],
input[type="email"],
input[type="password"],
input[type="tel"],
input[type="number"],
textarea,
select {
  width: 100%;
  font-size: 14px;
  font-family: inherit;
  padding: 12px 14px;
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-sm);
  background: var(--c-surface);
  color: var(--c-text);
  transition: border-color var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
  line-height: 1.4;
}
input::placeholder, textarea::placeholder { color: var(--c-text-3); }
input:focus, textarea:focus, select:focus,
.field input:focus, .field textarea:focus, .field select:focus {
  outline: none;
  border-color: var(--c-primary);
  box-shadow: var(--sh-focus);
  background: var(--c-surface);
}
.field textarea { min-height: 92px; resize: vertical; }
.field-hint { font-size: 12px; color: var(--c-text-3); margin-top: 6px; }

/* Hero field — the primary natural-language prompt in the AI dialog.
   Larger label, amber focus accent, a little breathing room so it reads
   as "start here" vs the classification fields below it. */
.field-hero {
  padding: 14px 16px;
  border-radius: 12px;
  background: linear-gradient(135deg, #fffbeb 0%, #fef3c7 100%);
  border: 1px solid #fcd34d;
  margin-bottom: 18px;
}
.field-hero > span {
  font-size: 14px;
  font-weight: 700;
  color: #78350f;
  letter-spacing: 0;
  margin-bottom: 8px;
}
.field-hero textarea {
  background: #fff;
  font-size: 15px;
  line-height: 1.5;
  border-color: #fcd34d;
}
.field-hero textarea:focus {
  border-color: #d97706;
  box-shadow: 0 0 0 3px rgba(245, 158, 11, 0.22);
}
.field-hero .field-hint {
  color: #92400e;
  opacity: 0.85;
}
/* Small header above the classification fields — visually softer than
   an <h4> but clearly separates the two zones of the form. */
.field-group-sub {
  margin-top: 6px;
  padding-top: 10px;
  border-top: 1px dashed var(--c-border);
}

/* Fieldset-based radio picker used for gender selection. Styled so each
   option becomes a clickable pill, with the checked state lit up warm. */
fieldset.field { border: none; padding: 0; margin: 0 0 16px; }
.radio-row {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}
.radio-row label {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 10px 14px;
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-sm);
  background: var(--c-surface);
  font-size: 14px;
  cursor: pointer;
  transition: border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
  user-select: none;
}
.radio-row label:hover { border-color: var(--c-primary-br); }
.radio-row input[type="radio"] {
  width: auto;
  margin: 0;
  accent-color: var(--c-primary);
}
.radio-row label:has(input[type="radio"]:checked) {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: var(--sh-focus);
}

input[type="file"] {
  font-size: 13px;
  padding: 10px 12px;
  background: var(--c-accent-3);
  border: 1.5px dashed var(--c-accent-br);
  border-radius: var(--r-sm);
  color: var(--c-text-2);
  cursor: pointer;
}
input[type="file"]:hover { background: #e0f2fe; }
input[type="file"]::file-selector-button {
  border: 1px solid var(--c-accent-br);
  background: var(--c-surface);
  padding: 6px 14px;
  margin-right: 12px;
  border-radius: var(--r-xs);
  font-weight: 700;
  color: var(--c-accent-2);
  cursor: pointer;
  font-size: 12px;
}

.row {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  align-items: center;
}

.check {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 12px 16px;
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-sm);
  margin-bottom: 8px;
  font-size: 14px;
  font-weight: 500;
  cursor: pointer;
  transition: background var(--dur-fast) var(--ease), border-color var(--dur-fast) var(--ease);
}
.check:hover { background: var(--c-primary-3); border-color: var(--c-primary-br); }
.check input[type="checkbox"] {
  accent-color: var(--c-primary);
  width: 18px;
  height: 18px;
}
.check:has(input:checked) {
  background: var(--c-primary-3);
  border-color: var(--c-primary);
}

/* ── Alerts & flash ────────────────────────────────────────────────── */
.alert, .flash {
  padding: 14px 18px;
  border-radius: var(--r-sm);
  font-size: 14px;
  font-weight: 500;
  margin-bottom: 16px;
  border: 1.5px solid transparent;
  display: flex;
  align-items: center;
  gap: 10px;
  animation: fadeInUp var(--dur-med) var(--ease) both;
}
.alert-error, .flash-error { background: var(--c-err-3); border-color: var(--c-err-br); color: var(--c-err-2); }
.flash-ok { background: var(--c-ok-3); border-color: var(--c-ok-br); color: var(--c-ok-2); }

.empty {
  background: var(--c-surface);
  border: 2px dashed var(--c-border-2);
  border-radius: var(--r-lg);
  padding: 48px 24px;
  text-align: center;
  color: var(--c-text-2);
  font-size: 14px;
}
.empty-big {
  background: var(--grad-cool-soft);
  border: 2px dashed var(--c-accent-br);
  padding: 64px 32px;
}
.empty-big .empty-icon {
  font-size: 56px;
  margin-bottom: 16px;
  display: inline-block;
  animation: floaty 3s var(--ease) infinite;
}
.empty-big h3 {
  font-size: 20px;
  color: var(--c-text);
  margin-bottom: 8px;
}
.empty-big p { max-width: 420px; margin: 0 auto 20px; }

/* ── Grids ─────────────────────────────────────────────────────────── */
.grid { display: grid; gap: 16px; }
.grid-kids  { grid-template-columns: repeat(auto-fill, minmax(250px, 1fr)); }
.grid-tests { grid-template-columns: repeat(auto-fill, minmax(280px, 1fr)); }
.grid-stats { grid-template-columns: repeat(auto-fill, minmax(180px, 1fr)); margin-bottom: 24px; }
.two-col { display: grid; grid-template-columns: 1fr 1fr; gap: 20px; }
@media (max-width: 860px) { .two-col { grid-template-columns: 1fr; } }

/* ── Kid cards ─────────────────────────────────────────────────────── */
.kid-card {
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 22px;
  display: flex;
  align-items: center;
  gap: 16px;
  box-shadow: var(--sh-xs);
  transition: transform var(--dur-med) var(--ease),
              box-shadow var(--dur-med) var(--ease),
              border-color var(--dur-fast) var(--ease);
  animation: fadeInUp var(--dur-slow) var(--ease) both;
}
.kid-card:hover {
  transform: translateY(-3px);
  box-shadow: var(--sh-md);
  border-color: var(--c-primary-br);
}
.kid-avatar {
  width: 54px;
  height: 54px;
  border-radius: var(--r-full);
  background: var(--grad-cool-soft);
  display: grid;
  place-items: center;
  font-size: 26px;
  flex-shrink: 0;
  border: 2px solid var(--c-accent-br);
}
.kid-info { flex: 1; min-width: 0; }
.kid-info strong { font-size: 15px; display: block; margin-bottom: 2px; }
.kid-info code {
  font-family: ui-monospace, Menlo, Consolas, monospace;
  font-size: 11px;
  background: var(--c-surface-2);
  padding: 1px 7px;
  border-radius: var(--r-xs);
  color: var(--c-text-2);
  border: 1px solid var(--c-border);
}
.add-card {
  background: var(--c-surface);
  border: 2px dashed var(--c-border-2);
  border-radius: var(--r-md);
  padding: 22px;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  cursor: pointer;
  color: var(--c-text-2);
  font-size: 14px;
  font-weight: 600;
  transition: all var(--dur-fast) var(--ease);
}
.add-card:hover {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  transform: translateY(-2px);
}
.add-card .add-icon {
  width: 32px;
  height: 32px;
  border-radius: var(--r-full);
  background: var(--c-primary-3);
  border: 2px solid var(--c-primary-br);
  display: grid;
  place-items: center;
  color: var(--c-primary);
  font-size: 18px;
  font-weight: 800;
  transition: all var(--dur-fast) var(--ease);
}
.add-card:hover .add-icon { background: var(--c-primary); color: #fff; border-color: var(--c-primary); transform: rotate(90deg); }

/* ── Subject / topic / test tree ───────────────────────────────────── */
.subject-block {
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 26px 30px;
  margin-bottom: 16px;
  box-shadow: var(--sh-xs);
  animation: fadeInUp var(--dur-slow) var(--ease) both;
  transition: border-color var(--dur-fast) var(--ease), box-shadow var(--dur-fast) var(--ease);
}
.subject-block:hover { border-color: var(--c-primary-br); box-shadow: var(--sh-sm); }
.subject-head {
  display: flex;
  align-items: center;
  gap: 14px;
  flex-wrap: wrap;
  margin-bottom: 14px;
  padding-bottom: 14px;
  border-bottom: 1px solid var(--c-border);
}
.subject-head h3 {
  margin: 0;
  font-size: 18px;
  font-weight: 800;
  flex: 1;
  display: flex;
  align-items: center;
  gap: 10px;
}
.subject-head h3::before {
  content: "";
  width: 8px;
  height: 28px;
  background: var(--grad-warm);
  border-radius: var(--r-full);
}
.topic-block {
  border-left: 2px solid var(--c-accent-br);
  padding: 4px 0 4px 18px;
  margin: 14px 0;
}
.topic-head {
  display: flex;
  align-items: center;
  gap: 12px;
  flex-wrap: wrap;
  margin-bottom: 10px;
}
.topic-head strong { flex: 1; font-size: 14px; color: var(--c-text); }

.test-list { list-style: none; padding: 0; margin: 10px 0 0; }
.test-list li {
  display: flex;
  align-items: stretch;
  gap: 6px;
  margin-bottom: 6px;
}
.test-list li a {
  flex: 1;
  min-width: 0;
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 12px 16px;
  border-radius: var(--r-sm);
  background: var(--c-surface-2);
  font-size: 13px;
  color: var(--c-text);
  font-weight: 600;
  transition: all var(--dur-fast) var(--ease);
  border: 1px solid var(--c-border);
}
.test-list li a:hover {
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  text-decoration: none;
  transform: translateX(3px);
  border-color: var(--c-primary-br);
}
/* Shared action row that sits next to the main link in a test-list li.
   Both the standalone edit <button> and the form-wrapped delete <button>
   get IDENTICAL dimensions (min-width + min-height) so the row reads
   evenly regardless of wrapper markup. This replaces the earlier
   .test-list-action / .test-list-delete classes, which had inconsistent
   rules depending on whether the button was bare or form-wrapped. */
.test-list-actions {
  display: flex;
  align-items: stretch;
  gap: 4px;
  flex-shrink: 0;
}
.test-list-actions > button,
.test-list-actions > form > button {
  min-width: 44px;
  padding: 0 12px;
  height: 100%;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}
.test-list-actions > form {
  display: flex;
  align-items: stretch;
}

/* Uniform action row for subject + topic headers (+ edit + delete).
   Uses the same min-width so headers match list rows visually. */
.head-actions {
  display: flex;
  align-items: center;
  gap: 6px;
  flex-shrink: 0;
}
.head-actions > button,
.head-actions > form > button {
  min-width: 44px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}
.head-actions > form { display: inline-flex; }

/* ── Question list (test editor) ───────────────────────────────────── */
.q-list { list-style: none; padding: 0; margin: 0; counter-reset: q; }
.q-item {
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 22px 28px 20px 74px;
  margin-bottom: 14px;
  position: relative;
  box-shadow: var(--sh-xs);
  animation: fadeInUp var(--dur-slow) var(--ease) both;
}
.q-item::before {
  counter-increment: q;
  content: counter(q);
  position: absolute;
  top: 22px;
  left: 22px;
  width: 34px;
  height: 34px;
  display: grid;
  place-items: center;
  border-radius: var(--r-full);
  background: var(--grad-warm);
  color: #fff;
  font-size: 14px;
  font-weight: 800;
  box-shadow: var(--sh-sm);
}
.q-prompt {
  font-weight: 600;
  color: var(--c-text);
  margin-bottom: 14px;
  font-size: 15px;
  line-height: 1.5;
}
.q-options { list-style: none; padding: 0; margin: 0 0 12px; display: flex; flex-direction: column; gap: 6px; }
.q-options li {
  padding: 10px 14px;
  border-radius: var(--r-sm);
  font-size: 13px;
  color: var(--c-text-2);
  background: var(--c-surface-2);
  border: 1.5px solid transparent;
}
.q-options li strong { color: var(--c-text-3); margin-right: 6px; }
.q-options li.correct {
  background: var(--c-ok-3);
  color: var(--c-ok-2);
  font-weight: 600;
  border-color: var(--c-ok-br);
}
.q-options li.correct strong { color: var(--c-ok); }
.q-options li.correct::after {
  content: "✓";
  margin-left: 8px;
  color: var(--c-ok);
  font-weight: 800;
}

/* Edit + delete action row on each question block in the test editor.
   Matches .test-list-actions / .head-actions so the whole app has one
   consistent icon-button size for destructive/edit actions. */
.q-actions {
  display: flex;
  gap: 6px;
  align-items: stretch;
  flex-shrink: 0;
}
.q-actions > a,
.q-actions > button,
.q-actions > form > button {
  min-width: 44px;
  padding: 0 12px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}
.q-actions > form {
  display: inline-flex;
  align-items: stretch;
}

/* Type badge on each question row in the editor's question list */
.q-type-badge {
  display: inline-block;
  margin-bottom: 6px;
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.06em;
}

/* Flashcard back-of-card preview in the editor question list */
.q-flashback {
  margin: 0 0 12px;
  padding: 12px 16px;
  background: var(--c-accent-3);
  border: 1.5px dashed var(--c-accent-br);
  border-radius: var(--r-sm);
  font-size: 14px;
}
.q-flashback > div:last-child {
  margin-top: 4px;
  font-weight: 500;
  color: var(--c-text);
}

/* ── Legal pages (Nutzungsbedingungen / Datenschutz / Impressum) ──── */
/* Narrow reading column, generous line-height, comfortable type sizes.
   Designed for long-text scanning, not for design flash. */
.legal-page {
  max-width: 780px;
  margin: 40px auto 80px;
  padding: 0 32px;
  line-height: 1.7;
  color: var(--c-text);
}
.legal-page .legal-head {
  border-bottom: 1px solid var(--c-border);
  padding-bottom: 20px;
  margin-bottom: 32px;
}
.legal-page .legal-head h1 {
  margin: 0 0 6px;
  font-size: 32px;
  letter-spacing: -0.02em;
}
.legal-page .legal-meta {
  margin: 0;
  color: var(--c-text-3);
  font-size: 13px;
}
.legal-page section { margin-bottom: 32px; }
.legal-page h2 {
  margin: 0 0 14px;
  font-size: 22px;
  font-weight: 800;
  color: var(--c-text);
  letter-spacing: -0.01em;
}
.legal-page h3 {
  margin: 20px 0 8px;
  font-size: 16px;
  font-weight: 700;
  color: var(--c-text);
}
.legal-page p { margin: 0 0 14px; }
.legal-page ul {
  margin: 0 0 16px;
  padding-left: 24px;
}
.legal-page ul li { margin-bottom: 6px; }
.legal-page .legal-intro {
  padding: 18px 22px;
  background: #fff7ed;
  border-left: 4px solid var(--c-primary);
  border-radius: var(--r-sm);
  font-size: 15px;
}
.legal-page .legal-contact {
  padding: 14px 18px;
  background: #f8fafc;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  margin: 10px 0 14px;
  font-size: 14px;
  line-height: 1.6;
}
.legal-page .legal-foot {
  margin-top: 40px;
  padding-top: 20px;
  border-top: 1px solid var(--c-border);
  color: var(--c-text-2);
  font-size: 14px;
}
.legal-page .legal-foot p { margin-bottom: 8px; }
.legal-page a { color: var(--c-primary); }
.legal-page a:hover { text-decoration: underline; }

@media (max-width: 720px) {
  .legal-page { padding: 0 20px; margin-top: 24px; }
  .legal-page .legal-head h1 { font-size: 26px; }
  .legal-page h2 { font-size: 19px; }
}

/* Terms consent row in the signup form */
.consent-row {
  display: flex;
  align-items: flex-start;
  gap: 10px;
  margin: 0 0 20px;
  padding: 12px 14px;
  background: #fff7ed;
  border: 1px solid rgba(249, 115, 22, 0.2);
  border-radius: var(--r-sm);
  font-size: 13px;
  line-height: 1.5;
  color: var(--c-text-2);
}
.consent-row input[type="checkbox"] {
  width: auto;
  margin: 3px 0 0;
  flex-shrink: 0;
  accent-color: var(--c-primary);
}
.consent-row a { color: var(--c-primary); font-weight: 600; }
.consent-row a:hover { text-decoration: underline; }

/* ── Landing page (public homepage) ───────────────────────────────── */
.landing-nav {
  display: flex;
  align-items: center;
  justify-content: space-between;
  max-width: 1200px;
  margin: 0 auto;
  padding: 10px 32px;   /* was 20px — the logo PNG has built-in top/bottom padding, so extra outer padding feels excessive */
  position: relative;
  z-index: 1;
}
/* Full-width white strip behind the nav. The nav content stays capped
   at 1200px (centered), but the white extends edge-to-edge so it reads
   as a proper nav bar — and crucially, the logo PNG's baked-in white
   rectangle blends invisibly into this white strip. */
.landing-nav::before {
  content: "";
  position: absolute;
  top: 0;
  bottom: 0;
  left: calc(50% - 50vw);
  width: 100vw;
  background: #fff;
  border-bottom: 1px solid rgba(0, 0, 0, 0.04);
  box-shadow: 0 1px 2px rgba(0, 0, 0, 0.03);
  z-index: -1;
}
.landing-brand-logo {
  height: 96px;   /* 140 → 80 → 60 → 96: the PNG has baked-in padding, so the visible owl+wordmark feels ~2/3 of the height value */
  width: auto;
  transition: transform var(--dur-med) var(--ease-bounce);
  /* The PNG has a solid white rectangle baked into the image. multiply
     blending drops those white pixels into the page background so only
     the owl + "Lernino" type remain visible — a clean cut-out without
     needing to re-export the asset. Orange stays orange, dark stays
     dark. If you ever replace logo.png with a true transparent-bg PNG
     you can delete this line. */
  mix-blend-mode: multiply;
}
.landing-brand:hover .landing-brand-logo { transform: rotate(-2deg) scale(1.04); }
.landing-nav-actions {
  display: flex;
  gap: 10px;
}

/* ═══════════════════════════════════════════════════════════════════
   Landing nav — hierarchy variant. Three actions with distinct weights:
     1. Language picker (utility)  — compact icon-first pill
     2. Log in (secondary)         — plain text link, no button chrome
     3. Start for free (primary)   — bold button, extra padding
   The wider gap before the primary CTA separates "utilities on the
   left" from "the action on the right". Classic SaaS-nav pattern.
   ═══════════════════════════════════════════════════════════════════ */
.landing-nav-actions--hierarchy {
  align-items: center;
  gap: 14px;
}

/* Compact language picker — shrinks the pill so it reads as utility,
   not a CTA. Overrides the default .lang-trigger size. */
.lang-menu--compact { margin-right: 0; }
.lang-trigger--compact {
  padding: 4px 10px;
  font-size: 12px;
  gap: 4px;
  color: var(--c-text-2);
  background: transparent;
  border: 1px solid transparent;
  box-shadow: none;
  opacity: 0.8;
  transition: opacity var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.lang-trigger--compact:hover,
.lang-menu[open] > .lang-trigger--compact {
  opacity: 1;
  background: #f3f4f6;
  border-color: #e5e7eb;
}
.lang-trigger--compact .lang-trigger-code {
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.04em;
}

/* Log in — demoted from a pill-button to a plain text link. Keeps the
   same hit area via padding so it's still easy to click. Hover darkens
   the text instead of painting a background. */
.nav-login-link {
  display: inline-flex;
  align-items: center;
  padding: 6px 8px;
  font-size: 14px;
  font-weight: 600;
  color: var(--c-text-2);
  text-decoration: none;
  transition: color var(--dur-fast) var(--ease);
}
.nav-login-link:hover,
.nav-login-link:focus-visible {
  color: var(--c-text);
  text-decoration: none;
  outline: none;
}
.nav-login-link:focus-visible {
  box-shadow: 0 0 0 3px rgba(249, 115, 22, 0.25);
  border-radius: 6px;
}

/* Start for free — primary action, slightly more weighty than the
   .btn btn-sm baseline. Extra horizontal padding + shadow so it reads
   as "THE action" at a glance. */
.nav-signup-btn {
  padding: 9px 18px;
  font-size: 14px;
  font-weight: 700;
  box-shadow: 0 4px 14px -4px rgba(249, 115, 22, 0.45);
  margin-left: 6px;  /* breathing room from the "Log in" link */
}
.nav-signup-btn:hover {
  box-shadow: 0 6px 18px -4px rgba(249, 115, 22, 0.55);
}

/* Mobile: tighter spacing, drop the "Log in" link's left padding. */
@media (max-width: 480px) {
  .landing-nav-actions--hierarchy { gap: 10px; }
  .nav-login-link { padding: 6px 4px; font-size: 13px; }
  .nav-signup-btn { padding: 8px 14px; }
}

.landing-hero {
  /* 1200px matches the .landing-nav max-width above — so the hero
     content's left and right edges line up exactly with the logo and
     the "Start for free" button. Previously 1000px, which made the
     hero look narrower than the nav. */
  max-width: 1200px;
  margin: 0 auto;
  /* Top tightened too — the nav is small now, no need for 64px breathing
     room. Bottom stays minimal since the laptop + caption is the visual
     closer; next section supplies its own top padding. */
  padding: 36px 32px 16px;
  text-align: center;
  position: relative;
}
/* The first .landing-section follows the hero directly — shrink its
   top padding so the transition feels like one continuous flow instead
   of two disconnected zones. */
.landing-hero + .landing-section {
  padding-top: 24px;
}
.landing-headline {
  font-size: 56px;
  font-weight: 900;
  line-height: 1.05;
  letter-spacing: -0.03em;
  margin: 0 0 20px;
  color: var(--c-text);
}
.landing-accent {
  background: linear-gradient(135deg, #f97316 0%, #ec4899 50%, #a855f7 100%);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.landing-sub {
  font-size: 20px;
  line-height: 1.5;
  color: var(--c-text-2);
  max-width: 640px;
  margin: 0 auto 32px;
}

/* Inline icons in the hero subtitle — AI emoji + WhatsApp green SVG.
   Aligned to the baseline of the surrounding text so they sit as
   siblings to the words they decorate, not floating above. */
.inline-icon {
  display: inline-flex;
  align-items: center;
  vertical-align: -3px;
  margin: 0 2px;
}
.inline-icon-ai {
  font-size: 22px;
  line-height: 1;
}
.inline-icon-wa img {
  width: 22px;
  height: 22px;
  display: block;
  filter: drop-shadow(0 1px 2px rgba(37, 211, 102, 0.25));
}
.landing-cta-row {
  display: flex;
  gap: 14px;
  justify-content: center;
  flex-wrap: wrap;
  margin-bottom: 24px;
}
.landing-trust {
  margin-top: 24px;
}

.landing-section {
  /* Same 1200px max as the nav + hero — every content band lines up,
     no jittery edge-shifts when scrolling from one section to the next. */
  max-width: 1200px;
  margin: 0 auto;
  padding: 72px 32px;
}

/* ═══════════════════════════════════════════════════════════════════
   Laptop mockup on the landing hero. Pure CSS — no image assets. The
   "screen" is a white card with a miniature version of the parent
   dashboard inside, so visitors see the product before they scroll.
   ═══════════════════════════════════════════════════════════════════ */
.landing-preview-wrap {
  max-width: 980px;
  margin: 40px auto 0;
  padding: 0 16px;
  text-align: center;
}
.laptop {
  position: relative;
  margin: 0 auto;
  max-width: 880px;
  filter: drop-shadow(0 40px 60px rgba(15, 23, 42, 0.18));
}
.laptop-screen {
  /* Bezel — dark charcoal rounded rectangle representing the laptop lid */
  background: linear-gradient(180deg, #1f2937 0%, #0f172a 100%);
  padding: 14px 14px 18px;
  border-radius: 16px 16px 4px 4px;
  border: 1px solid #334155;
  position: relative;
}
.laptop-screen::before {
  /* Tiny camera-notch dot centred in the top bezel */
  content: "";
  position: absolute;
  top: 6px;
  left: 50%;
  transform: translateX(-50%);
  width: 4px;
  height: 4px;
  border-radius: 50%;
  background: #475569;
  box-shadow: 0 0 0 1px #1e293b;
}
.laptop-screen-inner {
  /* Actual "glass" where the dashboard lives */
  background: #fafafa;
  border-radius: 6px;
  overflow: hidden;
  aspect-ratio: 16 / 10;
  display: flex;
  flex-direction: column;
  text-align: left;
}

/* Image-mode screen — no internal flex, just let the screenshot fill
   the glass. object-fit: cover + object-position: top 50% keeps the
   most important part (hero + kid cards) visible when the image is
   taller than 16:10. */
.laptop-screen-inner--img {
  display: block;
  position: relative;
}
.laptop-screenshot {
  width: 100%;
  height: 100%;
  display: block;
  object-fit: cover;
  object-position: top center;
}

/* Auto-scroll inside the laptop screen. The dashboard screenshots are
   much taller than 16:10, so static object-position: top chops off the
   bar chart at the bottom. Animate object-position from top to bottom
   and back so visitors see EVERYTHING — hero, cards, stats, chart —
   without switching tabs. Active slide only (avoid sync weirdness). */
.laptop-slider .laptop-screenshot.is-active {
  animation: dashboard-pan 12s ease-in-out infinite;
}
@keyframes dashboard-pan {
  0%   { object-position: 50% 0%;   }  /* top of dashboard (hero) */
  10%  { object-position: 50% 0%;   }  /* hold at top briefly */
  50%  { object-position: 50% 100%; }  /* reveal the chart at bottom */
  60%  { object-position: 50% 100%; }  /* hold at bottom briefly */
  100% { object-position: 50% 0%;   }  /* ease back to top for the loop */
}
/* Pause the pan when the user is interacting — don't yank their eye
   while they're trying to read. Hooks into :hover on the slider
   container (already the pause signal for the slide auto-advance). */
.laptop-slider:hover .laptop-screenshot.is-active,
.laptop-slider:focus-within .laptop-screenshot.is-active {
  animation-play-state: paused;
}
@media (prefers-reduced-motion: reduce) {
  .laptop-slider .laptop-screenshot.is-active { animation: none; }
}

/* Slider — all slides stack on top of each other inside the glass;
   only the .is-active one is visible (opacity fade). Works for both
   <img class="laptop-screenshot"> and <div class="laptop-slide">. */
.laptop-slider .laptop-screenshot,
.laptop-slider .laptop-slide {
  position: absolute;
  inset: 0;
  opacity: 0;
  transition: opacity 400ms var(--ease);
  pointer-events: none;
}
.laptop-slider .laptop-screenshot.is-active,
.laptop-slider .laptop-slide.is-active {
  opacity: 1;
  pointer-events: auto;
}
.laptop-slider .laptop-slide {
  display: flex;
  flex-direction: column;
  background: #fafafa;
  overflow: hidden;
}

/* ── Kid-detail slide specifics ──────────────────────────────────── */
.preview-kid-hero {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 12px;
  background: linear-gradient(135deg, #fff7ed 0%, #fef3f9 100%);
  border-radius: 10px;
  margin-bottom: 8px;
}
.preview-kid-hero-avatar {
  font-size: 26px;
  line-height: 1;
}
.preview-kid-hero-meta {
  flex: 1 1 auto;
}
.preview-kid-hero-meta strong {
  display: block;
  font-size: 15px;
  color: #111827;
}
.preview-kid-hero-meta small {
  display: block;
  font-size: 10px;
  color: #6b7280;
  margin-top: 1px;
}
.preview-owe {
  background: #fff;
  padding: 6px 10px;
  border-radius: 8px;
  text-align: right;
  border: 1px solid #e5e7eb;
}
.preview-owe small {
  display: block;
  font-size: 8.5px;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: #16a34a;
}
.preview-owe strong {
  font-size: 15px;
  color: #16a34a;
  font-weight: 800;
}
.preview-owe strong span { font-size: 9px; color: #16a34a; font-weight: 600; margin-left: 2px; }

.preview-stats-tight { grid-template-columns: repeat(4, 1fr); gap: 6px; }
.preview-stats-tight .preview-stat { padding: 6px 8px; }
.preview-stats-tight .preview-stat strong { font-size: 15px; }

.preview-strip {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 8px;
  margin-top: 4px;
}
.preview-strip-item {
  background: #fff;
  border: 1px solid #e5e7eb;
  border-left: 3px solid #f97316;
  border-radius: 8px;
  padding: 8px 10px;
}
.preview-strip-pill {
  display: inline-block;
  font-size: 8px;
  font-weight: 800;
  letter-spacing: 0.08em;
  color: #ea580c;
  margin-bottom: 4px;
}
.preview-strip-item strong {
  display: block;
  font-size: 12px;
  color: #111827;
}

/* Dot indicators — pinned to the BOTTOM-CENTRE of the screen glass,
   so visitors naturally tap/click them to switch. Small, white with
   low-opacity backing so they don't dominate the shot behind. */
.laptop-dots {
  position: absolute;
  left: 50%;
  bottom: 12px;
  transform: translateX(-50%);
  display: flex;
  gap: 8px;
  padding: 6px 10px;
  background: rgba(15, 23, 42, 0.35);
  backdrop-filter: blur(6px);
  -webkit-backdrop-filter: blur(6px);
  border-radius: 999px;
  z-index: 3;
}
.laptop-dot {
  appearance: none;
  -webkit-appearance: none;
  width: 10px;
  height: 10px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: rgba(255, 255, 255, 0.55);
  cursor: pointer;
  transition: background var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
}
.laptop-dot:hover,
.laptop-dot:focus-visible {
  background: rgba(255, 255, 255, 0.85);
  transform: scale(1.12);
  outline: none;
}
.laptop-dot.is-active {
  background: #fff;
  transform: scale(1.25);
  box-shadow: 0 0 0 2px rgba(249, 115, 22, 0.55);
}
/* Reduced-motion: drop the fade, keep dots clickable */
@media (prefers-reduced-motion: reduce) {
  .laptop-slider .laptop-screenshot { transition: none; }
  .laptop-dot { transition: none; }
}
.laptop-base {
  /* Trapezoid-ish keyboard deck under the screen */
  width: 108%;
  margin-left: -4%;
  height: 14px;
  background: linear-gradient(180deg, #94a3b8 0%, #64748b 60%, #475569 100%);
  border-radius: 0 0 14px 14px;
  position: relative;
}
.laptop-base::after {
  /* Touchpad hint — a thin lighter bar in the middle */
  content: "";
  position: absolute;
  top: 2px;
  left: 50%;
  transform: translateX(-50%);
  width: 110px;
  height: 4px;
  background: #334155;
  border-radius: 0 0 6px 6px;
}

/* ── Miniature dashboard inside the screen ────────────────────────── */
.preview-topbar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 8px 16px;
  border-bottom: 1px solid #e5e7eb;
  background: #fff;
  flex: 0 0 auto;
}
.preview-logo {
  height: 28px;
  width: auto;
  mix-blend-mode: multiply;
}
.preview-avatar {
  width: 24px;
  height: 24px;
  border-radius: 50%;
  background: linear-gradient(135deg, #f97316, #ec4899);
  color: #fff;
  font-size: 11px;
  font-weight: 700;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}

.preview-body {
  flex: 1 1 auto;
  padding: 18px 22px;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.preview-h {
  font-size: 22px;
  font-weight: 800;
  margin: 0;
  letter-spacing: -0.02em;
  color: #111827;
}
.preview-h span { display: inline-block; transform: rotate(-6deg); }
.preview-sub {
  font-size: 12px;
  color: #6b7280;
  margin: 0;
}

.preview-kid-row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 10px;
}
.preview-kid {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 12px;
  background: #fff;
  border: 1px solid #e5e7eb;
  border-radius: 10px;
  border-left: 4px solid #e5e7eb;
}
.preview-kid-good { border-left-color: #16a34a; }
.preview-kid-avatar {
  font-size: 22px;
  line-height: 1;
  flex: 0 0 auto;
}
.preview-kid strong {
  display: block;
  font-size: 13px;
  font-weight: 700;
  color: #111827;
}
.preview-kid small {
  display: block;
  font-size: 11px;
  color: #6b7280;
  margin-top: 1px;
}

.preview-stats {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 8px;
  margin-top: 4px;
}
.preview-stat {
  padding: 8px 10px;
  background: #fff;
  border: 1px solid #e5e7eb;
  border-radius: 8px;
  text-align: left;
}
.preview-stat small {
  display: block;
  font-size: 9px;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: #9ca3af;
  margin-bottom: 2px;
}
.preview-stat strong {
  display: block;
  font-size: 18px;
  font-weight: 800;
  color: #111827;
  line-height: 1.1;
}
.preview-stat-good { color: #16a34a !important; }
.preview-stat span {
  font-size: 10px;
  color: #6b7280;
}

.landing-preview-caption {
  margin: 22px auto 0;
  max-width: 560px;
  font-size: 15px;
  color: #4b5563;
  line-height: 1.45;
}

/* Narrow screens — shrink aggressively, hide stats grid if really tight */
@media (max-width: 720px) {
  .laptop { max-width: 100%; }
  .preview-body { padding: 12px 14px; gap: 8px; }
  .preview-h { font-size: 17px; }
  .preview-sub { font-size: 11px; }
  .preview-kid { padding: 8px 10px; gap: 8px; }
  .preview-kid-avatar { font-size: 18px; }
  .preview-kid strong { font-size: 11px; }
  .preview-kid small { font-size: 9.5px; }
  .preview-stat strong { font-size: 14px; }
  .preview-stat small { font-size: 8px; }
  .preview-stat span { font-size: 9px; }
}
@media (max-width: 440px) {
  .preview-stats { grid-template-columns: 1fr 1fr; }
  .preview-stat:last-child { display: none; }  /* keep it readable */
}
.landing-section-alt {
  /* Inherits the body's #fafafb grey via transparent bg. Hairline top
     border preserved for section separation. */
  background: transparent;
  max-width: none;
  padding-left: 32px;
  padding-right: 32px;
  border-top: 1px solid #eef0f2;
}
.landing-section-alt > h2,
.landing-section-alt > .landing-features {
  max-width: 1100px;
  margin-left: auto;
  margin-right: auto;
}
.landing-h2 {
  font-size: 36px;
  font-weight: 800;
  line-height: 1.15;
  letter-spacing: -0.02em;
  text-align: center;
  margin: 0 0 32px;   /* was 48px — tighter rhythm between heading and its content */
  color: var(--c-text);
}

/* How it works — 3 steps */
.landing-steps {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
  gap: 32px;
}
.landing-step {
  text-align: center;
}
.landing-step-num {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 56px;
  height: 56px;
  margin: 0 auto 16px;
  border-radius: 50%;
  background: var(--grad-warm);
  color: #fff;
  font-size: 26px;
  font-weight: 900;
  box-shadow: var(--sh-warm);
}

/* ═══════════════════════════════════════════════════════════════════
   How-it-works — 2-col split layout. Image takes the left half, the
   three numbered steps stack vertically on the right with the number
   as a circle badge. Stacks on mobile (≤820px).
   ═══════════════════════════════════════════════════════════════════ */
.landing-how-split {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 56px;
  align-items: center;
  max-width: 1100px;
  margin: 0 auto;
}
.landing-how-image {
  position: relative;
  border-radius: 20px;
  overflow: hidden;
  box-shadow: 0 24px 48px -24px rgba(15, 23, 42, 0.28);
  aspect-ratio: 4 / 3;
  background: #f3f4f6;   /* placeholder tint while the image loads */
}
.landing-how-image img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.landing-how-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 28px;
}
.landing-how-item {
  display: flex;
  gap: 18px;
  align-items: flex-start;
}
.landing-how-num {
  flex: 0 0 auto;
  width: 44px;
  height: 44px;
  border-radius: 50%;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: var(--grad-warm);
  color: #fff;
  font-weight: 900;
  font-size: 20px;
  box-shadow: 0 6px 16px -6px rgba(249, 115, 22, 0.55);
}
.landing-how-body h3 {
  font-size: 20px;
  font-weight: 700;
  margin: 0 0 6px;
  color: var(--c-text);
}
.landing-how-body p {
  margin: 0;
  font-size: 15px;
  line-height: 1.55;
  color: var(--c-text-2);
}

/* Mobile — image on top, steps below. */
@media (max-width: 820px) {
  .landing-how-split {
    grid-template-columns: 1fr;
    gap: 36px;
  }
  .landing-how-image { aspect-ratio: 16 / 10; max-width: 560px; margin: 0 auto; }
}
.landing-step h3 {
  margin: 0 0 8px;
  font-size: 20px;
  color: var(--c-text);
}
.landing-step p {
  margin: 0;
  color: var(--c-text-2);
  font-size: 15px;
  line-height: 1.5;
}

/* Three features */
.landing-features {
  display: grid;
  /* minmax(240px) lets 4 cards fit in 2×2 on medium screens and flow to
     4-across on wide desktops. Was 280px which forced an awkward 3+1. */
  grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
  gap: 20px;
}

/* Highlighted feature variant — soft orange accent + ribbon above the
   corner. Used for the marquee wins (AI, WhatsApp) to pull the eye
   without shouting. */
.landing-feature--highlight {
  position: relative;
  border: 1.5px solid #fcd34d;
  background: linear-gradient(180deg, #fffbeb 0%, var(--c-surface) 70%);
  box-shadow: 0 6px 18px -12px rgba(245, 158, 11, 0.35);
}
.landing-feature-badge {
  position: absolute;
  top: -12px;
  right: 14px;
  padding: 4px 12px;
  border-radius: 999px;
  background: linear-gradient(135deg, #f97316 0%, #ec4899 100%);
  color: #fff;
  font-size: 10px;
  font-weight: 800;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  box-shadow: 0 2px 8px rgba(236, 72, 153, 0.35);
  z-index: 2;
  white-space: nowrap;
}
.landing-feature {
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 32px 28px;
  box-shadow: 0 4px 16px -6px rgba(0, 0, 0, 0.08);
  transition: transform var(--dur-fast) var(--ease), box-shadow var(--dur-fast) var(--ease);
}
.landing-feature:hover {
  transform: translateY(-4px);
  box-shadow: 0 12px 28px -10px rgba(249, 115, 22, 0.2);
}
.landing-feature-icon {
  font-size: 40px;
  line-height: 1;
  margin-bottom: 16px;
}
.landing-feature h3 {
  margin: 0 0 10px;
  font-size: 22px;
  font-weight: 800;
  color: var(--c-text);
}
.landing-feature > p {
  margin: 0 0 16px;
  color: var(--c-text-2);
  line-height: 1.55;
}
.landing-feature-list {
  list-style: none;
  padding: 0;
  margin: 0;
}
.landing-feature-list li {
  position: relative;
  padding-left: 22px;
  margin-bottom: 6px;
  color: var(--c-text-2);
  font-size: 14px;
}
.landing-feature-list li::before {
  content: "✓";
  position: absolute;
  left: 0;
  color: #16a34a;
  font-weight: 800;
}

/* Contribution teaser */
.landing-contribute {
  /* Inherits body's #fafafb. */
  background: transparent;
  max-width: none;
  padding: 80px 32px;
  text-align: center;
  border-top: 1px solid #eef0f2;
}

/* ═══════════════════════════════════════════════════════════════════
   Testimonials carousel — rolls quotes from parents about AI, WhatsApp,
   and their kid's progress. Sits directly under the laptop so visitors
   see "social proof" right after seeing the product. Fades between
   quotes; dots at the bottom for manual navigation.
   ═══════════════════════════════════════════════════════════════════ */
.landing-testimonials {
  max-width: 780px;
  margin: 32px auto 56px;
  padding: 0 32px;
  text-align: center;
}
.landing-testimonials .landing-kicker {
  margin-bottom: 20px;
}
.testi-slider {
  position: relative;
  min-height: 220px;
}
.testi-slide {
  position: absolute;
  inset: 0;
  opacity: 0;
  transform: translateY(8px);
  transition: opacity 450ms var(--ease), transform 450ms var(--ease);
  pointer-events: none;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  padding: 24px 32px 56px;
  background: linear-gradient(180deg, #ffffff 0%, #fafbfc 100%);
  border: 1px solid var(--c-border);
  border-radius: 20px;
  box-shadow: 0 20px 40px -24px rgba(15, 23, 42, 0.15);
}
.testi-slide.is-active {
  opacity: 1;
  transform: translateY(0);
  pointer-events: auto;
}
.testi-icon {
  font-size: 28px;
  line-height: 1;
  margin-bottom: 10px;
  filter: drop-shadow(0 2px 4px rgba(0, 0, 0, 0.08));
}
.testi-quote {
  font-size: 18px;
  line-height: 1.55;
  font-weight: 500;
  color: var(--c-text);
  max-width: 620px;
  margin: 0 auto 18px;
  font-style: italic;
  letter-spacing: -0.01em;
}
.testi-author {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  padding: 6px 14px;
  background: #fff7ed;
  border-radius: 999px;
}
.testi-avatar {
  font-size: 22px;
  line-height: 1;
}
.testi-author strong {
  display: block;
  font-size: 13px;
  font-weight: 700;
  color: var(--c-text);
  line-height: 1.2;
}
.testi-author small {
  display: block;
  font-size: 11px;
  color: var(--c-text-3);
  line-height: 1.2;
}
.testi-dots {
  position: absolute;
  left: 50%;
  bottom: 18px;
  transform: translateX(-50%);
  display: flex;
  gap: 8px;
  z-index: 2;
}
.testi-dot {
  appearance: none;
  -webkit-appearance: none;
  width: 8px;
  height: 8px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: #d1d5db;
  cursor: pointer;
  transition: background var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
}
.testi-dot:hover,
.testi-dot:focus-visible {
  background: #9ca3af;
  outline: none;
}
.testi-dot.is-active {
  background: var(--c-primary);
  transform: scale(1.3);
}
@media (prefers-reduced-motion: reduce) {
  .testi-slide { transition: opacity 200ms linear; transform: none; }
}
@media (max-width: 640px) {
  .landing-testimonials { margin: 24px auto 40px; padding: 0 20px; }
  .testi-slider { min-height: 260px; }
  .testi-quote  { font-size: 16px; }
  .testi-slide  { padding: 20px 20px 50px; }
}

/* ═══════════════════════════════════════════════════════════════════
   About / founder story. Narrow column, generous line-height, warm
   signature line to make it read as a letter, not a sales pitch.
   ═══════════════════════════════════════════════════════════════════ */
.landing-about {
  text-align: center;
}
.landing-about-inner {
  max-width: 680px;
  margin: 0 auto;
}
.landing-kicker {
  display: inline-block;
  font-size: 11px;
  font-weight: 800;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: #f97316;
  background: #fff7ed;
  padding: 4px 12px;
  border-radius: 999px;
  margin-bottom: 16px;
}
.landing-about-body {
  font-size: 17px;
  line-height: 1.65;
  color: var(--c-text-2);
  margin: 0 0 14px;
}
.landing-about-signature {
  margin-top: 24px;
  font-style: italic;
  color: var(--c-text-3);
  font-size: 15px;
}

/* ═══════════════════════════════════════════════════════════════════
   Contact + Subscribe — two-up card grid. Same card visual language as
   the features above so the rhythm stays consistent.
   ═══════════════════════════════════════════════════════════════════ */
.landing-contact-section {
  text-align: center;
  background: transparent;
  max-width: none;
  padding: 72px 32px;
  border-top: 1px solid #eef0f2;
}
.landing-contact-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
  gap: 20px;
  max-width: 900px;
  margin: 0 auto;
}
.landing-contact-card {
  border-radius: 16px;
  padding: 32px 28px;
  text-align: left;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.landing-contact-icon {
  font-size: 32px;
  line-height: 1;
  margin-bottom: 12px;
}
.landing-contact-card h3 {
  font-size: 20px;
  font-weight: 700;
  margin: 0 0 8px;
}
.landing-contact-card p {
  font-size: 14.5px;
  line-height: 1.5;
  margin: 0 0 20px;
}

/* ── "Quiet" variant: Contact. Outlined, flat, hover-reveals fill.
      Reads as an invitation rather than a call-to-action. ─────────── */
.landing-contact-card--quiet {
  background: #fff;
  border: 1.5px dashed #d1d5db;
}
.landing-contact-card--quiet h3 { color: var(--c-text); }
.landing-contact-card--quiet p  { color: var(--c-text-2); }
.landing-contact-card--quiet:hover {
  transform: translateY(-2px);
  border-color: var(--c-primary);
  border-style: solid;
  box-shadow: 0 8px 20px -14px rgba(249, 115, 22, 0.35);
}
/* Email link replacing the button — text-only with arrow, underlined
   on hover. Feels like a hyperlink, not a CTA. */
.landing-contact-link {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 15px;
  font-weight: 700;
  color: var(--c-primary);
  text-decoration: none;
  transition: gap var(--dur-fast) var(--ease);
}
.landing-contact-link:hover {
  color: var(--c-primary);
  text-decoration: underline;
  gap: 10px;  /* arrow slides right */
}
.landing-contact-arrow {
  font-size: 18px;
  font-weight: 700;
}
.landing-contact-email {
  margin: 10px 0 0;
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-size: 12px;
  color: var(--c-text-3);
}

/* ── "Loud" variant: Subscribe. Violet gradient, white text, stands
      out as a completely different component from Contact. ────────── */
.landing-contact-card--loud {
  background: linear-gradient(135deg, #4c1d95 0%, #7c3aed 70%, #a855f7 100%);
  border: 1px solid #4c1d95;
  color: #fff;
  position: relative;
  overflow: hidden;
  box-shadow: 0 12px 24px -14px rgba(124, 58, 237, 0.55);
}
.landing-contact-card--loud::before {
  /* Decorative soft-circle in the top-right for depth. */
  content: "";
  position: absolute;
  top: -40px;
  right: -40px;
  width: 180px;
  height: 180px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(236, 72, 153, 0.35), transparent 70%);
  pointer-events: none;
}
.landing-contact-card--loud h3 { color: #fff; }
.landing-contact-card--loud p  { color: rgba(255, 255, 255, 0.82); }
.landing-contact-card--loud:hover {
  transform: translateY(-2px);
  box-shadow: 0 18px 36px -14px rgba(124, 58, 237, 0.65);
}

/* Subscribe form inside the loud card. White input on violet bg. */
.landing-subscribe-form {
  display: flex;
  flex-direction: column;
  gap: 10px;
  position: relative;    /* sit above the ::before blob */
  z-index: 1;
}
.landing-subscribe-input {
  font-size: 15px;
  padding: 12px 14px;
  border: 2px solid rgba(255, 255, 255, 0.28);
  border-radius: var(--r-sm);
  background: rgba(255, 255, 255, 0.12);
  color: #fff;
  transition: border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.landing-subscribe-input::placeholder { color: rgba(255, 255, 255, 0.6); }
.landing-subscribe-input:focus {
  outline: none;
  border-color: #fff;
  background: rgba(255, 255, 255, 0.2);
}
.landing-subscribe-form .btn {
  width: 100%;
  justify-content: center;
}
/* White-on-violet button, explicitly different from btn-primary */
.btn-white-on-violet {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 11px 20px;
  font-weight: 700;
  font-size: 14px;
  background: #fff;
  color: #4c1d95;
  border: 0;
  border-radius: var(--r-sm);
  cursor: pointer;
  font-family: inherit;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.btn-white-on-violet:hover {
  background: #fef3c7;
  transform: translateY(-1px);
  box-shadow: 0 6px 18px -6px rgba(0, 0, 0, 0.25);
}
.landing-subscribe-note {
  margin: 10px 0 0;
  color: rgba(255, 255, 255, 0.7) !important;
  font-size: 12px;
  position: relative;
  z-index: 1;
}

/* Narrow screens — single column, tighter padding. */
@media (max-width: 640px) {
  .landing-contact-section { padding: 56px 20px; }
  .landing-contact-card    { padding: 24px 20px; }
}
.landing-contribute-inner {
  max-width: 680px;
  margin: 0 auto;
}
.landing-contribute-text {
  font-size: 18px;
  line-height: 1.6;
  color: var(--c-text);
  margin: 0 0 20px;
}

/* Small emerald pill above the headline — visual anchor for "free". */
.landing-free-badge {
  display: inline-flex;
  align-items: center;
  padding: 6px 16px;
  margin-bottom: 18px;
  font-size: 12px;
  font-weight: 800;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: #047857;
  background: #ecfdf5;
  border: 1px solid #a7f3d0;
  border-radius: 999px;
}

/* Coffee card — the single optional ask, framed tangibly. White card on
   the warm gradient background so the offer feels like a sidebar, not
   a hard sell. */
.landing-coffee-card {
  display: flex;
  gap: 20px;
  align-items: flex-start;
  text-align: left;
  padding: 24px 26px;
  margin: 28px 0 8px;
  background: #fff;
  border: 1px solid rgba(249, 115, 22, 0.25);
  border-radius: var(--r-md);
  box-shadow: 0 10px 30px -14px rgba(124, 45, 18, 0.25);
}
.landing-coffee-icon {
  font-size: 48px;
  line-height: 1;
  flex-shrink: 0;
  filter: drop-shadow(0 4px 10px rgba(124, 45, 18, 0.15));
}
.landing-coffee-body { flex: 1; min-width: 0; }
.landing-coffee-title {
  margin: 0 0 8px;
  font-size: 20px;
  letter-spacing: -0.01em;
}
.landing-coffee-text {
  margin: 0 0 8px;
  font-size: 15px;
  line-height: 1.55;
  color: var(--c-text-2);
}
.landing-coffee-text:last-child { margin-bottom: 0; }
@media (max-width: 560px) {
  .landing-coffee-card { flex-direction: column; align-items: center; text-align: center; padding: 22px 18px; }
  .landing-coffee-icon { font-size: 42px; }
}

/* Footer */
/* ═══════════════════════════════════════════════════════════════════
   Footer — light grey, one shade deeper than the body canvas.
   Body is #fafafb, footer is #f3f4f6 so there's a subtle tonal
   transition without dark mode. Orange link hovers for warmth.
   ═══════════════════════════════════════════════════════════════════ */
.landing-footer {
  background: #f3f4f6;     /* one notch darker than body #fafafb */
  color: var(--c-text-2);
  border-top: 1px solid #e5e7eb;
  padding: 64px 32px 32px;
}
.landing-footer-inner {
  max-width: 1200px;
  margin: 0 auto;
}
/* Four-column grid on desktop: brand column is wider (2fr), the three
   link columns split the rest equally. Collapses to 2-across on tablet
   and single-column on phone. */
.landing-footer-grid {
  display: grid;
  grid-template-columns: 2fr 1fr 1fr 1fr;
  gap: 40px;
  margin-bottom: 48px;
}
.landing-footer-brand {
  max-width: 320px;
}
.landing-footer-logo {
  height: 40px;
  width: auto;
  display: block;
  margin-bottom: 14px;
  mix-blend-mode: multiply;   /* drop the PNG's baked-in white bg onto grey */
}
.landing-footer-tag {
  font-size: 14px;
  line-height: 1.55;
  color: var(--c-text-2);
  margin: 0 0 14px;
}
.landing-footer-locale {
  margin: 0;
  color: var(--c-text-3);
  font-size: 12px;
}

/* Link column headings — small caps, muted text. */
.landing-footer-col h4 {
  font-size: 11px;
  font-weight: 800;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--c-text-3);
  margin: 0 0 16px;
}
.landing-footer-col a {
  display: block;
  padding: 5px 0;
  color: var(--c-text-2);
  text-decoration: none;
  font-size: 14px;
  transition: color var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
}
.landing-footer-col a:hover {
  color: var(--c-primary);
  text-decoration: none;
  transform: translateX(2px);
}

/* Bottom copyright bar — hairline divider above, muted grey text. */
.landing-footer-bottom {
  padding-top: 24px;
  border-top: 1px solid #e5e7eb;
  text-align: center;
  color: var(--c-text-3);
  font-size: 12.5px;
  letter-spacing: 0.01em;
}

/* Tablet: 2 × 2 grid (brand spans 2 cols, links stack 2 cols each). */
@media (max-width: 900px) {
  .landing-footer-grid {
    grid-template-columns: 1fr 1fr;
    gap: 32px;
  }
  .landing-footer-brand {
    grid-column: 1 / -1;
    max-width: none;
  }
}
/* Mobile: single stack. */
@media (max-width: 560px) {
  .landing-footer { padding: 40px 24px 24px; }
  .landing-footer-grid {
    grid-template-columns: 1fr;
    gap: 28px;
  }
  .landing-footer-brand { text-align: center; }
  .landing-footer-logo { margin-left: auto; margin-right: auto; }
}

/* Phone */
@media (max-width: 720px) {
  .landing-headline { font-size: 40px; }
  .landing-sub { font-size: 17px; }
  .landing-h2 { font-size: 28px; margin-bottom: 32px; }
  .landing-section { padding: 48px 24px; }
  .landing-contribute { padding: 56px 24px; }
  .landing-nav { padding: 12px 18px; }
  .landing-brand-logo { height: 72px; }  /* mobile — scales with the new desktop size */
}

/* ── Support / contribution page ───────────────────────────────────── */
.support-why {
  padding: 28px 32px;
  margin-bottom: 28px;
  background: linear-gradient(180deg, #fff7ed 0%, var(--c-surface) 100%);
}
.support-why h2 { margin-top: 0; }
.support-cost-list {
  list-style: none;
  padding: 0;
  margin: 16px 0;
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
  gap: 10px;
}
.support-cost-list li {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 14px;
  background: rgba(255, 255, 255, 0.6);
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  font-size: 14px;
}
.support-cost-icon {
  font-size: 20px;
  flex-shrink: 0;
}

.support-form-wrap {
  display: grid;
  grid-template-columns: 2fr 1fr;
  gap: 24px;
  align-items: start;
}
.support-form { padding: 28px 32px; }

/* Coffee picker — 1-to-5 preset buttons showing coffee cups + amount */
.coffee-picker {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(120px, 1fr));
  gap: 10px;
  margin-bottom: 8px;
}
.coffee-preset {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 4px;
  padding: 14px 10px;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-md);
  cursor: pointer;
  font-family: inherit;
  color: var(--c-text);
  transition: all var(--dur-fast) var(--ease);
}
.coffee-preset:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  transform: translateY(-2px);
  box-shadow: 0 6px 14px -4px rgba(249, 115, 22, 0.2);
}
.coffee-preset-active {
  border-color: var(--c-primary);
  background: linear-gradient(135deg, #fff7ed 0%, #fed7aa 100%);
  box-shadow: var(--sh-warm);
}
.coffee-icons {
  font-size: 22px;
  line-height: 1.2;
  letter-spacing: 2px;
}
.coffee-count {
  font-size: 12px;
  font-weight: 700;
  color: var(--c-text-2);
  text-transform: uppercase;
  letter-spacing: 0.06em;
}
.coffee-amount {
  font-size: 18px;
  font-weight: 800;
  color: var(--c-primary);
  font-feature-settings: "tnum";
}

.support-presets {
  display: flex;
  gap: 8px;
  margin-bottom: 8px;
  flex-wrap: wrap;
}
.support-preset {
  flex: 1;
  min-width: 64px;
  padding: 14px 8px;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-sm);
  font-size: 18px;
  font-weight: 800;
  color: var(--c-text);
  cursor: pointer;
  transition: all var(--dur-fast) var(--ease);
  font-family: inherit;
}
.support-preset:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
}
.support-preset-active {
  border-color: var(--c-primary);
  background: var(--c-primary);
  color: #fff;
  box-shadow: var(--sh-warm);
}
.support-preset::after { content: " CHF"; font-size: 11px; font-weight: 600; opacity: 0.7; }

.support-amount-input {
  margin-top: 10px;
}

.support-preview {
  padding: 14px 18px;
  background: var(--c-primary-3);
  border: 1px solid var(--c-primary-br);
  border-radius: var(--r-sm);
  text-align: center;
  margin: 20px 0;
  font-size: 15px;
  color: var(--c-text);
}

.support-side .card { padding: 24px 28px; }
.support-other {
  list-style: none;
  padding: 0;
  margin: 12px 0 0;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.support-other li {
  padding-left: 22px;
  position: relative;
  line-height: 1.5;
  font-size: 14px;
  color: var(--c-text-2);
}
.support-other li::before {
  content: "→";
  position: absolute;
  left: 0;
  color: var(--c-primary);
  font-weight: 800;
}

@media (max-width: 720px) {
  .support-form-wrap { grid-template-columns: 1fr; }
  .support-presets { flex-wrap: wrap; }
  .support-preset { flex: 1 1 calc(33% - 8px); }
}

/* ── Reward badge on student test cards ────────────────────────────── */
.test-card-reward {
  display: flex;
  align-items: baseline;
  gap: 6px;
  padding: 8px 12px;
  background: linear-gradient(135deg, #dcfce7 0%, #fef3c7 100%);
  border: 1px solid rgba(34, 197, 94, 0.35);
  border-radius: var(--r-sm);
  font-size: 13px;
  color: var(--c-text);
  margin: 2px 0;
}
.test-card-reward strong {
  color: #15803d;
  font-size: 15px;
  font-weight: 800;
  font-feature-settings: "tnum";
}

/* ── Wallet (parent IOU ledger) ────────────────────────────────────── */
.wallet-hero {
  padding: 36px 32px 32px;
  background: linear-gradient(135deg, #fef3f9 0%, #fed7aa 50%, #fff7ed 100%);
  border-radius: var(--r-lg);
  box-shadow: 0 20px 60px -24px rgba(249, 115, 22, 0.35),
              inset 0 1px 0 rgba(255, 255, 255, 0.6);
  position: relative;
  overflow: hidden;
}
.wallet-hero::before {
  content: "💵";
  position: absolute;
  top: 10px; right: 24px;
  font-size: 120px;
  opacity: 0.14;
  transform: rotate(-8deg);
  pointer-events: none;
  /* Slight desaturation so the banknote feels like a neutral watermark
     instead of a bright solid-color accent. */
  filter: grayscale(0.6);
}
.wallet-hero-inner { position: relative; z-index: 1; }
.wallet-total-label {
  font-size: 12px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--c-text-2);
  margin-bottom: 6px;
}
.wallet-total {
  display: flex;
  align-items: baseline;
  gap: 8px;
  margin-bottom: 14px;
}
.wallet-total-num {
  font-size: 72px;
  font-weight: 900;
  line-height: 1;
  letter-spacing: -0.04em;
  color: #7c2d12;
  font-feature-settings: "tnum";
  text-shadow: 0 2px 0 rgba(255, 255, 255, 0.6);
}
.wallet-total-unit {
  font-size: 24px;
  font-weight: 800;
  color: #9a3412;
}
.wallet-total-breakdown {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 10px;
  font-size: 14px;
  color: var(--c-text);
}
.wallet-total-breakdown .dot { color: var(--c-text-3); }

.wallet-kids {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
  gap: 18px;
}
.wallet-kid-card {
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 22px 24px;
  box-shadow: 0 4px 12px -6px rgba(0, 0, 0, 0.08);
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.wallet-kid-card:hover {
  transform: translateY(-2px);
  box-shadow: 0 12px 28px -10px rgba(249, 115, 22, 0.25);
}
.wallet-kid-head {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 12px;
}
.wallet-kid-emoji { font-size: 32px; line-height: 1; }
.wallet-kid-name {
  margin: 0;
  font-size: 15px;
  font-weight: 700;
  color: var(--c-text-2);
}
.wallet-kid-total {
  display: flex;
  align-items: baseline;
  gap: 6px;
  margin-bottom: 16px;
}
.wallet-kid-total-num {
  font-size: 42px;
  font-weight: 900;
  line-height: 1;
  color: #16a34a;
  font-feature-settings: "tnum";
  letter-spacing: -0.02em;
}
.wallet-kid-total-unit {
  font-size: 16px;
  font-weight: 700;
  color: var(--c-text-2);
}
.wallet-kid-rows {
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 12px 0;
  border-top: 1px solid var(--c-border);
  border-bottom: 1px solid var(--c-border);
  margin-bottom: 12px;
}
.wallet-kid-row {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 12px;
  font-size: 13px;
  color: var(--c-text);
}
.wallet-kid-row strong {
  font-weight: 800;
  color: var(--c-text);
  font-feature-settings: "tnum";
}
.wallet-kid-foot { line-height: 1.5; }
/* Action row on each wallet kid card — "Bar ausgezahlt" button + the
   pending-redemptions shortcut when applicable. */
.wallet-kid-actions {
  margin-top: 14px;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}

@media (max-width: 720px) {
  .wallet-hero { padding: 24px 20px; }
  .wallet-total-num { font-size: 56px; }
  .wallet-hero::before { font-size: 80px; top: 10px; right: 14px; }
  .wallet-kids { grid-template-columns: 1fr; }
}

/* ── Vault (child rewards dashboard) ──────────────────────────────── */
/* The hero is intentionally loud: big gradient background, huge balance
   number, goal bar. For a kid, the balance IS the app — it's the reason
   they take another test. Don't underplay it. */
.vault-hero {
  position: relative;
  padding: 36px 32px 32px;
  background: linear-gradient(135deg, #fff7ed 0%, #fed7aa 40%, #fbcfe8 100%);
  border-radius: var(--r-lg);
  box-shadow: 0 20px 60px -24px rgba(249, 115, 22, 0.35),
              inset 0 1px 0 rgba(255, 255, 255, 0.6);
  overflow: hidden;
}
.vault-hero::before {
  content: "💰";
  position: absolute;
  top: 20px; right: 28px;
  font-size: 120px;
  opacity: 0.18;
  transform: rotate(-8deg);
  pointer-events: none;
}
.vault-hero-inner {
  position: relative;
  z-index: 1;
}
.vault-greet {
  display: flex;
  align-items: center;
  gap: 10px;
  font-size: 18px;
  font-weight: 700;
  color: var(--c-text);
  margin-bottom: 12px;
}
.vault-kid-emoji { font-size: 32px; line-height: 1; }
.vault-balance-label {
  font-size: 12px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--c-text-2);
  margin-bottom: 4px;
}
.vault-balance {
  display: flex;
  align-items: baseline;
  gap: 8px;
  margin-bottom: 24px;
}
.vault-balance-num {
  font-size: 84px;
  font-weight: 900;
  line-height: 1;
  letter-spacing: -0.04em;
  color: #7c2d12;
  font-feature-settings: "tnum";
  text-shadow: 0 2px 0 rgba(255, 255, 255, 0.6);
}
.vault-balance-unit {
  font-size: 28px;
  font-weight: 800;
  color: #9a3412;
}
.vault-goal {
  background: rgba(255, 255, 255, 0.65);
  backdrop-filter: saturate(180%) blur(6px);
  border: 1px solid rgba(249, 115, 22, 0.25);
  border-radius: var(--r-md);
  padding: 14px 18px;
  max-width: 520px;
}
.vault-goal-label {
  font-size: 14px;
  color: var(--c-text);
  margin-bottom: 8px;
}
.vault-goal-bar {
  position: relative;
  height: 14px;
  background: rgba(255, 255, 255, 0.85);
  border-radius: var(--r-full);
  overflow: hidden;
  margin-bottom: 8px;
  border: 1px solid rgba(249, 115, 22, 0.2);
}
.vault-goal-fill {
  height: 100%;
  background: linear-gradient(90deg, #f59e0b 0%, #f97316 50%, #ec4899 100%);
  border-radius: var(--r-full);
  transition: width 700ms var(--ease-bounce);
  box-shadow: 0 0 12px rgba(249, 115, 22, 0.5);
}
.vault-goal-pct {
  position: absolute;
  right: 8px;
  top: 50%;
  transform: translateY(-50%);
  font-size: 10px;
  font-weight: 800;
  color: var(--c-text);
  text-shadow: 0 1px 0 rgba(255, 255, 255, 0.8);
}
.vault-goal-remaining {
  font-size: 13px;
  color: var(--c-text-2);
}

/* Reward grid cards */
.reward-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
  gap: 18px;
}
.reward-card {
  display: flex;
  flex-direction: column;
  gap: 10px;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 24px;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.reward-card:hover {
  transform: translateY(-3px);
  box-shadow: 0 12px 28px -12px rgba(249, 115, 22, 0.25);
}
.reward-card-ready {
  border-color: rgba(34, 197, 94, 0.5);
  background: linear-gradient(180deg, rgba(220, 252, 231, 0.4) 0%, var(--c-surface) 60%);
}
.reward-card-locked { opacity: 0.88; }
.reward-card-emoji {
  font-size: 48px;
  line-height: 1;
  text-align: center;
}
.reward-card-name {
  margin: 0;
  font-size: 17px;
  font-weight: 800;
  color: var(--c-text);
  text-align: center;
}
.reward-card-desc {
  margin: 0;
  font-size: 13px;
  color: var(--c-text-2);
  text-align: center;
}
.reward-card-cost {
  display: flex;
  align-items: baseline;
  justify-content: center;
  gap: 4px;
  margin: 4px 0;
}
.reward-card-cost-num {
  font-size: 28px;
  font-weight: 900;
  color: var(--c-text);
  font-feature-settings: "tnum";
  letter-spacing: -0.02em;
}
.reward-card-cost-unit {
  font-size: 14px;
  font-weight: 700;
  color: var(--c-text-2);
}
.reward-card-bar {
  height: 10px;
  background: #f1f5f9;
  border-radius: var(--r-full);
  overflow: hidden;
}
.reward-card-bar-fill {
  height: 100%;
  background: linear-gradient(90deg, #fbbf24 0%, #f97316 100%);
  border-radius: var(--r-full);
  transition: width 600ms var(--ease);
}
.reward-card-bar-fill-ready {
  background: linear-gradient(90deg, #22c55e 0%, #16a34a 100%);
  box-shadow: 0 0 8px rgba(34, 197, 94, 0.5);
}
.reward-card-bar-label {
  text-align: center;
  margin: 4px 0 8px;
}

/* Transaction ledger */
.ledger {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.ledger-row {
  display: flex;
  align-items: center;
  gap: 14px;
  padding: 14px 18px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
}
.ledger-row-earn  { border-left: 4px solid #22c55e; }
.ledger-row-spend { border-left: 4px solid #f97316; }
.ledger-icon {
  font-size: 26px;
  line-height: 1;
  flex-shrink: 0;
}
.ledger-main { flex: 1; min-width: 0; }
.ledger-main strong { font-weight: 700; }
.ledger-status {
  display: inline-block;
  margin-left: 8px;
  font-size: 11px;
  font-weight: 700;
  padding: 2px 8px;
  border-radius: var(--r-full);
  background: #fef3c7;
  color: #b45309;
  border: 1px solid #fcd34d;
}
.ledger-status-ok {
  background: #dcfce7;
  color: #15803d;
  border-color: #86efac;
}
.ledger-amount {
  font-weight: 800;
  font-size: 16px;
  font-feature-settings: "tnum";
  flex-shrink: 0;
}
.ledger-amount-earn  { color: #16a34a; }
.ledger-amount-spend { color: #dc2626; }

/* Parent banker: catalog list rows */
.reward-catalog {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.reward-row {
  display: flex;
  align-items: center;
  gap: 14px;
  padding: 12px 14px;
  background: #f8fafc;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
}
.reward-row-emoji { font-size: 28px; line-height: 1; flex-shrink: 0; }
.reward-row-info { flex: 1; min-width: 0; }
.reward-row-cost {
  text-align: right;
  flex-shrink: 0;
}
.reward-row-cost strong {
  font-size: 18px;
  font-weight: 800;
  color: var(--c-text);
}

/* Phone tweaks */
@media (max-width: 720px) {
  .vault-hero { padding: 28px 22px 24px; }
  .vault-balance-num { font-size: 64px; }
  .vault-hero::before { font-size: 80px; top: 10px; right: 14px; }
  .reward-grid { grid-template-columns: 1fr; }
}

/* ── Parent home (kid-picker, Steve-Jobs-style) ───────────────────── */
/* The home page is deliberately spare: just a greeting and big kid cards.
   Eye path: greeting top → kid cards dominate middle → tools demoted below.
   One clear action per card (tap to enter), no competing focus. */

.home-hero {
  margin: 20px 0 32px;
}
.home-hero h1 {
  margin: 0 0 4px;
  font-size: 40px;
  font-weight: 900;
  letter-spacing: -0.03em;
  color: var(--c-text);
}
.home-hero .wave {
  display: inline-block;
  animation: waveHand 2.2s ease-in-out;
  transform-origin: 70% 80%;
}
@keyframes waveHand {
  0%, 100% { transform: rotate(0); }
  15%      { transform: rotate(14deg); }
  30%      { transform: rotate(-8deg); }
  45%      { transform: rotate(14deg); }
  60%      { transform: rotate(-4deg); }
  75%      { transform: rotate(10deg); }
}
.home-hero .sub {
  margin: 0;
  font-size: 16px;
  line-height: 1.5;
}

/* Kid cards — the heart of the screen. Big, clickable, warm. */
.home-kids {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
  gap: 16px;
  margin-bottom: 48px;
}
.home-kid-card {
  display: flex;
  align-items: center;
  gap: 20px;
  padding: 24px 28px;
  background: var(--c-surface);
  border: 2px solid var(--c-border);
  border-radius: var(--r-lg);
  color: var(--c-text);
  text-decoration: none;
  cursor: pointer;
  font-family: inherit;
  text-align: left;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
  position: relative;
  min-height: 108px;
}
.home-kid-card:hover {
  transform: translateY(-3px);
  box-shadow: 0 16px 36px -12px rgba(249, 115, 22, 0.3);
  border-color: var(--c-primary-br);
  text-decoration: none;
}
.home-kid-card:hover .home-kid-arrow {
  transform: translateX(4px);
  color: var(--c-primary);
}
/* Tonal left-border accents so the eye can scan status without reading */
.home-kid-card-good    { border-left: 6px solid #16a34a; }
.home-kid-card-warn    { border-left: 6px solid #f59e0b; }
.home-kid-card-pending { border-left: 6px solid #3b82f6; }
.home-kid-card-neutral { border-left: 6px solid var(--c-border); }
.home-kid-card-add {
  border: 2px dashed var(--c-border);
  background: transparent;
  color: var(--c-text-2);
}
.home-kid-card-add:hover {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  color: var(--c-text);
}

/* ── Kid-card edit/delete hover controls ─────────────────────────────
   The wrap sits in the grid in place of the old bare <a>. The link
   itself still fills the wrap; these two span controls sit absolutely
   over the top-right corner and reveal on hover / focus-within. */
.home-kid-card-wrap {
  position: relative;
  display: block;
}
.home-kid-card-wrap .home-kid-card {
  /* Reserve a little space on the right for the controls so the name
     never collides with the ✎ / × when revealed. */
  padding-right: 72px;
}
.kid-card-ctrl {
  position: absolute;
  top: 10px;
  width: 26px;
  height: 26px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--c-border);
  border-radius: 50%;
  background: var(--c-surface);
  color: var(--c-text-3);
  font-size: 14px;
  font-weight: 700;
  line-height: 1;
  cursor: pointer;
  user-select: none;
  z-index: 2;
  opacity: 0;
  pointer-events: none;
  transition: opacity var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
}
.kid-card-ctrl-edit { right: 46px; }
.kid-card-ctrl-del  { right: 14px; font-size: 17px; }

/* Reveal on hover / keyboard focus of the wrap (covers tab-into-span). */
.home-kid-card-wrap:hover .kid-card-ctrl,
.home-kid-card-wrap:focus-within .kid-card-ctrl {
  opacity: 1;
  pointer-events: auto;
}
@media (hover: none) {
  /* Touch devices have no hover — always show so the parent can use
     them on a tablet. */
  .kid-card-ctrl { opacity: 1; pointer-events: auto; }
}

.kid-card-ctrl-edit:hover,
.kid-card-ctrl-edit:focus-visible {
  background: var(--c-accent-3);
  border-color: var(--c-accent-br);
  color: var(--c-accent-2);
  transform: scale(1.08);
  outline: none;
}
.kid-card-ctrl-del:hover,
.kid-card-ctrl-del:focus-visible {
  background: var(--c-err-3);
  border-color: var(--c-err-br);
  color: var(--c-err-2);
  transform: scale(1.08);
  outline: none;
}

.home-kid-emoji {
  font-size: 56px;
  line-height: 1;
  flex-shrink: 0;
}
.home-kid-info {
  flex: 1;
  min-width: 0;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.home-kid-name {
  font-size: 22px;
  font-weight: 800;
  color: var(--c-text);
  letter-spacing: -0.01em;
}
.home-kid-status {
  font-size: 14px;
  color: var(--c-text-2);
  font-weight: 500;
}
.home-kid-arrow {
  font-size: 28px;
  font-weight: 300;
  color: var(--c-text-3);
  flex-shrink: 0;
  transition: transform var(--dur-fast) var(--ease), color var(--dur-fast) var(--ease);
}

/* Tools row — demoted to a slim, quiet strip. Tertiary priority. */
.home-tools {
  padding-top: 24px;
  border-top: 1px solid var(--c-border);
}
.home-tools-label {
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--c-text-3);
  margin-bottom: 12px;
}
.home-tools-row {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
}
.home-tool {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 10px 16px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-full);
  color: var(--c-text-2);
  text-decoration: none;
  font-size: 13px;
  font-weight: 600;
  transition: all var(--dur-fast) var(--ease);
}
.home-tool:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  color: var(--c-text);
  text-decoration: none;
  transform: translateY(-1px);
}
.home-tool-icon { font-size: 16px; line-height: 1; }

/* ── Kid Room (individual child workspace) ────────────────────────── */
.kid-hero {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 24px;
  padding: 28px 32px;
  background: linear-gradient(135deg, #fff7ed 0%, #ffedd5 50%, #fef3f9 100%);
  border-radius: var(--r-lg);
  box-shadow: 0 16px 40px -16px rgba(249, 115, 22, 0.25),
              inset 0 1px 0 rgba(255, 255, 255, 0.6);
  margin-top: 12px;
  flex-wrap: wrap;
}
.kid-hero-identity {
  display: flex;
  align-items: center;
  gap: 20px;
  min-width: 0;
}
.kid-hero-emoji {
  font-size: 64px;
  line-height: 1;
  flex-shrink: 0;
}
.kid-hero-name {
  margin: 0;
  font-size: 36px;
  font-weight: 900;
  letter-spacing: -0.03em;
  color: var(--c-text);
  line-height: 1;
}
.kid-hero-sub {
  margin: 6px 0 0;
  font-size: 13px;
}
.kid-hero-sub code {
  background: rgba(0, 0, 0, 0.06);
  padding: 2px 8px;
  border-radius: var(--r-sm);
  font-size: 12px;
}
.kid-hero-balance {
  text-align: right;
  padding: 12px 20px;
  background: rgba(255, 255, 255, 0.7);
  border: 1px solid rgba(249, 115, 22, 0.2);
  border-radius: var(--r-md);
  backdrop-filter: blur(4px);
}
.kid-hero-balance-label {
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: var(--c-text-2);
  margin-bottom: 4px;
}
.kid-hero-balance-num {
  font-size: 32px;
  font-weight: 900;
  line-height: 1;
  color: #16a34a;
  font-feature-settings: "tnum";
  letter-spacing: -0.02em;
}
.kid-hero-balance-unit {
  font-size: 15px;
  font-weight: 700;
  color: var(--c-text-2);
}

/* ── Kid room: Fortschritt dashboard ───────────────────────────────
   Four-tile stats row answering "is my kid using this, on a streak, how
   accurate, and how much done?" — plus a weak-topics list below. Only
   renders when the kid has at least one attempt, so a brand-new kid's
   room doesn't feel like a performance review. */
/* Onboarding banner shown when the kid has tests assigned but no attempts
   yet — tells the parent what will appear here so the empty tiles below
   feel like a preview, not a broken feature. */
.stats-preview {
  display: flex;
  gap: 16px;
  align-items: flex-start;
  padding: 16px 20px;
  margin-bottom: 16px;
  background: linear-gradient(135deg, #f0fdf4 0%, #eff6ff 100%);
  border: 1px solid #bbf7d0;
  border-radius: var(--r-md);
}
.stats-preview-icon {
  font-size: 32px;
  line-height: 1;
  flex-shrink: 0;
}
.stats-preview-title {
  margin: 0 0 4px;
  font-size: 16px;
  font-weight: 800;
  color: var(--c-text);
}
.stats-preview-sub {
  margin: 0;
  font-size: 13px;
  line-height: 1.5;
  color: var(--c-text-2);
}

.stat-tiles {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 14px;
}
/* Dimmed tiles for the "no activity yet" preview — convey "this will
   populate later" without looking disabled. */
.stat-tiles-dim .stat-tile {
  opacity: 0.72;
}
.stat-tiles-dim .stat-tile-num {
  color: var(--c-text-3) !important;
}
@media (max-width: 860px) {
  .stat-tiles { grid-template-columns: repeat(2, 1fr); }
}
.stat-tile {
  position: relative;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 16px 18px 18px;
  box-shadow: var(--sh-xs);
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.stat-tile-label {
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: var(--c-text-3);
}
.stat-tile-num {
  font-size: 32px;
  font-weight: 900;
  color: var(--c-text);
  line-height: 1;
  letter-spacing: -0.01em;
  font-feature-settings: "tnum";
}
.stat-tile-num-denom {
  font-size: 18px;
  font-weight: 700;
  color: var(--c-text-3);
  margin-left: 2px;
}
.stat-tile-sub {
  margin: 0;
}
/* Score tile tone — green/amber/red accent on the number + left border so
   the parent gets the read at a glance without reading the subtitle. */
/* Tone styling on the Durchschnitt tile — only the number takes the
   color now, so the tile's frame matches every other tile. */
.stat-tile-ok     .stat-tile-num { color: #16a34a; }
.stat-tile-warn   .stat-tile-num { color: #d97706; }
.stat-tile-danger .stat-tile-num { color: #dc2626; }
.stat-tile-muted  .stat-tile-num { color: var(--c-text-3); }
/* Completion progress bar on the "Erledigt" tile. */
.stat-tile-bar {
  margin-top: 10px;
  height: 6px;
  background: var(--c-surface-2);
  border-radius: 999px;
  overflow: hidden;
}
.stat-tile-bar-fill {
  height: 100%;
  background: var(--grad-warm);
  border-radius: 999px;
  transition: width var(--dur-med) var(--ease);
}

/* Weak-topics list: one-line rows linking to the subject room so the
   parent can jump straight to the problem area. Score pill is colored
   amber to cue "needs attention" without feeling alarming. */
.weak-topics {
  margin-top: 22px;
  background: #fffbeb;
  border: 1px solid #fde68a;
  border-radius: var(--r-md);
  padding: 16px 18px;
}
.weak-topics-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 10px;
  flex-wrap: wrap;
}
.weak-topics-label {
  font-weight: 800;
  color: #92400e;
}
.weak-topics-list {
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.weak-topic {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 14px;
  padding: 10px 14px;
  background: var(--c-surface);
  border: 1px solid #fde68a;
  border-radius: var(--r-sm);
  text-decoration: none;
  color: var(--c-text);
  transition: transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.weak-topic:hover {
  transform: translateX(3px);
  border-color: #f59e0b;
  box-shadow: 0 6px 14px -8px rgba(217, 119, 6, 0.35);
  text-decoration: none;
}
.weak-topic-body {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 0;
}
.weak-topic-name {
  font-weight: 700;
  font-size: 14px;
}
.weak-topic-score {
  font-size: 16px;
  font-weight: 900;
  color: #b45309;
  font-feature-settings: "tnum";
  padding: 4px 10px;
  background: #fef3c7;
  border-radius: 999px;
  flex-shrink: 0;
}

/* Row wrapping a weak-topic link + its "Erinnern" nudge button so the
   two sit side by side without the nudge click bubbling to the link. */
.weak-topic-row {
  display: flex;
  gap: 8px;
  align-items: stretch;
}
.weak-topic-row > .weak-topic { flex: 1; min-width: 0; }
.weak-topic-nudge {
  flex-shrink: 0;
  padding: 0 14px;
  background: #fff;
  border: 1px solid #fde68a;
  border-radius: var(--r-sm);
  font-size: 12px;
  font-weight: 700;
  color: #92400e;
  cursor: pointer;
  transition: transform var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.weak-topic-nudge:hover {
  transform: translateY(-1px);
  background: #fef3c7;
  border-color: #f59e0b;
}
.weak-topic-nudge:active { transform: translateY(0); }

/* "+ N weitere anzeigen" toggle under the weak-topics list. */
.weak-topics-toggle {
  margin-top: 10px;
  padding: 8px 14px;
  background: transparent;
  border: 1px dashed #fde68a;
  border-radius: var(--r-sm);
  font-size: 12px;
  font-weight: 700;
  color: #92400e;
  cursor: pointer;
  width: 100%;
  text-align: center;
  transition: background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.weak-topics-toggle:hover {
  background: #fef3c7;
  border-color: #f59e0b;
  border-style: solid;
}

/* Remind dialog — preset-chip grid for quick motivational templates. */
.remind-presets {
  display: flex;
  flex-direction: column;
  gap: 6px;
  margin: 12px 0 4px;
}
.remind-preset {
  padding: 10px 12px;
  background: var(--c-surface-2);
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  font-size: 13px;
  text-align: left;
  cursor: pointer;
  color: var(--c-text);
  transition: background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.remind-preset:hover {
  background: var(--c-primary-3);
  border-color: var(--c-primary);
}

/* ── Student-side "Kurz vor dem Ziel" ─────────────────────────────
   Encouraging weak-topic cards. Deliberately warm + friendly, not
   diagnostic — a green-cream gradient with a "Jetzt ueben" CTA that
   jumps straight to the test with the kid's lowest score in that
   topic. Same 70% data as the parent's Wo-zu-verbessern panel. */
.kid-almost-list {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
  gap: 12px;
}
.kid-almost-card {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  padding: 18px 20px;
  background: linear-gradient(135deg, #f0fdf4 0%, #fff7ed 100%);
  border: 1px solid #bbf7d0;
  border-radius: var(--r-md);
  text-decoration: none;
  color: var(--c-text);
  box-shadow: 0 6px 14px -10px rgba(22, 163, 74, 0.3);
  transition: transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.kid-almost-card:hover {
  transform: translateY(-2px);
  border-color: #34d399;
  box-shadow: 0 10px 24px -8px rgba(22, 163, 74, 0.35);
  text-decoration: none;
  color: var(--c-text);
}
.kid-almost-body { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 3px; }
.kid-almost-kicker {
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: #047857;
}
.kid-almost-name {
  font-size: 17px;
  letter-spacing: -0.01em;
  color: var(--c-text);
}
.kid-almost-hint {
  margin-top: 4px;
  letter-spacing: 0;
}
.kid-almost-cta {
  flex-shrink: 0;
  padding: 10px 16px;
  background: #16a34a;
  color: #fff;
  border-radius: 999px;
  font-size: 13px;
  font-weight: 800;
  box-shadow: 0 4px 10px -4px rgba(22, 163, 74, 0.5);
  transition: transform var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.kid-almost-card:hover .kid-almost-cta {
  background: #15803d;
  transform: translateX(3px);
}
@media (max-width: 560px) {
  .kid-almost-card { flex-direction: column; align-items: flex-start; }
  .kid-almost-cta  { align-self: flex-end; }
}

/* Student-side: reminder banner cards above the test list. */
.reminders-list {
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.reminder-card {
  display: flex;
  gap: 16px;
  align-items: flex-start;
  padding: 16px 20px;
  background: linear-gradient(135deg, #fdf4ff 0%, #fff7ed 100%);
  border: 1px solid #f5d0fe;
  border-radius: var(--r-md);
  box-shadow: 0 6px 14px -8px rgba(168, 85, 247, 0.2);
}
.reminder-card-icon {
  font-size: 30px;
  line-height: 1;
  flex-shrink: 0;
}
.reminder-card-body { flex: 1; min-width: 0; }
.reminder-card-context {
  font-size: 11px;
  font-weight: 800;
  color: #86198f;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  margin-bottom: 6px;
}
.reminder-card-message {
  margin: 0;
  font-size: 15px;
  line-height: 1.5;
  color: var(--c-text);
}
.reminder-card-dismiss { flex-shrink: 0; }
@media (max-width: 560px) {
  .reminder-card { flex-direction: column; }
  .reminder-card-dismiss { align-self: flex-end; }
}

/* ── Dashboard: Kind-Uebersicht (parent quick-glance panel) ─────────
   A deep per-kid snapshot shown below the kid-picker cards. The dropdown
   in the section header toggles which kid's panel is visible — all panels
   are pre-rendered so switching is instant. */
.home-overview .section-head {
  gap: 16px;
}
.home-overview .section-head h2 {
  margin: 0;
}
.overview-picker {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin-left: auto;
}
.overview-picker select {
  padding: 8px 12px;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  background: var(--c-surface);
  font-size: 14px;
  font-weight: 600;
  color: var(--c-text);
  cursor: pointer;
  min-width: 160px;
}
.overview-picker select:hover,
.overview-picker select:focus {
  border-color: var(--c-primary);
  outline: none;
}

.overview-panel {
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 22px;
  box-shadow: var(--sh-xs);
}

/* ── Portemonnaie card (premium) ─────────────────────────────────────
   The money card at the top of each kid's overview — designed to feel
   like a physical credit/debit card. Dark emerald base, gold-leaf amount,
   subtle top gloss, and a faint coin watermark behind the number. The
   whole card is one tap target that jumps to the wallet page. */
.overview-wallet {
  position: relative;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  padding: 22px 26px;
  border-radius: 14px;
  border: 1px solid rgba(16, 185, 129, 0.35);
  background:
    radial-gradient(1200px circle at 100% 0%, rgba(250, 204, 21, 0.15) 0%, transparent 50%),
    linear-gradient(135deg, #022c22 0%, #064e3b 45%, #065f46 100%);
  box-shadow:
    0 10px 30px -12px rgba(2, 44, 34, 0.55),
    inset 0 1px 0 rgba(255, 255, 255, 0.08);
  color: #ecfdf5;
  text-decoration: none;
  overflow: hidden;
  isolation: isolate;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
/* Gold watermark coin behind the number — faint but present. */
.overview-wallet::before {
  content: "";
  position: absolute;
  top: -40px; right: -40px;
  width: 200px; height: 200px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(250, 204, 21, 0.22) 0%, rgba(250, 204, 21, 0) 65%);
  z-index: 0;
  pointer-events: none;
}
/* Hairline top gloss — the glass finish on a real card. */
.overview-wallet::after {
  content: "";
  position: absolute;
  top: 0; left: 0; right: 0;
  height: 1px;
  background: linear-gradient(90deg, transparent 0%, rgba(255, 255, 255, 0.22) 50%, transparent 100%);
  z-index: 1;
  pointer-events: none;
}
.overview-wallet:hover {
  transform: translateY(-2px);
  border-color: rgba(250, 204, 21, 0.55);
  box-shadow:
    0 14px 36px -12px rgba(2, 44, 34, 0.65),
    inset 0 1px 0 rgba(255, 255, 255, 0.12);
  text-decoration: none;
  color: #ecfdf5;
}
.overview-wallet-body {
  position: relative;
  z-index: 2;
  display: flex;
  flex-direction: column;
  gap: 8px;
  min-width: 0;
}
.overview-wallet-label {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: rgba(236, 253, 245, 0.72);
}
.overview-wallet-num {
  font-size: 42px;
  font-weight: 900;
  line-height: 1;
  letter-spacing: -0.02em;
  font-feature-settings: "tnum";
  background: linear-gradient(135deg, #fde68a 0%, #fbbf24 45%, #f59e0b 100%);
  -webkit-background-clip: text;
          background-clip: text;
  -webkit-text-fill-color: transparent;
  text-shadow: 0 2px 12px rgba(250, 204, 21, 0.25);
}
.overview-wallet-unit {
  font-size: 18px;
  font-weight: 700;
  margin-left: 6px;
  color: rgba(253, 230, 138, 0.85);
  -webkit-text-fill-color: rgba(253, 230, 138, 0.85);
}
.overview-wallet-arrow {
  position: relative;
  z-index: 2;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  background: rgba(250, 204, 21, 0.12);
  border: 1px solid rgba(250, 204, 21, 0.35);
  color: #fbbf24;
  font-size: 18px;
  font-weight: 800;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
  transition: transform var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.overview-wallet:hover .overview-wallet-arrow {
  transform: translateX(4px);
  background: rgba(250, 204, 21, 0.22);
}

/* Werkzeuge tiles — grid row of parent tools directly under the wallet
   card. Each tile is a soft card that pops on hover. Auto-fills so
   layouts with one, two, or three tiles all read correctly. */
.overview-tools {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
  gap: 10px;
  margin-top: 12px;
}
/* Single-tile layout: stretch full width so it doesn't look like a dangling
   tile floating at 1/3 width. */
.overview-tools-single {
  grid-template-columns: 1fr;
}
@media (max-width: 720px) {
  .overview-tools { grid-template-columns: 1fr; }
}
.overview-tool {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 14px 16px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  text-decoration: none;
  color: var(--c-text);
  transition: transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.overview-tool:hover {
  transform: translateY(-1px);
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: 0 6px 14px -8px rgba(249, 115, 22, 0.25);
  text-decoration: none;
  color: var(--c-text);
}
.overview-tool-icon {
  font-size: 24px;
  line-height: 1;
  flex-shrink: 0;
}
.overview-tool-body {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 0;
}
.overview-tool-name {
  font-size: 14px;
  font-weight: 800;
  color: var(--c-text);
}
.overview-tool-sub {
  letter-spacing: 0;
}

/* Two-dropdown row for the chart header — Fach + Test side by side.
   Wraps onto two lines on narrow screens so neither picker gets
   crunched. */
.overview-chart-filters {
  display: flex;
  gap: 12px;
  flex-wrap: wrap;
  align-items: center;
}
.overview-chart-filters .overview-picker select {
  min-width: 140px;
}

/* Testverlauf chart — hand-rolled SVG so we don't pull in a charting lib
   for one line chart. Grid lines stay subtle except the 80% pass line,
   which is emphasized with the brand green. */
.overview-chart .chart-host {
  background: #fafbfc;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  padding: 10px 14px;
  /* Let the floating hover tooltip escape the top edge — with 100%
     bars the tooltip would otherwise be clipped at the chart border. */
  overflow: visible;
}
/* Just in case an ancestor clips — the block itself shouldn't either. */
.overview-chart { overflow: visible; }
.overview-chart .chart {
  width: 100%;
  height: auto;
  display: block;
  font-family: inherit;
}
/* Single reference line (80% pass threshold) with a tiny right-side
   label — replaces the four-line grid. */
.overview-chart .chart-ref {
  stroke: #16a34a;
  stroke-width: 1;
  stroke-dasharray: 4 4;
  opacity: 0.5;
}
.overview-chart .chart-ref-lbl {
  font-size: 7px;
  font-weight: 700;
  fill: #16a34a;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}
/* X-axis date label — just dd.mm. per bar. */
.overview-chart .x-lbl {
  font-size: 7px;
  font-weight: 600;
  fill: var(--c-text-3);
  font-feature-settings: "tnum";
  letter-spacing: 0.02em;
}
/* Subject label above each bar group — colored like the bars themselves
   so the link "this color = this subject" is immediate. */
.overview-chart .group-lbl {
  font-size: 9px;
  font-weight: 800;
  letter-spacing: 0.02em;
  font-feature-settings: "tnum";
  text-transform: uppercase;
}
/* Faint vertical line between subject groups — cues the cluster break
   without heavy visual weight. */
.overview-chart .group-divider {
  stroke: #e5e7eb;
  stroke-width: 1;
  stroke-dasharray: 2 3;
  opacity: 0.8;
}
.overview-chart .bar rect {
  transition: fill-opacity 0.12s;
  cursor: pointer;
}
.overview-chart .bar:hover rect {
  fill-opacity: 1 !important;
}
/* Inline score label (shown only in single-subject filtered mode) — sits
   inside the bar, white on the subject color. Tiny + tabular nums. */
.overview-chart .bar-lbl {
  font-size: 9px;
  font-weight: 700;
  font-feature-settings: "tnum";
  letter-spacing: -0.01em;
  pointer-events: none;
}

/* Floating tooltip card — shown when the parent hovers a bar. Lives
   inside the chart-host (position:relative) so absolute positioning
   works against the SVG bounds. */
.chart-host-pos { position: relative; }
.chart-tooltip {
  position: absolute;
  min-width: 180px;
  max-width: 260px;
  padding: 10px 14px;
  background: #fff;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  box-shadow: 0 10px 24px -8px rgba(0, 0, 0, 0.25);
  pointer-events: none;
  opacity: 0;
  transform: translate(-50%, -100%);
  transition: opacity 0.12s var(--ease);
  z-index: 10;
  font-size: 12px;
  line-height: 1.4;
}
.chart-tooltip.chart-tooltip-visible { opacity: 1; }

/* Little arrow on the underside (or upper when below). */
.chart-tooltip::after {
  content: "";
  position: absolute;
  left: 50%;
  transform: translateX(-50%);
  width: 10px;
  height: 10px;
  background: #fff;
  border-right: 1px solid var(--c-border);
  border-bottom: 1px solid var(--c-border);
}
.chart-tooltip::after {
  bottom: -6px;
  transform: translateX(-50%) rotate(45deg);
}

/* Tooltip content hierarchy. */
.chart-tooltip .tt-head {
  font-size: 10px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  margin-bottom: 4px;
}
.chart-tooltip .tt-test {
  font-size: 13px;
  font-weight: 700;
  color: var(--c-text);
  margin-bottom: 8px;
  line-height: 1.25;
}
.chart-tooltip .tt-score-row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px;
  margin-bottom: 4px;
}
.chart-tooltip .tt-score {
  font-size: 20px;
  font-weight: 900;
  font-feature-settings: "tnum";
  line-height: 1;
}
.chart-tooltip .tt-score-pass { color: #16a34a; }
.chart-tooltip .tt-score-fail { color: #d97706; }
.chart-tooltip .tt-meta {
  font-size: 11px;
  font-weight: 600;
  color: var(--c-text-3);
}
.chart-tooltip .tt-when {
  font-size: 11px;
  font-weight: 600;
  color: var(--c-text-2);
  font-feature-settings: "tnum";
}
.chart-tooltip .tt-day {
  display: block;
  margin-top: 6px;
  padding-top: 6px;
  border-top: 1px solid var(--c-border);
  font-size: 10px;
  font-weight: 700;
  color: #6366f1;
  letter-spacing: 0.02em;
}

/* Legend row below the chart — one chip per subject in view, with a
   tiny "faded = under 80%" note on the right when relevant. */
.chart-legend {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: center;
  gap: 8px 16px;
  padding: 10px 6px 2px;
  border-top: 1px dashed var(--c-border);
  margin-top: 6px;
}
.chart-legend-item {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 11px;
  font-weight: 700;
  color: var(--c-text);
  letter-spacing: 0.01em;
}
.chart-legend-swatch {
  width: 10px;
  height: 10px;
  border-radius: 2px;
  display: inline-block;
  flex-shrink: 0;
}
.chart-legend-count {
  font-weight: 600;
  font-feature-settings: "tnum";
}
.chart-legend-note {
  font-size: 10px;
  font-weight: 600;
  margin-left: auto;
}
@media (max-width: 560px) {
  .chart-legend-note { margin-left: 0; width: 100%; text-align: center; }
}

/* Sortable table header — currently used on the Datum column only.
   The whole <th> is a button so the click target is big; an arrow
   indicator shows the active direction. */
.th-sort { padding: 0 !important; }
.th-sort-btn {
  width: 100%;
  height: 100%;
  padding: 10px 14px;
  background: transparent;
  border: 0;
  color: inherit;
  font: inherit;
  font-size: inherit;
  font-weight: inherit;
  text-transform: inherit;
  letter-spacing: inherit;
  text-align: left;
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  gap: 6px;
  transition: color var(--dur-fast) var(--ease);
}
.th-sort-btn:hover { color: var(--c-primary); }
.th-sort-arrow {
  font-size: 10px;
  color: var(--c-primary);
  font-feature-settings: "tnum";
}

/* Test-title link inside the Ergebnisse table — reads as a normal
   title at rest, highlights on hover so the parent knows it's
   navigable to the test editor. */
.results-test-link {
  color: var(--c-text);
  font-weight: 700;
  text-decoration: none;
  transition: color var(--dur-fast) var(--ease);
}
.results-test-link:hover {
  color: var(--c-primary);
  text-decoration: underline;
}

/* ── Ergebnisse inline filters (kid room results table) ─────────────
   Per-column filter row under the <thead>. Each filter is a small
   dropdown that sits directly below its header label, so it reads as
   "refine this column". Filter logic is client-side — instant. */
.results-filter-row th {
  background: #fafbfc;
  padding: 8px 14px;
  border-top: 1px solid var(--c-border);
  text-transform: none;
  letter-spacing: 0;
  font-weight: 400;
}
.results-filter-select {
  width: 100%;
  padding: 6px 10px;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  background: var(--c-surface);
  font-size: 12px;
  font-weight: 600;
  color: var(--c-text);
  cursor: pointer;
}
.results-filter-select:hover,
.results-filter-select:focus {
  border-color: var(--c-primary);
  outline: none;
}

/* "Diese Woche" strip — an agenda row */
.week-strip {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: 12px;
}
/* Floating delete button that sits on top of a card-shaped link. The wrap
   is the grid child so the card keeps its slot; the button is positioned
   absolutely so clicks on it don't bubble to the underlying <a>. */
.card-del-wrap {
  position: relative;
  display: flex;
}
.card-del-wrap > a,
.card-del-wrap > .theme-card,
.card-del-wrap > .week-item {
  flex: 1;
  min-width: 0;
}
.card-del-form {
  position: absolute;
  top: 6px;
  right: 6px;
  margin: 0;
  z-index: 2;
}
.card-del-btn {
  width: 28px;
  height: 28px;
  padding: 0;
  border: 1px solid var(--c-border);
  background: var(--c-surface);
  color: var(--c-text-3);
  border-radius: 50%;
  font-size: 13px;
  line-height: 1;
  cursor: pointer;
  opacity: 0;
  transition: opacity var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.card-del-wrap:hover .card-del-btn,
.card-del-btn:focus-visible {
  opacity: 1;
}
.card-del-btn:hover {
  background: #fee2e2;
  border-color: #fca5a5;
  color: #b91c1c;
}
/* On touch devices hover doesn't exist — keep the button visible. */
@media (hover: none) {
  .card-del-btn { opacity: 1; }
}
.week-item {
  display: flex;
  flex-direction: column;
  gap: 4px;
  padding: 16px 18px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-left: 4px solid var(--c-primary);
  border-radius: var(--r-sm);
  text-decoration: none;
  color: var(--c-text);
  transition: all var(--dur-fast) var(--ease);
}
.week-item:hover {
  transform: translateX(3px);
  box-shadow: 0 6px 14px -6px rgba(249, 115, 22, 0.25);
  border-color: var(--c-primary);
  text-decoration: none;
}
.week-item-day {
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: var(--c-primary);
}
.week-item-title {
  font-size: 15px;
  font-weight: 700;
  color: var(--c-text);
}
.week-item-meta {
  font-size: 12px;
  line-height: 1.4;
}

/* Phone tweaks for the home + kid room */
@media (max-width: 720px) {
  .home-hero h1 { font-size: 30px; }
  .home-kids { grid-template-columns: 1fr; }
  .home-kid-card { padding: 18px 20px; min-height: 92px; }
  .home-kid-emoji { font-size: 44px; }
  .home-kid-name { font-size: 19px; }
  .kid-hero { padding: 20px 22px; }
  .kid-hero-name { font-size: 28px; }
  .kid-hero-emoji { font-size: 48px; }
  .kid-hero-balance { width: 100%; text-align: left; }
}

/* ── Theme cards (one per subject) + the shelf grid ────────────────── */
/* Clean, iOS-style cards. Left-edge accent color per subject (deterministic
   by name). No book ornaments, no drop-shadow theatre. Just readable tiles. */
.theme-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 14px;
}
.theme-card {
  position: relative;
  display: flex;
  align-items: center;
  gap: 16px;
  padding: 20px 22px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  text-decoration: none;
  color: var(--c-text);
  font-family: inherit;
  text-align: left;
  overflow: hidden;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
  cursor: pointer;
}
.theme-card:hover {
  transform: translateY(-2px);
  box-shadow: 0 12px 24px -10px rgba(0, 0, 0, 0.15);
  border-color: var(--accent, var(--c-primary));
  text-decoration: none;
  color: var(--c-text);
}
.theme-card-accent {
  position: absolute;
  left: 0; top: 0; bottom: 0;
  width: 6px;
  background: var(--accent, var(--c-primary));
}
.theme-card-emoji {
  font-size: 36px;
  line-height: 1;
  flex-shrink: 0;
}
.theme-card-body {
  flex: 1;
  min-width: 0;
  display: flex;
  flex-direction: column;
  gap: 3px;
}
.theme-card-title {
  font-size: 17px;
  font-weight: 800;
  color: var(--c-text);
  letter-spacing: -0.01em;
}
.theme-card-meta {
  font-size: 12px;
  color: var(--c-text-3);
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.05em;
}
.theme-card-arrow {
  font-size: 20px;
  color: var(--c-text-3);
  flex-shrink: 0;
  transition: transform var(--dur-fast) var(--ease), color var(--dur-fast) var(--ease);
}
.theme-card:hover .theme-card-arrow {
  color: var(--accent, var(--c-primary));
  transform: translateX(3px);
}
.theme-card-add {
  border: 1.5px dashed var(--c-border);
  background: transparent;
  color: var(--c-text-2);
}
.theme-card-add .theme-card-accent { display: none; }
.theme-card-add .theme-card-emoji  { color: var(--c-primary); }
.theme-card-add:hover {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  color: var(--c-text);
}

/* Subject hero (inside a theme) — simple, matches the card accent */
.subject-hero {
  display: flex;
  align-items: center;
  gap: 20px;
  padding: 24px 28px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-left: 8px solid var(--accent, var(--c-primary));
  border-radius: var(--r-md);
  margin-top: 12px;
  box-shadow: 0 4px 16px -8px rgba(0, 0, 0, 0.08);
}
.subject-hero-emoji {
  font-size: 56px;
  line-height: 1;
  flex-shrink: 0;
}
.subject-hero-body { flex: 1; min-width: 0; }
.subject-hero-title {
  margin: 0;
  font-size: 32px;
  font-weight: 900;
  letter-spacing: -0.03em;
  color: var(--c-text);
  line-height: 1.1;
}
.subject-hero-meta {
  margin: 4px 0 0;
  font-size: 14px;
  color: var(--c-text-2);
  font-weight: 600;
}

/* ── Wizard (test creation flow) ────────────────────────────────────── */
.wizard-progress {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 20px;
}
.wizard-dot {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 32px;
  height: 32px;
  border-radius: 50%;
  background: var(--c-surface);
  border: 2px solid var(--c-border);
  color: var(--c-text-3);
  font-weight: 800;
  font-size: 14px;
}
.wizard-dot-active {
  background: var(--c-primary);
  border-color: var(--c-primary);
  color: #fff;
}
.wizard-line {
  flex: 1;
  height: 2px;
  background: var(--c-border);
}

.wizard-step-title {
  margin: 0 0 4px;
  font-size: 18px;
  font-weight: 800;
  color: var(--c-text);
}

.wizard-topic-options {
  display: flex;
  flex-direction: column;
  gap: 6px;
  max-height: 200px;
  overflow-y: auto;
  padding: 4px;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  margin-top: 8px;
  background: #fafbfc;
}
/* Compact "Thema: Kapital" readout shown when the wizard was launched from
   "+ Neuer Test in <Thema>" — confirms the pick without forcing a re-choice. */
.wizard-topic-preset {
  display: flex;
  align-items: baseline;
  gap: 10px;
  padding: 10px 14px;
  margin-top: 8px;
  background: var(--c-primary-3);
  border: 1px solid var(--c-border);
  border-left: 3px solid var(--c-primary);
  border-radius: var(--r-sm);
}
.wizard-topic-preset-label {
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: var(--c-primary);
}
.wizard-topic-preset-name {
  font-size: 15px;
  font-weight: 700;
  color: var(--c-text);
}
.wizard-topic {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 12px;
  background: var(--c-surface);
  border-radius: var(--r-sm);
  cursor: pointer;
  transition: background var(--dur-fast) var(--ease);
}
.wizard-topic:hover { background: var(--c-primary-3); }
.wizard-topic input[type="radio"] {
  width: auto;
  margin: 0;
  accent-color: var(--c-primary);
}
.wizard-topic-new { font-weight: 700; color: var(--c-primary); }

/* Method tiles — big, icon-forward */
.wizard-methods {
  display: flex;
  flex-direction: column;
  gap: 10px;
  margin-top: 12px;
}
.wizard-method {
  display: flex;
  align-items: flex-start;
  gap: 16px;
  padding: 16px 18px;
  background: var(--c-surface);
  border: 2px solid var(--c-border);
  border-radius: var(--r-md);
  text-align: left;
  font-family: inherit;
  cursor: pointer;
  transition: all var(--dur-fast) var(--ease);
  width: 100%;
}
.wizard-method:hover:not([disabled]) {
  border-color: var(--c-primary-br);
  transform: translateY(-1px);
  box-shadow: 0 8px 18px -8px rgba(249, 115, 22, 0.2);
}
.wizard-method[disabled] {
  opacity: 0.5;
  cursor: not-allowed;
}
.wizard-method-active {
  border-color: var(--c-primary) !important;
  background: var(--c-primary-3);
  box-shadow: var(--sh-focus) !important;
}
.wizard-method-icon {
  font-size: 32px;
  line-height: 1;
  flex-shrink: 0;
}
.wizard-method div {
  display: flex;
  flex-direction: column;
  gap: 2px;
  flex: 1;
  min-width: 0;
}
.wizard-method strong {
  font-size: 15px;
  font-weight: 800;
  color: var(--c-text);
}

@media (max-width: 720px) {
  .theme-grid { grid-template-columns: 1fr; }
  .subject-hero { padding: 18px 20px; }
  .subject-hero-emoji { font-size: 44px; }
  .subject-hero-title { font-size: 24px; }
}

/* ── The Bookshelf ─────────────────────────────────────────────────── */
/* Visual metaphor: colorful hardcover books standing on a shelf. Each book
   uses CSS custom properties (--book-from, --book-to) set per-subject so
   the deterministic color scheme travels from shelf to interior. */

.shelf {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
  gap: 20px;
  padding: 24px;
  /* Warm wood-toned shelf backdrop — subtle, not literal */
  background:
    linear-gradient(180deg, rgba(255,247,237,0.5) 0%, rgba(254,215,170,0.3) 100%),
    var(--c-surface);
  border: 1px solid rgba(180, 83, 9, 0.15);
  border-radius: var(--r-lg);
  box-shadow:
    inset 0 -8px 16px -8px rgba(180, 83, 9, 0.2),   /* shelf shadow near bottom */
    0 2px 8px -4px rgba(0, 0, 0, 0.06);
  position: relative;
}
/* A thin wooden "shelf plank" line at the bottom */
.shelf::after {
  content: "";
  position: absolute;
  left: 24px; right: 24px;
  bottom: 18px;
  height: 4px;
  background: linear-gradient(180deg, rgba(180, 83, 9, 0.25), rgba(180, 83, 9, 0.05));
  border-radius: 2px;
  pointer-events: none;
}

.book {
  position: relative;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  aspect-ratio: 3 / 4;
  padding: 20px 16px 18px 22px;
  color: #fff;
  text-decoration: none;
  border-radius: 6px 4px 4px 6px;
  background: linear-gradient(135deg, var(--book-from, #dc2626) 0%, var(--book-to, #991b1b) 100%);
  box-shadow:
    0 12px 24px -10px rgba(0, 0, 0, 0.35),       /* ground shadow */
    inset -2px 0 0 rgba(0, 0, 0, 0.08),          /* right-edge darkening */
    inset 0 -3px 6px rgba(0, 0, 0, 0.18);         /* bottom darkening */
  transition: transform var(--dur-med) var(--ease),
              box-shadow var(--dur-med) var(--ease);
  font-family: inherit;
  border: none;
  cursor: pointer;
  text-align: left;
}
/* Fake "spine crease" — subtle vertical line near the left edge */
.book::before {
  content: "";
  position: absolute;
  left: 8px; top: 12px; bottom: 12px;
  width: 1px;
  background: rgba(255, 255, 255, 0.15);
  pointer-events: none;
}
.book-spine-shadow {
  position: absolute;
  left: 0; top: 0; bottom: 0;
  width: 10px;
  background: linear-gradient(90deg, rgba(0,0,0,0.2), rgba(0,0,0,0));
  border-radius: 6px 0 0 6px;
  pointer-events: none;
}
/* Pull the book off the shelf on hover */
.book:hover {
  transform: translateY(-8px) rotate(-1deg);
  box-shadow:
    0 24px 40px -12px rgba(0, 0, 0, 0.4),
    inset -2px 0 0 rgba(0, 0, 0, 0.08),
    inset 0 -3px 6px rgba(0, 0, 0, 0.18);
  text-decoration: none;
  color: #fff;
}
.book-emoji {
  font-size: 44px;
  line-height: 1;
  filter: drop-shadow(0 2px 4px rgba(0, 0, 0, 0.3));
}
.book-title {
  font-size: 18px;
  font-weight: 800;
  line-height: 1.2;
  letter-spacing: -0.01em;
  color: #fff;
  text-shadow: 0 1px 2px rgba(0, 0, 0, 0.3);
  margin-top: 12px;
  display: block;
}
.book-meta {
  display: block;
  margin-top: 4px;
  font-size: 11px;
  font-weight: 600;
  color: rgba(255, 255, 255, 0.85);
  text-transform: uppercase;
  letter-spacing: 0.06em;
}
/* A little ribbon bookmark peeking out the top */
.book-bookmark {
  position: absolute;
  top: -4px;
  right: 18px;
  width: 12px;
  height: 26px;
  background: rgba(255, 255, 255, 0.9);
  clip-path: polygon(0 0, 100% 0, 100% 100%, 50% 70%, 0 100%);
  pointer-events: none;
  opacity: 0.85;
}

/* The "+" ghost book at the end — dashed outline, no color fill */
.book-add {
  background: transparent;
  border: 2px dashed rgba(180, 83, 9, 0.3);
  color: var(--c-text-2);
  box-shadow: none;
}
.book-add::before,
.book-add .book-spine-shadow { display: none; }
.book-add .book-emoji { filter: none; color: var(--c-primary); }
.book-add .book-title { color: var(--c-text); text-shadow: none; }
.book-add .book-meta  { color: var(--c-text-3); }
.book-add:hover {
  border-color: var(--c-primary);
  background: rgba(249, 115, 22, 0.08);
  transform: translateY(-4px);
  box-shadow: none;
  color: var(--c-text);
}

/* ── Inside the book (subject room) ────────────────────────────────── */
.book-interior {
  padding: 32px 36px;
  border-radius: var(--r-lg);
  background:
    linear-gradient(135deg, var(--book-from) 0%, var(--book-to) 100%);
  box-shadow: 0 20px 48px -20px rgba(0, 0, 0, 0.35);
  color: #fff;
  position: relative;
  overflow: hidden;
}
/* Subtle paper-ish highlight on the right to suggest an open page */
.book-interior::after {
  content: "";
  position: absolute;
  right: 0; top: 0; bottom: 0;
  width: 40%;
  background: linear-gradient(270deg, rgba(255,255,255,0.08), rgba(255,255,255,0));
  pointer-events: none;
}
.book-interior-cover {
  position: relative;
  z-index: 1;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 10px;
}
.book-interior-emoji {
  font-size: 56px;
  line-height: 1;
  filter: drop-shadow(0 2px 6px rgba(0, 0, 0, 0.3));
}
.book-interior-title {
  margin: 0;
  font-size: 40px;
  font-weight: 900;
  letter-spacing: -0.03em;
  color: #fff;
  line-height: 1;
  text-shadow: 0 2px 4px rgba(0, 0, 0, 0.3);
}
.book-interior-meta {
  margin: 0;
  font-size: 14px;
  color: rgba(255, 255, 255, 0.9);
  font-weight: 600;
  letter-spacing: 0.02em;
}

/* Chapters (topics) as numbered sections */
.chapters {
  display: flex;
  flex-direction: column;
  gap: 18px;
  margin-top: 4px;
}
.chapter {
  background: #fffdf7;                                  /* paper off-white */
  border: 1px solid rgba(180, 83, 9, 0.15);
  border-radius: var(--r-md);
  padding: 18px 22px;
  box-shadow: 0 2px 6px -3px rgba(0, 0, 0, 0.06);
}
.chapter-head {
  display: flex;
  align-items: center;
  gap: 14px;
  margin-bottom: 10px;
}
.chapter-num {
  font-size: 28px;
  font-weight: 900;
  color: var(--c-primary);
  font-feature-settings: "tnum";
  letter-spacing: -0.02em;
  flex-shrink: 0;
  min-width: 48px;
}
.chapter-title-wrap {
  flex: 1;
  min-width: 0;
}
.chapter-title {
  margin: 0;
  font-size: 18px;
  font-weight: 800;
  color: var(--c-text);
  letter-spacing: -0.01em;
}
.chapter-meta {
  display: block;
  margin-top: 2px;
}
.chapter-empty {
  margin: 0;
  padding: 10px 0 2px 62px;                             /* indent under num */
}
/* Trash button on each chapter header — sits flush right, fades in on hover
   of the whole chapter card so it isn't visually loud when idle. */
.chapter-del-form {
  margin: 0 0 0 auto;                                   /* push to right edge */
}
.chapter-del-form .card-del-btn {
  opacity: 0;
}
.chapter:hover .chapter-del-form .card-del-btn,
.chapter-del-form .card-del-btn:focus-visible {
  opacity: 1;
}
@media (hover: none) {
  .chapter-del-form .card-del-btn { opacity: 1; }
}
/* Test-row trash: reserve space so the floating button doesn't overlap
   the "X Fragen" meta text when it fades in. */
.pages .card-del-wrap > .page-item {
  padding-right: 42px;
}
/* "+ Neuer Test in <Thema>" — ghost button under each chapter's test list,
   so the parent can add a test to that topic without re-picking it in the
   wizard. Styled as a dashed ghost so it reads as an action, not a test. */
.chapter-add-test {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin: 10px 0 0 62px;                                /* align under title */
  padding: 8px 14px;
  background: transparent;
  border: 1.5px dashed var(--c-border);
  border-radius: var(--r-sm);
  font-size: 13px;
  font-weight: 600;
  color: var(--c-text-2);
  cursor: pointer;
  transition: all var(--dur-fast) var(--ease);
}
.chapter-add-test:hover {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  color: var(--c-primary);
}
.chapter-add-test-icon {
  font-size: 16px;
  font-weight: 700;
  color: var(--c-primary);
  line-height: 1;
}
@media (max-width: 720px) {
  .chapter-add-test { margin-left: 48px; }
}

/* Pages (tests) inside a chapter */
.pages {
  list-style: none;
  padding: 0;
  margin: 6px 0 0;
  display: flex;
  flex-direction: column;
  gap: 4px;
  border-top: 1px dashed rgba(180, 83, 9, 0.2);
  padding-top: 10px;
}
.pages li { margin: 0; }
.page-item {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 10px 14px;
  border-radius: var(--r-sm);
  text-decoration: none;
  color: var(--c-text);
  transition: all var(--dur-fast) var(--ease);
}
.page-item:hover {
  background: rgba(249, 115, 22, 0.08);
  transform: translateX(4px);
  text-decoration: none;
}
.page-num {
  color: var(--c-primary);
  font-weight: 800;
  font-size: 18px;
  flex-shrink: 0;
}
.page-title {
  flex: 1;
  min-width: 0;
  font-weight: 600;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.page-meta { flex-shrink: 0; }
/* Inline per-test stats pill in the subject_room list — so the parent
   sees attempt count + best score at a glance without drilling into
   each test. Color-coded by pass status. */
.page-stat {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 3px 10px;
  border-radius: 999px;
  font-size: 12px;
  font-weight: 700;
  flex-shrink: 0;
  font-feature-settings: "tnum";
}
.page-stat-pass {
  background: #ecfdf5;
  color: #047857;
  border: 1px solid #a7f3d0;
}
.page-stat-warn {
  background: #fef3c7;
  color: #92400e;
  border: 1px solid #fcd34d;
}
.page-stat-idle {
  background: var(--c-surface-2);
  color: var(--c-text-3);
  border: 1px solid var(--c-border);
  font-weight: 600;
}

@media (max-width: 720px) {
  .shelf { grid-template-columns: repeat(auto-fill, minmax(140px, 1fr)); padding: 16px; gap: 14px; }
  .book { padding: 14px 12px 12px 16px; }
  .book-emoji { font-size: 32px; }
  .book-title { font-size: 14px; margin-top: 8px; }
  .book-interior { padding: 24px 22px; }
  .book-interior-emoji { font-size: 40px; }
  .book-interior-title { font-size: 28px; }
  .chapter { padding: 14px 16px; }
  .chapter-num { font-size: 22px; min-width: 36px; }
}

/* ── Calendar (parent month view) ─────────────────────────────────── */
.cal-nav {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  margin-bottom: 4px;
}
.cal-weekhead {
  display: grid;
  grid-template-columns: repeat(7, 1fr);
  gap: 6px;
  margin: 14px 0 6px;
}
.cal-weekhead > div {
  font-size: 11px;
  font-weight: 700;
  color: var(--c-text-3);
  text-transform: uppercase;
  letter-spacing: 0.08em;
  text-align: center;
  padding: 4px 0;
}
.cal-grid {
  display: grid;
  grid-template-columns: repeat(7, 1fr);
  grid-auto-rows: minmax(116px, 1fr);
  gap: 6px;
  margin-bottom: 16px;
}
.cal-cell {
  position: relative;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-sm);
  padding: 6px 8px 8px;
  display: flex;
  flex-direction: column;
  gap: 4px;
  overflow: hidden;
  transition: border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.cal-cell-out {
  background: #fafbfc;
  opacity: 0.65;
}
.cal-cell-weekend { background: #fefcf8; }
.cal-cell-today {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: 0 0 0 2px rgba(249, 115, 22, 0.15);
}
.cal-cell-drop {
  border-color: var(--c-primary);
  background: #fff7ed;
  box-shadow: 0 0 0 3px rgba(249, 115, 22, 0.25);
}
.cal-daynum {
  font-size: 12px;
  font-weight: 700;
  color: var(--c-text-2);
  font-feature-settings: "tnum";
}
.cal-cell-today .cal-daynum { color: var(--c-primary); }

.cal-pill {
  display: flex;
  align-items: center;
  gap: 5px;
  padding: 3px 7px;
  background: linear-gradient(135deg, #fff7ed 0%, #ffedd5 100%);
  border: 1px solid rgba(249, 115, 22, 0.35);
  border-radius: var(--r-full);
  font-size: 11px;
  line-height: 1.3;
  cursor: grab;
  user-select: none;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.cal-pill:hover {
  box-shadow: 0 2px 8px -2px rgba(249, 115, 22, 0.4);
  transform: translateY(-1px);
}
.cal-pill:active { cursor: grabbing; }
.cal-pill-dragging { opacity: 0.4; }
.cal-pill-time {
  font-weight: 800;
  color: var(--c-primary);
  font-feature-settings: "tnum";
}
.cal-pill-title {
  font-weight: 600;
  color: var(--c-text);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  min-width: 0;
}

.cal-dots {
  margin-top: auto;
  display: flex;
  align-items: center;
  gap: 3px;
  flex-wrap: wrap;
}
.cal-dot {
  display: inline-block;
  width: 8px;
  height: 8px;
  border-radius: 50%;
  flex-shrink: 0;
}
.cal-dot-ok  { background: #22c55e; }
.cal-dot-bad { background: #f59e0b; }
.cal-dot-more {
  font-size: 10px;
  font-weight: 700;
  color: var(--c-text-3);
  margin-left: 2px;
}

.cal-legend {
  display: flex;
  gap: 18px;
  flex-wrap: wrap;
  padding: 12px 0;
}
.cal-legend > span {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
.cal-swatch {
  display: inline-block;
  width: 14px;
  height: 14px;
  border-radius: var(--r-sm);
}
.cal-swatch-pill {
  background: linear-gradient(135deg, #fff7ed 0%, #ffedd5 100%);
  border: 1px solid rgba(249, 115, 22, 0.35);
}
.cal-swatch-today {
  background: var(--c-primary-3);
  border: 1.5px solid var(--c-primary);
}

/* Tight mobile: shrink cells, hide weekend decoration */
@media (max-width: 720px) {
  .cal-grid { grid-auto-rows: minmax(84px, 1fr); gap: 4px; }
  .cal-cell { padding: 4px 5px 6px; }
  .cal-pill { font-size: 10px; padding: 2px 5px; }
  .cal-pill-title { max-width: 60px; }
}

/* ── Mobile-first result detail card (parent single-result view) ──── */
/* Designed to be tapped from a WhatsApp notification on a phone. Keeps a
   max-width of 28rem so it never feels awkward on a big phone, and uses
   large text + high-contrast tones because the parent is often glancing. */
.result-detail-card {
  max-width: 28rem;
  margin: 24px auto;
  padding: 28px 24px 24px;
  background: var(--c-surface);
  border-radius: var(--r-lg);
  box-shadow: 0 20px 50px -20px rgba(49, 46, 129, 0.2),
              0 8px 20px -8px rgba(249, 115, 22, 0.12);
  border: 1px solid var(--c-border);
}

.rd-head {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 20px;
}
.rd-emoji {
  font-size: 36px;
  line-height: 1;
  flex-shrink: 0;
}
.rd-ident {
  min-width: 0;
  flex: 1;
}
.rd-name {
  margin: 0;
  font-size: 18px;
  font-weight: 800;
  color: var(--c-text);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.rd-context {
  margin: 2px 0 0;
  font-size: 12px;
  color: var(--c-text-3);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.rd-pill {
  flex-shrink: 0;
  padding: 5px 12px;
  border-radius: var(--r-full);
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.05em;
  border: 2px solid;
}
.rd-pill-good { color: #15803d; border-color: #86efac; background: #dcfce7; }
.rd-pill-mid  { color: #b45309; border-color: #fcd34d; background: #fef3c7; }
.rd-pill-bad  { color: #b91c1c; border-color: #fca5a5; background: #fee2e2; }

.rd-score-block {
  text-align: center;
  margin-bottom: 24px;
}
.rd-celebration {
  font-size: 56px;
  line-height: 1;
  margin-bottom: 4px;
}
.rd-score {
  font-size: 72px;
  font-weight: 900;
  line-height: 1;
  letter-spacing: -0.04em;
  font-feature-settings: "tnum";
}
.rd-score-good { color: #16a34a; }
.rd-score-mid  { color: #d97706; }
.rd-score-bad  { color: #dc2626; }
.rd-percent {
  font-size: 32px;
  vertical-align: top;
  margin-left: 2px;
}
.rd-sub {
  margin: 8px 0 0;
  font-size: 14px;
  color: var(--c-text-2);
}

/* Progress bar with the pass-threshold marker */
.rd-bar-wrap {
  margin-bottom: 24px;
}
.rd-bar-labels {
  display: flex;
  justify-content: space-between;
  align-items: center;
  font-size: 11px;
  color: var(--c-text-3);
  margin-bottom: 6px;
}
.rd-bar-goal {
  font-weight: 700;
  color: var(--c-text-2);
}
.rd-bar {
  position: relative;
  height: 12px;
  background: #f1f5f9;
  border-radius: var(--r-full);
  overflow: hidden;
}
.rd-bar-fill {
  height: 100%;
  border-radius: var(--r-full);
  transition: width 700ms var(--ease);
}
.rd-bar-fill-good { background: linear-gradient(90deg, #22c55e 0%, #16a34a 100%); }
.rd-bar-fill-mid  { background: linear-gradient(90deg, #f59e0b 0%, #d97706 100%); }
.rd-bar-fill-bad  { background: linear-gradient(90deg, #ef4444 0%, #dc2626 100%); }
.rd-bar-marker {
  position: absolute;
  top: -2px;
  bottom: -2px;
  width: 3px;
  background: rgba(15, 23, 42, 0.55);
  border-radius: 2px;
  pointer-events: none;
}

.rd-footer {
  padding: 14px 16px;
  background: #f8fafc;
  border-radius: var(--r-md);
  margin-bottom: 20px;
}
.rd-test-title {
  font-weight: 700;
  font-size: 15px;
  color: var(--c-text);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.rd-time {
  margin-top: 2px;
  font-size: 12px;
  color: var(--c-text-3);
}

.rd-actions .btn { width: 100%; }

/* Phone-specific tweaks: slightly smaller type + tighter padding */
@media (max-width: 480px) {
  .result-detail-card {
    margin: 12px auto;
    padding: 22px 18px 18px;
    border-radius: var(--r-md);
  }
  .rd-score { font-size: 60px; }
  .rd-percent { font-size: 28px; }
  .rd-celebration { font-size: 48px; }
}

/* ── Release schedule (test editor Veroeffentlichung card) ────────── */
.release-status {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 20px;
  flex-wrap: wrap;
}
.release-pill {
  display: inline-block;
  padding: 6px 14px;
  border-radius: var(--r-full);
  font-size: 13px;
  font-weight: 700;
  letter-spacing: 0;
}
.release-pill-live {
  background: #dcfce7;
  color: #15803d;
  border: 1px solid #86efac;
}
.release-pill-scheduled {
  background: #fef3c7;
  color: #b45309;
  border: 1px solid #fcd34d;
}
.release-form .row {
  display: flex;
  gap: 10px;
  flex-wrap: wrap;
}

/* Inline schedule badge in the parent dashboard Faecher tree */
.schedule-badge {
  display: inline-block;
  margin-left: 8px;
  padding: 2px 10px;
  font-size: 11px;
  font-weight: 700;
  background: #fef3c7;
  color: #b45309;
  border: 1px solid #fcd34d;
  border-radius: var(--r-full);
  letter-spacing: 0;
  vertical-align: middle;
}

/* ── Flashcard reveal card (student take-test) ────────────────────── */
.flashcard {
  min-height: 120px;
  margin: 20px 0;
  padding: 24px 28px;
  background: linear-gradient(135deg, #fff7ed 0%, #fef3f9 100%);
  border: 2px dashed rgba(249, 115, 22, 0.4);
  border-radius: var(--r-lg);
  box-shadow: 0 4px 12px -4px rgba(249, 115, 22, 0.15);
  display: flex;
  align-items: center;
  justify-content: center;
  text-align: center;
}
.flashcard-back {
  width: 100%;
}
.flashcard-answer {
  font-size: 22px;
  font-weight: 700;
  color: var(--c-text);
  line-height: 1.35;
}

/* ── Student test cards ────────────────────────────────────────────── */
.test-card {
  display: flex;
  flex-direction: column;
  gap: 10px;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 24px;
  text-decoration: none;
  color: inherit;
  box-shadow: var(--sh-xs);
  transition: transform var(--dur-med) var(--ease),
              box-shadow var(--dur-med) var(--ease),
              border-color var(--dur-fast) var(--ease);
  position: relative;
  overflow: hidden;
  animation: fadeInUp var(--dur-slow) var(--ease) both;
}
.test-card::before {
  content: "";
  position: absolute;
  inset: 0 0 auto 0;
  height: 5px;
  background: var(--grad-warm);
  opacity: 0;
  transition: opacity var(--dur-med) var(--ease);
}
.test-card:hover {
  transform: translateY(-5px);
  box-shadow: var(--sh-lg);
  border-color: var(--c-primary-br);
  text-decoration: none;
  color: inherit;
}
.test-card:hover::before { opacity: 1; }
.test-card-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 6px;
}
.test-card strong { font-size: 16px; font-weight: 800; color: var(--c-text); letter-spacing: -0.01em; }
.test-card-footer {
  margin-top: 8px;
  padding-top: 14px;
  border-top: 1px dashed var(--c-border);
  display: flex;
  justify-content: space-between;
  font-size: 12px;
  color: var(--c-text-2);
}
.badge {
  display: inline-flex;
  align-items: center;
  font-size: 11px;
  font-weight: 700;
  color: var(--c-accent-2);
  background: var(--c-accent-3);
  border: 1px solid var(--c-accent-br);
  padding: 4px 11px;
  border-radius: var(--r-full);
  letter-spacing: 0.01em;
}
.badge-warm {
  color: var(--c-primary-2);
  background: var(--c-primary-3);
  border-color: var(--c-primary-br);
}

/* ── Test editor: header meta chips ─────────────────────────────────
   Small status pills shown under the test title so the parent sees at a
   glance: subject, topic, who it's for, reward, and release status. All
   info is read-only here — edits happen in the cards lower down. */
.test-head .test-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin-top: 14px;
}
.chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 12px;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: 0.01em;
  border-radius: 999px;
  background: var(--c-surface-2);
  color: var(--c-text-2);
  border: 1px solid var(--c-border);
  white-space: nowrap;
}
.chip-warm {
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  border-color: var(--c-primary-br);
}
.chip-soft {
  background: #fff7ed;
  color: #9a3412;
  border-color: #fed7aa;
}
.chip-money {
  background: #ecfdf5;
  color: #065f46;
  border-color: #a7f3d0;
}
.chip-live {
  background: #ecfdf5;
  color: #047857;
  border-color: #a7f3d0;
}
.chip-scheduled {
  background: #fef3c7;
  color: #92400e;
  border-color: #fcd34d;
}
.chip-bonus {
  background: #fdf4ff;
  color: #86198f;
  border-color: #f5d0fe;
}

/* ── Test editor Ergebnisse summary ───────────────────────────────
   Single-card summary that replaces the broken vertical stats list.
   A one-line sentence ("X von Y Kindern haben bestanden 🎉") up top,
   and a compact chip row below with the underlying counts so nothing
   is hidden. Tone-colored left border nudges the parent to "good /
   watch / waiting" without a heavy banner. */
.results-summary {
  padding: 18px 22px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-left: 4px solid var(--c-border);
  border-radius: var(--r-md);
  box-shadow: var(--sh-xs);
  margin-bottom: 20px;
}
.results-summary-pass { border-left-color: #16a34a; background: #f0fdf4; }
.results-summary-warn { border-left-color: #d97706; background: #fffbeb; }
.results-summary-idle { border-left-color: var(--c-border); background: var(--c-surface-2); }

.results-summary-head {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 12px;
}
.results-summary-icon {
  font-size: 22px;
  line-height: 1;
}
.results-summary-headline {
  font-size: 17px;
  font-weight: 800;
  letter-spacing: -0.01em;
  color: var(--c-text);
}
.results-summary-chips {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}
.results-chip {
  display: inline-flex;
  align-items: center;
  padding: 5px 12px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: 999px;
  font-size: 12px;
  font-weight: 600;
  color: var(--c-text-2);
}
.results-chip strong {
  color: var(--c-text);
  font-weight: 800;
  margin-right: 4px;
  font-feature-settings: "tnum";
}
.results-chip-pass {
  background: #ecfdf5;
  color: #047857;
  border-color: #a7f3d0;
}
.results-chip-pass strong { color: #065f46; }
.results-chip-open {
  background: #fffbeb;
  color: #92400e;
  border-color: #fde68a;
}
.results-chip-open strong { color: #78350f; }

/* ── Theme card actions (edit-icon + delete) ────────────────────────
   Stacks both action buttons in the top-right of a subject card; both
   fade in together on hover. Mirrors the existing card-del-form
   behavior but fits two buttons side by side. */
.theme-card-actions {
  position: absolute;
  top: 6px;
  right: 6px;
  display: flex;
  gap: 4px;
  z-index: 2;
}
.theme-card-actions .card-del-btn {
  opacity: 0;
}
.card-del-wrap:hover .theme-card-actions .card-del-btn,
.theme-card-actions .card-del-btn:focus-visible {
  opacity: 1;
}
@media (hover: none) {
  .theme-card-actions .card-del-btn { opacity: 1; }
}

/* ── Emoji picker grid (subject icon chooser) ───────────────────────
   Used in both the "Neues Fach" and "Icon aendern" dialogs. 8-column
   grid on desktop, collapses on narrow screens. Active pick gets a
   warm ring so the parent can see their choice. */
.emoji-grid {
  display: grid;
  grid-template-columns: repeat(8, 1fr);
  gap: 6px;
  padding: 8px;
  background: #fafbfc;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  margin-top: 8px;
}
@media (max-width: 560px) {
  .emoji-grid { grid-template-columns: repeat(6, 1fr); }
}
.emoji-pick {
  height: 40px;
  padding: 0;
  font-size: 22px;
  line-height: 1;
  background: var(--c-surface);
  border: 1.5px solid transparent;
  border-radius: var(--r-sm);
  cursor: pointer;
  transition: transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.emoji-pick:hover {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  transform: translateY(-1px);
}
.emoji-pick-active {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: 0 0 0 3px rgba(249, 115, 22, 0.18);
}

/* ── Attempts table (test editor Ergebnisse) ────────────────────────
   Outer table is the per-kid summary. Clicking the ▸ toggle reveals
   an inner "attempts-sub" table with every attempt in order, plus a
   Trend column that shows the delta vs the previous attempt. */
.attempts-toggle-cell {
  width: 32px;
  padding-left: 14px !important;
  padding-right: 0 !important;
}
.attempts-toggle {
  width: 26px;
  height: 26px;
  padding: 0;
  border: 1px solid var(--c-border);
  border-radius: 6px;
  background: var(--c-surface);
  color: var(--c-text-2);
  font-size: 12px;
  font-weight: 800;
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  transition: background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.attempts-toggle:hover {
  background: var(--c-primary-3);
  border-color: var(--c-primary);
  color: var(--c-primary);
}
.attempts-toggle[aria-expanded="true"] {
  background: var(--c-primary-3);
  border-color: var(--c-primary);
  color: var(--c-primary);
}
.attempts-row-detail > td {
  background: #fafbfc;
  border-top: 1px solid var(--c-border);
}
.attempts-sub {
  width: 100%;
  border-collapse: collapse;
}
.attempts-sub thead th {
  padding: 10px 16px;
  text-align: left;
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  color: var(--c-text-3);
  background: #f3f4f6;
  border-bottom: 1px solid var(--c-border);
}
.attempts-sub tbody td {
  padding: 10px 16px;
  font-size: 13px;
  border-bottom: 1px solid rgba(229, 231, 235, 0.7);
}
.attempts-sub tbody tr:last-child td { border-bottom: 0; }
.attempts-sub tbody tr:hover td { background: rgba(249, 115, 22, 0.04); }

/* ── Support thanks page ─────────────────────────────────────────────
   Calm celebratory layout: a big emerald circle badge, the amount in a
   separate readout card, and the three "perks" as a vertical list so
   the page reads like a thank-you note, not a receipt. */
.thanks-hero {
  max-width: 640px;
  margin: 40px auto;
  padding: 48px 40px;
  text-align: center;
  background: linear-gradient(135deg, #f0fdf4 0%, #ecfdf5 60%, #fff7ed 100%);
  border: 1px solid #bbf7d0;
  border-radius: var(--r-xl);
  box-shadow: 0 20px 40px -20px rgba(22, 163, 74, 0.25);
}
.thanks-badge {
  width: 96px;
  height: 96px;
  margin: 0 auto 20px;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 48px;
  background: #fff;
  border-radius: 50%;
  border: 3px solid #a7f3d0;
  box-shadow: 0 10px 30px -10px rgba(22, 163, 74, 0.35);
  animation: thanks-pop 0.5s var(--ease-bounce, ease) both;
}
@keyframes thanks-pop {
  0%   { transform: scale(0.6); opacity: 0; }
  70%  { transform: scale(1.08); opacity: 1; }
  100% { transform: scale(1); }
}
.thanks-hero h1 {
  font-size: 32px;
  margin: 0 0 10px;
  letter-spacing: -0.01em;
}
.thanks-lead {
  font-size: 16px;
  color: var(--c-text-2);
  margin: 0 auto 28px;
  line-height: 1.5;
  max-width: 500px;
}
.thanks-amount-card {
  display: inline-flex;
  flex-direction: column;
  align-items: center;
  padding: 18px 36px;
  background: #fff;
  border: 1px solid #a7f3d0;
  border-radius: var(--r-md);
  margin-bottom: 28px;
  box-shadow: 0 6px 14px -8px rgba(22, 163, 74, 0.3);
}
.thanks-amount-label {
  font-size: 11px;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: #047857;
  margin-bottom: 4px;
}
.thanks-amount-num {
  font-size: 36px;
  font-weight: 900;
  color: #16a34a;
  line-height: 1;
  letter-spacing: -0.01em;
  font-feature-settings: "tnum";
}
.thanks-amount-unit {
  font-size: 16px;
  font-weight: 700;
  color: #059669;
  margin-left: 3px;
}
.thanks-amount-sub { margin-top: 6px; }

.thanks-gifts {
  list-style: none;
  padding: 0;
  margin: 0 auto 28px;
  max-width: 480px;
  text-align: left;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.thanks-gifts li {
  display: flex;
  align-items: flex-start;
  gap: 14px;
  padding: 14px 16px;
  background: rgba(255, 255, 255, 0.75);
  border: 1px solid rgba(167, 243, 208, 0.6);
  border-radius: var(--r-sm);
}
.thanks-gift-icon {
  font-size: 22px;
  line-height: 1;
  flex-shrink: 0;
}
.thanks-gifts li > div {
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.thanks-gifts li strong {
  font-size: 14px;
  color: var(--c-text);
}
.thanks-actions {
  display: flex;
  gap: 10px;
  justify-content: center;
  flex-wrap: wrap;
}
@media (max-width: 560px) {
  .thanks-hero { padding: 32px 20px; margin: 20px 10px; }
  .thanks-hero h1 { font-size: 26px; }
  .thanks-badge { width: 80px; height: 80px; font-size: 40px; }
}
/* Clickable jump-to-results chip — scrolls to #ergebnisse so the parent can
   go from the header straight to the table without hunting. */
.chip-stats {
  background: #eef2ff;
  color: #3730a3;
  border-color: #c7d2fe;
  cursor: pointer;
  transition: background var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
}
.chip-stats:hover {
  background: #e0e7ff;
  color: #312e81;
  text-decoration: none;
  transform: translateY(-1px);
}

/* ── Test editor: "Fragen" live panel on the right of the add form ─
   Sits next to the add-question form so the parent sees their question
   land immediately without scrolling. Scrolls independently inside its
   own box when the list grows longer than the form. */
.questions-panel {
  display: flex;
  flex-direction: column;
  min-height: 0;                                         /* allow inner scroll */
  max-height: 720px;
}
.questions-panel-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 14px;
}
.questions-panel-head h3 {
  margin: 0;
}
.questions-panel .q-list {
  overflow-y: auto;
  margin: 0 -8px;                                        /* bleed under padding for a cleaner scroll edge */
  padding: 0 8px;
}
/* Tighter question cards when they live inside the side panel — the
   default .q-item padding is tuned for full-width rows. */
.q-list-compact .q-item {
  padding: 18px 20px 16px 58px;
  margin-bottom: 10px;
}
.q-list-compact .q-item::before {
  top: 18px;
  left: 18px;
  width: 28px;
  height: 28px;
  font-size: 12px;
}
.q-list-compact .q-type-badge {
  margin-bottom: 4px;
}
.q-list-compact .q-prompt {
  font-size: 14px;
  margin-bottom: 10px;
}
.q-list-compact .q-options li {
  padding: 7px 11px;
  font-size: 12px;
}
.questions-empty {
  text-align: center;
  padding: 32px 16px;
  color: var(--c-text-3);
}
.questions-empty .empty-icon {
  font-size: 42px;
  margin-bottom: 6px;
}
.questions-empty h4 {
  margin: 6px 0 4px;
  color: var(--c-text);
}
.questions-empty p {
  margin: 0;
}

/* Main work grid (form + list). Stretch to match — both panels end at the
   same Y, same top edge. The right-hand list scrolls internally when it
   would overflow the left form's height, so the overall height is driven
   by the TALLEST panel without either one looking truncated. */
.test-main {
  align-items: stretch;
}
.test-main > .card { display: flex; flex-direction: column; }
/* Drop the .questions-panel max-height so it can stretch with the form;
   the inner q-list still scrolls on overflow (overflow-y:auto below). */
.test-main .questions-panel { max-height: none; }

/* Reading/Lesetext panel: let the passage textarea grow to fill the left
   card so its height matches the right panel's passage preview. Without
   this, the card sits tall but the textarea keeps its rows=8 default and
   leaves a big empty area at the bottom.
   `:not([hidden])` — our `display: flex` specificity beats the UA
   `[hidden] { display: none }` rule, so we must explicitly skip flex
   styling when the panel is hidden (non-Lesetext types). */
.test-main #r-panel:not([hidden]) { flex: 1; display: flex; flex-direction: column; min-height: 0; }
.test-main #r-panel:not([hidden]) > form[action$="/reading-passage"] {
  display: flex; flex-direction: column; flex: 1; min-height: 0;
}
.test-main #r-panel:not([hidden]) > form[action$="/reading-passage"] > .field {
  display: flex; flex-direction: column; flex: 1; min-height: 0;
}
.test-main #r-panel:not([hidden]) textarea[name="reading_passage"] {
  flex: 1; min-height: 220px;
}
/* On narrow screens the two-col stacks — drop the max-height so the page
   scrolls naturally instead of trapping scroll inside the list box. */
@media (max-width: 860px) {
  .questions-panel { max-height: none; }
  .questions-panel .q-list { overflow-y: visible; }
}

/* ── Test editor: Belohnung readout ─────────────────────────────────
   Compact "big number" at the top of the Belohnung card so the parent
   knows the effective reward without reading the whole form. */
.reward-readout {
  padding: 12px 16px;
  background: #ecfdf5;
  border: 1px solid #a7f3d0;
  border-radius: var(--r-sm);
  margin-bottom: 16px;
}
.reward-readout-main {
  display: flex;
  align-items: baseline;
  gap: 6px;
}
.reward-value {
  font-size: 28px;
  font-weight: 900;
  color: #047857;
  line-height: 1;
  letter-spacing: -0.01em;
}
.reward-unit {
  font-size: 14px;
  font-weight: 700;
  color: #059669;
}
.reward-readout-sub {
  margin-top: 6px;
}

/* Slight breathing room above the Einstellungen section. */
.test-settings {
  margin-top: 36px;
}

/* Collapsible Einstellungen — native <details> with a + / − chevron.
   Summary is the clickable header; we drop the default disclosure
   triangle so the custom chevron is the only cue. */
.test-settings-toggle > summary { list-style: none; cursor: pointer; }
.test-settings-toggle > summary::-webkit-details-marker { display: none; }
.test-settings-toggle > summary::marker { content: ""; }

.test-settings-summary {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  padding: 10px 0;
  transition: color var(--dur-fast) var(--ease);
}
.test-settings-summary h2 { margin: 0; }
.test-settings-summary:hover { color: var(--c-primary); }

.test-settings-chevron {
  width: 32px;
  height: 32px;
  border: 1px solid var(--c-border);
  border-radius: 50%;
  background: var(--c-surface);
  transition: background var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
  position: relative;
  flex-shrink: 0;
}
/* Single source of truth for the glyph — "+" when closed, "−" when open.
   Absolute-centered in the circle so both glyphs sit perfectly
   centered regardless of their rendered width. */
.test-settings-chevron::before {
  content: "+";
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 22px;
  font-weight: 800;
  line-height: 1;
  color: var(--c-primary);
  /* Pull the glyph up by 1px so the "+" crossbar sits on the optical
     center of the circle rather than the geometric one. */
  transform: translateY(-1px);
}
.test-settings-toggle[open] .test-settings-chevron::before {
  content: "−";
  font-size: 26px;
  /* The minus sign has no descender, so it's already optically
     centered — no translate needed. */
  transform: translateY(-2px);
}
.test-settings-summary:hover .test-settings-chevron {
  background: var(--c-primary-3);
  border-color: var(--c-primary);
}
/* Breathing room between summary and the revealed content. */
.test-settings-toggle[open] > .two-col {
  margin-top: 8px;
}

/* ── Pearl / stardust button ──────────────────────────────────────────
   Ported from the stardust-button React component and retuned to the
   brand's warm-orange palette. Idle shows a ✧ star; hover swaps to ✦,
   the glossy top rises and the bottom dims. Active sinks 4px to feel
   physically pressed. Use as a hero CTA — it's deliberately large. */
.btn-pearl {
  --pearl-bg:     #3b1507;                                /* espresso / dark roast */
  --pearl-bg-2:   #7c2d12;                                /* caramel mid */
  --pearl-accent: #fb923c;                                /* brand amber-500 */
  --pearl-glow:   #fed7aa;                                /* highlight cream */

  position: relative;
  display: inline-block;
  outline: none;
  cursor: pointer;
  border: 0;
  border-radius: 100px;
  background: radial-gradient(110% 120% at 50% 0%, var(--pearl-bg-2) 0%, var(--pearl-bg) 70%);
  transition: transform 0.2s ease, box-shadow 0.3s ease;
  box-shadow:
    inset 0 0.3rem 0.9rem rgba(255, 255, 255, 0.28),
    inset 0 -0.1rem 0.3rem rgba(0, 0, 0, 0.7),
    inset 0 -0.4rem 0.9rem rgba(255, 255, 255, 0.35),
    0 2.2rem 2.6rem -0.4rem rgba(60, 20, 5, 0.35),
    0 0.9rem 0.9rem -0.6rem rgba(0, 0, 0, 0.55);
}
.btn-pearl-wrap {
  display: block;
  padding: 26px 42px;
  border-radius: inherit;
  position: relative;
  overflow: hidden;
  font-size: 22px;
  font-weight: 600;
  color: rgba(253, 186, 116, 0.95);
  letter-spacing: 0.01em;
}
/* Top gloss bubble — the "glass marble" effect. */
.btn-pearl-wrap::before {
  content: "";
  position: absolute;
  left: -15%; right: -15%;
  bottom: 25%; top: -100%;
  border-radius: 50%;
  background: radial-gradient(circle at 50% 100%, rgba(251, 146, 60, 0.28) 0%, rgba(251, 146, 60, 0) 60%);
  transition: transform 0.3s ease;
  pointer-events: none;
}
/* Inner-top highlight to mimic a light ring on the top curve. */
.btn-pearl-wrap::after {
  content: "";
  position: absolute;
  left: 6%; right: 6%;
  top: 12%; bottom: 40%;
  border-radius: 22px 22px 0 0;
  box-shadow: inset 0 10px 8px -10px rgba(253, 186, 116, 0.75);
  background: linear-gradient(
    180deg,
    rgba(251, 146, 60, 0.28) 0%,
    rgba(0, 0, 0, 0) 55%,
    rgba(0, 0, 0, 0) 100%
  );
  transition: opacity 0.3s ease, transform 0.3s ease;
  pointer-events: none;
}
.btn-pearl-inner {
  position: relative;
  z-index: 1;
  display: inline-flex;
  align-items: center;
  gap: 12px;
  transform: translateY(2%);
  transition: transform 0.3s ease;
  -webkit-mask-image: linear-gradient(to bottom, rgba(253, 186, 116, 1) 45%, transparent);
          mask-image: linear-gradient(to bottom, rgba(253, 186, 116, 1) 45%, transparent);
}
.btn-pearl-star {
  display: inline-flex;
  font-size: 22px;
  line-height: 1;
}
.btn-pearl-star-hover { display: none; }
.btn-pearl:hover .btn-pearl-star-idle  { display: none; }
.btn-pearl:hover .btn-pearl-star-hover { display: inline-flex; }

.btn-pearl:hover {
  box-shadow:
    inset 0 0.3rem 0.5rem rgba(253, 186, 116, 0.42),
    inset 0 -0.1rem 0.3rem rgba(0, 0, 0, 0.7),
    inset 0 -0.4rem 0.9rem rgba(251, 146, 60, 0.62),
    0 2.6rem 3rem -0.4rem rgba(60, 20, 5, 0.45),
    0 0.9rem 0.9rem -0.6rem rgba(0, 0, 0, 0.6);
}
.btn-pearl:hover .btn-pearl-wrap::before { transform: translateY(-5%); }
.btn-pearl:hover .btn-pearl-wrap::after  { opacity: 0.45; transform: translateY(5%); }
.btn-pearl:hover .btn-pearl-inner        { transform: translateY(-4%); }

.btn-pearl:active {
  transform: translateY(4px);
  box-shadow:
    inset 0 0.3rem 0.5rem rgba(253, 186, 116, 0.55),
    inset 0 -0.1rem 0.3rem rgba(0, 0, 0, 0.8),
    inset 0 -0.4rem 0.9rem rgba(251, 146, 60, 0.42),
    0 2.2rem 2.6rem -0.4rem rgba(60, 20, 5, 0.35),
    0 0.9rem 0.9rem -0.6rem rgba(0, 0, 0, 0.65);
}

/* Respect reduced-motion: drop the hover transforms. */
@media (prefers-reduced-motion: reduce) {
  .btn-pearl,
  .btn-pearl-wrap::before,
  .btn-pearl-wrap::after,
  .btn-pearl-inner {
    transition: none;
  }
  .btn-pearl:hover .btn-pearl-wrap::before,
  .btn-pearl:hover .btn-pearl-wrap::after,
  .btn-pearl:hover .btn-pearl-inner {
    transform: none;
  }
}

/* ── "Get started" style support button (topbar coffee chip) ──────────
   Filled primary pill with a smaller accent square on the right that
   houses a chevron. On hover, the square expands across the button and
   the label fades — a satisfying reveal that reads as "this is an
   action". Ported from the get-started-button component. */
.gs-btn {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: flex-start;
  height: 40px;
  padding: 0 22px;
  min-width: 200px;
  margin-right: 10px;
  border-radius: 10px;
  background: var(--c-primary);
  color: #fff;
  font-size: 13px;
  font-weight: 700;
  letter-spacing: 0.01em;
  text-decoration: none;
  overflow: hidden;
  isolation: isolate;
  box-shadow: 0 2px 6px -1px rgba(249, 115, 22, 0.35);
  transition: background var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
}
.gs-btn:hover {
  background: var(--c-primary-2, #ea580c);
  text-decoration: none;
  color: #fff;
  box-shadow: 0 4px 10px -2px rgba(249, 115, 22, 0.45);
}

/* Label sits left; a fixed right-margin reserves space for the accent
   square at its idle width so nothing jumps when the icon expands. */
.gs-btn-label {
  display: inline-block;
  padding: 0 3rem 0 2px;                                /* reserves room for the icon square on the right */
  line-height: 1;
  transition: opacity 0.5s ease;
  white-space: nowrap;
}
.gs-btn:hover .gs-btn-label { opacity: 0; }

/* Accent square on the right — absolutely positioned so it can grow to
   consume the whole pill on hover without reflowing the label. */
.gs-btn-icon {
  position: absolute;
  right: 4px;
  top: 4px;
  bottom: 4px;
  z-index: 10;
  display: grid;
  place-items: center;
  width: 28%;
  border-radius: 6px;
  background: rgba(255, 255, 255, 0.18);
  color: #fff;
  transition: width 0.5s ease, transform 0.15s ease, background 0.3s ease;
}
.gs-btn:hover .gs-btn-icon {
  width: calc(100% - 8px);
  background: rgba(255, 255, 255, 0.22);
}
.gs-btn:active .gs-btn-icon { transform: scale(0.95); }
.gs-btn-icon svg {
  display: block;
  transition: transform 0.3s ease;
}
.gs-btn:hover .gs-btn-icon svg {
  transform: translateX(2px);
}

/* Mobile — shrink padding, keep the reveal effect readable. */
@media (max-width: 560px) {
  .gs-btn { padding: 0 12px; font-size: 12px; }
  .gs-btn-label { padding-right: 28px; }
  .gs-btn-icon { width: 32%; }
}
@media (prefers-reduced-motion: reduce) {
  .gs-btn, .gs-btn-label, .gs-btn-icon, .gs-btn-icon svg {
    transition: none;
  }
}

/* ── Take-test ─────────────────────────────────────────────────────── */
.take-card {
  max-width: 760px;
  margin: 40px auto;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-xl);
  padding: 48px 52px;
  box-shadow: var(--sh-xl);
  animation: slideUp var(--dur-slow) var(--ease) both;
}
.progress {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  font-size: 12px;
  color: var(--c-text-2);
  margin-bottom: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.08em;
}
.progress strong { color: var(--c-primary); font-weight: 800; font-size: 14px; }
.bar {
  height: 8px;
  background: var(--c-surface-2);
  border-radius: var(--r-full);
  overflow: hidden;
  margin: 10px 0 32px;
  border: 1px solid var(--c-border);
}
.bar-fill {
  height: 100%;
  background: var(--grad-warm);
  border-radius: var(--r-full);
  transition: width var(--dur-med) var(--ease);
  position: relative;
  overflow: hidden;
}
.bar-fill::after {
  content: "";
  position: absolute;
  inset: 0;
  background: linear-gradient(90deg, transparent 0%, rgba(255,255,255,0.4) 50%, transparent 100%);
  background-size: 200% 100%;
  animation: shimmer 2s linear infinite;
}
.feedback {
  padding: 16px 20px;
  border-radius: var(--r-md);
  font-size: 15px;
  font-weight: 600;
  margin-bottom: 24px;
  border: 1.5px solid transparent;
  display: flex;
  align-items: center;
  gap: 10px;
  animation: popIn 400ms var(--ease-bounce) both;
}
.feedback-icon {
  width: 28px;
  height: 28px;
  border-radius: var(--r-full);
  display: grid;
  place-items: center;
  font-weight: 800;
  flex-shrink: 0;
}
.feedback-ok  { background: var(--c-ok-3);  border-color: var(--c-ok-br);  color: var(--c-ok-2); }
.feedback-ok  .feedback-icon { background: var(--c-ok); color: #fff; }
.feedback-bad { background: var(--c-err-3); border-color: var(--c-err-br); color: var(--c-err-2); }
.feedback-bad .feedback-icon { background: var(--c-err); color: #fff; }

.take-question {
  font-size: 26px;
  font-weight: 800;
  line-height: 1.35;
  letter-spacing: -0.025em;
  color: var(--c-text);
  margin: 16px 0 28px;
}
.q-form { display: flex; flex-direction: column; gap: 12px; }
.choice {
  display: flex;
  align-items: center;
  gap: 18px;
  padding: 18px 22px;
  border: 2px solid var(--c-border);
  border-radius: var(--r-md);
  background: var(--c-surface);
  cursor: pointer;
  transition: border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
  position: relative;
}
.choice:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  transform: translateX(4px);
}
.choice input[type="radio"] {
  position: absolute;
  opacity: 0;
  pointer-events: none;
}
.choice:has(input:checked) {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: var(--sh-focus);
}
.choice:has(input:checked) .choice-letter {
  background: var(--grad-warm);
  color: #ffffff;
  border-color: var(--c-primary);
}
.choice-letter {
  display: grid;
  place-items: center;
  width: 40px;
  height: 40px;
  border-radius: var(--r-full);
  border: 2px solid var(--c-border-2);
  background: var(--c-surface-2);
  color: var(--c-text);
  font-weight: 800;
  font-size: 16px;
  flex-shrink: 0;
  transition: all var(--dur-fast) var(--ease);
}
.choice-text { flex: 1; font-size: 16px; font-weight: 500; }
.take-card .btn-primary { margin-top: 16px; padding: 16px 28px; font-size: 16px; }

/* ── Result hero ───────────────────────────────────────────────────── */
.result-card {
  max-width: 560px;
  margin: 72px auto;
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-xl);
  padding: 56px 40px 48px;
  text-align: center;
  box-shadow: var(--sh-xl);
  position: relative;
  overflow: hidden;
  animation: slideUp var(--dur-slow) var(--ease) both;
}
.result-card::before {
  content: "";
  position: absolute;
  inset: -1px -1px auto -1px;
  height: 6px;
  background: var(--grad-warm);
}
.result-card::after {
  content: "";
  position: absolute;
  top: -120px; left: -120px;
  width: 320px; height: 320px;
  background: radial-gradient(closest-side, rgba(251, 146, 60, 0.25), transparent 70%);
  pointer-events: none;
}
.result-card > * { position: relative; }
.result-emoji {
  font-size: 64px;
  margin-bottom: 8px;
  display: inline-block;
  animation: popIn 600ms var(--ease-bounce) both;
}
.result-card h1 {
  font-size: 14px;
  font-weight: 700;
  color: var(--c-text-2);
  text-transform: uppercase;
  letter-spacing: 0.14em;
  margin-bottom: 6px;
}
.result-test {
  font-size: 18px;
  font-weight: 700;
  color: var(--c-text);
  margin-bottom: 20px;
}
.result-pct {
  font-size: 108px;
  font-weight: 800;
  line-height: 1;
  letter-spacing: -0.05em;
  margin: 8px 0 16px;
  font-feature-settings: "tnum";
  animation: popIn 640ms var(--ease-bounce) both;
  animation-delay: 200ms;
  opacity: 0;
  animation-fill-mode: forwards;
}
.result-pct-good { color: var(--c-ok); }
.result-pct-mid  { color: var(--c-warn); }
.result-pct-bad  { color: var(--c-err); }
.result-sub {
  font-size: 14px;
  color: var(--c-text-2);
  margin-bottom: 32px;
}
.result-card .row { justify-content: center; gap: 12px; }

/* ── Admin stats ───────────────────────────────────────────────────── */
.stat-card {
  background: var(--c-surface);
  border: 1.5px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 24px 22px;
  text-align: left;
  box-shadow: var(--sh-xs);
  transition: transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease);
  position: relative;
  overflow: hidden;
  animation: fadeInUp var(--dur-slow) var(--ease) both;
}
.stat-card::before {
  content: "";
  position: absolute;
  top: 0; left: 0;
  width: 4px; height: 100%;
  background: var(--grad-warm);
  opacity: 0;
  transition: opacity var(--dur-fast) var(--ease);
}
.stat-card:hover {
  transform: translateY(-3px);
  border-color: var(--c-primary-br);
  box-shadow: var(--sh-sm);
}
.stat-card:hover::before { opacity: 1; }
.stat-val {
  font-size: 36px;
  font-weight: 800;
  color: var(--c-text);
  line-height: 1;
  letter-spacing: -0.03em;
  font-feature-settings: "tnum";
}
.stat-lbl {
  font-size: 11px;
  color: var(--c-text-2);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  margin-top: 10px;
}

/* ── Tables ────────────────────────────────────────────────────────── */
.tbl { width: 100%; border-collapse: collapse; }
.tbl th, .tbl td {
  text-align: left;
  padding: 14px 16px;
  border-bottom: 1px solid var(--c-border);
  font-size: 13px;
}
.tbl tr:last-child td { border-bottom: 0; }
.tbl th {
  font-weight: 700;
  color: var(--c-text-2);
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  background: var(--c-surface-2);
}
.tbl tbody tr { transition: background var(--dur-fast) var(--ease); }
.tbl tbody tr:hover { background: var(--c-primary-3); }
.tbl strong { font-weight: 800; font-feature-settings: "tnum"; }

/* ── Modal (native <dialog>) ───────────────────────────────────────── */
dialog.modal {
  border: none;
  padding: 0;
  border-radius: var(--r-lg);
  box-shadow: var(--sh-xl);
  max-width: 480px;
  width: 92vw;
  background: var(--c-surface);
  animation: slideUp var(--dur-med) var(--ease) both;
}
/* Wide variant — for dialogs with lots of content like the test-creation
   wizard (multi-step, method tiles, topic picker list). */
dialog.modal-lg { max-width: 640px; }
dialog.modal::backdrop {
  background: rgba(15, 23, 42, 0.5);
  backdrop-filter: blur(4px);
  -webkit-backdrop-filter: blur(4px);
  animation: fadeIn var(--dur-med) var(--ease) both;
}
.modal-head {
  padding: 24px 28px 8px;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
}
.modal-head h3 {
  font-size: 18px;
  font-weight: 800;
  letter-spacing: -0.01em;
  margin: 0;
}
.modal-close {
  background: var(--c-surface-2);
  border: 1px solid var(--c-border);
  width: 32px;
  height: 32px;
  border-radius: var(--r-full);
  cursor: pointer;
  color: var(--c-text-2);
  font-size: 18px;
  font-weight: 700;
  display: grid;
  place-items: center;
  transition: all var(--dur-fast) var(--ease);
}
.modal-close:hover { background: var(--c-err-3); border-color: var(--c-err-br); color: var(--c-err); transform: rotate(90deg); }
.modal-body { padding: 16px 28px 28px; }
.modal-sub { font-size: 13px; color: var(--c-text-2); margin-bottom: 18px; }
.modal-body form { margin: 0; }
.modal-actions {
  display: flex;
  gap: 10px;
  justify-content: flex-end;
  margin-top: 6px;
}

/* ── Responsive ────────────────────────────────────────────────────── */
@media (max-width: 720px) {
  .wrap { padding: 24px 20px 64px; }
  .topbar { padding: 14px 20px; }
  .topbar .who-role { display: none; }
  h1 { font-size: 26px; }
  h2 { font-size: 20px; }
  .hero { padding: 32px 24px; }
  .hero h1 { font-size: 30px; }
  .hero .stats { gap: 20px; }
  .card, .card-narrow, .card-wide { padding: 28px; }
  .card-narrow, .card-wide { margin: 28px auto; }
  .take-card { padding: 32px 24px; margin: 20px auto; }
  .take-question { font-size: 21px; }
  .result-card { padding: 44px 24px 36px; margin: 36px auto; }
  .result-pct { font-size: 84px; }
  .subject-block { padding: 20px; }
  dialog.modal { max-width: 100%; width: 100%; border-radius: var(--r-lg) var(--r-lg) 0 0; margin: auto 0 0; }
}


/* ═══════════════════════════════════════════════════════════════════════
   Typing game  — kid-side learn-to-type widget.
   Mac-style keyboard with glowing highlight for the next expected key.
   Pure CSS animations, no framework deps. Scales down on mobile.
   ═══════════════════════════════════════════════════════════════════════ */

.typing-page {
  max-width: 920px;
  margin: 0 auto;
}

.typing-hero {
  text-align: center;
  padding: 14px 16px 6px;   /* was 28px 16px 12px — tightened to claw back vertical real estate */
}
.typing-hero h1 {
  font-size: 30px;          /* was 38px */
  margin-bottom: 4px;
}
.typing-hero p {
  color: var(--c-text-2);
  font-size: 14px;
  max-width: 820px;   /* was 620px — gives the (short) subtitle room to stay on one line */
  margin: 0 auto;
  line-height: 1.4;
}

/* Practice-session timer chip. Idle grey → primary tint when ticking.
   Kept deliberately small so it reads as "passive info" not "deadline". */
.typing-timer {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin-top: 6px;    /* was 12px */
  padding: 3px 10px;
  border: 1px solid var(--c-border);
  border-radius: 999px;
  background: var(--c-surface);
  color: var(--c-text-3);
  font-size: 13px;
  font-variant-numeric: tabular-nums;  /* digits don't jitter on tick */
  line-height: 1.6;
  transition: color var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
.typing-timer.is-running {
  color: var(--c-primary);
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
}
.typing-timer-icon { font-size: 14px; }
.typing-timer-value { font-weight: 600; letter-spacing: 0.02em; }

/* ── Word picker ─────────────────────────────────────────────────────── */
.typing-picker {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(180px, 1fr));
  gap: 10px;           /* was 12px */
  margin: 12px 0 8px;  /* was 24px 0 12px */
}
.typing-word-card {
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 14px 16px;
  text-align: left;
  cursor: pointer;
  transition: all var(--dur-fast) var(--ease);
  font-family: inherit;
  font-size: 16px;
  color: var(--c-text);
  display: flex;
  flex-direction: column;
  gap: 6px;
}
/* CRITICAL: the rule above sets display:flex, which has the same
   specificity as the UA stylesheet's [hidden] { display: none } and
   thus WINS by source order — meaning tile.hidden = true has no
   visual effect without this override. Without this line, deleting a
   default word/sentence silently stores the hide but the tile stays
   on screen. */
.typing-word-card[hidden] {
  display: none !important;
}
.typing-word-card:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  transform: translateY(-1px);
}
.typing-word-card.active {
  border-color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: 0 0 0 3px rgba(249, 115, 22, 0.12);
}
.typing-word-card strong {
  font-size: 18px;
  letter-spacing: 0.04em;
}
.typing-word-card .diff-chip {
  font-size: 12px;
  color: var(--c-text-3);
  align-self: flex-start;
  padding: 2px 8px;
  background: var(--c-surface-2);
  border-radius: var(--r-sm);
}
.typing-word-card .diff-chip.diff-easy   { background: #ecfdf5; color: #047857; }
.typing-word-card .diff-chip.diff-medium { background: #fffbeb; color: #b45309; }
.typing-word-card .diff-chip.diff-hard   { background: #fef2f2; color: #b91c1c; }

/* ── Word display + status ───────────────────────────────────────────── */
.typing-stage {
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-lg);
  padding: 18px 24px;   /* was 28px 24px — less vertical padding */
  margin: 16px 0 20px;
  text-align: center;
}
.typing-prompt {
  font-size: 14px;
  color: var(--c-text-3);
  text-transform: uppercase;
  letter-spacing: 0.08em;
  margin-bottom: 12px;
}
.typing-word {
  font-size: 56px;
  font-weight: 800;
  letter-spacing: 0.12em;
  display: inline-flex;
  gap: 6px;
  justify-content: center;
  flex-wrap: wrap;
  margin-bottom: 16px;
}
.typing-letter {
  display: inline-block;
  min-width: 36px;
  padding: 4px 6px;
  border-radius: var(--r-sm);
  transition: all 200ms var(--ease);
  color: var(--c-text-3);
}

/* Length-aware shrink. renderWord() tags .typing-word with one of these
   based on currentWord.length — keeps short words big & inviting while
   long sentences stay visually contained (no 6-row letter walls). */
.typing-word.is-medium {
  font-size: 36px;
  letter-spacing: 0.08em;
  gap: 4px;
  margin-bottom: 12px;
}
.typing-word.is-medium .typing-letter { min-width: 24px; padding: 3px 4px; }

.typing-word.is-long {
  font-size: 26px;
  letter-spacing: 0.06em;
  gap: 3px;
  margin-bottom: 10px;
}
.typing-word.is-long .typing-letter { min-width: 18px; padding: 2px 3px; }

.typing-word.is-xlong {
  font-size: 20px;
  letter-spacing: 0.04em;
  gap: 2px;
  margin-bottom: 8px;
}
.typing-word.is-xlong .typing-letter { min-width: 14px; padding: 1px 2px; }
.typing-letter.done {
  color: var(--c-ok-2);
  background: var(--c-ok-3);
}
.typing-letter.current {
  color: var(--c-primary);
  background: var(--c-primary-3);
  box-shadow: 0 0 0 2px var(--c-primary-br);
  animation: typing-letter-pulse 1200ms ease-in-out infinite;
}
.typing-letter.space-glyph { color: var(--c-text-3); opacity: 0.35; }

@keyframes typing-letter-pulse {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-4px); }
}

.typing-progress {
  max-width: 320px;
  margin: 0 auto;
  height: 6px;
  background: var(--c-surface-2);
  border-radius: 999px;
  overflow: hidden;
}
.typing-progress-fill {
  height: 100%;
  width: 0%;
  background: linear-gradient(90deg, var(--c-primary), #fb923c);
  transition: width 240ms var(--ease);
}
.typing-progress-label {
  font-size: 13px;
  color: var(--c-text-3);
  margin-top: 8px;
}
.typing-status {
  margin-top: 14px;
  font-size: 16px;
  font-weight: 600;
  min-height: 24px;
  color: var(--c-text-2);
}
.typing-status.correct { color: var(--c-ok-2); }
.typing-status.wrong   { color: var(--c-err-2); animation: typing-shake 320ms ease-in-out; }
.typing-status.done    { color: var(--c-primary); font-size: 20px; }

@keyframes typing-shake {
  0%, 100% { transform: translateX(0); }
  25%      { transform: translateX(-6px); }
  75%      { transform: translateX(6px); }
}

.typing-actions {
  display: flex;
  gap: 10px;
  justify-content: center;
  flex-wrap: wrap;
  margin-top: 16px;
}

/* ── Keyboard widget ─────────────────────────────────────────────────── */
.kb-wrap {
  background: linear-gradient(180deg, #1c1c1f 0%, #111114 100%);
  border: 1px solid #2a2a2e;
  border-radius: 14px;
  padding: 18px;
  margin: 8px auto 24px;
  /* Stretch to match the tab panel above (same 1024px cap). Keys scale
     up with the container so a wide keyboard gets bigger, more tappable
     keys — better for kids tracking glow states. */
  max-width: 1024px;
  box-shadow:
    0 18px 40px -18px rgba(0, 0, 0, 0.4),
    inset 0 1px 0 rgba(255, 255, 255, 0.05);
}
.kb-rows {
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.kb-row {
  display: flex;
  gap: 6px;
  justify-content: center;
}
.kb-key {
  min-width: 40px;
  height: 52px;        /* bumped from 40 so key proportions feel right at wider sizes */
  flex: 1 1 48px;      /* flex-grow 1 so keys fill available width */
  max-width: 84px;     /* lifted from 56 so keys can breathe on wide viewports */
  border-radius: 10px;
  font-size: 15px;
  background: #18181b;
  border: 1px solid #2a2a2e;
  border-top-color: #3a3a3e;
  border-bottom-color: #151517;
  color: #a1a1aa;
  font-size: 13px;
  font-weight: 600;
  display: flex;
  align-items: center;
  justify-content: center;
  user-select: none;
  transition: all 120ms var(--ease);
  box-shadow:
    inset 0 -1px 0 rgba(0, 0, 0, 0.4),
    inset 0 1px 0 rgba(255, 255, 255, 0.04);
}
.kb-key.wide    { flex-grow: 1.4; max-width: none; }
.kb-key.xwide   { flex-grow: 2;   max-width: none; }
.kb-key.space   { flex-grow: 6;   max-width: none; height: 52px; }
.kb-key.active {
  background: linear-gradient(180deg, #1f1f23 0%, #141416 100%);
  border-color: var(--c-primary);
  color: #fff;
  box-shadow:
    0 0 0 1px var(--c-primary),
    0 0 24px rgba(249, 115, 22, 0.65),
    inset 0 1px 0 rgba(255, 255, 255, 0.08);
  animation: kb-glow 1200ms ease-in-out infinite;
}
.kb-key.hit {
  background: linear-gradient(180deg, #0f2a1f 0%, #0a1d15 100%);
  border-color: var(--c-ok);
  color: #bbf7d0;
  box-shadow:
    0 0 0 1px var(--c-ok),
    0 0 20px rgba(16, 185, 129, 0.55);
}
.kb-key.miss {
  background: linear-gradient(180deg, #2a0f14 0%, #1d0a0d 100%);
  border-color: var(--c-err);
  color: #fecaca;
  animation: kb-miss 240ms ease-in-out;
}

@keyframes kb-glow {
  0%, 100% { box-shadow:
    0 0 0 1px var(--c-primary),
    0 0 18px rgba(249, 115, 22, 0.45),
    inset 0 1px 0 rgba(255, 255, 255, 0.08); }
  50%      { box-shadow:
    0 0 0 1px var(--c-primary),
    0 0 32px rgba(249, 115, 22, 0.85),
    inset 0 1px 0 rgba(255, 255, 255, 0.08); }
}
@keyframes kb-miss {
  0%, 100% { transform: translateX(0); }
  25%      { transform: translateX(-4px); }
  75%      { transform: translateX(4px); }
}

/* Row-stagger fade in on page load — same idea as the reference, done in
   pure CSS keyframes instead of Framer Motion. */
.kb-row {
  opacity: 0;
  transform: translateY(-6px);
  animation: kb-row-in 420ms ease-out forwards;
}
.kb-row:nth-child(1) { animation-delay:  40ms; }
.kb-row:nth-child(2) { animation-delay: 140ms; }
.kb-row:nth-child(3) { animation-delay: 240ms; }
.kb-row:nth-child(4) { animation-delay: 340ms; }
@keyframes kb-row-in {
  to { opacity: 1; transform: translateY(0); }
}

.typing-hint {
  text-align: center;
  color: var(--c-text-3);
  font-size: 13px;
  margin-top: 4px;
}

/* ── Mobile scaling ──────────────────────────────────────────────────── */
@media (max-width: 720px) {
  .typing-word { font-size: 40px; }
  .typing-letter { min-width: 28px; }
  .kb-key {
    min-width: 28px;
    flex: 1 0 28px;
    height: 36px;
    font-size: 11px;
  }
  .kb-wrap { padding: 10px; }
}


/* ═══════════════════════════════════════════════════════════════════════
   Consolidated identity dropdown — replaces the three separate topbar
   items (language, name, logout) with one avatar menu. Based on the
   native <details> element so click/tap handling + keyboard focus work
   without a single line of framework JS.
   ═══════════════════════════════════════════════════════════════════════ */

.who-menu {
  position: relative;
}
.who-menu > summary.who {
  list-style: none;
  cursor: pointer;
  user-select: none;
  /* Inherit everything else from the existing .who rules so we keep the
     same avatar+name layout and hover state. */
}
.who-menu > summary.who::-webkit-details-marker { display: none; }
.who-menu > summary.who::marker { content: ; }

.who-chevron {
  margin-left: 4px;
  opacity: 0.55;
  transition: transform var(--dur-fast) var(--ease);
}
.who-menu[open] > summary .who-chevron {
  transform: rotate(180deg);
  opacity: 0.85;
}

/* Drop-down panel. Sits flush under the summary, pinned to its right
   edge so it never pushes the layout wider. Shadow + border match the
   rest of the app's card aesthetic. */
.who-panel {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  min-width: 260px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  box-shadow: var(--sh-md, 0 12px 32px -8px rgba(15, 23, 42, 0.18));
  padding: 6px;
  z-index: 60;
  animation: who-panel-in 140ms var(--ease) both;
}
@keyframes who-panel-in {
  from { opacity: 0; transform: translateY(-4px); }
  to   { opacity: 1; transform: translateY(0); }
}

.who-panel-identity {
  padding: 10px 12px 12px;
}
.who-panel-name {
  font-weight: 700;
  color: var(--c-text);
  font-size: 14px;
}
.who-panel-sub {
  font-size: 12px;
  color: var(--c-text-3);
  margin-top: 2px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 220px;
}

.who-panel-divider {
  height: 1px;
  background: var(--c-border);
  margin: 4px 2px;
}

.who-panel-item {
  display: flex;
  align-items: center;
  gap: 10px;
  width: 100%;
  padding: 10px 12px;
  border: 0;
  background: none;
  border-radius: var(--r-sm);
  font: inherit;
  font-size: 14px;
  color: var(--c-text);
  text-align: left;
  cursor: pointer;
  text-decoration: none;
  transition: background var(--dur-fast) var(--ease);
}
.who-panel-item:hover,
.who-panel-item:focus-visible {
  background: var(--c-surface-2);
  text-decoration: none;
  color: var(--c-text);
}
.who-panel-icon {
  flex: 0 0 auto;
  width: 18px;
  text-align: center;
  font-size: 16px;
}
.who-panel-item-danger { color: var(--c-err-2); }
.who-panel-item-danger:hover,
.who-panel-item-danger:focus-visible {
  background: var(--c-err-3);
  color: var(--c-err-2);
}
.who-panel-logout-form { margin: 0; }

/* Language row: label + 4 compact codes. Active locale is filled orange
   so the current selection is unmistakeable at a glance. */
.who-panel-lang {
  padding: 10px 12px 12px;
}
.who-panel-lang-label {
  display: flex;
  align-items: center;
  gap: 10px;
  font-size: 13px;
  color: var(--c-text-2);
  margin-bottom: 8px;
}
.who-panel-lang-choices {
  display: flex;
  gap: 6px;
  margin-left: 28px; /* aligns under the label text (past the icon) */
}
.who-panel-lang-choice {
  flex: 1 1 0;
  padding: 6px 8px;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  font-size: 12px;
  font-weight: 700;
  color: var(--c-text-2);
  text-align: center;
  text-decoration: none;
  transition: all var(--dur-fast) var(--ease);
}
.who-panel-lang-choice:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  color: var(--c-primary);
  text-decoration: none;
}
.who-panel-lang-choice.is-active {
  background: var(--c-primary);
  border-color: var(--c-primary);
  color: #fff;
}
.who-panel-lang-choice.is-active:hover {
  background: var(--c-primary-2);
  border-color: var(--c-primary-2);
  color: #fff;
}

/* Mobile: pin the panel to the right edge of the viewport so it never
   overflows, and shrink the min-width so it fits narrow screens. */
@media (max-width: 520px) {
  .who-panel {
    right: 0;
    min-width: 240px;
  }
  .who-name {
    max-width: 90px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }
}


/* ═══════════════════════════════════════════════════════════════════════
   Kid access credentials card — read-only reference for the parent.
   ═══════════════════════════════════════════════════════════════════════ */

.kid-access-card {
  background: linear-gradient(180deg, var(--c-primary-3) 0%, var(--c-surface) 70%);
  border: 1px solid var(--c-primary-br);
}
.kid-access-head h3 {
  font-size: 17px;
}
.kid-access-list {
  display: flex;
  flex-direction: column;
  gap: 10px;
  margin: 16px 0 0;
  padding: 0;
}
.kid-access-row {
  display: flex;
  /* Top-align the label with the value row so stacked layouts (narrow
     dialogs) stay visually tight. Center-align added extra space above
     short elements like the password hint <span>. */
  align-items: flex-start;
  gap: 8px 12px;
  flex-wrap: wrap;
}
.kid-access-row > dt {
  flex: 0 0 140px;
  font-size: 13px;
  font-weight: 600;
  color: var(--c-text-2);
  text-transform: none;
  letter-spacing: 0;
  /* Align label baseline with the first line of value content (which
     may be inside a padded code box or a plain span). */
  padding-top: 8px;
}
.kid-access-row > dd {
  flex: 1 1 auto;
  margin: 0;
  display: flex;
  align-items: center;
  gap: 10px;
  flex-wrap: wrap;
  min-height: 36px;
}
.kid-access-value {
  display: inline-block;
  padding: 6px 10px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 13px;
  color: var(--c-text);
  user-select: all;  /* click selects the whole value — makes copy-paste trivial */
}
.kid-access-copy {
  transition: all 140ms var(--ease);
}
.kid-access-copy-ok {
  background: var(--c-ok-3) !important;
  border-color: var(--c-ok-br) !important;
  color: var(--c-ok-2) !important;
}

/* Mobile: stack label + value vertically once the row gets cramped. */
@media (max-width: 560px) {
  .kid-access-row { flex-direction: column; align-items: flex-start; gap: 4px; }
  .kid-access-row > dt { flex: unset; }
}


/* ═══════════════════════════════════════════════════════════════════════
   Family personalization — photo + motto band on the parent dashboard,
   plus the side-by-side photo preview frames in settings.
   ═══════════════════════════════════════════════════════════════════════ */

/* ── Dashboard band ──────────────────────────────────────────────── */
.family-band {
  display: flex;
  align-items: center;
  gap: 20px;
  padding: 18px 22px;
  margin: 16px 0 20px;
  background: linear-gradient(120deg, var(--c-primary-3) 0%, var(--c-accent-3) 100%);
  border: 1px solid var(--c-primary-br);
  border-radius: var(--r-lg);
  box-shadow: var(--sh-sm, 0 6px 18px -12px rgba(15, 23, 42, 0.15));
}
.family-band-photo {
  flex: 0 0 auto;
  width: 88px;
  height: 88px;
  border-radius: 50%;
  object-fit: cover;
  background: var(--c-surface);
  border: 3px solid var(--c-surface);
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);
}
.family-band-photo-placeholder {
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 44px;
  background: var(--c-surface);
}
.family-band-body {
  flex: 1 1 auto;
  min-width: 0;
}
.family-band-welcome {
  font-size: 20px;
  font-weight: 700;
  color: var(--c-text);
  letter-spacing: -0.01em;
}
.family-band-motto {
  margin-top: 4px;
  font-size: 15px;
  font-style: italic;
  color: var(--c-text-2);
  /* Let long mottos wrap — no ellipsis; motto is meant to be read. */
}

@media (max-width: 560px) {
  .family-band { flex-direction: column; text-align: center; padding: 18px 16px; }
  .family-band-photo { width: 72px; height: 72px; }
  .family-band-welcome { font-size: 18px; }
}

/* ── Settings preview frames ─────────────────────────────────────── */
.family-photo-frame {
  width: 120px;
  height: 120px;
  border-radius: 50%;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  display: flex;
  align-items: center;
  justify-content: center;
  overflow: hidden;
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.04);
}
.family-photo-frame img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
.family-photo-frame-new { border: 2px solid var(--c-primary); }
.family-photo-placeholder { font-size: 56px; opacity: 0.55; }


/* ═══════════════════════════════════════════════════════════════════════
   Retry-remind button on failed results rows — sits next to the failed
   status badge. Small, unobtrusive chip that opens the shared remind
   dialog with test-specific context pre-filled.
   ═══════════════════════════════════════════════════════════════════════ */

.results-retry-nudge {
  font: inherit;
  font-size: 12px;
  font-weight: 600;
  padding: 4px 10px;
  background: var(--c-primary-3);
  color: var(--c-primary-2);
  border: 1px solid var(--c-primary-br);
  border-radius: 999px;
  cursor: pointer;
  white-space: nowrap;
  transition: all var(--dur-fast) var(--ease);
}
.results-retry-nudge:hover {
  background: var(--c-primary);
  border-color: var(--c-primary);
  color: #fff;
  transform: translateY(-1px);
}
.results-retry-nudge:active { transform: translateY(0); }


/* ═══════════════════════════════════════════════════════════════════════
   Fresh-password display — the single-shot box that surfaces after the
   parent resets a kid's password. Pulsing ring to draw the eye because
   it only shows for this one pageview.
   ═══════════════════════════════════════════════════════════════════════ */

.kid-access-fresh {
  display: flex;
  flex-direction: column;
  gap: 6px;
  padding: 12px 14px;
  background: var(--c-ok-3);
  border: 2px solid var(--c-ok);
  border-radius: var(--r-md);
  box-shadow: 0 0 0 3px rgba(16, 185, 129, 0.14);
  animation: kid-access-fresh-pulse 1200ms ease-in-out 2;
}
.kid-access-fresh-label {
  font-size: 13px;
  font-weight: 700;
  color: var(--c-ok-2);
}
.kid-access-fresh-row {
  display: flex;
  align-items: center;
  gap: 10px;
  flex-wrap: wrap;
}
.kid-access-fresh-value {
  display: inline-block;
  padding: 6px 12px;
  background: #fff;
  border: 1px solid var(--c-ok);
  border-radius: var(--r-sm);
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 15px;
  font-weight: 700;
  color: var(--c-text);
  user-select: all;
}
.kid-access-fresh-hint {
  font-size: 12px;
  color: var(--c-text-2);
  font-style: italic;
}
@keyframes kid-access-fresh-pulse {
  0%, 100% { box-shadow: 0 0 0 3px rgba(16, 185, 129, 0.14); }
  50%      { box-shadow: 0 0 0 6px rgba(16, 185, 129, 0.22); }
}


/* ═══════════════════════════════════════════════════════════════════════
   Toast-style flash notifications — replaces the old in-flow banner.
   Fixed top-right, slide-in + auto-dismiss. Click to dismiss early.
   Still uses the same .flash.type payload from the server (ok / error).
   ═══════════════════════════════════════════════════════════════════════ */

.toast {
  position: fixed;
  top: 96px;                      /* below the 88px-tall topbar + a gap */
  right: 24px;
  z-index: 100;
  display: flex;
  align-items: center;
  gap: 12px;
  min-width: 260px;
  max-width: min(440px, calc(100vw - 48px));
  padding: 14px 18px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-left-width: 6px;
  border-radius: var(--r-md);
  box-shadow: 0 12px 32px -8px rgba(15, 23, 42, 0.22);
  font-size: 14px;
  font-weight: 600;
  color: var(--c-text);
  cursor: pointer;
  animation: toast-in 240ms cubic-bezier(0.22, 1, 0.36, 1) both;
  transition: opacity 220ms ease, transform 220ms ease;
}
.toast-ok    { border-left-color: var(--c-ok);  background: var(--c-ok-3);  color: var(--c-ok-2); }
.toast-error { border-left-color: var(--c-err); background: var(--c-err-3); color: var(--c-err-2); }

.toast-icon {
  flex: 0 0 auto;
  width: 24px;
  height: 24px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  font-size: 14px;
  font-weight: 800;
  background: rgba(255, 255, 255, 0.6);
}
.toast-msg {
  flex: 1 1 auto;
  line-height: 1.4;
  /* Toast messages can contain the localized HTML entities we use for
     names + quotes — keep whitespace normal so they wrap cleanly. */
}
.toast-close {
  flex: 0 0 auto;
  background: transparent;
  border: 0;
  font-size: 20px;
  line-height: 1;
  color: inherit;
  opacity: 0.55;
  cursor: pointer;
  padding: 4px 6px;
  transition: opacity var(--dur-fast) var(--ease);
}
.toast-close:hover { opacity: 1; }

.toast-out {
  opacity: 0;
  transform: translateX(20px);
}

@keyframes toast-in {
  from { opacity: 0; transform: translateX(32px) scale(0.98); }
  to   { opacity: 1; transform: translateX(0)    scale(1);    }
}

/* Mobile: pin to top full-width-ish instead of floating card. */
@media (max-width: 560px) {
  .toast {
    top: 80px;
    left: 12px;
    right: 12px;
    max-width: none;
  }
}

/* Keep .flash around as a legacy utility in case any view still inlines
   it (e.g. an ad-hoc banner inside a card). Same palette, same feel. */
.flash { /* legacy — shares palette with .toast */ }


/* ═══════════════════════════════════════════════════════════════════════
   Collapsible "Zugangsdaten" summary — tucks the credentials card at the
   bottom of the kid page behind a single native <details> toggle. Design
   goal: visible enough to find, quiet enough to ignore on daily visits.
   ═══════════════════════════════════════════════════════════════════════ */

.kid-access-details {
  /* Lift the cursor on the summary so click affordance is obvious even
     before the user has seen the caret rotate. */
}
.kid-access-details > summary {
  list-style: none;   /* hide the default disclosure triangle */
  cursor: pointer;
  user-select: none;
  display: inline-flex;
  align-items: center;
  gap: 10px;
  padding: 10px 14px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  font-size: 15px;
  font-weight: 700;
  color: var(--c-text-2);
  transition: all var(--dur-fast) var(--ease);
}
.kid-access-details > summary::-webkit-details-marker { display: none; }
.kid-access-details > summary::marker { content: ""; }
.kid-access-details > summary:hover {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  color: var(--c-primary);
}

.kid-access-summary-icon  { font-size: 18px; }
.kid-access-summary-label { flex: 1 1 auto; }
.kid-access-summary-caret {
  display: inline-block;
  font-size: 14px;
  opacity: 0.6;
  transition: transform var(--dur-fast) var(--ease);
}
.kid-access-details[open] > summary .kid-access-summary-caret {
  transform: rotate(90deg);
  opacity: 1;
}
.kid-access-details[open] > summary {
  border-color: var(--c-primary-br);
  background: var(--c-primary-3);
  color: var(--c-primary);
}


/* ═══════════════════════════════════════════════════════════════════════
   Test-linked reminder styling — warmer left border + lock-hint styling
   so the kid sees this one's different from a dismissible parent nudge.
   ═══════════════════════════════════════════════════════════════════════ */

.reminder-card-linked {
  border-left: 4px solid var(--c-primary);
  background: linear-gradient(180deg, var(--c-primary-3) 0%, var(--c-surface) 60%);
}
.reminder-card-hint {
  margin-top: 6px;
  font-style: italic;
}
.reminder-card-cta {
  align-self: center;
  white-space: nowrap;
}


/* ═══════════════════════════════════════════════════════════════════════
   Compact hero variant — used on the kid's /student dashboard where the
   old centered-stack layout was wasting ~50% of its height. Two-column
   split: left = identity + stats, right = action buttons. Keeps the same
   warm gradient background so it still feels like the "home" moment.
   ═══════════════════════════════════════════════════════════════════════ */

.hero-compact {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 32px;
  padding: 22px 28px;       /* was 44px 48px on the default .hero */
  margin-bottom: 24px;
  text-align: left;         /* override .hero default center */
}
.hero-compact-main {
  flex: 1 1 auto;
  min-width: 0;             /* so the truncation inside works */
}
.hero-compact-greet {
  font-size: 28px;          /* was ~40px+ */
  margin: 0 0 4px;
  line-height: 1.15;
}
.hero-compact .sub {
  margin: 0 0 10px;
  font-size: 15px;
  color: var(--c-text-2);
}

/* Inline stats strip — replaces the 3 big tiles with a single text row. */
.hero-stats-inline {
  display: flex;
  align-items: center;
  gap: 10px;
  flex-wrap: wrap;
  font-size: 14px;
  color: var(--c-text-2);
}
.stat-inline {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
.stat-inline-icon {
  font-size: 16px;
}
.stat-inline strong {
  font-size: 18px;
  font-weight: 800;
  color: var(--c-text);
}
.stat-inline-dot {
  opacity: 0.45;
  font-weight: 700;
}

/* Actions column — stacked on desktop so buttons align right. */
.hero-compact-actions {
  display: flex;
  flex-direction: column;
  gap: 8px;
  flex: 0 0 auto;
  align-items: stretch;
}
.hero-compact-actions .btn { white-space: nowrap; }

/* ═══════════════════════════════════════════════════════════════════════
   Gift-card CTA — an OPEN TREASURE CHEST. "Learn to type" framed as a
   free bonus that Lernino is handing out. Warm amber/gold palette +
   wood-toned border + golden shimmer so it visually echoes the "My
   treasure" button above. Goes hand-in-glove, not head-to-head.

   Design choices:
   — No standalone icon slot; the title already starts with ⌨️, and the
     badge carries a 🎁 via ::before. One icon per concept, zero repeats.
   — Amber/gold palette (not violet) so it reads as "treasure" and sits
     in the same family as the orange primary button instead of clashing.
   — Hover = the chest lid "opens" (translateY + shadow deepens).
   — Shimmer = a slow gold glint, disabled under prefers-reduced-motion.
   ═══════════════════════════════════════════════════════════════════════ */
.gift-card {
  position: relative;
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 10px 8px 12px;
  border-radius: 12px;
  /* Warm amber → rose-gold wash. Reads as "open treasure chest". */
  background:
    linear-gradient(135deg, #fffbeb 0%, #fef3c7 55%, #fde68a 100%);
  border: 1px solid #d97706;   /* wood-trim gold — matches a chest's brass */
  box-shadow:
    0 1px 2px rgba(217, 119, 6, 0.10),
    inset 0 1px 0 rgba(255, 255, 255, 0.6);   /* subtle top-edge highlight */
  text-decoration: none;
  color: var(--c-text);
  overflow: hidden;
  transition: transform var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
  line-height: 1.2;
  white-space: nowrap;
}
.gift-card:hover {
  /* "Lid opens" — card lifts + glow deepens. */
  transform: translateY(-2px);
  border-color: #b45309;
  box-shadow:
    0 10px 22px -10px rgba(217, 119, 6, 0.55),
    inset 0 1px 0 rgba(255, 255, 255, 0.7);
}
.gift-card:focus-visible {
  outline: none;
  box-shadow:
    0 0 0 3px rgba(245, 158, 11, 0.35),
    inset 0 1px 0 rgba(255, 255, 255, 0.6);
  border-color: #b45309;
}

.gift-card-body {
  display: flex;
  flex-direction: column;
  gap: 1px;
  line-height: 1.15;
  min-width: 0;
  flex: 1 1 auto;
}
.gift-card-title {
  font-size: 14px;
  font-weight: 700;
  color: #78350f;   /* deep amber — legible on the gold wash */
  letter-spacing: 0;
  overflow: hidden;
  text-overflow: ellipsis;
}
.gift-card-sub {
  font-size: 11px;
  color: #92400e;
  font-weight: 600;
  letter-spacing: 0.02em;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* Inline chip — the "Gratis" pill, with a 🎁 on the front. Pill itself
   stays orange/rose (brand continuity), the 🎁 lives in ::before so the
   i18n text stays gift-free and translators don't accidentally strip
   the emoji. */
.gift-card-badge {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 3px 9px;
  border-radius: 999px;
  background: linear-gradient(135deg, #f97316 0%, #ec4899 100%);
  color: #fff;
  font-size: 10px;
  font-weight: 800;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  line-height: 1.4;
  box-shadow: 0 1px 2px rgba(236, 72, 153, 0.25);
}
.gift-card-badge::before {
  content: "🎁";
  font-size: 11px;
  text-transform: none;
  letter-spacing: 0;
  filter: drop-shadow(0 1px 1px rgba(0,0,0,0.15));
}

/* Gold glint — one slow diagonal sweep every ~8s, tinted warm so it
   reads as "treasure sparkle" rather than a generic loading shimmer. */
.gift-card-shimmer {
  position: absolute;
  top: 0;
  left: -70%;
  width: 45%;
  height: 100%;
  background: linear-gradient(
    110deg,
    transparent 0%,
    rgba(255, 236, 153, 0) 40%,
    rgba(255, 248, 220, 0.75) 50%,
    rgba(255, 236, 153, 0) 60%,
    transparent 100%
  );
  animation: gift-shimmer 8s ease-in-out infinite;
  pointer-events: none;
}
@keyframes gift-shimmer {
  0%, 40%   { transform: translateX(0);    opacity: 0; }
  45%       { opacity: 1; }
  75%       { transform: translateX(380%); opacity: 1; }
  80%, 100% { transform: translateX(380%); opacity: 0; }
}
@media (prefers-reduced-motion: reduce) {
  .gift-card-shimmer { animation: none; display: none; }
  .gift-card:hover, .gift-card:focus-visible { transform: none; }
}

/* Narrow screens — tighten gap/padding, everything else scales down. */
@media (max-width: 420px) {
  .gift-card { padding: 7px 8px 7px 10px; gap: 8px; }
  .gift-card-title { font-size: 13px; }
  .gift-card-sub { font-size: 10.5px; }
  .gift-card-badge { font-size: 9.5px; padding: 2px 7px; }
  .gift-card-badge::before { font-size: 10px; }
}

/* Mobile: stack vertically, buttons go side-by-side to save rows. */
@media (max-width: 720px) {
  .hero-compact {
    flex-direction: column;
    align-items: stretch;
    padding: 18px 20px;
  }
  .hero-compact-actions {
    flex-direction: row;
    flex-wrap: wrap;
  }
  .hero-compact-actions .btn { flex: 1 1 140px; text-align: center; }
}


/* ═══════════════════════════════════════════════════════════════════════
   Subtle "Zugangsdaten" deep-link in the kid-hero identity block.
   Sits under the "Username: joni" line. Styled as a low-contrast text
   link — zero visual weight unless hovered — so it stays out of the way
   on daily check-ins but is discoverable when the parent needs it.
   ═══════════════════════════════════════════════════════════════════════ */

.kid-hero-access-link {
  /* Reset native <button> chrome — default browser styles add a border,
     background, and padding that ruin the "styled as a link" effect. */
  -webkit-appearance: none;
  appearance: none;
  background: transparent;
  border: 0;
  padding: 0;
  font: inherit;
  cursor: pointer;
  line-height: 1.4;

  /* Styling — low-contrast text link */
  display: inline-flex;
  align-items: center;
  gap: 4px;
  margin-top: 6px;
  font-size: 12px;
  font-weight: 500;
  color: var(--c-text-3);
  text-decoration: none;
  border-bottom: 1px dashed transparent;
  transition: all var(--dur-fast) var(--ease);
}
.kid-hero-access-link:hover,
.kid-hero-access-link:focus-visible {
  color: var(--c-primary);
  border-bottom-color: var(--c-primary-br);
  text-decoration: none;
  outline: none;
}
.kid-hero-access-link:focus-visible {
  /* Keep keyboard-accessibility without the ugly default focus ring — the
     dashed underline becomes solid on focus. */
  border-bottom-style: solid;
}


/* ═══════════════════════════════════════════════════════════════════════
   Letters + sentences tile variants on the Learn-to-type picker.
   Letters get a purple chip + monospace letter-spread text. Sentences
   get a teal chip + narrower font so longer strings fit the tile.
   ═══════════════════════════════════════════════════════════════════════ */

.diff-chip.diff-letters {
  background: #ede9fe;
  color: #6d28d9;
}
.diff-chip.diff-sentence {
  background: #ccfbf1;
  color: #0f766e;
}

/* Letter tiles: display the letter spread with mono spacing so kids can
   read each individual character. A-Z stretched gets a smaller font so
   "ABCDEFGHIJKLMNOPQRSTUVWXYZ" doesn't overflow. */
.typing-word-card-letters strong {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  letter-spacing: 0.15em;
  font-size: 14px;
  line-height: 1.4;
  word-break: break-all;
}

/* Sentence tiles: allow wrapping so long sentences fit the tile without
   ugly mid-word truncation. */
.typing-word-card-sentence {
  /* Each sentence takes a FULL row so it reads as one line at a glance.
     Was span-2 (two tiles per row); that crowded sentences together and
     wrapped long ones. Full-row + nowrap + ellipsis is cleaner. */
  grid-column: 1 / -1;
  flex-direction: row;  /* chip on the left, sentence inline to its right */
  align-items: center;
  gap: 10px;
  padding: 10px 16px;   /* tighter vertical since it's a single line */
}
.typing-word-card-sentence strong {
  font-size: 15px;
  line-height: 1.4;
  /* Single-line display — long sentences get "…" truncation in the
     tile, but the full text still plays back in the stage when picked. */
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  flex: 1 1 auto;
  min-width: 0;
}
.typing-word-card-sentence .diff-chip {
  flex: 0 0 auto;
  align-self: center;   /* override parent's flex-start */
}

/* Active state tint for each tier so the visual language stays consistent
   with the chip color. Small touch — inherits from base .active otherwise. */
.typing-word-card-letters.active {
  border-color: #7c3aed;
  background: #ede9fe;
  box-shadow: 0 0 0 3px rgba(124, 58, 237, 0.12);
}
.typing-word-card-sentence.active {
  border-color: #0d9488;
  background: #ccfbf1;
  box-shadow: 0 0 0 3px rgba(13, 148, 136, 0.12);
}


/* ═══════════════════════════════════════════════════════════════════════
   Custom practice panel — sits right of the keyboard on desktop, stacks
   below on narrow viewports. Lets the kid drill their own word/sentence
   without limits beyond the built-in letter/word/sentence tiles.
   ═══════════════════════════════════════════════════════════════════════ */

/* Custom practice now lives inside a tab panel — centered, single
   column, reasonable max-width. No more 260px sidebar next to the
   keyboard. */
.typing-custom {
  max-width: 520px;
  margin: 0 auto;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: var(--r-md);
  padding: 20px 24px;
  display: flex;
  flex-direction: column;
  gap: 14px;
}
.typing-custom-hint {
  font-size: 14px;
  color: var(--c-text-2);
  margin: 0;
  line-height: 1.5;
  text-align: center;
}
.typing-custom-form {
  display: flex;
  gap: 10px;
  margin: 0;
  flex-wrap: wrap;
}
.typing-custom-input {
  flex: 1 1 260px;
  padding: 10px 14px;
  font: inherit;
  font-size: 15px;
  border: 1px solid var(--c-border);
  border-radius: var(--r-sm);
  color: var(--c-text);
  background: var(--c-bg);
  transition: border-color var(--dur-fast) var(--ease);
  text-transform: uppercase;
  letter-spacing: 0.02em;
}
.typing-custom-input:focus {
  outline: none;
  border-color: var(--c-primary);
  box-shadow: 0 0 0 3px var(--c-primary-3);
}
/* Sentences input PRESERVES case visually — kids practise Shift by
   typing "Hello world" literally. The Words input still shows uppercase
   because its sanitiser force-caps the value anyway. */
#typing-custom-input-sentences {
  text-transform: none;
  letter-spacing: normal;
}
.typing-custom-start {
  flex: 0 0 auto;
  white-space: nowrap;
}
.typing-custom-error {
  color: var(--c-err-2);
  margin: 0;
  text-align: center;
}

/* Legacy wrap class — kept empty-shelled in case any view still has
   .kb-row-wrap around. Not used by learn_typing any more. */
@media (max-width: 560px) {
  .typing-custom {
    padding: 16px 18px;
  }
}


/* ═══════════════════════════════════════════════════════════════════════
   Tabbed picker above the keyboard on the Learn-to-type page.
   Three tabs: Letters / Words / Sentences — one panel visible at a
   time. Keeps the whole page to a single viewport without scrolling.
   ═══════════════════════════════════════════════════════════════════════ */

.typing-tabs {
  max-width: 1024px;
  margin: 6px auto 12px;   /* was 12px auto 20px */
}
.typing-tabs-bar {
  display: flex;
  gap: 6px;
  padding: 4px;
  background: var(--c-surface);
  border: 1px solid var(--c-border);
  border-radius: 999px;
  width: fit-content;
  margin: 0 auto 16px;
}
.typing-tab {
  -webkit-appearance: none;
  appearance: none;
  background: transparent;
  border: 0;
  padding: 8px 18px;
  font: inherit;
  font-size: 14px;
  font-weight: 600;
  color: var(--c-text-2);
  cursor: pointer;
  border-radius: 999px;
  transition: all var(--dur-fast) var(--ease);
}
.typing-tab:hover:not(.is-active) {
  color: var(--c-primary);
  background: var(--c-primary-3);
}
.typing-tab.is-active {
  background: var(--c-primary);
  color: #fff;
  box-shadow: 0 2px 6px -2px rgba(249, 115, 22, 0.45);
}
.typing-tab:focus-visible {
  outline: 2px solid var(--c-primary);
  outline-offset: 2px;
}

.typing-tab-panel {
  animation: typing-tab-in 180ms var(--ease) both;
}
@keyframes typing-tab-in {
  from { opacity: 0; transform: translateY(-3px); }
  to   { opacity: 1; transform: translateY(0); }
}

/* Mobile — tabs wrap, stay readable. */
@media (max-width: 560px) {
  .typing-tabs-bar {
    width: 100%;
    justify-content: space-between;
  }
  .typing-tab {
    flex: 1 1 0;
    padding: 8px 10px;
    font-size: 13px;
  }
}


/* ═══════════════════════════════════════════════════════════════════════
   Tabs panel collapse — auto-hides the tile grid once the kid starts
   typing (keyboard-focused mode), "+" button on the tab bar brings it
   back when they want to pick again.
   ═══════════════════════════════════════════════════════════════════════ */

/* Toggle pill — sits at the right end of the tab bar. Same pill
   aesthetic as the tabs, but non-selectable so it never looks
   "active". */
.typing-tabs-toggle {
  -webkit-appearance: none;
  appearance: none;
  border: 0;
  background: transparent;
  margin-left: 6px;
  padding: 0;
  width: 32px;
  height: 32px;
  border-radius: 999px;
  font: inherit;
  font-size: 16px;
  font-weight: 700;
  color: var(--c-text-3);
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  transition: all var(--dur-fast) var(--ease);
}
.typing-tabs-toggle:hover {
  background: var(--c-primary-3);
  color: var(--c-primary);
}
.typing-tabs-toggle-icon {
  line-height: 1;
}

/* Collapsed state — hide all panels. Tab bar stays visible so kid can
   still switch category without re-expanding first. */
.typing-tabs.is-collapsed .typing-tab-panel {
  display: none;
}


/* ═══════════════════════════════════════════════════════════════════════
   Saved-words tiles inside the "Your word" tab — match the built-in
   picker-tile look but carry a gold "⭐" chip and a small × delete
   button in the top-right corner. Deletes don't trigger tile click
   (stopPropagation in the JS handler).
   ═══════════════════════════════════════════════════════════════════════ */

.typing-saved-head {
  font-size: 15px;
  margin: 0;
}
.typing-saved-hint {
  margin: 4px 0 10px;
}
.typing-saved-grid {
  /* reuses .typing-picker layout */
}
.typing-saved-empty {
  text-align: center;
  padding: 20px;
  border: 1px dashed var(--c-border);
  border-radius: var(--r-md);
  margin: 0;
}

/* ⭐ yellow chip — own tier, distinct from letters/words/sentences. */
.diff-chip.diff-saved {
  background: #fef3c7;
  color: #92400e;
}

.typing-word-card-saved {
  position: relative;  /* so .typing-saved-del can absolute-position */
  padding-right: 36px; /* reserve space for the × corner button */
}

.typing-saved-del {
  position: absolute;
  top: 6px;
  right: 6px;
  width: 26px;
  height: 26px;
  padding: 0;
  border: 1px solid var(--c-border);
  border-radius: 50%;
  background: var(--c-surface);
  color: var(--c-text-3);
  font-size: 18px;
  font-weight: 700;
  line-height: 1;
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  /* Always visible — hover-to-reveal is the wrong default for a kid app
     (touch devices can't hover, and it hides the affordance). Subtle at
     rest, red on hover so it's obvious what it does. */
  transition: all var(--dur-fast) var(--ease);
  z-index: 2;
}
.typing-saved-del:hover,
.typing-saved-del:focus-visible {
  background: var(--c-err-3);
  border-color: var(--c-err-br);
  color: var(--c-err-2);
  transform: scale(1.08);
  outline: none;
}

.typing-word-card-saved.active {
  border-color: #d97706;
  background: #fef3c7;
  box-shadow: 0 0 0 3px rgba(217, 119, 6, 0.14);
}


/* ═══════════════════════════════════════════════════════════════════════
   Editable-tile controls — small ✎ and × buttons on every default tile
   (Letters / Words / Sentences). Always visible, subtle at rest, colored
   on hover so the affordance is discoverable without hunting.
   ═══════════════════════════════════════════════════════════════════════ */

/* The default tiles now need room on the right for two small buttons. */
.typing-picker-editable .typing-word-card.is-default {
  position: relative;
  padding-right: 56px;   /* space for ✎ + × stacked horizontally */
}
/* Letter tiles don't carry edit/delete controls (A–Z are universal), so
   reclaim the reserved 56px padding — keeps single letters visually
   centred instead of shoved left. */
.typing-picker-editable .typing-word-card-letters.is-default {
  padding-right: 14px;
}

.tile-ctrl {
  position: absolute;
  top: 6px;
  width: 24px;
  height: 24px;
  padding: 0;
  border: 1px solid var(--c-border);
  border-radius: 50%;
  background: var(--c-surface);
  color: var(--c-text-3);
  font-size: 13px;
  font-weight: 700;
  line-height: 1;
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  transition: opacity var(--dur-fast) var(--ease), background var(--dur-fast) var(--ease),
              color var(--dur-fast) var(--ease), border-color var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
  z-index: 2;
  /* Hidden at rest — revealed on tile hover / keyboard focus. */
  opacity: 0;
  pointer-events: none;
  user-select: none;
}
.tile-ctrl-edit { right: 34px; }
.tile-ctrl-del  { right: 6px; font-size: 16px; }

/* Reveal controls when the parent tile is hovered or contains focus
   (keyboard tab into the span hits focus-within). */
.typing-word-card:hover .tile-ctrl,
.typing-word-card:focus-within .tile-ctrl,
.typing-word-card.is-editing .tile-ctrl {
  opacity: 1;
  pointer-events: auto;
}

/* Touch devices have no hover — always show so kids on tablets can
   still edit/delete. */
@media (hover: none) {
  .tile-ctrl {
    opacity: 1;
    pointer-events: auto;
  }
}

.tile-ctrl-edit:hover,
.tile-ctrl-edit:focus-visible {
  background: var(--c-accent-3);
  border-color: var(--c-accent-br);
  color: var(--c-accent-2);
  transform: scale(1.08);
  outline: none;
}
.tile-ctrl-del:hover,
.tile-ctrl-del:focus-visible {
  background: var(--c-err-3);
  border-color: var(--c-err-br);
  color: var(--c-err-2);
  transform: scale(1.08);
  outline: none;
}

/* Edit-mode input sits over the tile. */
.tile-edit-input {
  position: absolute;
  left: 14px;
  right: 56px;
  bottom: 14px;
  padding: 4px 8px;
  font: inherit;
  font-size: 16px;
  font-weight: 700;
  background: var(--c-surface);
  border: 2px solid var(--c-primary);
  border-radius: var(--r-sm);
  outline: none;
  text-transform: uppercase;
  letter-spacing: 0.02em;
  color: var(--c-text);
  z-index: 3;
}
.typing-word-card.is-editing {
  cursor: default;
}
/* Sentences preserve real case during inline edit — "Hello, world!" must
   display exactly as typed, not force-capped to "HELLO, WORLD!". Words
   and Letters tiles keep the uppercase display above because their data
   is genuinely all-caps. */
.typing-word-card-sentence .tile-edit-input {
  text-transform: none;
  letter-spacing: normal;
  font-weight: 500;
}

/* Reset-defaults button below each editable picker. */
.typing-picker-reset-wrap {
  text-align: center;
  margin-top: 14px;
}
.typing-reset-btn {
  -webkit-appearance: none;
  appearance: none;
  border: 1px dashed var(--c-border);
  background: transparent;
  padding: 6px 14px;
  border-radius: 999px;
  font: inherit;
  font-size: 12px;
  font-weight: 600;
  color: var(--c-text-3);
  cursor: pointer;
  transition: all var(--dur-fast) var(--ease);
}
.typing-reset-btn:hover {
  border-color: var(--c-primary-br);
  color: var(--c-primary);
  border-style: solid;
  background: var(--c-primary-3);
}


/* ═══════════════════════════════════════════════════════════════════════
   Inline "+ Add your own" bar — sits above the Words grid. Compact
   single-row form; kid-added entries appear as ⭐ tiles at the end of
   the grid after saving.
   ═══════════════════════════════════════════════════════════════════════ */

.typing-addown {
  max-width: 560px;
  margin: 0 auto 16px;
}
.typing-addown-form {
  display: flex;
  gap: 10px;
  flex-wrap: wrap;
  align-items: stretch;
}
.typing-addown-form .typing-custom-input {
  flex: 1 1 260px;
  /* Other styling inherited from the .typing-custom-input class. */
}

/* User-added tile — inherits grid layout; ⭐ tint + edit/delete buttons
   handled by .diff-saved and .tile-ctrl-* classes. Needs the same
   right-padding as other editable tiles so the controls don't overlap. */
.typing-word-card-own {
  position: relative;
  padding-right: 56px;
}
.typing-word-card-own.active {
  border-color: #d97706;
  background: #fef3c7;
  box-shadow: 0 0 0 3px rgba(217, 119, 6, 0.14);
}
