/* Social Kit Demo - the editor chrome, in each example kit's own dress, as
   the brand pack's "The kit in its dress" describes it and the rebrand loop
   showed it. app.mjs sets data-brand on the html element at boot, and brand.js
   before the first paint, from the address the editor was opened at.

   Kettlebrook: cream with thin espresso rules, light cream cards with soft
   corners, Fraunces names, a terracotta accent, and espresso for whatever is
   chosen. Graphite: graphite and steel with sharp 4 px corners, condensed
   Archivo capitals, and volt lime for the accent and for whatever is chosen.
   Neither is stitched: --seam is solid in both.

   The phone mockup keeps its own colours: it imitates a real phone and a real
   feed. */
:root {
  /* The two drag outlines sit on the post, not on the chrome, so they are
     chosen against the post: blue for a photo or clip, a hot pink for a
     piece. */
  --slot-outline: 87, 131, 179;
  --piece-outline: 236, 72, 153;
  --topbar-h: 58px;
  --rail-w: 208px;
  --settings-w: 372px;
}
html[data-brand="kettlebrook"] {
  --bg: #f6eedf;
  --bg-mid: #f6eedf;
  --bg-panel: #fbf6ec;
  --bg-darkest: #fffaf2;
  --stage: #ece2d0;
  --stage-glow: #f3eadb;
  --border: rgba(59, 36, 22, .2);
  --border-strong: rgba(59, 36, 22, .45);
  --seam: solid;
  --text: #3b2416;
  --text-dim: #7a5b45;
  --text-muted: #9c8470;
  /* Terracotta is a fill, with light cream on it; espresso draws the lines
     of whatever is hovered or focused, and fills whatever is chosen. */
  --accent: #c2572b;
  --accent-deep: #a8481f;
  --accent-soft: rgba(194, 87, 43, .12);
  --accent-glow: rgba(194, 87, 43, .25);
  --on-accent: #fbf6ec;
  --accent-text: #c2572b;
  --accent-line: #3b2416;
  --select-bg: #3b2416;
  --select-text: #fbf6ec;
  --select-note: #d9c4a8;
  --danger: #b23b2a;
  --ok: #5f8a4f;
  --warn: #a35a00;
  --backdrop: rgba(59, 36, 22, .35);
  --shadow: rgba(59, 36, 22, .22);
  --post-shadow: 0 24px 60px rgba(59, 36, 22, .28);
  --frame-ring: #3b2416;
  --caption: rgba(59, 36, 22, .78);
  --drop: rgba(246, 238, 223, .9);
  --sticker-ground: #d9c4a8;
  --radius: 16px;
  --btn-radius: 999px;
  --btn-case: none;
  --display: 'Fraunces', Georgia, serif;
  --display-axes: "SOFT" 100, "WONK" 1, "opsz" 36;
  --display-stretch: 100%;
  --display-weight: 700;
  --display-case: none;
  --note-case: none;
  --text-font: 'Instrument Sans', system-ui, Arial, sans-serif;
  --text-stretch: 100%;
}
html[data-brand="graphite"] {
  --bg: #1d2024;
  --bg-mid: #1d2024;
  --bg-panel: #23272c;
  --bg-darkest: #16181b;
  --stage: #16181b;
  --stage-glow: #1d2024;
  --border: #31363c;
  --border-strong: #4a5058;
  --seam: solid;
  --text: #edeff0;
  --text-dim: #8e959c;
  --text-muted: #6b7178;
  /* Volt lime is the accent and the chosen thing alike, graphite on it. */
  --accent: #c6f432;
  --accent-deep: #b4e01f;
  --accent-soft: rgba(198, 244, 50, .12);
  --accent-glow: rgba(198, 244, 50, .2);
  --on-accent: #16181b;
  --accent-text: #c6f432;
  --accent-line: #c6f432;
  --select-bg: #c6f432;
  --select-text: #16181b;
  --select-note: #3a4210;
  --danger: #e0533d;
  --ok: #7dad6e;
  --warn: #ff9f43;
  --backdrop: rgba(8, 9, 10, .6);
  --shadow: rgba(0, 0, 0, .5);
  --post-shadow: 0 30px 80px rgba(0, 0, 0, .6);
  --frame-ring: #31363c;
  --caption: rgba(22, 24, 27, .82);
  --drop: rgba(29, 32, 36, .9);
  --sticker-ground: #23272c;
  --radius: 4px;
  --btn-radius: 4px;
  --btn-case: uppercase;
  --display: 'Archivo', 'Arial Narrow', sans-serif;
  --display-axes: normal;
  --display-stretch: 62%;
  --display-weight: 900;
  --display-case: uppercase;
  --note-case: uppercase;
  --text-font: 'Archivo', Arial, sans-serif;
  --text-stretch: 85%;
}
/* Graphite's header rule carries a short lime bar at its left end. */
html[data-brand="graphite"] .topbar::after { content: ''; position: absolute; left: 0; bottom: -2px; width: 180px; height: 6px; background: var(--accent); }

* { box-sizing: border-box; }
html, body { height: 100%; margin: 0; }
body {
  background: var(--bg); color: var(--text);
  font-family: var(--text-font); font-stretch: var(--text-stretch); font-size: 13px; font-weight: 600; line-height: 1.4; letter-spacing: .1px;
  overflow: hidden; -webkit-font-smoothing: antialiased;
}
button, input, select { font: inherit; color: inherit; }
button { cursor: pointer; }
button:disabled { cursor: default; opacity: .45; }
::selection { background: var(--accent); color: var(--on-accent); }

/* ---------- top bar ---------- */
.topbar {
  position: relative; height: var(--topbar-h); display: flex; align-items: center; gap: 20px; padding: 0 16px;
  background: var(--bg-mid); border-bottom: 1.5px var(--seam) var(--border);
  -webkit-app-region: drag;
}
.topbar button, .topbar .seg { -webkit-app-region: no-drag; }
.topbar-brand { display: flex; align-items: center; gap: 10px; min-width: var(--rail-w); }
.topbar-crest svg { display: block; width: 26px; height: auto; }
.topbar h1 { margin: 0; font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 19px; letter-spacing: .01em; white-space: nowrap; }
.topbar h1 span { color: var(--accent-text); }
/* A made-up brand says so beside its name (the web demo's two). */
.example-tag { flex: none; padding: 2px 7px; border: 1.5px solid var(--accent-text); border-radius: var(--radius); color: var(--accent-text); font-size: 10px; font-weight: 700; letter-spacing: .12em; text-transform: uppercase; white-space: nowrap; }
.topbar-middle { flex: 1; display: flex; justify-content: center; gap: 14px; }
.topbar-actions { display: flex; align-items: center; gap: 8px; min-width: var(--settings-w); justify-content: flex-end; }
.saved { color: var(--text-dim); font-size: 12px; margin-right: 6px; min-width: 70px; text-align: right; }

