/* ---------------------------------------------------------------------------
   gaffgame.app.

   Chosen from three structures tried side by side in /lab/ on 2026-09-21: the
   tour, the shelf and the bento. This is the shelf. White ground, because the
   app's screenshots are cream and need to read as objects on a page rather than
   sink into it, and no device bezels around them for the same reason.

   Every picture here is a real capture out of the running prototype, taken by
   shots/capture.js against a seeded account. Nothing is a mockup, and nothing
   is a drawing of the product standing in for the product.

   Copy carries no em dashes anywhere, per the project rule.
--------------------------------------------------------------------------- */

:root {
  --ink: #171310;
  --cream: #F4EDDF;
  --paper: #FBF8F0;
  --blue: #93B4E8;
  --gold: #F2C93B;
  --pink: #E88AA8;
  --green: #8FCBA4;
  --violet: #B9A6E8;
  --ink-55: rgba(23, 19, 16, 0.55);
  --ink-70: rgba(23, 19, 16, 0.7);
  --hair: rgba(23, 19, 16, 0.12);
  --display: "Archivo Black", "Arial Black", sans-serif;
  --body: Inter, -apple-system, BlinkMacSystemFont, sans-serif;
  --mono: ui-monospace, "SF Mono", "Courier New", monospace;
}

* { box-sizing: border-box; }
html { -webkit-text-size-adjust: 100%; }
body {
  margin: 0; background: #fff; color: var(--ink);
  font-family: var(--body); line-height: 1.55;
}
img { max-width: 100%; height: auto; display: block; }
a { color: inherit; }

/* The screenshot, unframed. On white the cream needs an edge or it floats, so
   it gets a hairline and a soft lift instead of a phone drawn around it. */
.shot { border-radius: 18px; border: 1px solid var(--hair); box-shadow: 0 10px 30px rgba(23,19,16,.08); overflow: hidden; }
.shot img { width: 100%; }
.shot--plain { box-shadow: none; }

.wrap { width: min(1120px, 100% - 40px); margin: 0 auto; }
.sec { padding: 76px 0; }
.rule { border: 0; border-top: 1px solid var(--hair); margin: 0; }

.kick { margin: 0 0 12px; font-family: var(--mono); font-weight: 700; font-size: 11.5px; letter-spacing: 0.2em; text-transform: uppercase; color: var(--ink-55); }
h1, h2, h3 { font-family: var(--display); font-weight: 400; margin: 0; text-wrap: balance; }
h1 { font-size: clamp(38px, 6vw, 64px); line-height: 1.03; }
h2 { font-size: clamp(27px, 3.4vw, 40px); line-height: 1.1; }
h3 { font-size: 20px; }
p { margin: 12px 0 0; }
.lede { font-size: clamp(16.5px, 1.5vw, 19px); color: var(--ink-70); margin-top: 16px; max-width: 46ch; }
.small { font-size: 15px; color: var(--ink-70); }

/* Apple's badge is licensed artwork: it ships unmodified and only scales
   proportionally. Height 54 clears their 40px floor with room to read. Apple
   want clear space of a tenth of the badge height around it; the wrapper adds
   that above and below, and both badges already sit alone on their line. */
.badge { display: inline-block; line-height: 0; }
.badge img { height: 54px; width: auto; }
.badgewrap { padding: 5px 0; }
/* The nav asks before the page has said anything, so it asks quietly. One
   loud CTA above the fold, and it belongs to the hero. */
.nav__get { font-size: 14px; color: var(--ink-70); text-decoration: none; border-bottom: 1px solid var(--hair); padding-bottom: 2px; transition: color .15s, border-color .15s; }
.nav__get:hover { color: var(--ink); border-bottom-color: var(--ink); }
/* On a phone the full phrase takes half the bar and stops being quiet. */
@media (max-width: 620px) { .nav__get-long { display: none; } }


.nav { display: flex; align-items: center; justify-content: space-between; padding: 20px 0; }
.nav__brand { display: flex; align-items: center; gap: 9px; font-family: var(--display); font-size: 21px; }
.nav__brand img { width: 28px; height: 28px; }

/* ============ A. THE TOUR ============
   One idea per band, alternating sides, generous. The familiar app-marketing
   shape: slowest to read, easiest to skim, most room per game. */
.band { display: grid; grid-template-columns: 1fr 1fr; gap: 60px; align-items: center; }
.band--flip .band__shot { order: -1; }
.band__shot { max-width: 320px; justify-self: center; width: 100%; }
.band + .band { margin-top: 76px; }
.facts { display: flex; gap: 26px; flex-wrap: wrap; margin-top: 24px; }
.fact b { display: block; font-family: var(--display); font-weight: 400; font-size: 28px; line-height: 1; }
.fact span { font-family: var(--mono); font-size: 10.5px; letter-spacing: .12em; text-transform: uppercase; color: var(--ink-55); }

