/*
 * B05 Contact Sheet, on the shared core (rebuild on the generated art, Nov 7, 2026).
 *
 * For a photography school's video lessons. Every control is a frame of film, the art Gemini generated
 * for this design (sheets2/b05-contact-sheet.jpg): play, pause, volume, mute (the slash and X frame),
 * captions and fullscreen each sit in a black 35mm frame whose sprocket holes are real holes, so the
 * picture shows through them; the seek is the sheet's film strip with its white line and the plain white
 * dot as the playhead. A plain dark scrim (not film) under the row keeps the grotesk time readable.
 *
 * The seek preview reads like a photographer's contact sheet: five storyboard frames around the
 * pointer (the middle one the stock v10 slider thumbnail, the four around it v10 <media-thumbnail>
 * elements timed by contact.js, a styling aid only) and the frame under the pointer circled by the
 * grease-pencil loop harvested from the winning render (set-b/B05-contact-sheet.jpg, art/loop.png).
 *
 * Seek: the unplayed run is never stretched (the holes would turn into ovals): a left end, whole
 * sprocket periods tiled with background-repeat: round, and a right end. The played strip only shows
 * its white line (clipped to the line's rows), so the holes always come from the one tiled run.
 */

@font-face {
  font-family: "Hanken Grotesk";
  src: url(fonts/HankenGrotesk-500.woff2) format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Hanken Grotesk";
  src: url(fonts/HankenGrotesk-700.woff2) format("woff2");
  font-weight: 700;
  font-style: normal;
  font-display: swap;
}

.sk-root[data-skin="b05"] {
  --media-accent-color: #ffffff;
  --media-accent-text-color: #1e1f21;
  --media-border-radius: 12px;
  --media-font-family: "Hanken Grotesk", "Inter", system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;

  --cx-graphite: #1e1f21;
  --cx-red: #e2332b;
  --cx-red-hi: #ff5a4f;

  /* film strip: 110px tall in the art; end pieces 39px; the white line runs 47% to 53% */
  --cx-strip-h: 52px;
  --cx-line-top: 43%;
  --cx-line-bottom: 43%;

  --sk-pad: 6px;
  --sk-btn-radius: 10px;
  --sk-hit: 52px;
  --sk-icon: 52px;
  --sk-ink: #ffffff;
  --sk-ink-2: #dedfe3;
  --sk-surface: rgb(30 31 33 / .94);
  --sk-surface-solid: var(--cx-graphite);
  --sk-blur: 0px;
  --sk-hairline: rgb(255 255 255 / .08);
  --sk-hairline-strong: rgb(255 255 255 / .28);
  --sk-shadow: 0 1px 3px rgb(0 0 0 / .22), 0 10px 30px rgb(0 0 0 / .28);
  --sk-cc-on: #ffffff;
  --sk-focus: #ffffff;
  --sk-focus-gap: #0c0c0d;
  --sk-error-accent: var(--cx-red-hi);
  /* a plain dark scrim under the row (not film) */
  --cx-scrim-a: .86;
  --sk-scrim: linear-gradient(to top, rgb(12 12 14 / var(--cx-scrim-a)) 0, rgb(12 12 14 / calc(var(--cx-scrim-a) * .72)) 70px, rgb(12 12 14 / 0) 150px);
  /* Nov 15, 2026: Chrome has no VTTCue.lineAlign, so a cue hangs below the core's line instead of sitting on it;
     116 = the 84px row + a one-line cue + a gap (100 left the cue box resting on the film strip) */
  --sk-cue-clearance: 116px;

  --cx-bar-pad: 16px;
  --cx-bar-h: calc(var(--sk-hit) + var(--cx-bar-pad) * 2);
  --cx-frame-w: 92px;
}

.sk-root[data-skin="b05"] > mux-video {
  font-family: "Inter", system-ui, sans-serif;
}

/* ---------- The row of frames ---------- */

.cx-bar {
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  display: flex;
  align-items: center;
  gap: 8px;
  height: var(--cx-bar-h);
  padding: var(--cx-bar-pad) calc(18px + var(--sk-hit) + 8px) var(--cx-bar-pad) 18px;
  color: var(--sk-ink);
}

