:root {
  color-scheme: light;
  --bg: #F8F3E9;
  --surface: #FFFCF6;
  --text: #292522;
  --text-muted: #766e63;
  --accent: #722F37;
  --accent-dark: #551f26;
  --accent-soft: #e8d3d5;
  --secondary: #59634A;
  --secondary-dark: #454d39;
  --secondary-soft: #dde1d5;
  --mustard: #C99B4A;
  --mustard-dark: #a17936;
  --mustard-soft: #f0e2c4;
  --wordmark-a: #d9822b;
  --border: #e9e0d0;
  --shadow: 0 4px 16px rgba(41, 37, 34, 0.08);
  --radius: 14px;
}

* { box-sizing: border-box; }

body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  line-height: 1.5;
}

h1, h2, h3, h4, h5, h6 {
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
}

.tag {
  font-family: 'Segoe UI', system-ui, -apple-system, sans-serif;
}

.topbar {
  background: var(--accent-dark);
  color: #fff;
  border-bottom: 1px solid rgba(201, 155, 74, 0.35);
  position: sticky;
  top: 0;
  z-index: 100;
}

.topbar-inner {
  position: relative;
  max-width: 1100px;
  margin: 0 auto;
  padding: 0.45rem 1.25rem;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1.5rem;
  flex-wrap: wrap;
}

.topbar-wordmark {
  font-family: 'Allan', 'Rubik', 'Segoe UI', system-ui, -apple-system, cursive;
  font-weight: 700;
  font-size: 1.5rem;
  line-height: 1;
  letter-spacing: 0.02em;
  color: var(--mustard);
  text-decoration: none;
  display: inline-flex;
  align-items: center;
  transition: color 0.15s ease;
}

.topbar-logo-icon {
  width: 2rem;
  height: 2rem;
  flex: 0 0 auto;
  margin-right: 0.45rem;
}

.wordmark-roll {
  color: #fff;
}

.wordmark-a {
  color: var(--wordmark-a);
}

.topbar-wordmark:hover {
  color: #fff;
}

.topbar-nav {
  display: flex;
  align-items: center;
  gap: 0.2rem;
  flex-wrap: wrap;
}

.topbar-nav a {
  color: rgba(255, 255, 255, 0.8);
  text-decoration: none;
  font-size: 0.76rem;
  font-weight: 600;
  letter-spacing: 0.07em;
  text-transform: uppercase;
  padding: 0.4rem 0.8rem;
  border-radius: 999px;
  transition: background 0.15s ease, color 0.15s ease;
}

.topbar-nav a:hover {
  background: rgba(255, 255, 255, 0.14);
  color: #fff;
}

/* Desktop-only stand-in for the page's own search/filter toolbar — hidden
   until initTopbarSearchSwap() (app.js) reveals it once the real toolbar
   has scrolled fully out of view under this sticky topbar (the toolbar
   itself is NOT sticky — it just scrolls away normally; the topbar is the
   only thing pinned). Mirrors the real search input/selects rather than
   duplicating any filtering logic itself (see app.js for the sync). */
.topbar-search-wrap {
  display: none;
  /* Let the filter panel anchor to .topbar-inner, not this 420px search box. */
  position: static;
  flex: 1 1 auto;
  max-width: 420px;
}

.topbar-search-wrap.visible {
  display: block;
}

.topbar-search-row {
  display: flex;
  gap: 0.5rem;
}

.topbar-search-input {
  flex: 1;
  min-width: 0;
  padding: 0.45rem 0.8rem;
  border-radius: 8px;
  border: 1px solid rgba(255, 255, 255, 0.28);
  background: rgba(255, 255, 255, 0.12);
  color: #fff;
  font-size: 0.85rem;
}

.topbar-search-input::placeholder {
  color: rgba(255, 255, 255, 0.65);
}

.topbar-search-input:focus {
  outline: none;
  background: #fff;
  color: var(--text);
  border-color: #fff;
}

.topbar-filter-btn {
  flex: 0 0 auto;
  width: 36px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 8px;
  border: 1px solid rgba(255, 255, 255, 0.28);
  background: rgba(255, 255, 255, 0.12);
  color: #fff;
  cursor: pointer;
}

.topbar-filter-btn:hover {
  border-color: var(--mustard);
}

.topbar-filter-btn.active {
  background: var(--mustard);
  border-color: var(--mustard);
  color: var(--accent-dark);
}

/* Positioned relative to .topbar-inner (not .topbar-search-wrap) so its
   edges land flush with <main>'s own content edge below (both sit inside a
   max-width: 1100px box centered the same way; 1rem here matches main's
   own side padding) instead of floating as a narrow box under just the
   search input. */
.topbar-filter-panel {
  display: none;
  position: absolute;
  top: calc(100% + 1px);
  left: 1rem;
  right: 1rem;
  background: var(--surface);
  border-radius: 0 0 10px 10px;
  box-shadow: var(--shadow);
  padding: 0.9rem;
  gap: 0.6rem;
  z-index: 80;
}

.topbar-filter-panel.open {
  display: flex;
  flex-direction: row;
}

.topbar-filter-panel select {
  flex: 1 1 0;
  min-width: 0;
  padding: 0.5rem 0.6rem;
  border-radius: 8px;
  border: 1px solid var(--border);
  background: var(--bg);
  color: var(--text);
  font-size: 0.85rem;
}

.topbar-search-toggle-btn {
  display: none;
  flex: 0 0 auto;
  width: 36px;
  height: 36px;
  align-items: center;
  justify-content: center;
  border-radius: 8px;
  border: 1px solid rgba(255, 255, 255, 0.28);
  background: rgba(255, 255, 255, 0.12);
  color: #fff;
  cursor: pointer;
}

.topbar-search-toggle-btn:hover {
  border-color: var(--mustard);
}

.topbar-search-toggle-btn.active {
  background: var(--mustard);
  border-color: var(--mustard);
  color: var(--accent-dark);
}

/* On narrow screens there's no room for the desktop inline search row next
   to the wordmark, so it never appears there at all — a dedicated search
   icon button (initTopbarSearchToggle() in app.js) instead reveals the same
   .topbar-search-wrap as a full-width dropdown below the topbar, flush with
   the topbar's own edges same as .topbar-filter-panel already is. */