/* ============ B. THE SHELF ============
   The App Store's own shape. A rail of screenshots you swipe, then tight blocks
   underneath. Most product visible per screen, most familiar to a phone user. */
.rail { display: flex; gap: 16px; overflow-x: auto; padding: 4px 0 18px; scroll-snap-type: x mandatory; -webkit-overflow-scrolling: touch; }
.rail::-webkit-scrollbar { height: 6px; }
.rail::-webkit-scrollbar-thumb { background: var(--hair); border-radius: 3px; }
.rail > figure { flex: 0 0 236px; margin: 0; scroll-snap-align: start; }
.rail figcaption { margin-top: 10px; font-family: var(--mono); font-size: 10.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-55); }
.rail--full > figure { flex-basis: 260px; }
.blocks { display: grid; grid-template-columns: repeat(auto-fit, minmax(240px, 1fr)); gap: 18px; margin-top: 30px; }
.block { border-top: 2px solid var(--ink); padding-top: 14px; }
.block__k { font-family: var(--mono); font-size: 10.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-55); margin-top: 6px; }

/* ============ C. THE BENTO ============
   Everything at once, in tiles of different weights. Answers the brief most
   literally ("these shouldn't be surprises") and is the densest to read. */
.bento { display: grid; grid-template-columns: repeat(4, 1fr); gap: 16px; }
.tile { border-radius: 22px; padding: 22px; border: 1px solid var(--hair); background: var(--paper); display: flex; flex-direction: column; gap: 10px; min-width: 0; }
.tile--w2 { grid-column: span 2; }
.tile--w3 { grid-column: span 3; }
.tile--r2 { grid-row: span 2; }
.tile--ink { background: var(--ink); color: #fff; border-color: var(--ink); }
.tile--gold { background: var(--gold); }
.tile--blue { background: var(--blue); }
.tile--green { background: var(--green); }
.tile--violet { background: var(--violet); }
.tile--pink { background: var(--pink); }
.tile--shot { padding: 18px 18px 0; overflow: hidden; }
/* A bento only works if every tile is a controlled size. Left alone, a 640x1385
   screenshot at 484px wide stands 1047px and drags its whole grid row with it,
   which is what the first pass did: rows came out 403, 637, 1057, 1057. The
   shot gets a fixed window and shows its top. */
.tile--shot .shot { border-radius: 14px 14px 0 0; border-bottom: 0; box-shadow: none; height: 210px; overflow: hidden; }
.tile--r2.tile--shot .shot { height: 560px; }
.tile--w2.tile--shot .shot { height: 260px; }
.tile--r2.tile--w2.tile--shot .shot { height: 560px; }
.tile p { font-size: 14.5px; color: var(--ink-70); }
.tile--ink p { color: rgba(255,255,255,.75); }
.tile__n { font-family: var(--display); font-size: 34px; line-height: 1; }
.tile__k { font-family: var(--mono); font-size: 10.5px; letter-spacing: .12em; text-transform: uppercase; color: var(--ink-55); }
.tile--ink .tile__k { color: rgba(255,255,255,.5); }

.end { text-align: center; padding: 80px 0; }
.foot { margin-top: 36px; font-family: var(--mono); font-size: 11.5px; color: var(--ink-55); display: flex; gap: 16px; justify-content: center; flex-wrap: wrap; }

@media (max-width: 900px) {
  .band { grid-template-columns: 1fr; gap: 28px; }
  .band--flip .band__shot { order: 0; }
  .band__shot { max-width: 300px; }
  .bento { grid-template-columns: repeat(2, 1fr); }
  .tile--w3 { grid-column: span 2; }
  .sec { padding: 54px 0; }
}
@media (max-width: 560px) {
  .bento { grid-template-columns: 1fr; }
  .tile--w2, .tile--w3 { grid-column: span 1; }
}

/* ---------- B's rail, native app height ----------
   Every screen whole, the way the App Store shows them. A phone screen at 600
   wide is 1298 tall, so at a 236px rail width each figure stands about 511px.
   That is the shape of the real thing and it is meant to be tall. */
.rail--native > figure { flex-basis: 232px; }
.rail--native .shot { border-radius: 16px; }

/* ---------- the game marks ----------
   The app's own home-screen icons, lifted straight out of the prototype and
   rebound to currentColor so they carry no colour of their own. Inlined rather
   than loaded as <img>, because an SVG in an img has no context to resolve
   currentColor against. */
.block__icon { display: block; margin-bottom: 14px; color: var(--ink); }
.block__icon svg { width: 38px; height: 38px; display: block; }

/* ---------- a wide detail ----------
   Not every screen wants a phone around it. The index is a chart, so it runs
   wide and unframed, which also stops the economy section reading as a third
   row of handsets. */
.detail { margin: 28px 0 0; max-width: 700px; }
.detail figcaption { margin-top: 12px; font-family: var(--mono); font-size: 11px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-55); }

