/* new-pictures.css — 26 Oct 2026. THE NEW PICTURES page (src/NewPicturesPage.jsx): the Shots page's panel and tabs
   (one tab per Current project), one collapsible section per asset category, one card per asset (its latest new
   picture at its OWN ratio, as the Assets page's own character card), and the big viewer (the shot window's card). Its own np-* classes only (plus the app's .shots-panel, .tabs,
   .tab, .modal-backdrop, .modal-card, .modal-close-btn, .modal-nav-btn). Colours are tokens, so every skin repaints it
   and none resizes it. NO SHIFT (invariant 20): section heads are fixed, a card's picture box is reserved from the
   picture's known pixel size (aspect-ratio) before it loads, its text lines are fixed, an action changes a state
   line and buttons only, and the viewer floats over the page. Pictures sit on the white matte (.asset-matte). */
.view-page.np-page { gap: 12px; }

/* ── the panel + project tabs: the Shots page's own .shots-panel.glass > .shots-header > .tabs > .tab (shots.css);
   only the overflow of a long tab list is added here ── */
.np-panel { min-width: 0; }
/* ONE panel, like the Assets page (Hugo: "Remove the extra panel layer so New pictures matches the Assets page"): the
   page's own cream panel (section.view-page) holds the tabs; the Shots panel inside it keeps its tab row and spacing but
   paints nothing of its own (no fill, blur, shadow, border or sheen), in every skin. Measured: the chain is then the
   Assets page's (page > main panel > section.view-page > the cards) on the kids-series project (paper) and the Greek-skinned project (glass). */
html body .view-page.np-page > .shots-panel.np-panel,
html body .view-page.np-page > .shots-panel.np-panel.glass,
html body #app .view-page.np-page > .shots-panel.np-panel.glass {   /* #app: the paper skins fill the panel through an #app rule */
  background: none;
  background-color: transparent;
  box-shadow: none;
  backdrop-filter: none;
  -webkit-backdrop-filter: none;
  border-color: transparent;
}
html body .view-page.np-page > .shots-panel.np-panel::before,
html body .view-page.np-page > .shots-panel.np-panel::after { content: none; }
.np-head { flex: none; min-width: 0; }
/* THE ASSETS PAGE'S PLACES (measured on Princesses at 2268x1987, Hugo: "the tabs and the cards sit further in"): the
   tab row starts at the page panel's padding corner (the Assets .vp-tabs: no inset, 32px tall), 14px below it the
   scroller (the panel's own 14px gap) with the Assets .vp-scroll's 14px top padding and 14px top fade, and the cards
   reach the panel's padding edge on both sides. The inner Shots panel adds no inset of its own. */
html body .view-page.np-page > .shots-panel.np-panel { padding: 0; gap: 14px; overflow: visible; }   /* visible: it paints nothing, and its clip at 280..2228 cut the cards' shadows that the scroller below now has room for (the page panel still clips at its own edge) */
.np-panel > .shots-header.np-head { padding: 0; height: 32px; }
.np-tabs { min-width: 0; max-width: 100%; overflow-x: auto; overflow-y: hidden; scrollbar-width: none; flex-wrap: nowrap; }
.np-tabs::-webkit-scrollbar { display: none; }
.np-tabs .tab { flex: none; white-space: nowrap; }

