/* ==========================================================================
   Eden Tools — design system
   Everything shared by every page lives here. Tool-specific styles go in
   src/tools/<slug>/tool.css and should reuse these tokens and components.
   Light theme is the default; dark is opt-in via the header button
   (html[data-theme="dark"]).
   ========================================================================== */

/* ---------- Fonts (self-hosted Sora) ---------- */
@font-face {
  font-family: "Sora";
  font-style: normal; font-display: swap; font-weight: 100 800;
  src: url(/assets/fonts/sora-latin-wght-normal.woff2) format("woff2-variations"), url(/assets/fonts/sora-latin-wght-normal.woff2) format("woff2");
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}
@font-face {
  font-family: "Sora";
  font-style: normal; font-display: swap; font-weight: 100 800;
  src: url(/assets/fonts/sora-latin-ext-wght-normal.woff2) format("woff2-variations"), url(/assets/fonts/sora-latin-ext-wght-normal.woff2) format("woff2");
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}

/* ---------- Tokens (light = default) ---------- */
:root {
  --font-sans: "Sora", ui-sans-serif, system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
  --font-display: var(--font-sans);
  --font-mono: ui-monospace, "Cascadia Mono", "SF Mono", Menlo, Consolas, monospace;

  --bg: #ffffff;
  --bg-soft: #f5f6fa;
  --surface: #ffffff;
  --surface-2: #f8f9fc;
  --surface-sunken: #f1f3f8;
  --text: #0c0f17;
  --text-soft: #4a5263;
  --text-faint: #6f7789;
  --border: #e6e8f0;
  --border-strong: #d2d6e1;

  --primary: #4f46e5;
  --primary-hover: #4338ca;
  --primary-press: #3730a3;
  --primary-soft: #eef0ff;
  --primary-softer: #f6f7ff;
  --on-primary: #ffffff;
  --accent: #ec4899;
  --accent-soft: #fdf0f7;
  --gradient: linear-gradient(100deg, #4f46e5 0%, #7c3aed 50%, #db2777 100%);

  --danger: #d92d20;
  --danger-soft: #fef1f0;
  --warning: #b54708;
  --warning-soft: #fff6e6;
  --info: #175cd3;
  --info-soft: #eff5ff;
  --success: #067647;
  --success-soft: #ecfdf3;
  --focus: #4f46e5;

  --shadow-sm: 0 1px 2px rgb(16 24 40 / .05);
  --shadow: 0 1px 2px rgb(16 24 40 / .04), 0 4px 16px -4px rgb(16 24 40 / .08);
  --shadow-lg: 0 2px 4px rgb(16 24 40 / .04), 0 20px 40px -12px rgb(16 24 40 / .18);
  --ring: 0 0 0 4px rgb(79 70 229 / .18);
  --checker-a: #eceef3;
  --checker-b: #ffffff;

  --radius-xs: 8px;
  --radius-sm: 10px;
  --radius: 14px;
  --radius-lg: 18px;
  --radius-xl: 24px;
  --ease: cubic-bezier(.2, .8, .2, 1);
  --ease-spring: cubic-bezier(.34, 1.4, .64, 1);
  --header-h: 64px;
  --container: 1180px;
  --gutter: 24px;                       /* page side padding (16px on phones) */
  --preview-max-h: min(68vh, 720px);    /* tallest a picture/video preview gets */
  --actionbar-h: 0px;                   /* height of the phone bottom action bar while it floats (set by site.js) */

  --tool-hue: 245;
  --tool-bg: hsl(var(--tool-hue) 95% 96%);
  --tool-fg: hsl(var(--tool-hue) 72% 46%);
  --tool-ring: hsl(var(--tool-hue) 85% 90%);

  color-scheme: light;
  font-size: 106.25%; /* 17px */
}

/* Tool colour tiles: recomputed wherever a --tool-hue is set inline. */
[style*="--tool-hue"] { --tool-bg: hsl(var(--tool-hue) 95% 96%); --tool-fg: hsl(var(--tool-hue) 72% 46%); --tool-ring: hsl(var(--tool-hue) 85% 90%); }

/* Optional dark theme (only when the visitor turns it on). */
:root[data-theme="dark"] {
  --bg: #0b0d12;
  --bg-soft: #11141b;
  --surface: #141821;
  --surface-2: #191e29;
  --surface-sunken: #0f1218;
  --text: #f1f3f8;
  --text-soft: #b3bbcb;
  --text-faint: #8a93a6;
  --border: #252b38;
  --border-strong: #353d4e;
  --primary: #818cf8;
  --primary-hover: #99a3fa;
  --primary-press: #6f7bf5;
  --primary-soft: #1f2340;
  --primary-softer: #171a2e;
  --on-primary: #0b0d12;
  --accent: #f472b6;
  --accent-soft: #34172a;
  --gradient: linear-gradient(100deg, #818cf8 0%, #a78bfa 50%, #f472b6 100%);
  --danger: #f97066;
  --danger-soft: #3a1714;
  --warning: #fdb022;
  --warning-soft: #36260a;
  --info: #84adff;
  --info-soft: #152238;
  --success: #47cd89;
  --success-soft: #0f2a1d;
  --focus: #99a3fa;
  --shadow-sm: 0 1px 2px rgb(0 0 0 / .4);
  --shadow: 0 1px 2px rgb(0 0 0 / .4), 0 8px 24px -8px rgb(0 0 0 / .6);
  --shadow-lg: 0 2px 6px rgb(0 0 0 / .4), 0 24px 48px -16px rgb(0 0 0 / .75);
  --ring: 0 0 0 4px rgb(129 140 248 / .28);
  --checker-a: #1d222d;
  --checker-b: #161a23;
  color-scheme: dark;
}
:root[data-theme="dark"] [style*="--tool-hue"] { --tool-bg: hsl(var(--tool-hue) 45% 16%); --tool-fg: hsl(var(--tool-hue) 90% 76%); --tool-ring: hsl(var(--tool-hue) 40% 24%); }

/* ---------- Base ---------- */
*, *::before, *::after { box-sizing: border-box; }
[hidden] { display: none !important; }
html { -webkit-text-size-adjust: 100%; text-size-adjust: 100%; scroll-padding-top: calc(var(--header-h) + 16px); }
body {
  margin: 0;
  min-height: 100vh;
  min-height: 100dvh;
  display: flex;
  flex-direction: column;
  background: var(--bg);
  color: var(--text);
  font-family: var(--font-sans);
  font-size: 1rem;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  overflow-x: hidden;
  overflow-y: visible; /* an explicit x-only value would otherwise force y to auto, breaking position:sticky */
  overflow-wrap: break-word;
}
body > main { flex: 1 0 auto; }
img, svg, video, canvas { max-width: 100%; }
img, video, canvas { height: auto; }
h1, h2, h3, h4 { line-height: 1.15; margin: 0 0 .5em; text-wrap: balance; font-weight: 700; letter-spacing: -.025em; }
h1 { font-size: clamp(1.9rem, 1.4rem + 2vw, 2.7rem); letter-spacing: -.035em; }
h2 { font-size: clamp(1.3rem, 1.15rem + .6vw, 1.65rem); }
h3 { font-size: 1.08rem; letter-spacing: -.015em; font-weight: 650; }
p { margin: 0 0 1em; }
a { color: var(--primary); text-underline-offset: .2em; text-decoration-thickness: 1.5px; }
a:hover { color: var(--primary-hover); }
strong, b { font-weight: 650; }
small, .small { font-size: .875rem; }
hr { border: 0; border-top: 1px solid var(--border); margin: 1.5rem 0; }
kbd {
  font-family: var(--font-mono); font-size: .78em; padding: .1em .45em; border-radius: 6px;
  border: 1px solid var(--border-strong); border-bottom-width: 2px; background: var(--surface); color: var(--text-soft);
}
code { font-family: var(--font-mono); font-size: .88em; background: var(--bg-soft); padding: .1em .35em; border-radius: 6px; }
::selection { background: color-mix(in srgb, var(--primary) 22%, transparent); }
:focus-visible { outline: 2.5px solid var(--focus); outline-offset: 2px; border-radius: 6px; }
input, select, textarea, button { font: inherit; color: inherit; }
input[type="checkbox"], input[type="radio"] { accent-color: var(--primary); width: 1.15em; height: 1.15em; margin: 0; flex: none; }

.icon { width: 1.25em; height: 1.25em; flex: none; vertical-align: -.25em; }
.icon-sm { width: 1em; height: 1em; }
.icon-xs { width: .85em; height: .85em; vertical-align: -.1em; }
.icon-lg { width: 1.6em; height: 1.6em; }

.container { width: 100%; max-width: var(--container); margin-inline: auto; padding-inline: max(var(--gutter), env(safe-area-inset-left)) max(var(--gutter), env(safe-area-inset-right)); }

.sr-only { position: absolute !important; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0; }
.skip-link { position: absolute; left: 12px; top: -60px; z-index: 100; background: var(--primary); color: var(--on-primary); padding: .6rem 1rem; border-radius: var(--radius-sm); font-weight: 650; transition: top .2s; }
.skip-link:focus { top: 12px; color: var(--on-primary); }

/* Small layout helpers */
.stack { display: flex; flex-direction: column; gap: 1rem; }
.stack-sm { display: flex; flex-direction: column; gap: .5rem; }
.stack-lg { display: flex; flex-direction: column; gap: 1.5rem; }
.row { display: flex; flex-wrap: wrap; align-items: center; gap: .75rem; }
.row-sm { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; }
.row-between { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: .75rem; }
.grow { flex: 1 1 auto; min-width: 0; }
.muted { color: var(--text-soft); }
.faint { color: var(--text-faint); }
.center { text-align: center; }
.nowrap { white-space: nowrap; }
.mono { font-family: var(--font-mono); }
/* Grids collapse to one column when their container is too narrow for two readable fields
   (so a "Same as original" select never gets cut off in a side panel). .grid-keep = always side by side. */
.grid-2 { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 11rem), 1fr)); gap: .75rem; }
.grid-3 { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 8rem), 1fr)); gap: .75rem; }
.grid-2.grid-keep { grid-template-columns: repeat(2, minmax(0, 1fr)); }
.grid-3.grid-keep { grid-template-columns: repeat(3, minmax(0, 1fr)); }