.seg { display: inline-flex; background: var(--bg-darkest); border: 1.5px var(--seam) var(--border); border-radius: var(--btn-radius); padding: 2px; gap: 2px; }
.seg button {
  border: 1.5px solid transparent; background: transparent; color: var(--text-dim); padding: 4px 11px; border-radius: var(--btn-radius);
  font-size: 12px; font-weight: 800; letter-spacing: .02em; display: flex; flex-direction: column; align-items: center; line-height: 1.15;
  transition: color .12s, background .12s, border-color .12s;
}
.seg button small { font-weight: 600; font-size: 10px; opacity: .8; }
.seg button.active { background: var(--select-bg); border-color: var(--select-bg); color: var(--select-text); }
.seg button:not(.active):hover { color: var(--text); }

.btn {
  border: 1.5px var(--seam) var(--border); background: var(--bg-darkest); color: var(--text);
  padding: 7px 14px; border-radius: var(--btn-radius); font-weight: 800; font-size: 12.5px; letter-spacing: .02em;
  transition: border-color .12s, color .12s, background .12s;
}
.btn:hover:not(:disabled) { border-color: var(--accent-line); color: var(--accent-text); }
.btn.primary {
  background: var(--accent); color: var(--on-accent); border: 2px solid var(--accent); text-transform: var(--btn-case);
  box-shadow: 0 4px 12px var(--accent-glow);
}
.btn.primary:hover:not(:disabled) { background: var(--accent-deep); color: var(--on-accent); border-color: var(--accent-deep); }
.btn.small { padding: 4px 9px; font-size: 12px; border-radius: var(--btn-radius); }
.btn.ghost { background: transparent; }
.btn.danger:hover:not(:disabled) { border-color: var(--danger); color: var(--danger); }
.btn:focus-visible, .tbtn:focus-visible, .card:focus-visible, .seg button:focus-visible, .switch:focus-visible {
  outline: none; box-shadow: 0 0 0 2px var(--accent-line);
}

/* ---------- layout ---------- */
.editor {
  display: grid; grid-template-columns: var(--rail-w) 1fr var(--settings-w);
  height: calc(100% - var(--topbar-h));
}
.rail { background: var(--bg-mid); border-right: 1.5px var(--seam) var(--border); padding: 14px 12px; overflow-y: auto; }
.stage { display: flex; flex-direction: column; min-width: 0; }
.settings { background: var(--bg-mid); border-left: 1.5px var(--seam) var(--border); overflow-y: auto; }

/* ---------- rail ---------- */
.rail-label { color: var(--text-dim); font-size: 10.5px; font-weight: 800; letter-spacing: .14em; text-transform: uppercase; margin: 4px 6px 10px; }
.card {
  width: 100%; text-align: left; border: 1.5px var(--seam) var(--border); background: var(--bg-panel); border-radius: var(--radius);
  padding: 12px 12px 10px; margin-bottom: 8px; display: flex; flex-direction: column; gap: 3px;
  transition: border-color .12s, background .12s;
}
.card:hover:not(:disabled) { border-color: var(--accent-line); }
.card.active { border-style: solid; border-color: var(--select-bg); background: var(--select-bg); }
.card.active .card-name { color: var(--select-text); }
.card.active .card-note { color: var(--select-note); }
.card-name { font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 17px; letter-spacing: .01em; }
.card-note { color: var(--text-dim); font-size: 11.5px; text-transform: var(--note-case); letter-spacing: .02em; }
.card:disabled { opacity: .5; }

/* ---------- stage ---------- */
.viewport { flex: 1; position: relative; overflow: hidden; background: var(--stage);
  background-image: radial-gradient(circle at 50% 40%, var(--stage-glow) 0%, var(--stage) 70%); }
.viewport-inner { position: absolute; left: 0; top: 0; transform-origin: 0 0; }
.chrome-back, .chrome-front { position: absolute; left: 0; top: 0; }
.chrome-front { pointer-events: none; z-index: 2; }
/* Black behind the post is content, not chrome: it is what a see-through post
   (a lower third) shows over when there is no footage yet. */
