/* Catalogue styles.
   Palette carried over from the storefront design system, contrast verified:
   #EDEAE4 on #131211 = 15.6:1  ·  #D8B25C on #131211 = 9.3:1
   #1A7F5E measures 3.8:1 on the background, so it is a FILL only, never text. */

:root {
  --bg: #131211;
  --surface: #1b1917;
  --surface-hi: #23211f;
  --ink: #edeae4;
  --muted: #9d9b97;
  --gold: #d8b25c;
  --green: #1a7f5e;
  --border: rgba(237, 234, 228, 0.08);
  --border-hi: rgba(237, 234, 228, 0.14);
  --page: 1200px;
  --radius: 8px;
}

*, *::before, *::after { box-sizing: border-box; }

html { -webkit-text-size-adjust: 100%; }

body {
  margin: 0;
  background: var(--bg);
  color: var(--ink);
  font-family: Inter, system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size: 16px;
  line-height: 1.55;
  -webkit-font-smoothing: antialiased;
}

h1, h2, h3 {
  font-family: Archivo, Inter, system-ui, sans-serif;
  font-weight: 700;
  line-height: 1.12;
  letter-spacing: -0.015em;
  margin: 0;
}

h1 { font-size: clamp(1.9rem, 4.2vw, 2.75rem); }
h2 { font-size: clamp(1.4rem, 3vw, 2rem); }
h3 { font-size: 1.15rem; }

a { color: var(--gold); }

img { max-width: 100%; display: block; }

.wrap {
  max-width: var(--page);
  margin: 0 auto;
  padding: 0 24px;
}

.mono {
  font-family: "IBM Plex Mono", ui-monospace, SFMono-Regular, Menlo, monospace;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  font-size: 0.75rem;
  color: var(--muted);
}

/* ---------- header ---------- */

.site-header {
  border-bottom: 1px solid var(--border);
  position: sticky;
  top: 0;
  background: rgba(19, 18, 17, 0.92);
  backdrop-filter: blur(10px);
  z-index: 20;
}

.site-header .wrap {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 20px;
  min-height: 66px;
  flex-wrap: wrap;
}

.brand {
  font-family: Archivo, sans-serif;
  font-weight: 700;
  font-size: 1.05rem;
  letter-spacing: -0.01em;
  color: var(--ink);
  text-decoration: none;
}

.brand span { color: var(--gold); }

.header-end {
  display: flex;
  align-items: center;
  gap: 24px;
  flex-wrap: wrap;
}

.site-nav { display: flex; gap: 22px; flex-wrap: wrap; }

.site-nav a {
  color: var(--muted);
  text-decoration: none;
  font-size: 0.9rem;
}

.site-nav a:hover, .site-nav a[aria-current="page"] { color: var(--ink); }

/* ---------- hero ---------- */

.hero {
  position: relative;
  border-bottom: 1px solid var(--border);
  background: #0f0e0d center / cover no-repeat;
  min-height: 340px;
  display: flex;
  align-items: flex-end;
}

/* The banner carries gold highlights that reach near-white, so the scrim goes
   heavy wherever the text sits and stays light above it. The stops are derived
   from the text block's measured position, not guessed: the hero grows to fit
   its copy, so on a wide screen the words occupy the lower half while on a
   phone they fill it almost top to bottom — hence a separate profile below.
   Worst case measured over the banner: headline 12.8:1, lede 5.5:1. */
.hero::after {
  content: "";
  position: absolute;
  inset: 0;
  background: linear-gradient(180deg,
    rgba(19,18,17,0.34) 0%,
    rgba(19,18,17,0.42) 22%,
    rgba(19,18,17,0.90) 36%,
    rgba(19,18,17,0.95) 100%);
}

.hero .wrap { position: relative; z-index: 1; padding-block: 54px 44px; }

.hero p.lede {
  color: var(--muted);
  max-width: 56ch;
  margin: 14px 0 0;
}

/* ---------- catalogue grid ---------- */

.section { padding-block: 56px; }

.section-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 16px;
  margin-bottom: 26px;
  flex-wrap: wrap;
}

.grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 26px;
}

.card {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  overflow: hidden;
  text-decoration: none;
  color: inherit;
  display: flex;
  flex-direction: column;
  transition: transform 160ms ease-out, border-color 160ms ease-out, background 160ms ease-out;
}

.card:hover, .card:focus-visible {
  transform: translateY(-2px);
  border-color: var(--border-hi);
  background: var(--surface-hi);
}

.card-media {
  position: relative;
  aspect-ratio: 1 / 1;
  background: #100f0e;
}