@media (max-width: 700px) {
  /* Groups the search-toggle and menu buttons together flush against the
     right edge (margin-left: auto on a flex item eats the rest of
     .topbar-inner's space-between distribution) instead of the icon
     floating alone in the middle between the wordmark and the menu
     button. */
  .topbar-inner {
    gap: 0.5rem;
  }
  /* The topbar is the only visible search entry point on mobile. */
  .topbar-search-toggle-btn {
    display: flex;
    margin-left: auto;
  }
  .topbar-search-wrap {
    display: none;
    position: absolute;
    top: calc(100% + 1px);
    left: 0;
    right: 0;
    max-width: none;
    background: var(--surface);
    border: 1px solid var(--border);
    border-top: 3px solid var(--mustard);
    border-radius: 0 0 14px 14px;
    box-shadow: 0 12px 24px rgba(41, 37, 34, 0.18);
    padding: 0.75rem;
    z-index: 85;
  }
  .topbar-search-wrap.visible {
    display: block;
  }
  .topbar-search-input {
    background: var(--bg);
    color: var(--text);
    border: 1px solid var(--border);
  }
  .topbar-search-input::placeholder {
    color: var(--text-muted);
  }
  /* The funnel button's default white icon/translucent-white styling was
     tuned for sitting directly on the dark maroon topbar — inside this
     light-surfaced dropdown it was rendering white-on-near-white,
     effectively invisible. */
  .topbar-filter-btn {
    border-color: var(--border);
    background: var(--bg);
    color: var(--text-muted);
  }
  .topbar-filter-btn:hover {
    border-color: var(--accent);
    color: var(--accent-dark);
  }
  .topbar-filter-btn.active {
    background: var(--mustard);
    border-color: var(--mustard);
    color: var(--accent-dark);
  }
  .topbar-filter-panel {
    position: static;
    margin-top: 0.6rem;
    padding: 0;
    box-shadow: none;
  }
  .topbar-filter-panel.open {
    flex-direction: column;
  }
}

.topbar-menu-btn {
  display: none;
  flex: 0 0 auto;
  width: 36px;
  height: 36px;
  align-items: center;
  justify-content: center;
  border-radius: 8px;
  border: 1px solid var(--wordmark-a);
  background: rgba(217, 130, 43, 0.16);
  color: var(--wordmark-a);
  cursor: pointer;
}

.topbar-menu-btn:hover {
  background: rgba(217, 130, 43, 0.3);
}

.topbar-menu-btn.active {
  background: var(--wordmark-a);
  border-color: var(--wordmark-a);
  color: #fff;
}

/* Below this width the wordmark + (sometimes) topbar search + full nav no
   longer fit on one line and .topbar-nav starts wrapping onto its own
   messy second row — swap it for a single menu button that opens the same
   links as a dropdown instead. */
@media (max-width: 860px) {
  .topbar-menu-btn {
    display: flex;
  }
  .topbar-nav {
    display: none;
    position: absolute;
    top: calc(100% + 1px);
    left: 0;
    right: 0;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    background: var(--surface);
    border: 1px solid var(--border);
    border-top: 3px solid var(--mustard);
    border-radius: 0 0 14px 14px;
    box-shadow: 0 12px 24px rgba(41, 37, 34, 0.18);
    padding: 0.75rem;
    gap: 0.6rem;
    z-index: 90;
  }
  .topbar-nav.open {
    display: grid;
  }
  .topbar-nav a {
    display: flex;
    align-items: center;
    justify-content: center;
    min-height: 52px;
    padding: 0.7rem;
    border: 1px solid var(--border);
    border-radius: 10px;
    background: var(--bg);
    color: var(--text);
    text-align: center;
    font-size: 0.8rem;
    letter-spacing: 0.045em;
  }
  .topbar-nav a:hover,
  .topbar-nav a:focus-visible {
    background: var(--accent-soft);
    color: var(--accent-dark);
    border-color: var(--accent);
    outline: none;
  }
}

@media (max-width: 520px) {
  .topbar-inner {
    padding: 0.5rem 0.75rem;
  }
}

.site-header {
  background: var(--accent);
  color: #fff;
  padding: 2.5rem 1rem 3rem;
  text-align: center;
}

@media (max-width: 700px) {
  /* Inner pages already have the Roll a Recipe wordmark in the top bar. */
  .site-header.inner-header {
    padding: 0.85rem 0.75rem 1rem;
  }
  .site-header.inner-header .site-title {
    font-size: 1.25rem;
    line-height: 1.25;
    margin: 0;
  }
  .inner-header .tagline { display: none; }
  .site-header.listing-header {
    padding: 1rem 0.85rem 1.1rem;
  }
  .site-header.listing-header .site-title {
    font-size: clamp(1.4rem, 6vw, 1.65rem);
  }
  .site-header.listing-header .tagline {
    display: block;
    max-width: 36rem;
    margin: 0.35rem auto 0;
    font-size: 0.85rem;
    line-height: 1.4;
  }
}

.breadcrumbs {
  max-width: 1100px;
  margin: 0 auto;
  padding: 0.75rem 1.25rem 0.5rem;
  font-size: 0.8rem;
  color: var(--text-muted);
}

.breadcrumbs a {
  color: var(--text-muted);
  text-decoration: none;
}

.breadcrumbs a:hover {
  color: var(--accent);
  text-decoration: underline;
}

.breadcrumbs .crumb-sep {
  margin: 0 0.4rem;
  opacity: 0.6;
}

.breadcrumbs [aria-current="page"] {
  color: var(--text);
}

.header-inner h1,
.header-inner .site-title {
  margin: 0 0 0.4rem;
  font-size: clamp(1.6rem, 4vw, 2.4rem);
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-weight: 700;
}

.tagline {
  margin: 0;
  opacity: 0.92;
  font-size: 1rem;
}

main {
  max-width: 1100px;
  margin: -1.6rem auto 0;
  padding: 0 1rem 1.5rem;
}

/* Only the homepage overlaps its hero. Inner pages start after breadcrumbs. */
.breadcrumbs + main { margin-top: 0; }

@media (max-width: 700px) {
  .breadcrumbs {
    display: none;
  }
}

.picker {
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 1.6rem;
  text-align: center;
  margin-bottom: 1.5rem;
}

.reroll-picker {
  margin-top: 2rem;
  margin-bottom: 0;
}

.pick-btn {
  background: var(--accent);
  color: #fff;
  border: none;
  padding: 0.9rem 1.8rem;
  font-size: 1.05rem;
  border-radius: 999px;
  cursor: pointer;
  font-weight: 600;
  transition: transform 0.15s ease, background 0.15s ease;
}

.pick-btn:hover {
  background: var(--accent-dark);
  transform: translateY(-1px);
}

.pick-btn:disabled {
  cursor: default;
}

.pick-btn.spinning {
  animation: raffle-shake 0.35s ease-in-out infinite;
  background: var(--accent-dark);
}

@keyframes raffle-shake {
  0%, 100% { transform: rotate(0deg) translateY(-1px); }
  25% { transform: rotate(-3deg) translateY(-2px); }
  75% { transform: rotate(3deg) translateY(-2px); }
}

