/* =====================================================================
   RIDDLE KINGDOM — THEME
   A game by Aadvika

   The bones: colour, type, spacing, and the three layers of background
   that sit behind everything. Nothing in here knows about a screen or
   a button — that is app.css.

   Design notes
   - Shape    : the game is a phone. On a laptop it stays a phone,
                centred, because that is what it was drawn as.
   - Colour   : a deep violet night. One brand pink for anything that
                moves the player forward, and never for anything else.
   - Tint     : --h is the live subject hue. Choose Science and the
                whole app leans green; choose Math and it leans blue.
                One variable, no extra stylesheets.
   ===================================================================== */

:root{
  /* ---- the live subject hue, moved by JS ---- */
  --h: 282;

  /* ---- text scale ----
     One number, set from the profile, that every type size is multiplied
     by. A child who needs bigger text should not have to zoom the browser
     and fight the layout; this grows the type and lets the layout breathe
     around it. 1 normal, 1.12 large, 1.26 larger. */
  --scale: 1;

  --tint:    hsl(var(--h) 88% 64%);
  --tint-2:  hsl(calc(var(--h) + 34) 88% 60%);
  --tint-d:  hsl(var(--h) 70% 30%);
  --tint-glow: hsl(var(--h) 96% 62% / .40);

  /* ---- the night ---- */
  --void:    #140626;
  --void-2:  #1D0937;
  --deep:    #0C0318;

  /* ---- surfaces, lightest to darkest ---- */
  --surface:    #2A1150;
  --surface-2:  #33165F;
  --surface-3:  #3D1B71;
  --surface-lo: #1F0C3C;

  /* ---- brand pink : forward motion, and nothing else ---- */
  --pink:    #FF2E93;
  --pink-2:  #FF5FA8;
  --pink-d:  #B00D5F;
  --pink-glow: rgba(255,46,147,.45);

  /* ---- the supporting cast ---- */
  --violet:  #8B3FE8;
  --violet-d:#5B21A8;
  --gold:    #FFC64B;
  --gold-d:  #C98A0C;
  --win:     #2ED573;
  --win-d:   #12833F;
  --lose:    #FF5B7F;
  --gem:     #B26BFF;

  /* ---- ink ---- */
  --text:    #FFFFFF;
  --text-2:  #E4D9FA;
  --muted:   #B3A2D6;
  --muted-2: #8574AC;

  /* ---- lines and glazes ---- */
  --stroke:   rgba(255,255,255,.10);
  --stroke-2: rgba(255,255,255,.18);
  --stroke-3: rgba(255,255,255,.30);
  --fill:     rgba(255,255,255,.06);
  --fill-2:   rgba(255,255,255,.11);

  /* ---- radius ---- */
  --r-full: 999px;
  --r-xl:   28px;
  --r-lg:   22px;
  --r-md:   16px;
  --r-sm:   12px;
  --r-xs:   9px;

  /* ---- type ---- */
  --display: "Fredoka", "Trebuchet MS", "Segoe UI", sans-serif;
  --body:    "Nunito", "Trebuchet MS", "Segoe UI", sans-serif;

  /* ---- motion ---- */
  --ease:   cubic-bezier(.22,.9,.24,1);
  --spring: cubic-bezier(.2,.9,.28,1.5);

  /* ---- layout ----
     --phone is the column the whole app lives in. It grows a little on
     bigger screens; --wide is the extra room the quiz alone is allowed
     to take on a desktop, where it becomes two columns.
     --peep drives every part of the peephole, so one value resizes the
     ring, the window, the drifting orbs and the number together. */
  --phone:  460px;
  --wide:   880px;
  --peep:   82px;
  --gutter: 16px;
  --nav-h:  76px;
  --safe-b: env(safe-area-inset-bottom, 0px);
}

/* =====================================================================
   RESET
   ===================================================================== */
*{ box-sizing: border-box; margin: 0; padding: 0; }
html{ -webkit-text-size-adjust: 100%; }

body{
  min-height: 100vh;
  min-height: 100dvh;
  font-family: var(--body);
  font-weight: 600;
  color: var(--text);
  background: var(--deep);
  overflow-x: hidden;
  -webkit-tap-highlight-color: transparent;
}

button, input, select{ font: inherit; color: inherit; }
button{ background: none; border: none; cursor: pointer; }
img{ max-width: 100%; display: block; }

