/* =====================================================================
   ⚔️ The fight — PURGE and the maker

   The overlay startMakerDuel() in js/apps/duel.js builds: two sprites with
   health bars and, across the foot of the screen, the shared dialogue box out
   of css/dialogue.css. That file's own header is the specification for the
   fight; this is what it looks like.

   ⚠️ IT IS TRANSLUCENT ON PURPOSE. Every blow the father lands hands the desktop
   back a stage, and watching the dock, the icons and the menu bar return behind
   the fight is the best image in the sequence. A solid panel would waste it. Do
   not make this opaque, and do not put a background on .maker-duel-field.

   Everything here reuses the vocabulary the arc already has rather than
   inventing a second one: the vignette element and the blood-drop keyframes out
   of css/sacrifice.css, and body.sacrifice-shake. The hit is an opacity FLICKER
   rather than a squash — which is what a 1996 sprite battle actually did, and
   which is also the version that needs no exception to the OS's rule against
   growth and shrink animation. The only transform anywhere in here is a lunge,
   which is positional, exactly like every press state in the OS.

   The two health bars carry the arc's existing colour meanings and no new ones:
   PURGE's is the theme's blood red and the maker's is the same pale grey
   .sacrifice-quote uses for the father's own words, so the colours already say
   "the thing" and "a person" before either bar moves.
   ===================================================================== */

#maker-duel {
  position: fixed;
  inset: 0;
  /* Above body.devil-theme::after at 99998, which is the one thing in the theme
     this overlay is deliberately in front of. Everything else the Devil theme
     draws sits under those scanlines and should; this is the sequence's set
     piece, and left underneath them the nameplates and both health bars went
     murky enough to be unreadable. Below .purge-destroyed at 100100, which is
     the only surface in the OS that outranks it — and which this hands the
     screen to if PURGE wins. */
  z-index: 100000;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  overflow: hidden;
  /* Just enough to sit the fight forward of the desktop. The repaint behind it
     has to stay legible. */
  background: rgba(10, 2, 1, 0.55);
  opacity: 0;
  transition: opacity 0.6s ease;
  cursor: pointer;
}

#maker-duel.is-visible {
  opacity: 1;
}

#maker-duel.is-leaving {
  opacity: 0;
  transition: opacity 0.7s ease;
}

/* The Calculator steps behind the overlay for the duration of the fight and
   comes straight back for his last message. !important because js/system.js
   opens every window with an inline `display: block`, which no stylesheet can
   outrank any other way. */
body.maker-duel-open #calculator {
  display: none !important;
}

.maker-duel-rain {
  position: absolute;
  inset: 0;
  pointer-events: none;
  overflow: hidden;
}

/* Softer than the ritual's own, which is tuned for a solid black overlay with
   one line of text on it. At full strength over a field with two combatants and
   two health bars it took the nameplates down with it. */
#maker-duel .sacrifice-vignette {
  box-shadow: inset 0 0 130px rgba(139, 0, 0, 0.5),
    inset 0 0 320px rgba(40, 0, 0, 0.55);
}

/* --- The field ---
   The enemy up and to the right, the player down and to the left, and the box
   across the bottom.

   The max-width is what keeps that arrangement legible on a wide desktop.
   Pinned to the viewport edges the two combatants end up 1200px apart on a
   1440px screen, which is not a fight, it is two things in two corners. Centred
   in 1080px they face each other. */
.maker-duel-field {
  position: relative;
  flex: 1 1 auto;
  width: 100%;
  max-width: 1080px;
  min-height: 0;
  margin-inline: auto;
  padding: 4vh 3vw 0;
}

.maker-duel-side {
  position: absolute;
  display: flex;
  align-items: center;
  gap: 18px;
}

.maker-duel-side.is-purge {
  top: 4vh;
  right: 3vw;
}

.maker-duel-side.is-maker {
  bottom: 2vh;
  left: 3vw;
}

/* --- The sprites ---
   Data, not markup: MAKER_CAST in js/apps/maker-script.js maps a pose to a
   filename and this file knows none of them. */
.maker-duel-sprite {
  position: relative;
  display: flex;
  flex: 0 0 auto;
  align-items: flex-end;
  justify-content: center;
  width: 156px;
  height: 156px;
}

.maker-duel-sprite img {
  width: 100%;
  height: 100%;
  object-fit: contain;
  object-position: center bottom;
}