.pick-result {
  margin-top: 1.2rem;
  text-align: left;
}

.recipe-toolbar {
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 1.6rem;
  margin-bottom: 1.5rem;
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 1.5rem;
}

.toolbar-search {
  position: relative;
}

.toolbar-search input {
  width: 100%;
  min-width: 0;
  flex: 1;
  padding: 0.7rem 1rem;
  border-radius: 10px;
  border: 1px solid var(--border);
  background: var(--bg);
  color: var(--text);
  font-size: 1rem;
}

/* .search-row's own margin-bottom (see the homepage rule) is redundant
   here — the hint paragraph right below already supplies its own
   margin-top, so keeping both would double the gap. */
.toolbar-search .search-row {
  margin-bottom: 0;
}

.search-live-results {
  position: absolute;
  top: calc(100% + 0.4rem);
  left: 0;
  right: 0;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: 10px;
  box-shadow: var(--shadow);
  max-height: 320px;
  overflow-y: auto;
  overflow-x: hidden;
  z-index: 10;
}

.search-live-results.hidden { display: none; }

.search-live-item {
  display: flex;
  flex-direction: column;
  gap: 0.2rem;
  padding: 0.6rem 0.9rem;
  text-decoration: none;
  color: var(--text);
  border-bottom: 1px solid var(--border);
  min-width: 0;
}

.search-live-item:last-child { border-bottom: none; }
.search-live-item:hover { background: var(--bg); }

.search-live-name {
  font-weight: 600;
  font-size: 0.9rem;
}

.search-live-meta {
  font-size: 0.78rem;
  color: var(--text-muted);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.search-live-empty {
  padding: 0.8rem 0.9rem;
  font-size: 0.85rem;
  color: var(--text-muted);
}

.toolbar-search,
.toolbar-filters {
  transition: opacity 0.15s ease;
}

.toolbar-search.dimmed,
.toolbar-filters.dimmed {
  opacity: 0.4;
}

.toolbar-filters {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 0.6rem;
  align-content: start;
  border-left: 1px solid var(--border);
  padding-left: 1.5rem;
}

.toolbar-filters select {
  padding: 0.55rem 0.7rem;
  border-radius: 8px;
  border: 1px solid var(--border);
  background: var(--bg);
  color: var(--text);
  font-size: 0.9rem;
}

@media (max-width: 700px) {
  /* Collapsed behind the funnel button next to search, same as the
     homepage's .filter-row — placed after .toolbar-filters's base rule
     above so the display:none actually wins the cascade. */
  .toolbar-filters {
    display: none;
  }
  .toolbar-filters.open {
    display: grid;
    grid-template-columns: 1fr 1fr;
    margin-top: 0.9rem;
  }
}

.toolbar-search-hint {
  margin: 0.9rem 0 0;
  font-size: 0.85rem;
  line-height: 1.5;
  color: var(--text-muted);
}

@media (max-width: 700px) {
  .recipe-toolbar {
    grid-template-columns: 1fr;
    padding: 1rem;
    gap: 1rem;
  }
  .toolbar-filters {
    border-left: none;
    padding-left: 0;
    gap: 0.5rem;
  }
  .toolbar-search-hint {
    display: none;
  }
  .controls {
    padding: 0.9rem;
  }
}

.pick-result.hidden { display: none; }

.raffle-box {
  min-height: 200px;
  padding: 1.4rem 1.2rem;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  text-align: center;
  overflow: hidden;
}

.raffle-title {
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-size: clamp(1.4rem, 3vw, 1.9rem);
  font-weight: 700;
  color: var(--accent);
}

.raffle-name {
  display: inline-block;
  font-size: 0.95rem;
  font-weight: 500;
  color: var(--text-muted);
  animation: raffle-blur 0.09s ease-out;
}

@keyframes raffle-blur {
  0% { opacity: 0.2; transform: translateY(-6px) scaleY(1.3); filter: blur(2px); }
  100% { opacity: 1; transform: translateY(0) scaleY(1); filter: blur(0); }
}

.recipe-card.reveal {
  animation: raffle-pop 0.45s cubic-bezier(0.34, 1.56, 0.64, 1);
}

@keyframes raffle-pop {
  0% { opacity: 0; transform: scale(0.85) translateY(6px); }
  60% { opacity: 1; transform: scale(1.03) translateY(0); }
  100% { opacity: 1; transform: scale(1) translateY(0); }
}

.controls {
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 1.2rem;
  margin-bottom: 0.75rem;
}

@media (max-width: 700px) {
  /* On narrow screens the toolbar/controls card reads better flush against
     the edges right from first load, not just once scrolling has pinned it
     — plenty of width is already tight here, and the card's own side
     gutters are the first thing worth giving back. Placed after both
     .recipe-toolbar's and .controls's base rules above (not the earlier
     700px block) so it actually wins the cascade at equal specificity —
     same fix as the search-row/filter-row bugs above. */
  .recipe-toolbar,
  .controls {
    margin-left: -1rem;
    margin-right: -1rem;
    border-radius: 0;
  }
}

.search-row {
  display: flex;
  align-items: stretch;
  gap: 0.6rem;
  margin-bottom: 0.9rem;
}

#searchInput {
  flex: 1;
  min-width: 0;
  width: 100%;
  padding: 0.7rem 1rem;
  border-radius: 10px;
  border: 1px solid var(--border);
  background: var(--bg);
  color: var(--text);
  font-size: 1rem;
}

.filter-toggle-btn {
  display: none;
  flex: 0 0 auto;
  position: relative;
  width: 44px;
  align-items: center;
  justify-content: center;
  border-radius: 10px;
  border: 1px solid var(--border);
  background: var(--bg);
  color: var(--text-muted);
  cursor: pointer;
}

.filter-toggle-btn:hover {
  color: var(--accent-dark);
  border-color: var(--accent);
}

.filter-toggle-btn.active {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}

.filter-badge-dot {
  display: none;
  position: absolute;
  top: 6px;
  right: 6px;
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--mustard);
  border: 1.5px solid var(--surface);
}

.filter-toggle-btn.has-active-filters .filter-badge-dot {
  display: block;
}

@media (max-width: 700px) {
  /* The search box and filter button stay rounded at every width — only
     their container (.controls/.recipe-toolbar) goes flush/square on
     mobile. The row's own bottom margin only earns its keep once the
     filter row is actually open beneath it (.filter-row.open below
     supplies its own top margin when it opens) — otherwise it's just dead
     space above the very next card. */
  .search-row {
    margin-bottom: 0;
  }
}

.filter-row {
  display: flex;
  flex-wrap: wrap;
  gap: 0.6rem;
}

