/* The campfire (campfire.js): the base, the flame tongues standing on its embers, the near half of the base over their feet,
   a few sparks, and the warm glow breathing with the fire (--cf-heat, 0…1, set on every frame). */
.cf { position: relative; inline-size: var(--fw, 140px); aspect-ratio: 640 / 376; isolation: isolate; }
.cf-defs { position: absolute; inline-size: 0; block-size: 0; overflow: hidden; }
.cf-base, .cf-front { position: absolute; inset: 0; inline-size: 100%; block-size: 100%; object-fit: contain; pointer-events: none; -webkit-user-drag: none; }
/* the near half: the front logs' ends and the front stones, over the flames' feet */
.cf-front { z-index: 3; clip-path: inset(var(--cf-anchor, 58%) 0 0 0); }
.cf-flames { position: absolute; inset: 0; z-index: 2; pointer-events: none; container-type: size; }
/* a tongue stands on the embers; its height is a share of the base's width (--h, a number); it is placed in the drawing's
   own coordinates (left, from the centre), as the picture is not mirrored in Hebrew */
.cf-tongue { position: absolute; inset-block-end: calc(100% - var(--cf-anchor, 58%) - 4%); left: calc(50% + var(--x, 0%));
  block-size: calc(var(--h, 60) * 1cqw); inline-size: auto; max-inline-size: none; transform: translateX(-50%); transform-origin: 50% 100%;
  will-change: transform, opacity; -webkit-user-drag: none; }

/* the glow: under everything, warm, breathing with the flames */
.cf-glow { position: absolute; inset: -40% -35% -10%; z-index: 0; border-radius: 50%; pointer-events: none;
  background: radial-gradient(closest-side at 50% 55%, rgba(255, 190, 90, calc(.38 + var(--cf-heat, .5) * .22)), rgba(255, 120, 30, calc(.12 + var(--cf-heat, .5) * .1)) 55%, transparent);
  filter: blur(8px); }
:root[data-theme="dark"] .cf-glow { mix-blend-mode: screen; }
@media (prefers-color-scheme: dark) { :root:not([data-theme="light"]) .cf-glow { mix-blend-mode: screen; } }

/* a few sparks, rising and going out now and then */
.cf-sparks { position: absolute; inset: 0; z-index: 4; pointer-events: none; }
.cf-sparks i { position: absolute; left: calc(50% + var(--sx, 0%)); inset-block-end: calc(100% - var(--cf-anchor, 58%) + 30%); inline-size: 3px; block-size: 3px;
  border-radius: 50%; background: #ffcf6b; box-shadow: 0 0 6px 1px rgba(255, 170, 60, .8); opacity: 0;
  animation: cf-spark 3.8s ease-out infinite; animation-delay: var(--sd, 0s); }
@keyframes cf-spark { 0% { transform: translate(0, 0) scale(1); opacity: 0; } 8% { opacity: .95; } 60% { opacity: .5; } 100% { transform: translate(6px, -46px) scale(.4); opacity: 0; } }
.cf.still .cf-sparks { display: none; }
@media (prefers-reduced-motion: reduce) { .cf-sparks { display: none; } }

/* the roulette (a long press on the fire, index.html): while the ring spins the fire burns brighter; when it stops, a burst of
   sparks leaps up and the cushion it landed on glows warm for a few seconds (.wheel-item.chosen) */
.cf-roll .cf-glow { animation: cf-roar .5s ease-in-out infinite alternate; }
@keyframes cf-roar { to { scale: 1.12; opacity: .85; } }
.cf-win .cf-sparks i { animation: cf-burst 1.1s cubic-bezier(.2, .7, .3, 1) both; animation-delay: calc(var(--sd, 0s) * .06); }
@keyframes cf-burst { 0% { transform: translate(0, 0) scale(1.4); opacity: 0; } 10% { opacity: 1; }
  100% { transform: translate(calc(var(--sx, 0%) * .9), -78px) scale(.3); opacity: 0; } }
/* The chosen cushion glows. The glow on the picture stays still (a filter that changes is drawn again every frame); the
   pulse is a warm halo behind it that only breathes in opacity and scale (vision batch 16: transform and opacity only). */
:root:root .wheel-item.chosen .pillow img {   /* (:root twice: above the night filter in index.html) */
   filter: drop-shadow(0 0 8px rgba(255, 176, 70, .85)) drop-shadow(0 0 18px rgba(255, 140, 40, .4)); }
.wheel-item.chosen .pillow::before { content: ''; position: absolute; inset: -16%; z-index: -1; border-radius: 50%; pointer-events: none;
  background: radial-gradient(closest-side, rgba(255, 186, 90, .55), rgba(255, 140, 40, .2) 62%, transparent);
  opacity: .35; animation: cf-chosen 1.6s ease-in-out infinite alternate; will-change: opacity, transform; }
@keyframes cf-chosen { to { opacity: 1; transform: scale(1.08); } }
@media (prefers-reduced-motion: reduce) { .wheel-item.chosen .pillow::before { animation: none; opacity: .7; } }
:root[data-motion="reduce"] .wheel-item.chosen .pillow::before { animation: none; opacity: .7; }
.wheel-item.chosen .label { color: var(--olive-ink); }
@media (prefers-reduced-motion: reduce) { .cf-roll .cf-glow { animation: none; } }

/* No control on another (vision batch 17, the audit's overlap check). The ring's cushions sit close round the fire and their
   pictures (with their clear margins) overlap their neighbours, so a tap on one cushion's edge opened the next one. A cushion is
   pressed only on its core now, an oval in the middle of the picture, and the front cushion's name too; the rest of its box lets
   the touch through to the ring (a drag still spins it). Measured over a whole turn at 375 px: no two cores touch. */
.wheel-item, .wheel-item .pillow, .wheel-item .pillow img, .wheel-item .label { pointer-events: none; }
.wheel-item .pillow::after { content: ""; position: absolute; inset: 28% 20%; border-radius: 50%; pointer-events: auto; }
.wheel-item.front .label { pointer-events: auto; }
/* the music corner: while the player's record is parked on the stump (body.mu-docked) it is the one to press, not the empty slot
   under it; and the songbook cushion is pressed only clear of the record (its inline-end part lies under the record) */
body.mu-one-record.mu-docked .corner .rec { pointer-events: none; }
.corner .song { pointer-events: none; }
.corner .song::after { content: ""; position: absolute; inset-block: 12% 14%; inset-inline: 8% 30%; border-radius: 40%; pointer-events: auto; }