/* ---------- Header ---------- */
.site-header {
  position: sticky; top: 0; z-index: 50;
  background: color-mix(in srgb, var(--bg) 88%, transparent);
  -webkit-backdrop-filter: saturate(1.8) blur(16px);
  backdrop-filter: saturate(1.8) blur(16px);
  border-bottom: 1px solid transparent;
  padding-top: env(safe-area-inset-top);
  transition: border-color .2s, box-shadow .2s;
}
.site-header.is-scrolled { border-bottom-color: var(--border); }
.header-inner { display: flex; align-items: center; justify-content: space-between; gap: .75rem; min-height: var(--header-h); }
.brand { display: inline-flex; align-items: center; gap: .55rem; min-height: 44px; text-decoration: none; color: var(--text); flex: none; -webkit-tap-highlight-color: transparent; }
.brand:hover { color: var(--text); }
.brand-mark { width: 34px; height: 34px; transition: transform .45s var(--ease-spring); }
@media (hover: hover) { .brand:hover .brand-mark { transform: rotate(-8deg) scale(1.06); } }
.brand-name { font-weight: 700; font-size: 1.12rem; letter-spacing: -.035em; }
.brand-name span { color: var(--text-faint); font-weight: 500; }
.brand-sm .brand-mark { width: 26px; height: 26px; }
.brand-sm .brand-name { font-size: .98rem; }
.header-actions { display: flex; align-items: center; gap: .25rem; }
.icon-theme-dark { display: none; }
:root[data-theme="dark"] .icon-theme-light { display: none; }
:root[data-theme="dark"] .icon-theme-dark { display: inline; }

/* Tools menu */
.menu { position: relative; }
.menu-chevron { transition: transform .25s var(--ease); }
.menu-button[aria-expanded="true"] .menu-chevron { transform: rotate(180deg); }
.menu-button[aria-expanded="true"] { --btn-bg: var(--bg-soft); }
.menu-panel {
  position: absolute; right: 0; top: calc(100% + 8px);
  width: min(640px, calc(100vw - 32px));
  max-height: calc(100vh - var(--header-h) - 24px); max-height: calc(100dvh - var(--header-h) - 24px); overflow-y: auto;
  background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-lg);
  box-shadow: var(--shadow-lg); padding: .75rem;
  transform-origin: top right;
  animation: menu-in .2s var(--ease) both;
}
@keyframes menu-in { from { opacity: 0; transform: translateY(-6px) scale(.98); } }
.menu-backdrop { display: none; }
.menu-grid { columns: 2; column-gap: .75rem; }
.menu-group { padding: .25rem; break-inside: avoid; }
.menu-group-title { font-size: .72rem; font-weight: 650; letter-spacing: .08em; text-transform: uppercase; color: var(--text-faint); margin: .35rem .5rem .35rem; }
.menu-group ul { list-style: none; margin: 0; padding: 0; }
.menu-group a { display: flex; align-items: center; gap: .65rem; min-height: 44px; padding: .4rem .5rem; border-radius: var(--radius-sm); color: var(--text); text-decoration: none; font-weight: 550; font-size: .95rem; line-height: 1.25; -webkit-tap-highlight-color: transparent; }
.menu-group a:focus-visible, .menu-group a:active { background: var(--bg-soft); }
@media (hover: hover) { .menu-group a:hover { background: var(--bg-soft); } }
.menu-group a[aria-current="page"] { background: var(--primary-softer); color: var(--primary); }
/* Phones: a full-width sheet under the header that scrolls by itself; the page behind is locked and dimmed. */
@media (max-width: 640px) {
  .menu { position: static; }
  .menu-panel {
    position: fixed; left: 0; right: 0; top: calc(var(--header-h) + env(safe-area-inset-top)); width: auto;
    max-height: calc(100vh - var(--header-h) - env(safe-area-inset-top) - 32px);
    max-height: calc(100dvh - var(--header-h) - env(safe-area-inset-top) - 32px);
    overscroll-behavior: contain; -webkit-overflow-scrolling: touch;
    border-width: 1px 0; border-radius: 0 0 var(--radius-xl) var(--radius-xl);
    padding: .35rem max(10px, env(safe-area-inset-right)) calc(.75rem + env(safe-area-inset-bottom)) max(10px, env(safe-area-inset-left));
    transform-origin: top center; animation: sheet-down .24s var(--ease) both;
  }
  .menu-backdrop:not([hidden]) {
    display: block; position: fixed; left: 0; right: 0; bottom: 0; top: calc(var(--header-h) + env(safe-area-inset-top)); z-index: -1;
    background: rgb(12 15 23 / .42); animation: fade .2s both;
  }
  .menu-grid { columns: 1; }
  .menu-group { padding: .15rem 0; }
  .menu-group-title { margin: .6rem .6rem .25rem; }
  .menu-group a { min-height: 52px; padding: .45rem .6rem; font-size: 1rem; gap: .8rem; }
  .menu-group .tool-icon-sm { width: 36px; height: 36px; border-radius: 10px; }
  .menu-group .tool-icon-sm .icon { width: 19px; height: 19px; }
  :root.menu-open, :root.menu-open body { overflow: hidden; }
}
@keyframes sheet-down { from { opacity: 0; transform: translateY(-12px); } }

/* ---------- Buttons ---------- */
.btn {
  --btn-bg: var(--surface);
  --btn-fg: var(--text);
  --btn-border: var(--border-strong);
  display: inline-flex; align-items: center; justify-content: center; gap: .5em;
  min-height: 46px; padding: .55em 1.1em;
  border-radius: var(--radius-sm); border: 1px solid var(--btn-border);
  background: var(--btn-bg); color: var(--btn-fg);
  font-weight: 600; font-size: .95rem; line-height: 1.15; letter-spacing: -.01em; text-decoration: none; text-align: center;
  cursor: pointer; user-select: none; -webkit-tap-highlight-color: transparent;
  box-shadow: var(--shadow-sm);
  transition: transform .14s var(--ease), background-color .16s, border-color .16s, box-shadow .16s, color .16s;
}
.btn:active:not([disabled]) { transform: scale(.97); }
.btn[disabled], .btn[aria-disabled="true"] { opacity: .5; cursor: not-allowed; }
.btn-primary {
  --btn-bg: var(--primary); --btn-fg: var(--on-primary); --btn-border: var(--primary);
  box-shadow: 0 1px 2px rgb(16 24 40 / .12), inset 0 1px 0 rgb(255 255 255 / .16), 0 6px 16px -6px color-mix(in srgb, var(--primary) 70%, transparent);
}
.btn-soft { --btn-bg: var(--primary-soft); --btn-fg: var(--primary); --btn-border: transparent; box-shadow: none; }
.btn-ghost { --btn-bg: transparent; --btn-border: transparent; box-shadow: none; }
.btn-danger { --btn-fg: var(--danger); }
/* Hover looks only for real pointers (a tapped button on a phone must not stay "hovered"). */
@media (hover: hover) {
  .btn:hover { --btn-bg: var(--surface-2); --btn-border: var(--text-faint); color: var(--btn-fg); }
  .btn-primary:hover { --btn-bg: var(--primary-hover); --btn-border: var(--primary-hover); --btn-fg: var(--on-primary); box-shadow: 0 1px 2px rgb(16 24 40 / .12), inset 0 1px 0 rgb(255 255 255 / .16), 0 10px 22px -8px color-mix(in srgb, var(--primary) 80%, transparent); }
  .btn-soft:hover { --btn-bg: color-mix(in srgb, var(--primary-soft) 80%, var(--primary) 12%); --btn-border: transparent; --btn-fg: var(--primary); }
  .btn-ghost:hover { --btn-bg: var(--bg-soft); --btn-border: transparent; }
  .btn-danger:hover { --btn-bg: var(--danger-soft); --btn-border: var(--danger); --btn-fg: var(--danger); }
}
.btn-ghost:active:not([disabled]) { --btn-bg: var(--bg-soft); }
.btn-lg { min-height: 54px; padding: .7em 1.4em; font-size: 1.02rem; border-radius: var(--radius); }
.btn-xl { min-height: 60px; padding: .8em 1.7em; font-size: 1.08rem; border-radius: var(--radius); }
.btn-sm { min-height: 36px; padding: .35em .8em; font-size: .85rem; }
.btn-icon { width: 46px; padding: 0; }
.btn-icon.btn-sm { width: 36px; }
.btn-block { display: flex; width: 100%; }
.btn[aria-pressed="true"] { --btn-bg: var(--primary-soft); --btn-border: var(--primary); --btn-fg: var(--primary); }
.btn .spinner { width: 1.1em; height: 1.1em; }
.btn-group { display: inline-flex; flex-wrap: wrap; gap: .5rem; }
.btn-link { background: none; border: 0; padding: 0; color: var(--primary); font-weight: 600; cursor: pointer; text-decoration: underline; text-underline-offset: .2em; }