@media (max-width: 700px) {
  /* The full region/diet/spice/time/clear/condiments row is a lot of
     vertical real estate to spend before a reader has even seen a recipe
     card — collapse it behind the funnel button next to search, matching
     the recipe-toolbar's own already-compact mobile layout. Placed after
     the base .filter-toggle-btn/.filter-row rules above (not the earlier
     700px block) so it actually wins the cascade at equal specificity. */
  .filter-toggle-btn {
    display: flex;
  }
  .filter-row {
    display: none;
  }
  .filter-row.open {
    display: flex;
    margin-top: 0.9rem;
  }
}

.filter-row select {
  flex: 1 1 150px;
  padding: 0.55rem 0.7rem;
  border-radius: 8px;
  border: 1px solid var(--border);
  background: var(--bg);
  color: var(--text);
  font-size: 0.92rem;
}

/* A select carrying an actual choice (not its "All Regions"/"Any Time"
   placeholder) gets a visibly distinct border/background — otherwise every
   filter select looks identical whether or not it's actually narrowing the
   results. Toggled in app.js (markActiveSelects()) alongside the existing
   filter-badge-dot logic, not pure CSS, since there's no selector for "a
   <select>'s chosen option has a non-empty value". */
.filter-row select.active,
.toolbar-filters select.active,
.topbar-filter-panel select.active {
  border-color: var(--accent);
  background: var(--accent-soft);
  color: var(--accent-dark);
  font-weight: 600;
}

.clear-btn {
  flex: 0 0 auto;
  padding: 0.55rem 1rem;
  border-radius: 8px;
  border: 1px solid var(--border);
  background: transparent;
  color: var(--text-muted);
  cursor: pointer;
  font-size: 0.92rem;
}

.clear-btn:hover { color: var(--accent-dark); border-color: var(--accent); }

.toggle-btn {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
  padding: 0.55rem 1rem;
  border-radius: 8px;
  border: 1px solid var(--border);
  background: transparent;
  color: var(--text-muted);
  cursor: pointer;
  font-size: 0.92rem;
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
}

.toggle-btn:hover { color: var(--accent-dark); border-color: var(--accent); }

.toggle-btn.active {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}

.result-count {
  color: var(--text-muted);
  font-size: 0.9rem;
  margin: 0.4rem 0.2rem 1rem;
}

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

.region-page-intro {
  color: var(--text-muted);
  margin: 0 0.2rem 1rem;
}

.region-page-intro a {
  color: var(--accent-dark);
  font-weight: 600;
  text-decoration: none;
}

.region-page-intro a:hover {
  text-decoration: underline;
}

.region-nav {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem;
  margin: 0 0.2rem 1.5rem;
}

.region-nav-link {
  padding: 0.45rem 0.9rem;
  border-radius: 999px;
  border: 1px solid var(--border);
  background: var(--surface);
  color: var(--text);
  text-decoration: none;
  font-size: 0.85rem;
  font-weight: 600;
  transition: transform 0.15s ease, background 0.15s ease;
}

.region-nav-link:hover {
  transform: translateY(-1px);
  border-color: var(--accent);
}

.region-nav-link.active {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}

.category-select-wrap { display: none; }

@media (max-width: 700px) {
  .region-nav { display: none; }
  .category-select-wrap {
    display: block;
    margin: 0 0.2rem 1.5rem;
  }
  .category-select-wrap label {
    display: block;
    margin-bottom: 0.4rem;
    color: var(--text-muted);
    font-size: 0.78rem;
    font-weight: 700;
    letter-spacing: 0.05em;
    text-transform: uppercase;
  }
  .category-select {
    width: 100%;
    min-height: 48px;
    padding: 0.65rem 0.8rem;
    border: 2px solid var(--accent);
    border-radius: 10px;
    background: var(--surface);
    color: var(--accent-dark);
    font: inherit;
    font-weight: 700;
  }
  .category-select:focus-visible {
    outline: 2px solid var(--mustard);
    outline-offset: 2px;
  }
}

.ad-card {
  border-radius: var(--radius);
  border: 2px dashed var(--border);
  background: repeating-linear-gradient(
    135deg,
    var(--surface),
    var(--surface) 10px,
    var(--bg) 10px,
    var(--bg) 20px
  );
  min-height: 340px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 0.3rem;
  text-align: center;
  padding: 1rem;
}

.ad-card-label {
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-weight: 600;
  color: var(--text-muted);
  font-size: 0.95rem;
}

.ad-card-sublabel {
  font-size: 0.78rem;
  color: var(--text-muted);
  opacity: 0.75;
}

.inline-ad-slot {
  border-radius: var(--radius);
  border: 2px dashed var(--border);
  background: repeating-linear-gradient(
    135deg,
    var(--surface),
    var(--surface) 10px,
    var(--bg) 10px,
    var(--bg) 20px
  );
  min-height: 110px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 0.25rem;
  text-align: center;
  padding: 1rem;
  margin: 1.5rem 0;
}

/* Keep planned ad placements in the HTML/JS for launch, but reserve no
   visible space until AdSense is configured and the privacy policy updated. */
.ad-card,
.inline-ad-slot {
  display: none;
}

.recipe-card {
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 0;
  overflow: hidden;
  transition: transform 0.15s ease;
  display: flex;
  flex-direction: column;
  color: inherit;
  position: relative;
}

.recipe-card:hover { transform: translateY(-3px); }
.recipe-card:focus-within { outline: 2px solid var(--accent); outline-offset: 2px; }

.recipe-card-link {
  display: flex;
  flex-direction: column;
  flex: 1;
  min-width: 0;
  text-decoration: none;
  color: inherit;
}

.card-media {
  position: relative;
}

.recipe-card-img {
  width: 100%;
  aspect-ratio: 1 / 1;
  object-fit: cover;
  display: block;
  background: var(--accent-soft);
}

.fav-btn {
  position: absolute;
  z-index: 2;
  top: 0.6rem;
  right: 0.6rem;
  width: 34px;
  height: 34px;
  border-radius: 50%;
  border: none;
  background: rgba(0, 0, 0, 0.35);
  color: #fff;
  font-size: 1.15rem;
  line-height: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  backdrop-filter: blur(2px);
  transition: transform 0.15s ease, background 0.15s ease;
}

.fav-btn:hover {
  transform: scale(1.1);
  background: rgba(0, 0, 0, 0.5);
}

.fav-btn.active {
  color: var(--accent);
  background: rgba(255, 255, 255, 0.9);
}

.match-badge {
  position: absolute;
  top: 0.6rem;
  left: 0.6rem;
  background: var(--accent);
  color: #fff;
  font-size: 0.7rem;
  font-weight: 700;
  padding: 0.25rem 0.55rem;
  border-radius: 999px;
  z-index: 1;
  box-shadow: 0 1px 4px rgba(0, 0, 0, 0.25);
}

