/* Site shell extras: nav quick-search, search results. Loaded on every page by layout.js. */
/* Search lives at the right end of the nav row (dropping under the tabs on phones), tucked in like another tab. */
.quick-search { display: flex; gap: 6px; align-items: center; margin: 8px 0 10px; flex: none; }
.quick-search input { width: 11rem; margin: 0; padding: 6px 14px; border-width: 2px; border-radius: 999px; box-shadow: var(--shadow-sm); }
@media (max-width: 560px) {
  .quick-search { flex: 1 1 100%; margin: 0 0 10px; }
  .quick-search input { width: auto; flex: 1; min-width: 0; }
}

.search-group h2 small { font: 600 var(--fs-sm) var(--body); margin-left: 6px; }
.search-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 12px 20px; grid-template-columns: repeat(auto-fill, minmax(min(100%, 240px), 1fr)); }
.search-art { display: flex; align-items: center; gap: 10px; }
.search-art svg { flex: none; }
kbd { font: 700 .9em var(--body); padding: 0 .4em; border: 2px solid var(--ink); border-radius: 6px; background: var(--tint); }

/* What two of the Settings switches do (the page itself is public/settings.css). .reduce-motion copies style.css's prefers-reduced-motion rule. */
.reduce-motion *, .reduce-motion *::before, .reduce-motion *::after { animation: none !important; transition: none !important; scroll-behavior: auto !important; }
/* Battery (shell.js): animations pause while the tab is hidden or the page has sat untouched for 20 s (html.anim-paused),
   and inside anything scrolled off screen (.anim-off). SMIL loops can't be paused from CSS, so shell.js pauses those itself. */
.anim-paused *, .anim-paused *::before, .anim-paused *::after,
.anim-off, .anim-off::before, .anim-off::after, .anim-off *, .anim-off *::before, .anim-off *::after { animation-play-state: paused !important; }
/* The selectors above stop at a <use> clone's shadow tree, so a pet drawn twice through <use> (a sticker's die-cut outline mask)
   kept Chrome drawing 60 frames a second on an idle /stickers. A custom property inherits into the clone, and a style query on it
   pauses everything under it. */
.anim-paused, .anim-off { --battery: paused; }
@container style(--battery: paused) { *, *::before, *::after { animation-play-state: paused !important; } }
.compact { --gap: 10px; --gap-sm: 6px; }
.compact .site-head { padding-top: 8px; padding-bottom: 10px; }
.compact .site-body { padding-top: 10px; }
.compact .card { padding: 12px 16px; }
#restore-form input[type=file] { width: 17em; }

/* Footer ♪ toggle for land music (public/music.js unhides it). Lit up while music is on. */

/* A tab's sub-row (layout.js SUBNAV): small pills under the tab row on the pages that belong to the Glimlings and World tabs.
   Tablets and desktops only; phones reach the same pages from the bottom bar and the More sheet. */
.sub-nav { padding: 0 clamp(16px, 3vw, 32px); margin: 2px 0 -6px; }
.sub-nav ul { list-style: none; margin: 0; padding: 0 4px; display: flex; flex-wrap: wrap; gap: 8px; }
.sub-nav a { display: inline-flex; align-items: center; min-height: 36px; padding: 4px 14px; font: 600 var(--fs-sm) var(--display); color: var(--ink); text-decoration: none;
  background: var(--card); border: 2px solid var(--ink); border-radius: 999px; box-shadow: var(--shadow-sm); }
.sub-nav a:hover { background: var(--hi-soft); }
.sub-nav a[aria-current="page"] { background: var(--pick); }
@media (min-width: 1000px) { .sub-nav { padding-inline: max(clamp(16px, 3vw, 32px), calc((100% - var(--page-max)) / 2 + 28px)); } }
@media (max-width: 1024px) { .sub-nav a { min-height: 44px; } }
@media (max-width: 767px) { .sub-nav { display: none; } }

/* ---------- Tablet and phone shell ----------
   768-1024px: all tabs in one top row, search folds into a header icon that opens a popover.
   Up to 767px: a fixed bottom tab bar (four tabs + a More sheet), a one-line header, and a slim pet bar. */
