/* Snughouse. Calm by default: lichen paper, ink text, one warm lamp colour reserved for "something is waiting". */

@font-face { font-family: "Atkinson Hyperlegible Next"; font-weight: 400; font-style: normal; font-display: swap;
  src: url("/fonts/atkinson-hyperlegible-next-latin-400-normal.woff2") format("woff2"); }
@font-face { font-family: "Atkinson Hyperlegible Next"; font-weight: 600; font-style: normal; font-display: swap;
  src: url("/fonts/atkinson-hyperlegible-next-latin-600-normal.woff2") format("woff2"); }
@font-face { font-family: "Atkinson Hyperlegible Next"; font-weight: 700; font-style: normal; font-display: swap;
  src: url("/fonts/atkinson-hyperlegible-next-latin-700-normal.woff2") format("woff2"); }

:root {
  --bg: #f6f3ee;
  --paper: #fffdf9;
  --ink: #1e2a4a;
  --ink-soft: #56607a;
  --rule: #e3ded5;
  --moss: #1e2a4a;
  --on-moss: #ffffff;
  --lamp: #f5a93b;
  --lamp-soft: #fdecd0;
  --danger: #a33a2f;
  --scrim: rgba(16, 22, 40, 0.86);
  --radius: 14px;
  --col: 600px;
  --gutter: 20px;
  --tabbar: 68px;
  color-scheme: light;

  /* Motion. Every timing and curve in one place (the phone app has the same in mobile/src/theme/motion.ts).
     Motion explains what just happened and never performs: it only answers something the person did.
     At most 300 ms, most 150 to 200 ms. Ease-out appearing, ease-in leaving. Only the like heart overshoots. */
  --motion-press: 100ms;     /* button shrinks while pressed */
  --motion-fade: 150ms;      /* colour changes, and the fade used when Reduce Motion is on */
  --motion-list: 200ms;      /* a new post or comment arriving, a deleted post leaving */
  --motion-open: 250ms;      /* dialogs sliding up, the photo viewer growing from its thumbnail */
  --motion-close: 200ms;     /* closing is a little quicker */
  --motion-pop: 250ms;       /* the like heart's one pop */
  --motion-progress: 300ms;  /* progress bars gliding to their next value */
  --ease-out: cubic-bezier(0.33, 1, 0.68, 1);
  --ease-in: cubic-bezier(0.32, 0, 0.67, 0);
  --ease-in-out: cubic-bezier(0.45, 0, 0.55, 1);
  --press-scale: 0.96;
  --like-pop-scale: 1.2;
  --new-item-offset: -12px;
}

@media (prefers-color-scheme: dark) {
  :root {
    --bg: #121829;
    --paper: #1a2238;
    --ink: #eef0f6;
    --ink-soft: #a8b0c4;
    --rule: #2b3550;
    --moss: #f5a93b;
    --on-moss: #1e2a4a;
    --lamp-soft: #3d3020;
    --danger: #f0877b;
    --scrim: rgba(0, 0, 0, 0.9);
    color-scheme: dark;
  }
}

* { box-sizing: border-box; }

html {
  font-size: 112.5%; /* 18px: easy to read for every generation in a family group */
  -webkit-text-size-adjust: 100%;
  background: var(--bg);
}

body {
  margin: 0;
  background: var(--bg);
  color: var(--ink);
  font-family: "Atkinson Hyperlegible Next", system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
  line-height: 1.5;
  min-height: 100vh;
  min-height: 100dvh;
  overflow-wrap: anywhere;
}

h1, h2, h3, p { margin: 0; }
h1 { font-size: 1.75rem; line-height: 1.15; font-weight: 700; letter-spacing: -0.012em; text-wrap: balance; }
h2 { font-size: 1.25rem; line-height: 1.25; font-weight: 700; text-wrap: balance; }
h3 { font-size: 1.05rem; line-height: 1.3; font-weight: 700; }
p { text-wrap: pretty; max-width: 60ch; }
a { color: var(--moss); text-underline-offset: 3px; }
.noscript { padding: 24px; }

:focus-visible { outline: 3px solid var(--moss); outline-offset: 2px; border-radius: 6px; }

.soft { color: var(--ink-soft); }
.small { font-size: 0.85rem; }
.strong { font-weight: 700; }
.visually-hidden { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; }

/* ---------- shell ---------- */

.shell { max-width: var(--col); margin: 0 auto; min-height: 100vh; min-height: 100dvh; display: flex; flex-direction: column; }
.page { flex: 1; padding: 28px var(--gutter) calc(var(--tabbar) + 48px + env(safe-area-inset-bottom)); }
.page.no-tabs { padding-bottom: 48px; }
.stack > * + * { margin-top: 20px; }
.stack-lg > * + * { margin-top: 32px; }
.stack-sm > * + * { margin-top: 10px; }
.row { display: flex; align-items: center; gap: 12px; }
.row-wrap { display: flex; flex-wrap: wrap; align-items: center; gap: 10px 12px; }
.spread { display: flex; align-items: center; justify-content: space-between; gap: 12px; }
.grow { flex: 1; min-width: 0; }