/* ---------- Form controls ---------- */
.field { display: flex; flex-direction: column; gap: .35rem; min-width: 0; }
.field > label, .label { font-weight: 600; font-size: .9rem; color: var(--text); }
.field .hint, .hint { font-size: .82rem; color: var(--text-faint); margin: 0; line-height: 1.45; }
.input, .select, .textarea,
.field input:not([type="checkbox"]):not([type="radio"]):not([type="range"]):not([type="color"]):not([type="file"]),
.field select, .field textarea {
  width: 100%; min-height: 46px; padding: .55rem .8rem;
  background: var(--surface); color: var(--text);
  border: 1px solid var(--border-strong); border-radius: var(--radius-sm);
  font-size: 1rem; box-shadow: var(--shadow-sm); transition: border-color .15s, box-shadow .15s;
}
.textarea, .field textarea { min-height: 110px; resize: vertical; line-height: 1.5; }
.select, .field select {
  appearance: none; -webkit-appearance: none; padding-right: 2.4rem; cursor: pointer;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='24' height='24' viewBox='0 0 24 24' fill='none' stroke='%236f7789' stroke-width='2.2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E");
  background-repeat: no-repeat; background-position: right .7rem center; background-size: 1.05rem;
}
.input:hover, .select:hover, .textarea:hover, .field input:hover, .field select:hover, .field textarea:hover { border-color: var(--text-faint); }
.input:focus, .select:focus, .textarea:focus, .field input:focus, .field select:focus, .field textarea:focus {
  outline: none; border-color: var(--primary); box-shadow: var(--ring);
}
.input-group { display: flex; align-items: stretch; }
.input-group > .input, .input-group > input { border-top-right-radius: 0; border-bottom-right-radius: 0; }
.input-addon { display: inline-flex; align-items: center; padding: 0 .8rem; border: 1px solid var(--border-strong); border-left: 0; border-radius: 0 var(--radius-sm) var(--radius-sm) 0; background: var(--bg-soft); color: var(--text-soft); font-weight: 550; font-size: .9rem; }
input[type="number"] { font-variant-numeric: tabular-nums; }

.check { display: flex; align-items: center; gap: .6rem; min-height: 40px; cursor: pointer; font-weight: 500; }
.check input { cursor: pointer; }

