/* Solitaire Nest — styles.css
   4 themes as CSS-variable sets toggled by <html data-theme>. No external assets. */

*, *::before, *::after { box-sizing: border-box; }
html, body { margin: 0; padding: 0; }

:root {
  --sans: -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
  --gap: clamp(3px, 1vw, 8px);
  --cw: 66px;              /* set at runtime by ui.js layout() */
  --ch: 92px;
  --ring: #4f8cff;
}

/* ============================ THEMES ============================ */
/* Felt & Brass (default) */
:root, :root[data-theme="felt"] {
  --page: #142b20; --panel: #1c3428; --line: rgba(212,175,95,.18); --muted: #9fb3a6; --ink: #f4ecd7;
  --accent: #d4af5f; --ring: #4f8cff;
  --scene-bg: radial-gradient(120% 120% at 50% 0%, #2a634c 0%, #1a4636 55%, #123528 100%);
  --scene-tex: repeating-linear-gradient(115deg, rgba(255,255,255,.02) 0 2px, transparent 2px 5px);
  --scene-shadow: 0 20px 50px -22px rgba(0,0,0,.55); --scene-border: 1px solid rgba(212,175,95,.22);
  --stext: #f2ead6; --card-r: 8px;
  --card: #f8f2e4; --card-border: 1px solid #e7dcc2; --card-shadow: 0 3px 7px rgba(0,0,0,.28);
  --card-shadow-hover: 0 12px 22px rgba(0,0,0,.38); --red: #b23a2e; --black: #26221a;
  --back: repeating-linear-gradient(45deg,#1c4a39 0 7px,#245a45 7px 14px);
  --slot-line: rgba(212,175,95,.5); --slot-bg: transparent;
  --display: Georgia, "Times New Roman", serif; --display-w: 600; --display-ls: .005em;
  --logo-bg: linear-gradient(#d4af5f,#b78e3d); --logo-shadow: 0 2px 6px rgba(0,0,0,.3);
  --chip: rgba(9,32,24,.72); --chip-text: #efe6cf; --chip-border: 1px solid rgba(212,175,95,.28); --chip-r: 10px;
  --btn: linear-gradient(#e3c877,#cda447); --btn-text: #26221a; --btn-shadow: 0 3px 0 #9c7a34; --btn-r: 999px;
  --tile: rgba(9,32,24,.55); --tile-text: #efe6cf; --tile-border: 1px solid rgba(212,175,95,.22); --tile-r: 14px; --tile-shadow: none;
  --sel: #ffd76a; --drop: #6ee7a8;
}
/* Sunroom */
:root[data-theme="sun"] {
  --page: #fdf3e6; --panel: #fffaf1; --line: #eeddc6; --muted: #8a7358; --ink: #5c4636;
  --accent: #e2914b; --ring: #3b6fe0;
  --scene-bg: linear-gradient(165deg,#fdeed9 0%,#f6d8bb 100%);
  --scene-tex: radial-gradient(circle at 15% 20%, rgba(255,255,255,.5) 0, transparent 40%);
  --scene-shadow: 0 20px 46px -24px rgba(140,90,50,.4); --scene-border: 1px solid #efd9c0;
  --stext: #5c4636; --card-r: 13px;
  --card: #fffaf1; --card-border: 1px solid #ecddc8; --card-shadow: 0 4px 10px rgba(150,110,70,.22);
  --card-shadow-hover: 0 14px 24px rgba(150,110,70,.3); --red: #d8635a; --black: #584f5c;
  --back: radial-gradient(circle at 3px 3px, #cfe0c4 2px, transparent 2.4px) 0 0/9px 9px, #9db98f;
  --slot-line: #c9a982; --slot-bg: rgba(255,255,255,.35);
  --display: "Trebuchet MS", var(--sans); --display-w: 700; --display-ls: .01em;
  --logo-bg: linear-gradient(#f2b06a,#e2914b); --logo-shadow: 0 3px 8px rgba(200,130,70,.35);
  --chip: #fffaf1; --chip-text: #7a6449; --chip-border: 1px solid #eeddc6; --chip-r: 12px;
  --btn: linear-gradient(#e79a52,#dd8440); --btn-text: #fff; --btn-shadow: 0 3px 0 #b96a2e; --btn-r: 12px;
  --tile: #fffaf1; --tile-text: #6a563f; --tile-border: 1px solid #eedfc8; --tile-r: 16px; --tile-shadow: 0 4px 12px rgba(150,110,70,.14);
  --sel: #f0a35a; --drop: #7bbf7e;
}
/* Playful Pop */
:root[data-theme="pop"] {
  --page: #eafaf4; --panel: #ffffff; --line: #171633; --muted: #5a5975; --ink: #171633;
  --accent: #ff7a45; --ring: #5b6cff;
  --scene-bg: #6fc6b4; --scene-tex: radial-gradient(circle at 4px 4px, rgba(255,255,255,.35) 2px, transparent 2.5px) 0 0/22px 22px;
  --scene-shadow: 0 18px 0 -6px rgba(23,22,51,.12); --scene-border: 2.5px solid #171633;
  --stext: #171633; --card-r: 12px;
  --card: #ffffff; --card-border: 2.5px solid #171633; --card-shadow: 3px 4px 0 rgba(23,22,51,.9);
  --card-shadow-hover: 5px 7px 0 rgba(23,22,51,.9); --red: #ef476f; --black: #171633;
  --back: repeating-linear-gradient(45deg,#ff7a45 0 9px,#5b6cff 9px 18px);
  --slot-line: #171633; --slot-bg: rgba(255,255,255,.28);
  --display: var(--sans); --display-w: 900; --display-ls: -.02em;
  --logo-bg: #ffd166; --logo-shadow: 2px 3px 0 #171633;
  --chip: #171633; --chip-text: #fff; --chip-border: none; --chip-r: 11px;
  --btn: #ff7a45; --btn-text: #fff; --btn-shadow: 3px 4px 0 #171633; --btn-r: 12px;
  --tile: #fff; --tile-text: #171633; --tile-border: 2.5px solid #171633; --tile-r: 14px; --tile-shadow: 3px 4px 0 rgba(23,22,51,.9);
  --sel: #ffd166; --drop: #06d6a0;
}
/* Midnight Lounge */
:root[data-theme="mid"] {
  --page: #14161d; --panel: #1c1f27; --line: #2c303b; --muted: #9b9280; --ink: #ece0c9;
  --accent: #e6b365; --ring: #7aa0ff;
  --scene-bg: radial-gradient(120% 130% at 50% -10%, #294241 0%, #1b2a2e 50%, #14161d 100%);
  --scene-tex: radial-gradient(circle at 50% 40%, rgba(230,179,101,.10) 0, transparent 55%);
  --scene-shadow: 0 22px 52px -20px rgba(0,0,0,.7); --scene-border: 1px solid rgba(230,179,101,.2);
  --stext: #ece0c9; --card-r: 9px;
  --card: #f2e9d5; --card-border: 1px solid rgba(230,179,101,.35); --card-shadow: 0 4px 14px rgba(0,0,0,.45);
  --card-shadow-hover: 0 14px 28px rgba(0,0,0,.55), 0 0 0 1px rgba(230,179,101,.5); --red: #dd6551; --black: #2b2620;
  --back: radial-gradient(circle at 4px 4px, rgba(230,179,101,.4) 1.6px, transparent 2px) 0 0/11px 11px, #1e3a37;
  --slot-line: rgba(230,179,101,.45); --slot-bg: rgba(255,255,255,.03);
  --display: "Palatino Linotype", Georgia, serif; --display-w: 600; --display-ls: .01em;
  --logo-bg: linear-gradient(#e6b365,#c8934a); --logo-shadow: 0 0 14px rgba(230,179,101,.45);
  --chip: rgba(12,16,20,.6); --chip-text: #ecdfc6; --chip-border: 1px solid rgba(230,179,101,.22); --chip-r: 10px;
  --btn: linear-gradient(#e6b365,#cf9a4f); --btn-text: #20242b; --btn-shadow: 0 0 16px rgba(230,179,101,.4); --btn-r: 999px;
  --tile: rgba(12,18,20,.5); --tile-text: #ecdfc6; --tile-border: 1px solid rgba(230,179,101,.2); --tile-r: 14px; --tile-shadow: none;
  --sel: #f0c674; --drop: #4fd08a;
}

/* ============================ BASE ============================ */
body {
  background: var(--page); color: var(--ink); font-family: var(--sans);
  -webkit-font-smoothing: antialiased; line-height: 1.5;
  padding-bottom: env(safe-area-inset-bottom);
}
a { color: inherit; }
h1, h2, h3 { font-family: var(--display); font-weight: var(--display-w); letter-spacing: var(--display-ls); }
:focus-visible { outline: 2px solid var(--ring); outline-offset: 2px; border-radius: 4px; }
button { font: inherit; }

/* ============================ TOP BAR ============================ */
.topbar {
  position: sticky; top: 0; z-index: 40;
  background: color-mix(in srgb, var(--page) 92%, transparent);
  backdrop-filter: blur(8px);
  border-bottom: 1px solid var(--line);
  padding: calc(8px + env(safe-area-inset-top)) clamp(8px, 2vw, 16px) 8px;
}
.topbar-inner { max-width: 1040px; margin: 0 auto; display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.brand { display: flex; align-items: center; gap: 9px; margin-right: auto; }
.logo { width: 34px; height: 34px; border-radius: 10px; display: grid; place-items: center; font-size: 19px;
  background: var(--logo-bg); box-shadow: var(--logo-shadow); flex: 0 0 auto; }
.brand .word { font-family: var(--display); font-weight: var(--display-w); font-size: 18px; letter-spacing: var(--display-ls); line-height: 1.05; }
.brand .word small { display: block; font-family: var(--sans); font-weight: 700; font-size: 12px; letter-spacing: .12em; text-transform: uppercase; color: var(--accent); margin-top: 2px; }
.chips { display: flex; gap: 6px; }
.chip { background: var(--chip); color: var(--chip-text); border: var(--chip-border); border-radius: var(--chip-r); padding: 5px 9px;
  display: flex; flex-direction: column; align-items: flex-start; min-width: 48px; }
.chip b { font-size: 14px; font-variant-numeric: tabular-nums; line-height: 1.1; }
.chip span { font-size: 8.5px; letter-spacing: .1em; text-transform: uppercase; opacity: .7; }

/* Toolbar row */
.toolbar { max-width: 1040px; margin: 8px auto 0; display: flex; gap: 6px; flex-wrap: wrap; align-items: center; }
.tbtn { border: 1px solid var(--line); background: var(--panel); color: var(--ink); cursor: pointer;
  font-size: 13px; font-weight: 600; padding: 7px 12px; border-radius: 999px; display: inline-flex; align-items: center; gap: 6px;
  transition: transform .12s ease, background .12s; }
.tbtn:hover { background: color-mix(in srgb, var(--panel) 80%, var(--ink) 6%); }
.tbtn:active { transform: translateY(1px); }
.tbtn[aria-pressed="true"], .tbtn.on { background: var(--ink); color: var(--page); border-color: var(--ink); }
.tbtn.hidden { display: none; }
.tbtn.primary { background: var(--accent); color: #fff; border-color: transparent; }

/* Mobile "More" overflow menu: on small screens the secondary actions collapse behind one ⋯
   button so the toolbar stays a single clean row. On desktop everything flows inline as before. */
.tb-more { display: none; }
.more-menu { display: contents; }
/* "Big" (bigger cards/text) is an accessibility control — keep its label visible even on mobile
   where other button labels collapse to icons, so it's easy to find for low-vision users. */
.tb-big .txt { display: inline !important; }
.tb-big[aria-pressed="true"] { background: var(--accent); color: #fff; border-color: transparent; }
@media (max-width: 900px) {
  .toolbar { position: relative; }
  .tb-more { display: inline-flex; }
  .more-menu {
    display: none; position: absolute; top: calc(100% + 6px); right: 0; z-index: 41;
    flex-direction: column; align-items: stretch; gap: 6px; padding: 8px; min-width: 178px;
    background: var(--panel); border: 1px solid var(--line); border-radius: 14px;
    box-shadow: 0 14px 34px rgba(0,0,0,.45);
  }
  .more-menu.open { display: flex; }
  .more-menu .tbtn { justify-content: flex-start; width: 100%; border-radius: 10px; }
  .more-menu .tbtn .txt { display: inline !important; } /* labels always visible inside the menu */
}

/* Main button (mockup style) */
.btn { font-weight: 700; font-size: 13.5px; cursor: pointer; border: none; padding: 9px 15px;
  border-radius: var(--btn-r); background: var(--btn); color: var(--btn-text); box-shadow: var(--btn-shadow); transition: transform .12s ease; }
.btn:active { transform: translateY(1px); }
.btn.ghost { background: var(--panel); color: var(--ink); border: 1px solid var(--line); box-shadow: none; }

/* ============================ BOARD (scene) ============================ */
.stage { max-width: 1040px; margin: 12px auto; padding: 0 clamp(6px, 2vw, 16px); }
.board {
  border-radius: 22px; padding: clamp(10px, 2.5vw, 20px); position: relative; overflow: hidden;
  background: var(--scene-bg); color: var(--stext); box-shadow: var(--scene-shadow); border: var(--scene-border);
  transition: background .3s ease;
}
.board::after { content: ""; position: absolute; inset: 0; pointer-events: none; background: var(--scene-tex); opacity: 1; }
.board > * { position: relative; z-index: 1; }

/* Top grid: stock, waste, spacer, 4 foundations — aligned to tableau columns */
.topgrid { display: grid; grid-template-columns: repeat(7, var(--cw)); gap: var(--gap); justify-content: center; margin-bottom: 12px; }
.tableau { display: grid; grid-template-columns: repeat(7, var(--cw)); gap: var(--gap); justify-content: center; align-items: start; }

.col { display: flex; flex-direction: column; min-height: var(--ch); position: relative; }
/* vertical overlap: less for face-up (show rank), more for face-down */
.col > .card + .card, .col > .card + .down { margin-top: calc(var(--ch) * -0.66); }
.col > .down + .card, .col > .down + .down { margin-top: calc(var(--ch) * -0.82); }

/* Drop-zone highlight on columns/foundations */
.dropzone.valid-target::after { content: ""; position: absolute; inset: -3px; border-radius: calc(var(--card-r) + 4px);
  box-shadow: 0 0 0 2px var(--drop), 0 0 14px var(--drop); pointer-events: none; z-index: 8; }
.col.dropzone { min-width: var(--cw); }

/* ============================ CARDS ============================ */
.card, .down, .slot { width: var(--cw); height: var(--ch); border-radius: var(--card-r); box-sizing: border-box; flex: 0 0 auto; }
.slot { border: 1.5px dashed var(--slot-line); display: grid; place-items: center; color: var(--slot-line);
  font-size: calc(var(--cw) * 0.42); background: var(--slot-bg); }
.card {
  background: var(--card); border: var(--card-border); box-shadow: var(--card-shadow); position: relative;
  font-family: Georgia, serif; user-select: none; -webkit-user-select: none; cursor: grab;
  font-size: calc(var(--cw) * 0.2); transition: transform .13s ease, box-shadow .13s ease;
  touch-action: none;
}
.card .corner { position: absolute; font-weight: 700; line-height: .9; text-align: center; letter-spacing: -.02em; white-space: nowrap; }
.card .corner.tl { top: .34em; left: .42em; }
.card .corner.br { bottom: .34em; right: .42em; transform: rotate(180deg); }
.card .pip { position: absolute; inset: 0; display: grid; place-items: center; font-size: 2.1em; }
.card.red { color: var(--red); }
.card.black { color: var(--black); }
.card.dim { opacity: .38; }
.card.selected { box-shadow: 0 0 0 2px var(--sel), 0 0 16px var(--sel), var(--card-shadow); transform: translateY(-4px); z-index: 6; }
.card.hintpulse { animation: hintpulse .6s ease 2; }
@keyframes hintpulse { 0%,100% { box-shadow: var(--card-shadow); } 50% { box-shadow: 0 0 0 3px var(--drop), 0 0 18px var(--drop); } }
@media (hover: hover) {
  /* Hover feedback with NO geometry change (no transform) so it can never flicker at the
     bottom edge. Instead the active card lights up + gains a tight, connected lift-shadow,
     which reads as intentional rather than a big detached float. */
  .col > .card:last-child:hover, .waste .card:last-child:hover {
    box-shadow: var(--card-shadow), 0 7px 16px -6px rgba(0,0,0,.5);
    filter: brightness(1.06); z-index: 5;
  }
}

/* Face-down card + its frame + back patterns */
.down { background: var(--back); border: var(--card-border); box-shadow: var(--card-shadow); position: relative; overflow: hidden; cursor: default; }
.down::before { content: ""; position: absolute; inset: 3px; border-radius: calc(var(--card-r) - 2px);
  border: 1.5px solid rgba(255,255,255,.22); box-shadow: inset 0 0 0 1px rgba(0,0,0,.12); pointer-events: none; }
.down.back-1 { background: repeating-linear-gradient(45deg,#22355c 0 7px,#2f4a7e 7px 14px); }
.down.back-2 { background: radial-gradient(circle at 4px 4px, #e7b6c6 2px, transparent 2.4px) 0 0/11px 11px, #7a2f45; }
.down.back-3 { background:
    linear-gradient(45deg, rgba(255,255,255,.18) 25%, transparent 25%, transparent 75%, rgba(255,255,255,.18) 75%) 0 0/16px 16px,
    linear-gradient(-45deg, rgba(0,0,0,.12) 25%, transparent 25%, transparent 75%, rgba(0,0,0,.12) 75%) 8px 8px/16px 16px, #2f6d5b; }
.down.back-4 { background: conic-gradient(from 0deg at 50% 50%, #3b2f6e 0 30deg, #52449a 30deg 60deg) ; }
.down.back-5 { background:
    repeating-linear-gradient(0deg, rgba(255,255,255,.16) 0 1.5px, transparent 1.5px 9px),
    repeating-linear-gradient(90deg, rgba(255,255,255,.16) 0 1.5px, transparent 1.5px 9px), #8a3a2e; }
.down.back-6 { background: repeating-linear-gradient(135deg,#0f766e 0 8px,#115e59 8px 16px),
    repeating-linear-gradient(45deg,#0f766e 0 8px,#134e4a 8px 16px); background-blend-mode: multiply; }
.down.back-7 { background: radial-gradient(circle at 6px 6px, rgba(255,255,255,.28) 3.5px, transparent 4px) 0 0/16px 16px, #464a8a; }
.down.back-8 { background: repeating-linear-gradient(90deg,#1f3a34 0 6px,#2c5a4d 6px 12px, #d4af5f 12px 13px, #2c5a4d 13px 14px); }
.down.back-custom { background-size: cover; background-position: center; }

/* Stock / waste */
.stockcell, .wastecell, .foundcell { position: relative; width: var(--cw); height: var(--ch); }
.wastecell { overflow: visible; }
.waste { display: flex; }
.waste .card + .card { margin-left: calc(var(--cw) * -0.66); }
.stock-empty { display: grid; place-items: center; font-size: calc(var(--cw) * 0.4); border: 1.5px dashed var(--slot-line); color: var(--slot-line); border-radius: var(--card-r); width: var(--cw); height: var(--ch); cursor: pointer; }
.stockcell { cursor: pointer; }
.stock-count { position: absolute; bottom: -2px; right: -2px; background: var(--ink); color: var(--page); font-size: 9px; font-weight: 700; border-radius: 8px; padding: 1px 5px; z-index: 3; }

/* Foundation empty slot suit ghost */
.foundcell .slot { opacity: .9; }

/* ============================ PANELS / MODALS ============================ */
.backdrop { position: fixed; inset: 0; z-index: 60; background: rgba(0,0,0,.5); display: grid; place-items: center; padding: 16px; }
.backdrop[hidden] { display: none; }
.panel { background: var(--panel); color: var(--ink); border: 1px solid var(--line); border-radius: 18px; padding: 18px 18px 20px;
  max-width: 440px; width: 100%; max-height: 88vh; overflow: auto; box-shadow: 0 24px 60px -20px rgba(0,0,0,.5); }
.panel h2 { margin: 0 0 4px; font-size: 20px; }
.panel .sub { color: var(--muted); font-size: 13px; margin: 0 0 14px; }
.panel .row { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 9px 0; border-top: 1px solid var(--line); }
.panel .row:first-of-type { border-top: none; }
.panel .label b { display: block; font-size: 14px; }
.panel .label span { display: block; font-size: 12px; color: var(--muted); }
.panel-head { display: flex; align-items: center; justify-content: space-between; margin-bottom: 8px; }
.xbtn { border: none; background: transparent; color: var(--muted); font-size: 22px; line-height: 1; cursor: pointer; padding: 4px 8px; border-radius: 8px; }
.xbtn:hover { background: color-mix(in srgb, var(--panel) 80%, var(--ink) 8%); }
.savednote { display: flex; align-items: center; gap: 7px; font-size: 12px; color: var(--muted); margin: 10px 0 0; }
.savednote .tick { color: #3f9d6b; font-weight: 800; }

/* Theme swatches */
.swatches, .backs { display: grid; grid-template-columns: repeat(4, 1fr); gap: 10px; margin-top: 4px; }
.swatch { border: 2px solid var(--line); border-radius: 12px; padding: 8px; cursor: pointer; background: var(--panel); text-align: center; font-size: 11px; font-weight: 700; color: var(--ink); }
.swatch .prev { height: 46px; border-radius: 8px; margin-bottom: 6px; border: 1px solid rgba(0,0,0,.15); }
.swatch[aria-pressed="true"] { border-color: var(--accent); box-shadow: 0 0 0 2px var(--accent); }
.prev.felt { background: radial-gradient(120% 120% at 50% 0%, #2a634c, #123528); }
.prev.sun { background: linear-gradient(165deg,#fdeed9,#f6d8bb); }
.prev.pop { background: #6fc6b4; }
.prev.mid { background: radial-gradient(120% 130% at 50% -10%, #294241, #14161d); }

.backs { grid-template-columns: repeat(4, 1fr); }
.backswatch { aspect-ratio: 5/7; border-radius: 10px; cursor: pointer; border: 2px solid var(--line); position: relative; overflow: hidden; }
.backswatch[aria-pressed="true"] { border-color: var(--accent); box-shadow: 0 0 0 2px var(--accent); }
.backswatch .down { width: 100%; height: 100%; border-radius: 8px; }
.uploadrow { margin-top: 12px; display: flex; flex-direction: column; gap: 6px; }
.uploadrow input[type=file] { font-size: 12px; }

/* Toggle switch */
.switch { position: relative; width: 46px; height: 26px; flex: 0 0 auto; }
.switch input { opacity: 0; width: 0; height: 0; }
.switch .track { position: absolute; inset: 0; background: var(--line); border-radius: 999px; transition: background .15s; cursor: pointer; }
.switch .track::before { content: ""; position: absolute; top: 3px; left: 3px; width: 20px; height: 20px; background: #fff; border-radius: 50%; transition: transform .15s; box-shadow: 0 1px 3px rgba(0,0,0,.3); }
.switch input:checked + .track { background: var(--accent); }
.switch input:checked + .track::before { transform: translateX(20px); }
.switch input:focus-visible + .track { outline: 2px solid var(--ring); outline-offset: 2px; }

/* Stats grid */
.statgrid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; margin-top: 6px; }
.statcell { background: color-mix(in srgb, var(--panel) 85%, var(--ink) 5%); border: 1px solid var(--line); border-radius: 12px; padding: 10px; text-align: center; }
.statcell b { display: block; font-size: 20px; font-variant-numeric: tabular-nums; }
.statcell span { font-size: 11px; color: var(--muted); }

/* Drag ghost */
#dragLayer { position: fixed; left: 0; top: 0; z-index: 80; pointer-events: none; }
#dragLayer .card + .card { margin-top: calc(var(--ch) * -0.66); }
/* Drag juice: the picked-up run lifts, tilts, and casts a deep shadow while held. */
#dragLayer .card { box-shadow: 0 16px 26px rgba(0,0,0,.34), var(--card-shadow-hover); }
#dragLayer { transform-origin: center; }
#dragLayer .card:first-child { transform: rotate(-2deg) scale(1.05); transition: transform .08s ease; }
@media (prefers-reduced-motion: reduce){ #dragLayer .card:first-child { transform: none; } }

/* Win / confetti */
.confetti { position: fixed; inset: 0; z-index: 55; pointer-events: none; overflow: hidden; }
.confetti i { position: absolute; width: 9px; height: 14px; top: -20px; border-radius: 2px; animation: fall linear forwards; }
@keyframes fall { to { transform: translateY(110vh) rotate(720deg); opacity: .9; } }
#winRecord { margin: 0 0 12px; font-weight: 700; color: var(--accent); font-size: 14px; }

/* Invalid-move shake */
.shake { animation: shake .3s ease; }
@keyframes shake { 10%,90% { transform: translateX(-2px); } 30%,70% { transform: translateX(4px); } 50% { transform: translateX(-4px); } }

/* Deal-in: columns cascade up when a new hand is dealt */
.board.dealin .col, .board.dealin #topgrid > * { animation: dealin .4s ease both; }
.board.dealin .col:nth-child(1) { animation-delay: .02s; } .board.dealin .col:nth-child(2) { animation-delay: .05s; }
.board.dealin .col:nth-child(3) { animation-delay: .08s; } .board.dealin .col:nth-child(4) { animation-delay: .11s; }
.board.dealin .col:nth-child(5) { animation-delay: .14s; } .board.dealin .col:nth-child(6) { animation-delay: .17s; }
.board.dealin .col:nth-child(7) { animation-delay: .20s; }
@keyframes dealin { from { opacity: 0; transform: translateY(14px); } to { opacity: 1; transform: none; } }

/* ============================ SEO CONTENT ============================ */
.content { max-width: 760px; margin: 32px auto 0; padding: 0 20px 64px; }
.content h1 { font-size: clamp(22px, 4vw, 30px); margin: 0 0 6px; }
.content h2 { font-size: 20px; margin: 28px 0 8px; }
.content p, .content li { font-size: 15px; color: var(--ink); }
.content .lede { color: var(--muted); font-size: 16px; }
.content ul, .content ol { padding-left: 20px; }
.content li { margin: 4px 0; }
.moregames { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 12px; margin-top: 12px; list-style: none; padding: 0; }
.moregames a { display: flex; align-items: center; gap: 11px; background: var(--tile); color: var(--tile-text); border: var(--tile-border); border-radius: var(--tile-r); box-shadow: var(--tile-shadow); padding: 12px 14px; text-decoration: none; transition: transform .13s ease; }
.moregames a:hover { transform: translateY(-3px); }
.moregames b { font-family: var(--display); font-weight: var(--display-w); font-size: 15px; display: block; }
.moregames span { font-size: 11px; opacity: .7; }
/* Uniform card height: li fills the grid cell, the card fills the li, min-height floors 1- vs 2-line copy. */
.moregames > li { display: flex; }
.moregames a { flex: 1; min-height: 76px; }
.fan { width: 30px; height: 34px; position: relative; flex: 0 0 auto; }
.fan i { position: absolute; width: 16px; height: 22px; border-radius: 4px; background: var(--card); border: var(--card-border); box-shadow: 0 1px 2px rgba(0,0,0,.2); top: 6px; }
.fan i:nth-child(1) { left: 0; transform: rotate(-16deg); }
.fan i:nth-child(2) { left: 7px; top: 3px; }
.fan i:nth-child(3) { left: 14px; transform: rotate(16deg); }
.foot { max-width: 760px; margin: 0 auto; padding: 18px 20px calc(28px + env(safe-area-inset-bottom)); color: var(--muted); font-size: 12.5px; border-top: 1px solid var(--line); }
.foot a { color: var(--accent); }

.cta { display: inline-block; margin: 14px 0; background: var(--accent); color: #fff; text-decoration: none; font-weight: 700; padding: 11px 18px; border-radius: 12px; }

/* Visually hidden (for a11y labels) */
.sr-only { position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0,0,0,0); white-space: nowrap; border: 0; }

/* ============================ RESPONSIVE ============================ */
@media (max-width: 560px) {
  .brand .word small { display: block; font-size: 11px; }
  .chip { min-width: 42px; padding: 4px 7px; }
  .chip b { font-size: 13px; }
  .toolbar { gap: 5px; }
  .tbtn { padding: 6px 10px; font-size: 12px; }
}
@media (max-width: 380px) {
  .tbtn .txt { display: none; }
  .tbtn { padding: 7px 9px; }
}

/* ---- Mobile LANDSCAPE = immersive play. Landscape is short on height, so the top bar + the SEO
   text + the footer would squeeze the board and force scrolling. Here we drop all of that, lock
   every scroll axis (no 4-way scroll), give the board the whole screen, and leave just a small site
   name in the corner. Tap the name to reveal the controls as a slim top overlay; tap again to hide. */
/* Hidden by default; the landscape block below (later in source) flips it to flex when matched.
   NOTE: this MUST come before the @media rule — media queries don't add specificity, so a later
   equal-specificity rule wins regardless of the query. (This ordering bug hid the rail entirely.) */
.land-rail { display: none; }
@media (orientation: landscape) and (max-height: 540px) {
  html, body { overflow: hidden; height: 100dvh; overscroll-behavior: none; }
  .topbar, .content, .foot { display: none; }
  main { height: 100dvh; margin: 0; }
  /* reserve the left strip for the rail so the board sits fully to its right (never under it) */
  .stage { margin: 0; padding: 0 clamp(4px, 1.5vw, 14px) 0 calc(100px + env(safe-area-inset-left)); max-width: none; height: 100dvh; display: grid; place-items: center; }
  .board { height: 100dvh; width: 100%; border-radius: 0; padding: 6px clamp(4px, 1.4vw, 12px); box-sizing: border-box; display: flex; flex-direction: column; justify-content: center; }
  .topgrid { margin-bottom: 6px; }
  /* dynamic fan — shared.js sizes --stackpx so the tallest column fits the height (fills space, no clip) */
  .col > .card + .card, .col > .card + .down, .col > .down + .card, .col > .down + .down { margin-top: calc(var(--stackpx, 20px) - var(--ch)); }
  .land-rail { display: flex; }
  /* the Pip mascot + its recall button cover cards on a small landscape screen — hide in immersive mode */
  #pip-root, #pip-recall { display: none !important; }
  /* streak pill defaults to top-CENTER (over the foundations here) — move it to the reserved left
     strip, top corner, clear of the cards. !important: streak.js injects its style after this file. */
  #sn-streak { top: calc(5px + env(safe-area-inset-top)) !important; left: calc(6px + env(safe-area-inset-left)) !important; right: auto !important; transform: none !important; z-index: 66; }
  #sn-streak-cal { top: 40px !important; left: calc(6px + env(safe-area-inset-left)) !important; transform: none !important; }
  /* ℹ️ info overlay — this game's description/rules (the hidden .content) as a full scrollable modal */
  html[data-landinfo] .content { display: block; position: fixed; inset: 0; z-index: 80; margin: 0; max-width: none; overflow-y: auto; -webkit-overflow-scrolling: touch; overscroll-behavior: contain; background: color-mix(in srgb, var(--page) 97%, #000 3%); padding: calc(16px + env(safe-area-inset-top)) clamp(16px, 6vw, 64px) 44px; }
  html[data-landinfo] .content h1 { margin-top: 6px; }
  html[data-landinfo] .land-info-close { display: flex; }
  /* tapped name → slim toolbar overlay (just the buttons), so New/Undo/Hint stay reachable */
  html[data-landbar] .topbar { display: block; position: fixed; inset: 0 0 auto 0; z-index: 70; padding: calc(4px + env(safe-area-inset-top)) 8px 4px; background: color-mix(in srgb, var(--page) 94%, transparent); backdrop-filter: blur(8px); border-bottom: 1px solid var(--line); }
  html[data-landbar] .topbar-inner { display: none; }
  html[data-landbar] .toolbar { margin: 0; justify-content: center; }
}
/* Landscape rail (injected by shared.js) — site name + other-game links in the empty side space.
   Hidden except in the landscape immersive mode above. */
.land-rail { flex-direction: column; gap: 3px; position: fixed; left: calc(3px + env(safe-area-inset-left)); top: 50%; transform: translateY(-50%); z-index: 65; width: 78px; box-sizing: border-box; max-height: 96dvh; overflow-y: auto; overscroll-behavior: contain; padding: 3px; scrollbar-width: none; }
.land-rail-game span { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.land-rail::-webkit-scrollbar { display: none; }
.land-rail-brand { font: 800 11.5px/1 var(--sans, system-ui); color: var(--ink); text-decoration: none; padding: 2px 4px 3px; margin: 0; border: 0; background: none; text-align: left; cursor: pointer; letter-spacing: .01em; }
.land-rail-brand b { color: var(--accent); font-weight: 800; }
.land-rail-game { display: flex; align-items: center; gap: 5px; text-decoration: none; color: var(--ink); font-size: 10.5px; font-weight: 700; padding: 2px 6px 2px 2px; border-radius: 999px; background: color-mix(in srgb, var(--page) 78%, var(--ink) 8%); transition: transform .12s ease; }
@media (hover: hover) { .land-rail-game:hover { transform: translateX(2px); } }
.land-rail-game i { font-style: normal; display: grid; place-items: center; width: 16px; height: 21px; flex: 0 0 auto; border-radius: 4px; background: var(--card, #fbf7ec); color: #16110a; font: 800 10.5px/1 var(--display, Georgia, serif); box-shadow: 0 1px 2px rgba(0,0,0,.3); }
.land-rail-game.cur { background: var(--accent); color: #fff; }
.land-rail-game.cur i { box-shadow: 0 0 0 2px rgba(255,255,255,.5); }
.land-rail-info { display: flex; align-items: center; gap: 5px; font: 700 10.5px/1 var(--sans, system-ui); color: var(--ink); padding: 2px 6px 2px 2px; border-radius: 999px; background: none; border: 1px dashed color-mix(in srgb, var(--ink) 32%, transparent); cursor: pointer; margin-top: 2px; text-align: left; }
.land-rail-info i { font-style: normal; display: grid; place-items: center; width: 16px; height: 21px; flex: 0 0 auto; border-radius: 4px; background: color-mix(in srgb, var(--accent) 22%, transparent); color: var(--accent); font: 800 12px/1 var(--sans, system-ui); }
.land-rail-fs { display: flex; align-items: center; gap: 5px; font: 700 10.5px/1 var(--sans, system-ui); color: var(--ink); padding: 2px 6px 2px 2px; border-radius: 999px; background: color-mix(in srgb, var(--accent) 14%, transparent); border: 1px solid color-mix(in srgb, var(--accent) 42%, transparent); cursor: pointer; text-align: left; margin: 1px 0 2px; }
.land-rail-fs i { font-style: normal; display: grid; place-items: center; width: 16px; height: 21px; flex: 0 0 auto; border-radius: 4px; background: var(--accent); color: #fff; font: 800 13px/1 var(--sans, system-ui); }
.land-info-close { display: none; position: fixed; top: calc(7px + env(safe-area-inset-top)); right: calc(10px + env(safe-area-inset-right)); z-index: 81; width: 34px; height: 34px; align-items: center; justify-content: center; border-radius: 999px; border: 1px solid var(--line); background: var(--tile, #fff); color: var(--tile-text, #1a1a1a); font-size: 15px; cursor: pointer; box-shadow: 0 3px 12px -3px rgba(0,0,0,.4); }

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after { transition: none !important; animation: none !important; }
  .card.selected { transform: none; }
}

/* ===== UX polish: brand underline off · loading spinner · distinct game icons ===== */
.brand, .brand:hover, .brand:focus { text-decoration: none; }

/* Loading state while the board is empty (JS not rendered yet): a little deck of cards that
   gently rocks as if being shuffled/dealt. Vanishes the moment any card exists. */
.board { position: relative; min-height: 220px; }
.board:not(:has(.card))::before {
  content: ""; position: absolute; left: 50%; top: 50%; width: 50px; height: 68px; margin: -42px 0 0 -25px;
  border-radius: 7px; background: linear-gradient(155deg, #faf4e6, #ece1c8);
  box-shadow:
    0 0 0 1px rgba(0,0,0,.06),
    9px 5px 0 -2px #f1e7cf, 9px 5px 0 -1px rgba(0,0,0,.06),
    18px 10px 0 -4px #e9dcbf, 18px 10px 0 -3px rgba(0,0,0,.06),
    0 14px 26px rgba(0,0,0,.42);
  transform-origin: 50% 92%;
  animation: snDeal 1.25s ease-in-out infinite; z-index: 1;
}
body:has(.backdrop:not([hidden])) .board::before { display: none; } /* hide behind any open panel */
@keyframes snDeal { 0%,100% { transform: translateY(0) rotate(-5deg); } 50% { transform: translateY(-10px) rotate(5deg); } }
@media (prefers-reduced-motion: reduce) { .board:not(:has(.card))::before { animation: none; } }

/* Distinct, uniform per-game icons in "More games" (mask = takes the theme text color). */
.moregames a .fan { width: 30px; height: 40px; flex: 0 0 auto; background: currentColor; opacity: .82;
  -webkit-mask-repeat: no-repeat; mask-repeat: no-repeat; -webkit-mask-position: center; mask-position: center;
  -webkit-mask-size: contain; mask-size: contain; }
.moregames a .fan i { display: none; }
.moregames a[href="/"] .fan, .moregames a[href="/klondike.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M12 2C12 8 21 9 21 15C21 18 17 19 13 16.5C13.5 20 15 21 17 22H7C9 21 10.5 20 11 16.5C7 19 3 18 3 15C3 9 12 8 12 2Z'/%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M12 2C12 8 21 9 21 15C21 18 17 19 13 16.5C13.5 20 15 21 17 22H7C9 21 10.5 20 11 16.5C7 19 3 18 3 15C3 9 12 8 12 2Z'/%3E%3C/svg%3E"); }
.moregames a[href="/freecell.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Crect x='2' y='2' width='9' height='9' rx='1.6'/%3E%3Crect x='13' y='2' width='9' height='9' rx='1.6'/%3E%3Crect x='2' y='13' width='9' height='9' rx='1.6'/%3E%3Crect x='13' y='13' width='9' height='9' rx='1.6'/%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Crect x='2' y='2' width='9' height='9' rx='1.6'/%3E%3Crect x='13' y='2' width='9' height='9' rx='1.6'/%3E%3Crect x='2' y='13' width='9' height='9' rx='1.6'/%3E%3Crect x='13' y='13' width='9' height='9' rx='1.6'/%3E%3C/svg%3E"); }
.moregames a[href="/spider-solitaire.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Ccircle cx='12' cy='13' r='4'/%3E%3Cg fill='none' stroke='black' stroke-width='1.7' stroke-linecap='round'%3E%3Cpath d='M8.5 11 4 8M8 13 3 13M8.5 15 4 18M15.5 11 20 8M16 13 21 13M15.5 15 20 18'/%3E%3C/g%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Ccircle cx='12' cy='13' r='4'/%3E%3Cg fill='none' stroke='black' stroke-width='1.7' stroke-linecap='round'%3E%3Cpath d='M8.5 11 4 8M8 13 3 13M8.5 15 4 18M15.5 11 20 8M16 13 21 13M15.5 15 20 18'/%3E%3C/g%3E%3C/svg%3E"); }
.moregames a[href="/pyramid.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M12 3 22 21 2 21Z'/%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M12 3 22 21 2 21Z'/%3E%3C/svg%3E"); }
.moregames a[href="/golf-solitaire.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath fill='none' stroke='black' stroke-width='2' d='M6 2v20'/%3E%3Cpath d='M6 3 17 6.5 6 10Z'/%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath fill='none' stroke='black' stroke-width='2' d='M6 2v20'/%3E%3Cpath d='M6 3 17 6.5 6 10Z'/%3E%3C/svg%3E"); }
.moregames a[href="/tripeaks-solitaire.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M12 4 18 17 6 17Z'/%3E%3Cpath d='M5 9 10 19 0 19Z'/%3E%3Cpath d='M19 9 24 19 14 19Z'/%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M12 4 18 17 6 17Z'/%3E%3Cpath d='M5 9 10 19 0 19Z'/%3E%3Cpath d='M19 9 24 19 14 19Z'/%3E%3C/svg%3E"); }
.moregames a[href="/yukon-solitaire.html"] .fan {
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M2 21 9 7 13 14 17 5 22 21Z'/%3E%3C/svg%3E");
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M2 21 9 7 13 14 17 5 22 21Z'/%3E%3C/svg%3E"); }

/* ===== Depth pass: premium felt · card material · reward pop (all games, shared) ===== */
/* Warm top-light + edge vignette layered over the felt — turns a flat gradient into a lit table. */
:root, :root[data-theme="felt"] {
  --scene-spot: radial-gradient(75% 55% at 50% -8%, rgba(255,238,196,.12), transparent 62%);
  --scene-vignette: radial-gradient(135% 115% at 50% 36%, transparent 50%, rgba(0,0,0,.34) 100%);
}
:root[data-theme="mid"] {
  --scene-spot: radial-gradient(75% 55% at 50% -8%, rgba(230,179,101,.15), transparent 62%);
  --scene-vignette: radial-gradient(135% 120% at 50% 36%, transparent 48%, rgba(0,0,0,.44) 100%);
}
:root[data-theme="sun"] {
  --scene-spot: radial-gradient(80% 60% at 50% -10%, rgba(255,255,255,.55), transparent 60%);
  --scene-vignette: radial-gradient(135% 120% at 50% 42%, transparent 60%, rgba(150,100,55,.16) 100%);
}
:root[data-theme="pop"] {
  --scene-spot: none;
  --scene-vignette: radial-gradient(140% 120% at 50% 40%, transparent 66%, rgba(23,22,51,.10) 100%);
}
.board { background: var(--scene-spot, none), var(--scene-vignette, none), var(--scene-bg); }
/* finer felt weave on top of the theme's own texture */
.board::after {
  background:
    repeating-linear-gradient(90deg, rgba(255,255,255,.016) 0 1px, transparent 1px 3px),
    repeating-linear-gradient(0deg, rgba(0,0,0,.022) 0 1px, transparent 1px 3px),
    var(--scene-tex);
}

/* Cards feel printed: soft top-left gloss + edge highlight + inner bottom shade. */
.card {
  background: linear-gradient(152deg, rgba(255,255,255,.34), rgba(255,255,255,0) 42%), var(--card);
  box-shadow: inset 0 1px 0 rgba(255,255,255,.6), inset 0 -9px 15px -9px rgba(0,0,0,.12), var(--card-shadow);
}
.down { box-shadow: inset 0 1px 0 rgba(255,255,255,.28), var(--card-shadow); }

/* Reward pop when a card reaches its foundation (controllers add .landed on the grown suit). */
.foundcell .card.landed { animation: snLand .44s cubic-bezier(.34,1.56,.64,1); }
@keyframes snLand {
  0%   { transform: scale(.7); }
  45%  { transform: scale(1.13); box-shadow: 0 0 0 3px var(--accent), 0 0 22px -2px var(--accent), var(--card-shadow); }
  100% { transform: scale(1); }
}
/* Empty foundation reads as a lit target. */
.foundcell .slot { box-shadow: inset 0 0 26px rgba(255,255,255,.05); }

/* Logo chip gets a glossy top light. */
.logo { position: relative; overflow: hidden; }
.logo::after { content: ""; position: absolute; inset: 0; pointer-events: none;
  background: linear-gradient(158deg, rgba(255,255,255,.5), transparent 55%); }

/* ===== Real card faces: stacked corner index · counted pips · court letters ===== */
.card .corner { display: flex; flex-direction: column; align-items: center; line-height: .84; }
.card .corner b { font-weight: 700; }
.card .corner i { font-style: normal; font-size: .82em; margin-top: .01em; }
/* number-card pip field (A = one big pip, J/Q/K = court index) */
.card .pips { position: absolute; inset: 9% 12%; pointer-events: none; }
.card .pips .p { position: absolute; transform: translate(-50%, -50%); font-size: 1.1em; line-height: 1; }
.card .pips .p.f { transform: translate(-50%, -50%) rotate(180deg); }
.card .ace { position: absolute; inset: 0; display: grid; place-items: center; font-size: 2.9em; line-height: 1; }
.card .court { position: absolute; inset: 0; display: flex; flex-direction: column;
  align-items: center; justify-content: center; line-height: .9; }
.card .court b { font-family: var(--display); font-weight: 700; font-size: 2.2em; }
.card .court i { font-style: normal; font-size: 1.25em; margin-top: .03em; }

/* ===== Large / easy-to-read mode (accessibility) — html[data-big] ===== */
/* Columns must still fit, so the card doesn't grow; instead everything PRINTED on it scales up
   and goes bolder + higher-contrast. Since stacked cards only reveal their corner index, a big
   bold rank there is exactly what low-vision / older players need. Plus larger UI text. */
html[data-big] .card { font-size: calc(var(--cw) * 0.25); }
html[data-big] .card .corner { line-height: .8; }
html[data-big] .card .corner b { font-weight: 800; font-size: 1.28em; }
html[data-big] .card .corner i { font-size: .92em; }
html[data-big] .card.red { color: #bf261c; }
html[data-big] .card.black { color: #05070c; }
html[data-big] .card .pips .p { font-size: 1.12em; }
html[data-big] .card .court b { font-size: 2.35em; }
html[data-big] .card .ace { font-size: 3.15em; }
html[data-big] .tbtn { font-size: 15px; padding: 8px 13px; }
html[data-big] .chip b { font-size: 17px; }
html[data-big] .chip span { font-size: 9.5px; }
html[data-big] .brand .word { font-size: 20px; }
html[data-big] .brand .word small { font-size: 13px; }
html[data-big] .content p, html[data-big] .content li { font-size: 16.5px; }
html[data-big] .panel { font-size: 15px; }
html[data-big] .more-menu .tbtn { font-size: 15.5px; }