.recipe-card-body {
  padding: 1.1rem;
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
  flex-grow: 1;
}

.raffle-card {
  align-items: stretch;
}

.raffle-card .recipe-card-link { flex-direction: row; }

.raffle-card .card-media {
  width: 200px;
  height: 200px;
  flex-shrink: 0;
}

.raffle-card .recipe-card-img {
  width: 200px;
  height: 200px;
  aspect-ratio: 1 / 1;
}

.raffle-card .recipe-card-body {
  justify-content: center;
}

@media (max-width: 520px) {
  .raffle-card .recipe-card-link { flex-direction: column; }

  .raffle-card .card-media {
    width: 100%;
    height: auto;
    aspect-ratio: 2 / 1;
  }

  .raffle-card .recipe-card-img {
    width: 100%;
    height: 100%;
    aspect-ratio: 2 / 1;
  }
}

.recipe-card h3 {
  margin: 0;
  font-size: 1.1rem;
}

.recipe-meta {
  font-size: 0.82rem;
  color: var(--text-muted);
}

.recipe-desc {
  font-size: 0.88rem;
  color: var(--text-muted);
  flex-grow: 1;
  display: -webkit-box;
  -webkit-line-clamp: 3;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

.tag-row {
  display: flex;
  flex-wrap: wrap;
  gap: 0.35rem;
}

.modal .tag-row {
  margin-bottom: 1rem;
}

.tag {
  background: var(--accent-soft);
  color: var(--accent-dark);
  padding: 0.2rem 0.6rem;
  border-radius: 999px;
  font-size: 0.75rem;
  font-weight: 600;
}

.tag-sage {
  background: var(--secondary-soft);
  color: var(--secondary-dark);
}

.tag-mustard {
  background: var(--mustard-soft);
  color: var(--mustard-dark);
}

.tag-condiment {
  background: transparent;
  border: 1.5px solid var(--mustard-dark);
  color: var(--mustard-dark);
  font-weight: 700;
}

.shared-ingredients-row {
  margin: 0.1rem 0 0.4rem;
}

.tag-shared {
  background: var(--secondary-soft);
  border: 1px solid var(--secondary-soft);
  color: var(--secondary-dark);
  font-weight: 600;
}

.search-live-condiment {
  font-size: 0.65rem;
  padding: 0.05rem 0.4rem;
  vertical-align: middle;
  margin-left: 0.3rem;
}

.fav-toast {
  position: fixed;
  right: 1.5rem;
  bottom: 1.5rem;
  z-index: 200;
  display: flex;
  align-items: center;
  gap: 0.55rem;
  background: var(--accent);
  color: #fff;
  padding: 0.7rem 1.1rem;
  border-radius: 999px;
  box-shadow: var(--shadow);
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-weight: 600;
  font-size: 0.92rem;
  opacity: 0;
  transform: translateY(12px) scale(0.95);
  pointer-events: none;
  transition: opacity 0.2s ease, transform 0.2s ease;
}

.fav-toast.show {
  opacity: 1;
  transform: translateY(0) scale(1);
}

.fav-toast-icon {
  font-size: 1.1rem;
  line-height: 1;
  animation: fav-toast-pop 0.35s ease;
}

.fav-toast.show .fav-toast-icon {
  animation: fav-toast-pop 0.35s ease;
}

@keyframes fav-toast-pop {
  0% { transform: scale(0.6); }
  50% { transform: scale(1.25); }
  100% { transform: scale(1); }
}

.fav-toast-count {
  background: rgba(255, 255, 255, 0.25);
  border-radius: 999px;
  padding: 0.1rem 0.5rem;
  font-size: 0.8rem;
}

@media (max-width: 520px) {
  .fav-toast {
    right: 1rem;
    bottom: 1rem;
    padding: 0.6rem 0.9rem;
  }
}

.favorites-nav-btn.hidden { display: none; }

.favorites-nav-btn {
  position: fixed;
  bottom: 1.1rem;
  left: 1.5rem;
  z-index: 300;
  display: flex;
  align-items: center;
  gap: 0.4rem;
  background: var(--surface);
  color: var(--accent-dark);
  border: 1px solid var(--border);
  padding: 0.5rem 0.9rem;
  border-radius: 999px;
  box-shadow: var(--shadow);
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-weight: 600;
  font-size: 0.85rem;
  text-decoration: none;
  transition: transform 0.15s ease, background 0.15s ease, color 0.15s ease, border-color 0.15s ease;
}

.favorites-nav-btn:hover {
  transform: translateY(-1px);
}

.favorites-nav-btn.has-favorites {
  background: var(--accent);
  color: #fff;
  border-color: var(--accent);
}

/* Toggled by an IntersectionObserver on the footer (see
   initFavoritesButtonFooterFade in app.js) — the pill stays position:fixed
   the whole time (no layout-dependent repositioning to get wrong or race
   against page load), just switches to a color that actually contrasts
   against the footer's dark maroon background once it has scrolled into
   view. Without this, the .has-favorites fill (also a dark maroon) reads
   as nearly the same color as the footer behind it. */
.favorites-nav-btn.near-footer {
  background: var(--mustard);
  color: var(--accent-dark);
  border-color: var(--mustard-dark);
}

.favorites-nav-btn.near-footer:hover {
  background: var(--mustard-dark);
  color: #fff;
}

.favorites-nav-icon {
  font-size: 1rem;
  line-height: 1;
}

@media (max-width: 640px) {
  .favorites-nav-btn {
    bottom: 0.7rem;
    left: 0.7rem;
    padding: 0.45rem 0.75rem;
    font-size: 0.8rem;
  }
}

.favorites-banner.hidden { display: none; }

.favorites-banner {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 0.75rem;
  background: var(--accent-soft);
  color: var(--accent-dark);
  border-radius: 10px;
  padding: 0.7rem 1rem;
  margin: 0.4rem 0.2rem 1.2rem;
  font-size: 0.92rem;
  font-weight: 600;
}

.favorites-banner button,
.favorites-banner a {
  flex: 0 0 auto;
  display: inline-block;
  background: transparent;
  border: 1px solid var(--accent-dark);
  color: var(--accent-dark);
  border-radius: 8px;
  padding: 0.4rem 0.8rem;
  font-size: 0.85rem;
  font-weight: 600;
  cursor: pointer;
  text-decoration: none;
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  transition: background 0.15s ease, color 0.15s ease;
}

.favorites-banner button:hover,
.favorites-banner a:hover {
  background: var(--accent-dark);
  color: #fff;
}

.no-results {
  text-align: center;
  color: var(--text-muted);
  padding: 3rem 1rem;
}

.load-more-wrap {
  display: flex;
  justify-content: center;
  margin: 2rem 0 1rem;
}

.load-more-btn {
  display: inline-block;
  background: var(--surface);
  color: var(--accent);
  border: 2px solid var(--accent);
  padding: 0.75rem 2rem;
  border-radius: 999px;
  font-size: 0.95rem;
  font-weight: 600;
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  text-decoration: none;
  cursor: pointer;
  transition: background 0.15s ease, color 0.15s ease, transform 0.15s ease;
}

.load-more-btn:hover {
  background: var(--accent);
  color: #fff;
  transform: translateY(-1px);
}

.load-more-btn.hidden { display: none; }

.modal-overlay {
  position: fixed;
  inset: 0;
  background: rgba(20, 14, 8, 0.55);
  display: flex;
  align-items: flex-start;
  justify-content: center;
  padding: 3vh 1rem;
  overflow-y: auto;
  z-index: 100;
}

.modal-overlay.hidden { display: none; }

.modal {
  background: var(--surface);
  border-radius: var(--radius);
  max-width: 640px;
  width: 100%;
  padding: 2rem;
  /* .modal-img-wrap below bleeds the recipe photo edge-to-edge by
     negative-margining out exactly this padding — keep it in a variable so
     the two stay in sync at every breakpoint instead of drifting apart. */
  --modal-pad: 2rem;
  position: relative;
  box-shadow: var(--shadow);
}

@media (max-width: 700px) {
  /* .modal is both the popup dialog and the recipe entry article
     (.recipe-main) — 2rem of padding on every side reads as excessive
     dead space on a phone screen already spending 1rem on <main>'s own
     gutter either side. */
  .modal {
    padding: 1.1rem;
    --modal-pad: 1.1rem;
  }
}

.recipe-page-layout {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(260px, 340px);
  gap: 2rem;
  margin-top: 0.5rem;
  align-items: start;
}

.recipe-page-layout .recipe-main {
  max-width: none;
  grid-column: 1;
  grid-row: 1;
}

.related-recipes {
  position: sticky;
  top: var(--sidebar-sticky-top, 7.75rem);
  display: flex;
  flex-direction: column;
  gap: 1rem;
  will-change: transform;
  transform: translateZ(0);
  grid-column: 2;
  grid-row: 1;
}

.recipe-page-layout > .region-page-intro {
  grid-column: 1;
  grid-row: 2;
  margin-top: -0.5rem;
}

.related-recipes-title {
  margin: 0 0 0.2rem;
  font-size: 0.95rem;
  font-weight: 700;
  color: var(--text-muted);
  text-transform: uppercase;
  letter-spacing: 0.04em;
}

.related-card .recipe-card-img {
  aspect-ratio: 2 / 1;
}

.related-card .recipe-card-body {
  padding: 0.85rem 0.95rem;
  gap: 0.35rem;
}

.related-card h3 {
  font-size: 0.95rem;
}

.related-card .recipe-desc {
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

@media (max-width: 860px) {
  .recipe-page-layout {
    grid-template-columns: 1fr;
  }
  .recipe-page-layout .recipe-main,
  .recipe-page-layout .related-recipes,
  .recipe-page-layout > .region-page-intro {
    grid-column: 1;
    grid-row: auto;
  }
  .related-recipes {
    position: static;
    flex-direction: row;
    flex-wrap: wrap;
  }
  .related-recipes .recipe-card {
    flex: 1 1 240px;
  }
  .ad-card {
    min-height: 120px;
    flex: 1 1 100%;
  }
  .related-recipes-title {
    flex: 1 1 100%;
  }
  .sidebar-tips {
    flex: 1 1 100%;
  }
}

@media (max-width: 520px) {
  .related-recipes {
    flex-direction: column;
  }
  .related-recipes .recipe-card {
    /* The 240px flex-basis above is a width hint for the row-wrap tablet
       layout; in column mode it becomes a height constraint instead and
       clips the description/ingredient-pills, so let the card grow to fit
       its content here. */
    flex: 1 1 auto;
  }
}

.sidebar-tips {
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 1rem 1.1rem;
}

.sidebar-tips-title {
  margin: 0 0 0.7rem;
  font-size: 0.95rem;
  font-weight: 700;
  color: var(--text-muted);
  text-transform: uppercase;
  letter-spacing: 0.04em;
}

.sidebar-tips-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 0.7rem;
}

.sidebar-tip-link {
  display: flex;
  align-items: center;
  gap: 0.7rem;
  text-decoration: none;
  color: var(--text);
}

.sidebar-tip-media {
  flex: 0 0 auto;
  width: 48px;
  aspect-ratio: 1 / 1;
  min-height: 0;
  overflow: hidden;
  border-radius: 8px;
  background: var(--accent-soft);
}

.sidebar-tip-img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.sidebar-tip-title {
  font-size: 0.85rem;
  line-height: 1.3;
  font-weight: 600;
}

.sidebar-tip-link:hover .sidebar-tip-title {
  color: var(--accent-dark);
}

.modal-close {
  z-index: 2;
  background: var(--accent-soft);
  color: var(--accent-dark);
  border: none;
  width: 34px;
  height: 34px;
  border-radius: 50%;
  cursor: pointer;
  font-size: 1rem;
  flex-shrink: 0;
  display: flex;
  align-items: center;
  justify-content: center;
}

.modal h2 { margin-top: 0; }

.modal-title-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 0.6rem;
}

