/* Fence Challenge · the play controls shared by the three labs.
 *
 * Around every board:
 *   - rotate and flip lead the play area at its top left, above the board
 *     and the pieces, in the same place as on the hub cards; back to the hub
 *     and print this board's kit end that row on the right on phones, and
 *     sit left of the language switch on wide screens;
 *   - the board group (.boardbar): erase alone on the left, the camera on the
 *     right, the camera the largest control of the page. On phones the group
 *     sits right under the pieces, the credit under it; on wide screens it
 *     sits right under the board, the camera's right edge on the board's,
 *     the credit between erase and the camera. The same in the three labs.
 * Every control is a 44 x 44 px (or larger) touch box, at least 8 px from the
 * next one; the ring drawn inside it can be smaller (--ink), so quiet
 * controls stay discreet. */

.ctl {
  --ring: rgba(255, 255, 255, 0.2);
  --fill: rgba(255, 255, 255, 0.045);
  --fg: rgba(255, 255, 255, 0.9);
  --ink: 3px;
  position: relative;
  display: inline-grid;
  place-items: center;
  flex: 0 0 auto;
  box-sizing: border-box;
  width: 44px;
  height: 44px;
  margin: 0;
  padding: 0;
  border: 0;
  border-radius: 999px;
  background: transparent;
  color: var(--fg);
  font: inherit;
  font-size: 16px;
  line-height: 1;
  text-decoration: none;
  cursor: pointer;
  -webkit-tap-highlight-color: transparent;
  touch-action: manipulation;
  user-select: none;
  -webkit-user-select: none;
}
.ctl[hidden] { display: none !important; }
.ctl::before {
  content: "";
  position: absolute;
  inset: var(--ink);
  border-radius: inherit;
  border: 1px solid var(--ring);
  background: var(--fill);
  transition: border-color 0.12s ease, background 0.12s ease, box-shadow 0.12s ease, transform 0.12s ease;
}
.ctl > * { position: relative; }
.ctl svg { width: 20px; height: 20px; display: block; }
@media (hover: hover) {
  .ctl:hover::before { border-color: rgba(255, 255, 255, 0.42); background: rgba(255, 255, 255, 0.09); }
  .ctl.cam:hover::before { border-color: var(--accent, #2ff3ff); background: var(--fill); filter: brightness(1.2); }
}
.ctl:active::before { transform: scale(0.93); }
.ctl:focus-visible { outline: 2px solid rgba(255, 255, 255, 0.65); outline-offset: 1px; }

/* Quiet: status and help, drawn small inside their touch box. */
.ctl.quiet {
  --ink: 8px;
  --ring: rgba(255, 255, 255, 0.13);
  --fill: transparent;
  --fg: rgba(255, 255, 255, 0.58);
  font-size: 13px;
}
.ctl.quiet svg { width: 16px; height: 16px; }

/* Erase: quiet, and it asks for a second tap (play-ui.js). Armed, it turns
   rose and shakes once; it disarms by itself after a moment. */
.ctl.erase { --fg: rgba(255, 255, 255, 0.5); }
.ctl.erase.is-armed {
  --ring: rgba(255, 95, 143, 0.95);
  --fill: rgba(255, 95, 143, 0.2);
  --fg: #ff9cbc;
  animation: ctlArm 0.34s ease-in-out;
}
.ctl.erase.is-armed::before { box-shadow: 0 0 14px rgba(255, 95, 143, 0.45); }
@keyframes ctlArm {
  0%, 100% { transform: translateX(0); }
  25% { transform: translateX(-3px); }
  50% { transform: translateX(3px); }
  75% { transform: translateX(-2px); }
}

/* The camera: the one bright control. Off, an accent outline; on, filled,
   so its state reads from across a table. */
.ctl.cam {
  --ink: 0px;
  --ring: var(--accent, #2ff3ff);
  --fill: var(--accent-soft, rgba(47, 243, 255, 0.14));
  --fg: var(--accent, #2ff3ff);
  width: 76px;
  height: 56px;
  border-radius: 28px;
}
.ctl.cam::before {
  border-width: 1.5px;
  box-shadow: 0 0 18px var(--accent-glow, rgba(47, 243, 255, 0.4)), inset 0 0 14px var(--accent-soft, rgba(47, 243, 255, 0.14));
}
.ctl.cam svg { width: 28px; height: 28px; }
/* Open, as on the hub cards: filled in the board's colour, a cross to close
   it, and a ring pulsing out of it while it films. */
.ctl.cam .camOff { display: none; }
.ctl.cam[aria-pressed="true"] .camOn { display: none; }
.ctl.cam[aria-pressed="true"] .camOff { display: block; }
.ctl.cam[aria-pressed="true"] { --fill: var(--accent, #2ff3ff); --fg: #07060a; }
.ctl.cam[aria-pressed="true"]::before { box-shadow: 0 0 26px var(--accent-glow, rgba(47, 243, 255, 0.4)); }
.ctl.cam[aria-pressed="true"]::after {
  content: "";
  position: absolute;
  inset: -2px;
  border-radius: inherit;
  border: 2px solid var(--accent, #2ff3ff);
  pointer-events: none;
  animation: camPulse 1.6s ease-out infinite;
}
@keyframes camPulse { 0% { transform: scale(1); opacity: 0.9; } 100% { transform: scale(1.45); opacity: 0; } }
/* Opened from a printed sheet's QR code, a camera that could not start by
   itself waits for a tap: a ring pulses out of it. */
.ctl.cam.is-ready:not([aria-pressed="true"])::before {
  border-width: 2px;
  box-shadow: 0 0 30px var(--accent-glow, rgba(47, 243, 255, 0.4)), inset 0 0 14px var(--accent-soft, rgba(47, 243, 255, 0.14));
}
.ctl.cam.is-ready:not([aria-pressed="true"])::after {
  content: "";
  position: absolute;
  inset: -2px;
  border-radius: inherit;
  border: 2px solid var(--accent, #2ff3ff);
  pointer-events: none;
  animation: camReady 1.6s ease-out infinite;
}
@keyframes camReady { 0% { transform: scale(1); opacity: 0.9; } 100% { transform: scale(1.22); opacity: 0; } }

/* Locked or not yet possible. */
.ctl[aria-disabled="true"], .ctl.locked { opacity: 0.32; filter: grayscale(0.6); }

/* The board group: erase far left, the camera far right. */
.boardbar {
  display: flex;
  align-items: center;
  gap: 8px;
}
.boardbar .bar-gap { flex: 1 1 auto; }

/* Language switch: three 44 x 44 px touch boxes, 8 px apart; the chosen
   language keeps its small yellow pill. */
.langSel { gap: 8px; padding: 0 4px; }
.langSel button {
  position: relative;
  z-index: 0;
  min-width: 44px;
  min-height: 44px;
  padding: 0;
  background: transparent;
  -webkit-tap-highlight-color: transparent;
}
.langSel button[aria-pressed="true"] { background: transparent; }
.langSel button[aria-pressed="true"]::before {
  content: "";
  position: absolute;
  z-index: -1;
  inset: 11px 3px;
  border-radius: 999px;
  background: #ffd24a;
}

/* While the camera films, the pieces and rotate and flip stay in sight,
   dimmed, and wait. */
#piece-tray,
.piece-actions > .act,
.board-actions > .act { transition: opacity 0.18s ease; }
body:has(.ctl.cam[aria-pressed="true"]) #piece-tray,
body:has(.ctl.cam[aria-pressed="true"]) .piece-actions > .act,
body:has(.ctl.cam[aria-pressed="true"]) .board-actions > .act {
  opacity: 0.4;
  pointer-events: none;
}

/* The area: the number the game is about, large and lit in the board's
   colour (--area-accent, else --accent), its word small beside it. A tap
   measures again. Its strip keeps 44 px; play-ui.js lets the pill reach
   lower into the free room under that strip (--area-reach, never closer
   than 8 px to what lies below) and sizes the number (--area-num) so that
   three digits still keep 8 px from whatever sits beside the pill. */
.measure {
  --area: var(--area-accent, var(--accent, #2ff3ff));
  --area-reach: 0px;
  display: inline-flex;
  align-self: flex-start;
  align-items: center;
  gap: 10px;
  box-sizing: border-box;
  height: calc(44px + var(--area-reach));
  margin: 0;
  padding: 0 18px 0 16px;
  border-radius: 999px;
  border: 1.5px solid color-mix(in srgb, var(--area) 62%, transparent);
  background: radial-gradient(120% 140% at 50% 0%, color-mix(in srgb, var(--area) 20%, transparent), rgba(7, 6, 10, 0.82) 78%);
  box-shadow: 0 0 20px color-mix(in srgb, var(--area) 34%, transparent), inset 0 0 14px color-mix(in srgb, var(--area) 16%, transparent);
  color: var(--area);
  font-family: "Manrope", "Avenir Next", "Segoe UI", sans-serif;
  white-space: nowrap;
  cursor: pointer;
  -webkit-tap-highlight-color: transparent;
  transition: box-shadow 0.2s ease;
}
.measure .area-word {
  font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
  font-size: 11px;
  font-weight: 700;
  letter-spacing: 0.06em;
  line-height: 1;
  opacity: 0.85;
}
.measure .area-word:not(:lang(de)) { text-transform: lowercase; }
.measure .area-num {
  font-size: var(--area-num, 36px);
  font-weight: 800;
  line-height: 1;
  letter-spacing: 0;
  font-variant-numeric: tabular-nums;
  color: var(--area);
  text-shadow: 0 0 8px color-mix(in srgb, var(--area) 60%, transparent), 0 0 22px color-mix(in srgb, var(--area) 45%, transparent);
}
@media (hover: hover) {
  .measure:hover { box-shadow: 0 0 26px color-mix(in srgb, var(--area) 48%, transparent), inset 0 0 16px color-mix(in srgb, var(--area) 22%, transparent); }
}
.measure:active { transform: scale(0.97); }
.measure:focus-visible { outline: 2px solid color-mix(in srgb, var(--area) 70%, white); outline-offset: 2px; }

/* Back to the hub and print this board's kit. */
.lab-nav { display: flex; gap: 8px; margin-left: auto; }
.ctl.nav { --fg: rgba(255, 255, 255, 0.78); }
.ctl.nav svg { width: 19px; height: 19px; }

/* The credit link, one line in the same place and style in the three labs:
   a 44 px tall touch box, never closer than 16 px to the camera. */
.side-brand {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 44px;
  min-height: 44px;
  max-width: 100%;
  padding: 0 16px;
  box-sizing: border-box;
  white-space: nowrap;
  text-decoration: none;
  color: #8fe8ff;
  font-family: "Manrope", "Avenir Next", "Segoe UI", sans-serif;
  font-weight: 700;
  font-size: 0.76rem;
  letter-spacing: 0.04em;
  line-height: 1.2;
  text-shadow: 0 0 9px rgba(0, 209, 255, 0.3), 0 0 18px rgba(0, 255, 162, 0.16);
}
.side-brand:hover { color: #d7f8ff; }
@media (max-width: 640px) { .side-brand { font-size: 0.66rem; } }

@media (prefers-reduced-motion: reduce) {
  .ctl.erase.is-armed { animation: none; }
  .ctl.cam[aria-pressed="true"]::after { animation: none; transform: scale(1.18); opacity: 0.6; }
  .ctl.cam.is-ready:not([aria-pressed="true"])::after { animation: none; transform: scale(1.1); opacity: 0.7; }
}

/* The board takes keyboard focus (arrow keys move the chosen piece). */
#board-canvas:focus-visible,
#game-board:focus-visible { outline: 2px solid rgba(255, 255, 255, 0.65); outline-offset: 2px; }

/* A piece chip can be dragged onto the board. */
.piece-chip-ring,
.piece-btn { touch-action: none; }
