/* ui.css - child UI look: Start, Home, HUD holds, tray, bubbles (docs/ui-spec.md 4-6). Owner: ui-designer (L5).
 * Geometry (sizes, insets, tray grid) is layout.css (mobile-spec). Tokens only; no inline styles: JS sets classes and CSSOM props. */

/* ---- screens: sky to meadow, soft hills and clouds (decor only) ---- */
.screen {
  position: absolute; inset: 0; z-index: calc(var(--z-hud) + 100);
  background:
    radial-gradient(56vmax 12vmax at 10% 104%, var(--ground) 99%, #0000),
    radial-gradient(72vmax 16vmax at 88% 106%, var(--ground-far) 99%, #0000),
    linear-gradient(var(--c-home-top), var(--c-home-bottom));
  opacity: 0; visibility: hidden;
  transition: opacity var(--dur-base) var(--ease-in-out), visibility 0s linear var(--dur-base);
  display: grid; place-items: center;
  pointer-events: none; /* a fading screen never swallows the next press */
}
.screen::before {
  content: ""; position: absolute; inset: 0; z-index: -1; pointer-events: none;
  --cl: radial-gradient(closest-side, #fffd 96%, #fff0);
  background: /* two clouds, three puffs each, offsets in px so they stay joined at every width */
    var(--cl) 12% 8% / 120px 40px, var(--cl) calc(12% + 22px) calc(8% - 18px) / 56px 52px, var(--cl) calc(12% - 26px) calc(8% - 8px) / 40px 34px,
    var(--cl) 84% 14% / 140px 44px, var(--cl) calc(84% + 18px) calc(14% - 20px) / 66px 60px, var(--cl) calc(84% - 34px) calc(14% - 10px) / 46px 40px;
  background-repeat: no-repeat;
}
.app[data-screen="start"] .screen-start, .app[data-screen="home"] .screen-home { opacity: 1; visibility: visible; transition-delay: 0s; pointer-events: auto; }
.app:not([data-screen="scene"]) :is(.stage, .hud, .bubbles) { visibility: hidden; }

/* ---- toy buttons: chunky outline, offset shadow; press sinks, hover lifts (mouse only) ---- */
.theme, .hold, .tile, .tray-arrow > span {
  border: var(--stroke-ui) solid var(--c-line); box-shadow: var(--shadow-toy);
  transition: transform var(--dur-instant) var(--ease-out), box-shadow var(--dur-instant) var(--ease-out);
}
.theme:active, .tile:active, .tray-arrow:active > span { transform: translateY(3px) scale(var(--scale-press)); box-shadow: var(--shadow-toy-pressed); }
@media (hover: hover) and (pointer: fine) {
  .theme:hover, .hold:hover, .tile:hover, .tray-arrow:hover > span { transform: translateY(-2px); box-shadow: var(--shadow-toy-raised); }
}

/* ---- Start ---- */
.screen-start { padding: var(--keep-t) var(--keep-r) var(--keep-b) var(--keep-l); }
.play {
  --d: clamp(128px, 32vmin, 200px);
  position: relative; isolation: isolate; width: var(--d); height: var(--d); border-radius: var(--radius-round);
  display: grid; place-items: center;
  animation: breathe var(--dur-breathe) var(--ease-in-out) infinite;
}
.play::before { /* soft white halo around the art disc */
  content: ""; position: absolute; inset: -9%; z-index: -1; border-radius: inherit;
  background: #ffffffb3; box-shadow: 0 0 0 4px #ffffff59;
}
.play-icon, .play-icon > svg { width: 100%; height: 100%; display: block; }
.play-icon > svg { filter: drop-shadow(0 5px 0 rgb(58 47 74 / 0.28)); transition: filter var(--dur-instant) var(--ease-out); }
.app:not([data-screen="start"]) .play { animation: none; } /* H4: a hidden screen's infinite animation keeps the compositor and main frames running at 60 Hz */
.play:active { transform: translateY(3px) scale(var(--scale-press)); animation: none; }
.play:active .play-icon > svg { filter: drop-shadow(0 1px 0 rgb(58 47 74 / 0.28)); }
@keyframes breathe { 50% { transform: scale(var(--scale-breathe)); } }

/* ---- Home: 3 x 3 in every orientation (mobile-spec 8.2) ---- */
.screen-home { padding: calc(var(--keep-t) + 76px) var(--keep-r) var(--keep-b) var(--keep-l); }
.home-grid {
  --cell: min(var(--size-theme-max), calc((100vw - var(--keep-l) - var(--keep-r) - 2 * var(--gap-theme)) / 3),
              calc((100dvh - var(--keep-t) - 76px - var(--keep-b) - 2 * var(--gap-theme)) / 3));
  display: grid; grid-template-columns: repeat(3, var(--cell)); grid-auto-rows: var(--cell); gap: var(--gap-theme);
  align-content: center; justify-content: center;
}
@media (orientation: landscape) {
  .screen-home { padding: var(--keep-t) calc(var(--keep-r) + 76px) var(--keep-b) calc(var(--keep-l) + 76px); }
  .home-grid { --cell: min(var(--size-theme-max), calc((100dvh - var(--keep-t) - var(--keep-b) - 2 * var(--gap-theme)) / 3),
                           calc((100vw - var(--keep-l) - var(--keep-r) - 152px - 2 * var(--gap-theme)) / 3)); }
}
.theme { padding: 8%; border-radius: var(--radius-l); display: grid; place-items: center; background: var(--bk, var(--c-face)); }
.theme > svg { width: 100%; height: 100%; }
.theme[data-theme="farm"] { --bk: var(--c-theme-farm); }
.theme[data-theme="animals"] { --bk: var(--c-theme-animals); }
.theme[data-theme="cars"] { --bk: var(--c-theme-cars); }
.theme[data-theme="parcels"] { --bk: var(--c-theme-parcels); }
.theme[data-theme="city"] { --bk: var(--c-theme-city); }
.theme[data-theme="village"] { --bk: var(--c-theme-village); }
.theme[data-theme="nature"] { --bk: var(--c-theme-nature); }
.theme[data-theme="abc"] { --bk: var(--c-theme-abc); }
.theme[data-theme="shapes"] { --bk: var(--c-theme-shapes); }
.theme.is-opening { animation: bounce 400ms var(--ease-bounce) both; box-shadow: var(--shadow-toy), var(--shadow-glow); }
.theme.is-soon { animation: wiggle var(--dur-slow) var(--ease-in-out), twinkle var(--dur-slow) var(--ease-in-out); }
@keyframes bounce { 50% { transform: scale(1.12); } }
@keyframes wiggle { 20%, 60% { rotate: var(--wiggle-angle); } 40%, 80% { rotate: calc(-1 * var(--wiggle-angle)); } }
@keyframes twinkle { 50% { box-shadow: var(--shadow-toy), var(--shadow-glow); } }

/* ---- HUD hold buttons ---- */
.hold { background: var(--c-face); touch-action: none; }
.hold-icon { width: var(--size-hold-icon); height: var(--size-hold-icon); display: block; }
.hold-icon > svg { width: 100%; height: 100%; }
.hold .ring { position: absolute; inset: -11px; opacity: 0; pointer-events: none; transition: opacity var(--dur-fast) var(--ease-out); }
.hold .ring > svg { width: 100%; height: 100%; }
.hold .ring-fill { transition: stroke-dashoffset var(--dur-fast) var(--ease-out); }
.hold.is-holding .ring-fill { transition: none; } /* JS writes --hold every frame while held */
.hold:is(.is-holding, .is-hinting, .is-done) { box-shadow: var(--shadow-toy-pressed); transform: translateY(3px) scale(var(--scale-press)); }
.hold:is(.is-holding, .is-hinting, .is-done) .ring { opacity: 1; }
.hold.is-hinting { animation: wiggle var(--dur-slow) var(--ease-in-out); }
.hold-clear[data-sweepback="true"] { box-shadow: var(--shadow-toy), var(--shadow-glow); animation: glow var(--dur-pulse) var(--ease-in-out) infinite alternate; }
@keyframes glow { to { box-shadow: var(--shadow-toy), var(--shadow-glow-big); } }

/* ---- keyboard focus: blue ring + white halo, outside the hold ring ---- */
:is(.hold, .tile, .tray-arrow, .theme, .play):focus-visible {
  outline: var(--focus-width) solid var(--c-focus); outline-offset: var(--focus-offset);
  box-shadow: var(--shadow-toy), 0 0 0 calc(var(--focus-offset) + 1px) var(--c-focus-halo);
}
.hold:focus-visible { outline-offset: calc(var(--ring-width) + var(--ring-gap) + var(--stroke-ui) + var(--focus-offset)); }
/* H1: the hold ring sits over the scene, where blue alone is ~1.8:1 on the night sky: white halos on both sides of the outline */
.hold:focus-visible::after {
  content: ""; position: absolute; pointer-events: none; border-radius: var(--radius-round);
  inset: calc(-1 * (var(--stroke-ui) + var(--ring-width) + var(--ring-gap) + var(--stroke-ui) + var(--focus-offset))); /* the outline's inner edge */
  box-shadow: inset 0 0 0 2px var(--c-focus-halo), 0 0 0 var(--focus-width) var(--c-focus), 0 0 0 calc(var(--focus-width) + 2px) var(--c-focus-halo);
}
.tray-arrow:focus-visible { border-radius: var(--radius-round); outline-offset: calc(var(--focus-offset) - (var(--tray-cell) - var(--size-tray-arrow)) / 2); box-shadow: none; }
.play:focus-visible { outline-offset: calc(var(--d) * 0.09 + var(--focus-offset)); box-shadow: none; }

/* ---- tray ---- */
.tray { background: linear-gradient(var(--c-paper) 40%, var(--c-paper-2)); }
.tray.is-drop { background: var(--c-paper-2); box-shadow: inset 0 var(--stroke-ui) 0 var(--c-line), inset 0 0 0 6px var(--c-glow); }
.tile { padding: 8px; background: var(--c-face); border-radius: var(--radius-tile); touch-action: none; }
.tile > svg { width: 100%; height: 100%; pointer-events: none; }
.tile-care { border-radius: var(--radius-round); background: var(--c-basket); border-style: dashed; border-color: var(--c-basket-line); }
.tile.is-asked { box-shadow: var(--shadow-toy), var(--shadow-glow); animation: wiggle var(--dur-slow) var(--ease-in-out); }
.tile.is-twinkle { animation: wiggle var(--dur-slow) var(--ease-in-out), twinkle 1s var(--ease-in-out); }
.tray-gap { pointer-events: none; }
.tray-arrow { touch-action: none; }
.tray-arrow > span { display: grid; place-items: center; background: var(--c-face); border-radius: var(--radius-round); pointer-events: none; }
.tray-arrow svg { width: 28px; height: 28px; pointer-events: none; }
.tray-arrow[data-dir="left"] svg { transform: scaleX(-1); } /* Next and Back point outwards, away from the tiles (child-educator M2); tray.js sets data-dir */

/* ---- bubbles and hearts (bubble art 128 x 116, icon slot x36 y16 w56 h56) ---- */
.bubbles { position: absolute; inset: 0; z-index: var(--z-bubbles); pointer-events: none; }
.bubble {
  position: absolute; width: var(--size-bubble); height: calc(var(--size-bubble) * 116 / 128);
  translate: -50% -100%; transform-origin: 10% 95%;
  filter: drop-shadow(0 3px 0 rgb(58 47 74 / 0.2));
  animation: bubble-in var(--dur-base) var(--ease-bounce) both;
}
.bubble > svg { position: absolute; inset: 0; width: 100%; height: 100%; }
.bubble > .bubble-icon { inset: 13.8% auto auto 28.1%; width: 43.75%; height: 48.3%; }
.hearts { position: absolute; display: flex; gap: 4px; translate: -50% -100%; animation: hearts var(--dur-hearts) var(--ease-out) both; }
.hearts > svg { width: var(--size-heart); height: var(--size-heart); }
@keyframes bubble-in { from { opacity: 0; scale: 0.6; } }
@keyframes hearts { 0% { opacity: 0; } 15% { opacity: 1; } 100% { opacity: 0; margin-top: -8px; } }
@keyframes fade { 0%, 100% { opacity: 0; } 15% { opacity: 1; } }
@keyframes fade-in { from { opacity: 0; } }

/* ---- reduced motion: no scale, rotation or travel; glows hold steady; fades stay ---- */
html[data-reduced-motion] :is(.play, .theme.is-opening, .hold-clear[data-sweepback="true"]) { animation: none; }
html[data-reduced-motion] .bubble { animation-name: fade-in; }
html[data-reduced-motion] .hearts { animation-name: fade; }
html[data-reduced-motion] :is(.theme, .hold, .tile, .tray-arrow > span):hover { transform: none; }