.modal-title-row h1,
.modal-title-row h2 {
  margin: 0;
  flex: 1 1 auto;
  min-width: 0;
}

.modal-title-row-actions {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  flex-shrink: 0;
}

.modal-fav-btn {
  position: static;
  flex-shrink: 0;
  background: var(--accent-soft);
  color: var(--accent-dark);
  backdrop-filter: none;
}

.modal-fav-btn:hover {
  background: var(--accent-soft);
  transform: scale(1.1);
}

.modal-fav-btn.active {
  background: var(--accent);
  color: #fff;
}

.modal-img-wrap {
  position: relative;
  margin: 1rem calc(-1 * var(--modal-pad, 2rem));
  width: calc(100% + 2 * var(--modal-pad, 2rem));
}

.modal-img {
  width: 100%;
  aspect-ratio: 16 / 9;
  object-fit: cover;
  display: block;
  background: var(--accent-soft);
}

/* A solid pill behind the credit text, rather than trying to guess light vs.
   dark text from the photo underneath — the old approach sampled only the
   image's bottom-right corner for brightness, so it broke as soon as the
   credit line wrapped to two lines and covered more of the photo than that
   sampled swatch (exactly what happens with a longer photographer name).
   A background that's always dark enough for white text is legible over
   any photo, full stop. */
