/* ==================================================================
   The piece shell — every full-bleed art page
   ==================================================================
   /logo, /atextual, /tartan, and /larvascript are single-screen
   pieces sharing one frame: the site masthead on top, the art filling
   everything between, a control bar underneath. No site footer; these
   pages are one screen with no scroll.

   Tokens, masthead, nav, focus ring, the square control, the button,
   the motion gate, the source field, and the motion guard all come
   from css/site.css. What is left here is the frame itself.
   ================================================================== */

/* --- the frame ------------------------------------------------------ */

.piece {
  min-height: 100dvh;
  display: grid;
  grid-template-rows: auto minmax(0, 1fr) auto;
  padding-bottom: 0;
}

/* .shell centers itself with auto inline margins, which on a grid item
   shrinks to fit instead of stretching, so the head and the bar claim
   the full track back. */

.piece > .shell { width: 100%; }

.piece__head {
  padding-top: .8rem;
  padding-bottom: .9rem;
  background: var(--surface);
  position: relative;
  z-index: var(--z-header);
}

/* The stage clips, never scrolls, and owns its background so a piece
   can go black under a light page. */

.piece__stage {
  position: relative;
  overflow: hidden;
  background: var(--surface);
}

/* No blanket "inset: 0" on stage children: a rule on the child would
   lose to it on specificity, and several pieces need a child that sits
   somewhere other than the four corners. */

/* --- the control bar ------------------------------------------------ */

/* justify-content, not a second auto margin. A long readout can push
   the squares onto a row of their own, where no .bar__id holds the
   free space; two auto margins would split the shared row and leave a
   hole in the middle. flex-end only speaks on rows where nothing else
   claims the space. */

.bar {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: flex-end;
  gap: 1rem var(--shell-pad);
  padding-top: .9rem;
  padding-bottom: 1.1rem;
  background: var(--surface);
  position: relative;
  z-index: var(--z-header);
}

.bar__id {
  display: grid;
  gap: .2rem;
  align-content: center;
  margin-inline-end: auto;
}

.bar__title {
  margin: 0;
  font-size: 1.15rem;
  line-height: var(--leading-tight);
  letter-spacing: -.01em;
}

/* Each control matches the width of its square, so the captions
   underneath cannot push the squares apart. The push to the right edge
   comes from .bar__id claiming the free space, not from an auto margin
   here. */

.bar__controls {
  display: flex;
  flex-wrap: wrap;
  gap: .9rem 1.1rem;
}

/* The readout names what is showing. A polite live region, so a screen
   reader hears the change without losing its place. */

.bar__readout {
  margin: 0;
  align-self: center;
  font-family: var(--font-mono);
  font-size: .8rem;
  line-height: 1.7;
  color: var(--text);
}

.bar__readout b { font-weight: 400; }

.bar__line { display: block; }

/* --- chrome away ----------------------------------------------------
   Clicking the art hides the head and the bar, and Escape does the same
   from the keyboard.

   The frame gives up its other two rows at the same time. .piece is a
   three-row grid, and hiding the head and the bar leaves the stage
   auto-placed into the first row, which is auto-sized: the art would
   collapse to nothing instead of going full screen. */

.piece.is-bare {
  grid-template-rows: minmax(0, 1fr);
}

.is-bare .piece__head,
.is-bare .bar {
  display: none;
}

/* The hit target covers the stage and shows nothing, so the art is the
   button. */

.overlay {
  position: absolute;
  inset: 0;
  z-index: 1;
  width: 100%;
  padding: 0;
  border: 0;
  background: transparent;
  cursor: pointer;
}

/* The focus ring on the hit target, drawn by the stage rather than the
   button. Two reasons: .overlay fills the stage exactly and
   .piece__stage clips, so the shared +3px offset paints outside the
   clip; and /larvascript gives the overlay mix-blend-mode and opacity,
   which apply to the element whole, outline included, and blend the
   ring into the art. A pseudo element on the button blends with it.
   The inward outline stays behind @supports for browsers with no
   :has(), where a faint ring beats none. */

.overlay:focus-visible {
  outline: 3px solid var(--focus-ring);
  outline-offset: -6px;
}

@supports not selector(:focus-visible) {
  .overlay:focus { outline: 3px solid var(--focus-ring); outline-offset: -6px; }
}

@supports selector(:has(*)) {
  .overlay:focus-visible { outline: none; }

  .piece__stage:has(.overlay:focus-visible)::after {
    content: '';
    position: absolute;
    inset: 3px;
    z-index: 3;
    border: 3px solid var(--focus-ring);
    border-radius: var(--radius-sm);
    pointer-events: none;
  }
}

/* The hint sits over the hit target, so it stays see-through to the
   pointer; otherwise the corner that says how to restore the controls
   is the one corner that cannot. */

.hint {
  pointer-events: none;
  position: absolute;
  right: var(--space-4);
  bottom: var(--space-4);
  z-index: 2;
  margin: 0;
  padding: .5rem .7rem;
  background: var(--surface);
  color: var(--text);
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .16em;
  text-transform: uppercase;
}

.hint[hidden] { display: none; }

/* --- narrow screens -------------------------------------------------
   The bar wraps before the stage gives up its height. The squares and
   the source field shrink in css/site.css, where they live. */

@media (max-width: 599px) {
  .bar {
    gap: .55rem .9rem;
    padding-top: .7rem;
    padding-bottom: .7rem;
  }

  .bar__title { font-size: 1rem; }
  .bar__readout { font-size: .72rem; line-height: 1.45; }

  /* The id sits on its own line down here, so the auto margin above has
     nothing to push against and the controls take the right edge. */
  .bar__controls { margin-inline-start: auto; }

}

/* --- print ----------------------------------------------------------
   A screen of animation prints as nothing useful, so the page prints
   its title alone. */

@media print {
  .piece { height: auto; display: block; }
  .piece__stage, .bar__controls { display: none; }
}