.canvas-box { position: absolute; z-index: 1; background: #000; box-shadow: 0 0 0 2px var(--frame-ring), var(--post-shadow); }
.canvas-box iframe { display: block; border: 0; background: #000; }
.canvas-shield { position: absolute; inset: 0; }

/* phone frame: everything in canvas units (1080 wide), scaled with the canvas.
   Drawn behind the canvas box; the overlays are drawn in front of it. */
.phone { position: absolute; width: 1180px; height: 2440px; padding: 50px; background: #14162a; border-radius: 170px;
  box-shadow: 0 0 0 6px #23263f, 0 0 0 10px #090a14, 0 60px 160px rgba(0, 0, 0, .7); }
.phone-screen { position: relative; width: 1080px; height: 2340px; background: #000; border-radius: 120px; }
.phone-island { position: absolute; left: 50%; top: 94px; transform: translateX(-50%); width: 300px; height: 92px; background: #000; border-radius: 50px; z-index: 30; }
.phone-home { position: absolute; left: 50%; bottom: 80px; transform: translateX(-50%); width: 420px; height: 14px; border-radius: 7px; background: rgba(255, 255, 255, .85); z-index: 30; }
.phone-overlay { position: absolute; pointer-events: none; font-family: -apple-system, 'Segoe UI', Roboto, sans-serif; color: #fff; }

/* story overlay */
.ov-story-progress { position: absolute; left: 30px; right: 30px; top: 150px; display: flex; gap: 10px; }
.ov-story-progress i { flex: 1; height: 8px; border-radius: 4px; background: rgba(255, 255, 255, .35); }
.ov-story-progress i.done { background: #fff; }
.ov-story-head { position: absolute; left: 30px; top: 180px; display: flex; align-items: center; gap: 22px; font-size: 38px; font-weight: 600; text-shadow: 0 2px 8px rgba(0, 0, 0, .6); }
/* The profile picture: the studio's mark on its own dark, as its account shows it. */
.ov-avatar { width: 96px; height: 96px; border-radius: 50%; background: #1c1c1c; display: flex; align-items: center; justify-content: center; border: 4px solid #fff; }
.ov-avatar svg { width: 52px; height: auto; }
.ov-story-head small { font-weight: 400; opacity: .75; }
.ov-story-dots { position: absolute; right: 40px; top: 205px; font-size: 44px; letter-spacing: 4px; text-shadow: 0 2px 8px rgba(0, 0, 0, .6); }
.ov-story-reply { position: absolute; left: 30px; right: 30px; bottom: 90px; display: flex; align-items: center; gap: 26px; }
.ov-story-reply .pill { flex: 1; height: 112px; border: 3px solid rgba(255, 255, 255, .75); border-radius: 60px; display: flex; align-items: center; padding: 0 44px; font-size: 38px; color: rgba(255, 255, 255, .85); }
.ov-story-reply .ico { width: 70px; height: 70px; }
.ov-story-reply .ico svg { width: 100%; height: 100%; fill: none; stroke: #fff; stroke-width: 5; stroke-linecap: round; stroke-linejoin: round; }
.ov-gradient-top { position: absolute; left: 0; right: 0; top: 0; height: 420px; background: linear-gradient(180deg, rgba(0, 0, 0, .5), transparent); }
.ov-gradient-bottom { position: absolute; left: 0; right: 0; bottom: 0; height: 420px; background: linear-gradient(0deg, rgba(0, 0, 0, .55), transparent); }

/* feed overlay: header above, actions below, in a black feed */
.ov-feed-head { display: flex; align-items: center; gap: 24px; padding: 0 30px; height: 150px; font-size: 38px; font-weight: 600; }
.ov-feed-head .ov-avatar { width: 92px; height: 92px; border: 3px solid #1c1c1c; }
.ov-feed-head .ov-more { margin-left: auto; font-size: 44px; letter-spacing: 4px; }
.ov-feed-actions { display: flex; align-items: center; gap: 44px; padding: 34px 34px 20px; }
.ov-feed-actions svg { width: 76px; height: 76px; fill: none; stroke: #fff; stroke-width: 5; stroke-linecap: round; stroke-linejoin: round; }
.ov-feed-actions .ov-save { margin-left: auto; }
.ov-feed-text { padding: 0 34px; font-size: 36px; line-height: 1.35; }
.ov-feed-text b { font-weight: 700; }
.ov-feed-text .dim { color: #9aa0b4; }

/* ---------- transport ---------- */
.transport {
  height: 62px; display: flex; align-items: center; gap: 14px; padding: 0 18px;
  background: var(--bg-mid); border-top: 1.5px var(--seam) var(--border);
}
.tbtn {
  width: 34px; height: 34px; border-radius: 6px; border: 1.5px var(--seam) var(--border); background: var(--bg-darkest); color: var(--text);
  display: inline-flex; align-items: center; justify-content: center;
  transition: border-color .12s, color .12s, background .12s;
}
.tbtn:hover { border-color: var(--accent-line); color: var(--accent-text); }
.tbtn svg { width: 16px; height: 16px; fill: currentColor; }
.tbtn.active { background: var(--accent-soft); border-style: solid; border-color: var(--accent-line); color: var(--accent-text); }
/* The play button is the one primary control down here. */
.tbtn.play { width: 42px; height: 42px; background: var(--accent); border: 2px solid var(--accent); color: var(--on-accent); box-shadow: 0 4px 12px var(--accent-glow); }
.tbtn.play:hover { background: var(--accent-deep); color: var(--on-accent); border-color: var(--accent-deep); }
.scrub { flex: 1; position: relative; height: 34px; display: flex; align-items: center; }
.scrub input[type=range] { width: 100%; margin: 0; accent-color: var(--accent); cursor: pointer; }
/* Scrubber marks (the still frame, or a template's own like the logo intro
   and outro): a tick with a wider invisible target; click to jump there. */
.scrub .marks { position: absolute; inset: 0; pointer-events: none; }
.scrub .mark { position: absolute; top: 1px; width: 14px; height: 14px; margin-left: -7px; padding: 0; border: 0; background: transparent;
               cursor: pointer; pointer-events: auto; z-index: 2; }
.scrub .mark::before { content: ''; position: absolute; left: 6px; top: 3px; width: 2px; height: 8px; border-radius: 1px; background: var(--accent); opacity: .8; }
.scrub .mark:hover::before { opacity: 1; top: 1px; height: 11px; }
.tcode { font-variant-numeric: tabular-nums; color: var(--text-dim); font-size: 12.5px; min-width: 132px; text-align: right; }
.tcode b { color: var(--text); font-weight: 800; }

/* ---------- settings ---------- */
/* Three tools beside a long template name do not fit a 372px column, so the
   head wraps as a whole: the name keeps the first line and the tools drop to
   the second, intact. Without this the words inside them break instead, which
   is how "Match sizes" ends up stacked two high beside a two line "3 sizes". */
.settings-head { padding: 16px 18px 10px; border-bottom: 1.5px var(--seam) var(--border); display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 10px; }
.settings-head h2 { margin: 0; font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 21px; letter-spacing: .01em; }
.settings-head .hint { color: var(--text-dim); font-size: 11.5px; }
.settings-head .head-tools { display: flex; align-items: center; gap: 10px; margin-left: auto; }
.settings-head .head-tools .btn, .settings-head .hint { white-space: nowrap; }
/* The two arrows, a step back and a step forward. Bigger type so they read as
   arrows, with the line height pinned so the glyph's own font cannot change
   their height. They stretch to the row, which Reset sets: on their own they
   came out 1.8px shorter than it and the borders did not line up. */
.btn.step { font-size: 15px; line-height: 1; padding: 4px 8px; align-self: stretch; }
.form { padding: 12px 18px 30px; display: flex; flex-direction: column; gap: 12px; }
.field { display: flex; flex-direction: column; gap: 5px; }
.field label, .rows-label { color: var(--text-dim); font-size: 10.5px; font-weight: 800; letter-spacing: .1em; text-transform: uppercase; }
.field input[type=text], .field input[type=number], .field select {
  background: var(--bg-darkest); border: 1.5px var(--seam) var(--border); border-radius: 6px; padding: 7px 9px; color: var(--text); width: 100%;
  font-weight: 600;
}
.field input:focus, .field select:focus {
  outline: none; border-style: solid; border-color: var(--accent-line); box-shadow: 0 0 0 2px var(--accent-glow);
}
.field select { appearance: none; background-image: linear-gradient(45deg, transparent 50%, var(--text-dim) 50%), linear-gradient(135deg, var(--text-dim) 50%, transparent 50%);
  background-position: calc(100% - 16px) 55%, calc(100% - 11px) 55%; background-size: 5px 5px; background-repeat: no-repeat; padding-right: 26px; }
.toggle { display: flex; align-items: center; justify-content: space-between; gap: 10px; min-width: 0; padding: 8px 10px; background: var(--bg-darkest); border: 1.5px var(--seam) var(--border); border-radius: 6px; }
.toggle .tlabel { font-size: 13px; }
.switch { position: relative; flex-shrink: 0; width: 38px; height: 22px; border-radius: 11px; background: var(--border-strong); border: 0; padding: 0; transition: background .15s; }
.switch::after { content: ''; position: absolute; top: 3px; left: 3px; width: 16px; height: 16px; border-radius: 50%; background: #fff; box-shadow: 0 1px 3px rgba(0, 0, 0, .25); transition: transform .15s; }
.switch.on { background: var(--accent); }
.switch.on::after { transform: translateX(16px); }
.action-row { display: flex; align-items: center; gap: 10px; }
.action-note { color: var(--text-dim); font-size: 11.5px; flex: 1; }
.action-note.ok { color: var(--ok); }
.action-note.warn { color: var(--warn); }

.rows { display: flex; flex-direction: column; gap: 8px; }
.rows-head { display: flex; align-items: center; justify-content: space-between; }
.row-card { background: var(--bg-panel); border: 1.5px var(--seam) var(--border); border-radius: 9px; padding: 10px; display: grid; grid-template-columns: 1fr 1fr; gap: 8px; }
.row-card .field.wide, .row-card > .span-row { grid-column: 1 / -1; }
.row-card .field label { font-size: 10px; }
/* What a typed file name will be, under its box. */
.name-hint { color: var(--text-dim); font-size: 11.5px; font-weight: 600; overflow-wrap: anywhere; }
/* One switch per row. These carry a written label and a switch beside it,
   not the small numeric fields the row card was built for, and three of
   them across a 372px panel cannot shrink below their own labels: a grid
   item's minimum is its content, so the card overflowed the panel and the
   last switch sat off the edge of the window. Stacked, they also read the
   same way as the standalone switches further down the panel. */
.group-card { grid-template-columns: 1fr; }
.row-card .field input, .row-card .field select { padding: 5px 8px; }
.row-tools { grid-column: 1 / -1; display: flex; gap: 6px; justify-content: flex-end; }
.row-tools .btn { padding: 3px 8px; font-size: 11.5px; }
.rows-empty { color: var(--text-dim); font-size: 12px; padding: 6px 2px; }

/* ---------- panels ---------- */
.panel-host { position: fixed; inset: 0; z-index: 100; }
.panel-backdrop { position: absolute; inset: 0; background: var(--backdrop); }
.panel { position: absolute; top: 0; right: 0; bottom: 0; width: 440px; background: var(--bg-mid); border-left: 1.5px var(--seam) var(--border);
  display: flex; flex-direction: column; box-shadow: -20px 0 60px var(--shadow); }
.panel-head { display: flex; align-items: center; justify-content: space-between; padding: 16px 18px; border-bottom: 1.5px var(--seam) var(--border); }
.panel-head h2 { margin: 0; font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 21px; letter-spacing: .01em; }
.panel-body { padding: 16px 18px; overflow-y: auto; display: flex; flex-direction: column; gap: 16px; flex: 1; }
/* Each panel builds its own root (a plain div) inside .panel. It has to be the
   column that fills the panel, or the body grows with its contents instead of
   scrolling: thirty photos made the library 3700px tall in an 860px window,
   with no way to reach the last of them. */
.panel > div { display: flex; flex-direction: column; flex: 1; min-height: 0; }
.panel-section h3 { margin: 0 0 8px; color: var(--text-dim); font-size: 10.5px; font-weight: 800; letter-spacing: .1em; text-transform: uppercase; }
.checks { display: flex; flex-wrap: wrap; gap: 8px; }
.chip { display: inline-flex; align-items: center; gap: 7px; padding: 6px 11px; border: 1.5px var(--seam) var(--border); border-radius: 20px; background: var(--bg-darkest); cursor: pointer; font-size: 12.5px; font-weight: 700; }
.chip input { accent-color: var(--accent); margin: 0; }
.chip.on { border-style: solid; border-color: var(--accent-line); background: var(--accent-soft); color: var(--accent-text); }
.folder-row { display: flex; align-items: center; gap: 8px; }
.folder-path { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; background: var(--bg-darkest); border: 1.5px var(--seam) var(--border); border-radius: 6px; padding: 7px 9px; color: var(--text-dim); font-size: 12px; }
.folder-path.set { color: var(--text); }
.progress { display: flex; flex-direction: column; gap: 8px; }
.progress-item { background: var(--bg-panel); border: 1.5px var(--seam) var(--border); border-radius: 8px; padding: 9px 11px; font-size: 12.5px; }
.progress-item .bar { height: 5px; background: var(--border); border-radius: 3px; margin-top: 7px; overflow: hidden; }
.progress-item .bar i { display: block; height: 100%; background: var(--accent); width: 0; transition: width .2s; }
.progress-item.done { border-style: solid; border-color: var(--ok); }
.progress-item.error { border-style: solid; border-color: var(--danger); }
.file-list { margin: 0; padding: 0; list-style: none; color: var(--text-dim); font-size: 12px; }
.file-list li { padding: 2px 0; }
.panel-foot { display: flex; gap: 8px; padding: 14px 18px; border-top: 1.5px var(--seam) var(--border); }
.panel-foot .btn { flex: 1; }

/* ---------- photos ---------- */
.gizmo { position: absolute; cursor: grab; outline: 2px dashed rgba(var(--slot-outline), 0); outline-offset: -2px; transition: outline-color .15s; }
.gizmo:hover { outline-color: rgba(var(--slot-outline), .95); }
.gizmo.dragging { cursor: grabbing; outline-color: rgb(var(--slot-outline)); outline-style: solid; }

/* A piece gizmo sits over the slot gizmo, so a patch lying on the illustration
   band takes the drag while the open art around it still takes its own. The
   outline is the brand's own orange rather than the slot's blue, so it is
   plain which of the two is under the pointer. */
.gizmo.piece { z-index: 2; }
.gizmo.piece:hover { outline-color: rgba(var(--piece-outline), .9); }
.gizmo.piece.dragging { outline-color: rgb(var(--piece-outline)); }
.photo-field .photo-box { position: relative; height: 120px; border-radius: 8px; overflow: hidden; background: var(--bg-darkest); border: 1.5px var(--seam) var(--border); display: flex; align-items: center; justify-content: center; }
.photo-field .photo-box img { width: 100%; height: 100%; object-fit: cover; display: block; }
.photo-field .photo-name { position: absolute; left: 0; right: 0; bottom: 0; padding: 4px 8px; font-size: 11px; color: #fff; background: var(--caption); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.photo-field .photo-empty { color: var(--text-dim); font-size: 12.5px; }
.photo-tools { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 6px; }
.zoom-row { display: flex; align-items: center; gap: 10px; margin-top: 8px; }
.zoom-row input[type=range] { flex: 1; accent-color: var(--accent); margin: 0; }
.zoom-label { color: var(--text-dim); font-size: 10.5px; font-weight: 800; letter-spacing: .1em; text-transform: uppercase; }
.zoom-read { min-width: 3.4em; text-align: right; color: var(--accent-text); font-size: 11.5px; font-weight: 800; font-variant-numeric: tabular-nums; }
.zoom-hint { color: var(--text-muted); font-size: 11.5px; margin-top: 4px; }

.length-form { padding-bottom: 0; }
.length-row { display: flex; align-items: center; gap: 10px; }
.length-row input[type=number] { width: 110px; }
.length-unit { color: var(--text-dim); font-size: 12.5px; }
.length-hint { color: var(--text-muted); font-size: 11.5px; line-height: 1.4; }

.tile-form { padding-top: 6px; padding-bottom: 8px; border-bottom: 1.5px var(--seam) var(--border); gap: 6px; }
.tile-form .tile-body { transition: opacity .15s; }
.tile-form .tile-body.off { opacity: .45; }
.tile-form select { width: 92px; }

/* ---------- the panel's dropdowns ----------
   The post's fields in dropdowns, Stickers among them (2026-10-15). Each
   heading is the template name's colour and face a size down, so it stands
   out from the dim labels inside, with the arrow turning as it opens. */
.section { border-bottom: 1.5px var(--seam) var(--border); padding-bottom: 2px; }
.section > summary, .sticker-group > summary { cursor: pointer; list-style: none; display: flex; align-items: center; gap: 8px; user-select: none; }
.section > summary::-webkit-details-marker, .sticker-group > summary::-webkit-details-marker { display: none; }
.section > summary::before, .sticker-group > summary::before { content: ''; border-left: 5px solid currentColor; border-top: 4px solid transparent; border-bottom: 4px solid transparent; transition: transform .15s; }
.section[open] > summary::before, .sticker-group[open] > summary::before { transform: rotate(90deg); }
.section > summary { color: var(--text); font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 16px; letter-spacing: .01em; padding: 6px 0; }
.section > summary::before { border-left-width: 6px; border-top-width: 5px; border-bottom-width: 5px; }
.section-body { display: flex; flex-direction: column; gap: 10px; padding: 6px 0 12px; }

/* ---------- stickers ----------
   A dropdown that opens onto a row per group, each opening onto its stickers
   to scroll through: Chadley's picture of the library. */
.sticker-count { margin-left: auto; color: var(--text-muted); font-family: var(--text-font); font-size: 11px; font-weight: 700; letter-spacing: 0; text-transform: none; }
.sticker-group { margin-top: 6px; background: var(--bg-panel); border: 1.5px var(--seam) var(--border); border-radius: 9px; }
.sticker-group > summary { padding: 8px 10px; color: var(--text); font-size: 12.5px; font-weight: 800; }
.sticker-strip { display: flex; gap: 6px; overflow-x: auto; padding: 2px 8px 10px; scroll-snap-type: x proximity; }
.sticker-thumb { flex: 0 0 auto; width: 84px; height: 84px; padding: 3px; border-radius: 10px; border: 1.5px var(--seam) transparent; background: var(--sticker-ground); cursor: pointer; scroll-snap-align: start; }
.sticker-thumb:hover { border-color: var(--accent-line); }
.sticker-thumb:focus-visible { outline: 2px solid var(--accent-line); outline-offset: 1px; }
.sticker-art .sticker { display: block; width: 100%; height: 100%; }
.sticker-on { margin-top: 10px; display: flex; flex-direction: column; gap: 6px; }
.sticker-on-item { display: flex; align-items: center; gap: 8px; }
.sticker-mini { flex: 0 0 auto; width: 34px; height: 34px; border-radius: 7px; background: var(--sticker-ground); }
.sticker-name { flex: 1; color: var(--text); font-size: 12.5px; }

/* A sticker's gizmo lies over the patches, as the sticker does, in the
   piece's orange, turned as the sticker is. Its two buttons are a screen size
   at any zoom (--k is canvas pixels per screen pixel, set as the gizmos follow
   the page) and stay upright however the sticker is turned (--r). */
.gizmo.sticker { z-index: 3; border-radius: 14px; }
.gizmo.sticker:hover { outline-color: rgba(var(--piece-outline), .9); }
.gizmo.sticker.dragging, .gizmo.sticker.turning, .gizmo.sticker.scaling { outline-color: rgb(var(--piece-outline)); outline-style: solid; }
.sticker-off, .sticker-turn, .sticker-scale { position: absolute; top: 0; width: calc(26px * var(--k, 1)); height: calc(26px * var(--k, 1)); padding: 0;
  border-radius: 50%; border: calc(2px * var(--k, 1)) solid #fff; color: #fff; display: flex; align-items: center; justify-content: center;
  opacity: 0; transition: opacity .15s; }
.sticker-off { right: 0; transform: translate(35%, -35%) rotate(calc(-1 * var(--r, 0deg))); background: var(--danger); cursor: pointer;
  font: 800 calc(17px * var(--k, 1))/1 var(--text-font); }
.sticker-turn { left: 0; transform: translate(-35%, -35%) rotate(calc(-1 * var(--r, 0deg))); background: var(--accent); color: var(--on-accent); border-color: var(--on-accent); cursor: ew-resize; touch-action: none; }
/* The scale handle, on the corner below the cross (2026-10-15). */
.sticker-scale { top: auto; bottom: 0; right: 0; transform: translate(35%, 35%) rotate(calc(-1 * var(--r, 0deg))); background: var(--accent); color: var(--on-accent); border-color: var(--on-accent); cursor: nwse-resize; touch-action: none; }
.sticker-turn svg, .sticker-scale svg { width: 62%; height: 62%; }
.gizmo.sticker:hover .sticker-off, .gizmo.sticker:hover .sticker-turn, .gizmo.sticker:hover .sticker-scale,
.gizmo.sticker.turning .sticker-turn, .gizmo.sticker.scaling .sticker-scale,
.sticker-off:focus-visible, .sticker-turn:focus-visible, .sticker-scale:focus-visible { opacity: 1; }
/* A patch has the sticker's cross and scale handle too (2026-10-20): the
   cross takes it off the post, the handle scales it. */
.gizmo.piece:hover .piece-off, .gizmo.piece:hover .piece-scale, .gizmo.piece.scaling .piece-scale { opacity: 1; }
.gizmo.piece.scaling { outline-color: rgb(var(--piece-outline)); }
/* The video window's gizmo (2026-10-23): under the patches, as the window is,
   turned as the window is, with the sticker's turn and scale handles and a
   hand on its fourth corner that slides what is in the window. */
.gizmo.window { z-index: 1; }
.gizmo.window:hover { outline-color: rgba(var(--piece-outline), .9); }
.gizmo.window.dragging, .gizmo.window.turning, .gizmo.window.scaling, .gizmo.window.panning { outline-color: rgb(var(--piece-outline)); outline-style: solid; }
.window-pan { position: absolute; bottom: 0; left: 0; width: calc(26px * var(--k, 1)); height: calc(26px * var(--k, 1)); padding: 0;
  border-radius: 50%; border: calc(2px * var(--k, 1)) solid var(--on-accent); background: var(--accent); color: var(--on-accent);
  display: flex; align-items: center; justify-content: center; opacity: 0; transition: opacity .15s;
  transform: translate(-35%, 35%) rotate(calc(-1 * var(--r, 0deg))); cursor: move; touch-action: none; }
.window-pan svg { width: 62%; height: 62%; }
.gizmo.window:hover .sticker-turn, .gizmo.window:hover .sticker-scale, .gizmo.window:hover .window-pan,
.gizmo.window.turning .sticker-turn, .gizmo.window.scaling .sticker-scale, .gizmo.window.panning .window-pan,
.window-pan:focus-visible { opacity: 1; }

.colour-row { display: flex; align-items: center; gap: 10px; }
.colour-row input[type=color] { width: 52px; height: 34px; padding: 2px; border: 1.5px var(--seam) var(--border); border-radius: 6px; background: var(--bg-darkest); cursor: pointer; }
.colour-note { flex: 1; color: var(--text-dim); font-size: 11.5px; letter-spacing: .04em; }

.library-body { position: relative; }
.library-body.dragging::after { content: 'Drop to import'; position: absolute; inset: 8px; border: 3px dashed var(--accent-line); border-radius: 12px; display: flex; align-items: center; justify-content: center; background: var(--drop); color: var(--text); font-size: 16px; font-weight: 800; pointer-events: none; }
.library-tools { display: flex; align-items: center; gap: 10px; }
.library-hint { color: var(--text-dim); font-size: 12px; flex: 1; }
.library-grid { display: grid; grid-template-columns: repeat(2, 1fr); gap: 10px; }
.library-item { background: var(--bg-panel); border: 1.5px var(--seam) var(--border); border-radius: 9px; overflow: hidden; display: flex; flex-direction: column; }
.library-item.pickable .thumb { cursor: pointer; }
.library-item.pickable:hover { border-color: var(--accent-line); }
.library-item .thumb { aspect-ratio: 4 / 3; background: var(--bg-darkest); }
.library-item .thumb img { width: 100%; height: 100%; object-fit: cover; display: block; }
.library-item .thumb { position: relative; }
.clip-badge { position: absolute; right: 6px; bottom: 6px; padding: 2px 7px; border-radius: 5px; background: var(--caption); color: #fff; font-size: 11px; font-weight: 800; letter-spacing: .04em; }
/* A sound has no picture: a note on the green the timeline gives sound, so it
   reads as the same thing in both places. */
.library-item .sound-thumb { position: absolute; inset: 0; display: flex; align-items: center; justify-content: center;
  background: #4f7a44; color: #fff; font-size: 46px; line-height: 1; }
.library-item .meta { display: flex; flex-direction: column; gap: 2px; padding: 7px 9px 4px; }
.library-item .name { font-size: 12px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.library-item .dims { font-size: 11px; color: var(--text-dim); }
.library-item .tools { display: flex; gap: 6px; padding: 4px 9px 9px; }
.library-empty { color: var(--text-dim); font-size: 12.5px; padding: 20px 4px; }

/* ---------- queue ---------- */
.queue { display: flex; flex-direction: column; gap: 8px; }
.queue-empty { color: var(--text-dim); font-size: 12.5px; padding: 6px 2px; }
.queue-item { display: grid; grid-template-columns: 64px 1fr; gap: 10px; background: var(--bg-panel); border: 1.5px var(--seam) var(--border); border-radius: 9px; padding: 8px; }
.queue-item .qthumb { width: 64px; height: 80px; border-radius: 5px; overflow: hidden; background: var(--bg-darkest); grid-row: 1 / 3; }
.queue-item .qthumb img { width: 100%; height: 100%; object-fit: cover; display: block; }
.queue-item .qmeta { display: flex; flex-direction: column; gap: 2px; font-size: 12.5px; min-width: 0; }
.queue-item .qmeta span { color: var(--text-dim); font-size: 11.5px; }
.queue-item .qtools { display: flex; gap: 6px; align-items: flex-end; }
.btn.added { border-style: solid; border-color: var(--ok); color: var(--ok); }

/* ---------- about ---------- */
.about p { margin: 0; color: var(--text-dim); font-size: 13px; line-height: 1.5; }
.about-hero { display: flex; align-items: center; gap: 14px; }
.about-hero svg { width: 54px; height: auto; }
.about-name { font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 21px; letter-spacing: .01em; }
.about-version { color: var(--text-dim); font-size: 12px; }
.about-tools { display: flex; gap: 8px; margin-top: 10px; }
.about-fine { font-size: 11.5px; }

/* ---------- toast ---------- */
.toast { position: fixed; left: 50%; bottom: 84px; transform: translateX(-50%); z-index: 200; background: var(--bg-panel); border: 1.5px var(--seam) var(--accent-line);
  color: var(--text); padding: 10px 16px; border-radius: 8px; font-size: 13px; font-weight: 700; box-shadow: 0 10px 40px var(--shadow); max-width: 560px; }
.toast.error { border-style: solid; border-color: var(--danger); }

/* In-app questions, in place of the native confirm box. */
.confirm-host { position: fixed; inset: 0; z-index: 300; display: flex; align-items: center; justify-content: center; }
.confirm-backdrop { position: absolute; inset: 0; background: var(--backdrop); }
.confirm { position: relative; width: min(420px, calc(100vw - 48px)); background: var(--bg-panel); border: 2px var(--seam) var(--accent-line); border-radius: 14px;
           padding: 20px 22px 18px; box-shadow: 0 24px 60px var(--shadow); }
.confirm-title { margin: 0 0 8px; font-family: var(--display); font-variation-settings: var(--display-axes); font-stretch: var(--display-stretch); font-weight: var(--display-weight); text-transform: var(--display-case); font-size: 21px; letter-spacing: .01em; color: var(--accent-text); }
.confirm-message { margin: 0 0 18px; color: var(--text-dim); font-size: 13px; line-height: 1.5; }
.confirm-tools { display: flex; justify-content: flex-end; gap: 8px; }
.btn.destructive { background: var(--danger); border: 2px solid #fff; color: #fff; }
.btn.destructive:hover:not(:disabled) { background: #a83f31; border-color: #fff; color: #fff; }

/* Transport: the clip sound switch and the clip's frame rate. */
.tbtn[hidden] { display: none; }
.tcode i { font-style: normal; color: var(--accent-text); margin-left: 8px; }

/* ---------- the editor ----------
   The timeline, the monitor and the tray, in the same ink as the rest of the
   chrome: solid edges, the panel colours, and the yellow for whatever is
   chosen (a tool, the scrub, a picked clip). The clips themselves keep one
   colour in both themes, blue for a picture and green for a sound, with white
   names, because a thumbnail or a waveform sits on them either way. */
/* A box that is display:flex would otherwise beat the hidden attribute: the
   timeline would show over the templates. */
[hidden] { display: none !important; }

.viewport.monitor { display: flex; align-items: center; justify-content: center; padding: 14px; }
/* A ring rather than a border: a border would take a pixel off each side of
   the box the pictures are placed in, and it would no longer be the canvas's
   exact shape. Black, as the exported file's own ground is. */
.mon-box { position: relative; max-width: 100%; max-height: 100%; height: 100%; background: #000;
  box-shadow: 0 0 0 1.5px var(--border-strong), var(--post-shadow); border-radius: 6px; overflow: hidden; }
/* Each picture is placed in the box the export draws it in (the editor sets
   its left, top, width and height); until then it fills, as the export does. */
.mon-box > .mon-video { position: absolute; left: 0; top: 0; width: 100%; height: 100%; object-fit: cover; background: transparent; }
.mon-frame { position: absolute; box-sizing: border-box; border: 1.5px dashed var(--accent); pointer-events: none; }
.mon-grip { position: absolute; inset: 0; cursor: move; }
.mon-grip.dragging { cursor: grabbing; }
.frame-card { display: flex; flex-direction: column; gap: 6px; }
.frame-card .zoom-row { margin-top: 0; }

.timeline { flex: none; height: 232px; display: flex; flex-direction: column; gap: 6px;
  padding: 8px 10px 10px; border-top: 1.5px var(--seam) var(--border); background: var(--bg-mid); }
/* Nothing on the timeline is text to copy. Without this, scrubbing the
   playhead along the ruler selected the time labels it passed over. */
.timeline { user-select: none; }
.tl-tools { display: flex; align-items: center; gap: 10px; }
.tl-label { color: var(--text-dim); font-size: 10.5px; font-weight: 800; letter-spacing: .14em; text-transform: uppercase; }
.tl-zoom { flex: 0 0 200px; accent-color: var(--accent); margin: 0; }
.tl-readout { margin-left: auto; color: var(--text-dim); font-size: 12px; font-weight: 700; font-variant-numeric: tabular-nums; }
.tl-body { flex: 1; min-height: 0; display: flex; gap: 8px; }
.tl-scroll { flex: 1; min-width: 0; overflow: auto; border: 1.5px var(--seam) var(--border); border-radius: 8px; background: var(--bg-darkest); }
/* The tool strip beside the tracks. */
.tl-strip { flex: none; display: flex; flex-direction: column; gap: 6px; }
.tl-strip .tl-tool { flex: 1; max-height: 62px; width: 56px; display: flex; flex-direction: column; align-items: center;
  justify-content: center; gap: 3px; padding: 0; font: inherit; color: var(--text-dim); cursor: pointer;
  background: var(--bg-darkest); border: 1.5px var(--seam) var(--border); border-radius: 8px; }
.tl-strip .tl-tool:hover { color: var(--accent-text); border-color: var(--accent-line); }
.tl-tool-name { font-size: 10px; font-weight: 800; letter-spacing: .06em; text-transform: uppercase; }
.tl-tool.on, .tl-strip .tl-tool.on, .tl-scrub.on, .tl-snap.on, .tl-play.on {
  border-style: solid; border-color: var(--accent-line); background: var(--accent-soft); color: var(--accent-text); }
.tl-play { min-width: 64px; }
.tl-scrub, .tl-snap { display: inline-flex; align-items: center; gap: 6px; }
.tl-inner { position: relative; min-width: 100%; }
.tl-ruler { position: relative; height: 22px; border-bottom: 1.5px var(--seam) var(--border); background: var(--bg-panel); }
.tl-tick { position: absolute; top: 3px; padding-left: 4px; border-left: 1px solid var(--border-strong);
  color: var(--text-dim); font-size: 10px; font-weight: 700; font-variant-numeric: tabular-nums; white-space: nowrap; }
.tl-rows { position: relative; }
.tl-track { position: relative; border-bottom: 1px var(--seam) var(--border); }
.tl-track.audio { background: rgba(125, 173, 110, .06); }
.tl-clip { position: absolute; top: 4px; bottom: 4px; border-radius: 7px; overflow: hidden; cursor: pointer;
  background-color: #3f5f86; background-size: cover; background-position: center;
  border: 1.5px var(--seam) rgba(255, 255, 255, .5); }
.tl-clip.audio { background-color: #4f7a44; }
.tl-clip.on { border-style: solid; border-color: var(--accent); box-shadow: 0 0 0 1px var(--accent) inset; }
.tl-clip.on.lead { box-shadow: 0 0 0 2px var(--accent) inset; }
.tl-link { display: inline-block; margin-right: 4px; vertical-align: -1px; line-height: 0; }
.tl-clip.missing { background-color: #6b2a20; border-color: var(--danger); }
.tl-clip-name { position: absolute; left: 6px; bottom: 4px; right: 6px; color: #fff; font-size: 11px; font-weight: 800;
  text-shadow: 0 1px 3px rgba(0, 0, 0, .8); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.tl-wave { position: absolute; left: 0; top: 4px; width: 100%; height: 38px; }
/* A sound track with nothing on it: the flat line of silence. */
.tl-clip.audio.mute { background-color: #3d4a38; }
.tl-clip.audio.mute::before { content: ''; position: absolute; left: 0; right: 0; top: 23px; height: 1px; background: rgba(255, 255, 255, .45); }
.tl-roi { position: absolute; top: 0; bottom: 0; background: var(--accent-soft);
  border-left: 2px solid var(--accent-line); border-right: 2px solid var(--accent-line); pointer-events: none; }
/* The ends of the region, to take hold of and drag: the edge line, wider to
   grab than it looks, with a flag at the top pointing into the region. */
.tl-mark { position: absolute; top: 0; bottom: 0; width: 14px; margin-left: -7px; z-index: 2; cursor: ew-resize; touch-action: none; }
.tl-mark::after { content: ''; position: absolute; top: 0; width: 9px; height: 11px; background: var(--accent); }
.tl-mark.in::after { left: 7px; clip-path: polygon(0 0, 100% 0, 0 100%); }
.tl-mark.out::after { left: -2px; clip-path: polygon(0 0, 100% 0, 100% 100%); }
.tl-mark:hover::before, .tl-mark.held::before { content: ''; position: absolute; top: 0; bottom: 0; left: 5px; width: 4px; background: var(--accent); }
/* Where a held end is, just under the ruler. */
.tl-mark-time { position: absolute; top: 25px; z-index: 5; transform: translateX(-50%); padding: 2px 6px; border-radius: 4px;
  background: var(--accent); color: var(--on-accent); font-size: 11px; font-weight: 800; font-variant-numeric: tabular-nums;
  white-space: nowrap; pointer-events: none; }
.tl-playhead { position: absolute; top: 0; bottom: 0; width: 2px; margin-left: -1px; background: var(--accent);
  pointer-events: none; box-shadow: 0 0 6px rgba(var(--piece-outline), .8); }
.timeline.razoring .tl-clip { cursor: crosshair; }
/* The box dragged across empty space to pick clips. */
.tl-marquee { position: absolute; z-index: 4; border: 1.5px dashed var(--accent-line); background: var(--accent-soft); pointer-events: none; }
/* Right-click on a clip. */
.tl-menu { position: fixed; z-index: 60; min-width: 190px; padding: 4px; display: flex; flex-direction: column;
  background: var(--bg-panel); border: 1.5px var(--seam) var(--border-strong); border-radius: 9px; box-shadow: 0 10px 30px var(--shadow); }
.tl-menu-item { display: flex; justify-content: space-between; gap: 18px; padding: 7px 10px; border: 0; border-radius: 6px;
  background: transparent; color: var(--text); font: inherit; font-size: 13px; font-weight: 700; text-align: left; cursor: pointer; }
.tl-menu-item:hover:not(:disabled) { background: var(--accent-soft); color: var(--accent-text); }
.tl-menu-item:disabled { opacity: .4; cursor: default; }
.tl-menu-keys { color: var(--text-dim); font-size: 11.5px; font-weight: 600; }

.region-card { display: flex; flex-direction: column; gap: 8px; }
.region-read { font-size: 12.5px; font-variant-numeric: tabular-nums; }
.region-tools { display: flex; flex-wrap: wrap; gap: 6px; }
.clip-facts { color: var(--text-dim); font-size: 12px; }
.clip-facts.link-note { line-height: 1.4; }

.tray-head { display: flex; align-items: center; justify-content: space-between; gap: 8px; margin-bottom: 8px; }
.tray-list { display: flex; flex-direction: column; gap: 8px; }
.tray-item { display: grid; grid-template-columns: 56px 1fr auto; grid-template-rows: auto auto; gap: 2px 10px;
  align-items: center; padding: 6px; border: 1.5px var(--seam) var(--border); border-radius: 8px; background: var(--bg-panel); cursor: grab; }
.tray-item:hover { border-color: var(--accent-line); }
.tray-thumb { grid-column: 1; grid-row: 1 / 3; width: 56px; height: 40px; border-radius: 5px; background: var(--bg-darkest) center/cover no-repeat; }
.tray-name { grid-column: 2; grid-row: 1; min-width: 0; font-size: 12.5px; font-weight: 700; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.tray-meta { grid-column: 2; grid-row: 2; color: var(--text-dim); font-size: 11px; }
.tray-item .btn { grid-column: 3; grid-row: 1 / 3; }
.tray-buttons { grid-column: 3; grid-row: 1 / 3; display: flex; gap: 6px; }
/* What has been taken off the tray, listed under it to be put back. */
.tray-removed-toggle { margin-top: 10px; }
.tray-removed { margin-top: 8px; }
.tray-removed .tray-item { opacity: .7; cursor: default; }

/* The web demo: nothing comes in and nothing goes out, so the controls that
   import, export, queue, edit or open files are taken off the page, and the
   tile, which only shapes an export. Everything else stays. */
html[data-demo] :is(#btn-about, #btn-update-queue, #btn-to-editor, #btn-queue, #btn-export, .tile-form, [data-import], [data-clear], [data-delete], [data-hint]) { display: none !important; }