/* His box is 6:5 because his artwork is: all five poses are 480x400 on one
   shared canvas, and a square box would letterbox him down to four fifths of
   the size PURGE is drawn at. Measure the art if it is ever replaced. */
.maker-duel-side.is-maker .maker-duel-sprite {
  width: 180px;
  height: 150px;
}

.maker-duel-side.is-purge .maker-duel-sprite img {
  image-rendering: pixelated;
  filter: drop-shadow(0 0 18px rgba(255, 45, 31, 0.45));
}

.maker-duel-side.is-maker .maker-duel-sprite img {
  filter: drop-shadow(0 0 22px rgba(242, 222, 215, 0.4));
}

/* --- The fallback, which is what ships until the artwork does ---
   None of the father's five pictures is in the repo yet, so every one of his
   poses falls through to this: a framed pale screen with a cursor sitting in
   it, which is the same device #archive-journal .journal-page.is-unfinished
   uses on his last page — a cursor left where somebody stopped typing. It says
   "there is something there and it has no portrait", which is exactly true, and
   it is also what the fight looked like before the owner supplied a face.
   Nothing regresses if the files never land.

   Pale rather than red throughout, because #c9c9c9 already means "this is a
   person" in this arc — it is .sacrifice-quote's colour, and his health bar's. */
.maker-duel-blank {
  display: none;
  width: 26px;
  height: 40px;
  margin-bottom: 22px;
  background: #c9c9c9;
  box-shadow: 0 0 18px rgba(242, 222, 215, 0.7);
  animation: makerDuelCursor 1.1s steps(2, end) infinite;
}

.maker-duel-sprite.is-blank img {
  display: none;
}

.maker-duel-sprite.is-blank {
  width: 118px;
  height: 146px;
  border: 3px solid #c9c9c9;
  background: rgba(201, 201, 201, 0.07);
  box-shadow: inset 0 0 26px rgba(201, 201, 201, 0.12);
}

.maker-duel-sprite.is-blank .maker-duel-blank {
  display: block;
}

@keyframes makerDuelCursor {
  0%,
  100% {
    opacity: 1;
  }
  50% {
    opacity: 0.18;
  }
}

/* --- Nameplates ---
   Ordinary retro chrome: hard black border, hard offset shadow, flat fill. The
   one thing they are not is rounded. */
.maker-duel-plate {
  display: flex;
  flex-direction: column;
  gap: 5px;
  min-width: 168px;
  padding: 7px 11px 9px;
  border: 3px solid #000;
  background: rgba(20, 5, 4, 0.94);
  box-shadow: 4px 4px 0 rgba(0, 0, 0, 0.9);
}

.maker-duel-plate-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
}

.maker-duel-name {
  font-family: "VT323", monospace;
  font-size: 20px;
  line-height: 1;
  letter-spacing: 3px;
  color: #f2ded7;
}

/* Numerals, so VT323 and never Pixelify Sans. The figure is here rather than
   only the bar because the menu prices every blow in the same units, and a cost
   the visitor cannot check against anything is not a decision. */
.maker-duel-hp {
  font-family: "VT323", monospace;
  font-size: 19px;
  line-height: 1;
  color: #c9c9c9;
}

.maker-duel-bar {
  display: block;
  width: 100%;
  height: 12px;
  border: 2px solid #000;
  background: #1a0503;
  overflow: hidden;
}

.maker-duel-fill {
  display: block;
  width: 100%;
  height: 100%;
  background: #ff2d1f;
  /* Discrete enough to read as a hit landing rather than as a slider moving. */
  transition: width 0.42s steps(8, end);
}

.maker-duel-side.is-maker .maker-duel-fill {
  background: #c9c9c9;
}

/* Spent. The bar is empty and the sprite goes out — no fade to nothing, because
   both of them are still on the field when the fight ends. */
.maker-duel-side.is-spent .maker-duel-sprite img {
  filter: grayscale(100%) brightness(0.4);
}

/* The cursor stops. That is what "finished" looks like on a side with no
   picture, and it is the same stillness his last page ends on. */
.maker-duel-side.is-spent .maker-duel-blank {
  animation: none;
  opacity: 0.2;
}

/* Down but not finished — the reprieve, and the only state in the fight that is
   undone a beat after it lands. */
.maker-duel-side.is-down .maker-duel-sprite {
  opacity: 0.45;
}