.np-scroll {
  flex: 1 1 auto;
  display: flex;
  flex-direction: column;
  min-width: 0;
  min-height: 0;
  overflow-y: auto;
  overflow-x: hidden;
  /* 20px of room on each side (the page panel's own padding) taken back by the margin: the cards stay put and their
     shadows are not cut by the scroller's edge */
  padding: 14px 20px 8px;
  margin: 0 -20px;
  mask-image: linear-gradient(180deg, transparent 0px, #000 14px);
  -webkit-mask-image: linear-gradient(180deg, transparent 0px, #000 14px);
}
.np-note {
  flex: none;
  margin: 6px 0;
  padding: 10px 14px;
  font-size: var(--fs-13);
  color: var(--ink);
  background: var(--sep-card-fill);
  border-left: 3px solid var(--warn);
  border-radius: var(--r-sm);
}
.np-empty { flex: none; font-size: var(--fs-13); color: var(--ink-muted); padding: 10px 6px; }
.np-none { font-size: var(--fs-12); color: var(--ink-muted); }

/* ── a section (one asset category) ── */
.np-sec { flex: none; display: flex; flex-direction: column; border-top: 1px solid var(--card-border); }
.np-sec:first-of-type { border-top: 0; }
.np-sec-head {
  flex: none;
  height: 48px;
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 0;
  border: 0;
  background: transparent;
  color: var(--ink);
  cursor: pointer;
  text-align: left;
  min-width: 0;
}
.np-sec-chev { flex: none; color: var(--ink-muted); transition: transform var(--dur-2) ease; }
.np-sec.is-open .np-sec-chev { transform: rotate(90deg); }
.np-sec-label { font-size: var(--fs-14); font-weight: var(--fw-bold); letter-spacing: var(--track-12); text-transform: uppercase; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-sec-n {
  min-width: 26px;
  height: 20px;
  padding: 0 7px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: var(--r-pill);
  font-size: var(--fs-11-5);
  font-weight: var(--fw-bold);
  font-variant-numeric: tabular-nums;
  color: var(--ink);
  background: var(--sep-card-fill);
  border: 1px solid var(--card-border);
}
.np-sec-sub { font-size: var(--fs-12); color: var(--ink-muted); white-space: nowrap; }

/* justified rows: each card grows in proportion to its picture's ratio (the inline flex), so every card of a row has
   the same height and every picture fills its box; the ::after filler keeps the last row at its base size */
.np-grid { display: flex; flex-wrap: wrap; gap: 18px; padding: 0 0 22px; }
.np-grid::after { content: ""; flex: 1000 1 0px; }

/* ── a card = the Assets page's character card (.character-card.glass.interactive-card + .character-thumb +
   .character-body, views-pages.css / views-extras.css / the skins); only its thumb ratio (inline, the picture's own)
   and its width in the justified row are set here ── */
.character-card.np-card { min-width: 0; }
.character-card.np-card .character-thumb.np-card-thumb { aspect-ratio: auto; }
.character-card.np-card .np-card-img { object-fit: cover; object-position: center; }
.character-card.np-card.is-discarded .np-card-img { opacity: 0.35; }
.np-card-count {
  position: absolute;
  top: 8px;
  right: 8px;
  z-index: 1;
  min-width: 24px;
  height: 22px;
  padding: 0 7px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: var(--r-pill);
  font-size: var(--fs-11-5);
  font-weight: var(--fw-bold);
  font-variant-numeric: tabular-nums;
  color: var(--ink-cream-3);
  background: color-mix(in srgb, var(--shade-6) 78%, transparent);
}

/* states, one colour each */
.np-state { font-size: var(--fs-12); font-weight: var(--fw-semi); color: var(--ink-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-state--wip { color: var(--warn); }
.np-state--good, .np-state--promoted, .np-state--card { color: var(--ok); }
.np-state--discarded { color: var(--danger); }

/* ── Promote / Good / Discard ── */
.np-actions { display: grid; grid-template-columns: repeat(3, 96px); gap: 8px; }
.np-btn {
  height: 32px;
  padding: 0 8px;
  font-size: var(--fs-12-5);
  font-weight: var(--fw-semi);
  color: var(--ink);
  background: var(--input-bg);
  border: 1px solid var(--input-border);
  border-radius: var(--r-xs);
  cursor: pointer;
  white-space: nowrap;
}
.np-btn:disabled { opacity: 0.45; cursor: default; }
.np-btn--promote:not(:disabled) { background: var(--cta-bg); color: var(--cta-ink); border-color: var(--cta-bg); }
.np-btn--good.is-on { background: color-mix(in srgb, var(--ok) 22%, var(--input-bg)); border-color: var(--ok); }
.np-btn--discard:not(:disabled):hover { border-color: var(--danger); color: var(--danger); }
/* 3 Nov 2026 — Hugo: "when I promoted one, i need to see the Promote button highlighted with a gold border" */
.np-btn--promote.is-on, .np-btn--promote.is-on:disabled {
  opacity: 1; color: var(--ink); background: color-mix(in srgb, var(--gold) 16%, var(--input-bg));
  border: 1px solid var(--gold); box-shadow: inset 0 0 0 1px var(--gold);
}
/* 3 Nov 2026 — cards picked with Shift / Ctrl-click, and the bar that acts on them (fixed, so nothing below moves) */
.np-card.is-selected { outline: 3px solid var(--gold); outline-offset: 2px; }
.np-bulk {
  position: fixed; left: 50%; bottom: 24px; transform: translateX(-50%); z-index: var(--z-dropdown);
  display: flex; align-items: center; gap: 10px; height: 52px; padding: 0 14px; box-sizing: border-box;
  border-radius: var(--r-sm); background: var(--panel-raised); border: 1px solid var(--input-border); box-shadow: var(--shadow-card);
}
.np-bulk .np-btn { width: 96px; }
.np-bulk-n { min-width: 72px; font-size: var(--fs-12-5); font-weight: var(--fw-bold); color: var(--ink); }
.np-bulk-hint { min-width: 150px; font-size: var(--fs-11); color: var(--ink-muted); }
/* the viewer's redo row for an In focus card (fixed height: the picture box never jumps) */
.np-vw-redo { flex: none; display: flex; align-items: center; gap: 8px; height: 40px; margin-top: 10px; }
.np-vw-redo-text {
  flex: 1 1 auto; min-width: 0; height: 32px; box-sizing: border-box; padding: 0 10px;
  border: 1px solid var(--input-border); border-radius: var(--r-xs); background: var(--input-bg); color: var(--ink);
  font-family: var(--font-body); font-size: var(--fs-12-5);
}
.np-vw-redo-text:focus { outline: none; border-color: var(--leaf); }
.np-vw-redo-line { flex: none; width: 150px; overflow: hidden; white-space: nowrap; text-overflow: ellipsis; font-size: var(--fs-11); color: var(--ink-muted); }
.np-vw-redo-line.is-err { color: var(--danger); }
.np-vw-redo .np-btn { flex: none; }
/* In focus: the assets of a group with no new picture, on one line */
.np-fc-none { padding: 0 0 14px; font-size: var(--fs-12); color: var(--ink-muted); }

/* ── the viewer: the shot window's own card (.modal-card.modal-card--shot.glass: opaque in every skin) that hugs the
   picture; the picture's box is set inline from its pixel size (1:1, scaled down only to fit the window) ── */
.modal-backdrop.np-vw-backdrop { z-index: var(--z-modal); padding: 22px; }
.modal-backdrop .modal-card.modal-card--shot.np-vw {
  max-width: none;
  max-height: none;
  height: auto;
  overflow: hidden;
  padding: 14px 16px 12px;
  gap: 10px;
  align-items: center;
}
/* the glass skins paint the shot window as a see-through gradient: under it, the page colour, so nothing shows through */
body[data-skin-family="glass"] .modal-backdrop .modal-card.modal-card--shot.np-vw { background-color: var(--bg); }
.np-vw > * { align-self: stretch; }
.np-vw-head { flex: none; height: 44px; display: flex; align-items: center; gap: 16px; min-width: 0; }
.np-vw-titles { flex: 1 1 auto; min-width: 0; }
.np-vw-name { font-size: var(--fs-17); font-weight: var(--fw-bold); color: var(--ink); line-height: 24px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-vw-sub { font-size: var(--fs-12); color: var(--ink-muted); line-height: 18px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-vw-count { flex: none; min-width: 64px; text-align: right; font-size: var(--fs-14); font-weight: var(--fw-bold); font-variant-numeric: tabular-nums; color: var(--ink); }
.modal-close-btn.np-vw-close { position: static; flex: none; width: 34px; height: 34px; }
.np-vw > .np-vw-stage { align-self: center; flex: none; }
/* the picture's corners: the window's large-card shape (--r-card 14px inside the window's --r-lg 20px), not a chip's 6px */
.np-vw-stage { position: relative; overflow: hidden; border-radius: var(--r-card); background: var(--asset-matte, var(--panel-raised)); }
.np-vw-img { display: block; user-select: none; -webkit-user-drag: none; image-rendering: auto; }
.np-vw-stage.is-zoomed .np-vw-img { cursor: grab; }
.np-vw-stage.is-zoomed .np-vw-img:active { cursor: grabbing; }
.np-vw-img.is-discarded { opacity: 0.4; }
/* 1 Nov 2026 — the NEXT picture loads and decodes here, unseen and out of the flow; the shown picture and its box swap to
   it in one render once it is ready (never the previous picture stretched into the new box) */
.np-vw-img--next { position: absolute; left: 0; top: 0; visibility: hidden; pointer-events: none; }
/* the model that made the picture, next to its file name in the caption */
.np-vw-model { color: var(--ink); font-weight: var(--fw-semi); }
.np-vw-stage .wz-reset { z-index: 3; }
/* the action row, right under the picture: previous · state + Promote / Good / Discard · next */
.np-vw-bar { flex: none; height: 48px; display: flex; align-items: center; justify-content: space-between; gap: 14px; }
.np-vw-bar-mid { display: flex; align-items: center; gap: 14px; }
.np-vw-err { font-size: var(--fs-12); font-weight: var(--fw-semi); color: var(--danger); white-space: nowrap; }
.modal-nav-btn.np-vw-step { position: static; transform: none; width: 44px; height: 36px; flex: none; }
.np-vw-strip { flex: none; height: 86px; display: flex; align-items: center; gap: 8px; overflow-x: auto; overflow-y: hidden; scrollbar-width: thin; padding: 2px 2px 4px; }
.np-vw-thumb {
  flex: none;
  height: 72px;
  padding: 0;
  border: 2px solid transparent;
  border-radius: var(--r-xs);
  overflow: hidden;
  background: var(--panel-raised);
  cursor: pointer;
  opacity: 0.72;
  transition: opacity var(--dur-2) ease, border-color var(--dur-2) ease;
}
.np-vw-thumb img { display: block; width: 100%; height: 100%; object-fit: cover; }
.np-vw-thumb:hover { opacity: 1; }
.np-vw-thumb.is-on { border-color: var(--status-accent); opacity: 1; }
.np-vw-thumb.is-discarded img { opacity: 0.35; }

/* ── IN FOCUS (2 Nov 2026, src/NewPicturesPage.jsx NewPicturesFocus): the review list at the top of the selected tab.
   The final shape (2 Nov, evening): one block per film, inside it one group per civilisation, each a grid of the Assets
   page's OWN asset cards (.props-grid > .prop-card: cover, name, status pill, one line). Nothing is added under a card,
   so it is exactly the Assets card's size: its marks ("N new" / Done, "Redo asked", "Needs a hero") sit ON the cover.
   The redo request + Done live in a fixed panel beside the open asset window. Heads and lines have fixed heights (no
   shift while pictures load or a button is pressed). ── */
.np-focus { flex: none; display: flex; flex-direction: column; gap: 10px; padding: 0 0 22px; margin: 0 0 6px; border-bottom: 2px solid var(--card-border); }
.np-fc-top { flex: none; height: 40px; display: flex; align-items: center; gap: 14px; min-width: 0; }
.np-fc-heading { font-size: var(--fs-18); font-weight: var(--fw-bold); letter-spacing: var(--track-12); text-transform: uppercase; color: var(--ink); }
.np-fc-left { flex: none; font-size: var(--fs-12-5); font-weight: var(--fw-semi); font-variant-numeric: tabular-nums; color: var(--ink-muted); white-space: nowrap; }
.np-fc-err { flex: 1 1 auto; min-width: 0; font-size: var(--fs-12-5); font-weight: var(--fw-semi); color: var(--danger); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-fc-group { flex: none; height: 24px; display: flex; align-items: flex-end; font-size: var(--fs-12); font-weight: var(--fw-bold); letter-spacing: var(--track-12); text-transform: uppercase; color: var(--ink-muted); }
.np-fc-block { flex: none; display: flex; flex-direction: column; border: 1px solid var(--card-border); border-radius: var(--r-md); background: var(--sep-card-fill); }
.np-fc-head {
  flex: none; height: 48px; display: flex; align-items: center; gap: 10px; min-width: 0;
  padding: 0 14px; border: 0; background: transparent; color: var(--ink); cursor: pointer; text-align: left;
}
.np-fc-block.is-open .np-sec-chev { transform: rotate(90deg); }
.np-fc-title { flex: none; font-size: var(--fs-14); font-weight: var(--fw-bold); white-space: nowrap; }
.np-fc-why { flex: 1 1 auto; min-width: 0; font-size: var(--fs-12-5); color: var(--ink-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-fc-rows { display: flex; flex-direction: column; gap: 6px; padding: 0 14px 14px; }
/* one civilisation of the film: a fixed head line, then its cards */
.np-fc-civ { display: flex; flex-direction: column; gap: 8px; }
.np-fc-civ-head { flex: none; height: 30px; display: flex; align-items: flex-end; gap: 8px; border-bottom: 1px solid var(--card-border); padding-bottom: 6px; }
.np-fc-civ-name { font-size: var(--fs-13); font-weight: var(--fw-bold); letter-spacing: var(--track-12); text-transform: uppercase; color: var(--ink); white-space: nowrap; }
.np-fc-civ-n { font-size: var(--fs-12); font-weight: var(--fw-semi); font-variant-numeric: tabular-nums; color: var(--ink-muted); }
.np-fcc.is-noopen { cursor: default; }
.np-fcc.is-on { border-color: var(--status-accent); }
/* the main mark on the cover: the versions waiting for him, or the decision taken */
.np-fcc-new {
  position: absolute; top: 10px; left: 10px; z-index: 1;
  height: 24px; padding: 0 10px; border-radius: var(--r-pill);
  background: var(--cta-bg); color: var(--cta-ink);
  font-size: var(--fs-12); font-weight: var(--fw-bold); line-height: 24px; white-space: nowrap;
}
.np-fcc-new.is-done { background: var(--ok); color: var(--ink-on-dark); }
/* the flags at the cover's foot: a redo request waits for Claude, the card has no clean hero yet */
.np-fcc-flags { position: absolute; left: 10px; bottom: 10px; z-index: 1; display: flex; flex-wrap: wrap; gap: 6px; max-width: calc(100% - 20px); }
.np-fcc-flag {
  flex: none; height: 22px; padding: 0 9px; border-radius: var(--r-pill);
  font-size: var(--fs-11-5); font-weight: var(--fw-bold); line-height: 22px; white-space: nowrap;
}
.np-fcc-flag--redo { background: var(--warn); color: var(--ink-on-dark); }
.np-fcc-flag--hero { background: var(--danger); color: var(--ink-on-dark); }
/* the panel under the open asset window (the window is centred and at most 1100 px tall: ~440 px free below it at
   2268x1987; a landscape sheet makes it as wide as the screen, so nothing fits beside it). One row: the card + Done,
   the redo request box, Save / Clear. Every line has a fixed height, so saving or clearing never moves it. */
.np-fcp {
  position: fixed; z-index: var(--z-modal); left: 50%; bottom: 28px; transform: translateX(-50%);
  width: min(1320px, calc(100vw - 64px)); height: 176px; box-sizing: border-box;
  display: grid; grid-template-columns: 300px minmax(0, 1fr) 170px; gap: 18px; padding: 16px 18px;
  border: 1px solid var(--card-border); border-radius: var(--r-md);
  background: var(--panel-raised); color: var(--ink); box-shadow: var(--shadow-card);
}
.np-fcp-info, .np-fcp-req, .np-fcp-act { min-width: 0; display: flex; flex-direction: column; gap: 6px; }
.np-fcp-name { flex: none; height: 24px; font-size: var(--fs-16); font-weight: var(--fw-bold); line-height: 24px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-fcp-meta { flex: none; height: 36px; font-size: var(--fs-12); line-height: 18px; color: var(--ink-muted); overflow: hidden; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; }
.np-fcp-state { flex: none; height: 24px; display: flex; align-items: center; gap: 8px; }
.np-fcp-state-word { flex: 1 1 auto; min-width: 0; font-size: var(--fs-12-5); font-weight: var(--fw-semi); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-btn.np-fcp-done { flex: none; margin-top: auto; }
.np-fcp-label { flex: none; height: 18px; font-size: var(--fs-12); font-weight: var(--fw-bold); letter-spacing: var(--track-12); text-transform: uppercase; color: var(--ink-muted); }
.np-fcp-text {
  flex: 1 1 auto; min-height: 0; resize: none; padding: 8px 12px; box-sizing: border-box;
  font: inherit; font-size: var(--fs-13); line-height: 1.45; color: var(--ink);
  background: var(--input-bg); border: 1px solid var(--input-border); border-radius: var(--r-sm);
}
.np-fcp-text:focus { outline: none; border-color: var(--status-accent); }
.np-fcp-act { justify-content: flex-end; gap: 8px; }
.np-fcp-act .np-btn { flex: none; }
.np-fcp-line { flex: none; height: 16px; font-size: var(--fs-12); line-height: 16px; color: var(--ink-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.np-fcp-line.is-err { color: var(--danger); font-weight: var(--fw-semi); }