:focus-visible{
  outline: 3px solid var(--gold);
  outline-offset: 3px;
  border-radius: var(--r-xs);
}

/* Screen readers only — used for the live region that announces the
   verdict, so the game is followable without seeing the colour change. */
.sr-only{
  position: absolute; width: 1px; height: 1px;
  padding: 0; margin: -1px; overflow: hidden;
  clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}

/* =====================================================================
   THE NIGHT — three fixed layers behind the app

   0  drifting coloured light, blurred to a haze
   1  stars, twinkling slowly
   2  fine grain and a vignette, so nothing looks like flat CSS
   ===================================================================== */
.sky{
  position: fixed; inset: 0; z-index: 0; pointer-events: none;
  background:
    radial-gradient(120% 80% at 50% 0%,  var(--void-2), transparent 60%),
    radial-gradient(100% 70% at 50% 100%, #240D45, transparent 62%),
    linear-gradient(180deg, var(--void), var(--deep));
}

.haze{
  position: fixed; inset: -30%; z-index: 0;
  filter: blur(100px);
  opacity: .55;
  pointer-events: none;
  transition: opacity .6s ease;
}
.blob{ position: absolute; border-radius: 50%; mix-blend-mode: screen; }
.b1{
  width: 54vmax; height: 54vmax; left: -10%; top: -14%;
  background: hsl(var(--h) 88% 44%);
  animation: drift1 34s var(--ease) infinite alternate;
}
.b2{
  width: 46vmax; height: 46vmax; right: -12%; top: 20%;
  background: hsl(calc(var(--h) + 58) 86% 42%);
  animation: drift2 40s var(--ease) infinite alternate;
}
.b3{
  width: 48vmax; height: 48vmax; left: 18%; bottom: -22%;
  background: hsl(calc(var(--h) + 300) 82% 40%);
  animation: drift3 46s var(--ease) infinite alternate;
}
@keyframes drift1{ to{ transform: translate3d(10vw, 8vh, 0)   scale(1.18) } }
@keyframes drift2{ to{ transform: translate3d(-12vw, 12vh, 0) scale(.86) } }
@keyframes drift3{ to{ transform: translate3d(8vw, -12vh, 0)  scale(1.14) } }

.stars{
  position: fixed; inset: 0; z-index: 1; pointer-events: none;
  background:
    radial-gradient(1.6px 1.6px at 12% 22%, #fff9, transparent),
    radial-gradient(1.3px 1.3px at 78% 14%, #fff8, transparent),
    radial-gradient(1.7px 1.7px at 33% 71%, #fff9, transparent),
    radial-gradient(1.2px 1.2px at 62% 46%, #fff7, transparent),
    radial-gradient(1.5px 1.5px at 88% 78%, #fff8, transparent),
    radial-gradient(1.3px 1.3px at 46% 9%,  #fff7, transparent),
    radial-gradient(1.5px 1.5px at 8%  62%, #fff8, transparent),
    radial-gradient(1.2px 1.2px at 95% 40%, #fff7, transparent),
    radial-gradient(1.6px 1.6px at 24% 92%, #fff8, transparent),
    radial-gradient(1.3px 1.3px at 69% 88%, #fff7, transparent),
    radial-gradient(1.4px 1.4px at 54% 63%, #fff8, transparent),
    radial-gradient(1.2px 1.2px at 40% 34%, #fff6, transparent),
    radial-gradient(1.5px 1.5px at 84% 58%, #fff7, transparent),
    radial-gradient(1.3px 1.3px at 17% 44%, #fff8, transparent);
  animation: twinkle 7s ease-in-out infinite;
}
@keyframes twinkle{ 0%,100%{ opacity:.9 } 50%{ opacity:.45 } }

.grain{
  position: fixed; inset: 0; z-index: 2; pointer-events: none;
  opacity: .045;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='180' height='180'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.9' numOctaves='3'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
}
.vignette{
  position: fixed; inset: 0; z-index: 2; pointer-events: none;
  background: radial-gradient(120% 100% at 50% 36%, transparent 44%, #06020Ccc 100%);
}

#confetti{ position: fixed; inset: 0; z-index: 90; pointer-events: none; }

/* =====================================================================
   TYPE
   ===================================================================== */
.h1{
  font-family: var(--display);
  font-weight: 700;
  font-size: 25px;
  line-height: 1.15;
  letter-spacing: -.02em;
}
.h2{
  font-family: var(--display);
  font-weight: 600;
  font-size: 19px;
  letter-spacing: -.01em;
}
.h3{
  font-family: var(--display);
  font-weight: 600;
  font-size: 15.5px;
}
.eyebrow{
  font-family: var(--display);
  font-weight: 600;
  font-size: 11px;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--muted);
}
.lede{
  font-size: 14.5px;
  line-height: 1.6;
  color: var(--text-2);
  font-weight: 600;
}
.small{ font-size: 12.5px; color: var(--muted); font-weight: 700; }

/* =====================================================================
   READING AND SEEING

   Three settings, applied to the root element. They exist because the
   game should not stop being playable for a child who needs bigger text,
   a plainer letter shape, or more contrast — and because Fredoka, which
   makes this game look like a game, is genuinely tiring for some readers.

   All three are settings rather than a second stylesheet, for the same
   reason the subject tint is one variable: two stylesheets drift apart.
   ===================================================================== */

/* ---- bigger text ----
   Everything that matters is sized in px, so the scale is applied by
   growing the root font size and having the layout follow. The type
   variables below are what actually move. */
html{ font-size: calc(100% * var(--scale)); }

/* Type set in px does not follow a root font-size, so the sizes that
   carry the game are restated in em at the larger scales. Only the ones
   a child actually reads — a 10px label growing would break the layout
   for no benefit. */
:root[style*="--scale: 1.12"] .qtext,
:root[style*="--scale: 1.26"] .qtext,
:root[style*="--scale: 1.12"] .opt-text,
:root[style*="--scale: 1.26"] .opt-text,
:root[style*="--scale: 1.12"] .why-body,
:root[style*="--scale: 1.26"] .why-body,
:root[style*="--scale: 1.12"] .lede,
:root[style*="--scale: 1.26"] .lede{
  font-size: calc(1em * var(--scale));
  line-height: 1.55;
}

/* ---- plainer letters ----
   A rounded display face is charming and it is not easy for everybody.
   This swaps to a plain, wide, high-legibility stack and opens up the
   spacing, which is most of what helps. */
:root.plain-font{
  --display: "Verdana", "DejaVu Sans", "Tahoma", "Segoe UI", sans-serif;
  --body:    "Verdana", "DejaVu Sans", "Tahoma", "Segoe UI", sans-serif;
}
:root.plain-font body{
  letter-spacing: .012em;
  word-spacing: .06em;
}
:root.plain-font .qtext,
:root.plain-font .opt-text,
:root.plain-font .why-body,
:root.plain-font .rev-why{
  letter-spacing: .022em;
  line-height: 1.62;
}
/* the wordmark is set very tight, which a wide font cannot survive */
:root.plain-font .wordmark{ letter-spacing: -.01em; font-size: clamp(30px, 8.5vw, 42px); }

/* ---- stronger contrast ----
   Brightens the ink and quiets the moving light behind it. The drifting
   haze is lovely and it is the single biggest enemy of contrast in this
   design, so it is what goes. */
:root.hi-contrast{
  --text:    #FFFFFF;
  --text-2:  #FFFFFF;
  --muted:   #E6DEF7;
  --muted-2: #C9BEE6;
  --stroke:   rgba(255,255,255,.22);
  --stroke-2: rgba(255,255,255,.34);
  --stroke-3: rgba(255,255,255,.5);
  --surface:    #241046;
  --surface-2:  #2C1355;
  --surface-3:  #351866;
  --surface-lo: #170A2E;
  --void:    #0B0418;
  --void-2:  #140726;
  --deep:    #06010E;
}
:root.hi-contrast .haze{ opacity: .12; }
:root.hi-contrast .grain{ opacity: .02; }
:root.hi-contrast .stars{ opacity: .5; }
:root.hi-contrast .vignette{ display: none; }
:root.hi-contrast .qcard,
:root.hi-contrast .opt,
:root.hi-contrast .panel{ border-color: var(--stroke-2); }
:root.hi-contrast .small,
:root.hi-contrast .mode-note,
:root.hi-contrast .daily-note,
:root.hi-contrast .badge-desc{ color: var(--muted); }


/* =====================================================================
   MOTION — honoured everywhere, one place to switch it off
   ===================================================================== */
@media (prefers-reduced-motion: reduce){
  *, *::before, *::after{
    animation-duration: .01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: .01ms !important;
    scroll-behavior: auto !important;
  }
  .haze{ opacity: .4; }
}