.tabbar {
  position: fixed; left: 0; right: 0; bottom: 0; z-index: 20;
  background: color-mix(in srgb, var(--paper) 94%, transparent);
  -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px);
  border-top: 1px solid var(--rule);
  padding-bottom: env(safe-area-inset-bottom);
}
.tabbar-inner { max-width: var(--col); margin: 0 auto; display: grid; grid-template-columns: repeat(3, 1fr); }
.tab {
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 2px;
  min-height: var(--tabbar); color: var(--ink-soft); text-decoration: none; font-size: 0.8rem; font-weight: 600;
  position: relative;
}
.tab svg { width: 26px; height: 26px; }
.tab[aria-current="page"] { color: var(--moss); }
.tab[aria-current="page"]::after {
  content: ""; position: absolute; top: 0; left: 28%; right: 28%; height: 3px; background: var(--moss); border-radius: 0 0 3px 3px;
}
.tab .dot { position: absolute; top: 12px; left: calc(50% + 9px); width: 11px; height: 11px; background: var(--lamp); border-radius: 50%; border: 2px solid var(--paper); }

/* ---------- controls ---------- */

.btn {
  appearance: none; border: 2px solid transparent; border-radius: 12px; min-height: 48px; padding: 10px 20px;
  font: inherit; font-weight: 700; cursor: pointer; text-decoration: none; display: inline-flex; align-items: center; justify-content: center; gap: 8px;
  background: var(--moss); color: var(--on-moss); text-align: center;
}
.btn:hover { filter: brightness(1.06); }
.btn:active { transform: scale(var(--press-scale)); }
/* Every button, icon and tab shrinks a little while pressed. */
.btn, .act, .tab, .sw, .swc, .media-cell, .rsvp button, .row-link, .choice, .snippet, .today-groupline, .back, .subnav a {
  transition: transform var(--motion-press) var(--ease-out);
}
.act:active, .tab:active, .sw:active, .swc:active, .rsvp button:active, .row-link:active, .choice:active,
.snippet:active, .today-groupline:active, .back:active, .subnav a:active { transform: scale(var(--press-scale)); }
.media-cell:active { transform: scale(0.98); }
.btn[disabled] { opacity: 0.55; cursor: default; transform: none; filter: none; }
.btn-line { background: transparent; color: var(--ink); border-color: var(--rule); }
.btn-line:hover { border-color: var(--ink-soft); filter: none; }
.btn-quiet { background: transparent; color: var(--moss); padding-left: 8px; padding-right: 8px; min-height: 44px; }
.btn-danger { background: transparent; color: var(--danger); border-color: var(--danger); }
.btn-danger-fill { background: var(--danger); color: #fff; }
.btn-small { min-height: 40px; padding: 6px 14px; font-size: 0.9rem; border-radius: 10px; }
.btn-block { display: flex; width: 100%; }
.btn svg { width: 20px; height: 20px; flex: none; }

.field { display: block; }
.field > label, .field > .label { display: block; font-weight: 700; margin-bottom: 6px; }
.field .hint { color: var(--ink-soft); font-size: 0.88rem; margin-top: 6px; }
input[type="text"], input[type="email"], input[type="password"], input[type="datetime-local"], input[type="search"], textarea, select {
  width: 100%; font: inherit; color: var(--ink); background: var(--paper);
  border: 1.5px solid var(--rule); border-radius: 12px; padding: 11px 14px; min-height: 48px;
}
textarea { resize: vertical; min-height: 96px; line-height: 1.45; }
input:focus, textarea:focus, select:focus { border-color: var(--moss); outline: 2px solid var(--moss); outline-offset: 1px; }
select { appearance: none; background-image: linear-gradient(45deg, transparent 50%, var(--ink-soft) 50%), linear-gradient(135deg, var(--ink-soft) 50%, transparent 50%);
  background-position: calc(100% - 20px) 52%, calc(100% - 14px) 52%; background-size: 6px 6px; background-repeat: no-repeat; padding-right: 38px; }
.check { display: flex; gap: 12px; align-items: flex-start; cursor: pointer; }
.check input { width: 24px; height: 24px; margin: 2px 0 0; accent-color: var(--moss); flex: none; }
.error { color: var(--danger); font-weight: 600; }
.form-error { background: color-mix(in srgb, var(--danger) 12%, var(--paper)); border-left: 4px solid var(--danger); padding: 10px 14px; border-radius: 8px; color: var(--ink); }

.choices { display: grid; gap: 10px; }
.choice { display: flex; gap: 12px; align-items: flex-start; padding: 14px; border: 1.5px solid var(--rule); border-radius: var(--radius); background: var(--paper); cursor: pointer; }
.choice:has(input:checked) { border-color: var(--moss); outline: 1px solid var(--moss); }
.choice input { width: 22px; height: 22px; margin: 2px 0 0; accent-color: var(--moss); flex: none; }
.choice .strong { display: block; }

.notice { background: var(--lamp-soft); border-left: 4px solid var(--lamp); padding: 14px 16px; border-radius: 8px; }
.notice > * + * { margin-top: 10px; }
.empty { padding: 36px 0; text-align: left; }
.empty > * + * { margin-top: 14px; }

/* ---------- group list and badges ---------- */

.rows { border-top: 1px solid var(--rule); }
.row-link { display: flex; align-items: center; gap: 14px; padding: 16px 0; border-bottom: 1px solid var(--rule); text-decoration: none; color: inherit; }
.row-link:hover .row-title { text-decoration: underline; text-underline-offset: 3px; }
.row-title { font-weight: 700; font-size: 1.08rem; line-height: 1.25; }
.badge {
  flex: none; width: 46px; height: 46px; border-radius: 50%; display: grid; place-items: center;
  color: #fff; font-weight: 700; font-size: 1.15rem;
}
.badge.sm { width: 34px; height: 34px; font-size: 0.95rem; }
/* a group's own picture sits over its letter badge */
.badge.has-img { position: relative; overflow: hidden; }
.badge.has-img img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; border-radius: 50%; }
.group-pic { display: flex; align-items: center; gap: 14px; }
.group-pic .badge { width: 64px; height: 64px; font-size: 1.5rem; }
.tone-0 { background: #1e2a4a; } .tone-1 { background: #2f5f86; } .tone-2 { background: #6b4a7a; }
.tone-3 { background: #a4561b; } .tone-4 { background: #4a5a66; } .tone-5 { background: #b5473a; }
.pill { flex: none; min-width: 26px; padding: 2px 9px; border-radius: 99px; background: var(--lamp); color: #1e2a4a; font-weight: 700; font-size: 0.85rem; text-align: center; }

/* ---------- group header, sub-navigation ---------- */

.back { display: inline-flex; align-items: center; gap: 4px; margin: -8px 0 8px -8px; padding: 8px; color: var(--moss); text-decoration: none; font-weight: 600; min-height: 44px; }
.back svg { width: 20px; height: 20px; }
.subnav { display: flex; gap: 4px; border-bottom: 1px solid var(--rule); margin: 18px calc(var(--gutter) * -1) 0; padding: 0 calc(var(--gutter) - 8px); overflow-x: auto; scrollbar-width: none; }
.subnav::-webkit-scrollbar { display: none; }
.subnav a { padding: 12px 12px 11px; color: var(--ink-soft); text-decoration: none; font-weight: 600; white-space: nowrap; border-bottom: 3px solid transparent; min-height: 48px; }
.subnav a[aria-current="page"] { color: var(--ink); border-bottom-color: var(--moss); }

/* ---------- composer ---------- */

.composer { border-bottom: 1px solid var(--rule); padding-bottom: 22px; }
.composer > * + * { margin-top: 12px; }
.previews { display: grid; grid-template-columns: repeat(auto-fill, minmax(84px, 1fr)); gap: 8px; }
.preview { position: relative; aspect-ratio: 1; border-radius: 10px; overflow: hidden; background: var(--rule); }
.preview img, .preview video { width: 100%; height: 100%; object-fit: cover; display: block; }
.preview button { position: absolute; top: 4px; right: 4px; width: 32px; height: 32px; border-radius: 50%; border: 0; background: var(--scrim); color: #fff; cursor: pointer; display: grid; place-items: center; }
.preview button svg { width: 16px; height: 16px; }
.preview .tag { position: absolute; left: 6px; bottom: 6px; background: var(--scrim); color: #fff; font-size: 0.75rem; padding: 1px 7px; border-radius: 99px; }
.progress { height: 8px; background: var(--rule); border-radius: 99px; overflow: hidden; }
.progress > span { display: block; height: 100%; width: calc(var(--p, 0) * 1%); background: var(--moss); transition: width var(--motion-progress) var(--ease-in-out); }
.file-input { position: absolute; width: 1px; height: 1px; opacity: 0; pointer-events: none; }

/* ---------- feed ---------- */

.day { margin-top: 30px; font-weight: 700; color: var(--ink-soft); font-size: 0.95rem; }
.post { padding: 18px 0 20px; border-bottom: 1px solid var(--rule); }
.post-head { display: flex; align-items: baseline; gap: 10px; flex-wrap: wrap; }
.post-author { font-weight: 700; }
.post-time { color: var(--ink-soft); font-size: 0.88rem; }
.new-dot { display: inline-block; width: 10px; height: 10px; border-radius: 50%; background: var(--lamp); margin-left: 2px; align-self: center; }
.post-body { margin-top: 6px; white-space: pre-wrap; max-width: 60ch; }
.media-grid { margin-top: 12px; display: grid; gap: 4px; border-radius: 12px; overflow: hidden; }
.media-grid.n1 { grid-template-columns: 1fr; }
.media-grid.n2, .media-grid.n4 { grid-template-columns: 1fr 1fr; }
.media-grid.n3, .media-grid.n5, .media-grid.n6, .media-grid.many { grid-template-columns: repeat(3, 1fr); }
.media-cell { position: relative; padding: 0; border: 0; background: var(--rule); cursor: pointer; display: block; aspect-ratio: 1; overflow: hidden; }
.media-grid.n1 .media-cell { aspect-ratio: var(--ratio, 4 / 3); max-height: 72vh; }
.media-cell img { width: 100%; height: 100%; object-fit: cover; display: block; }
.media-cell .play { position: absolute; inset: 0; display: grid; place-items: center; }
.media-cell .play span { width: 54px; height: 54px; border-radius: 50%; background: var(--scrim); color: #fff; display: grid; place-items: center; }
.media-cell .play svg { width: 26px; height: 26px; margin-left: 3px; }
.media-cell .dur { position: absolute; right: 8px; bottom: 8px; background: var(--scrim); color: #fff; font-size: 0.78rem; padding: 1px 8px; border-radius: 99px; }
.post-actions { display: flex; align-items: center; gap: 4px; margin: 10px 0 0 -10px; flex-wrap: wrap; }
.act { appearance: none; background: transparent; border: 0; color: var(--ink-soft); font: inherit; font-weight: 600; min-height: 44px; padding: 6px 10px; border-radius: 10px; display: inline-flex; align-items: center; gap: 7px; cursor: pointer; }
.act:hover { color: var(--ink); background: color-mix(in srgb, var(--ink) 6%, transparent); }
.act svg { width: 22px; height: 22px; }
.act[aria-pressed="true"] { color: var(--danger); }
.act[aria-pressed="true"] svg { fill: currentColor; }
.act.danger:hover { color: var(--danger); }
.comments { margin-top: 8px; padding-left: 14px; border-left: 3px solid var(--rule); }
.comments > * + * { margin-top: 12px; }
.comment-head { display: flex; align-items: baseline; gap: 8px; flex-wrap: wrap; }
.comment p { white-space: pre-wrap; }
.comment-form { display: flex; gap: 8px; align-items: flex-start; }
.comment-form input { flex: 1; min-width: 0; }
.more { margin-top: 24px; }

.caught-up { margin: 34px 0 10px; display: flex; gap: 16px; align-items: center; }
.caught-up .sunrise { flex: none; width: 52px; height: 52px; color: var(--ink-soft); }
.caught-up .sunrise .glow { fill: var(--lamp); opacity: 0.45; } /* shown lit: nothing animates on its own */
.caught-up .sunrise .sun { fill: var(--lamp); }
.caught-up .title { font-weight: 700; font-size: 1.1rem; }

/* ---------- events ---------- */

.events > * + * { border-top: 1px solid var(--rule); }
.event { display: grid; grid-template-columns: 58px 1fr; gap: 16px; padding: 20px 0; }
.date-block { text-align: center; line-height: 1.05; padding-top: 2px; }
.date-block .d { font-size: 1.9rem; font-weight: 700; display: block; }
.date-block .w, .date-block .m { font-size: 0.85rem; color: var(--ink-soft); font-weight: 600; display: block; }
.event-title { font-weight: 700; font-size: 1.1rem; line-height: 1.25; }
.event-meta { color: var(--ink-soft); margin-top: 2px; }
.event-notes { margin-top: 8px; white-space: pre-wrap; max-width: 56ch; }
.rsvp { display: flex; gap: 6px; flex-wrap: wrap; margin-top: 12px; }
.rsvp button { appearance: none; font: inherit; font-weight: 600; min-height: 44px; padding: 6px 14px; border-radius: 99px; border: 1.5px solid var(--rule); background: transparent; color: var(--ink); cursor: pointer; }
.rsvp button[aria-pressed="true"] { background: var(--moss); border-color: var(--moss); color: var(--on-moss); }

/* ---------- people, settings ---------- */

.members { border-top: 1px solid var(--rule); }
.member { display: flex; align-items: center; gap: 12px; padding: 12px 0; border-bottom: 1px solid var(--rule); flex-wrap: wrap; }
.member .who { flex: 1; min-width: 150px; }
.member select { width: auto; min-height: 40px; padding: 6px 34px 6px 12px; font-size: 0.9rem; }
.section > * + * { margin-top: 14px; }
.section-title { padding-top: 6px; }
.invite-link { display: flex; gap: 8px; }
.invite-link input { font-size: 0.9rem; }
.usage { width: 100%; height: 12px; border-radius: 99px; background: var(--rule); overflow: hidden; }
.usage > span { display: block; height: 100%; width: calc(var(--p, 0) * 1%); background: var(--moss); transition: width var(--motion-progress) var(--ease-in-out); }
.usage.high > span { background: var(--danger); }
.sep { border: 0; border-top: 1px solid var(--rule); margin: 8px 0; }

/* ---------- today ---------- */

.today-group { padding: 18px 0; border-bottom: 1px solid var(--rule); }
.today-group > * + * { margin-top: 10px; }
.snippet { display: flex; gap: 12px; align-items: center; }
.snippet img { width: 56px; height: 56px; border-radius: 8px; object-fit: cover; flex: none; background: var(--rule); }
.snippet .text { min-width: 0; }
.snippet .text span { display: block; overflow: hidden; text-overflow: ellipsis; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; }
.coming > * + * { margin-top: 14px; }
.coming a { text-decoration: none; color: inherit; display: block; padding: 4px 0; }
.coming a:hover .strong { text-decoration: underline; text-underline-offset: 3px; }

/* ---------- welcome / auth ---------- */

.welcome { padding-top: 0; }
/* Signed-out pages share the public homepage's navy top (home.css has the same values). Full width, so it
   runs edge to edge like the homepage; the page column is 600px, so the bar's contents line up with the form. */
body:has(.auth-head) { overflow-x: clip; }
.auth-head { width: 100vw; margin: -28px 0 0 calc(50% - 50vw); background: #1e2a4a; color: #fff3cf; }
.auth-top { display: flex; align-items: center; justify-content: space-between; gap: 16px; max-width: var(--col); margin: 0 auto; padding: 14px var(--gutter); }
.auth-brand { display: inline-flex; align-items: center; gap: 12px; color: #fff3cf; text-decoration: none; font-weight: 700; font-size: 1.25rem; letter-spacing: -0.01em; min-height: 44px; }
.auth-brand img { width: 40px; height: 40px; border-radius: 10px; display: block; }
.auth-link { color: #fff3cf; font-weight: 600; min-height: 44px; display: inline-flex; align-items: center; }
.auth-band { max-width: var(--col); margin: 0 auto; padding: 10px var(--gutter) 34px; }
.auth-band h1 { color: #fff; font-size: 2rem; line-height: 1.1; }
.auth-band h1::after { content: ""; display: block; width: 56px; height: 5px; border-radius: 3px; background: #e4624a; margin-top: 16px; }
.auth-band p { margin-top: 14px; color: #fff3cf; }
.auth-head :focus-visible { outline-color: #f5a93b; }
.welcome > .auth-head + * { margin-top: 28px; }
.brand { display: flex; align-items: center; gap: 12px; margin-bottom: 14px; }
.brand svg { width: 44px; height: 44px; }
.brand .name { font-size: 1.5rem; font-weight: 700; letter-spacing: -0.01em; }
.welcome h1 { max-width: 14ch; }
.invite-card { padding: 18px 0; border-top: 1px solid var(--rule); border-bottom: 1px solid var(--rule); }
.invite-card > * + * { margin-top: 6px; }

/* ---------- dialogs, lightbox, toast ---------- */

dialog { border: 0; padding: 0; background: var(--paper); color: var(--ink); border-radius: 18px; width: min(92vw, 440px); max-height: 88vh; overflow: auto; }
dialog::backdrop { background: var(--scrim); }
.dialog-body { padding: 24px; }
.dialog-body > * + * { margin-top: 16px; }
.dialog-actions { display: flex; gap: 10px; justify-content: flex-end; flex-wrap: wrap; }

dialog.lightbox { width: 100vw; max-width: 100vw; height: 100vh; height: 100dvh; max-height: none; border-radius: 0; background: #000; color: #fff; }
.lightbox-stage { position: absolute; inset: 0; display: grid; place-items: center; padding: 64px 0 76px; }
.lightbox-stage img, .lightbox-stage video { max-width: 100%; max-height: 100%; object-fit: contain; display: block; }
.lightbox-bar { position: absolute; left: 0; right: 0; display: flex; justify-content: space-between; align-items: center; padding: 10px 12px; gap: 8px; z-index: 2; }
.lightbox-bar.top { top: 0; padding-top: max(10px, env(safe-area-inset-top)); }
.lightbox-bar.bottom { bottom: 0; padding-bottom: max(12px, env(safe-area-inset-bottom)); }
.lightbox .btn { background: rgba(255, 255, 255, 0.16); color: #fff; }
.lightbox .btn:focus-visible { outline-color: #fff; }
.lightbox .loading { color: #c8d3ce; }

.toast { position: fixed; left: 50%; bottom: calc(var(--tabbar) + 22px + env(safe-area-inset-bottom)); transform: translateX(-50%); z-index: 60;
  background: var(--ink); color: var(--bg); padding: 12px 18px; border-radius: 12px; font-weight: 600; max-width: min(92vw, 440px); text-align: center; }
.toast.error { background: var(--danger); color: #fff; }

@media (prefers-reduced-motion: reduce) {
  /* No scale effects; slides and zooms become a short fade (see the motion section at the end). */
  :root { --press-scale: 1; --like-pop-scale: 1; --new-item-offset: 0px; }
  .media-cell:active { transform: none; }
  html { scroll-behavior: auto; }
}


/* ---------- small additions ---------- */
[hidden] { display: none !important; }
.brand img { width: 44px; height: 44px; border-radius: 10px; }
.feed > .caught-up:first-child { margin-top: 18px; }
.comment-head .btn-quiet { margin-left: auto; }
.member select { max-width: 11rem; }

[tabindex="-1"]:focus { outline: none; }
.snippet { color: var(--ink); text-decoration: none; }
.snippet:hover .text span { text-decoration: underline; text-underline-offset: 3px; }

/* ---------- group switcher ---------- */
.switcher {
  position: relative;
  background: color-mix(in srgb, var(--paper) 94%, transparent);
  -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px);
  border-bottom: 1px solid var(--rule);
  padding-top: env(safe-area-inset-top);
}
.switcher-inner {
  display: flex; gap: 4px; overflow-x: auto; -webkit-overflow-scrolling: touch; scrollbar-width: none;
  max-width: var(--col); margin: 0 auto; padding: 10px calc(var(--gutter) - 6px) 8px;
}
.switcher-inner::-webkit-scrollbar { display: none; }
.sw { flex: none; width: 72px; display: flex; flex-direction: column; align-items: center; gap: 5px; padding: 3px 0; border-radius: 12px; text-decoration: none; color: var(--ink-soft); }
.sw-icon { position: relative; display: block; }
.sw .badge { width: 50px; height: 50px; font-size: 1.2rem; transition: box-shadow 0.15s ease; }
.sw.active .badge { box-shadow: 0 0 0 3px var(--paper), 0 0 0 5.5px var(--moss); }
.sw-name { width: 100%; padding: 0 2px; text-align: center; overflow: hidden; display: -webkit-box; -webkit-box-orient: vertical; -webkit-line-clamp: 2; line-clamp: 2; font-size: 0.75rem; font-weight: 600; line-height: 1.2; overflow-wrap: anywhere; }
.sw.active .sw-name { color: var(--ink); font-weight: 700; }
.sw .pill { position: absolute; top: -5px; right: -7px; min-width: 22px; padding: 0 5px; font-size: 0.72rem; line-height: 1.45; border: 2px solid var(--paper); }
.sw .badge.add { background: transparent; color: var(--moss); border: 2px dashed var(--moss); }
.sw .badge.add svg { width: 22px; height: 22px; }

/* ---------- laptop and desktop ----------
   The phone layout is tuned for thumbs: big type, tall controls, tabs fixed to the bottom.
   On a laptop that wastes the screen and hides the bottom of long forms behind the tab bar,
   so from 700px wide the type is smaller, spacing is tighter and the tabs move to a top bar. */
@media (min-width: 700px) {
  html { font-size: 100%; }
  :root { --tabbar: 0px; --gutter: 24px; }
  .page { padding: 24px var(--gutter) 48px; }
  .stack > * + * { margin-top: 16px; }
  .stack-lg > * + * { margin-top: 24px; }

  .tabbar { position: sticky; top: 0; bottom: auto; left: auto; right: auto; order: -1; z-index: 25; border-top: 0; border-bottom: 1px solid var(--rule); padding-bottom: 0; }
  .tabbar-inner { grid-template-columns: repeat(3, auto); justify-content: start; gap: 2px; padding: 0 calc(var(--gutter) - 12px); }
  .tab { flex-direction: row; gap: 8px; min-height: 52px; padding: 0 14px; font-size: 0.95rem; }
  .tab svg { width: 22px; height: 22px; }
  .tab[aria-current="page"]::after { top: auto; bottom: 0; left: 10px; right: 10px; height: 3px; border-radius: 3px 3px 0 0; }
  .toast { bottom: 24px; }

  .btn { min-height: 44px; padding: 8px 18px; }
  .btn-small { min-height: 36px; padding: 4px 12px; }
  input[type="text"], input[type="email"], input[type="password"], input[type="datetime-local"], input[type="search"], textarea, select { min-height: 44px; padding: 9px 12px; }
  textarea { min-height: 84px; }
  .back { min-height: 36px; margin-bottom: 4px; }

  /* choice cards become one line: name, then its hint */
  .choices { gap: 8px; }
  .choice { padding: 10px 14px; align-items: center; }
  .choice .strong { display: inline; margin-right: 8px; }
  .row-link { padding: 12px 0; }
  .post { padding: 14px 0 16px; }
  .empty { padding: 24px 0; }
}

/* ---------- compact group bar (appears once the full row has scrolled away) ---------- */
.switcher-compact {
  position: fixed; top: 0; left: 0; right: 0; z-index: 14; padding-top: env(safe-area-inset-top, 0px);
  max-width: var(--col); margin: 0 auto;
  background: color-mix(in srgb, var(--paper) 96%, transparent);
  -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px);
  border-bottom: 1px solid var(--rule);
  transform: translateY(-120%); transition: transform 0.18s ease;
}
.switcher-compact.show { transform: none; }
.switcher-compact .switcher-inner { padding: 3px calc(var(--gutter) - 8px); gap: 0; align-items: center; }
.swc { position: relative; flex: none; display: block; padding: 5px; border-radius: 50%; text-decoration: none; }
.swc .badge { width: 34px; height: 34px; font-size: 0.95rem; }
.swc.active .badge { box-shadow: 0 0 0 2px var(--paper), 0 0 0 4px var(--moss); }
.swc .dot { position: absolute; top: 3px; right: 3px; width: 12px; height: 12px; border-radius: 50%; background: var(--lamp); border: 2px solid var(--paper); }
.swc .badge.add { background: transparent; color: var(--moss); border: 2px dashed var(--moss); }
.swc .badge.add svg { width: 16px; height: 16px; }

/* wide screens: the small icons sit just under the sticky tab bar (must come after the base rule above) */
@media (min-width: 700px) {
  .switcher-compact { top: 53px; }
}

/* Storage top-ups */
.addons { list-style: none; padding: 0; margin: 0; }
.addons li { display: flex; align-items: center; gap: 12px; padding: 10px 0; border-bottom: 1px solid var(--rule); }
.addons li:last-child { border-bottom: 0; }
.addons .grow > p { margin: 0; }
.composer .btn { white-space: nowrap; }

/* ---------- WhatsApp import ---------- */
.post-title { margin: 8px 0 0; font-size: 1.05rem; line-height: 1.3; }
.media-wrap > .btn { margin-top: 10px; }
.lightbox-caption { position: absolute; left: 0; right: 0; bottom: calc(64px + env(safe-area-inset-bottom)); z-index: 2; padding: 28px 16px 8px; max-height: 26vh; overflow: auto; background: linear-gradient(to top, rgba(0, 0, 0, 0.7), rgba(0, 0, 0, 0)); }
.lightbox-caption p { margin: 0 auto; max-width: 60ch; text-align: left; white-space: pre-wrap; }
.lightbox-caption .who { font-weight: 700; }
.lightbox-caption .said { margin-top: 2px; color: #e6ede9; }
.lightbox.captioned .lightbox-stage { padding-bottom: 150px; }
.steps { margin: 0; padding-left: 1.4em; }
.steps li + li { margin-top: 6px; }
.facts { margin: 0; padding-left: 1.2em; }
.facts li + li { margin-top: 4px; }
.order-choice { border: 0; padding: 0; margin: 0; min-width: 0; }
.order-choice legend { padding: 0; margin: 0 0 10px; font-weight: 700; }
.order-choice .check + .check { margin-top: 10px; }
.sub-h { margin: 18px 0 0; font-size: 1.05rem; }

/* Today timeline: each post says which group it is in */
.today-item > .post { padding-top: 6px; }
.today-groupline { display: inline-flex; align-items: center; gap: 8px; margin-top: 18px; color: var(--moss); font-weight: 600; font-size: 0.9rem; text-decoration: none; min-height: 32px; }
.today-groupline .badge.sm { width: 24px; height: 24px; font-size: 0.7rem; }
.today-groupline:hover span { text-decoration: underline; text-underline-offset: 3px; }

/* the cog on the You page */
.btn.icon-only { min-width: 48px; padding-left: 10px; padding-right: 10px; }
.btn.icon-only svg { width: 26px; height: 26px; }

/* ---------- motion ----------
   Timings and curves are the --motion-* and --ease-* values at the top. */

/* A post you just made slides in from the top; a comment you just sent fades in. */
@keyframes arrive { from { opacity: 0; transform: translateY(var(--new-item-offset)); } to { opacity: 1; transform: none; } }
.arrive { animation: arrive var(--motion-list) var(--ease-out); }
@keyframes appear { from { opacity: 0; } to { opacity: 1; } }
.appear { animation: appear var(--motion-list) var(--ease-out); }

/* A deleted post fades and the gap closes. Its height is set in script first, then this takes it to 0. */
.leaving {
  overflow: hidden; opacity: 0; height: 0 !important; padding-top: 0 !important; padding-bottom: 0 !important;
  margin-top: 0 !important; margin-bottom: 0 !important; border-bottom-width: 0 !important;
  transition: opacity var(--motion-list) var(--ease-in), height var(--motion-list) var(--ease-in),
    padding var(--motion-list) var(--ease-in), margin var(--motion-list) var(--ease-in);
}

/* The like heart: fills with one small pop when liked (the only overshoot), just fades when unliked. */
.act svg { transition: fill var(--motion-fade) var(--ease-out); }
@keyframes like-pop { 0% { transform: scale(1); } 50% { transform: scale(var(--like-pop-scale)); } 100% { transform: scale(1); } }
.act.popped svg { animation: like-pop var(--motion-pop) var(--ease-out); }

/* Dialogs slide up with the dim fading in, and close a little quicker. */
@keyframes sheet-in { from { opacity: 0; transform: translateY(48px); } to { opacity: 1; transform: none; } }
@keyframes sheet-out { from { opacity: 1; transform: none; } to { opacity: 0; transform: translateY(48px); } }
@keyframes dim-in { from { opacity: 0; } to { opacity: 1; } }
@keyframes dim-out { from { opacity: 1; } to { opacity: 0; } }
dialog[open]:not(.lightbox) { animation: sheet-in var(--motion-open) var(--ease-out); }
dialog[open]:not(.lightbox)::backdrop { animation: dim-in var(--motion-open) var(--ease-out); }
dialog.closing:not(.lightbox) { animation: sheet-out var(--motion-close) var(--ease-in) forwards; }
dialog.closing:not(.lightbox)::backdrop { animation: dim-out var(--motion-close) var(--ease-in) forwards; }

/* The photo viewer grows from the tapped thumbnail and shrinks back to it (positions set in script).
   Swiping down moves the photo with your finger and fades the black background. */
dialog.lightbox { background: transparent; }
.lightbox-bg { position: fixed; inset: 0; background: #000; opacity: 0; transition: opacity var(--motion-open) var(--ease-out); }
.lightbox.shown .lightbox-bg { opacity: 1; }
.lightbox.closing-anim .lightbox-bg { opacity: 0 !important; transition-duration: var(--motion-close); transition-timing-function: var(--ease-in); }
.lightbox-stage, .lightbox-bar, .lightbox-caption { opacity: 0; transition: opacity var(--motion-fade) var(--ease-out); }
.lightbox.ready .lightbox-stage, .lightbox.ready .lightbox-bar, .lightbox.ready .lightbox-caption { opacity: 1; }
.lightbox.closing-anim .lightbox-stage, .lightbox.closing-anim .lightbox-bar, .lightbox.closing-anim .lightbox-caption { opacity: 0; }
.lightbox.dragging .lightbox-stage, .lightbox.dragging .lightbox-bg { transition: none; }
.lightbox-stage { transition: opacity var(--motion-fade) var(--ease-out), transform var(--motion-close) var(--ease-out); }
.lightbox-bar { z-index: 4; }
.lightbox-ghost {
  position: fixed; z-index: 3; object-fit: cover; pointer-events: none;
  transition: left var(--motion-open) var(--ease-out), top var(--motion-open) var(--ease-out),
    width var(--motion-open) var(--ease-out), height var(--motion-open) var(--ease-out);
}
.lightbox-ghost.back {
  transition-duration: var(--motion-close); transition-timing-function: var(--ease-in);
}

@media (prefers-reduced-motion: reduce) {
  /* Slides become a short fade. */
  .arrive, .appear { animation: appear var(--motion-fade) var(--ease-out); }
  dialog[open]:not(.lightbox) { animation: appear var(--motion-fade) var(--ease-out); }
  dialog[open]:not(.lightbox)::backdrop { animation: dim-in var(--motion-fade) var(--ease-out); }
  dialog.closing:not(.lightbox) { animation: dim-out var(--motion-fade) var(--ease-in) forwards; }
  dialog.closing:not(.lightbox)::backdrop { animation: dim-out var(--motion-fade) var(--ease-in) forwards; }
  .leaving { transition: opacity var(--motion-fade) var(--ease-in); height: auto !important; }
  .act.popped svg { animation: none; }
  .lightbox-bg { transition-duration: var(--motion-fade); }
}

/* ---------- folding sections (Settings pages): click a heading to open it ---------- */
.fold { border-bottom: 1px solid var(--rule); }
.fold > summary {
  list-style: none; cursor: pointer; display: flex; align-items: center; justify-content: space-between; gap: 12px;
  min-height: 56px; padding: 6px 0;
}
.fold > summary::-webkit-details-marker { display: none; }
.fold > summary h2 { margin: 0; font-size: 1.15rem; }
.fold > summary svg { width: 22px; height: 22px; flex: none; color: var(--ink-soft); transition: transform var(--motion-fade) var(--ease-out); }
.fold[open] > summary svg { transform: rotate(180deg); }
.fold > summary:focus-visible { outline: 3px solid var(--moss); outline-offset: 2px; border-radius: 6px; }
.fold-body { padding: 0 0 22px; }
.fold-body > * > * + * { margin-top: 14px; }
.stack-lg > .fold + .fold { margin-top: 0; }

/* The group header: its name and the cog for managing groups */
.group-head { display: flex; align-items: center; justify-content: space-between; gap: 12px; }
.group-head h1 { font-size: 1.5rem; margin: 0; overflow-wrap: anywhere; }

/* Theme picker */
.swatches { display: flex; flex-wrap: wrap; gap: 10px; }
.swatch { display: flex; flex-direction: column; align-items: center; gap: 6px; width: 64px; cursor: pointer; font-size: 0.8rem; font-weight: 600; }
.swatch input { position: absolute; opacity: 0; pointer-events: none; }
.swatch .chip { width: 44px; height: 44px; border-radius: 50%; border: 1px solid var(--rule); display: grid; place-items: center; color: #fff; }
.swatch .chip.auto { background: linear-gradient(135deg, var(--paper) 50%, var(--bg) 50%); color: var(--ink); }
.swatch .chip svg { width: 22px; height: 22px; visibility: hidden; }
.swatch input:checked + .chip { box-shadow: 0 0 0 3px var(--paper), 0 0 0 5px var(--moss); }
.swatch input:checked + .chip svg { visibility: visible; }
.swatch input:focus-visible + .chip { outline: 3px solid var(--moss); outline-offset: 4px; }

/* A switch row: the title and hint on the left, the switch on the right */
.toggle { display: flex; align-items: center; gap: 14px; min-height: 48px; cursor: pointer; }
.toggle > span:first-child { flex: 1; }
.toggle > span:first-child > span { display: block; }
.toggle input { appearance: none; flex: none; width: 50px; height: 30px; border-radius: 99px; background: var(--rule); position: relative; cursor: pointer; transition: background var(--motion-fade) ease; margin: 0; }
.toggle input::after { content: ""; position: absolute; top: 3px; left: 3px; width: 24px; height: 24px; border-radius: 50%; background: #fff; box-shadow: 0 1px 3px rgba(0,0,0,0.3); transition: transform var(--motion-fade) var(--ease-out); }
.toggle input:checked { background: var(--moss); }
.toggle input:checked::after { transform: translateX(20px); }
.toggle input:focus-visible { outline: 3px solid var(--moss); outline-offset: 3px; }
.part-h { font-size: 0.8rem; text-transform: uppercase; letter-spacing: 0.06em; color: var(--ink-soft); margin: 18px 0 2px; }
.saved-note { color: var(--ink-soft); font-size: 0.9rem; }

/* ---------- coloured bars (Settings, Theme). White on the chosen colour. ---------- */
:root[data-bar] .tabbar, :root[data-bar] .switcher, :root[data-bar] .switcher-compact { background: var(--bar); border-color: transparent; }
:root[data-bar] .tab { color: rgba(255, 255, 255, 0.78); }
:root[data-bar] .tab[aria-current="page"] { color: #fff; }
:root[data-bar] .tab[aria-current="page"]::after { background: #fff; }
:root[data-bar] .tab .dot { border-color: var(--bar); }
:root[data-bar] .sw, :root[data-bar] .sw.active .sw-name { color: #fff; }
:root[data-bar] .sw .badge, :root[data-bar] .swc .badge { box-shadow: 0 0 0 1.5px rgba(255, 255, 255, 0.9); }
:root[data-bar] .sw.active .badge { box-shadow: 0 0 0 3px var(--bar), 0 0 0 5.5px #fff; }
:root[data-bar] .swc.active .badge { box-shadow: 0 0 0 2px var(--bar), 0 0 0 4px #fff; }
:root[data-bar] .sw .badge.add, :root[data-bar] .swc .badge.add { color: #fff; border-color: #fff; box-shadow: none; }
:root[data-bar] .sw .pill, :root[data-bar] .swc .dot { border-color: var(--bar); }