.site-nav .nav-ic, .search-btn, .tab-morebtn, .site-nav .tab-music, .acct-sky, .pet-toggle, .narrow-only { display: none; }
.sheet, .search-pop { margin: 0; padding: 10px; color: var(--ink); background: var(--card); border: var(--line) solid var(--ink); border-radius: var(--r-card); box-shadow: var(--shadow); overflow: visible; }
.sheet:not(:popover-open), .search-pop:not(:popover-open) { display: none; }
.search-pop { inset: 88px 16px auto auto; width: min(360px, calc(100vw - 32px)); }
.search-pop form { display: flex; gap: 8px; margin: 0; }
.search-pop input { flex: 1; min-width: 0; margin: 0; }
.search-pop .btn { min-height: 44px; }
.sheet::backdrop { background: color-mix(in srgb, var(--ink) 35%, transparent); }
.search-btn { align-items: center; justify-content: center; width: 44px; height: 44px; padding: 0; cursor: pointer; background: var(--card); border: 2px solid var(--ink); border-radius: 50%; box-shadow: var(--shadow-sm); }
.search-btn:hover, .search-btn[aria-expanded="true"] { background: var(--pick); }
/* Header ♪: struck through when off, a gentle bob when on (shell.js pauses it when idle, hidden or off screen) */
.music-btn { position: relative; display: inline-flex; align-items: center; justify-content: center; width: 44px; height: 44px; padding: 0; cursor: pointer; color: var(--ink); background: var(--card); border: 2px solid var(--ink); border-radius: 50%; box-shadow: var(--shadow-sm); }
.music-btn[hidden] { display: none; }
.music-btn:hover { background: var(--pick); }
.music-btn[aria-pressed="false"] svg { opacity: .7; filter: grayscale(1); }
.music-btn[aria-pressed="false"]::after { content: ''; position: absolute; width: 30px; height: 3px; border-radius: 2px; background: var(--ink); box-shadow: 0 0 0 2px var(--card); rotate: -45deg; }
.music-btn[aria-pressed="true"] svg { animation: music-bob 1.2s ease-in-out infinite alternate; }
/* transform, not translate:/rotate:, so the compositor runs it: Chrome ticks the separate properties on the main thread on an <svg>. */
@keyframes music-bob { from { transform: translate(0, 1px) rotate(-8deg); } to { transform: translate(0, -2px) rotate(8deg); } }
.reduce-motion .music-btn svg { animation: none; }
@media (prefers-reduced-motion: reduce) { .music-btn svg, .site-nav .tab-music svg { animation: none; } }

@media (max-width: 1024px) {
  .quick-search { display: none; }
  .search-btn { display: inline-flex; }
}
/* 10 tabs across 768px (Friends since 2026-10-14) and its badge: tighter tabs, no sideways scrolling, about 10px to spare. */
@media (min-width: 768px) and (max-width: 1024px) {
  .site-nav ul { overflow: visible; gap: 4px; }
  .site-nav a { padding: 8px 4px; font-size: .86rem; }
}
/* Desktop under 1700px: ten tabs overflowed the row at 1280 (69px) and 1440 (21px), so a little less padding and gap (preview pick). */
@media (min-width: 1025px) and (max-width: 1699px) {
  .site-nav ul { gap: 6px; }
  .site-nav a { padding-inline: 11px; } /* style-ok: the picked spacing; 10px also fits, 12px overflows 1280 */
}
/* The Friends tab's waiting-requests number beside its label, pink like Pigeon Post's (phones carry it on the More button and the sheet tile). */
@media (min-width: 768px) {
  .site-nav a > .tab-badge {
    display: inline-grid; place-items: center; min-width: 22px; height: 22px; margin-left: 6px; padding: 0 6px; vertical-align: 1px;
    font: 700 .78rem var(--display); color: #fff; background: var(--pink); border: 2px solid var(--ink); border-radius: 999px;
  }
}
@media (min-width: 768px) and (max-width: 1024px) { .site-nav a > .tab-badge { margin-left: 4px; } }