/* --- The blows --- */

@keyframes makerDuelLungeRight {
  0%,
  100% {
    transform: translate(0, 0);
  }
  45% {
    transform: translate(38px, -12px);
  }
}

@keyframes makerDuelLungeLeft {
  0%,
  100% {
    transform: translate(0, 0);
  }
  45% {
    transform: translate(-38px, 12px);
  }
}

.maker-duel-side.is-maker.is-attacking .maker-duel-sprite {
  animation: makerDuelLungeRight 0.38s ease-in-out;
}

.maker-duel-side.is-purge.is-attacking .maker-duel-sprite {
  animation: makerDuelLungeLeft 0.38s ease-in-out;
}

/* The hit. A 1996 sprite battle flickered the sprite it had just damaged and so
   does this — steps(2, end) keeps it a hard on/off rather than a soft pulse. */
@keyframes makerDuelHit {
  0%,
  100% {
    opacity: 1;
  }
  50% {
    opacity: 0.15;
  }
}

.maker-duel-side.is-hit .maker-duel-sprite {
  animation: makerDuelHit 0.13s steps(2, end) 4;
}

/* --- The box ---
   The shared dialogue box out of css/dialogue.css, docked across the bottom.
   Nothing about its look is restated here; only where it sits. */
.maker-duel-dock {
  flex: 0 0 auto;
  width: calc(100% - 8vw);
  max-width: 1080px;
  margin: 0 auto 4vh;
}

@media (prefers-reduced-motion: reduce) {
  .maker-duel-side.is-attacking .maker-duel-sprite,
  .maker-duel-side.is-hit .maker-duel-sprite,
  .maker-duel-blank {
    animation: none;
  }
  .maker-duel-fill {
    transition: none;
  }
  #maker-duel {
    transition: none;
  }
}

/* --- Tablet --- */
@media (max-width: 768px) {
  .maker-duel-sprite {
    width: 112px;
    height: 112px;
  }

  .maker-duel-side.is-maker .maker-duel-sprite {
    width: 132px;
    height: 110px;
  }

  .maker-duel-sprite.is-blank {
    width: 92px;
    height: 114px;
  }
}

/* --- Phone ---
   Measured at 320x568. Absolute corners do not survive that width: the plate is
   168px minimum and the sprite is 104px, so a row of the two is 290px before
   padding and the two sides overlap in the middle of the screen. So the field
   becomes a column — PURGE above, the maker below — which is the same reflow
   .pill-buttons-container had to take, and the box keeps the bottom.

   The budget, at 320x568: the field takes two rows of 76px plus a 14px gap and
   14px of padding, so about 180px; the box is calc(100% - 20px) with a 70px
   floor, and a four-option menu adds four 24px rows plus a 14px caption, so
   about 190px with a 12px bottom margin. That is roughly 382px against 568,
   which leaves the field the slack rather than the box. Anything added to
   either has to be re-measured against the turn prompt, which is the tallest
   thing the box ever shows. */
@media (max-width: 600px) {
  .maker-duel-field {
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    padding: 14px 14px 0;
  }

  .maker-duel-side,
  .maker-duel-side.is-purge,
  .maker-duel-side.is-maker {
    position: static;
    top: auto;
    right: auto;
    bottom: auto;
    left: auto;
    flex-direction: row;
    gap: 12px;
  }

  /* PURGE keeps the right-hand side of its own row, which is the last of the
     original geometry worth keeping at this width. */
  .maker-duel-side.is-purge {
    align-self: flex-end;
  }

  .maker-duel-sprite {
    width: 76px;
    height: 76px;
  }

  .maker-duel-side.is-maker .maker-duel-sprite {
    width: 90px;
    height: 75px;
  }

  .maker-duel-sprite.is-blank {
    width: 60px;
    height: 76px;
    border-width: 2px;
  }

  .maker-duel-blank {
    width: 16px;
    height: 22px;
    margin-bottom: 12px;
  }

  .maker-duel-plate {
    min-width: 128px;
    padding: 5px 8px 7px;
  }

  .maker-duel-name {
    font-size: 17px;
    letter-spacing: 2px;
  }

  .maker-duel-hp {
    font-size: 16px;
  }

  .maker-duel-bar {
    height: 10px;
  }

  .maker-duel-dock {
    width: calc(100% - 20px);
    margin: 0 auto 12px;
  }
}