/* ---------- viz beside copy ----------
   The index is a chart, so it leads on the left and the copy answers it on the
   right. Shot on white out of the app itself rather than cropped off a phone,
   so it brings no cream rectangle onto the page with it. */
.split { display: grid; grid-template-columns: 1fr 1fr; gap: 56px; align-items: center; }
.split__viz { margin: 0; }
/* No frame. The block was shot on white, so a border would draw a card around
   something that is meant to sit straight on the page. */
.split__viz .shot { border: 0; border-radius: 0; box-shadow: none; overflow: visible; }
.split__viz figcaption { margin-top: 14px; font-family: var(--mono); font-size: 11px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-55); }
@media (max-width: 900px) {
  .split { grid-template-columns: 1fr; gap: 26px; }
  .split__viz { order: -1; }
}

/* The paper's own sentence, quoted rather than paraphrased. It says the thing
   better than marketing copy would, and attributing it shows the product has a
   voice before anyone has installed it. */
.pull { margin: 22px 0 0; padding-left: 18px; border-left: 3px solid var(--ink); }
.pull p { margin: 0; font-family: var(--display); font-size: clamp(18px, 1.9vw, 22px); line-height: 1.25; }
.pull cite { display: block; margin-top: 10px; font-style: normal; font-family: var(--mono); font-size: 11px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-55); }

/* ---------- the rail that introduces as it shows ----------
   The three games used to be named in the rail's captions and then introduced
   again in a section below it, six hundred pixels apart. One introduction now,
   under the screen it belongs to, so the picture and the words arrive together. */
.rail--told > figure { flex-basis: 248px; }
.rail--told figcaption { margin-top: 14px; text-transform: none; letter-spacing: 0; color: var(--ink); font-family: var(--body); }
.rail__icon { display: block; margin-bottom: 10px; color: var(--ink); }
.rail__icon svg { width: 32px; height: 32px; display: block; }
.rail__name { display: block; font-family: var(--display); font-size: 18px; line-height: 1.15; }
.rail__k { display: block; margin-top: 5px; font-family: var(--mono); font-size: 10.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--ink-55); }
.rail__b { display: block; margin-top: 8px; font-size: 14px; line-height: 1.5; color: var(--ink-70); }

/* ---------- the host, in the lede ----------
   He was a second display block in a second column, which is what made the
   first screen busy: two Archivo Black statements at the same volume, and a
   third headline underneath repeating the idea. He now occupies the lede's
   slot, in the body face, so he can only ever be subordinate to the headline.
   The face is the app's own eyeroll mood, generated from its drawing code
   rather than redrawn. */
/* Cap the children, not the container. A max-width on .hero itself re-centred
   it inside .wrap so the hero sat indented from every section below; killing
   the auto margin to fix that pushed it flush against the viewport edge and
   lost the page gutter. The wrap keeps its job, the lines keep their measure. */
.hero { padding: 34px 0 10px; }
.hero h1 { max-width: 15ch; }
.hero .says, .hero .says { display: flex; gap: 16px; align-items: flex-start; margin-top: 20px; }
.says__face { flex: none; color: var(--ink); }
.says__face svg { display: block; }
.says__k { margin: 2px 0 0; font-family: var(--mono); font-size: 11px; letter-spacing: .16em; text-transform: uppercase; color: var(--ink-55); }
.says__q { margin: 6px 0 0; font-size: clamp(17px, 1.7vw, 20px); line-height: 1.5; color: var(--ink); }

/* ---------- the one social reason to install ----------
   It used to be a third of a text row next to GAFF Town, which a new player
   cannot reach for about ten days (TOWN_PRICE is 15,000), and Make Your Own,
   which is the hardest thing here to explain. Those two came out. This is the
   only place on the page that answers "can I do this with other people", so it
   gets a band.

   No screenshot: the friends board needs a real league, the app's own demo data
   for it is unreachable from any surviving code path, and injecting rows to
   photograph would be manufacturing a screen the product does not show. */
.friends { display: flex; gap: 26px; align-items: flex-start; }
.friends__mark { flex: none; color: var(--ink); }
.friends__mark svg { display: block; }
@media (max-width: 600px) { .friends { flex-direction: column; gap: 16px; } }