.img-credit-overlay {
  position: absolute;
  right: 0.6rem;
  bottom: 0.6rem;
  max-width: calc(100% - 1.2rem);
  padding: 0.3rem 0.55rem;
  border-radius: 8px;
  background: rgba(20, 16, 14, 0.65);
  font-size: 0.72rem;
  font-weight: 500;
  line-height: 1.35;
  color: #fdfaf5;
  text-align: right;
}

.img-credit-overlay a {
  color: inherit;
  text-decoration: underline;
  text-decoration-color: rgba(253, 250, 245, 0.5);
}

.img-credit-overlay a:hover {
  text-decoration-color: currentColor;
}

.modal-section h4,
.modal-section h2 {
  margin: 1.2rem 0 0.5rem;
  font-size: 1.05rem;
  color: var(--accent-dark);
}

.modal-section ul, .modal-section ol {
  padding-left: 1.2rem;
  margin: 0;
}

.modal-section li { margin-bottom: 0.35rem; }

.static-page {
  max-width: 720px;
  margin: 0 auto;
  line-height: 1.7;
}

.static-page h1 {
  margin: 0 0 0.3rem;
}

.static-page .static-page-updated {
  color: var(--text-muted);
  font-size: 0.85rem;
  margin: 0 0 1.5rem;
}

.static-page h2 {
  margin: 1.8rem 0 0.6rem;
  font-size: 1.15rem;
  color: var(--accent-dark);
}

.static-page p {
  margin: 0 0 1rem;
}

.static-page ul, .static-page ol {
  padding-left: 1.3rem;
  margin: 0 0 1rem;
}

.static-page li {
  margin-bottom: 0.4rem;
}

.static-page a {
  color: var(--accent-dark);
}

.static-page-back {
  display: inline-block;
  margin-top: 1.5rem;
  font-size: 0.9rem;
  color: var(--text-muted);
  text-decoration: none;
}

.static-page-back:hover {
  color: var(--accent-dark);
}

.gloss-term {
  background: none;
  border: none;
  padding: 0;
  margin: 0;
  font: inherit;
  color: inherit;
  cursor: pointer;
  text-decoration: underline dotted var(--mustard-dark);
  text-underline-offset: 3px;
  text-decoration-thickness: 1.5px;
}

.gloss-term:hover,
.gloss-term.active {
  color: var(--accent-dark);
  text-decoration-style: solid;
}

.glossary-panel {
  margin-top: 0.8rem;
  padding: 0.9rem 1rem;
  background: var(--mustard-soft);
  border-left: 3px solid var(--mustard-dark);
  border-radius: 8px;
  animation: raffle-pop 0.25s ease;
}

.allergen-note {
  margin: 0.9rem 0 0;
  padding: 0.7rem 1rem;
  background: var(--mustard-soft);
  border-left: 3px solid var(--mustard-dark);
  border-radius: 8px;
  font-size: 0.85rem;
  line-height: 1.5;
  color: var(--text);
}

.allergen-note a {
  color: var(--accent-dark);
}

.variant-note {
  margin-top: 0.9rem;
  padding: 0.9rem 1rem;
  background: var(--secondary-soft);
  border-left: 3px solid var(--secondary-dark);
  border-radius: 8px;
  font-size: 0.88rem;
  line-height: 1.55;
  color: var(--text);
}

.variant-note strong {
  color: var(--secondary-dark);
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
}

.glossary-panel.hidden { display: none; }

.glossary-panel-title {
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-weight: 700;
  color: var(--mustard-dark);
  margin-bottom: 0.3rem;
}

.glossary-panel-desc {
  margin: 0;
  font-size: 0.88rem;
  color: var(--text);
  line-height: 1.5;
}

.glossary-panel-note {
  margin: 0.5rem 0 0;
  font-size: 0.8rem;
  color: var(--text-muted);
  font-style: italic;
}

.glossary-recipe-link {
  display: inline-flex;
  align-items: center;
  margin-top: 0.6rem;
  background: var(--mustard-soft);
  border: 1.5px solid var(--mustard-dark);
  border-radius: 999px;
  padding: 0.4rem 0.9rem;
  font-size: 0.85rem;
  font-weight: 600;
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  color: var(--mustard-dark);
  cursor: pointer;
  text-decoration: none;
  transition: background 0.15s ease, color 0.15s ease;
}

.glossary-recipe-link:hover { background: var(--mustard-dark); color: #fff; }

.modal-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 0.7rem;
  margin-top: 1.6rem;
  padding-top: 1.2rem;
  border-top: 1px solid var(--border);
}

.action-btn {
  flex: 1 1 180px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.45rem;
  padding: 0.7rem 1rem;
  border-radius: 999px;
  font-size: 0.9rem;
  font-weight: 600;
  font-family: 'Arimo', 'Segoe UI', system-ui, -apple-system, sans-serif;
  border: none;
  cursor: pointer;
  text-decoration: none;
  transition: transform 0.15s ease, background 0.15s ease;
}

.action-btn:hover { transform: translateY(-1px); }

.whatsapp-btn {
  background: #25D366;
  color: #fff;
}