@media (max-width: 767px) {
  :root { --bar-h: 64px; }
  body { padding-bottom: calc(var(--bar-h) + env(safe-area-inset-bottom)); }

  /* Header on one line: logo, search, coins, bell, menu. Mail lives in More; the sky clock and land chip move into the menu. */
  .site-head { flex-wrap: nowrap; gap: 8px; padding: 8px 10px 12px; }
  .logo { flex: 0 1 150px; min-width: 0; }
  .site-head:not(.signed-in) .logo { flex-shrink: 0; flex-basis: 140px; } /* logged out there is room: search, Log in, Join */
  @media (max-width: 359px) { /* 320px logged out: logo, search, Log in and Join need 365px at full size */
    .site-head:not(.signed-in) .logo { flex-shrink: 1; min-width: 104px; }
    .site-head:not(.signed-in) .who > .btn { padding-inline: 10px; }
  }
  .logo svg { height: auto; width: 100%; }
  .land-chip, .who-mail, .charms .sky-charm { display: none; }
  .who { flex: none; margin-left: auto; gap: 8px; }
  .charms { gap: 8px; }
  .charm { min-width: 44px; min-height: 44px; padding: 0; }
  .coins { min-height: 44px; padding: 0 10px; font-size: .95rem; }
  .account summary { padding: 2px; }
  .account-panel { width: min(260px, calc(100vw - 20px)); }
  .account-panel a, .account-panel button { min-height: 44px; align-content: center; }
  .acct-sky { display: flex; align-items: center; justify-content: center; gap: 10px; padding: 4px 4px 8px; border-bottom: 2px dashed var(--rule); }
  .acct-sky .sky-charm { cursor: default; }
  .acct-me { justify-items: center; text-align: center; }
  .acct-me .title-tag { justify-self: center; }
  .acct-sky a { text-align: center; padding: 8px 12px; min-height: 44px; align-content: center; background: color-mix(in oklab, var(--land-accent) 18%, #fff); border: 2px solid var(--ink); border-radius: 999px; } /* style-ok: land paint, as .land-chip */
  .who > .btn { min-height: 44px; display: inline-flex; align-items: center; }
  .wide-only { display: none; }
  .narrow-only { display: inline; }
  .search-pop { inset: 68px 10px auto 10px; width: auto; }

  /* Bottom tab bar: icon over label, equal-width tabs, the current one on the --pick pill. */
  .site-nav { position: fixed; inset: auto 0 0 0; z-index: 40; display: block; padding: 0 8px env(safe-area-inset-bottom); background: var(--card); border-top: var(--line) solid var(--ink); }
  .site-nav ul { display: grid; grid-auto-flow: column; grid-auto-columns: minmax(0, 1fr); gap: 8px; padding: 6px 0; overflow: visible; }
  .site-nav li { display: flex; }
  .site-nav .tab-more { display: none; }
  .site-nav .tab-morebtn { display: flex; position: relative; }
  /* Phones: the music toggle is the bar's last tab (the header has no room), struck through when off */
  .who .music-btn { display: none; }
  .site-nav .tab-music { display: flex; }
  .site-nav .tab-music button[hidden] { display: none; }
  .site-nav .tab-music button { position: relative; }
  .site-nav .tab-music button[aria-pressed="false"] svg { opacity: .7; filter: grayscale(1); }
  .site-nav .tab-music button[aria-pressed="false"]::after { content: ''; position: absolute; top: 17px; left: calc(50% - 15px); width: 30px; height: 3px; border-radius: 2px; background: var(--ink); box-shadow: 0 0 0 2px var(--card); rotate: -45deg; }
  .site-nav .tab-music button[aria-pressed="true"] svg { animation: music-bob 1.2s ease-in-out infinite alternate; }
  .reduce-motion .site-nav .tab-music svg { animation: none; }
  .site-nav a, .site-nav button {
    flex: 1; display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 1px; min-height: 52px; padding: 2px 0;
    font: 700 .72rem/1.1 var(--display); color: var(--ink); text-decoration: none; background: none; cursor: pointer; letter-spacing: -.02em; /* .72rem, tighter: six tabs with Music */
    border: 2px solid transparent; border-radius: 14px; box-shadow: none;
  }
  .site-nav a:hover, .site-nav button:hover { background: var(--hi-soft); }
  .site-nav a[aria-current="page"], .site-nav button[aria-current="page"], .site-nav button[aria-expanded="true"] { background: var(--pick); border-color: var(--ink); }
  .site-nav a[data-phone-off][aria-current="page"] { background: none; border-color: transparent; } /* lit through its desktop sub-row; on phones More holds this page (layout.js inSheet) */
  .site-nav .nav-ic { display: block; }
  .site-nav a, .site-nav button { min-width: 0; } /* a long label never widens its column into the next tab */
  .tab-badge, .sheet .tab-badge { display: grid; place-items: center; min-width: 20px; height: 20px; padding: 0 5px; font: 700 .72rem var(--display); color: #fff; background: var(--pink); border: 2px solid var(--ink); border-radius: 999px; } /* style-ok: 5px keeps a two-digit count centered in the 20px badge */
  .site-nav .tab-badge { position: absolute; top: 0; left: calc(50% + 6px); }

  @media (max-width: 360px) { .site-nav a, .site-nav button { font-size: .66rem; } } /* "Glimlings" fits a 45px tab at 320px */

  /* More sheet: a card resting on the bar, a 3-across grid of icon-over-label tiles, the unread badge on the icon's corner. */
  .sheet { inset: auto 10px calc(var(--bar-h) + env(safe-area-inset-bottom) + 10px) 10px; width: auto; max-height: calc(100dvh - var(--bar-h) - env(safe-area-inset-bottom) - 20px); overflow-y: auto; padding: 6px; } /* width: auto beats the popover UA fit-content */
  .sheet ul { list-style: none; margin: 0; padding: 0; display: grid; grid-template-columns: repeat(3, 1fr); gap: 4px; }
  .sheet a { position: relative; display: grid; justify-items: center; align-content: center; gap: 4px; min-height: 84px; padding: 8px 4px; font: 700 .9rem/1.15 var(--display); text-align: center; color: var(--ink); text-decoration: none; border-radius: 14px; }
  @media (hover: hover) { .sheet a:hover { background: var(--hi); } } /* touch keeps :hover on the last tapped tile */
  .sheet a[aria-current="page"] { background: var(--pick); }
  .sheet .tab-badge { position: absolute; top: 4px; left: calc(50% + 10px); }
  /* The Builders' Board's "new" dot: no number, the same pink as a badge, on the icon's corner. */
  .sheet .tab-dot { position: absolute; top: 6px; left: calc(50% + 10px); width: 14px; height: 14px; background: var(--pink); border: 2px solid var(--ink); border-radius: 50%; }

  /* Pet strip: a 56px bar (face, name, level, three tiny meters, chevron) until the chevron opens today's strip. */
  .pet-toggle { display: grid; place-items: center; position: absolute; top: 0; right: 0; z-index: 2; width: 44px; height: 44px; padding: 0; color: var(--ink); background: none; border: 0; cursor: pointer; }
  .pet-toggle svg { transition: rotate .2s; }
  .pet-toggle[aria-expanded="true"] svg { rotate: 180deg; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) {
    grid-template-columns: auto minmax(0, 1fr) 44px; grid-template-areas: "face id tog" "face meters tog"; gap: 0 10px; min-height: 56px; padding: 6px 4px 6px 8px; align-items: center; cursor: pointer;
  }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) > :not(.pet-stage, .pet-id, .pet-meters, .pet-toggle) { display: none; }
  /* Collapsed, the toggle is the chevron cell and its ::before stretches over the whole bar, so any tap opens it. */
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-toggle { position: static; grid-area: tog; width: auto; height: auto; align-self: stretch; }
  .pet-toggle[aria-expanded="false"]::before { content: ''; position: absolute; inset: 0; z-index: 2; border-radius: inherit; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-stage { width: 44px; height: 44px; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-stage svg { width: 68px; margin: 2px 0 0 -12px; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-id { flex-wrap: nowrap; gap: 8px; align-items: center; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-id > :not(.pet-name, .pet-level) { display: none; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-name { font-size: 1.05rem; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-level { flex: none; width: 24px; height: 24px; font-size: .7rem; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-meters { flex-wrap: nowrap; gap: 8px; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-meters li { display: flex; align-items: center; gap: 3px; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-meters li > span:not(.stat-bar) { display: none; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-meters li > b { font-size: .68rem; font-weight: 700; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-meters .stat-bar { display: block; width: 24px; height: 8px; }
  .pet-panel:has(.pet-toggle[aria-expanded="false"]) .pet-meters .hb-q { display: none; } /* the slim bar has no room; the open panel shows it */
  .pet-panel-empty { min-height: 56px; padding: 6px 12px; flex-wrap: nowrap; justify-content: space-between; align-items: center; }
  .pet-panel-empty p { display: none; }
  .pet-panel-empty .btn { min-height: 44px; display: inline-flex; align-items: center; }

  /* Footer: centered, links 44px tall with 12px between them. */
  .site-foot p:last-child { display: flex; flex-wrap: wrap; justify-content: center; gap: 12px; }
  .site-foot a { display: inline-flex; align-items: center; min-height: 44px; margin: 0; padding: 0 6px; }

  /* Fixed bottom things clear the bar: the corner visitor (finds.css). */
  body .find-visitor { bottom: calc(var(--bar-h) + env(safe-area-inset-bottom) + 12px); }
}
/* 320px phones: the coin pill gives up its padding so the logo keeps some width. */
@media (max-width: 359px) {
  .site-head { padding-inline: 8px; }
}

/* ---------- Feedback (src/routes/feedback.js): the bubble, its sheet and the form ----------
   The bubble is a round speech balloon at the bottom right, above the phone tab bar and under every bar and overlay (z 30).
   shell.js adds .fb-tucked while a phone scrolls (and whenever resting would sit on a link or button): it slides off the edge
   to a half-circle, still tappable. Hidden in the game play view, while a phone keyboard is up, and on admin pages (layout.js). */
.fb-bubble {
  --fb-b: 24px; --fb-r: 16px;
  position: fixed; z-index: 30; right: calc(var(--fb-r) + env(safe-area-inset-right)); bottom: calc(var(--fb-b) + env(safe-area-inset-bottom));
  display: grid; place-items: center; width: 48px; height: 48px; color: var(--ink); background: var(--hi);
  border: var(--line) solid var(--ink); border-radius: 50%; box-shadow: var(--shadow-sm); text-decoration: none;
  transition: transform .25s var(--ease-out);
}
.fb-bubble svg { transition: opacity .2s; }
.fb-bubble:hover { background: var(--pick); color: var(--ink); }
.fb-bubble:focus-visible { outline: 3px solid var(--ink); outline-offset: 3px; box-shadow: var(--shadow-sm), 0 0 0 9px var(--sky); }
.fb-tip {
  position: absolute; right: calc(100% + 10px); top: 50%; translate: 0 -50%; padding: 4px 12px; white-space: nowrap; pointer-events: none;
  font: 600 var(--fs-xs) var(--display); color: #fff; background: var(--ink); border-radius: 999px; opacity: 0; transition: opacity .15s;
}
.fb-bubble:focus-visible .fb-tip { opacity: 1; }
@media (hover: hover) { .fb-bubble:hover .fb-tip { opacity: 1; } }
.fb-bubble.fb-tucked { transform: translateX(calc(50% + var(--fb-r) + env(safe-area-inset-right))); }
.fb-bubble.fb-away { opacity: 0; pointer-events: none; }
.fb-bubble.fb-tucked svg, .fb-bubble.fb-tucked .fb-tip { opacity: 0; }
body:has(.find-visitor-right:not(.is-gone)) .fb-bubble { --fb-b: 104px; } /* the corner visitor sits in the same corner */
body:has(dialog.game-dialog[open]) .fb-bubble { display: none; }
body:has(.find-toast:not(.is-out)) .fb-bubble { opacity: 0; pointer-events: none; } /* a pop-up (finds.css) sits in its corner for a few seconds */
@media (pointer: coarse) { /* a focused text box means the phone keyboard is up */
  body:has(:is(input:not([type=checkbox], [type=radio], [type=range], [type=file], [type=button], [type=submit], [type=color], [type=hidden]), textarea, [contenteditable]):focus) .fb-bubble { display: none; }
}
@media (max-width: 767px) {
  .fb-bubble { --fb-b: calc(var(--bar-h) + 12px); --fb-r: 12px; }
  body:has(.find-visitor-right:not(.is-gone)) .fb-bubble { --fb-b: calc(var(--bar-h) + 96px); }
}

/* The sheet: a <dialog> shell.js opens with the form inside. Phones get a bottom sheet; wider screens a centered card. */
.fb-sheet { width: min(560px, calc(100vw - 32px)); max-height: calc(100dvh - 32px); margin: auto; padding: 0; overflow: auto; color: var(--ink); background: transparent; border: 0; }
.fb-sheet::backdrop { background: color-mix(in srgb, var(--ink) 40%, transparent); }
.fb-sheet .fb-card { margin: 0; }
.fb-sheet .pop-close { position: sticky; top: 8px; float: right; margin: 8px 8px 0 0; z-index: 1; }
@media (max-width: 767px) {
  .fb-sheet { width: 100%; max-width: 100%; max-height: calc(100dvh - 24px - env(safe-area-inset-top)); margin: auto 0 0; padding-bottom: env(safe-area-inset-bottom); }
  .fb-sheet .fb-card { border-radius: var(--r-card) var(--r-card) 0 0; }
}
.fb-form { display: grid; gap: 12px; }
.fb-form > label { display: grid; gap: 4px; font-weight: 700; }
.fb-form fieldset { margin: 0; }
.fb-form .swatch { min-height: 44px; }
.fb-form small { margin-top: -8px; }
.fb-context dl { display: grid; grid-template-columns: max-content 1fr; gap: 4px 12px; margin: 8px 0 0; font-size: var(--fs-sm); }
.fb-context dt { font-weight: 800; }
.fb-context dd { margin: 0; overflow-wrap: anywhere; white-space: pre-line; }
.fb-context summary { cursor: pointer; font-weight: 700; min-height: 44px; display: flex; align-items: center; }
.fb-form .hint, .fb-error { margin: 0; }
.fb-error { color: var(--loss); font-weight: 700; }