/* Film-frame buttons: the art is the whole button; hover lifts the frame a touch brighter */
.sk-root[data-skin="b05"] :is(.cx-bar .sk-btn, .sk-fs) {
  transition: none;
}
.sk-root[data-skin="b05"] :is(.cx-bar .sk-btn, .sk-fs) .sk-icon {
  filter: drop-shadow(0 2px 4px rgb(0 0 0 / .45));
  transition: filter var(--sk-exit) linear;
}
.sk-root[data-skin="b05"] :is(.cx-bar .sk-btn, .sk-fs):hover .sk-icon {
  filter: drop-shadow(0 2px 4px rgb(0 0 0 / .45)) brightness(1.5);
  transition-duration: var(--sk-enter);
}
.sk-root[data-skin="b05"] :is(.cx-bar .sk-btn, .sk-fs):active .sk-icon {
  filter: drop-shadow(0 1px 2px rgb(0 0 0 / .45)) brightness(1.2);
}

/* Focus: white ring outside a black gap, following the frame's rounded corners */
.sk-root[data-skin="b05"] .sk-btn:focus-visible {
  box-shadow: 0 0 0 var(--sk-focus-off) var(--sk-focus-gap);
}

/* Captions: on = a white bar under the frame (shape and position); off = the frame dimmed */
.sk-root[data-skin="b05"] .sk-cc::after {
  bottom: -7px;
  width: 20px;
  height: 3px;
  box-shadow: 0 0 0 1px #0c0c0d;
}
.sk-root[data-skin="b05"] .sk-cc:not([data-active]) .sk-icon {
  filter: drop-shadow(0 2px 4px rgb(0 0 0 / .45)) brightness(.7) contrast(.85);
}

/* Fullscreen: the row's last frame on desktop, top-right when narrow */
.sk-root[data-skin="b05"] .sk-controls > .sk-fs {
  position: absolute;
  right: 18px;
  bottom: var(--cx-bar-pad);
}

/* ---------- Time ---------- */

.cx-bar .sk-time {
  padding: 0 6px;
  font: 700 18px/1 var(--media-font-family);
  font-variant-numeric: tabular-nums;
  text-shadow: 0 1px 2px rgb(0 0 0 / .85), 0 0 10px rgb(0 0 0 / .5);
}
.cx-bar .sk-time media-time[data-type="duration"],
.cx-bar .sk-time media-time-separator {
  color: var(--sk-ink-2);
}

/* ---------- Seek: the film strip ---------- */

.cx-seek {
  --sk-seek-hit: var(--cx-strip-h);
  --sk-seek-radius: 10px;
  height: var(--cx-strip-h);
  margin-inline: 4px;
}
.sk-root[data-skin="b05"] .sk-track,
.sk-root[data-skin="b05"] .sk-seek[data-interactive] .sk-track {
  height: 100%;
  border-radius: 0;
  background: none;
  overflow: visible;
  transition: none;
}
/* the unplayed run: two ends and the whole-period tile between them (round keeps the holes round) */
.sk-root[data-skin="b05"] .sk-track::before,
.sk-root[data-skin="b05"] .sk-track > .sk-buffer {
  content: "";
  position: absolute;
  inset: 0;
  width: auto;
  padding: 0 calc(var(--cx-strip-h) * 39 / 110);
  border-radius: 0;
  background:
    url(art/seek-unplayed-capl.png) left center / auto 100% no-repeat,
    url(art/seek-unplayed-capr.png) right center / auto 100% no-repeat,
    url(art/seek-unplayed-tile.png) 0 0 / auto 100% round;
  background-origin: border-box, border-box, content-box;
  background-clip: border-box, border-box, content-box;
}
.sk-root[data-skin="b05"] .sk-track > .sk-buffer {
  filter: brightness(1.45);
  clip-path: inset(var(--cx-line-top) calc(100% - var(--media-slider-buffer, 0%)) var(--cx-line-bottom) 0);
}
/* played: the white line, clipped at the fill and to the line's rows */
.sk-root[data-skin="b05"] .sk-track > .sk-fill {
  inset: 0;
  width: auto;
  border-style: solid;
  border-color: transparent;
  border-width: 0 calc(var(--cx-strip-h) * .2884);
  border-image-source: url(art/seek-played.png);
  border-image-slice: 0 32 fill;
  border-image-width: 0 calc(var(--cx-strip-h) * .2884);
  border-image-repeat: stretch;
  border-radius: 0;
  background: none;
  clip-path: inset(var(--cx-line-top) calc(100% - var(--media-slider-fill, 0%)) var(--cx-line-bottom) 0);
}
/* the playhead: the plain white dot from the sheet */
.sk-root[data-skin="b05"] .cx-seek .sk-thumb {
  --sk-thumb: 20px;
  background: url(art/knob.png) center / contain no-repeat;
  filter: drop-shadow(0 1px 2px rgb(0 0 0 / .6));
}
@media (prefers-reduced-motion: no-preference) {
  .sk-root[data-skin="b05"] .cx-seek .sk-thumb {
  /* thumb containment (Gus's rule, Nov 7): the core centers the thumb on the fill
     percentage, so unclamped it spills half its width past the track at 0% and 100%.
     Travel is clamped to [half width + 3px, 100% - half width - 3px] so the thumb
     stays fully inside its track at both ends, mid-drag grow included. */
  left: clamp(calc(var(--sk-thumb-w, var(--sk-thumb)) / 2 + 3px), var(--media-slider-fill), calc(100% - var(--sk-thumb-w, var(--sk-thumb)) / 2 - 3px));
    transition: scale var(--sk-exit) var(--sk-ease);
  }
  .sk-root[data-skin="b05"] .cx-seek[data-interactive] .sk-thumb {
    scale: 1.3;
    transition-duration: var(--sk-enter);
  }
}