.switch { display: flex; align-items: center; gap: .75rem; min-height: 44px; cursor: pointer; font-weight: 550; }
.switch input { position: absolute; opacity: 0; width: 1px; height: 1px; }
.switch-track { position: relative; flex: none; width: 46px; height: 28px; border-radius: 99px; background: var(--border-strong); transition: background-color .2s; }
.switch-track::after { content: ""; position: absolute; top: 3px; left: 3px; width: 22px; height: 22px; border-radius: 50%; background: #fff; box-shadow: 0 1px 3px rgb(16 24 40 / .3); transition: transform .25s var(--ease-spring); }
.switch input:checked + .switch-track { background: var(--primary); }
.switch input:checked + .switch-track::after { transform: translateX(18px); }
.switch input:focus-visible + .switch-track { outline: 2.5px solid var(--focus); outline-offset: 2px; }

/* Segmented control (styled radio group) */
/* Options share the width equally; when they can't fit (narrow panel, phone) they wrap onto a second row
   instead of squashing or spilling out. */
.seg { display: flex; flex-wrap: wrap; gap: 3px; padding: 3px; background: var(--surface-sunken); border: 1px solid var(--border); border-radius: var(--radius); max-width: 100%; }
.seg label { flex: 1 1 0; position: relative; min-width: min-content; max-width: 100%; cursor: pointer; -webkit-tap-highlight-color: transparent; }
.seg input { position: absolute; opacity: 0; inset: 0; width: 100%; height: 100%; margin: 0; cursor: pointer; }
.seg span { display: flex; align-items: center; justify-content: center; gap: .4em; min-height: 40px; padding: .35rem .6rem; border-radius: calc(var(--radius) - 4px); font-weight: 600; font-size: .88rem; color: var(--text-soft); text-align: center; line-height: 1.15; transition: background-color .18s, color .18s, box-shadow .18s; }
@media (hover: hover) { .seg label:hover span { color: var(--text); } }
.seg input:checked + span { background: var(--surface); color: var(--text); box-shadow: 0 1px 3px rgb(16 24 40 / .1), 0 0 0 1px var(--border); }
.seg input:focus-visible + span { outline: 2.5px solid var(--focus); outline-offset: 1px; }
.seg-wrap { flex-wrap: wrap; }
.seg-wrap label { flex: 1 1 30%; }

/* Range slider with live value */
.range { display: flex; flex-direction: column; gap: .15rem; }
.range-head { display: flex; justify-content: space-between; align-items: baseline; gap: .5rem; }
.range-head label { font-weight: 600; font-size: .9rem; }
.range-value { font-variant-numeric: tabular-nums; font-weight: 650; color: var(--primary); font-size: .88rem; min-width: 3ch; text-align: right; }
input[type="range"] { -webkit-appearance: none; appearance: none; width: 100%; height: 30px; background: transparent; cursor: pointer; margin: 0; --fill: 50%; }
input[type="range"]::-webkit-slider-runnable-track { height: 6px; border-radius: 99px; background: linear-gradient(to right, var(--primary) var(--fill), var(--border-strong) var(--fill)); }
input[type="range"]::-moz-range-track { height: 6px; border-radius: 99px; background: var(--border-strong); }
input[type="range"]::-moz-range-progress { height: 6px; border-radius: 99px; background: var(--primary); }
input[type="range"]::-webkit-slider-thumb { -webkit-appearance: none; width: 22px; height: 22px; margin-top: -8px; border-radius: 50%; background: #fff; border: 2px solid var(--primary); box-shadow: 0 2px 6px rgb(16 24 40 / .2); transition: transform .15s var(--ease-spring); }
input[type="range"]::-moz-range-thumb { width: 18px; height: 18px; border-radius: 50%; background: #fff; border: 2px solid var(--primary); box-shadow: 0 2px 6px rgb(16 24 40 / .2); }
input[type="range"]:active::-webkit-slider-thumb { transform: scale(1.15); }
input[type="range"]:focus-visible { outline: none; }
input[type="range"]:focus-visible::-webkit-slider-thumb { box-shadow: var(--ring); }
input[type="range"]:focus-visible::-moz-range-thumb { box-shadow: var(--ring); }

/* Colour input + swatches */
input[type="color"] { -webkit-appearance: none; appearance: none; width: 46px; height: 46px; padding: 4px; border: 1px solid var(--border-strong); border-radius: var(--radius-sm); background: var(--surface); cursor: pointer; }
input[type="color"]::-webkit-color-swatch-wrapper { padding: 0; }
input[type="color"]::-webkit-color-swatch { border: 0; border-radius: 6px; }
input[type="color"]::-moz-color-swatch { border: 0; border-radius: 6px; }
.swatches { display: flex; flex-wrap: wrap; gap: .4rem; }
.swatch { width: 34px; height: 34px; border-radius: 50%; border: 2px solid var(--surface); box-shadow: 0 0 0 1px var(--border-strong); cursor: pointer; padding: 0; transition: transform .15s var(--ease-spring); }
@media (hover: hover) { .swatch:hover { transform: scale(1.1); } }
/* Bigger touch targets for fingers (layout on desktop stays the same). */
@media (pointer: coarse) {
  input[type="range"] { height: 40px; }
  .check { min-height: 44px; }
  .swatch { width: 40px; height: 40px; }
}
.swatch[aria-pressed="true"] { box-shadow: 0 0 0 2.5px var(--primary); }

/* "More options" disclosure */
details.more { border-top: 1px solid var(--border); }
details.more > summary {
  list-style: none; display: flex; align-items: center; justify-content: space-between; gap: .5rem;
  min-height: 50px; cursor: pointer; font-weight: 600; color: var(--text); user-select: none;
}
details.more > summary::-webkit-details-marker { display: none; }
details.more > summary::after {
  content: ""; width: 1.05rem; height: 1.05rem; flex: none; background: currentColor; opacity: .55;
  -webkit-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2.4' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E") center/contain no-repeat;
  mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2.4' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E") center/contain no-repeat;
  transition: transform .25s var(--ease);
}
details.more[open] > summary::after { transform: rotate(180deg); }
@media (hover: hover) { details.more > summary:hover { color: var(--primary); } }
details.more > summary { -webkit-tap-highlight-color: transparent; }
details.more > .more-body { padding-bottom: 1rem; display: flex; flex-direction: column; gap: 1rem; animation: rise .3s var(--ease) both; }

/* ---------- Surfaces ---------- */
.panel { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-lg); box-shadow: var(--shadow); padding: 1.25rem; }
.panel-flat { box-shadow: none; }
.panel-title { font-size: 1.02rem; font-weight: 650; letter-spacing: -.015em; margin: 0 0 .9rem; }
.panel-section + .panel-section { border-top: 1px solid var(--border); padding-top: 1rem; margin-top: 1rem; }
.card { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1rem; }

.step { display: flex; align-items: center; gap: .6rem; font-size: 1.02rem; font-weight: 650; letter-spacing: -.015em; margin: 0 0 .8rem; }
.step-num { display: inline-grid; place-items: center; width: 1.65rem; height: 1.65rem; flex: none; border-radius: 50%; background: var(--primary); color: var(--on-primary); font-size: .82rem; font-weight: 700; letter-spacing: 0; }

/* ---------- Tool page frame ---------- */
.tool-hero { padding: 1.75rem 0 1.25rem; position: relative; isolation: isolate; }
.tool-hero::before {
  content: ""; position: absolute; inset: -64px 0 -40px; z-index: -1; pointer-events: none;
  background:
    radial-gradient(45% 80% at 10% 20%, color-mix(in srgb, var(--tool-bg) 100%, transparent), transparent 70%);
}
.crumbs { display: flex; align-items: center; flex-wrap: wrap; gap: .35rem; font-size: .85rem; margin-bottom: .9rem; color: var(--text-faint); }
.crumbs a { color: var(--text-soft); text-decoration: none; font-weight: 500; }
.crumbs a:hover { color: var(--primary); text-decoration: underline; }
.tool-heading { display: flex; align-items: center; gap: 1rem; animation: rise .5s var(--ease) both; }
.tool-heading h1 { margin: 0; }
.tool-lead { margin: .3rem 0 0; font-size: 1.05rem; color: var(--text-soft); }
.tool-icon {
  display: inline-grid; place-items: center; flex: none; width: 48px; height: 48px; border-radius: 14px;
  background: var(--tool-bg); color: var(--tool-fg); box-shadow: inset 0 0 0 1px var(--tool-ring);
  transition: transform .35s var(--ease-spring);
}
.tool-icon .icon { width: 24px; height: 24px; }
.tool-icon-lg { width: 64px; height: 64px; border-radius: 18px; }
.tool-icon-lg .icon { width: 32px; height: 32px; }
.tool-icon-sm { width: 32px; height: 32px; border-radius: 9px; }
.tool-icon-sm .icon { width: 17px; height: 17px; }
@media (max-width: 560px) {
  .tool-heading { align-items: flex-start; gap: .8rem; }
  .tool-icon-lg { width: 50px; height: 50px; border-radius: 14px; }
  .tool-icon-lg .icon { width: 26px; height: 26px; }
}
.tool-app { padding-bottom: 2.5rem; }

.workspace { display: grid; grid-template-columns: minmax(0, 1fr) minmax(300px, 380px); gap: 1.25rem; align-items: start; }
.workspace-main { min-width: 0; display: flex; flex-direction: column; gap: 1rem; }
.workspace-side { min-width: 0; display: flex; flex-direction: column; gap: 1rem; position: sticky; top: calc(var(--header-h) + 12px); }
@media (max-width: 920px) {
  .workspace { grid-template-columns: minmax(0, 1fr); }
  .workspace-side { position: static; }
}

.actions { display: flex; flex-direction: column; gap: .6rem; }
.actions .btn-primary { width: 100%; }

/* Phone/tablet action bar (see "Phones" in docs/TOOL_GUIDE.md).
   site.js adds .js-actionbar to <html> and, while the bar's normal place (the end of its panel) is still
   below the bottom of the screen but its workspace is on screen, adds .is-floating: the bar is then pinned
   to the bottom of the screen, full width. Once you scroll down to its normal place it docks there and
   scrolls away with the page, so it never covers the help section or the footer. An empty
   .actionbar-slot (added by site.js just before the bar) keeps its space while it floats, so nothing jumps.
   The bar has the same size docked and floating, so the hand-over is seamless. */
.actionbar-slot { display: none; }
@media (max-width: 920px) {
  .js-actionbar .actions-sticky {
    flex-direction: row; flex-wrap: wrap; align-items: stretch; gap: .5rem;
    margin-top: .25rem; padding: .7rem 0 calc(.7rem + env(safe-area-inset-bottom));
    border-top: 1px solid var(--border);
  }
  .js-actionbar .actions-sticky > * { flex: 1 1 auto; }
  .js-actionbar .actions-sticky > .btn { width: auto; min-height: 50px; font-size: 1rem; padding-inline: 1rem; white-space: nowrap; }
  .js-actionbar .actions-sticky > .btn-primary { flex: 1 1 58%; }
  .js-actionbar .actions-sticky > .btn-ghost { flex: 0 1 auto; --btn-border: var(--border-strong); }
  .js-actionbar .actionbar-slot.is-active { display: block; }
  .js-actionbar .actions-sticky.is-floating {
    position: fixed; z-index: 45; left: 0; right: 0; bottom: 0; margin: 0;
    padding-inline: max(var(--gutter), env(safe-area-inset-left), calc((100% - 680px) / 2)) max(var(--gutter), env(safe-area-inset-right), calc((100% - 680px) / 2));
    background: var(--surface);
    box-shadow: 0 -8px 24px -12px rgb(16 24 40 / .22);
  }
  :root.js-actionbar[data-theme="dark"] .actions-sticky.is-floating { box-shadow: 0 -8px 24px -8px rgb(0 0 0 / .6); }
}

/* ---------- Dropzone ---------- */
.dropzone {
  position: relative; display: flex; flex-direction: column; align-items: center; justify-content: center; text-align: center;
  gap: .75rem; min-height: 340px; padding: 2.5rem 1.25rem;
  border: 2px dashed var(--border-strong);
  border-radius: var(--radius-xl);
  background:
    radial-gradient(100% 80% at 50% 0%, color-mix(in srgb, var(--tool-bg) 90%, transparent), transparent 70%),
    var(--surface);
  cursor: pointer;
  transition: border-color .2s, background-color .2s, transform .25s var(--ease), box-shadow .25s;
  animation: rise .5s .05s var(--ease) both;
}
.dropzone { -webkit-tap-highlight-color: transparent; }
.dropzone:active { border-color: var(--primary); }
@media (hover: hover) {
  .dropzone:hover { border-color: var(--primary); box-shadow: var(--shadow); }
  .dropzone:hover .dropzone-icon { transform: translateY(-3px); }
}
.dropzone.is-dragging { border-style: solid; border-color: var(--primary); transform: scale(1.01); box-shadow: 0 0 0 6px color-mix(in srgb, var(--primary) 16%, transparent), var(--shadow-lg); }
.dropzone.is-dragging .dropzone-icon { transform: translateY(-6px) scale(1.08); }
.dropzone-icon {
  display: grid; place-items: center; width: 76px; height: 76px; border-radius: 22px;
  background: var(--tool-bg); color: var(--tool-fg); box-shadow: inset 0 0 0 1px var(--tool-ring); margin-bottom: .25rem;
  transition: transform .35s var(--ease-spring);
}
.dropzone-icon .icon { width: 36px; height: 36px; }
.dropzone-title { font-size: clamp(1.25rem, 1.1rem + .8vw, 1.6rem); font-weight: 700; letter-spacing: -.03em; margin: 0; }
.dropzone-hint { margin: 0; color: var(--text-soft); font-size: .92rem; }
.dropzone-formats { margin: .25rem 0 0; font-size: .82rem; color: var(--text-faint); max-width: 46ch; }
.dropzone .btn { margin-top: .35rem; max-width: 100%; }
/* Compact "add more files" zone: icon + title + button on one row when there is room; in a narrow panel or
   on a phone the button wraps onto its own full-width row (the title never gets squashed word by word). */
.dropzone-compact { min-height: 0; padding: .9rem 1rem; flex-direction: row; flex-wrap: wrap; justify-content: flex-start; gap: .75rem 1rem; border-radius: var(--radius-lg); animation: none; text-align: left; }
.dropzone-compact .dropzone-icon { width: 44px; height: 44px; border-radius: 13px; margin: 0; }
.dropzone-compact .dropzone-icon .icon { width: 22px; height: 22px; }
.dropzone-compact .dropzone-text { flex: 1 1 9rem; min-width: 0; display: flex; flex-direction: column; gap: .15rem; }
.dropzone-compact .dropzone-title { font-size: 1rem; font-weight: 650; letter-spacing: -.015em; }
.dropzone-compact .dropzone-formats { margin: 0; }
.dropzone-compact .btn { flex: 1 0 auto; margin: 0; }

/* ---------- Preview ---------- */
.preview {
  position: relative; display: grid; place-items: center; min-height: 300px; padding: 1rem; overflow: hidden;
  border-radius: var(--radius-lg); border: 1px solid var(--border);
  background-color: var(--checker-b);
  background-image: conic-gradient(var(--checker-a) 25%, transparent 0 50%, var(--checker-a) 0 75%, transparent 0);
  background-size: 20px 20px;
}
.preview > img, .preview > canvas, .preview > video, .preview > svg { display: block; max-width: 100%; max-height: var(--preview-max-h); width: auto; height: auto; object-fit: contain; border-radius: 4px; box-shadow: 0 2px 12px rgb(16 24 40 / .12); }
.preview-plain { background: var(--surface-sunken); }
.preview-meta { display: flex; flex-wrap: wrap; gap: .4rem 1rem; font-size: .88rem; color: var(--text-soft); }
.preview-meta strong { color: var(--text); }

/* Before / after compare slider (ui.js compareSlider) */
.compare { position: relative; display: inline-block; max-width: 100%; line-height: 0; user-select: none; touch-action: pan-y; border-radius: 4px; overflow: hidden; box-shadow: 0 2px 12px rgb(16 24 40 / .12); }
.compare > * { display: block; max-width: 100%; max-height: var(--preview-max-h); width: auto; height: auto; }
.compare-after { position: absolute; inset: 0; clip-path: inset(0 0 0 var(--pos, 50%)); }
.compare-after > * { width: 100%; height: 100%; max-height: none; object-fit: contain; }
.compare-handle { position: absolute; top: 0; bottom: 0; left: var(--pos, 50%); width: 0; cursor: ew-resize; }
.compare-handle::before { content: ""; position: absolute; top: 0; bottom: 0; left: -1.5px; width: 3px; background: #fff; box-shadow: 0 0 0 1px rgb(0 0 0 / .25); }
.compare-knob { position: absolute; top: 50%; left: 0; width: 44px; height: 44px; transform: translate(-50%, -50%); border-radius: 50%; background: #fff; color: #0c0f17; display: grid; place-items: center; box-shadow: 0 2px 10px rgb(0 0 0 / .35); border: 0; cursor: ew-resize; padding: 0; touch-action: none; }
.compare-label { position: absolute; top: 10px; padding: .2rem .55rem; border-radius: 99px; background: rgb(12 15 23 / .65); color: #fff; font-size: .75rem; font-weight: 600; line-height: 1.4; pointer-events: none; }
.compare-label-before { left: 10px; }
.compare-label-after { right: 10px; }

/* ---------- Notices, badges, progress ---------- */
.notice { display: flex; gap: .7rem; align-items: flex-start; padding: .85rem 1rem; border-radius: var(--radius); background: var(--info-soft); color: var(--text); border: 1px solid color-mix(in srgb, var(--info) 22%, transparent); font-size: .9rem; }
.notice > .icon { color: var(--info); margin-top: .1em; }
.notice p { margin: 0; }
.notice-warn { background: var(--warning-soft); border-color: color-mix(in srgb, var(--warning) 25%, transparent); }
.notice-warn > .icon { color: var(--warning); }
.notice-error { background: var(--danger-soft); border-color: color-mix(in srgb, var(--danger) 25%, transparent); }
.notice-error > .icon { color: var(--danger); }
.notice-success { background: var(--success-soft); border-color: color-mix(in srgb, var(--success) 25%, transparent); }
.notice-success > .icon { color: var(--success); }

.badge { display: inline-flex; align-items: center; gap: .3em; padding: .12em .6em; border-radius: 99px; background: var(--bg-soft); color: var(--text-soft); font-size: .75rem; font-weight: 600; line-height: 1.55; white-space: nowrap; }
.badge-primary { background: var(--primary-soft); color: var(--primary); }
.badge-accent { background: var(--accent-soft); color: var(--accent); }
.chip { display: inline-flex; align-items: center; gap: .35em; padding: .3em .75em; border-radius: 99px; border: 1px solid var(--border); background: var(--surface); font-size: .85rem; font-weight: 550; }

.progress { position: relative; height: 10px; border-radius: 99px; background: var(--surface-sunken); border: 1px solid var(--border); overflow: hidden; }
.progress-bar { position: absolute; inset: 0 auto 0 0; width: var(--p, 0%); border-radius: inherit; background: var(--gradient); transition: width .3s var(--ease); }
.progress-bar::after { content: ""; position: absolute; inset: 0; background: linear-gradient(90deg, transparent, rgb(255 255 255 / .35), transparent); animation: shimmer 1.4s linear infinite; }
.progress.is-indeterminate .progress-bar { width: 35%; animation: indeterminate 1.3s var(--ease) infinite; }
@keyframes shimmer { from { transform: translateX(-100%); } to { transform: translateX(100%); } }
@keyframes indeterminate { from { left: -35%; } to { left: 100%; } }
.progress-label { display: flex; justify-content: space-between; gap: .5rem; font-size: .85rem; color: var(--text-soft); margin-top: .4rem; }

.spinner { display: inline-block; width: 1.25em; height: 1.25em; border-radius: 50%; border: 2.5px solid currentColor; border-right-color: transparent; animation: spin .8s linear infinite; vertical-align: -.2em; flex: none; }
@keyframes spin { to { transform: rotate(360deg); } }

.result { display: flex; flex-direction: column; align-items: center; text-align: center; gap: .5rem; padding: 1.5rem 1rem; border-radius: var(--radius-lg); background: var(--success-soft); border: 1px solid color-mix(in srgb, var(--success) 22%, transparent); animation: pop .45s var(--ease-spring) both; }
.result-check { display: grid; place-items: center; width: 60px; height: 60px; border-radius: 50%; background: var(--success); color: #fff; animation: pop .5s .1s var(--ease-spring) both; }
.result-check .icon { width: 32px; height: 32px; stroke-width: 3; }
.result-title { font-weight: 700; font-size: 1.12rem; letter-spacing: -.02em; margin: 0; }
.result-meta { color: var(--text-soft); margin: 0; font-size: .9rem; }

.file-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: .5rem; }
.file-item { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem .75rem; padding: .6rem .75rem; border: 1px solid var(--border); border-radius: var(--radius); background: var(--surface); animation: rise .3s var(--ease) both; }
.file-thumb { width: 46px; height: 46px; flex: none; border-radius: 10px; object-fit: cover; background: var(--surface-sunken); }
.file-info { flex: 1 1 7rem; min-width: 0; }
.file-name { font-weight: 600; font-size: .92rem; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.file-sub { font-size: .8rem; color: var(--text-faint); }

.tabs { display: flex; gap: .25rem; border-bottom: 1px solid var(--border); overflow-x: auto; overflow-y: hidden; scrollbar-width: none; overscroll-behavior-x: contain; }
.tabs::-webkit-scrollbar { display: none; }
.tab { flex: none; display: inline-flex; align-items: center; gap: .45rem; min-height: 44px; padding: .5rem .9rem; margin-bottom: -1px; background: none; border: 0; border-bottom: 2px solid transparent; font-weight: 600; font-size: .92rem; color: var(--text-soft); cursor: pointer; border-radius: 8px 8px 0 0; -webkit-tap-highlight-color: transparent; }
@media (hover: hover) { .tab:hover { color: var(--text); background: var(--bg-soft); } }
.tab[aria-selected="true"] { color: var(--primary); border-bottom-color: var(--primary); }

/* Dialogs: centred card on bigger screens, a bottom sheet on phones (see the Phones section).
   The body scrolls by itself; the buttons always stay visible. */
dialog.dialog { border: 1px solid var(--border); padding: 0; border-radius: var(--radius-lg); background: var(--surface); color: var(--text); box-shadow: var(--shadow-lg); width: min(480px, calc(100vw - 32px)); max-width: calc(100vw - 32px); max-height: calc(100vh - 32px); max-height: calc(100dvh - 32px); overflow: hidden; }
dialog.dialog.dialog-wide { width: min(720px, calc(100vw - 32px)); }
dialog.dialog[open] { display: flex; flex-direction: column; animation: pop .28s var(--ease-spring) both; }
dialog.dialog::backdrop { background: rgb(12 15 23 / .45); -webkit-backdrop-filter: blur(4px); backdrop-filter: blur(4px); animation: fade .2s both; }
.dialog-body { padding: 1.4rem 1.4rem 1rem; flex: 1 1 auto; min-height: 0; overflow-y: auto; overscroll-behavior: contain; }
.dialog-title { font-size: 1.15rem; font-weight: 700; margin: 0 0 .5rem; }
.dialog-actions { flex: none; display: flex; justify-content: flex-end; flex-wrap: wrap; gap: .5rem; padding: 0 1.4rem 1.4rem; }
:root.dialog-open, :root.dialog-open body { overflow: hidden; }

/* Toasts sit above the phone action bar while it floats (--actionbar-h), and above open dialogs
   (ui.js promotes the host to the top layer as a popover). */
.toasts { position: fixed; z-index: 200; left: 50%; bottom: calc(max(20px, env(safe-area-inset-bottom)) + var(--actionbar-h)); transform: translateX(-50%); display: flex; flex-direction: column; align-items: center; gap: .5rem; pointer-events: none; width: max-content; max-width: calc(100vw - 32px); transition: bottom .2s var(--ease); }
.toasts[popover] { inset: auto auto calc(max(20px, env(safe-area-inset-bottom)) + var(--actionbar-h)) 50%; margin: 0; padding: 0; border: 0; background: none; color: inherit; overflow: visible; }
.toast { pointer-events: auto; display: flex; align-items: center; gap: .6rem; padding: .7rem 1.05rem; border-radius: 1.5rem; background: #0c0f17; color: #f1f3f8; font-weight: 550; font-size: .92rem; line-height: 1.4; box-shadow: var(--shadow-lg); animation: toast-in .35s var(--ease-spring) both; }
.toast .icon { color: #6ce9a6; }
.toast-error .icon { color: #fda29b; }
.toast-info .icon { color: #a4bcfd; }
.toast.is-leaving { animation: toast-out .25s var(--ease) both; }
:root[data-theme="dark"] .toast { background: #f1f3f8; color: #0c0f17; }
:root[data-theme="dark"] .toast .icon { color: #067647; }
:root[data-theme="dark"] .toast-error .icon { color: #d92d20; }
:root[data-theme="dark"] .toast-info .icon { color: #175cd3; }
@keyframes toast-in { from { opacity: 0; transform: translateY(16px) scale(.96); } }
@keyframes toast-out { to { opacity: 0; transform: translateY(8px) scale(.97); } }

/* ---------- Help / FAQ section on tool pages ---------- */
.tool-help { padding-top: 2.5rem; padding-bottom: 1rem; border-top: 1px solid var(--border); }
.tool-help h2 { margin-bottom: 1.1rem; }
.how-steps { list-style: none; margin: 0 0 2.5rem; padding: 0; display: grid; grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); gap: 1rem; counter-reset: how; }
.how-steps li { counter-increment: how; position: relative; padding: 1.1rem 1.1rem 1.1rem 3.8rem; border-radius: var(--radius-lg); background: var(--surface); border: 1px solid var(--border); }
.how-steps li::before { content: counter(how); position: absolute; left: 1rem; top: 1.05rem; display: grid; place-items: center; width: 1.9rem; height: 1.9rem; border-radius: 50%; background: var(--tool-bg); color: var(--tool-fg); box-shadow: inset 0 0 0 1px var(--tool-ring); font-weight: 700; font-size: .9rem; }
.how-steps strong { display: block; margin-bottom: .15rem; }
.how-steps p { margin: 0; color: var(--text-soft); font-size: .9rem; }
.faq { display: flex; flex-direction: column; gap: .5rem; max-width: 820px; }
.faq details { border: 1px solid var(--border); border-radius: var(--radius); background: var(--surface); padding: 0 1.1rem; transition: box-shadow .2s; }
.faq details[open] { box-shadow: var(--shadow); }
.faq summary { list-style: none; cursor: pointer; display: flex; justify-content: space-between; align-items: center; gap: 1rem; min-height: 56px; font-weight: 600; }
.faq summary::-webkit-details-marker { display: none; }
.faq summary::after { content: "+"; font-size: 1.4rem; font-weight: 400; color: var(--text-faint); transition: transform .25s var(--ease); line-height: 1; }
.faq details[open] summary::after { transform: rotate(45deg); color: var(--primary); }
.faq details > div, .faq details > p { padding-bottom: 1rem; color: var(--text-soft); margin: 0; font-size: .95rem; }

/* ---------- Tool cards (home, related) ---------- */
.tool-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(min(100%, 290px), 1fr)); gap: .9rem; }
.tool-card {
  --i: 0;
  position: relative; display: flex; align-items: center; gap: 1rem;
  padding: 1.05rem 1.1rem; min-height: 96px;
  background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-lg);
  color: var(--text); text-decoration: none;
  box-shadow: var(--shadow-sm);
  transition: transform .25s var(--ease), box-shadow .25s var(--ease), border-color .25s;
  animation: rise .55s var(--ease) both; animation-delay: calc(var(--i) * 40ms + 60ms);
}
.tool-card { -webkit-tap-highlight-color: transparent; }
.tool-card:focus-visible { color: var(--text); transform: translateY(-3px); box-shadow: var(--shadow-lg); border-color: var(--tool-ring); }
@media (hover: hover) {
  .tool-card:hover { color: var(--text); transform: translateY(-3px); box-shadow: var(--shadow-lg); border-color: var(--tool-ring); }
  .tool-card:hover .tool-icon { transform: rotate(-6deg) scale(1.07); }
}
.tool-card:active { transform: translateY(-1px) scale(.99); }
.tool-card-text { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: .15rem; }
.tool-card-title { margin: 0; font-size: 1rem; font-weight: 650; letter-spacing: -.02em; }
.tool-card-desc { color: var(--text-soft); font-size: .86rem; line-height: 1.45; }
.tool-card-arrow { color: var(--text-faint); opacity: 0; transform: translateX(-6px); transition: opacity .2s, transform .25s var(--ease); }
.tool-card:focus-visible .tool-card-arrow { opacity: 1; transform: none; color: var(--tool-fg); }
@media (hover: hover) { .tool-card:hover .tool-card-arrow { opacity: 1; transform: none; color: var(--tool-fg); } }
@media (hover: none) { .tool-card-arrow { opacity: .5; transform: none; } }
.tool-grid-compact .tool-card { min-height: 84px; }

.related { padding-top: 2rem; padding-bottom: 3.5rem; }
.related h2 { font-size: 1.25rem; margin-bottom: 1rem; }

/* ---------- Home page ---------- */
/* overflow-x: clip keeps the decorative glow from widening the page on phones (it used to make an
   iPhone lay the page out 10% wider than the screen); the glow may still spill upwards under the header. */
.hero { position: relative; isolation: isolate; padding: clamp(3rem, 1.5rem + 6vw, 6rem) 0 2.5rem; text-align: center; overflow-x: clip; }
.hero::before {
  content: ""; position: absolute; inset: -64px 0 0; z-index: -2; pointer-events: none;
  background-image: radial-gradient(circle at 1px 1px, color-mix(in srgb, var(--text) 13%, transparent) 1px, transparent 0);
  background-size: 22px 22px;
  -webkit-mask-image: radial-gradient(70% 65% at 50% 30%, #000 20%, transparent 75%);
  mask-image: radial-gradient(70% 65% at 50% 30%, #000 20%, transparent 75%);
}
.hero::after {
  content: ""; position: absolute; z-index: -1; pointer-events: none; left: 50%; top: -120px; width: min(900px, 100%); height: 420px; transform: translateX(-50%);
  background: radial-gradient(closest-side, rgb(124 58 237 / .16), rgb(79 70 229 / .10) 45%, transparent 75%);
  filter: blur(10px);
  animation: glow 9s ease-in-out infinite alternate;
}
:root[data-theme="dark"] .hero::after { background: radial-gradient(closest-side, rgb(129 140 248 / .22), rgb(167 139 250 / .12) 45%, transparent 75%); }
@keyframes glow { to { transform: translateX(-50%) scale(1.08) translateY(12px); } }
.hero h1 { font-size: clamp(2.3rem, 1.3rem + 4.2vw, 4.1rem); line-height: 1.05; max-width: 15ch; margin: 0 auto 1rem; letter-spacing: -.035em; font-weight: 750; animation: rise .6s .05s var(--ease) both; }
.hero h1 .grad { background: var(--gradient); -webkit-background-clip: text; background-clip: text; color: transparent; }
.hero-sub { font-size: clamp(1rem, .95rem + .35vw, 1.18rem); color: var(--text-soft); max-width: 44ch; margin: 0 auto 2rem; animation: rise .6s .1s var(--ease) both; }
.search { position: relative; max-width: 620px; margin: 0 auto; animation: rise .6s .15s var(--ease) both; }
.search .icon { position: absolute; left: 1.15rem; top: 50%; transform: translateY(-50%); width: 1.3rem; height: 1.3rem; color: var(--text-faint); pointer-events: none; }
.search input {
  width: 100%; min-height: 60px; padding: 0 1.25rem 0 3.2rem; border-radius: 16px;
  border: 1px solid var(--border-strong); background: var(--surface); box-shadow: var(--shadow);
  font-size: 1.02rem; transition: border-color .2s, box-shadow .2s;
}
.search input::placeholder { color: var(--text-faint); }
.search input:focus { outline: none; border-color: var(--primary); box-shadow: var(--ring), var(--shadow); }
.search-suggest { display: flex; flex-wrap: wrap; justify-content: center; align-items: center; gap: .45rem; margin: 1rem auto 0; max-width: 640px; animation: rise .6s .2s var(--ease) both; }
.search-suggest span { color: var(--text-faint); font-size: .85rem; }
.search-suggest button { border: 1px solid var(--border); background: var(--surface); color: var(--text-soft); border-radius: 99px; padding: .32rem .8rem; font-size: .85rem; font-weight: 550; cursor: pointer; white-space: nowrap; -webkit-tap-highlight-color: transparent; transition: border-color .15s, color .15s, transform .15s var(--ease); }
.search-suggest button:active { border-color: var(--primary); color: var(--primary); }
@media (hover: hover) { .search-suggest button:hover { border-color: var(--primary); color: var(--primary); transform: translateY(-1px); } }
.search-empty { text-align: center; color: var(--text-soft); padding: 1.5rem 0; }
.categories { padding-bottom: 2rem; }
.category { padding-top: 2.25rem; scroll-margin-top: calc(var(--header-h) + 8px); }
.category-head { display: flex; align-items: baseline; flex-wrap: wrap; gap: .25rem 1rem; margin-bottom: 1rem; }
.category-head h2 { margin: 0; font-size: 1.3rem; }
.category-head p { margin: 0; color: var(--text-faint); font-size: .92rem; }
.family-band { margin-top: 2.5rem; margin-bottom: 4rem; }
.family-card {
  position: relative; overflow: hidden; isolation: isolate; display: flex; align-items: center; justify-content: space-between; flex-wrap: wrap; gap: 1.25rem;
  padding: clamp(1.5rem, 1rem + 2vw, 2.4rem); border-radius: var(--radius-xl);
  background: #0c0f17; color: #f1f3f8; border: 1px solid #1f2430;
  box-shadow: var(--shadow-lg);
}
.family-card::before { content: ""; position: absolute; inset: 0; z-index: -1; background: radial-gradient(60% 120% at 100% 0%, rgb(124 58 237 / .45), transparent 60%), radial-gradient(50% 100% at 0% 100%, rgb(79 70 229 / .35), transparent 60%); }
.family-card h2 { color: #fff; margin: 0 0 .35rem; }
.family-card p { margin: 0; color: #b3bbcb; max-width: 52ch; }
.family-card .btn { --btn-bg: #fff; --btn-fg: #0c0f17; --btn-border: #fff; }
.family-card .btn:hover { --btn-bg: #eef0ff; --btn-fg: #0c0f17; --btn-border: #eef0ff; }
.family-kicker { font-size: .75rem; font-weight: 650; letter-spacing: .1em; text-transform: uppercase; color: #a5b4fc; margin-bottom: .45rem !important; }

/* ---------- Simple text pages (about, privacy, …) ---------- */
.page-head { padding: 3rem 0 1.5rem; }
.page-head h1 { margin: 0 0 .5rem; }
.page-head p { color: var(--text-soft); font-size: 1.08rem; margin: 0; max-width: 60ch; }
.prose { max-width: 760px; padding-bottom: 4rem; }
.prose h2 { font-size: 1.3rem; margin-top: 2rem; }
.prose h3 { margin-top: 1.5rem; }
.prose ul, .prose ol { padding-left: 1.3rem; }
.prose li { margin-bottom: .4rem; }
.prose table { width: 100%; border-collapse: collapse; font-size: .92rem; }
.prose th, .prose td { text-align: left; padding: .55rem .6rem; border-bottom: 1px solid var(--border); vertical-align: top; }
.prose th { font-weight: 650; }

.not-found { text-align: center; padding: 5rem 0 4rem; }
.not-found .big { font-size: clamp(4rem, 3rem + 6vw, 7rem); font-weight: 750; letter-spacing: -.05em; line-height: 1; background: var(--gradient); -webkit-background-clip: text; background-clip: text; color: transparent; margin: 0 0 .5rem; }

/* ---------- Footer (compact) ---------- */
.site-footer { margin-top: auto; border-top: 1px solid var(--border); padding: 1.4rem 0 calc(1.4rem + env(safe-area-inset-bottom)); font-size: .88rem; }
.footer-inner { display: flex; align-items: center; flex-wrap: wrap; gap: .75rem 1.75rem; }
.footer-links { display: flex; flex-wrap: wrap; gap: .4rem 1.25rem; flex: 1 1 auto; }
.site-footer a:not(.brand) { color: var(--text-soft); text-decoration: none; }
.site-footer a:not(.brand):hover { color: var(--primary); }
.footer-copy { margin: 0; color: var(--text-faint); }

/* ==========================================================================
   Phones and small tablets. Everything above is written for desktop first;
   this block reshapes the shared pieces for touch screens. Tool agents: see
   "Phones" in docs/TOOL_GUIDE.md for the rules your tool.css should follow.
   ========================================================================== */
@supports (height: 1svh) { :root { --preview-max-h: min(68svh, 720px); } }

/* Tablets and landscape phones: one column, less air. */
@media (max-width: 920px) {
  .tool-app { padding-bottom: 2rem; }
}

/* Short screens (landscape phones): a slimmer header. */
@media (max-height: 500px) and (orientation: landscape) {
  :root { --header-h: 52px; --preview-max-h: min(62vh, 560px); }
  .brand-mark { width: 28px; height: 28px; }
  .site-header { background: var(--bg); }
}

@media (max-width: 640px) {
  :root { --header-h: 56px; --gutter: 16px; --preview-max-h: min(50vh, 440px); }
  @supports (height: 1svh) { :root { --preview-max-h: min(50svh, 440px); } }

  /* Header: solid (content never shows through it), compact. Without the blur it is also no longer a
     containing block, so the tools sheet can be fixed to the screen. */
  .site-header { background: var(--bg); -webkit-backdrop-filter: none; backdrop-filter: none; }
  .header-inner { gap: .5rem; }
  .brand-mark { width: 30px; height: 30px; }
  .brand-name { font-size: 1.06rem; }
  .header-actions { gap: .15rem; margin-right: -.35rem; }
  .menu-button { padding-inline: .75rem; gap: .45rem; }
  .menu-chevron { display: none; }

  /* Headings and text */
  h1 { font-size: clamp(1.6rem, 1.2rem + 2.4vw, 1.9rem); }
  h2 { font-size: 1.22rem; }

  /* Buttons: the big variants are a little less huge. */
  .btn-xl { min-height: 56px; font-size: 1.04rem; padding-inline: 1.3rem; }
  .btn-lg { min-height: 52px; }

  /* Form bits */
  .seg span { padding-inline: .45rem; }
  .panel { padding: 1rem; border-radius: var(--radius); }

  /* Tool page top: breadcrumb, then icon + title on one line, then the lead across the full width. */
  .tool-hero { padding: .7rem 0 .9rem; }
  .tool-hero::before { inset: -56px 0 -24px; }
  .crumbs { font-size: .82rem; margin-bottom: .35rem; }
  .crumbs a { display: inline-block; padding: .55rem 0; margin: -.35rem 0; }
  .tool-heading { display: grid; grid-template-columns: auto minmax(0, 1fr); align-items: center; column-gap: .75rem; row-gap: .45rem; }
  .tool-heading > div { display: contents; }
  .tool-heading h1 { font-size: clamp(1.45rem, 1.1rem + 2vw, 1.7rem); line-height: 1.12; }
  .tool-lead { grid-column: 1 / -1; margin: 0; font-size: .95rem; line-height: 1.5; }
  .tool-icon-lg, .tool-heading .tool-icon-lg { width: 44px; height: 44px; border-radius: 12px; }
  .tool-icon-lg .icon, .tool-heading .tool-icon-lg .icon { width: 23px; height: 23px; }
  .tool-app { padding-bottom: 1.5rem; }

  /* Start screen: the dropzone fits on screen with the title above it. */
  .dropzone { min-height: 0; padding: 1.75rem 1rem 1.6rem; gap: .6rem; border-radius: var(--radius-lg); }
  .dropzone-icon { width: 60px; height: 60px; border-radius: 18px; }
  .dropzone-icon .icon { width: 30px; height: 30px; }
  .dropzone-title { font-size: 1.25rem; }
  .dropzone .btn-xl { width: 100%; max-width: 20rem; }
  .dropzone-compact { padding: .8rem .85rem; }

  /* Work screen (.workspace): preview first, then the settings flow straight on the page (no card inside a
     card), then the action bar. */
  .workspace { gap: 1rem; }
  .workspace-main, .workspace-side { gap: .75rem; }
  .workspace-side > .panel { padding: 0; border: 0; border-radius: 0; background: none; box-shadow: none; }
  .preview { min-height: 180px; padding: .6rem; border-radius: var(--radius); }
  .preview-meta { font-size: .85rem; gap: .25rem .8rem; }

  /* Dialogs: bottom sheet */
  dialog.dialog, dialog.dialog.dialog-wide {
    width: 100%; max-width: 100%; margin: auto 0 0; border-width: 1px 0 0;
    border-radius: var(--radius-xl) var(--radius-xl) 0 0;
    max-height: calc(100vh - 24px); max-height: calc(100dvh - 24px);
  }
  dialog.dialog[open] { animation: sheet-up .3s var(--ease) both; }
  .dialog-body { padding: 1.3rem var(--gutter) .9rem; }
  .dialog-actions { padding: .25rem var(--gutter) calc(1rem + env(safe-area-inset-bottom)); }
  .dialog-actions > .btn { flex: 1 1 8rem; }

  /* Toasts: full-width-ish and above everything at the bottom */
  .toasts { max-width: calc(100vw - 24px); }
  /* While a bottom sheet is open, messages appear at the top so they never cover its buttons. */
  :root.dialog-open .toasts { top: max(16px, env(safe-area-inset-top)); bottom: auto; }
  .toast { font-size: .9rem; }

  /* Help + questions */
  .tool-help { padding-top: 1.75rem; }
  .tool-help h2 { margin-bottom: .8rem; }
  .how-steps { gap: .6rem; margin-bottom: 1.75rem; }
  .how-steps li { padding: .85rem .9rem .85rem 3.2rem; border-radius: var(--radius); }
  .how-steps li::before { left: .85rem; top: .85rem; width: 1.75rem; height: 1.75rem; font-size: .85rem; }
  .faq details { padding: 0 .95rem; }
  .faq summary { min-height: 54px; font-size: .97rem; line-height: 1.35; padding: .5rem 0; }
  .faq details > div, .faq details > p { font-size: .93rem; }

  /* Tool cards become one grouped list of compact rows (like a phone's settings screen). The 1px gap over
     the border-coloured background draws the separators, so hidden cards (search) never leave a double line. */
  .tool-grid { display: flex; flex-direction: column; gap: 1px; background: var(--border); border: 1px solid var(--border); border-radius: var(--radius-lg); overflow: hidden; box-shadow: var(--shadow-sm); animation: rise .5s .05s var(--ease) both; }
  .tool-card { min-height: 70px; padding: .75rem .85rem; gap: .85rem; border: 0; border-radius: 0; box-shadow: none; animation: none; }
  .tool-card:active { transform: none; background: var(--surface-2); }
  @media (hover: hover) { .tool-card:hover { transform: none; box-shadow: none; background: var(--surface-2); } }
  .tool-card:focus-visible { transform: none; box-shadow: inset 0 0 0 2.5px var(--focus); outline: none; }
  .tool-card .tool-icon { width: 44px; height: 44px; border-radius: 12px; }
  .tool-card .tool-icon .icon { width: 22px; height: 22px; }
  .tool-card-title { font-size: .98rem; }
  .tool-card-desc { font-size: .84rem; line-height: 1.4; }
  .tool-card-arrow { width: 1.1em; height: 1.1em; }
  .tool-grid-compact .tool-card { min-height: 66px; }
  .related { padding-top: 1.25rem; padding-bottom: 2.25rem; }
  .related h2 { font-size: 1.12rem; margin-bottom: .7rem; }

  /* Home */
  .hero { padding: 1.6rem 0 1.25rem; }
  .hero::after { top: -90px; height: 320px; animation: none; }
  .hero h1 { font-size: clamp(1.9rem, 1.1rem + 4.4vw, 2.35rem); line-height: 1.08; max-width: 13ch; margin-bottom: .7rem; }
  .hero-sub { font-size: 1rem; line-height: 1.55; margin-bottom: 1.25rem; max-width: 32ch; }
  .search input { min-height: 54px; border-radius: 14px; padding-left: 3rem; font-size: 1rem; }
  .search .icon { left: 1rem; }
  /* "Try:" suggestions: one tidy row you can swipe sideways, instead of a ragged two-line block. */
  .search-suggest {
    flex-wrap: nowrap; justify-content: flex-start; overflow-x: auto; scrollbar-width: none; overscroll-behavior-x: contain;
    margin: .75rem calc(-1 * var(--gutter)) 0; padding: 0 var(--gutter) 2px; gap: .4rem; scroll-padding-inline: var(--gutter);
    -webkit-mask-image: linear-gradient(to right, transparent, #000 var(--gutter), #000 calc(100% - 28px), transparent);
    mask-image: linear-gradient(to right, transparent, #000 var(--gutter), #000 calc(100% - 28px), transparent);
  }
  .search-suggest::-webkit-scrollbar { display: none; }
  .search-suggest span, .search-suggest button { flex: none; }
  .search-suggest button { min-height: 44px; padding: .4rem .9rem; font-size: .88rem; }
  .search-suggest::after { content: ""; flex: none; width: 12px; }
  .categories { padding-bottom: .5rem; }
  .category { padding-top: 1.5rem; }
  .category-head { flex-direction: column; gap: .1rem; margin-bottom: .65rem; }
  .category-head h2 { font-size: 1.18rem; }
  .category-head p { font-size: .88rem; }
  .search-empty { padding: 1.25rem 0 .5rem; }
  .family-band { margin-top: 1.75rem; margin-bottom: 2.25rem; }
  .family-card { padding: 1.35rem 1.2rem; border-radius: var(--radius-lg); gap: 1rem; }
  .family-card h2 { font-size: 1.25rem; }
  .family-card p { font-size: .95rem; }
  .family-card .btn { width: 100%; }

  /* Simple pages */
  .page-head { padding: 1.6rem 0 1rem; }
  .prose { padding-bottom: 2.5rem; }
  .prose table { display: block; overflow-x: auto; }

  /* Footer: brand + copyright on one line, links underneath with finger-sized gaps. */
  .site-footer { padding: .9rem 0 calc(.75rem + env(safe-area-inset-bottom)); }
  .footer-inner { gap: .25rem 1rem; justify-content: space-between; }
  .footer-links { order: 3; flex: 1 1 100%; gap: 0 1.15rem; }
  .footer-links a { display: inline-flex; align-items: center; min-height: 44px; }
  .footer-copy { font-size: .82rem; }
}

@media (max-width: 374px) {
  :root { --gutter: 14px; }
  .js-actionbar .actions-sticky > .btn-primary:not(.btn-icon) > .icon { display: none; }
  .js-actionbar .actions-sticky > .btn { padding-inline: .7rem; font-size: .94rem; letter-spacing: -.015em; }
  .js-actionbar .actions-sticky { gap: .4rem; }
  .brand-name { font-size: 1rem; }
  /* The menu button keeps its accessible name through aria-label. */
  .menu-button > span { display: none; }
  .menu-button { width: 46px; padding: 0; }
  .search-suggest > span { display: none; }
  .search input { font-size: 16px; padding-right: .75rem; }
}

@keyframes sheet-up { from { transform: translateY(40px); opacity: .4; } }

/* ---------- Motion ---------- */
@keyframes rise { from { opacity: 0; transform: translateY(12px); } }
@keyframes fade { from { opacity: 0; } }
@keyframes pop { from { opacity: 0; transform: scale(.94); } }
/* backwards (not both): a transform left in effect after the animation would make the view the containing
   block for position:fixed children and break the phone action bar. */
[data-view]:not([hidden]) { animation: rise .4s var(--ease) backwards; }
.fade-in { animation: fade .35s var(--ease) both; }
.pop-in { animation: pop .4s var(--ease-spring) both; }
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after { animation-duration: .01ms !important; animation-delay: 0ms !important; animation-iteration-count: 1 !important; transition-duration: .01ms !important; scroll-behavior: auto !important; }
}

/* ---------- Print ---------- */
@media print {
  .site-header, .site-footer, .related, .tool-help, .skip-link, .toasts { display: none !important; }
  body { background: #fff; color: #000; }
}