.card-media--photo { background: #fff; }

.card-media img { width: 100%; height: 100%; object-fit: contain; }

/* Placeholder for products with no photograph yet. Deliberately typographic
   so it reads as a catalogue convention rather than a failed image load. */
.ph {
  width: 100%; height: 100%;
  display: flex; flex-direction: column; justify-content: center; align-items: center;
  gap: 12px; padding: 22px; text-align: center;
  background:
    linear-gradient(180deg, rgba(216,178,92,0.05), transparent 60%), #100f0e;
  border-bottom: 1px solid var(--border);
}

.ph-fmt {
  font-family: "IBM Plex Mono", monospace;
  font-size: 0.62rem; letter-spacing: 0.14em; text-transform: uppercase;
  color: var(--gold);
}

.ph-title {
  font-family: Archivo, sans-serif; font-weight: 600;
  font-size: 1.02rem; line-height: 1.3; color: rgba(237,234,228,0.82);
  max-width: 16ch;
}

.badge {
  position: absolute;
  top: 10px;
  left: 10px;
  font-family: "IBM Plex Mono", monospace;
  font-size: 0.65rem;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  padding: 5px 9px;
  border-radius: 4px;
  background: var(--gold);
  color: #131211;
  font-weight: 600;
}

.badge--jp { background: var(--gold); }
.badge--en { background: var(--green); color: #fff; }

.card-body { padding: 16px 16px 18px; display: flex; flex-direction: column; gap: 8px; flex: 1; }

.card-title {
  font-family: Archivo, sans-serif;
  font-weight: 600;
  font-size: 1rem;
  line-height: 1.3;
}

.card-spec { font-family: "IBM Plex Mono", monospace; font-size: 0.7rem; letter-spacing: 0.07em; text-transform: uppercase; color: var(--muted); }

.card-foot { margin-top: auto; display: flex; flex-direction: column; gap: 3px; }

.price { font-weight: 600; font-size: 1.1rem; font-variant-numeric: tabular-nums; white-space: nowrap; }

.stock { font-family: "IBM Plex Mono", monospace; font-size: 0.7rem; letter-spacing: 0.06em; text-transform: uppercase; color: var(--muted); }

.stock--low { color: var(--gold); }

/* ---------- product detail ---------- */

.detail {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: 44px;
  padding-block: 48px;
  align-items: start;
}

.detail-media {
  background: #100f0e;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  aspect-ratio: 1 / 1;
  overflow: hidden;
}

.detail-media--photo { background: #fff; }
.detail-media img { width: 100%; height: 100%; object-fit: contain; }
.detail-media .ph-title { font-size: 1.4rem; max-width: 20ch; }

.detail dl { display: grid; grid-template-columns: max-content 1fr; gap: 8px 22px; margin: 22px 0; }
.detail dt { font-family: "IBM Plex Mono", monospace; font-size: 0.72rem; letter-spacing: 0.07em; text-transform: uppercase; color: var(--muted); }
.detail dd { margin: 0; }

.detail ul { padding-left: 18px; color: var(--ink); }
.detail ul li { margin-bottom: 5px; }

.price-row { display: flex; align-items: baseline; gap: 14px; margin: 6px 0 0; flex-wrap: wrap; }
.price-lg { font-size: 1.8rem; font-weight: 600; font-variant-numeric: tabular-nums; }

.chips { display: flex; gap: 8px; flex-wrap: wrap; margin: 18px 0 0; }
.chip { border: 1px solid var(--border-hi); border-radius: 999px; padding: 5px 12px; font-size: 0.78rem; color: var(--muted); }

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 9px;
  background: var(--green);
  color: #fff;
  text-decoration: none;
  font-weight: 600;
  padding: 13px 24px;
  /* A transparent border so a button with one and a button without are the
     same height, and vertical-align:middle so an icon inside one does not
     shift it off its neighbour's baseline. */
  border: 1px solid transparent;
  vertical-align: middle;
  border-radius: 6px;
  min-height: 48px;
  line-height: 22px;
  margin-top: 22px;
}

/* The envelope is decorative, so it never sets the line box — it rides along
   with whatever text it sits beside and takes that text's colour. */
.ico {
  flex: 0 0 auto;
  display: block;
  overflow: visible;
}

.btn:hover { background: #167052; }
.btn--ghost { background: transparent; border-color: var(--border-hi); color: var(--ink); }
.btn--ghost:hover { background: var(--surface-hi); }

.notice {
  border-left: 2px solid var(--gold);
  padding: 10px 0 10px 14px;
  color: var(--muted);
  font-size: 0.9rem;
  margin: 20px 0 0;
}

/* ---------- footer ---------- */

.site-footer {
  border-top: 1px solid var(--border);
  padding-block: 34px 44px;
  color: var(--muted);
  font-size: 0.85rem;
}

.site-footer .wrap { display: flex; gap: 22px; justify-content: space-between; flex-wrap: wrap; }
.site-footer a { color: var(--muted); }

.contact-link {
  display: inline-flex;
  align-items: center;
  gap: 7px;
}

.contact-link:hover { color: var(--ink); }

.disclaimer { max-width: 62ch; margin-top: 18px; font-size: 0.78rem; line-height: 1.5; }

/* ---------- responsive ---------- */

@media (max-width: 760px) {
  .detail { grid-template-columns: 1fr; gap: 28px; padding-block: 32px; }
  .section { padding-block: 40px; }
  .hero { min-height: 260px; }
  .site-header .wrap { min-height: 58px; padding-block: 10px; }

  /* The copy wraps to about 215px here, so a hero sized to the text alone
     leaves it almost no clear space and the banner cannot show through
     whatever the scrim does. Height is set so roughly the top third stays
     free of text, which is the part of the banner people actually see. */
  .hero { min-height: 420px; }

  .hero::after {
    background: linear-gradient(180deg,
      rgba(19,18,17,0.22) 0%,
      rgba(19,18,17,0.30) 26%,
      rgba(19,18,17,0.90) 38%,
      rgba(19,18,17,0.95) 100%);
  }
}

/* Narrower than this the copy wraps to another couple of lines and starts
   higher up the hero, so the dark part has to begin sooner. Less of the banner
   shows here than on a wider phone, which is the unavoidable trade when the
   text needs most of the height. */
@media (max-width: 400px) {
  .hero::after {
    background: linear-gradient(180deg,
      rgba(19,18,17,0.22) 0%,
      rgba(19,18,17,0.26) 15%,
      rgba(19,18,17,0.90) 25%,
      rgba(19,18,17,0.95) 100%);
  }
}

:focus-visible { outline: 2px solid var(--gold); outline-offset: 2px; }

/* ---------- category tiles ---------- */

.cats {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
  gap: 18px;
  margin-top: 22px;
}

.cat {
  display: block;
  padding: 22px 22px 20px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  text-decoration: none;
  color: inherit;
  transition: transform 160ms ease-out, border-color 160ms ease-out, background 160ms ease-out;
}

.cat:hover, .cat:focus-visible {
  transform: translateY(-2px);
  border-color: var(--border-hi);
  background: var(--surface-hi);
}

.cat h3 { margin-bottom: 8px; }
.cat p { margin: 0 0 14px; color: var(--muted); font-size: 0.92rem; }
.cat .mono { color: var(--gold); }

/* ---------- set blocks ---------- */

.setblock { margin: 0; padding-top: 48px; scroll-margin-top: 80px; }
.setblock:first-of-type { padding-top: 8px; }

.setblock .section-head {
  border-bottom: 1px solid var(--border);
  padding-bottom: 12px;
  margin-bottom: 22px;
  align-items: baseline;
}

.setblock h2 .mono { margin-left: 10px; color: var(--gold); }

/* Rows within a block sit closer together than the gap between blocks, so the
   grouping reads structurally rather than as one long undifferentiated run. */
.setblock .grid { row-gap: 20px; }

/* ---------- homepage rails ---------- */

/* One horizontally scrolling row per category, so adding products widens the
   homepage rather than lengthening it. The scrolling is CSS — the script only
   adds the arrows and the auto-advance on top. */

.rail-section + .rail-section { margin-top: 46px; }

.rail-section .section-head { margin-bottom: 18px; }

.rail-more {
  font-family: "IBM Plex Mono", monospace;
  font-size: 0.72rem;
  letter-spacing: 0.07em;
  text-transform: uppercase;
  text-decoration: none;
  white-space: nowrap;
}

.rail-more:hover { text-decoration: underline; }

.rail { position: relative; }

.rail-track {
  display: flex;
  gap: 26px;
  overflow-x: auto;
  scroll-snap-type: x proximity;
  scroll-padding-left: 2px;
  /* Room for the card's hover lift, which would otherwise be clipped. */
  padding: 4px 2px 6px;
  margin: -4px -2px -6px;
  scrollbar-width: thin;
  scrollbar-color: var(--border-hi) transparent;
  overscroll-behavior-x: contain;
}

.rail-track::-webkit-scrollbar { height: 8px; }
.rail-track::-webkit-scrollbar-track { background: transparent; }
.rail-track::-webkit-scrollbar-thumb {
  background: var(--border-hi);
  border-radius: 4px;
}

.rail-track > .card {
  flex: 0 0 clamp(150px, 40vw, 260px);
  scroll-snap-align: start;
}

.rail-nav {
  position: absolute;
  top: calc(50% - 40px);
  transform: translateY(-50%);
  z-index: 2;
  width: 38px;
  height: 38px;
  border-radius: 50%;
  border: 1px solid var(--border-hi);
  background: rgba(19, 18, 17, 0.92);
  color: var(--ink);
  font-size: 1.4rem;
  line-height: 1;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  opacity: 0;
  transition: opacity 140ms ease-out, background 140ms ease-out;
}

.rail:hover .rail-nav,
.rail-nav:focus-visible { opacity: 1; }

.rail-nav:hover { background: var(--surface-hi); }
.rail-nav:disabled { opacity: 0 !important; pointer-events: none; }
.rail-nav--prev { left: -6px; }
.rail-nav--next { right: -6px; }

/* Touch devices have no hover to reveal the arrows, and swiping is the
   native gesture there, so the arrows stay out of the way. */
@media (hover: none) {
  .rail-nav { display: none; }
}

@media (max-width: 560px) {
  .rail-track { gap: 12px; }
  .rail-section + .rail-section { margin-top: 34px; }
}

/* ---------- game bands ---------- */

/* Every category splits by game first, then by set (or grading company). The
   game heading is the louder of the two so the two levels stay readable when a
   game holds a lot of sets. */
.gameband { padding-top: 18px; scroll-margin-top: 80px; }
.gameband + .gameband { padding-top: 56px; }

.gameband-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 16px;
  flex-wrap: wrap;
  padding-bottom: 10px;
  border-bottom: 1px solid var(--border-hi);
}

.gameband-head h2 { font-size: clamp(1.5rem, 3.2vw, 2.1rem); }

.gameband .setblock:first-of-type { padding-top: 30px; }
.gameband .setblock h3 { font-family: Archivo, sans-serif; font-size: 1.25rem; }
.gameband .setblock .section-head { border-bottom-color: var(--border); }

/* ---------- search ---------- */

.search { position: relative; margin: 0; }

.search input {
  width: 210px;
  max-width: 100%;
  padding: 8px 12px;
  border-radius: 6px;
  border: 1px solid var(--border-hi);
  background: var(--surface);
  color: var(--ink);
  font: inherit;
  font-size: 0.88rem;
  -webkit-appearance: none;
  appearance: none;
}

.search input::placeholder { color: var(--muted); }
.search input:focus { border-color: var(--gold); outline: none; }

.search-panel {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  width: min(380px, calc(100vw - 48px));
  background: var(--surface);
  border: 1px solid var(--border-hi);
  border-radius: var(--radius);
  box-shadow: 0 18px 40px rgba(0, 0, 0, 0.5);
  max-height: min(420px, 70vh);
  overflow-y: auto;
  z-index: 30;
}

.search-results { list-style: none; margin: 0; padding: 6px; }

.search-results a {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 8px;
  border-radius: 6px;
  text-decoration: none;
  color: var(--ink);
}

.search-results a:hover,
.search-results [aria-selected="true"] a { background: var(--surface-hi); }

.search-thumb {
  flex: 0 0 44px;
  width: 44px;
  height: 44px;
  border-radius: 4px;
  overflow: hidden;
  background: #fff;
}

.search-thumb img { width: 100%; height: 100%; object-fit: contain; }
.search-thumb-blank { display: block; width: 100%; height: 100%; background: #100f0e; }

.search-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; flex: 1; }

.search-title {
  font-size: 0.88rem;
  font-weight: 600;
  line-height: 1.25;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.search-meta {
  font-family: "IBM Plex Mono", monospace;
  font-size: 0.65rem;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: var(--muted);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.search-price {
  font-size: 0.82rem;
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.search-empty { padding: 14px 12px; color: var(--muted); font-size: 0.88rem; }

@media (max-width: 760px) {
  .header-end { width: 100%; gap: 12px; }
  .search { width: 100%; order: -1; }
  .search input { width: 100%; }
  .search-panel { right: auto; left: 0; width: 100%; }
}

/* ---------- phone product grid ---------- */

/* Phones get two products per row instead of one, so a set is scannable
   without a lot of scrolling. Only the product cards shrink — page structure,
   headings and the rest of the site are untouched, and nothing above this
   width changes at all. */
@media (max-width: 560px) {
  .grid {
    grid-template-columns: repeat(auto-fill, minmax(148px, 1fr));
    gap: 12px;
  }

  .setblock .grid { row-gap: 12px; }

  .card-body { padding: 10px 10px 12px; gap: 5px; }
  .card-title { font-size: 0.85rem; line-height: 1.25; }
  .card-spec { font-size: 0.6rem; letter-spacing: 0.05em; }
  .card-foot { gap: 2px; }
  .price { font-size: 0.95rem; }
  .stock { font-size: 0.6rem; }

  .badge { font-size: 0.55rem; padding: 3px 6px; top: 6px; left: 6px; }

  .ph { padding: 12px; gap: 8px; }
  .ph-fmt { font-size: 0.55rem; letter-spacing: 0.1em; }
  .ph-title { font-size: 0.8rem; max-width: 14ch; }
}
