/* ==========================================================================
   PhotoSensei — /cards/ landing page
   Loaded AFTER site.css, never instead of it: the reset, tokens, self-hosted
   Inter, header, footer and store badges all come from there. This file adds
   only what /cards/ needs.

   EVERY rule below is scoped under `.cards`, the class on this page's <body>
   and nowhere else. That scoping is load-bearing, not tidiness: both files
   are served to the same origin under one CSP, and an unscoped selector here
   would reach index.html and 404.html the moment either loads this sheet.

   No <style> block and no style="" attribute exists on the page. The CSP is
   `style-src 'self'` with no 'unsafe-inline', so an inline style would not be
   applied at all — it would be blocked, silently, with the page still 200.
   ========================================================================== */

/* --- The foil -------------------------------------------------------------
   A generic holographic sweep built from scratch: cyan, violet, pink, gold,
   mint, closing on cyan again so the loop is seamless. Deliberately NOT any
   trading-card game's palette, and deliberately not the pokemon-cards-css
   holo effect — no borrowed scheme, no card-game typeface, no slab look.

   RESTRAINT IS THE RULE. The foil appears on exactly four things: the H1,
   the one divider under the hero, the four step numerals, and the edge of
   each screenshot frame. Everything else on this page is the ordinary dark
   palette from site.css. Adding a fifth foil element is a change to the
   page's whole character, not a tweak.                                     */
.cards {
  --foil: linear-gradient(100deg,
    #7FE7E1 0%,
    #B9A3F5 22%,
    #F5A8D0 44%,
    #EBC77A 66%,
    #9CE8B8 84%,
    #7FE7E1 100%);
  --foil-span: 300% 100%;
  --foil-roll: 18s;
  --sleeve: rgba(236, 231, 222, 0.20);
  --panel: #120F0C;
}

@keyframes cards-foil-roll {
  from { background-position:   0% 50%; }
  to   { background-position: 100% 50%; }
}

/* --- Hero ---------------------------------------------------------------- */
/* The lede runs longer here than on the main page, where 34ch is tuned to a
   one-line promise. */
.cards .lede { max-width: 48ch; }

/* --- Prose links ---------------------------------------------------------
   Two in-copy links live on this page: the lessons anchor in "The bonus you
   get anyway", and the privacy policy in "Worth knowing". site.css already
   makes every <a> brass and leaves the underline on, which is legible here;
   this states it explicitly and gives the page its own hover and focus.
   Brass on the ground is 6.58:1 and the hover tone 14.64:1, both past AA,
   and the underline means a link is never signalled by colour alone.
   focus-visible repeats site.css's global ring deliberately, so this page
   keeps its focus state even if that rule is ever scoped narrower.        */
.cards .prose a {
  color: var(--accent);
  text-decoration-thickness: 1px;
  text-underline-offset: 0.25em;
}
.cards .prose a:hover {
  color: var(--text);
  text-decoration-thickness: 2px;
}
.cards .prose a:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 3px;
  border-radius: 2px;
}

/* H1 IN FOIL, WITH A SOLID FALLBACK THAT COMES FIRST.
   `color` is set unconditionally to a light tone that reads on the dark
   ground at 15.30:1. Only inside @supports is it traded for transparent, so
   a browser without background-clip:text never renders invisible text — the
   failure mode this ordering exists to prevent. */
.cards .foil-text { color: #E8EDF2; }

@supports ((-webkit-background-clip: text) or (background-clip: text)) {
  .cards .foil-text {
    background-image: var(--foil);
    background-size: var(--foil-span);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
    animation: cards-foil-roll var(--foil-roll) linear infinite;
  }
}

/* The single divider under the hero. */
.cards .foil-rule {
  border: 0;
  height: 2px;
  border-radius: 2px;
  margin: clamp(2.25rem, 6vw, 3.25rem) 0 0;
  background-image: var(--foil);
  background-size: var(--foil-span);
  animation: cards-foil-roll var(--foil-roll) linear infinite;
}

/* --- The four steps ------------------------------------------------------
   `ol` is not touched by site.css's `ul` reset, so it is zeroed here. The
   numeral is a counter on ::before, which is what keeps the foil circles at
   exactly four with no per-item markup.                                    */
.cards .steps {
  list-style: none;
  margin: 0;
  padding: 0;
  counter-reset: cards-step;
  max-width: var(--prose);
}
.cards .steps > li {
  counter-increment: cards-step;
  position: relative;
  padding-inline-start: 3.75rem;
  min-height: 2.5rem;
}
.cards .steps > li + li { margin-block-start: 1.5rem; }
.cards .steps > li::before {
  content: counter(cards-step);
  position: absolute;
  inset-inline-start: 0;
  inset-block-start: -0.15em;
  width: 2.5rem;
  height: 2.5rem;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  background-image: var(--foil);
  background-size: var(--foil-span);
  animation: cards-foil-roll var(--foil-roll) linear infinite;
  /* Ground, not white: every stop of the foil sits at 8.26:1 or better
     against it, so the numeral holds AA wherever the sweep happens to be. */
  color: #191612;
  font-size: 0.9375rem;
  font-weight: 700;
  line-height: 1;
}

/* --- Toploaders ----------------------------------------------------------
   Three layers, outside in: the foil edge, the clear-sleeve inner edge, and
   the dark inner panel the screenshot sits on. A real toploader read, not a
   grading slab — there is no label plate and no serial strip, deliberately. */
.cards .shelf {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
  gap: clamp(0.75rem, 2.5vw, 1.5rem);
  margin-block-start: clamp(2.5rem, 6vw, 3.5rem);
}
.cards .toploader {
  margin: 0;
  padding: 3px;
  border-radius: 9px;
  background-image: var(--foil);
  background-size: var(--foil-span);
  animation: cards-foil-roll var(--foil-roll) linear infinite;
}
.cards .toploader-sleeve {
  border: 1px solid var(--sleeve);
  border-radius: 7px;
  padding: 7px;
  background-color: var(--panel);
}
.cards .toploader img {
  display: block;
  width: 100%;
  height: auto;
  border-radius: 3px;
}

/* --- Phone ---------------------------------------------------------------
   Two frames across at 400px rather than three squeezed ones. */
@media (max-width: 430px) {
  .cards .shelf { grid-template-columns: repeat(auto-fill, minmax(132px, 1fr)); }
  .cards .steps > li { padding-inline-start: 3.25rem; }
  .cards .steps > li::before { width: 2.25rem; height: 2.25rem; }
}

/* --- Reduced motion ------------------------------------------------------
   The foil STAYS; only the roll stops. Removing the gradient too would
   change the design for these users rather than calm it. A fixed position
   is set so the paused sweep is a deliberate frame, not wherever the
   animation happened to be cancelled.                                      */
@media (prefers-reduced-motion: reduce) {
  .cards .foil-text,
  .cards .foil-rule,
  .cards .steps > li::before,
  .cards .toploader {
    animation: none;
    background-position: 35% 50%;
  }
}
