/* Palette: warm cocoa-brown chrome + cream content + a vivid red-orange accent — modeled on
   a mobile food-ordering app reference (dark brown header/nav, white item cards, orange CTA).
   --gold/--gold-soft/etc. keep their historical names (see below) but now carry that
   red-orange hue instead of the site's original amber-gold. */
:root{
  --bg: #f2e4c8;
  --panel: #f8eeda;
  --panel-2: #ffffff;
  --border: #e8d9b8;
  --gold: #e8531f;
  --gold-soft: rgba(232,83,31,.13);
  --gold-hover: #c8410f;
  --gold-text: #fff8f0;
  --text: #3a2415;
  --text-dim: #8c7a5e;
  --chrome-bg: linear-gradient(180deg,#3d2013,#2a1409);
  --chrome-text: #fdf3e2;
  --chrome-text-dim: rgba(253,243,226,.68);
  --font: 'Poppins', system-ui, -apple-system, sans-serif;
  --header-h: 70px;
  --footer-h: 0px;
}

/* light theme — toggled via [data-theme] on <html>, set by the theme switch in the sidebar.
   Same cream/orange identity, but the header/footer chrome goes light too instead of dark
   cocoa-brown, for a cleaner/brighter alternative rather than a literal light-vs-dark swap. */
:root[data-theme="light"]{
  --bg:#fffaf0;
  --panel: var(--bg);
  --panel-2:#ffffff;
  --border:#efe1c4;
  --gold:#c8410f;
  --gold-soft:rgba(200,65,15,.11);
  --gold-hover:#a3350c;
  --gold-text:#fff8f0;
  --text:#2a1c10;
  --text-dim:#8d7e68;
  --chrome-bg: #ffffff;
  --chrome-text: var(--text);
  --chrome-text-dim: var(--text-dim);
}

*{box-sizing:border-box}
html,body{height:100%}
body{
  margin:0;
  font-family:var(--font);
  background:
    radial-gradient(1200px 600px at 50% -10%, rgba(232,83,31,.08), transparent 60%),
    var(--bg);
  color:var(--text);
  -webkit-font-smoothing:antialiased;
}

/* global link safety net — no link on this site should ever render in browser-default
   blue/purple; every <a> falls back to the gold theme color unless a component class
   (like .btn-call) gives it its own look */
a{color:var(--gold)}
a:visited{color:var(--gold)}

.app-shell{
  max-width:480px;
  margin:0 auto;
  min-height:100vh;
  min-height:100dvh;
  display:flex;
  flex-direction:column;
  background:var(--panel);
  border-left:1px solid var(--border);
  border-right:1px solid var(--border);
  box-shadow:0 0 40px rgba(60,32,19,.12);
}

/* ---------- HEADER ---------- */
.bot-header{
  display:flex;
  flex-wrap:wrap;
  align-items:center;
  justify-content:space-between;
  gap:8px 12px;
  min-height:var(--header-h);
  padding:10px 20px;
  background:var(--chrome-bg);
  border-bottom:1px solid var(--border);
  position:sticky;
  top:0;
  z-index:30;
}
/* .brand is a <button> (doubles as the header's Home affordance — the bottom-nav Home
   tab is mobile-only, so desktop otherwise has no way back to the default view) reset
   to look identical to the plain div it used to be */
.brand{display:flex;align-items:center;gap:10px;min-width:0;background:none;border:none;padding:0;margin:0;font:inherit;text-align:left;cursor:pointer;color:inherit}
.brand:focus-visible{outline:2px solid var(--gold);outline-offset:3px;border-radius:8px}
.brand-mark{
  color:var(--gold);
  display:flex;
  flex-shrink:0;
  width:42px;height:42px;
  align-items:center;justify-content:center;
  border:1.5px solid var(--gold);
  border-radius:50%;
  background:var(--gold-soft);
}
.brand-text{display:flex;flex-direction:column;min-width:0}
.brand-name{font-weight:700;font-size:15px;color:var(--chrome-text);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.brand-tag{font-size:11px;color:var(--chrome-text-dim);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.btn-call{
  display:flex;align-items:center;gap:6px;
  flex-shrink:0;
  font-size:12.5px;font-weight:600;
  color:var(--gold-text);
  background:var(--gold);
  padding:8px 12px;
  border-radius:999px;
  text-decoration:none;
  white-space:nowrap;
}

/* branches + rating, grouped on the header's right side; wraps to its own second line
   (still right-aligned) if the header gets too narrow to fit next to the brand */
.header-actions{
  display:flex;
  flex-wrap:wrap;
  align-items:center;
  justify-content:flex-end;
  gap:8px;
  flex:1 1 auto;
  min-width:0;
}

/* desktop-only entry point to the branches page (the bottom nav's own "Branches" tab
   covers this on mobile, where .header-actions has no room for a second pill anyway —
   see the max-width:860px block, which hides this and shows the bottom nav instead) */
.branches-pill{
  display:inline-flex;
  align-items:center;
  gap:6px;
  flex-shrink:0;
  background:transparent;
  border:1px solid rgba(255,255,255,.3);
  color:var(--chrome-text);
  font-family:var(--font);
  font-size:12px;
  font-weight:600;
  padding:6px 14px;
  border-radius:999px;
  cursor:pointer;
  transition:border-color .15s,background .15s,color .15s;
}
:root[data-theme="light"] .branches-pill{border-color:var(--border)}
.branches-pill:hover{border-color:var(--gold);color:var(--gold)}
.branches-pill.is-active{background:var(--gold);border-color:var(--gold);color:var(--gold-text)}
.branches-pill svg{flex-shrink:0}

/* the search bar is part of the app bar itself — a full-width row that always wraps
   onto its own line below brand/rating, rather than a separate sticky strip below the
   header. Now also holds the language switch + wishlist button alongside the search
   pill, so it's a flex row itself — justify-content:center keeps that trio centered as
   a group, same visual position the search-pill alone used to center itself to.
   width:100% (not flex-basis:100%) forces the full-width row — Chromium has a real
   layout bug where a *percentage flex-basis* on an item that ends up alone on its own
   wrapped line, inside a `justify-content:space-between` container, resolves against
   the wrong box and overflows past the container's own padding on one side (caught
   here: the wishlist button was rendering flush against the header's outer edge on
   mobile, 20px further right than it should, ignoring .bot-header's right padding
   entirely — flex-basis:100% measured 298px on a 320px-wide phone where the container's
   actual content width was 278px). `width` percentages don't have this bug, so
   flex-basis is left at its default (`auto`) and `width` does the full-width-row job
   instead; flex-grow/shrink stay at 0 since the explicit width already fixes the size. */
.header-search{
  flex:0 0 auto;
  width:100%;
  margin:0;
  display:flex;
  align-items:center;
  justify-content:center;
  gap:10px;
}

/* circular language toggle, sitting right before the search bar (a single instance now,
   replacing the old header/bottom-nav pair — see buildLangSwitch()/langSwitchTriggers in
   js/app.js) — shows only the language you'd switch TO, as menu.json's short
   language.*.label. Solid gold, since it's a standing "do this" action rather than a
   location indicator (same convention as .bottom-nav-item.is-active/.branches-pill.is-active),
   unlike .wishlist-btn just below, which is an outline toggle into a view. */
.lang-switch-btn{
  flex-shrink:0;
  width:38px;
  height:38px;
  border-radius:50%;
  display:flex;
  align-items:center;
  justify-content:center;
  border:none;
  background:var(--gold);
  color:var(--gold-text);
  font-family:var(--font);
  font-size:10px;
  font-weight:700;
  line-height:1.1;
  text-align:center;
  padding:2px;
  cursor:pointer;
  transition:background .15s;
}
.lang-switch-btn:hover{background:var(--gold-hover)}
.lang-switch-btn[hidden]{display:none}
/* clamps to 2 lines instead of overflowing the circle — Tamil script in particular
   ("தமிழ்") needs the room a single line at a legible size wouldn't give it */
.lang-switch-btn span{
  display:-webkit-box;
  -webkit-line-clamp:2;
  -webkit-box-orient:vertical;
  overflow:hidden;
}

/* circular button next to the search bar that opens the wishlist popup (#wishlist-modal).
   Sized to match .search-pill's rendered height so the pair reads as one row. Outline
   style (like .theme-toggle) rather than solid gold — it's a toggle into a view, not a
   standing CTA the way .lang-switch-btn just above is. */
.wishlist-btn{
  position:relative;
  flex-shrink:0;
  width:38px;
  height:38px;
  border-radius:50%;
  display:flex;
  align-items:center;
  justify-content:center;
  border:1px solid var(--border);
  background:var(--panel-2);
  color:var(--text-dim);
  cursor:pointer;
  transition:border-color .15s,color .15s,background .15s;
}
.wishlist-btn:hover{border-color:var(--gold);color:var(--gold)}
.wishlist-btn svg{flex-shrink:0}
.wishlist-badge{
  position:absolute;
  top:-3px;
  right:-3px;
  min-width:16px;
  height:16px;
  padding:0 3px;
  border-radius:999px;
  background:var(--gold);
  color:var(--gold-text);
  font-family:var(--font);
  font-size:10px;
  font-weight:700;
  line-height:16px;
  text-align:center;
}
.wishlist-badge[hidden]{display:none}

/* ---------- SIDEBAR SETTINGS (theme toggle + language switch, pinned to the sidebar's
   bottom edge — one location shared by the mobile drawer and the permanent desktop
   sidebar, instead of a separate fixed footer bar) ---------- */
.sidebar-settings{
  display:flex;
  align-items:center;
  justify-content:center;
  gap:8px;
  flex-shrink:0;
  padding:12px 10px;
  border-top:1px solid var(--border);
  background:var(--panel-2);
}
/* unconditional display:flex above would defeat the hidden attribute (see the [hidden] gotcha in CLAUDE.md) */
.sidebar-settings[hidden]{display:none}
.theme-toggle{
  display:flex;
  align-items:center;
  justify-content:center;
  flex-shrink:0;
  width:32px;
  height:32px;
  border:1px solid var(--border);
  border-radius:50%;
  background:var(--panel-2);
  color:var(--gold);
  cursor:pointer;
  transition:background .15s,border-color .15s;
}
.theme-toggle:hover{border-color:var(--gold);background:var(--gold-soft)}
.theme-toggle svg{width:16px;height:16px}
.theme-toggle .icon-sun{display:none}
:root[data-theme="light"] .theme-toggle .icon-moon{display:none}
:root[data-theme="light"] .theme-toggle .icon-sun{display:block}

.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;
}

/* ---------- LAYOUT: 20 / 80 ---------- */
.layout{
  flex:1;
  display:flex;
  align-items:flex-start;
  min-height:0;
}

.sidebar{
  flex:0 0 20%;
  max-width:280px;
  min-width:200px;
  height:calc(100vh - var(--header-h) - var(--footer-h));
  /* 100vh on mobile browsers (iOS Safari especially) reports the viewport as if the
     address-bar chrome weren't showing, overshooting the actually-visible area — since
     .bottom-nav is position:fixed to the *real* visible bottom, that overshoot let this
     pane silently extend behind it (the reported "bottom bar hides categories" bug).
     100dvh (dynamic viewport height) tracks the true visible viewport as browser chrome
     shows/hides; unsupported browsers simply ignore this line and keep the 100vh height
     above. Same fix applied to .content/.subsidebar below and .app-shell's min-height. */
  height:calc(100dvh - var(--header-h) - var(--footer-h));
  position:sticky;
  top:var(--header-h);
  display:flex;
  flex-direction:column;
  /* same background as .content (via .app-shell) and no dividing border — the reference
     mockup's category rail and item list read as one continuous surface, not two split
     panels; only the cards themselves (not a panel edge) separate the two columns */
  background:var(--panel);
}
/* .sidebar has an unconditional display:flex above, which beats the user-agent
   [hidden]{display:none} default at equal specificity — same gotcha documented
   elsewhere in this file for .card-grid/.subfilter/.branches-list. Hidden while the
   Our Branches page is showing (see showBranchesPage()/renderCards() in js/app.js):
   categories/sub-categories are a menu-browsing concept and shouldn't appear
   alongside a page that isn't the menu, and .content is a flex:1 sibling so it
   fills the freed width automatically. */
.sidebar[hidden]{display:none}
.sidebar-inner{flex:1;min-height:0;overflow-y:auto;padding:14px 10px;display:flex;flex-direction:column;gap:8px}

.sidebar-group{flex-shrink:0}

/* square-ish card per category: icon in a colored roundel on top, label centered below —
   stacked vertically as one scrollable column (mirrors the reference app's category rail,
   built from icons rather than photos since this menu has no per-dish/category photography) */
.sidebar-cat{
  width:100%;
  display:flex;
  flex-direction:column;
  align-items:center;
  gap:8px;
  font-family:var(--font);
  font-size:14px;
  font-weight:700;
  text-align:center;
  color:var(--text);
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:16px;
  padding:14px 8px;
  cursor:pointer;
  box-shadow:0 2px 6px rgba(0,0,0,.05);
  transition:background .15s,color .15s,border-color .15s,transform .1s;
}
.sidebar-cat:hover{border-color:var(--gold);transform:translateY(-1px)}
.sidebar-cat.is-active{
  background:var(--gold);
  border-color:var(--gold);
  color:var(--gold-text);
}
.sidebar-cat.is-active .sidebar-icon-wrap{background:rgba(255,255,255,.22)}
.sidebar-icon-wrap{
  display:flex;
  align-items:center;
  justify-content:center;
  width:44px;
  height:44px;
  border-radius:12px;
  background:var(--gold-soft);
  flex-shrink:0;
  transition:background .15s;
}
.sidebar-cat .sidebar-icon{font-size:22px;line-height:1}
.sidebar-label{
  display:-webkit-box;
  -webkit-line-clamp:2;
  -webkit-box-orient:vertical;
  overflow:hidden;
  line-height:1.25;
}

/* ---------- SUB-CATEGORY COLUMN (desktop only — a third column between Main
   Categories and the item list; see #subfilter for mobile's pill-row equivalent) ---------- */
.subsidebar{
  flex:0 0 18%;
  max-width:220px;
  min-width:170px;
  height:calc(100vh - var(--header-h) - var(--footer-h));
  height:calc(100dvh - var(--header-h) - var(--footer-h));
  position:sticky;
  top:var(--header-h);
  display:flex;
  flex-direction:column;
  background:var(--panel);
  /* a clearly visible divider between the main-category sidebar and this sub-category
     column — var(--border) alone is too close in tone to var(--panel) (both panels
     share the same background) to read as a real separator, so this uses the stronger
     --text-dim tone instead, per explicit request after the two columns read as one
     undivided block. The plain var(--border) line stays first as a fallback for
     browsers without color-mix() support. */
  border-left:1px solid var(--border);
  border-left:2px solid color-mix(in srgb, var(--text-dim) 50%, transparent);
}
/* same [hidden]-vs-unconditional-display gotcha as .sidebar/.card-grid/.subfilter above */
.subsidebar[hidden]{display:none}
.subsidebar-inner{flex:1;min-height:0;overflow-y:auto;padding:14px 10px;display:flex;flex-direction:column;gap:8px}
.subsidebar-btn{
  width:100%;
  text-align:left;
  font-family:var(--font);
  font-size:13px;
  font-weight:600;
  color:var(--text-dim);
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:12px;
  padding:11px 14px;
  cursor:pointer;
  transition:background .15s,color .15s,border-color .15s;
}
.subsidebar-btn:hover{border-color:var(--gold);color:var(--text)}
.subsidebar-btn.is-active{
  background:var(--gold);
  border-color:var(--gold);
  color:var(--gold-text);
}

/* ---------- CONTENT (80%) ---------- */
.content{
  flex:1;
  min-width:0;
  height:calc(100vh - var(--header-h) - var(--footer-h));
  height:calc(100dvh - var(--header-h) - var(--footer-h));
  position:sticky;
  top:var(--header-h);
  display:flex;
  flex-direction:column;
}

/* decorative food icons + smoke drifting behind the grid, only visible through empty gaps */
.content-decor{
  position:absolute;
  inset:0;
  overflow:hidden;
  pointer-events:none;
  z-index:0;
}
.decor-item{
  position:absolute;
  font-size:32px;
  opacity:.16;
  filter:blur(1.5px) grayscale(.2);
  will-change:transform;
  animation:foodDrift linear infinite;
}
.di-1{top:8%;  left:-14%; font-size:40px; animation-duration:34s; animation-delay:0s}
.di-2{top:26%; left:-18%; font-size:28px; animation-duration:26s; animation-delay:-6s}
.di-3{top:48%; left:-15%; font-size:36px; animation-duration:38s; animation-delay:-14s}
.di-4{top:66%; left:-20%; font-size:26px; animation-duration:22s; animation-delay:-3s}
.di-5{top:16%; left:-22%; font-size:30px; animation-duration:30s; animation-delay:-20s}
.di-6{top:82%; left:-16%; font-size:34px; animation-duration:36s; animation-delay:-10s}
@keyframes foodDrift{
  from{transform:translateX(0) translateY(0) rotate(0deg)}
  to{transform:translateX(130vw) translateY(-24px) rotate(10deg)}
}

.smoke-puff{
  position:absolute;
  width:180px;
  height:180px;
  border-radius:50%;
  background:radial-gradient(circle, rgba(232,83,31,.12), transparent 70%);
  filter:blur(8px);
  animation:puffDrift ease-in-out infinite;
}
.sp-1{top:5%;  left:15%; animation-duration:22s; animation-delay:0s}
.sp-2{top:45%; left:55%; animation-duration:28s; animation-delay:-9s}
.sp-3{top:70%; left:20%; animation-duration:25s; animation-delay:-16s}
@keyframes puffDrift{
  0%,100%{transform:translate(0,0) scale(1); opacity:.5}
  50%{transform:translate(36px,-50px) scale(1.25); opacity:.85}
}

@media (prefers-reduced-motion: reduce){
  .decor-item,.smoke-puff{animation:none}
}

.content-sticky{
  position:relative;
  z-index:1;
  flex-shrink:0;
  padding:20px 22px 0;
  background:var(--panel);
}
.content-head{margin-bottom:4px}
.content-head h2{margin:0;font-size:22px;font-weight:800}

/* ---------- SEARCH BAR (lives in the app bar itself now — a second wrapped row inside
   .bot-header, see the header rules above — rather than a separate strip below it) ---------- */
.search-pill{
  display:flex;
  align-items:center;
  gap:10px;
  flex:1 1 auto;
  /* without this, .search-pill's automatic flex-shrink floor (min-width:auto's default)
     was effectively its own *preferred* content width, not its actual min-content —
     since it's a flex container in its own right, not a plain box — so on a narrow
     phone it never shrank to fit alongside .lang-switch-btn/.wishlist-btn at all: the
     row's total content silently overflowed #search-form's edges by the same amount on
     both sides (justify-content:center centers overflow symmetrically), pushing the
     wishlist icon out past the header's own right padding. min-width:0 is the standard
     fix — it lets the browser shrink this flex item down toward its real min-content
     (icon + padding; #search-input already has its own min-width:0 for the same reason). */
  min-width:0;
  max-width:480px;
  margin:0;
  padding:9px 14px;
  background:var(--panel-2);
  border:none;
  border-radius:999px;
  color:var(--text-dim);
  box-shadow:0 3px 12px rgba(0,0,0,.3);
  transition:box-shadow .2s ease,background .2s ease,color .2s ease;
}
.search-pill:focus-within{
  color:var(--gold);
  background:var(--panel);
  box-shadow:0 0 0 4px var(--gold-soft),0 3px 12px rgba(0,0,0,.35);
}
/* the input itself carries no border/background/padding of its own — it used to have
   its own gold border + pill radius, which visually read as a second nested pill sitting
   inside .search-pill's own rounded background, separating the icon from the placeholder
   text instead of the two reading as one "🔍 Search dishes…" unit. .search-pill alone is
   now the only visible pill; the icon and input just sit side by side inside it (the
   10px gap above provides the icon-to-text spacing). */
.header-search input{
  flex:1;
  min-width:0;
  border:none;
  outline:none;
  background:transparent;
  color:var(--text);
  font-family:var(--font);
  font-size:14px;
  padding:0;
}

.content-title-row{
  display:flex;
  align-items:center;
  justify-content:center;
}
.content-title-row h2{
  min-width:0;
  text-align:center;
  overflow:hidden;
  text-overflow:ellipsis;
  white-space:nowrap;
}

.result-summary{
  font-size:12.5px;
  color:var(--text-dim);
  text-align:center;
  margin:8px 2px 6px;
}

.subfilter{
  display:flex;
  flex-wrap:wrap;
  gap:8px;
  margin:0 2px 14px;
}
.subfilter[hidden]{display:none}
/* the pill row is the only sub-category UI now that the desktop #subsidebar column is
   permanently hidden (see the LAYOUT RULES note near the end of this file) */
.subfilter-btn{
  font-family:var(--font);
  font-size:12.5px;
  font-weight:600;
  color:var(--text-dim);
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:999px;
  padding:7px 14px;
  cursor:pointer;
  transition:background .15s,color .15s,border-color .15s;
}
.subfilter-btn:hover{border-color:var(--gold);color:var(--text)}
.subfilter-btn.is-active{
  background:var(--gold);
  border-color:var(--gold);
  color:var(--gold-text);
}

/* only this pane scrolls — categories (sidebar) and the title/count above stay put */
.content-scroll{
  position:relative;
  z-index:1;
  flex:1;
  min-height:0;
  overflow-y:auto;
  padding:0 22px 40px;
}

.empty-state{
  color:var(--text-dim);
  font-size:14px;
  padding:30px 4px;
}

/* ---------- MENU ITEM LIST (dynamic) ---------- */
.card-grid{
  display:flex;
  flex-direction:column;
  gap:12px;
}
/* an explicit [hidden] override is required here — [hidden] and .card-grid are equal
   specificity, and author styles (this rule) beat the user-agent [hidden] default, so
   without this the JS `cardGrid.hidden = true` pattern used across selectTop/selectSub/
   runSearch/showBranchesPage silently does nothing and old cards stay visible underneath
   whatever replaces them (caught when it left old category cards showing through the
   branches page) */
.card-grid[hidden]{display:none}
.food-card{
  position:relative;
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:16px;
  padding:12px 14px;
  display:flex;
  align-items:center;
  gap:14px;
  box-shadow:0 2px 8px rgba(0,0,0,.05);
  transition:border-color .15s,transform .15s,box-shadow .15s;
}
.food-card{cursor:pointer}
.food-card:hover{border-color:var(--gold);transform:translateY(-2px);box-shadow:0 6px 16px rgba(0,0,0,.08)}
.food-card:focus-visible{outline:2px solid var(--gold);outline-offset:2px}

/* icon stands in for a dish photo (this menu has no per-item photography — see CLAUDE.md) */
.food-card-media{
  flex-shrink:0;
  width:56px;
  height:56px;
  border-radius:14px;
  background:var(--gold-soft);
  display:flex;
  align-items:center;
  justify-content:center;
}
.food-card-icon{font-size:26px;line-height:1}
.food-card-info{
  flex:1;
  min-width:0;
  display:flex;
  flex-direction:column;
  gap:2px;
}
.food-card-name{
  font-size:14.5px;
  font-weight:700;
  color:var(--text);
  line-height:1.3;
}
.food-card-cat{
  font-size:10.5px;
  color:var(--text-dim);
  text-transform:uppercase;
  letter-spacing:.04em;
}
.food-card-price{
  font-weight:700;
  font-size:14px;
  color:var(--gold);
  line-height:1.3;
  margin-top:2px;
}
/* per-card wishlist toggle, sitting right before the chevron — lets a dish be
   wishlisted straight from the list without opening the item-detail modal.
   e.stopPropagation() in js/app.js keeps its click from also opening that modal
   (the card itself is a role="button" with its own click handler). */
.food-card-wishlist{
  flex-shrink:0;
  display:flex;
  align-items:center;
  justify-content:center;
  width:26px;
  height:26px;
  border:none;
  border-radius:50%;
  background:none;
  color:var(--text-dim);
  cursor:pointer;
  transition:color .15s,background .15s;
}
.food-card-wishlist:hover{color:var(--gold);background:var(--gold-soft)}
.food-card-wishlist .wishlist-heart-icon path{transition:fill .15s}
.food-card-wishlist.is-active{color:var(--gold)}
.food-card-wishlist.is-active .wishlist-heart-icon path{fill:currentColor}

.food-card-chevron{
  flex-shrink:0;
  display:flex;
  align-items:center;
  justify-content:center;
  width:26px;
  height:26px;
  border-radius:50%;
  color:var(--gold);
  background:var(--gold-soft);
}

/* ---------- ITEM DETAIL MODAL ---------- */
.modal-backdrop{
  display:none;
  position:fixed;
  inset:0;
  background:rgba(0,0,0,.6);
  z-index:60;
}
.modal-backdrop.is-open{display:block}

.item-modal{
  position:fixed;
  left:50%;
  top:50%;
  transform:translate(-50%,-46%) scale(.97);
  width:min(420px, 90vw);
  max-height:85vh;
  overflow-y:auto;
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:16px;
  box-shadow:0 20px 60px rgba(0,0,0,.5);
  z-index:65;
  opacity:0;
  visibility:hidden;
  transition:opacity .2s ease, transform .2s ease;
}
.item-modal.is-open{
  opacity:1;
  visibility:visible;
  transform:translate(-50%,-50%) scale(1);
}
.modal-close{
  position:absolute;
  top:10px;
  right:10px;
  width:32px;
  height:32px;
  border:none;
  border-radius:50%;
  background:var(--panel);
  color:var(--text);
  font-size:20px;
  line-height:1;
  cursor:pointer;
  z-index:2;
}
.modal-close:hover{background:var(--gold);color:var(--gold-text)}
.modal-icon{
  font-size:64px;
  text-align:center;
  padding:36px 20px 8px;
  background:radial-gradient(circle at 50% 30%, var(--gold-soft), transparent 70%);
}
.modal-body{padding:8px 24px 24px}
.modal-top{
  display:flex;
  align-items:flex-start;
  justify-content:space-between;
  gap:12px;
  margin-bottom:4px;
}
.modal-title{margin:0;font-size:19px;font-weight:800;color:var(--text)}
.modal-price{font-size:19px;font-weight:800;color:var(--gold);white-space:nowrap;flex-shrink:0}
.modal-cat{
  margin:0 0 18px;
  font-size:11.5px;
  font-weight:600;
  text-transform:uppercase;
  letter-spacing:.05em;
  color:var(--text-dim);
}
.modal-wishlist{width:100%;justify-content:center;border:none;font-family:var(--font);font-size:12.5px;cursor:pointer}
/* heart icon fills solid once the item is already wishlisted — a visual toggle state
   layered on top of the shared .btn-call solid-gold pill look, same "is this on"
   convention as .bottom-nav-item.is-active/.branches-pill.is-active elsewhere */
.modal-wishlist .wishlist-heart-icon path{transition:fill .15s}
.modal-wishlist.is-active .wishlist-heart-icon path{fill:currentColor}

/* ---------- WISHLIST POPUP (opened from the header's #wishlist-btn, next to the search
   bar; shares #modal-backdrop and the same floating-panel look/motion as .item-modal
   above, since they're both small "here's some info" overlays, never open together) ---------- */
.wishlist-modal{
  position:fixed;
  left:50%;
  top:50%;
  transform:translate(-50%,-46%) scale(.97);
  width:min(420px, 90vw);
  max-height:80vh;
  overflow-y:auto;
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:16px;
  box-shadow:0 20px 60px rgba(0,0,0,.5);
  z-index:65;
  opacity:0;
  visibility:hidden;
  transition:opacity .2s ease, transform .2s ease;
}
.wishlist-modal.is-open{
  opacity:1;
  visibility:visible;
  transform:translate(-50%,-50%) scale(1);
}
.wishlist-modal-body{padding:44px 20px 24px}
.wishlist-modal-head{
  display:flex;
  align-items:center;
  justify-content:space-between;
  gap:10px;
  margin-bottom:14px;
}
.wishlist-modal-title{margin:0;font-size:19px;font-weight:800;color:var(--text)}
/* text-style action, not a pill — sits opposite the title rather than competing with the
   solid-gold CTA convention used elsewhere (.btn-call/.rating-bar/.branch-direction) */
.wishlist-clear-btn{
  flex-shrink:0;
  background:none;
  border:none;
  color:var(--gold);
  font-family:var(--font);
  font-size:12.5px;
  font-weight:600;
  cursor:pointer;
  padding:4px 2px;
}
.wishlist-clear-btn:hover{color:var(--gold-hover)}
.wishlist-list{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:10px}
/* mirrors .branch-item's card treatment — same background-on-background reasoning
   (this list sits directly on .wishlist-modal's own var(--panel-2), like .branch-item
   sits on .content's var(--panel)) */
.wishlist-item{
  display:flex;
  align-items:center;
  gap:12px;
  background:var(--panel);
  border:1px solid var(--border);
  border-radius:12px;
  padding:10px 12px;
}
.wishlist-item-icon{font-size:24px;flex-shrink:0}
.wishlist-item-info{flex:1;min-width:0;display:flex;flex-direction:column;gap:2px}
.wishlist-item-name{font-weight:700;font-size:14px;color:var(--text);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.wishlist-item-price{font-size:13px;color:var(--gold);font-weight:700}
.wishlist-item-remove{
  flex-shrink:0;
  width:30px;
  height:30px;
  border:none;
  border-radius:50%;
  background:var(--panel-2);
  color:var(--text-dim);
  font-size:16px;
  line-height:1;
  cursor:pointer;
}
.wishlist-item-remove:hover{background:var(--gold);color:var(--gold-text)}

/* ---------- BRANCHES PAGE (shown inline in .content-scroll, like search results —
   not a popup, see showBranchesPage() in js/app.js) ---------- */
.branches-list{
  list-style:none;
  margin:0;
  padding:0;
  display:flex;
  flex-direction:column;
  gap:10px;
}
.branches-list[hidden]{display:none}
/* each branch item mirrors the food item-detail popup's own title/price row:
   [ branch title .......... Direction (button) ]
   [ address, dim, like the modal's category tag ]
   background matches .food-card (var(--panel-2)) since this list now sits directly on
   the content area's own background (var(--panel)) rather than inside a modal panel */
.branch-item{
  background:var(--panel-2);
  border:1px solid var(--border);
  border-radius:14px;
  padding:14px 16px;
}
.branch-top{
  display:flex;
  align-items:center;
  justify-content:space-between;
  gap:12px;
}
.branch-name{
  margin:0;
  min-width:0;
  font-size:15px;
  font-weight:800;
  color:var(--text);
}
.branch-address{
  margin:6px 0 0;
  font-size:12px;
  color:var(--text-dim);
  line-height:1.4;
}
a.branch-direction,
a.branch-direction:link,
a.branch-direction:visited,
a.branch-direction:active{
  flex-shrink:0;
  display:inline-flex;
  align-items:center;
  gap:5px;
  background:var(--gold);
  color:var(--gold-text);
  font-family:var(--font);
  font-size:12px;
  font-weight:700;
  text-decoration:none;
  border:none;
  outline:none;
  white-space:nowrap;
  padding:7px 13px;
  border-radius:999px;
  cursor:pointer;
  transition:background .15s;
}
a.branch-direction:hover,
a.branch-direction:visited:hover{
  background:var(--gold-hover);
  color:var(--gold-text);
  text-decoration:none;
}

/* ---------- HOME PAGE (a neutral welcome panel — the photo carousel + restaurant
   name/tagline, no food items and no sidebar — shown only on the Home tab; distinct
   from Menu, which lands on category browsing. See showHomePage() in js/app.js.) ---------- */
.home-panel{
  display:flex;
  flex-direction:column;
  align-items:center;
  justify-content:center;
  text-align:center;
  gap:16px;
  /* fill the whole scroll area (rather than a fixed 70vh) so the carousel below can stretch
     into the leftover height instead of leaving empty bands above/below the content */
  min-height:100%;
  padding:20px 14px 24px;
}
/* same [hidden]-vs-unconditional-display gotcha as .card-grid/.subfilter/.branches-list above */
.home-panel[hidden]{display:none}
/* crossfade banner styling — see startCrossfadeCarousel() in js/app.js. Sized larger
   (up from an earlier 640px/2.4:1) and closer to the source photos' own 370:278 (~1.33:1)
   ratio, so it actually uses the available content width/height on desktop instead of
   sitting as a comparatively small letterboxed strip in the middle of a mostly-empty panel */
.home-carousel{
  position:relative;
  width:100%;
  /* grows to take whatever height is left in .home-panel (so the phone-width desktop column
     and tall phones have no dead space), bounded so it never gets absurdly tall or short */
  flex:1 1 220px;
  min-height:200px;
  max-height:480px;
  border-radius:16px;
  overflow:hidden;
  border:2px solid var(--gold);
  box-shadow:0 10px 26px rgba(0,0,0,.25);
}
.home-carousel-img{
  position:absolute;
  inset:0;
  width:100%;
  height:100%;
  object-fit:cover;
  opacity:0;
  transition:opacity 1s ease;
}
.home-carousel-img.is-active{opacity:1}
@media (prefers-reduced-motion: reduce){
  .home-carousel-img{transition:none}
}
.home-panel-title{margin:0;font-size:24px;font-weight:800;color:var(--text)}
/* decorative row between the welcome title and the carousel: waiter.gif on the left,
   menu.png (menu-book icon) on the right */
/* a single <button> wrapping both icons (waiter + menu) — tapping either goes to the Menu page
   (see #home-menu-btn in js/app.js). One button rather than two so it's one tab stop / one
   screen-reader action; button chrome reset below so it looks like the plain row it replaced. */
.home-panel-icons{
  display:flex;align-items:center;justify-content:center;gap:12px;
  background:var(--panel);
  border:none;padding:0;margin:0;font:inherit;color:inherit;
  cursor:pointer;
  -webkit-tap-highlight-color:transparent;
}
.home-panel-icons:focus-visible{outline:2px solid var(--gold);outline-offset:6px;border-radius:12px}
.home-panel-icon{display:block;flex-shrink:0;width:112px;height:112px;object-fit:contain}
/* waiter.gif has an opaque white background (no alpha), which shows as a white square on the
   cream panel — multiply makes the white drop out against any light panel color. It needs a
   real backdrop in the *same stacking context* to blend with: .content-scroll is its own
   (z-index:1, background-less) stacking context, so without the var(--panel) background on
   .home-panel-icons above, multiply had nothing to blend against and the white stayed white. */
.home-panel-icon[src$=".gif"]{mix-blend-mode:multiply}

/* attention-grabbing shake on the menu icon: a short wiggle, then a pause, repeating —
   a constant shake would be irritating, so ~0.9s of motion per 3s cycle. Bottom-center
   origin so it rocks like a bell/bookmark rather than spinning around its middle. */
.home-panel-icon--menu{
  transform-origin:50% 90%;
  animation:menu-shake 3s ease-in-out infinite;
}
@keyframes menu-shake{
  0%,35%,100%{transform:rotate(0deg)}
  4%{transform:rotate(-12deg)}
  8%{transform:rotate(12deg)}
  12%{transform:rotate(-10deg)}
  16%{transform:rotate(10deg)}
  20%{transform:rotate(-6deg)}
  24%{transform:rotate(6deg)}
  28%{transform:rotate(-3deg)}
  32%{transform:rotate(3deg)}
}
@media (prefers-reduced-motion: reduce){
  .home-panel-icon--menu{animation:none}
}

/* ---------- WELCOME POPUP (poster shown on every fresh page load, then fades out on its own —
   see initWelcomePopup() in js/app.js). z-index sits above the header (30), bottom nav (32)
   and the item/wishlist modals (60/65) so nothing pokes through it. ---------- */
.welcome-popup{
  position:fixed;
  inset:0;
  z-index:100;
  display:flex;
  align-items:center;
  justify-content:center;
  padding:16px;
  background:rgba(0,0,0,.75);
  opacity:1;
  transition:opacity .6s ease;
  animation:welcome-popup-in .35s ease;
}
/* same [hidden]-vs-unconditional-display gotcha as the other display:flex elements above */
.welcome-popup[hidden]{display:none}
.welcome-popup.is-leaving{opacity:0;pointer-events:none}
.welcome-popup-img{
  display:block;
  width:auto;
  height:auto;
  max-width:100%;
  max-height:calc(100vh - 32px);
  max-height:calc(100dvh - 32px);
  object-fit:contain;
  border-radius:14px;
  box-shadow:0 20px 60px rgba(0,0,0,.6);
  transform:scale(1);
  transition:transform .6s ease;
}
.welcome-popup.is-leaving .welcome-popup-img{transform:scale(.92)}
@keyframes welcome-popup-in{from{opacity:0}to{opacity:1}}
@media (prefers-reduced-motion: reduce){
  .welcome-popup,.welcome-popup-img{transition:none;animation:none}
}

/* ---------- ENQUIRY PAGE (shown inline in .content-scroll like the Branches page — see
   showEnquiryPage() in js/app.js). A fixed 75% / 25% vertical split of the scroll area: the
   poster on top (scaled down to fit whole), one row of two cards below (phone number | Follow us + socials). ---------- */
.enquiry-panel{
  display:flex;
  flex-direction:column;
  height:100%;
}
/* same [hidden]-vs-unconditional-display gotcha as .card-grid/.subfilter/.branches-list above */
.enquiry-panel[hidden]{display:none}
.enquiry-media{
  flex:1 1 75%;             /* shrinks (poster scales down) if the cards below need more than 25% */
  min-height:0;
  display:flex;
  align-items:center;
  justify-content:center;
  padding-bottom:8px;
}
.enquiry-img{
  display:block;
  width:auto;
  height:auto;
  max-width:100%;
  max-height:100%;
  object-fit:contain;
  border-radius:12px;
  border:2px solid var(--gold);
  box-shadow:0 8px 22px rgba(0,0,0,.2);
}
/* bottom 25%: ONE row split into two cards side by side — phone number on the left, "Follow us:" +
   social icons on the right. A grid (not flex) so the row is centered vertically in its 25% while
   both cards stretch to the same height; if one card is hidden the other takes the full row. */
.enquiry-actions{
  flex:0 0 25%;
  min-height:min-content;   /* never clip the cards on a short screen — the poster gives up height instead */
  display:grid;
  grid-auto-flow:column;
  grid-auto-columns:minmax(0,1fr);
  align-content:center;
  gap:8px;
}
.enquiry-call,
.enquiry-call:visited,
.enquiry-follow{
  display:flex;
  flex-direction:column;
  justify-content:center;
  align-items:center;       /* content centered horizontally inside each card */
  text-align:center;
  min-width:0;
  padding:10px 12px;
  border-radius:14px;
  box-shadow:0 2px 6px rgba(0,0,0,.05);
}
.enquiry-call[hidden],
.enquiry-follow[hidden]{display:none}
/* left card — the phone number. Solid gold: the primary action, per the site-wide CTA convention */
.enquiry-call,
.enquiry-call:visited{
  gap:6px;
  background:var(--gold);
  border:1px solid var(--gold);
  color:var(--gold-text);
  text-decoration:none;
  transition:background .15s,transform .1s;
}
.enquiry-call:hover{background:var(--gold-hover);border-color:var(--gold-hover);transform:translateY(-1px)}
.enquiry-call .enquiry-action-icon{background:rgba(255,255,255,.22);color:var(--gold-text)}
.enquiry-call-head{
  display:flex;
  align-items:center;
  justify-content:center;
  gap:8px;
}
.enquiry-call-label{font-size:12px;font-weight:600;opacity:.9}
.enquiry-call-number{font-size:16px;font-weight:800;letter-spacing:.2px;white-space:nowrap}
/* right card — "Follow us:" heading over a row of social icon buttons */
.enquiry-follow{
  gap:8px;
  background:var(--panel-2);
  border:1px solid var(--border);
}
.enquiry-follow-title{
  font-size:12px;
  font-weight:700;
  line-height:1.25;
  color:var(--text);
}
.enquiry-socials{
  display:flex;
  flex-wrap:wrap;
  justify-content:center;
  gap:6px;
}
.enquiry-socials .enquiry-action-icon{width:32px;height:32px}
/* icon-only (the platform name lives in each link's aria-label/title) */
.enquiry-action,
.enquiry-action:visited{
  display:flex;
  border-radius:50%;
  text-decoration:none;
  transition:transform .1s,background .15s;
}
.enquiry-action:hover{background:var(--gold);transform:translateY(-1px)}
.enquiry-action:hover .enquiry-action-icon{background:transparent;color:var(--gold-text)}
.enquiry-action[hidden]{display:none}
.enquiry-action-icon{
  display:flex;
  align-items:center;
  justify-content:center;
  width:30px;
  height:30px;
  border-radius:50%;
  background:var(--gold-soft);
  color:var(--gold);
  flex-shrink:0;
}

/* ---------- BOTTOM NAV (mobile only — Home / Menu / Branches / Call tabs, fixed to the
   viewport bottom like a native app's tab bar; desktop keeps the permanent sidebar +
   header actions instead, so this stays hidden there — see the max-width:860px block) ---------- */
.bottom-nav{
  display:none;
  position:fixed;
  /* confined to the phone-width column (matches .app-shell's max-width), centered — not
     left:0/right:0, which would stretch it across the whole viewport on desktop */
  left:50%;
  transform:translateX(-50%);
  width:100%;
  max-width:480px;
  bottom:0;
  min-height:var(--footer-h);
  z-index:32;
  align-items:stretch;
  justify-content:space-around;
  padding:6px 4px;
  padding-bottom:calc(6px + env(safe-area-inset-bottom, 0px));
  background:var(--chrome-bg);
  border-top:1px solid var(--border);
}
.bottom-nav-item{
  flex:1;
  display:flex;
  flex-direction:column;
  align-items:center;
  justify-content:center;
  gap:2px;
  min-width:0;
  margin:0 3px;
  font-family:var(--font);
  font-size:10.5px;
  font-weight:600;
  color:var(--chrome-text-dim);
  text-decoration:none;
  background:transparent;
  border:none;
  border-radius:12px;
  padding:6px 2px;
  cursor:pointer;
  transition:color .15s,background .15s;
}
.bottom-nav-item:hover{color:var(--chrome-text)}
/* the selected tab (category browsing lives behind Menu/Home) gets the same solid
   primary-color fill every other "selected" control on the site uses (sidebar-cat,
   subfilter-btn, lang-btn) instead of just a tinted label, so it reads as clearly
   "on" rather than a subtle color shift */
.bottom-nav-item.is-active{background:var(--gold);color:var(--gold-text)}
.bottom-nav-item svg{flex-shrink:0}

.rating-bar,
.rating-bar:visited{
  flex-shrink:0;
  display:flex;
  align-items:center;
  gap:6px;
  background:var(--gold);
  color:var(--gold-text);
  font-family:var(--font);
  font-size:12px;
  font-weight:600;
  text-decoration:none;
  padding:6px 14px;
  border-radius:999px;
  transition:background .15s;
}
.rating-bar:hover,
.rating-bar:visited:hover{background:var(--gold-hover)}
.rating-stars{color:var(--gold-text);font-size:13px;letter-spacing:1px}
.rating-bar-text-short{display:none}

/* ---------- LAYOUT RULES (formerly the `@media (max-width:860px)` "mobile" block) ----------
   These now apply at EVERY viewport width, on purpose: per explicit request the desktop view
   is a phone-width column (see .app-shell{max-width:480px}) with the exact same layout as
   mobile, instead of a separate wide 3-column desktop layout that left large empty gaps. The
   base rules above (wide sidebar, 18% sub-category column, header pills, etc.) are therefore
   dormant defaults that these rules always override; to bring back a real desktop layout,
   wrap this block in `@media (max-width:860px){...}` again and restore the removed
   `@media (min-width:861px){.subfilter{display:none}}` rule. */
/* header now holds brand + rating-bar on row 1 and the full-width search bar wrapped
   onto row 2 (.header-search's width:100% forces that regardless of available
   width) — bump --header-h to match that wrapped height as a safe pre-measurement
   fallback so the sticky-pane math (.sidebar/.content height) still lines up exactly
   before syncHeaderHeight() (js/app.js) tightens it precisely */
:root{--header-h:132px}

/* shorter, crisper label + tighter padding so it comfortably fits next to the brand */
.rating-bar{gap:3px;padding:4px 8px;font-size:11px}
.rating-stars{font-size:11px}
.rating-bar-text-full{display:none}
.rating-bar-text-short{display:inline}

/* trim the brand block too (smaller mark + tighter text) — between this and the
   rating-bar's own shrink above, brand + rating-bar reliably share row 1 down to
   narrow phones (~360px), not just larger ones (390px+) */
.brand{gap:6px}
.brand-mark{width:32px;height:32px}
.brand-mark svg{width:24px;height:24px}
.brand-name{font-size:13.5px}
.brand-tag{font-size:10px}

/* the 20/80 category-rail + content split stays PERMANENTLY visible at every width
   (no drawer/overlay any more) — on a phone that 20% column is only ~70-100px, so
   every dimension inside it (icon, label, settings row) shrinks to fit rather than
   the column growing to fit a desktop-sized card */
.sidebar{
  flex:0 0 25%;
  min-width:76px;
  max-width:130px;
  /* divider between the main-category rail and the sub-category pills / item list — same
     stronger-than-hairline tone the (now hidden) desktop #subsidebar used, with a plain
     --border fallback line first for browsers without color-mix() */
  border-right:1px solid var(--border);
  border-right:2px solid color-mix(in srgb, var(--text-dim) 50%, transparent);
}
.sidebar-inner{padding:8px 5px;gap:6px}
.sidebar-cat{padding:10px 4px;gap:5px;font-size:11.5px;font-weight:700;border-radius:12px}
.sidebar-icon-wrap{width:34px;height:34px;border-radius:10px}
.sidebar-cat .sidebar-icon{font-size:17px}
.sidebar-settings{flex-direction:column;padding:8px 4px;gap:6px}

/* the sub-category column is desktop-only — mobile has no room for a third pane
   alongside the icon rail, so it keeps the horizontal #subfilter pill row instead */
.subsidebar{display:none}

.content-sticky{padding:16px 10px 0}
.content-scroll{padding:0 10px 40px}
.content-head h2{font-size:19px}
.food-card{padding:10px 12px;gap:10px}
.food-card-media{width:46px;height:46px}
.food-card-icon{font-size:22px}

/* the bottom nav replaces desktop's sidebar-settings-adjacent footer entirely on mobile —
   --footer-h drives the sticky-pane math (.sidebar/.content height) so it must match
   this bar's real rendered height. 60px is a safe pre-JS fallback only (same pattern
   as --header-h's own media-query fallback) — syncFooterHeight() (js/app.js) tightens
   it to the bar's exact measured height immediately on load, which varies by device
   (most notably env(safe-area-inset-bottom), the home-indicator inset on notched
   phones, which this fixed value can't account for). */
:root{--footer-h:60px}
.bottom-nav{display:flex}
.branches-pill{display:none}