/* Volume: a short run of the same film beside the speaker frame */
.cx-bar .sk-volume {
  gap: 0;
}
.sk-root[data-skin="b05"] .sk-volume-slider {
  --sk-vol-w: 104px;
  --cx-strip-h: 30px;
  margin-inline: 6px 2px;
}
.sk-root[data-skin="b05"] .sk-volume-slider .sk-track {
  height: var(--cx-strip-h);
}
.sk-root[data-skin="b05"] .sk-volume-slider .sk-thumb {
  /* thumb containment (Gus's rule, Nov 7): the core centers the thumb on the fill
     percentage, so unclamped it spills half its width past the track at 0% and 100%.
     Travel is clamped to [half width + 0px, 100% - half width - 0px] so the thumb
     stays fully inside its track at both ends, mid-drag grow included. */
  left: clamp(calc(var(--sk-thumb-w, var(--sk-thumb)) / 2 + 0px), var(--media-slider-fill), calc(100% - var(--sk-thumb-w, var(--sk-thumb)) / 2 - 0px));
  --sk-thumb: 14px;
  background: url(art/knob.png) center / contain no-repeat;
}

/* ---------- The contact sheet: five frames around the pointer ---------- */

.cx-seek .cx-sheet {
  bottom: calc(100% + 14px);
  gap: 6px;
  /* Nov 15, 2026: the stock clamp (overflow="clamp") keeps the preview inside the seek, so where the sheet is
     wider than the seek (players about 520 to 930px wide) it pinned to the seek's right end and ran off the
     player's left edge. The same clamp, restated with a floor: the sheet never starts left of the play frame
     (the seek begins after the 18px pad, the play frame, the 8px gap and its 4px margin). The two-row layout's
     seek spans the row, so the floor never binds there. Sheet width: five frames, four 4px gaps, 4px pad. */
  --cx-sheet-w: calc(var(--cx-frame-w) * 5 + 24px);
  left: max(calc(-12px - var(--sk-hit)), min(max(0px, calc(var(--media-slider-pointer) - var(--cx-sheet-w) / 2)), calc(100% - var(--cx-sheet-w)))) !important;
}
.cx-strip {
  display: flex;
  gap: 4px;
  padding: 4px;
  border-radius: 8px;
  background: var(--cx-graphite);
  box-shadow: inset 0 0 0 1px var(--sk-hairline), 0 1px 3px rgb(0 0 0 / .3), 0 10px 28px rgb(0 0 0 / .35);
}
.cx-frame {
  display: block;
  flex: none;
  width: var(--cx-frame-w);
  min-width: var(--cx-frame-w);
  max-width: var(--cx-frame-w);
  aspect-ratio: 16 / 9;
  overflow: hidden;
  border-radius: 4px;
  background: #0f1011;
}
.cx-near[data-empty]::part(image) {
  visibility: hidden;
}
.cx-near[data-empty] {
  background: repeating-linear-gradient(135deg, #18191b 0 6px, #141516 6px 12px);
}
.cx-strip .sk-preview-image {
  --sk-preview-w: var(--cx-frame-w);
  min-width: var(--cx-frame-w);
  max-width: var(--cx-frame-w);
  box-shadow: none;
}
.cx-strip .sk-preview-image[data-hidden] {
  display: block;
  visibility: hidden;
}
.cx-pick {
  position: relative;
  display: block;
  flex: none;
}
/* Grease pencil: the loop from the render, around the frame under the pointer */
.cx-loop {
  position: absolute;
  left: -9px;
  top: -8px;
  width: calc(100% + 18px);
  height: calc(100% + 16px);
  pointer-events: none;
  user-select: none;
  filter: drop-shadow(0 1px 0 rgb(0 0 0 / .45));
}
.cx-sheet .sk-preview-time {
  padding: 5px 9px;
  border-radius: 6px;
  background: var(--cx-graphite);
  box-shadow: inset 0 0 0 1px var(--sk-hairline-strong), 0 2px 6px rgb(0 0 0 / .3);
  font: 700 13px/1 var(--media-font-family);
}

/* ---------- Center play: the play frame (decorative; the row's Play is the real one) ---------- */

.sk-root[data-skin="b05"] .sk-center {
  padding-bottom: var(--cx-bar-h);
}
.sk-root[data-skin="b05"] .cx-bigplay {
  --sk-icon: 124px;
  display: grid;
  place-items: center;
  width: var(--sk-icon);
  height: var(--sk-icon);
  padding: 0;
  border: 0;
  border-radius: 18px;
  background: none;
  cursor: pointer;
}
.sk-root[data-skin="b05"] .cx-bigplay .sk-icon {
  filter: drop-shadow(0 6px 14px rgb(0 0 0 / .45));
  transition: filter var(--sk-exit) linear;
}
.sk-root[data-skin="b05"] .cx-bigplay:hover .sk-icon {
  filter: drop-shadow(0 6px 14px rgb(0 0 0 / .45)) brightness(1.4);
  transition-duration: var(--sk-enter);
}

/* ---------- Designed states ---------- */

.sk-root[data-skin="b05"] .sk-spinner {
  width: 66px;
  height: 66px;
  background: none;
  box-shadow: none;
}
.sk-root[data-skin="b05"] .sk-spinner .sk-icon {
  width: 66px;
  height: 66px;
}
.sk-root[data-skin="b05"] .sk-error {
  gap: 8px;
  padding: 22px 6px 6px;
  border-radius: 12px;
  background: rgb(30 31 33 / .97);
}
.sk-root[data-skin="b05"] .sk-error-title {
  padding-inline: 14px;
  font: 700 18px/1.2 var(--media-font-family);
}
.sk-root[data-skin="b05"] .sk-error-text {
  padding-inline: 14px;
  color: var(--sk-ink-2);
  font-family: "Inter", system-ui, sans-serif;
}
.sk-root[data-skin="b05"] .sk-error-close {
  width: 100%;
  margin-top: 10px;
  border-radius: 6px;
  background: #ffffff;
  color: var(--cx-graphite);
  font: 700 15px/1 var(--media-font-family);
}
.sk-root[data-skin="b05"] .sk-error-close:focus-visible {
  outline-color: #ffffff;
}
.sk-root[data-skin="b05"] .sk-empty p {
  padding: 11px 18px;
  border-radius: 8px;
  background: var(--sk-surface);
  font: 500 15px/1 var(--media-font-family);
}

/* ---------- Mid widths ---------- */

@container sk (max-width: 819px) {
  .sk-root[data-skin="b05"] :is(.sk-controls, .sk-center) {
    --sk-hit: 46px;
    --sk-icon: 46px;
    --cx-bar-pad: 12px;
    --cx-strip-h: 46px;
    --cx-frame-w: 72px;
    --cx-bar-h: calc(var(--sk-hit) + var(--cx-bar-pad) * 2);
  }
  .sk-root[data-skin="b05"] .cx-bigplay {
    --sk-icon: 104px;
  }
}
@container sk (max-width: 679px) {
  .sk-root[data-skin="b05"] .sk-volume-slider {
    display: none;
  }
}

/* ---------- Narrow: two rows (the strip on top); fullscreen becomes a frame at the top-right ---------- */

@container sk (max-width: 519px) {
  .sk-root[data-skin="b05"] :is(.sk-controls, .sk-center) {
    --sk-hit: 44px;
    --sk-icon: 44px;
    --cx-strip-h: 34px;
    --cx-bar-pad: 8px;
    --cx-frame-w: 50px;
    --cx-bar-h: calc(var(--cx-bar-pad) * 2 + var(--cx-strip-h) + 4px + var(--sk-hit));
  }
  .cx-bar {
    display: grid;
    grid-template-columns: var(--sk-hit) var(--sk-hit) auto 1fr var(--sk-hit);
    grid-template-rows: var(--cx-strip-h) var(--sk-hit);
    gap: 4px 8px;
    padding: var(--cx-bar-pad) 10px;
  }
  .cx-bar .sk-seek {
    grid-column: 1 / -1;
    grid-row: 1;
    margin-inline: 0;
  }
  .cx-bar .sk-play { grid-column: 1; grid-row: 2; }
  .cx-bar .sk-volume { grid-column: 2; grid-row: 2; }
  .cx-bar .sk-time { grid-column: 3; grid-row: 2; font-size: 16px; }
  .cx-bar .sk-cc { grid-column: 5; grid-row: 2; }
  .sk-root[data-skin="b05"] .cx-seek .sk-thumb {
    --sk-thumb: 16px;
  }
  .sk-root[data-skin="b05"] .sk-controls > .sk-fs {
    top: 10px;
    right: 10px;
    bottom: auto;
  }
  .sk-root[data-skin="b05"] .cx-bigplay {
    --sk-icon: 76px;
  }
  .sk-root[data-skin="b05"][data-started]:not([data-ended]) .cx-bigplay {
    opacity: 0;
    pointer-events: none;
  }
}
@media (max-width: 551px) {
  .sk-root[data-skin="b05"] {
    --sk-cue-clearance: 120px;
  }
}

/* ---------- Preference fallbacks ---------- */

@media (prefers-reduced-transparency: reduce), (prefers-contrast: more) {
  .sk-root[data-skin="b05"] {
    --sk-scrim: linear-gradient(to top, rgb(12 12 14) 0, rgb(12 12 14) calc(var(--cx-bar-h) + 6px), rgb(12 12 14 / 0) calc(var(--cx-bar-h) + 6px));
  }
}
@media (prefers-contrast: more) {
  .sk-root[data-skin="b05"] {
    --sk-focus-w: 3px;
    --sk-ink-2: #e2e3e6;
  }
  .cx-bar .sk-time {
    text-shadow: none;
  }
}
@media (forced-colors: active) {
  .cx-bar {
    border-top: 2px solid CanvasText;
    background: Canvas;
  }
  .sk-root[data-skin="b05"] .cx-seek .sk-track {
    outline: 1px solid CanvasText;
  }
  .sk-root[data-skin="b05"] .sk-track > .sk-buffer {
    background: repeating-linear-gradient(90deg, CanvasText 0 1px, Canvas 1px 4px);
    filter: none;
    forced-color-adjust: none;
  }
  .sk-root[data-skin="b05"] .sk-track > .sk-fill {
    border-image: none;
    background: Highlight;
    forced-color-adjust: none;
  }
  .cx-strip {
    border: 1px solid CanvasText;
  }
  .sk-root[data-skin="b05"] :is(.sk-error, .sk-empty p) {
    border: 2px solid CanvasText;
    background: Canvas;
  }
  .sk-root[data-skin="b05"] .sk-error-close {
    border: 2px solid ButtonText;
    background: ButtonFace;
    color: ButtonText;
  }
}

/* Nov 15, 2026 (coordinator audit g1b): the core keeps a focused row visible while idle, but the backdrop
   has no such guard, so for keyboard users the scrim dropped and the time fell to about 1.3:1 over a bright
   frame. Keep the scrim up whenever a control holds focus. */
.sk-root[data-skin="b05"]:has(.sk-controls :focus-visible) .sk-backdrop { opacity: 1; }