.whatsapp-btn:hover { background: #1fb457; }

.copy-btn {
  background: var(--secondary-soft);
  color: var(--secondary-dark);
}

.copy-btn:hover { background: var(--secondary); color: #fff; }

.copy-btn.copied {
  background: var(--secondary);
  color: #fff;
}

.site-footer {
  background: var(--accent-dark);
  color: rgba(255, 255, 255, 0.75);
  margin-top: 3rem;
  padding: 2.5rem 1rem 2rem;
}

.footer-inner {
  max-width: 800px;
  margin: 0 auto;
  text-align: center;
}

.footer-brand {
  color: #fff;
  font-family: 'Rubik', 'Segoe UI', system-ui, -apple-system, sans-serif;
  font-weight: 700;
  font-size: 1.1rem;
  margin: 0 0 0.9rem;
}

.footer-links {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: 1.2rem;
  margin-bottom: 1.2rem;
}

.footer-links a {
  color: #fff;
  text-decoration: none;
  font-size: 0.88rem;
  font-weight: 600;
}

.footer-links a:hover {
  color: var(--mustard);
  text-decoration: underline;
}

.analytics-consent-settings {
  padding: 0;
  border: 0;
  background: none;
  color: #fff;
  font: inherit;
  font-size: 0.88rem;
  font-weight: 600;
  cursor: pointer;
}

.analytics-consent-settings:hover,
.analytics-consent-settings:focus-visible {
  color: var(--mustard);
  text-decoration: underline;
}

.analytics-consent-banner {
  position: fixed;
  z-index: 300;
  left: max(1rem, calc((100vw - 700px) / 2));
  right: max(1rem, calc((100vw - 700px) / 2));
  bottom: 1rem;
  max-height: calc(100vh - 2rem);
  overflow: auto;
  padding: 1.2rem;
  border: 1px solid var(--border);
  border-top: 4px solid var(--mustard);
  border-radius: var(--radius);
  background: var(--surface);
  color: var(--text);
  box-shadow: 0 12px 36px rgba(41, 37, 34, 0.25);
}

.analytics-consent-copy h2 {
  margin: 0 0 0.35rem;
  font-size: 1.1rem;
  color: var(--accent-dark);
}

.analytics-consent-copy p {
  margin: 0 0 1rem;
  font-size: 1rem;
  line-height: 1.5;
}

.analytics-consent-copy a {
  color: var(--accent-dark);
  text-decoration: underline;
}

.analytics-consent-actions {
  display: flex;
  gap: 0.65rem;
}

.analytics-consent-actions button {
  flex: 1 1 0;
  min-height: 44px;
  padding: 0.6rem 0.8rem;
  border: 1px solid var(--accent);
  border-radius: 9px;
  background: var(--accent);
  color: #fff;
  font: inherit;
  font-weight: 700;
  cursor: pointer;
}

.analytics-consent-actions button:hover,
.analytics-consent-actions button:focus-visible {
  background: var(--accent-dark);
  outline: 2px solid var(--mustard);
  outline-offset: 2px;
}

@media (max-width: 520px) {
  .analytics-consent-actions { flex-direction: column; }
}

/* Region/diet browse links: still real crawlable links to region/*.html
   and diet/*.html (the whole point of those pages existing is to be
   discoverable via an on-page link, not just the sitemap), just tucked
   into the footer instead of sitting above the fold duplicating what the
   region/diet filter dropdowns already do. */
.footer-region-links {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: 0.5rem 0.9rem;
  margin: 0 0 0.9rem;
}

.footer-region-links a {
  color: rgba(255, 255, 255, 0.6);
  text-decoration: none;
  font-size: 0.78rem;
}

.footer-region-links a:hover {
  color: var(--mustard);
  text-decoration: underline;
}

.footer-tagline {
  font-size: 0.8rem;
  line-height: 1.6;
  margin: 0;
  color: rgba(255, 255, 255, 0.45);
}

.tips-section {
  margin-top: 3rem;
  padding-top: 2.5rem;
  border-top: 1px solid var(--border);
}

.tips-section h2 {
  margin: 0 0 0.3rem;
  font-size: 1.5rem;
  color: var(--accent);
}

.tips-intro {
  margin: 0 0 1.5rem;
  color: var(--text-muted);
  font-size: 0.92rem;
}

.tips-grid {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 1rem;
}

@media (max-width: 900px) {
  .tips-grid { grid-template-columns: repeat(2, 1fr); }
}

@media (max-width: 520px) {
  .tips-grid { grid-template-columns: 1fr; }
}

.tip-card {
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  overflow: hidden;
  cursor: pointer;
  display: flex;
  flex-direction: column;
  text-decoration: none;
  color: inherit;
  transition: transform 0.15s ease;
}

.tip-card:hover { transform: translateY(-3px); }

.tip-card-top {
  padding: 1rem 1rem 0.6rem;
}

.tip-card-top h3 {
  margin: 0;
  font-size: 0.95rem;
  line-height: 1.35;
  min-height: 2.7em;
  color: var(--text);
}

.tip-card-media {
  width: 100%;
  aspect-ratio: 2 / 1;
  min-height: 0;
  overflow: hidden;
  background: var(--accent-soft);
}

.tip-card-img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.tip-card-bottom {
  padding: 0.6rem 1rem 1rem;
}

.tip-card-bottom p {
  margin: 0;
  font-size: 0.8rem;
  line-height: 1.5;
  color: var(--text-muted);
}

.tips-footnote {
  margin-top: 1.4rem;
  padding-top: 1rem;
  border-top: 1px solid var(--border);
  font-size: 0.76rem;
  line-height: 1.6;
  color: var(--text-muted);
}

.tips-footnote strong {
  color: var(--text);
}

.tips-footnote a {
  color: var(--secondary-dark);
}

/* The full tips/index.html listing — a 2-up grid of horizontal cards
   (square thumbnail + title/excerpt), distinct from the vertical .tip-card
   used in the homepage's own tips section. Server-rendered in a stable
   (alphabetical) order for crawlability; app.js reshuffles the cards
   client-side on load for visual variety without touching the ad slots'
   fixed positions (see initTipsListShuffle()). */
.tips-list-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 1.25rem;
  margin-top: 1.5rem;
}

.tips-list-card {
  display: flex;
  gap: 1rem;
  background: var(--surface);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 1rem;
  text-decoration: none;
  color: inherit;
  transition: transform 0.15s ease;
}

.tips-list-card:hover {
  transform: translateY(-3px);
}

.tips-list-card-media {
  flex: 0 0 128px;
  aspect-ratio: 1 / 1;
  border-radius: 10px;
  overflow: hidden;
  background: var(--accent-soft);
}

.tips-list-card-media img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.tips-list-card-body {
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 0.4rem;
  min-width: 0;
}

.tips-list-card-body h3 {
  margin: 0;
  font-size: 1rem;
  line-height: 1.35;
  color: var(--text);
}

.tips-list-card-body p {
  margin: 0;
  font-size: 0.85rem;
  line-height: 1.5;
  color: var(--text-muted);
}

.tips-list-grid .inline-ad-slot {
  grid-column: 1 / -1;
}

@media (max-width: 700px) {
  .tips-list-grid {
    grid-template-columns: 1fr;
  }
  .tips-list-card-media {
    flex-basis: 96px;
  }
}

@media (max-width: 700px) {
  /* Keep the original inputs in the DOM for filter/search state, while the
     topbar dropdown provides their only visible mobile interface. */
  .recipe-toolbar,
  .controls,
  .detail-page .site-header,
  .static-info-page .site-header {
    display: none;
  }
  .detail-page main,
  .static-info-page main {
    margin-top: 1rem;
  }
  .topbar-extra-btn {
    flex: 1 1 0;
    min-width: 0;
    padding: 0.45rem 0.25rem;
    border: 1px solid var(--border);
    border-radius: 8px;
    background: var(--bg);
    color: var(--text);
    font: inherit;
    font-size: 0.78rem;
    white-space: nowrap;
    cursor: pointer;
  }
  .topbar-extra-row {
    display: flex;
    gap: 0.5rem;
  }
  .topbar-extra-btn.active {
    background: var(--accent-soft);
    border-color: var(--accent);
    color: var(--accent-dark);
  }
}

@media (min-width: 701px) {
  .topbar-extra-btn { display: none; }
}
