/*
 * shop↑lifter — backend UI
 *
 *   ┌──────────────────────────────────────┐
 *   │  internal tool · same brand · violet │
 *   │  paper · ink · a touch of violet     │
 *   │  Playfair for expressive headings    │
 *   └──────────────────────────────────────┘
 *
 * Mirrors the frontend palette (website/style.css). The existing
 * --green / --olive variables are kept as aliases pointing
 * at the new paper/ink/violet tokens so existing component rules don't
 * all need rewriting. Anything genuinely tied to status (red for fail,
 * yellow for warn) keeps its literal hex.
 */

@import url("fonts/fonts.css");

:root {
  /* canonical brand tokens (same names as the frontend) */
  --paper:        #faf7f1;
  --paper-deep:   #f3eee2;
  --paper-rule:   #d8d0bd;
  --ink:          #1d1a17;
  --ink-soft:     #4a443c;
  --ink-mute:     #7a7466;
  --accent:       #7643E5;
  --accent-soft:  #ede5f0;  /* 10% accent over paper — focus rings, hover bg */
  --accent-lift:  #baa1f2;  /* 50% accent + white — for use on dark surfaces */
  --accent-tint:  #f4eef7;  /*  5% accent over paper — subtle row hover wash */
  --red:          #b04040;
  /* ── semantic state tokens (pass / warn / fail / info) ── */
  --st-ok-bg:   #d9edd4;
  --st-ok-fg:   #285e22;
  --st-warn-bg: #fdeeda;   /* Schwer card wash — one orange warn family */
  --st-warn-fg: #b45309;   /* Schwer card text */
  --st-fail-bg: #f2d5d5;
  --st-fail-fg: #822525;
  --st-info-bg: #e3eaf4;
  --st-info-fg: #2a4a78;
  --white:        #ffffff;

  /* legacy aliases — old class rules still read these names */
  --green-dark:   var(--ink);
  --green:        var(--accent);
  --green-light:  var(--accent-soft);
  --olive:        var(--ink-mute);
  --sand:         var(--paper-rule);

  /* fonts: Inter for UI, Playfair for the expressive accents */
  --font:         'Inter', 'Helvetica Neue', Helvetica, Arial, sans-serif;
  --serif:        'Playfair Display', Georgia, 'Times New Roman', serif;
}

*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }

html { font-size: 15px; }

body {
  font-family: var(--font);
  background: var(--paper);
  color: var(--ink);
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;

  /* a very faint paper grain — same trick as the homepage,
     pure CSS, no images */
  background-image:
    radial-gradient(rgba(29, 26, 23, 0.025) 1px, transparent 1px),
    radial-gradient(rgba(29, 26, 23, 0.018) 1px, transparent 1px);
  background-size: 3px 3px, 7px 7px;
  background-position: 0 0, 1px 2px;
  background-attachment: fixed;
}

a { color: var(--accent); text-decoration: none; }
a:hover { text-decoration: underline; }

/* ── header ── */
.app-header {
  background: rgba(250, 247, 241, 0.92);
  backdrop-filter: saturate(140%) blur(6px);
  border-bottom: 1px solid var(--paper-rule);
  padding: 0.6rem 2rem;
  display: flex;
  align-items: center;
  justify-content: space-between;
  position: sticky;
  top: 0;
  z-index: 30;
}

/* SVG wordmark from the homepage — shop + violet arrow + lifter */
.app-logo {
  display: inline-flex;
  align-items: center;
  text-decoration: none;
  height: 32px;
}
.app-logo img,
.app-logo .app-logo-svg { display: block; height: 32px; width: auto; }
.app-logo:hover { text-decoration: none; }

/* ── sticky-bar context cluster (assessment) ──
   Sits next to the logo; margin-right: auto absorbs the free space so
   the nav stays right-aligned. Hidden until .is-visible (toggled by an
   IntersectionObserver once the header card scrolls away). */
.hdr-ctx {
  display: flex;
  align-items: baseline;
  gap: 0.5rem;
  min-width: 0;
  margin-left: 1.25rem;
  margin-right: auto;
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.18s ease;
}
.hdr-ctx.is-visible { opacity: 1; pointer-events: auto; }
.hdr-ctx__name {
  font-weight: 600;
  font-size: 0.9rem;
  color: var(--ink);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 16rem;
}
.hdr-ctx__sep { color: var(--ink-mute); }
.hdr-ctx__shop {
  font-size: 0.875rem;
  color: var(--accent);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 18rem;
}
@media (max-width: 900px) { .hdr-ctx { display: none; } }

.app-nav { display: flex; align-items: center; gap: 1.25rem; }
.app-nav a { color: var(--ink-soft); font-size: 0.875rem; }
.app-nav a:hover { color: var(--ink); text-decoration: none; }

.app-logout { display: inline-flex; align-items: center; gap: 0.4rem; }
.app-logout svg { display: block; }

/* ── main ── */
.app-main { max-width: 1100px; margin: 0 auto; padding: 2rem; }

/* ── build stamp ──
   Tiny footer note showing when the running image was built. Helps
   answer "did the redeploy actually land?" without shelling into the
   container. Centred, very low-contrast — informational, not decor. */
.app-build-stamp {
  max-width: 1100px;
  margin: 0 auto;
  padding: 1rem 2rem 1.5rem;
  font-family: ui-monospace, 'SF Mono', Menlo, Consolas, monospace;
  font-size: 0.7rem;
  color: var(--ink-mute);
  text-align: center;
  opacity: 0.55;
}
.app-build-stamp a { color: inherit; }

/* footer "git sync" — repairs a diverged customers repo (commit →
   pull --rebase → push). Form styled to sit inline in the stamp line;
   button dressed as a link so the footer stays one quiet row. */
.gs-form { display: inline; }
.gs-btn {
  background: none;
  border: none;
  padding: 0;
  font: inherit;
  color: inherit;
  text-decoration: underline;
  cursor: pointer;
}
.gs-btn:hover { color: var(--accent); }

/* ── git-sync result page ── */
.gs-wrap {
  max-width: 780px;
  margin: 0 auto;
  padding: 2rem 2rem 3rem;
}
.gs-title { font-size: 1.6rem; margin: 0 0 1rem; }
.gs-status { font-weight: 600; }
.gs-status--ok   { color: #285e22; }
.gs-status--fail { color: var(--red); }
.gs-log {
  background: var(--paper-deep);
  border: 1px solid var(--paper-rule);
  border-radius: 6px;
  padding: 0.8rem 1rem;
  font-size: 0.78rem;
  overflow-x: auto;
  white-space: pre-wrap;
}

/* ── changelog (internal, passkey-gated) ── */
.cl-wrap {
  max-width: 780px;
  margin: 0 auto;
  padding: 2rem 2rem 3rem;
}
.cl-title { font-size: 1.6rem; margin: 0 0 0.15rem; }
.cl-note { font-size: 0.8rem; color: var(--ink-mute); margin: 0 0 2rem; }
.cl-version {
  padding-top: 1.4rem;
  margin-top: 1.4rem;
  border-top: 1px solid var(--paper-rule);
}
.cl-version:first-of-type { border-top: none; margin-top: 0; padding-top: 0; }
.cl-ver { display: flex; align-items: baseline; gap: 0.7rem; margin: 0 0 0.5rem; }
.cl-num {
  font-size: 1.15rem;
  font-weight: 600;
  color: var(--accent);
  font-variant-numeric: tabular-nums;
}
.cl-date { font-size: 0.8rem; color: var(--ink-mute); }
.cl-sec {
  font-size: 0.72rem;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  color: var(--ink-soft);
  margin: 1rem 0 0.35rem;
}
.cl-list { margin: 0; padding-left: 1.1rem; }
.cl-list li { font-size: 0.88rem; line-height: 1.5; color: var(--ink); margin-bottom: 0.3rem; }
.cl-list a { color: var(--accent); font-family: ui-monospace, 'SF Mono', Menlo, Consolas, monospace; font-size: 0.8em; }
.cl-list code { font-family: ui-monospace, 'SF Mono', Menlo, Consolas, monospace; font-size: 0.85em; }

/* ── buttons ── */
/* Stamped feel: ink-black base, violet on hover. Same vocabulary as
   the frontend so the brand carries through into the tools UI. */
.btn {
  display: inline-block;
  padding: 0.5rem 1.2rem;
  border-radius: 2px;          /* deliberately almost-square */
  font-family: var(--font);
  font-size: 0.85rem;
  font-weight: 600;
  letter-spacing: 0.01em;
  border: 2px solid transparent;
  cursor: pointer;
  transition: background 0.18s, color 0.18s, border-color 0.18s, transform 0.12s;
  text-decoration: none;
}
.btn:hover { transform: translateY(-1px); text-decoration: none; }

.btn-primary {
  background: var(--accent);
  color: var(--paper);
  border-color: var(--accent);
}
.btn-primary:hover { background: #4a3bbf; border-color: #4a3bbf; }

.btn-outline {
  background: transparent;
  color: var(--accent);
  border-color: var(--accent);
}
.btn-outline:hover { background: var(--accent); color: var(--paper); }

.btn-sm { padding: 0.3rem 0.8rem; font-size: 0.78rem; }
.btn-nav {
  background: var(--accent-soft);
  color: var(--accent);
  border: 1px solid transparent;
  border-radius: 2px;
  padding: 0.35rem 0.9rem;
  font-size: 0.8rem;
  font-weight: 700;
}
.btn-nav:hover { background: var(--accent); color: var(--paper); text-decoration: none; }

/* ── intake editor ── */
.intake-header {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 2rem;
  margin-bottom: 1rem;
  padding-bottom: 1.25rem;
  border-bottom: 2px solid var(--paper-rule);
}
.intake-back {
  font-size: 0.8rem;
  color: var(--ink-mute);
  text-decoration: none;
}
.intake-back:hover { color: var(--accent); text-decoration: none; }
.intake-meta h1 {
  font-family: var(--serif);
  font-style: italic;
  font-weight: 700;
  font-size: 2rem;
  color: var(--ink);
  letter-spacing: -0.01em;
  margin-top: 0.2rem;
}
.intake-sub {
  font-size: 0.85rem;
  color: var(--ink-mute);
  margin-top: 0.25rem;
}
.intake-sub a { color: var(--accent); }
.intake-actions {
  flex-shrink: 0;
  display: flex;
  gap: 0.5rem;
}

/* Pull-from-Forgejo button — secondary action, muted look so the
   primary Save button keeps the visual weight. */
.btn-pull {
  background: var(--paper-deep);
  color: var(--ink-soft);
  border-color: var(--paper-rule);
}
.btn-pull:hover { background: var(--paper); color: var(--accent); }
.btn-pull:disabled {
  background: transparent;
  color: var(--ink-mute);
  cursor: default;
  transform: none;
}
.intake-hint {
  font-size: 0.8rem;
  color: var(--ink-mute);
  margin-bottom: 0.75rem;
  font-style: italic;
}
.intake-textarea {
  width: 100%;
  min-height: 70vh;
  padding: 1rem 1.2rem;
  font-family: ui-monospace, 'SF Mono', Menlo, Consolas, monospace;
  font-size: 0.9rem;
  line-height: 1.6;
  color: var(--ink);
  background: var(--white);
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
  resize: vertical;
  /* Tab indents inside the textarea instead of moving focus —
     handy for nested markdown lists. */
  tab-size: 2;
}
.intake-textarea:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 2px rgba(118, 67, 229, 0.12);
}

/* ── intake form (per-customer rendered view) ───────── */
.intake-form { max-width: 72ch; }
.intake-section { margin: 2rem 0 1rem; }
.intake-section-heading {
  font-size: 1rem;
  font-weight: 700;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--accent);
  border-bottom: 2px solid var(--accent);
  padding-bottom: 0.3em;
  margin-bottom: 1rem;
}
.intake-sub-heading {
  font-size: 0.8rem;
  font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: var(--ink-soft);
  margin: 1.2rem 0 0.5rem;
}
.intake-cb-row {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  padding: 0.35rem 0;
  border-bottom: 1px solid var(--paper-rule);
  line-height: 1.5;
}
.intake-cb-row:last-child { border-bottom: none; }
.intake-cb-toggle {
  display: flex;
  align-items: baseline;
  gap: 0.5rem;
  flex-shrink: 0;
  cursor: pointer;
}
/* force native checkbox rendering — Pico resets appearance globally */
.intake-cb-row input[type="checkbox"] {
  -webkit-appearance: checkbox !important;
  appearance: checkbox !important;
  flex-shrink: 0;
  width: 1.1rem;
  height: 1.1rem;
  accent-color: var(--accent);
  cursor: pointer;
  margin: 0;
}
.intake-cb-label { font-size: 0.9rem; }
.intake-cb-row.is-checked .intake-cb-label { color: var(--ink-mute); text-decoration: line-through; text-decoration-color: var(--paper-rule); }
.intake-note-input {
  flex: 1;
  min-width: 0;
  font-family: inherit;
  font-size: 0.8rem;
  color: var(--ink-soft);
  background: transparent;
  border: none;
  border-bottom: 1px dashed var(--paper-rule);
  padding: 0 4px;
  outline: none;
  transition: border-color 0.12s, color 0.12s;
}
.intake-note-input:focus { border-bottom-color: var(--accent); color: var(--ink); }
.intake-note-input::placeholder { font-style: italic; opacity: 0.45; }
.intake-hint { font-size: 0.78rem; color: var(--ink-mute); font-style: italic; margin: 0 0 0.2rem 1.6rem; }
.intake-indented-input { margin: 0.2rem 0 0.4rem 1.6rem; font-size: 0.85rem; }
.intake-inline-input {
  display: inline-block;
  font-family: inherit;
  font-size: 0.85rem;
  color: var(--ink);
  background: var(--white);
  border: none;
  border-bottom: 1.5px solid var(--paper-rule);
  padding: 0 4px;
  min-width: 8rem;
  outline: none;
  transition: border-color 0.12s;
}
.intake-inline-input:focus { border-bottom-color: var(--accent); }

/* ── Auftragsbestätigung gate — stamp display chrome ──────────────
   Stamp pill (background + label/date typography + ✕ button) is
   re-used by setStampToday()/clearStamp() in assessment.html which
   regenerates the innerHTML of #abStampSent / #abStampZust on save.
   The surrounding .ah__gate row + .ah__gate-stamp button live in
   the assessment-header redesign block at the bottom. */
.ab-stamp {
  display: inline-flex; align-items: center; gap: 0.35rem;
  background: #ffffff;
  border: 1px solid color-mix(in srgb, var(--accent) 20%, transparent);
  border-radius: 6px;
  padding: 0.2em 0.55em;
  font-size: 0.85rem;
}
.ab-stamp-label { font-weight: 600; color: var(--ink-soft); }
.ab-stamp-date  { font-variant-numeric: tabular-nums; color: var(--ink); }
.ab-stamp-clear {
  background: none; border: none; padding: 0;
  color: var(--ink-mute); font-size: 0.9rem; line-height: 1;
  cursor: pointer;
}
.ab-stamp-clear:hover { color: var(--red); }

/* ── Auftragsbestätigung — Copy-Paste-Werkstatt (Seitenlayout) ───────── */
.ab-page { max-width: 760px; margin: 1.5rem auto; padding: 0 1rem; }
.ab-back { font-size: 0.85rem; color: var(--accent); text-decoration: none; }
.ab-back:hover { text-decoration: underline; }
.ab-head h1 { margin: 0.5rem 0 0.3rem; }
.ab-sub { color: var(--ink-soft); font-size: 0.9rem; margin: 0 0 1.2rem; }
.ab-flag {
  display: inline-block;
  font-size: 0.72rem; font-weight: 700; letter-spacing: 0.04em;
  padding: 0.1em 0.55em; border-radius: 2px;
  text-transform: uppercase;
}
.ab-flag-b2c { background: var(--accent-soft); color: var(--accent); border: 1px solid var(--accent); }
.ab-flag-b2b { background: var(--paper-deep); color: var(--ink-soft); border: 1px solid var(--paper-rule); }
.ab-row {
  display: grid; grid-template-columns: 80px 1fr auto; gap: 0.6rem;
  align-items: center; margin-bottom: 0.6rem;
}
.ab-label { font-size: 0.78rem; font-weight: 600; color: var(--ink-soft); }
.ab-input {
  font-family: inherit; font-size: 0.9rem;
  padding: 0.4rem 0.6rem;
  border: 1px solid var(--paper-rule); border-radius: 3px;
  background: var(--paper);
}
.ab-body-wrap { margin-top: 1rem; }
.ab-body-head {
  display: flex; justify-content: space-between; align-items: center;
  margin-bottom: 0.4rem;
}
.ab-body-actions { display: flex; gap: 0.5rem; }
.ab-body {
  width: 100%; box-sizing: border-box;
  font-family: 'SF Mono', Menlo, Consolas, monospace;
  font-size: 0.85rem; line-height: 1.55;
  padding: 0.8rem 1rem;
  border: 1px solid var(--paper-rule); border-radius: 4px;
  background: var(--paper);
  resize: vertical;
}
.ab-warn {
  margin: 1rem 0; padding: 0.6rem 0.9rem;
  background: #fff3cd; color: #856404;
  border: 1px solid #ffe69c; border-radius: 3px;
  font-size: 0.85rem;
}
.ab-foot { margin-top: 1.5rem; color: var(--ink-soft); font-size: 0.85rem; }

/* Save button: muted when clean, violet-accent when changes are pending.
   The dirty state borrows the accent-soft fill from the frontend's
   call-to-action tokens so unsaved work is obvious without being loud. */
.btn-save {
  background: var(--paper-deep);
  color: var(--ink-soft);
  border-color: var(--paper-rule);
}
.btn-save:hover { background: var(--paper); }
.btn-save:disabled {
  background: transparent;
  color: var(--ink-mute);
  border-color: var(--paper-rule);
  cursor: default;
  transform: none;
}
.btn-save:disabled:hover { transform: none; }
.btn-save-dirty {
  background: var(--accent-soft);
  color: var(--accent);
  border-color: var(--accent);
}
.btn-save-dirty:hover { background: var(--accent); color: var(--paper); }

/* Save button inserted into the nav row on the assessment page via
   the `nav_extras` Jinja block. Sized smaller than the inline Save
   button so it fits next to the nav links without dominating the bar. */
.save-nav {
  padding: 0.32rem 0.85rem;
  font-size: 0.82rem;
}

/* ── page header ── */
.page-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 1.5rem;
  padding-bottom: 1rem;
  border-bottom: 2px solid var(--sand);
}
.page-header h1 .dash__count {
  font-family: var(--font);
  font-style: normal;
  font-weight: 400;
  font-size: 0.95rem;
  color: var(--ink-mute);
  margin-left: 0.4rem;
  vertical-align: middle;
}
.page-header h1 {
  font-family: var(--serif);
  font-style: italic;
  font-weight: 700;
  font-size: 2rem;
  color: var(--ink);
  letter-spacing: -0.01em;
}

/* ══════════════════════════════════════════════════════════════
 *  Dashboard — Kunden list ("Listenzeile")
 *  ────────────────────────────────────────────────────────────
 *   ┌──── 220 ────┬──── flex 1 ────┬──── 132 ────┐
 *   │   thumb     │     main       │  status·⋮   │
 *   │ screenshot  │ name·id·url    │   ──┐       │
 *   │ (or empty)  │ notes·chips    │   donut     │
 *   └─────────────┴────────────────┴─────────────┘
 *
 *  The row is a <div>; a transparent <a class="row__link"> overlay
 *  catches clicks via pointer-events routing (so the kebab button
 *  can sit inside the row without auto-closing the anchor — a
 *  <button> inside <a> is invalid HTML and breaks the layout).
 * ══════════════════════════════════════════════════════════════ */

.rows { list-style: none; padding: 0; margin: 0; display: flex; flex-direction: column; gap: 0.75rem; }
.rows > li { list-style: none; }

.row {
  display: grid;
  grid-template-columns: 220px minmax(0, 1fr) 132px;
  grid-template-areas: "thumb main aside";
  gap: 1.25rem;
  background: var(--white);
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  box-shadow: 0 2px 10px rgba(29, 26, 23, 0.06);
  padding: 0.9rem 1rem;
  position: relative;
  align-items: stretch;
  transition: border-color .14s, background .14s, box-shadow .14s;
}
.row:hover {
  border-color: var(--accent-lift);
  background: var(--accent-tint);
  box-shadow: 0 2px 10px -8px rgba(118, 67, 229, .35);
}

/* overlay link sits behind everything via DOM-order paint; content
 * cells re-enable pointer-events only on shop URL so clicks elsewhere
 * fall through and navigate to the assessment page. */
.row__link {
  position: absolute;
  inset: 0;
  border-radius: 12px;
  text-decoration: none;
}
.row__link:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}
.row__thumb,
.row__main,
.row__aside {
  position: relative;
  pointer-events: none;
}
.row .menu,
.row .kebab,
.row .menu__list,
.row .menu__item,
.row a.row__url,
.row a.row__techcheck-cta {
  pointer-events: auto;
}

/* ── thumb (post-consent screenshot, cropped to top-of-fold) ── */
.row__thumb {
  grid-area: thumb;
  width: 220px;
  height: 124px;
  overflow: hidden;
  border-radius: 8px;
  border: 1px solid var(--paper-rule);
  background: var(--paper-deep);
  align-self: center;
}
.row__thumb img {
  display: block;
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: top center;
}
.row__thumb--empty {
  display: flex; align-items: center; justify-content: center;
  background:
    repeating-linear-gradient(
      135deg,
      var(--paper-deep) 0 12px,
      var(--paper) 12px 24px
    );
}
.row__thumb-caption {
  font-size: 0.68rem;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--ink-mute);
  text-align: center;
}

/* ── main (centre column) ── */
.row__main {
  grid-area: main;
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 0.35rem;
  min-width: 0;
  padding: 0.1rem 0;
}
.row__title {
  display: flex;
  align-items: baseline;
  gap: 0.6rem;
  flex-wrap: wrap;
}
.row__name {
  font-family: var(--serif);
  font-style: italic;
  font-weight: 700;
  font-size: 1.65rem;
  letter-spacing: -0.01em;
  color: var(--ink);
}
.row__id {
  font-family: ui-monospace, 'SF Mono', Menlo, monospace;
  font-size: 0.78rem;
  color: var(--ink-soft);
}
.row__date {
  font-size: 0.78rem;
  color: var(--ink-mute);
}
.row__url {
  font-size: 0.92rem;
  color: var(--ink-soft);
  align-self: flex-start;
  max-width: 100%;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  text-decoration: underline;
  text-decoration-color: var(--paper-rule);
  cursor: pointer;
  transition: color .14s, text-decoration-color .14s;
}
.row__url:hover {
  color: var(--accent);
  text-decoration-color: var(--accent);
}
.row__note {
  font-size: 0.85rem;
  font-style: italic;
  color: var(--ink-mute);
  line-height: 1.45;
  max-width: 60ch;
}
.row__chips {
  display: flex;
  gap: 0.4rem;
  flex-wrap: wrap;
  margin-top: 0.15rem;
}

/* ── signal chips (platform, broken-link counts, …) ──
   sized like the assessment cockpit's .ck-chip; max-width + normal
   wrapping keep long labels (tech↑scan CTA) inside the card on
   narrow screens instead of overflowing the border */
.chip {
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
  padding: 0.2rem 0.55rem;
  border-radius: 999px;
  font-size: 0.78rem;
  letter-spacing: 0.01em;
  border: 1px solid transparent;
  max-width: 100%;
  min-width: 0;
}
.chip--neutral { background: var(--paper-deep); color: var(--ink-soft); border-color: var(--paper-rule); }

/* ── aside (right column: status pill · kebab · score donut) ── */
.row__aside {
  grid-area: aside;
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  justify-content: space-between;
  gap: 0.5rem;
  min-width: 0;
}
.row__top {
  display: flex;
  align-items: center;
  gap: 0.3rem;
}
/* dashboard score = signed index + compact bonus/malus axis */
.row__score { width: 128px; display: flex; flex-direction: column; align-items: stretch; gap: 0.15rem; }
.row__idx { font-size: 1.15rem; font-weight: 700; line-height: 1; text-align: right; font-variant-numeric: tabular-nums; color: var(--ink); }
.row__idx--neg { color: var(--st-fail-fg); }
.row__idx--neutral { color: var(--st-warn-fg); }
.row__idx--pos { color: var(--st-ok-fg); }
.row__idx--empty { color: var(--ink-mute); font-weight: 400; }

/* ── status pill (phase-bucket coloured, read-only) ── */
.pill {
  font-size: 0.7rem;
  font-weight: 600;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  padding: 0.28rem 0.55rem;
  border-radius: 3px;
  white-space: nowrap;
  border: 1px solid transparent;
}
.pill--lead     { background: var(--paper-deep); color: var(--ink-mute); border-color: var(--paper-rule); }
.pill--paid     { background: var(--accent-tint); color: var(--accent); border-color: var(--accent-soft); }
.pill--progress { background: var(--accent); color: var(--white); border-color: var(--accent); }
.pill--done     { background: var(--accent-soft); color: var(--accent); border-color: var(--accent-soft); }
.pill--closed   { background: var(--paper-rule); color: var(--ink-soft); border-color: var(--paper-rule); }
.pill--failed   { background: #f6dada; color: var(--red); border-color: #e9bcbc; }

/* ── kebab + dropdown menu ── */
.menu {
  position: relative;
  display: inline-flex;
}
.kebab {
  background: transparent;
  border: 0;
  font-size: 1.2rem;
  line-height: 1;
  cursor: pointer;
  color: var(--ink-mute);
  padding: 0.15rem 0.4rem;
  border-radius: 3px;
}
.kebab:hover { background: var(--paper-deep); color: var(--ink); }
.menu.is-open .kebab { background: var(--paper-deep); color: var(--ink); }

.menu__list {
  position: absolute;
  top: calc(100% + 4px);
  right: 0;
  z-index: 50;
  min-width: 200px;
  background: var(--white);
  border: 1px solid var(--paper-rule);
  border-radius: 4px;
  box-shadow: 0 8px 24px -10px rgba(29, 26, 23, .22);
  padding: 0.3rem 0;
  display: none;
}
.menu.is-open .menu__list { display: block; }

.menu__item {
  display: block;
  width: 100%;
  text-align: left;
  background: none;
  border: 0;
  padding: 0.45rem 0.85rem;
  font-family: inherit;
  font-size: 0.86rem;
  color: var(--ink-soft);
  text-decoration: none;
  white-space: nowrap;
  cursor: pointer;
  transition: background .1s, color .1s;
}
.menu__item:hover,
.menu__item:focus-visible {
  background: var(--accent-tint);
  color: var(--ink);
  outline: none;
}
.menu__item--accent { color: var(--accent); font-weight: 500; }
.menu__item--accent:hover { background: var(--accent-soft); color: var(--accent); }
.menu__item--danger { color: var(--red); }
.menu__item--danger:hover { background: #fbeaea; color: var(--red); }

.menu__sep {
  border: 0;
  border-top: 1px solid var(--paper-rule);
  margin: 0.3rem 0;
}

/* Score is now the bonus/malus axis (.sax / .row__score), not a donut. */

/* ── state mods ── */
.row--closed { opacity: 0.7; }
.row--closed:hover { opacity: 1; }
.row--lead .row__main { color: var(--ink-soft); }

/* ── responsive: single column below 760px (house breakpoint) ──
 *
 *   ┌─────────────────────────┐
 *   │ ███ screenshot ████████ │   full-width hero
 *   ├─────────────────────────┤
 *   │ KSC  lead_2026_178      │
 *   │ angelegt · url · chips  │
 *   │ ┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈ │
 *   │ PILL          ⋮   ◍96%  │   aside as footer row
 *   └─────────────────────────┘
 */
@media (max-width: 760px) {
  .row {
    grid-template-columns: minmax(0, 1fr);
    grid-template-areas:
      "thumb"
      "main"
      "aside";
    row-gap: 0.75rem;
  }
  .row__thumb {
    width: 100%;
    height: auto;
    aspect-ratio: 2 / 1;
    align-self: auto;
  }
  .row__aside {
    flex-direction: row;
    align-items: center;
    justify-content: space-between;
    padding-top: 0.6rem;
    border-top: 1px dashed var(--paper-rule);
  }
  .row__score { width: 108px; }
  .row__name { font-size: 1.35rem; }
}

/* .cc-tool-form is preserved as a passthrough wrapper class in the
   redesigned tools strip (assessment.html) — runTechProfile() and
   runBrokenLinks() locate their inputs via btn.closest('.cc-tool-form').
   All visible styling now lives under .tool__* further down. */

/* ── pagination ── */
.pagination {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 1.25rem;
  margin: 2rem 0 1rem;
}
.pagination__btn {
  display: inline-block;
  padding: 0.35rem 0.9rem;
  border-radius: 2px;
  background: var(--accent-soft);
  color: var(--accent);
  font-size: 0.82rem;
  font-weight: 700;
  text-decoration: none;
  border: 1px solid transparent;
  transition: background 0.15s, color 0.15s;
}
.pagination__btn:hover { background: var(--accent); color: var(--paper); text-decoration: none; }
.pagination__btn--disabled {
  background: transparent;
  color: var(--ink-mute);
  cursor: default;
  pointer-events: none;
}
.pagination__info {
  font-size: 0.82rem;
  color: var(--ink-soft);
  white-space: nowrap;
}

/* ── empty state ── */
.empty-state { text-align: center; padding: 4rem 0; color: var(--ink-soft); }
.empty-state .btn { margin-top: 1rem; }

/* ── form card ── */
.form-card {
  max-width: 680px;
  background: var(--white);
  border: 1px solid var(--sand);
  border-radius: 4px;
  padding: 2rem;
}
.form-row { margin-bottom: 1.25rem; }

label {
  display: block;
  font-size: 0.75rem;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.05em;
  color: var(--ink-soft);
  margin-bottom: 0.35rem;
}
input:not([type="checkbox"]):not([type="radio"]), select, textarea {
  width: 100%;
  padding: 0.55rem 0.75rem;
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
  font-family: var(--font);
  font-size: 0.9rem;
  color: var(--ink);
  background: var(--white);
  appearance: none;
  -webkit-appearance: none;
  transition: border-color 0.12s, box-shadow 0.12s;
}
input[type="checkbox"], input[type="radio"] { accent-color: var(--accent); cursor: pointer; }
input:not([type="checkbox"]):not([type="radio"]):focus, select:focus, textarea:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 2px rgba(118, 67, 229, 0.12);
}
textarea { resize: vertical; }

/* Native select caret is gone via appearance:none — paint a violet
   chevron ourselves so it actually *looks* like a dropdown. The SVG
   is inlined to avoid a second request. */
select {
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 8'><path d='M1 1.5 L6 6.5 L11 1.5' fill='none' stroke='%237643E5' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'/></svg>");
  background-repeat: no-repeat;
  background-position: right 0.6rem center;
  background-size: 10px 7px;
  padding-right: 1.8rem;
  cursor: pointer;
}

.form-actions { display: flex; gap: 0.75rem; margin-top: 1.5rem; }

/* assessment header / score / shop-url / notes — replaced by the
   .ah / .ah__* / .donut block at the bottom of this file. */

/* ── criteria — native <details> accordion ──
   Wrapped in the same white-card chrome the tools strip and .ah header
   carry, so the interview blends into the redesigned top instead of
   sitting raw on the paper background. */
.assessment-body {
  background: #ffffff;
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  padding: 0.5rem 1.5rem;
  margin: 0 0 1rem;
}
.criteria-category {
  margin-bottom: 0.5rem;
  border-bottom: 1px solid var(--paper-rule);
}
.criteria-category:last-child { border-bottom: none; }

/* The <summary> is the clickable category header. Big Playfair italic
   in violet so it reads like the cover h1/h2 — same brand vocabulary
   the rest of the UI carries. Default-closed so a long catalog doesn't
   dump everything on the screen at once. */
.category-title {
  font-family: var(--serif);
  font-style: italic;
  font-weight: 700;
  font-size: 1.6rem;
  color: var(--accent);
  letter-spacing: -0.01em;
  padding: 0.9rem 0;
  cursor: pointer;
  list-style: none;
  display: flex;
  align-items: center;
  gap: 0.6rem;
  transition: color 0.15s;
}
.category-title:hover { color: var(--ink); }
/* Hide the native disclosure triangle (different per browser); paint
   our own ▸ so the rotation animation is consistent. */
.category-title::-webkit-details-marker { display: none; }
.category-title::marker { content: ''; }
.category-title::before {
  content: "▸";
  display: inline-block;
  font-size: 1rem;
  color: var(--accent);
  transition: transform 0.18s;
  /* normalize the caret's baseline so it sits on the cap-line of
     the Playfair italic letters next to it */
  transform-origin: 50% 55%;
}
.criteria-category[open] > .category-title::before {
  transform: rotate(90deg);
}

/* Per-category progress: a small colored dot + "rated / total" count
   sitting on the summary line. Red = nothing rated, yellow = partial
   (these auto-open via [open] on the <details>), green = all done. */
.cat-status-dot {
  display: inline-block;
  width: 0.7rem;
  height: 0.7rem;
  border-radius: 50%;
  flex: 0 0 auto;
}
.cat-status-red    { background: #c44545; }
.cat-status-yellow { background: #e0a92b; }
.cat-status-green  { background: #3a9b4a; }
.cat-progress {
  margin-left: auto;
  font-family: var(--font);
  font-style: normal;
  font-weight: 500;
  font-size: 0.85rem;
  color: var(--ink-soft);
  letter-spacing: 0;
}

.criterion {
  padding: 0.8rem 0;
  border-bottom: 1px solid var(--sand);
}
.criterion:last-child { border-bottom: none; }

.criterion-header {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  margin-bottom: 0.35rem;
}
.criterion-meta { display: flex; align-items: center; gap: 0.5rem; }
.criterion-id { font-family: monospace; font-size: 0.72rem; color: #aaa; }

.severity-badge {
  font-size: 0.65rem;
  font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  padding: 0.1rem 0.45rem;
  border-radius: 2px;
}
.severity-high   { background: #f2d5d5; color: #822525; }
.severity-medium { background: #fbe6c5; color: #7a4a10; }
.severity-low    { background: #f5e9b8; color: #6b5a10; }

.criterion-title { font-size: 0.9rem; font-weight: 600; color: var(--ink); }
.criterion-text  { font-size: 0.82rem; color: var(--ink-soft); margin-top: 0.15rem; }

.criterion-toggle {
  display: flex;
  gap: 0.4rem;
  margin: 0.5rem 0;
}
.toggle-btn {
  flex: 1 1 0;
  min-height: 44px;
  padding: 0.4rem 0.5rem;
  font-size: 0.82rem;
  font-weight: 600;
  border: 1px solid var(--sand);
  border-radius: 3px;
  background: var(--white);
  color: var(--ink-soft);
  cursor: pointer;
  text-align: center;
  transition: background 0.1s, color 0.1s, border-color 0.1s;
}
.toggle-btn:hover { border-color: var(--green-light); background: var(--paper-deep); }
.toggle-btn.active { background: var(--green); color: var(--white); border-color: var(--green); }
.toggle-fail.active { background: var(--red); border-color: var(--red); }
.toggle-clear.active { background: var(--sand); color: var(--ink-soft); border-color: var(--sand); }

.criterion-note {
  width: 100%;
  margin-top: 0.5rem;
  padding: 0.4rem 0.6rem;
  font-size: 0.82rem;
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
  font-family: var(--font);
  color: var(--ink);
  background: var(--paper-deep);
  resize: vertical;
}
.criterion-note:focus {
  outline: none;
  border-color: var(--green);
}

/* ── Quick-Win Wirkung/Aufwand chips + per-finding controls ── */
.wirkung-chip, .aufwand-chip {
  font-size: 0.62rem;
  font-weight: 700;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  padding: 0.1rem 0.4rem;
  border-radius: 2px;
  white-space: nowrap;
}
.wirkung-hoch   { background: var(--accent-soft); color: var(--accent); }
.wirkung-mittel { background: var(--accent-tint); color: var(--ink-soft); }
.wirkung-gering { background: #eceae2; color: #6e6857; }
.aufwand-gering { background: #d9edd4; color: #285e22; }
.aufwand-mittel { background: #fbe6c5; color: #7a4a10; }
.aufwand-hoch   { background: #f2d5d5; color: #822525; }

/* per-finding control row — only shown when the finding is a FAIL */
.qw-controls { display: none; }
.criterion.is-fail .qw-controls {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 0.4rem 0.6rem;
  margin-top: 0.5rem;
  padding: 0.45rem 0.6rem;
  background: var(--paper-deep);
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
}
.qw-label {
  font-size: 0.62rem;
  font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: var(--ink-mute);
}
.aufwand-toggle { display: inline-flex; gap: 0.25rem; }
.auf-btn {
  min-height: 32px;
  padding: 0.2rem 0.5rem;
  font-size: 0.72rem;
  font-weight: 600;
  border: 1px solid var(--sand);
  border-radius: 3px;
  background: var(--white);
  color: var(--ink-soft);
  cursor: pointer;
}
.auf-btn:hover  { border-color: var(--accent); }
.auf-btn.active { background: var(--accent); color: var(--white); border-color: var(--accent); }

.qwpin {
  margin-left: auto;
  min-width: 32px;
  min-height: 32px;
  font-size: 1rem;
  line-height: 1;
  border: 1px solid var(--sand);
  border-radius: 3px;
  background: var(--white);
  color: #999;
  cursor: pointer;
}
.qwpin.st-pin  { color: var(--accent); border-color: var(--accent); }
.qwpin.st-excl { color: var(--red);    border-color: var(--red); }

/* ── Quick-Wins preview panel ── */
.qw-panel {
  margin: 1.5rem 0;
  padding: 1rem 1.2rem;
  background: var(--accent-tint);
  border: 1px solid #d8cbe8;
  border-left: 3px solid var(--accent);
  border-radius: 4px;
}
.qw-panel-title { font-size: 1rem; margin: 0 0 0.6rem; color: var(--ink); }
.qw-panel-hint  { font-size: 0.72rem; font-weight: 400; color: var(--ink-mute); }
.qw-list {
  margin: 0;
  padding-left: 1.4rem;
  display: flex;
  flex-direction: column;
  gap: 0.4rem;
}
.qw-item { font-size: 0.82rem; display: flex; align-items: center; flex-wrap: wrap; gap: 0.4rem; }
.qw-item-title { font-weight: 600; color: var(--accent); text-decoration: none; }
.qw-item-title:hover { text-decoration: underline; }
.qw-item-cat { font-size: 0.7rem; color: var(--ink-mute); }
.qw-pinned-badge { font-size: 0.62rem; font-weight: 700; color: var(--accent); }
.qw-panel-empty { font-size: 0.82rem; color: var(--ink-soft); margin: 0; }

/* ── criterion media ── */
.criterion-media {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem;
  align-items: center;
  margin-top: 0.6rem;
  padding: 0.3rem;
  border: 1.5px dashed transparent;
  border-radius: 4px;
  transition: border-color 0.12s, background 0.12s;
}
.criterion-media.media-dragover {
  border-color: var(--accent);
  background: var(--accent-tint);
}
.media-thumb {
  position: relative;
  display: inline-block;
}
.media-thumb img {
  width: 72px;
  height: 72px;
  object-fit: cover;
  border-radius: 3px;
  border: 1px solid var(--paper-rule);
  display: block;
}
.media-del {
  position: absolute;
  top: -6px;
  right: -6px;
  width: 18px;
  height: 18px;
  line-height: 16px;
  padding: 0;
  font-size: 0.8rem;
  border: none;
  border-radius: 50%;
  background: #8b2020;
  color: #fff;
  cursor: pointer;
}
.media-add {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  height: 72px;
  min-width: 100px;
  padding: 0 1rem;
  font-size: 0.78rem;
  color: var(--olive);
  border: 1px dashed var(--paper-rule);
  border-radius: 3px;
  cursor: pointer;
}
.media-add:hover {
  border-color: var(--green);
  color: var(--green);
}


/* ── tech profile panel (assessment page) ──────────────────────────
   Each panel is a <details> accordion (default closed). The
   <summary class="tech-panel-header"> carries the title, date, and a
   one-line digest. Chevron rotates 90deg via the [open] selector.
   .interpret-panel uses #interpretPanel which the suggestion-jump JS
   opens before scrolling a target row into view. */
.tech-panel {
  background: var(--white);
  border: 1px solid var(--sand);
  border-radius: 4px;
  margin-bottom: 0.75rem;
  font-size: 0.82rem;
}
.tech-panel > summary {
  list-style: none;
  cursor: pointer;
  padding: 0.6rem 1.25rem;
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.55rem;
  border-radius: 4px;
}
.tech-panel > summary::-webkit-details-marker { display: none; }
.tech-panel > summary:hover { background: var(--paper-deep); }
.tech-panel[open] > summary {
  border-bottom: 1px solid var(--paper-rule);
  border-radius: 4px 4px 0 0;
}
.tech-panel-header {
  font-size: 0.72rem;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--olive);
}
/* Children that were styled INSIDE a div header now sit as inline-flex
   items inside the summary — neutralize their margin-left tweaks. */
.tech-panel-header .tech-panel-date,
.tech-panel-header .tp-egress { margin-left: 0; }
.tech-panel-chevron {
  display: inline-block;
  color: var(--ink-mute);
  font-size: 0.7rem;
  transition: transform 120ms ease-out;
  margin-right: 0.1rem;
}
.tech-panel[open] > summary .tech-panel-chevron { transform: rotate(90deg); }
.tech-panel-digest {
  font-weight: 400;
  text-transform: none;
  letter-spacing: 0;
  color: var(--ink-soft);
  font-size: 0.78rem;
  margin-left: auto;
  text-align: right;
}
.tech-panel-digest strong { color: var(--ink); font-weight: 600; }
.tech-panel-digest-warn { color: var(--red); }
/* Body padding lives on each direct child of <details> except the
   summary, so we keep the original "1rem 1.25rem" padding feel
   without wrapping each panel's existing markup in an extra div. */
.tech-panel > :not(summary) {
  padding-left: 1.25rem;
  padding-right: 1.25rem;
}
.tech-panel > :nth-last-child(1):not(summary) {
  padding-bottom: 1rem;
}
.tech-panel[open] > summary + * {
  padding-top: 0.8rem;
}
.tech-panel-date {
  font-weight: 400;
  color: #aaa;
  margin-left: 0.75rem;
  text-transform: none;
  letter-spacing: 0;
}
.tp-egress {
  font-weight: 400;
  color: var(--ink-mute);
  margin-left: 0.75rem;
  text-transform: none;
  letter-spacing: 0;
  font-size: 0.75rem;
}
.tp-egress code {
  font-family: monospace;
  color: var(--ink-soft);
  background: var(--accent-tint);
  padding: 0 0.25rem;
  border-radius: 2px;
}
.tech-panel-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
  gap: 0.5rem 1.5rem;
  margin-bottom: 0.75rem;
}
/* min-width: 0 — grid items otherwise grow to the min-content width of a
   long unbreakable asset URL and shove the whole grid sideways */
.tp-item { display: flex; flex-direction: column; gap: 0.1rem; min-width: 0; }
.tp-label {
  font-size: 0.68rem;
  font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: #aaa;
}
/* Favicon coverage grid — canonical sizes (16/32/180/192/512). Each cell
   shows either the actual declared raster, the SVG scaled by the browser,
   or an N/A marker. Cells render at a uniform display size; the label
   below reports the source so a 16-px raster vs. a 16-px SVG render look
   the same on-page but the operator can still see what's actually
   provided. */
.tp-favicon-sub { margin-top: 0.75rem; }
.tp-favicon-grid {
  display: flex;
  flex-wrap: wrap;
  gap: 0.6rem;
  margin: 0.4rem 0 0.5rem;
}
.tp-fav-cell {
  flex: 0 0 80px;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 0.2rem;
  padding: 0.5rem 0.3rem;
  background: var(--paper-deep);
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
  text-align: center;
}
.tp-fav-imgbox {
  width: 48px;
  height: 48px;
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--paper);
  border: 1px solid var(--paper-rule);
  border-radius: 2px;
}
.tp-fav-preview {
  max-width: 40px;
  max-height: 40px;
  object-fit: contain;
}
.tp-fav-na-mark {
  font-family: monospace;
  font-size: 0.7rem;
  color: #aaa;
}
.tp-fav-cap {
  font-family: monospace;
  font-size: 0.72rem;
  color: var(--ink-soft);
}
.tp-fav-src { font-size: 0.7rem; }
.tp-fav-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 0.35rem;
  align-items: center;
  font-size: 0.8rem;
}
.tp-sec-headers { display: flex; flex-wrap: wrap; gap: 0.35rem; margin-top: 0.5rem; }
.tp-sec-badge {
  font-size: 0.7rem;
  padding: 0.1rem 0.5rem;
  border-radius: 999px;
  font-family: monospace;
}
.tp-sec-ok      { background: var(--st-ok-bg);   color: var(--st-ok-fg); }
.tp-sec-missing { background: var(--st-fail-bg); color: var(--st-fail-fg); }
.tp-sec-warn    { background: var(--st-warn-bg); color: var(--st-warn-fg); }

/* ── Tech-Profil Pass B (LLM suggestion panel) ── */
.interpret-panel {
  border-left: 3px solid var(--accent);
}
.interpret-controls {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  margin-bottom: 0.5rem;
}
.interpret-cost {
  opacity: 0.7;
  font-weight: 400;
}
.interpret-status {
  font-size: 0.78rem;
  color: var(--ink-mute);
}
.interpret-disabled {
  font-size: 0.78rem;
  font-style: italic;
  color: var(--ink-mute);
}
.interpret-error {
  margin: 0.5rem 0;
  padding: 0.5rem 0.75rem;
  background: #f5d5d5;
  color: #8b2020;
  border-radius: 3px;
  font-size: 0.8rem;
}
.interpret-empty {
  margin: 0.5rem 0 0;
  font-size: 0.82rem;
  color: var(--ink-mute);
  font-style: italic;
}
.interpret-list {
  list-style: none;
  padding: 0;
  margin: 0.75rem 0 0;
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
}
.interpret-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding: 0.55rem 0.75rem;
  background: var(--paper-deep);
  border: 1px solid var(--sand);
  border-radius: 3px;
}
.interpret-row-meta {
  display: flex;
  align-items: baseline;
  gap: 0.6rem;
  flex: 1;
  min-width: 0;
}
.interpret-cid {
  font-family: monospace;
  font-size: 0.78rem;
  color: var(--accent);
  font-weight: 700;
  white-space: nowrap;
  text-decoration: none;
  border-bottom: 1px dotted transparent;
}
a.interpret-cid:hover {
  border-bottom-color: var(--accent);
}
.interpret-rationale {
  font-size: 0.85rem;
  color: var(--ink);
}
.interpret-row-actions {
  display: flex;
  gap: 0.35rem;
  flex-shrink: 0;
}
.btn-accept {
  background: transparent;
  color: #1a5c1a;
  border-color: #b8d8b8;
}
.btn-accept:hover { background: #1a5c1a; color: var(--paper); border-color: #1a5c1a; }
.btn-dismiss {
  background: transparent;
  color: var(--ink-mute);
  border-color: var(--paper-rule);
}
.btn-dismiss:hover { background: var(--paper); color: var(--ink); }

/* ── auto-check ↔ Pass B source badges ─────────────────────────────
   rule = deterministic profiler observation; llm = Claude judgement.
   Visual distinction kept lightweight so the inbox doesn't look busy. */
.interpret-badge {
  font-size: 0.7rem;
  font-weight: 600;
  padding: 0.1rem 0.45rem;
  border-radius: 2px;
  white-space: nowrap;
  letter-spacing: 0.02em;
}
.interpret-badge-rule {
  background: var(--accent-tint);
  color: var(--accent);
  border: 1px solid var(--accent-soft);
}
.interpret-badge-llm {
  background: var(--paper);
  color: var(--ink-soft);
  border: 1px dashed var(--paper-rule);
}

.interpret-bulk {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  margin: 0.5rem 0 0.25rem;
}
.interpret-bulk-status {
  font-size: 0.8rem;
  color: var(--ink-mute);
}

/* Dim "manuell prüfen" list for rule-checks that returned `unknown`.
   No accept button — only a small × to clear once handled by hand. */
.interpret-unknown {
  margin-top: 0.9rem;
  padding-top: 0.6rem;
  border-top: 1px dashed var(--paper-rule);
  opacity: 0.78;
}
.interpret-unknown-header {
  font-size: 0.78rem;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  color: var(--ink-mute);
  margin-bottom: 0.4rem;
}
.interpret-unknown-list {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 0.3rem;
}
.interpret-unknown-row {
  display: flex;
  align-items: baseline;
  gap: 0.6rem;
  padding: 0.35rem 0.55rem;
  font-size: 0.82rem;
  color: var(--ink-soft);
  font-style: italic;
  background: transparent;
}
.interpret-unknown-row .btn {
  margin-left: auto;
  font-style: normal;
}

/* Green "Auto-bestanden" list — same row layout as unknowns, but
   informational only (no action buttons). Tinted green so it's
   visually distinct from the suggestion-fail rows above. */
.interpret-passes {
  margin-top: 0.9rem;
  padding-top: 0.6rem;
  border-top: 1px dashed var(--paper-rule);
}
.interpret-passes-header {
  font-size: 0.78rem;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  color: #1a5c1a;
  margin-bottom: 0.4rem;
}
.interpret-passes-list {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 0.3rem;
}
.interpret-pass-row {
  display: flex;
  align-items: baseline;
  gap: 0.6rem;
  padding: 0.35rem 0.55rem;
  font-size: 0.82rem;
  color: var(--ink-soft);
  background: rgba(26, 92, 26, 0.04);
  border-left: 2px solid rgba(26, 92, 26, 0.25);
}

/* Mobile: stack meta / actions vertically. Without this the flex row
   squeezes the rationale to ~one-word width and the action buttons end
   up vertically centered against the tall wrapped column, overlapping
   the text mid-row. */
@media (max-width: 720px) {
  .interpret-row {
    flex-direction: column;
    align-items: stretch;
    gap: 0.5rem;
  }
  .interpret-row-meta {
    flex-wrap: wrap;
    row-gap: 0.25rem;
  }
  .interpret-rationale {
    flex-basis: 100%;
  }
  .interpret-row-actions {
    justify-content: flex-end;
  }
  .interpret-unknown-row,
  .interpret-pass-row {
    flex-wrap: wrap;
    row-gap: 0.25rem;
  }
  .interpret-unknown-row .interpret-rationale,
  .interpret-pass-row .interpret-rationale {
    flex-basis: 100%;
  }
}

/* Briefly highlight a criterion that just got marked-as-fail by an
   accepted suggestion, so the eye can follow the scroll-into-view. */
@keyframes criterion-flash {
  0%   { background: rgba(118, 67, 229, 0.18); }
  100% { background: transparent; }
}
.criterion-just-set {
  animation: criterion-flash 2s ease-out;
}
.interpret-row-flash {
  animation: criterion-flash 2s ease-out;
}

/* Pill on the criterion row pointing back to the open suggestion. The
   suggest variant uses the brand accent (actionable); the unknown variant
   stays neutral (it's only a "please verify by hand" nudge). */
.criterion-pending {
  display: inline-flex;
  align-items: center;
  gap: 0.3rem;
  font-size: 0.7rem;
  font-weight: 600;
  padding: 0.1rem 0.45rem;
  border-radius: 999px;
  white-space: nowrap;
  letter-spacing: 0.02em;
  text-decoration: none;
  margin-left: 0.4rem;
  cursor: pointer;
  transition: background 120ms ease;
}
.criterion-pending-suggest {
  background: var(--accent-tint);
  color: var(--accent);
  border: 1px solid var(--accent-soft);
}
.criterion-pending-suggest:hover {
  background: var(--accent-soft);
}
.criterion-pending-unknown {
  background: var(--paper);
  color: var(--ink-mute);
  border: 1px dashed var(--paper-rule);
}
.criterion-pending-unknown:hover {
  color: var(--ink);
  border-color: var(--ink-mute);
}
/* The pass pill reuses the .btn-accept green so it visually echoes the
   ✓ Übernehmen action — same color = "rule already verified this". */
.criterion-pending-pass {
  background: transparent;
  color: #1a5c1a;
  border: 1px solid #b8d8b8;
}
.criterion-pending-pass:hover {
  background: rgba(26, 92, 26, 0.08);
}

/* ── tech-panel subsections (cookies / hosts / tls / hygiene / shots) ── */
.tp-sub {
  margin-top: 1rem;
  padding-top: 0.75rem;
  border-top: 1px solid var(--sand);
}
.tp-sub-title {
  font-size: 0.68rem;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--olive);
  margin-bottom: 0.5rem;
}
.tp-faint { color: var(--ink-mute); font-size: 0.78rem; }
.tp-callout {
  background: #fdf6e3;
  border-left: 3px solid #d8b568;
  padding: 0.4rem 0.6rem;
  font-size: 0.78rem;
  margin: 0.5rem 0;
}
.tp-warn {
  background: #fdeeda;
  border-left: 3px solid #e07b1a;
  padding: 0.4rem 0.6rem;
  font-size: 0.78rem;
  margin: 0.5rem 0;
  color: #5a3a08;
}
/* ── legal-005 Datenschutz service checklist ── */
.dse-checklist {
  background: var(--paper-deep);
  border-left: 3px solid var(--accent);
  padding: 0.5rem 0.7rem;
  margin: 0.5rem 0;
  border-radius: 0 4px 4px 0;
}
.dse-url { overflow-wrap: anywhere; word-break: break-all; }
.dse-cl-head { font-size: 0.78rem; color: var(--ink-soft); margin-bottom: 0.4rem; }
.dse-verdict {
  display: inline-block;
  font-size: 0.68rem;
  font-weight: 700;
  padding: 0.1rem 0.5rem;
  border-radius: 999px;
  margin-left: 0.3rem;
  white-space: nowrap;
}
.dse-verdict--ok   { background: var(--st-ok-bg);   color: var(--st-ok-fg); }
.dse-verdict--warn { background: var(--st-warn-bg); color: var(--st-warn-fg); }
.dse-cl-note { font-size: 0.73rem; color: var(--red); margin: 0.1rem 0 0.4rem; }
.dse-cl-list { list-style: none; margin: 0; padding: 0; }
.dse-cl-row {
  display: flex;
  align-items: baseline;
  flex-wrap: wrap;
  gap: 0.4rem;
  padding: 0.22rem 0;
  border-top: 1px solid var(--paper-rule);
}
.dse-cl-row:first-child { border-top: none; }
.dse-cl-label { display: flex; align-items: baseline; gap: 0.4rem; cursor: pointer; }
.dse-cl-cb { margin: 0; flex-shrink: 0; transform: translateY(1px); }
.dse-svc { font-weight: 600; color: var(--ink); font-size: 0.8rem; }
.dse-pill {
  font-size: 0.64rem;
  font-weight: 700;
  padding: 0.06rem 0.45rem;
  border-radius: 999px;
  white-space: nowrap;
}
.dse-pill--ok   { background: var(--st-ok-bg);   color: var(--st-ok-fg); }
.dse-pill--warn { background: var(--st-warn-bg); color: var(--st-warn-fg); }
.dse-pill--fail { background: var(--st-fail-bg); color: var(--st-fail-fg); }
.dse-ev {
  font-size: 0.68rem;
  color: var(--ink-mute);
  font-style: italic;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 30ch;
}
/* false detection: row greyed + struck through, excluded from verdict/report */
.dse-cl-row--removed .dse-cl-label,
.dse-cl-row--removed .dse-pill,
.dse-cl-row--removed .dse-ev { opacity: 0.45; }
.dse-cl-row--removed .dse-svc { text-decoration: line-through; }
.dse-cl-rm {
  margin-left: auto;
  border: none;
  background: none;
  color: var(--ink-mute);
  font-size: 0.8rem;
  line-height: 1;
  padding: 0 0.2rem;
  cursor: pointer;
  flex-shrink: 0;
}
.dse-cl-rm:hover { color: var(--red); }
.tp-info {
  background: #e8f0fb;
  border-left: 3px solid #5b82c5;
  padding: 0.4rem 0.6rem;
  font-size: 0.78rem;
  margin: 0.5rem 0;
  color: #1e3a6e;
}
.tp-mini-list {
  list-style: none;
  margin: 0.25rem 0 0;
  padding: 0;
  font-size: 0.78rem;
}
.tp-mini-list li { padding: 0.1rem 0; word-break: break-all; }
.tp-sev {
  display: inline-block;
  font-size: 0.66rem;
  font-weight: 700;
  font-family: monospace;
  padding: 0.05rem 0.4rem;
  border-radius: 2px;
  text-transform: uppercase;
  letter-spacing: 0.04em;
  margin-right: 0.4rem;
}
.tp-sev-info { background: var(--st-info-bg); color: var(--st-info-fg); }
.tp-sev-warn { background: var(--st-warn-bg); color: var(--st-warn-fg); }
.tp-sev-high { background: var(--st-fail-bg); color: var(--st-fail-fg); }

/* Web Vitals verdict markers — tiny inline labels next to each metric. */
.wv-good, .wv-warn, .wv-bad {
  font-style: normal;
  font-size: 0.7rem;
  font-weight: 600;
  margin-left: 0.4rem;
  padding: 0.05rem 0.35rem;
  border-radius: 2px;
}
.wv-good { background: var(--st-ok-bg);   color: var(--st-ok-fg); }
.wv-warn { background: var(--st-warn-bg); color: var(--st-warn-fg); }
.wv-bad  { background: var(--st-fail-bg); color: var(--st-fail-fg); }

/* ── Web Vitals gauge (wvg-*) ─────────────────────────────────
   Three-zone bar: inactive 55% opacity, active zone full + border.
   wvg-row spans the full tech-panel-grid width (grid-column:1/-1).
───────────────────────────────────────────────────────────────── */
.wvg-row {
  grid-column: 1 / -1;
  display: flex;
  align-items: flex-start;
  gap: 1rem;
  margin-bottom: 0.6rem;
}
.wvg-note { grid-column: 1 / -1; font-size: 0.7rem; margin-top: -0.2rem; margin-bottom: 0.4rem; }
.wvg-label {
  min-width: 7rem;
  flex-shrink: 0;
  padding-top: 0.42rem;
  font-size: 0.68rem;
  font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: #aaa;
}
/* ── zone bar (.zbar) — ONE segmented three-zone bar, shared by the
   web-vitals gauge (.wvg-*, green→red) and the score axis (.sax-*,
   red→green). They are the same widget: 3 flex segments, rounded ends, an
   active-zone underline, a pointer stage below. Only colour order, size and
   the overlay (threshold labels vs. zero tick) differ.

   Ends are rounded by EXPLICIT class (.zbar-end-l / .zbar-end-r on the
   physically first/last segment), never :first/:last-child — the colour
   order flips between the two bars AND both keep overlay children (threshold
   labels, zero tick) inside the bar that would otherwise steal :last-child
   and leave one end square. Radius is --zbar-r (default 5px). */
.zbar { position: relative; display: flex; }
.zbar-seg {
  flex: 1;
  min-width: 0;   /* long labels must not push a segment past its zone */
  overflow: hidden;
  display: flex;
  align-items: center;
  justify-content: center;
  font-weight: 700;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  opacity: 0.5;
}
.zbar-seg.active { opacity: 1; box-shadow: inset 0 -3px 0 currentColor; }
.zbar-end-l { border-radius: var(--zbar-r, 5px) 0 0 var(--zbar-r, 5px); }
.zbar-end-r { border-radius: 0 var(--zbar-r, 5px) var(--zbar-r, 5px) 0; }

/* web-vitals gauge — zbar in green→amber→red, taller, brighter idle */
.wvg-gauge { flex: 1; min-width: 0; }
.wvg-bar { height: 1.75rem; }
.wvg-seg { font-size: 0.6rem; opacity: 0.55; }
.wvg-ok  { background: var(--st-ok-bg);   color: var(--st-ok-fg); }
.wvg-warn {
  background: var(--st-warn-bg); color: var(--st-warn-fg);
  border-left: 1px solid rgba(0,0,0,.06);
  border-right: 1px solid rgba(0,0,0,.06);
}
.wvg-bad { background: var(--st-fail-bg); color: var(--st-fail-fg); }
.wvg-ptr-stage { position: relative; height: 1.9rem; }
.wvg-ptr {
  position: absolute;
  top: 0.2rem;
  /* left set inline from Jinja2 (pct already clamped server-side) */
  transform: translateX(-50%);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 1px;
}
.wvg-val {
  font-size: 0.65rem;
  font-weight: 700;
  color: var(--accent);
  white-space: nowrap;
}
.wvg-thresh-lbl {
  position: absolute;
  top: 0.1rem;
  font-size: 0.56rem;
  color: rgba(0,0,0,0.38);
  transform: translateX(-50%);
  white-space: nowrap;
  z-index: 1;
}
.wvg-val2 {
  font-size: 0.57rem;
  font-weight: 500;
  color: var(--ink-mute);
  white-space: nowrap;
  text-align: center;
}
.wvg-ptr-stage.wvg-has-val2 { height: 2.7rem; }

/* ── Bonus/Malus score axis ──────────────────────────────────────────
   Bipolar −100…0…+100 bar: red (Nachholbedarf) · orange (neutral, straddles
   0) · green (gut aufgestellt). Marker at (index+100)/2 %; the segments fall
   on equal thirds, so the ±33 zone thresholds line up with the borders and
   orange straddles the null. Shares the --st-* palette with the wvg gauge. */
/* score axis — the same .zbar, in red→amber→green (flipped order). Geometry,
   segment layout, rounding and active underline all come from .zbar / .zbar-seg
   / .zbar-end-*; only colour, height and the centre tick are sax-specific. */
.sax { width: 100%; }
.sax-bar { height: 1.6rem; }
.sax-seg { font-size: 0.58rem; }
.sax-neg { background: var(--st-fail-bg); color: var(--st-fail-fg); }
.sax-mid {
  background: var(--st-warn-bg); color: var(--st-warn-fg);
  border-left: 1px solid rgba(0,0,0,.06);
  border-right: 1px solid rgba(0,0,0,.06);
}
.sax-pos { background: var(--st-ok-bg); color: var(--st-ok-fg); }
/* null tick at dead centre — the "0" of the axis */
.sax-zero {
  position: absolute; top: -2px; bottom: -2px; left: 50%;
  width: 2px; margin-left: -1px;
  background: rgba(0,0,0,.30); z-index: 1;
}
.sax-ptr-stage { position: relative; height: 0.95rem; }
.sax-ptr {
  position: absolute; top: 0;
  /* left set inline; pct = (index+100)/2, clamped 1–99 */
  transform: translateX(-50%);
  display: flex; flex-direction: column; align-items: center;
}
.sax--empty .sax-seg { opacity: 0.4; }
/* compact — dashboard rows + category overview: no labels, slimmer, tighter radius */
.sax--compact .sax-bar { height: 0.72rem; --zbar-r: 4px; }
.sax--compact .sax-seg { font-size: 0; }
.sax--compact .sax-ptr-stage { height: 0.8rem; }

/* Category overview (assessment) — one axis row per assessed category. */
.catov-list { list-style: none; margin: 0.4rem 0 0; padding: 0; }
.catov-row {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 2.6rem 150px 2.6rem;
  align-items: center;
  gap: 0.6rem;
  padding: 0.3rem 0;
  border-top: 1px solid var(--paper-rule);
}
.catov-row:first-child { border-top: none; }
.catov-name {
  font-size: 0.82rem; font-weight: 600; color: var(--ink);
  text-decoration: none; overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.catov-name:hover { color: var(--accent); text-decoration: underline; }
.catov-idx { font-size: 0.85rem; font-weight: 700; text-align: right; font-variant-numeric: tabular-nums; }
.catov-idx--neg { color: var(--st-fail-fg); }
.catov-idx--neutral { color: var(--st-warn-fg); }
.catov-idx--pos { color: var(--st-ok-fg); }
.catov-tally { font-size: 0.72rem; color: var(--ink-mute); text-align: right; font-variant-numeric: tabular-nums; }
@media (max-width: 560px) {
  .catov-row { grid-template-columns: minmax(0, 1fr) 2.4rem; grid-template-areas: "name idx" "bar bar"; }
  .catov-name { grid-area: name; }
  .catov-idx  { grid-area: idx; }
  .catov-row .sax { grid-area: bar; }
  .catov-tally { display: none; }
}

/* ── weight-breakdown donut + legend ── */
/* HTTP-Anfragen headline stat — a request count is a first-order perf signal,
   so it gets a prominent badge above the vitals grid, not a buried grid cell. */
.wvg-reqs {
  display: inline-flex; align-items: center; gap: 0.55rem;
  margin: 0 0 0.7rem; padding: 0.3rem 0.8rem 0.3rem 0.65rem;
  background: var(--accent-tint); border: 1px solid var(--accent-soft);
  border-radius: 10px;
}
.wvg-reqs-num {
  font-size: 1.7rem; font-weight: 800; line-height: 1;
  color: var(--accent); font-variant-numeric: tabular-nums; letter-spacing: -0.02em;
}
.wvg-reqs-lbl { font-size: 0.82rem; font-weight: 700; color: var(--ink-soft); line-height: 1.15; }
.wvg-reqs-sub { font-size: 0.72rem; font-weight: 500; color: var(--ink-mute); }

.wvg-breakdown {
  grid-column: 1 / -1;
  display: flex;
  align-items: center;
  gap: 1.5rem;
  margin: 0.1rem 0 0.4rem;
}
.wvg-donut-svg { flex-shrink: 0; width: 120px; height: 120px; }
.wvg-legend {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-wrap: wrap;
  gap: 0.2rem 1.2rem;
}
.wvg-legend-item { display: flex; align-items: center; gap: 0.35rem; font-size: 0.75rem; }
.wvg-legend-dot { width: 8px; height: 8px; border-radius: 2px; flex-shrink: 0; }
.wvg-legend-name { color: var(--ink-soft); }
.wvg-legend-val  { color: var(--ink); font-weight: 600; white-space: nowrap; }
.wvg-breakdown-note {
  grid-column: 1 / -1;
  font-size: 0.63rem;
  color: var(--ink-mute);
  margin-bottom: 0.3rem;
}

.tp-issue-list { list-style: none; margin: 0; padding: 0; font-size: 0.78rem; }
.tp-issue {
  padding: 0.2rem 0;
  border-top: 1px solid var(--sand);
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.4rem;
}
.tp-issue:first-child { border-top: none; }
.tp-issue-hdr { font-family: monospace; color: var(--ink); }
.tp-issue-text { color: var(--ink-soft); flex: 1; min-width: 200px; }
.tp-details {
  margin: 0.5rem 0;
  font-size: 0.78rem;
}
.tp-details > summary {
  cursor: pointer;
  color: var(--olive);
  padding: 0.2rem 0;
}
.cookie-table { border-collapse: collapse; width: 100%; font-size: 0.75rem; margin: 0.4rem 0 0; }
.cookie-table th { text-align: left; font-weight: 600; color: var(--ink-soft); font-size: 0.67rem; text-transform: uppercase; letter-spacing: 0.04em; padding: 0.2rem 0.5rem; border-bottom: 1px solid var(--paper-rule); }
.cookie-table td { padding: 0.2rem 0.5rem; vertical-align: top; border-bottom: 1px solid var(--paper-rule); }
.cookie-table tr:last-child td { border-bottom: none; }
.cookie-table code { font-size: 0.72rem; }
.ct-val { font-size: 0.67rem; color: var(--ink-mute); max-width: 22ch; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; display: block; }
.ct-flags { display: flex; gap: 0.2rem; flex-wrap: wrap; }
.host-service { font-weight: 600; color: var(--ink); }
.host-raw { color: var(--ink-mute); font-size: 0.88em; }
.tp-flag {
  font-size: 0.66rem;
  font-family: monospace;
  padding: 0.05rem 0.35rem;
  border-radius: 2px;
  white-space: nowrap;
}
.tp-flag-ok { background: var(--st-ok-bg); color: var(--st-ok-fg); }
.tp-flag-off { background: var(--paper-deep); color: var(--ink-mute); }
.tp-flag-neutral { background: var(--paper-deep); color: var(--ink-soft); }
.ct-warn { color: var(--red); cursor: help; font-weight: 700; }
.ct-legend { font-size: 0.66rem; color: var(--ink-mute); margin: 0.3rem 0 0; line-height: 1.4; }
.tp-seo-text { display: block; margin-top: 0.15rem; font-size: 0.72rem; color: var(--ink-mute); overflow-wrap: break-word; }
.tp-shot-row {
  display: flex;
  flex-wrap: wrap;
  gap: 1rem;
  font-size: 0.78rem;
}
.tp-shot { flex: 1; min-width: 200px; }
.tp-shot-img {
  display: block;
  width: 100%;
  height: 380px;          /* Crop tall shop screenshots from the top
                             so the dashboard preview matches the PDF
                             ratio and doesn't sprawl to 8000+ px. */
  object-fit: cover;
  object-position: top center;
  margin-top: 0.3rem;
  border: 1px solid #d6cfb8;
  border-radius: 3px;
  background: #f5f2eb;
}

/* ── broken-links list ── */
.bl-list { list-style: none; margin: 0.25rem 0 0; padding: 0; }
.bl-row {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.6rem;
  padding: 0.25rem 0;
  border-top: 1px solid var(--sand);
  font-size: 0.78rem;
  word-break: break-all;
}
.bl-code {
  flex: none;
  font-family: monospace;
  font-size: 0.7rem;
  font-weight: 700;
  padding: 0.1rem 0.4rem;
  border-radius: 2px;
  background: var(--st-fail-bg);
  color: var(--st-fail-fg);
}
.bl-source {
  flex: 1 1 auto;
  min-width: 0;
  color: #8a8475;
  font-size: 0.72rem;
}
.bl-clean  { color: #1a5c1a; font-size: 0.82rem; margin: 0.25rem 0 0; }
/* robots.txt-disallowed but linked (blackhole/honeypot guard). Amber and
   informational — never counted as broken; the chip reads "robots" so it's
   clearly not a 4xx/5xx. These links were deliberately NOT crawled. */
.bl-robots { margin-top: 0.9rem; padding-top: 0.6rem; border-top: 1px dashed var(--sand); }
.bl-robots-head { margin: 0 0 0.15rem; font-size: 0.82rem; font-weight: 700; color: #b45309; }
.bl-robots-note { margin: 0 0 0.35rem; font-size: 0.74rem; color: #8a8475; }
.bl-code-robots { background: #fdeeda; color: #b45309; }
.bl-link {
  flex: 1 1 auto;
  min-width: 0;
  font-family: ui-monospace, 'SF Mono', Menlo, Consolas, monospace;
  font-size: 0.74rem;
  word-break: break-all;
}
.bl-link-src {
  color: #8a8475;
  font-size: 0.7rem;
  text-decoration: underline;
  text-decoration-color: transparent;
  transition: text-decoration-color .14s, color .14s;
}
.bl-link-src:hover {
  color: var(--accent);
  text-decoration-color: var(--accent);
}
/* Action buttons per broken-link row. ↻ re-checks a single URL through
   the original egress (transient WAF / 5xx retry without re-crawling).
   × dismisses permanently. Both subtle by default; light up to brand
   purple on hover. Recheck sits next to dismiss at the far right via
   margin-left: auto on the first one so the pair always anchors right. */
.bl-recheck,
.bl-dismiss {
  flex: none;
  background: transparent;
  border: 1px solid var(--paper-rule);
  border-radius: 2px;
  color: var(--ink-mute);
  cursor: pointer;
  font-size: 0.95rem;
  line-height: 1;
  padding: 0.05rem 0.4rem;
}
.bl-recheck { margin-left: auto; }
.bl-recheck:hover,
.bl-dismiss:hover {
  border-color: var(--accent);
  color: var(--accent);
  background: var(--accent-soft);
}
.bl-recheck:disabled,
.bl-dismiss:disabled { opacity: 0.5; cursor: wait; }

/* ── tech↑scan extra pages (light per-page scans) ── */
.xp-list { list-style: none; margin: 0.4rem 0 0; padding: 0; }
.xp-row {
  padding: 0.55rem 0;
  border-top: 1px solid var(--sand);
  font-size: 0.8rem;
}
.xp-head { display: flex; align-items: baseline; gap: 0.6rem; flex-wrap: wrap; }
.xp-url  { font-size: 0.72rem; color: var(--ink-soft); word-break: break-all; }
.xp-metrics {
  display: flex;
  gap: 1.1rem;
  flex-wrap: wrap;
  margin-top: 0.25rem;
  color: var(--ink-soft);
}
.xp-axe-warn { color: #8b2020; font-weight: 600; }
.xp-actions { margin-top: 0.35rem; display: flex; gap: 0.5rem; }
.xp-add {
  display: flex;
  gap: 0.5rem;
  align-items: center;
  flex-wrap: wrap;
  margin-top: 0.7rem;
}
.xp-add-label { width: 10rem; }
.xp-add-url   { flex: 1; min-width: 16rem; }

/* ── a11y violation list (axe-core output) ── */
.a11y-list { list-style: none; margin: 0.4rem 0 0; padding: 0; }
.a11y-row {
  display: grid;
  /* impact | rule id | wcag level | count | help | link */
  grid-template-columns: 5rem 9rem 6.5rem 3rem 1fr auto;
  align-items: baseline;
  gap: 0.55rem;
  padding: 0.4rem 0;
  border-top: 1px solid var(--sand);
  font-size: 0.8rem;
}
.a11y-impact {
  text-transform: uppercase;
  font-size: 0.62rem;
  font-weight: 700;
  letter-spacing: 0.08em;
  padding: 0.1rem 0.4rem;
  border-radius: 2px;
  text-align: center;
}
.a11y-critical .a11y-impact { background: #f2d5d5; color: #822525; }
.a11y-serious  .a11y-impact { background: #fbe6c5; color: #7a4a10; }
.a11y-moderate .a11y-impact { background: #f5e9b8; color: #6b5a10; }
.a11y-minor    .a11y-impact { background: #e6e3d8; color: #5f5b50; }
.a11y-id       { font-family: monospace; font-size: 0.78rem; color: var(--ink-soft); }
.a11y-wcag     { font-size: 0.68rem; color: var(--ink-mute); white-space: nowrap; }
.a11y-count    { font-weight: 600; }
.a11y-help     { color: var(--ink); }
.a11y-selectors { grid-column: 5; font-family: monospace; font-size: 0.7rem; color: #7a7466; word-break: break-all; }
.a11y-helplink { font-size: 0.72rem; color: var(--accent); white-space: nowrap; }
/* Mobile: the grid's fixed tracks (~24rem) alone exceed a phone
   viewport — the row scrolls sideways and the help text wraps one word
   per line. Reflow: meta chips share a wrapped line, help + selectors +
   screenshots take full rows. */
@media (max-width: 720px) {
  .a11y-row {
    display: flex;
    flex-wrap: wrap;
    column-gap: 0.55rem;
    row-gap: 0.3rem;
  }
  .a11y-help,
  .a11y-selectors { flex-basis: 100%; }

  /* Web Vitals gauge: the zone words (gut/verbesserbar/schlecht) overflow
     the narrow segments and collide. Colour coding carries the meaning on
     mobile — drop the words, keep the segments + threshold numbers + pointer. */
  .wvg-seg { font-size: 0; }

  /* Cookie/storage tables overflow the viewport (4 wide columns). Let them
     scroll horizontally instead of clipping the WERT column off-screen. */
  .cookie-table {
    display: block;
    width: 100%;
    overflow-x: auto;
    -webkit-overflow-scrolling: touch;
    white-space: nowrap;
  }
}
.tech-panel-error { color: var(--red); font-size: 0.85rem; margin: 0.25rem 0 0; }

/* ── boolean pill (yes/no facts in tech grid) ── */
.tp-pill {
  display: inline-block;
  font-size: 0.7rem;
  font-weight: 600;
  padding: 0.12rem 0.55rem;
  border-radius: 999px;
  letter-spacing: 0.01em;
}
.tp-pill--ok   { background: var(--st-ok-bg);   color: var(--st-ok-fg); }
.tp-pill--warn { background: var(--st-warn-bg); color: var(--st-warn-fg); }
.tp-pill--fail { background: var(--st-fail-bg); color: var(--st-fail-fg); }

/* ── TLS grade explainer table ─────────────────────────────────────────── */
.tls-grade-table {
  border-collapse: collapse;
  font-size: 0.78rem;
  margin-top: 0.6em;
  width: 100%;
}
.tls-grade-table th {
  text-align: left;
  color: var(--ink-mute);
  font-weight: 600;
  padding: 0.15em 0.5em 0.3em 0.4em;
  border-bottom: 1px solid var(--paper-rule);
}
.tls-grade-table td {
  padding: 0.3em 0.5em 0.3em 0.4em;
  vertical-align: middle;
  border-bottom: 1px solid var(--paper-rule);
}
.tls-grade-table td:first-child { padding-right: 0.75em; white-space: nowrap; }
.tls-grade-table tr.tls-grade-active td {
  background: rgba(118,67,229,0.5);
  color: #fff;
}

.tp-path {
  display: inline-block;
  font-size: 0.72rem;
  font-family: ui-monospace, 'SF Mono', Menlo, Consolas, monospace;
  background: var(--paper-deep);
  color: var(--ink-soft);
  padding: 0.05rem 0.3rem;
  border-radius: 2px;
  margin: 0.1rem 0.1rem 0 0;
  /* long asset URLs (200-char cache-buster query strings) must wrap
     inside the grid cell, not blow the layout open sideways */
  max-width: 100%;
  overflow-wrap: anywhere;
  word-break: break-all;
}

/* ── out-of-range inline hint ── */
.tp-range-warn {
  font-size: 0.7rem;
  font-style: normal;
  font-weight: 500;
  background: var(--st-warn-bg);
  color: var(--st-warn-fg);
  padding: 0.05rem 0.4rem;
  border-radius: 999px;
  margin-left: 0.2rem;
}

/* ── grouped grid sections inside tech panel ── */
.tp-grid-group { margin-bottom: 0.5rem; }
.tp-grid-group + .tp-grid-group { margin-top: 0.9rem; }
.tp-group-label {
  font-size: 0.65rem;
  font-weight: 700;
  letter-spacing: 0.07em;
  text-transform: uppercase;
  color: var(--ink-mute);
  margin-bottom: 0.4rem;
  padding-bottom: 0.2rem;
  border-bottom: 1px solid var(--paper-rule);
}

/* ── nested subsection (e.g. Reject-Parity inside Cookies) ── */
.tp-sub--nested {
  margin-top: 0.5rem;
  padding-top: 0.4rem;
  border-top: none;
  margin-left: 0.75rem;
  padding-left: 0.75rem;
  border-left: 2px solid var(--paper-rule);
}

/* ── issue list spacing when below security pill bar ── */
.tp-sec-headers + .tp-issue-list { margin-top: 0.5rem; }

/* ── expenses ── */
.recommendation-section {
  background: #ffffff;
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  padding: 1.5rem;
  margin: 1.5rem 0 0;
}
.recommendation-title {
  font-size: 0.72rem;
  font-weight: 700;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--olive);
  margin-bottom: 0.3rem;
}
.recommendation-hint {
  font-size: 0.78rem;
  color: #8a8475;
  margin-bottom: 0.8rem;
}
.recommendation-input {
  width: 100%;
  padding: 0.6rem 0.8rem;
  font-size: 0.9rem;
  line-height: 1.5;
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
  font-family: var(--font);
  color: var(--ink);
  resize: vertical;
}
.recommendation-input:focus {
  outline: none;
  border-color: var(--green);
}

.expenses-section {
  background: #ffffff;
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  padding: 1.5rem;
  margin: 1.5rem 0 0;
}
.expenses-title {
  font-size: 0.72rem;
  font-weight: 700;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--olive);
  margin-bottom: 1rem;
}
.expenses-table {
  width: 100%;
  border-collapse: collapse;
  font-size: 0.85rem;
  margin-bottom: 1rem;
}
.expenses-table th {
  text-align: left;
  padding: 0.4rem 0.6rem;
  font-size: 0.7rem;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--olive);
  border-bottom: 2px solid var(--sand);
}
.expenses-table td { padding: 0.5rem 0.6rem; border-bottom: 1px solid var(--sand); }
.expenses-table tfoot td { border-top: 2px solid var(--sand); border-bottom: none; font-weight: 700; }
.amount-cell  { text-align: right; font-variant-numeric: tabular-nums; font-family: monospace; }
.total-label  { color: var(--ink-soft); font-size: 0.82rem; }
.total-amount { font-size: 1rem; color: var(--green-dark); }
.no-expenses  { font-size: 0.85rem; color: var(--ink-soft); margin-bottom: 1rem; }

.expense-form {
  display: flex;
  gap: 0.5rem;
  flex-wrap: wrap;
  align-items: center;
  margin-top: 0.75rem;
}
.expense-form input {
  padding: 0.35rem 0.6rem;
  font-size: 0.85rem;
  border: 1px solid var(--paper-rule);
  border-radius: 3px;
  width: auto;
}
#expDate   { width: 130px; }
#expDesc   { flex: 1; min-width: 160px; }

/* ════════════════════════════════════════════════════════════════
 *  ASSESSMENT HEADER — phase strip + header card + tools strip
 *  ─────────────────────────────────────────────────────────────────
 *  Class namespace: .phase__*, .ah__*, .tool__*, .donut.
 *  Mockup + decision context: website/proposals/assessment-header/.
 * ═══════════════════════════════════════════════════════════════ */

/* ── Technik-Check status banners (status 12 / 13) ── */
.banner-info,
.banner-success {
  padding: .65rem 1.25rem;
  border-radius: 8px;
  margin: 0 0 1.25rem;
  font-size: .875rem;
}
.banner-info {
  background: var(--paper-deep);
  border: 1px solid var(--paper-rule);
  color: var(--ink-soft);
}
.banner-success {
  background: #edf7ed;
  border: 1px solid #b2d9b2;
  color: #2d5a2d;
}
.banner-success a { color: inherit; font-weight: 600; }

/* phase strip — eight-node timeline, one node per status tens block */
.phase {
  background: var(--paper-deep);
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  padding: 1.25rem 2rem 1rem;
  margin: 0 0 1.25rem;
  /* lift the strip so its sub-status popover paints above the banner +
     cockpit; the app-header (z 30) still stays above the strip */
  position: relative;
  z-index: 20;
}
.phase__track {
  list-style: none !important;
  margin: 0; padding: 0;
  display: grid;
  grid-template-columns: repeat(8, 1fr);
  position: relative;
}
/* connector runs from the centre of the first column (100%/16) to the
   centre of the last; each step advances by one column (100%/8) */
.phase__track::before {
  content: ""; position: absolute;
  left: 6.25%; right: 6.25%; top: 0.65rem; height: 2px;
  background: var(--paper-rule);
  z-index: 0;
}
.phase__track::after {
  content: ""; position: absolute;
  left: 6.25%; width: 0; top: 0.65rem; height: 2px;
  background: var(--accent-lift);
  z-index: 0;
}
.phase__track:has(.phase__step:nth-child(1).is-current)::after { width: 0; }
.phase__track:has(.phase__step:nth-child(2).is-current)::after { width: 12.5%; }
.phase__track:has(.phase__step:nth-child(3).is-current)::after { width: 25%; }
.phase__track:has(.phase__step:nth-child(4).is-current)::after { width: 37.5%; }
.phase__track:has(.phase__step:nth-child(5).is-current)::after { width: 50%; }
.phase__track:has(.phase__step:nth-child(6).is-current)::after { width: 62.5%; }
.phase__track:has(.phase__step:nth-child(7).is-current)::after { width: 75%; }
.phase__track:has(.phase__step:nth-child(8).is-current)::after { width: 87.5%; }
.phase__step {
  list-style: none !important;
  position: relative;
  display: flex; flex-direction: column; align-items: center;
  z-index: 1;
}
.phase__dot {
  width: 1.3rem; height: 1.3rem; border-radius: 50%;
  background: var(--paper-deep);
  border: 2px solid var(--paper-rule);
  transition: all 120ms ease-out;
}
.phase__num {
  margin-top: 0.5rem;
  font-size: 0.7rem; letter-spacing: 0.06em; font-weight: 600;
  color: var(--ink-mute);
}
.phase__name {
  font-size: 0.85rem; color: var(--ink-soft); margin-top: 0.1rem;
}
.phase__step.is-current .phase__dot {
  background: var(--accent); border-color: var(--accent);
  box-shadow: 0 0 0 4px var(--accent-soft);
}
.phase__step.is-current .phase__num { color: var(--accent); }
.phase__step.is-current .phase__name { color: var(--ink); }
.phase__step.is-past .phase__dot {
  background: var(--accent-lift); border-color: var(--accent-lift);
}
.phase__step.is-past .phase__num { color: var(--ink-soft); }

/* milestone as button — opens the sub-status popover */
.phase__btn {
  background: none; border: 0; padding: 0; margin: 0;
  font: inherit; cursor: pointer;
  display: flex; flex-direction: column; align-items: center;
}
.phase__btn:hover .phase__dot { border-color: var(--accent-lift); }
.phase__btn:hover .phase__name { color: var(--ink); }

/* sub-status popover — the display:flex below would override the
   [hidden] attribute's UA display:none, so restate it explicitly */
.phase__pop[hidden] { display: none; }
.phase__pop {
  position: absolute; top: calc(100% + 0.4rem); left: 50%;
  transform: translateX(-50%);
  background: var(--paper);
  border: 1px solid var(--paper-rule);
  border-radius: 10px;
  box-shadow: 0 8px 24px rgba(29, 26, 23, 0.14);
  padding: 0.35rem; z-index: 20;
  display: flex; flex-direction: column; gap: 2px;
}
.phase__step:first-child .phase__pop { left: 0; transform: none; }
.phase__step:last-child .phase__pop { left: auto; right: 0; transform: none; }
.phase__pop-item {
  background: none; border: 0; font: inherit;
  font-size: 0.85rem; text-align: left; white-space: nowrap;
  padding: 0.4rem 0.65rem; border-radius: 6px;
  color: var(--ink-soft); cursor: pointer;
}
.phase__pop-item:hover { background: var(--accent-tint); color: var(--ink); }
.phase__pop-item.is-done { color: var(--ink-mute); }
.phase__pop-item.is-done::after { content: " ✓"; color: var(--accent-lift); }
.phase__pop-item.is-current {
  background: var(--accent-soft); color: var(--accent); font-weight: 600;
}

/* failed payment inside this block (x9 statuses) — after the state
   rules above so red wins over is-current purple */
.phase__step.is-failed .phase__dot {
  background: var(--red); border-color: var(--red);
  box-shadow: 0 0 0 4px rgba(176, 64, 64, 0.15);
}
.phase__step.is-failed .phase__num { color: var(--red); }


/* assessment header card */
.ah {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 280px;
  gap: 1.25rem;
  background: #ffffff;
  border: 1px solid var(--paper-rule);
  border-radius: 14px;
  padding: 1.5rem;
  margin: 0 0 1rem;
}
.ah__identity { display: flex; align-items: center; gap: 0.4rem; }
.ah__name {
  font-size: 1.7rem; font-weight: 700; letter-spacing: -0.01em;
  color: var(--ink);
  padding: 0 0.15rem;
  border-radius: 4px;
  outline: none;
  margin: 0;
}
.ah__name:focus, .ah__name:hover { background: var(--accent-soft); }
.ah__icon-btn {
  background: transparent; border: none;
  color: var(--ink-mute);
  padding: 0.25rem 0.45rem;
  border-radius: 6px;
  font-size: 0.9rem; line-height: 1;
  cursor: pointer;
}
.ah__icon-btn:hover { color: var(--accent); background: var(--accent-soft); }

.ah__url {
  display: flex; align-items: center; gap: 0.4rem;
  margin: 0.25rem 0 0.9rem;
}
.ah__url-input {
  flex: 1 1 auto; min-width: 0;
  background: transparent;
  border: 1px solid transparent;
  border-radius: 6px;
  padding: 0.35rem 0.5rem;
  color: var(--ink-soft);
  font-size: 0.95rem;
}
.ah__url-input:hover { border-color: var(--paper-rule); }
.ah__url-input:focus {
  outline: none;
  border-color: var(--accent);
  background: #fff;
  color: var(--ink);
}
.ah__url-open {
  color: var(--ink-mute);
  font-size: 0.95rem;
  text-decoration: none;
  padding: 0.25rem 0.45rem;
  border-radius: 6px;
}
.ah__url-open:hover { color: var(--accent); background: var(--accent-soft); }

.ah__meta {
  display: flex; flex-wrap: wrap;
  gap: 0.75rem 1.25rem;
  align-items: center;
  padding-bottom: 0.9rem;
  margin-bottom: 0.9rem;
  border-bottom: 1px dashed var(--paper-rule);
}
.ah__field { display: flex; flex-direction: column; gap: 0.15rem; }
.ah__field-lbl {
  font-size: 0.7rem; letter-spacing: 0.06em;
  text-transform: uppercase; color: var(--ink-mute);
}
.ah__select {
  background: transparent;
  border: 1px solid var(--paper-rule);
  border-radius: 6px;
  padding: 0.35rem 1.6rem 0.35rem 0.55rem;
  font-size: 0.95rem;
  color: var(--ink);
  appearance: none;
  background-image:
    linear-gradient(45deg, transparent 50%, var(--ink-mute) 50%),
    linear-gradient(135deg, var(--ink-mute) 50%, transparent 50%);
  background-position: calc(100% - 1rem) 50%, calc(100% - 0.7rem) 50%;
  background-size: 5px 5px;
  background-repeat: no-repeat;
  font-family: inherit;
}
.ah__select:hover { border-color: var(--accent); color: var(--accent); }
.ah__select:focus { outline: none; border-color: var(--accent); box-shadow: 0 0 0 3px var(--accent-soft); }
.ah__intake {
  display: inline-flex; align-items: center; gap: 0.45rem;
  margin-left: auto;
  color: var(--ink-soft);
  font-size: 0.92rem;
  text-decoration: none;
}
.ah__intake:hover { color: var(--accent); text-decoration: none; }
.ah__intake-arrow { font-size: 0.78rem; opacity: 0.7; }
.ah__gate-reopen {
  font-size: 0.82rem;
  color: var(--ink-mute);
  text-decoration: none;
  padding: 0.15rem 0.5rem;
  border: 1px dashed var(--paper-rule);
  border-radius: 6px;
}
.ah__gate-reopen:hover { color: var(--accent); border-color: var(--accent); text-decoration: none; }

/* extra .chip modifiers used by the assessment header — the base .chip
   rule + .chip--neutral live further up (dashboard origin). */
.chip--mute   { background: var(--paper-deep); color: var(--ink-mute); border-color: var(--paper-rule); }
.chip--done   { background: #e8f5e9; color: #2e6b2e; border-color: #b2dfb2; }
.chip--accent { background: var(--accent-tint); color: var(--accent); border-color: var(--accent-soft); font-weight: 600; }
.chip--accent:hover { background: var(--accent-soft); }

/* AB-gate row — hides via .is-hidden when stamps complete */
.ah__gate {
  display: flex; flex-wrap: wrap;
  gap: 0.6rem 0.9rem;
  align-items: center;
  padding: 0.65rem 0.85rem;
  background: var(--accent-soft);
  border: 1px solid color-mix(in srgb, var(--accent) 15%, transparent);
  border-radius: 10px;
  margin: 0 0 0.9rem;
  font-size: 0.9rem;
}
.ah__gate.is-hidden { display: none; }
.ah__gate-toggle {
  display: inline-flex; align-items: center; gap: 0.4rem;
  color: var(--ink); cursor: pointer;
}
.ah__gate-toggle input { accent-color: var(--accent); }
.ah__gate-link { color: var(--accent); font-weight: 500; text-decoration: none; }
.ah__gate-link:hover { text-decoration: underline; }
.ah__gate-stamp {
  background: #ffffff;
  border: 1px solid color-mix(in srgb, var(--accent) 25%, transparent);
  color: var(--accent);
  padding: 0.3rem 0.7rem;
  border-radius: 6px;
  font-size: 0.85rem; font-weight: 500;
  cursor: pointer;
  font-family: inherit;
}
.ah__gate-stamp:hover { background: var(--accent); color: #fff; }
/* keep the existing .ab-stamp display chrome (used by stamp JS) — only
   the in-progress button .ab-stamp-btn was replaced by .ah__gate-stamp */

/* credentials — collapsible <details> */
.ah__creds {
  border: 1px solid var(--paper-rule);
  border-radius: 10px;
  background: var(--paper);
  margin: 0 0 0.9rem;
}
.ah__creds > summary {
  list-style: none;
  cursor: pointer;
  display: flex; align-items: baseline; gap: 0.6rem;
  padding: 0.55rem 0.85rem;
  font-size: 0.9rem; color: var(--ink-soft);
}
.ah__creds > summary::-webkit-details-marker { display: none; }
.ah__creds-icon {
  display: inline-block;
  transition: transform 120ms ease-out;
  color: var(--ink-mute);
}
.ah__creds[open] .ah__creds-icon { transform: rotate(90deg); }
.ah__creds-hint {
  color: var(--ink-mute); font-size: 0.8rem; margin-left: auto;
}
.ah__creds-list {
  display: flex; flex-direction: column;
  border-top: 1px solid var(--paper-rule);
}
.ah__cred {
  display: grid;
  grid-template-columns: 6.5rem 1fr auto;
  gap: 0.65rem;
  align-items: center;
  padding: 0.45rem 0.85rem;
  border-bottom: 1px solid color-mix(in srgb, var(--paper-rule) 50%, transparent);
}
.ah__cred:last-child { border-bottom: none; }
.ah__cred-lbl {
  font-size: 0.7rem; letter-spacing: 0.06em;
  text-transform: uppercase; color: var(--ink-mute);
}
.ah__cred-val {
  font-size: 0.88rem;
  color: var(--ink);
  background: transparent;
  border: 1px solid transparent;
  border-radius: 5px;
  padding: 0.2rem 0.4rem;
  min-width: 0;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
  font-family: 'JetBrains Mono', ui-monospace, Menlo, monospace;
}
.ah__cred-val.ah__cred-input { font-family: inherit; }
.ah__cred-val.ah__cred-link { font-family: inherit; color: var(--accent); text-decoration: none; }
.ah__cred-val.ah__cred-link:hover { text-decoration: underline; }
.ah__cred-val.ah__cred-input:hover,
.ah__cred-val.ah__cred-link:hover { border-color: var(--paper-rule); }
.ah__cred-val.ah__cred-input:focus {
  outline: none; border-color: var(--accent); background: #fff;
}
.ah__cred-copy {
  background: transparent;
  border: 1px solid var(--paper-rule);
  border-radius: 5px;
  padding: 0.2rem 0.45rem;
  color: var(--ink-mute);
  font-size: 0.85rem;
  cursor: pointer;
}
.ah__cred-copy:hover { color: var(--accent); border-color: var(--accent); }

.ah__notes {
  width: 100%;
  background: var(--paper);
  border: 1px solid var(--paper-rule);
  border-radius: 8px;
  padding: 0.55rem 0.75rem;
  color: var(--ink);
  resize: vertical;
  font-family: inherit;
  font-size: 0.95rem;
}
.ah__notes:focus { outline: none; border-color: var(--accent); box-shadow: 0 0 0 3px var(--accent-soft); }

.ah__score-sub {
  font-size: 0.78rem; color: var(--ink-mute); letter-spacing: 0.04em;
}
.ah__pdf {
  position: relative;
  margin-top: 0.4rem;
  width: 100%;
}
.ah__pdf-pop {
  position: absolute;
  right: 0; top: calc(100% + 0.45rem);
  width: 280px;
  padding: 0.5rem;
  background: #fff;
  border: 1px solid var(--paper-rule);
  border-radius: 8px;
  box-shadow: 0 8px 24px rgba(0, 0, 0, 0.12);
  opacity: 0; visibility: hidden;
  transform: translateY(-3px);
  transition: opacity 120ms, transform 120ms, visibility 120ms;
  z-index: 30;
  pointer-events: none;
  text-align: left;
}
.ah__pdf:hover .ah__pdf-pop,
.ah__pdf:focus-visible .ah__pdf-pop {
  opacity: 1; visibility: visible; transform: translateY(0);
}
.ah__pdf-pop img {
  width: 100%; height: auto; border-radius: 4px; display: block;
  border: 1px solid var(--paper-rule);
}
.ah__pdf-pop-cap, .ah__pdf-pop-hint {
  display: block; margin-top: 0.4rem;
  font-size: 0.75rem; color: var(--ink-mute); text-align: center;
}

/* post-consent shop screenshot in the right rail · click → full size */
.ah__shot {
  display: block;
  width: 100%;
  margin-top: 0.4rem;
  background: #fff;
  border: 1px solid var(--paper-rule);
  border-radius: 8px;
  overflow: hidden;
  text-decoration: none;
  transition: border-color 120ms;
}
.ah__shot:hover { border-color: var(--accent); text-decoration: none; }
.ah__shot img {
  display: block;
  width: 100%;
  height: auto;
  max-height: 220px;
  object-fit: cover;
  object-position: top center;
}
.ah__shot-cap {
  display: block;
  padding: 0.3rem 0.6rem;
  font-size: 0.72rem;
  color: var(--ink-mute);
  text-align: center;
  border-top: 1px solid var(--paper-rule);
  letter-spacing: 0.02em;
}


/* ════════════════════════════════════════════════════════════════
 *  TOOLS — four compact one-line strips
 * ═══════════════════════════════════════════════════════════════ */
ul.tools {
  list-style: none !important;
  margin: 0 0 1rem;
  padding: 0;
  background: #ffffff;
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  overflow: hidden;
}
ul.tools li.tool {
  list-style: none !important;
  display: flex;
  align-items: center;
  gap: 0.85rem;
  padding: 0.65rem 1rem;
  border-bottom: 1px solid color-mix(in srgb, var(--paper-rule) 55%, transparent);
}
ul.tools li.tool:last-child { border-bottom: none; }
.tool__label {
  flex: 0 0 8.5rem;
  font-size: 0.7rem; letter-spacing: 0.07em;
  text-transform: uppercase;
  color: var(--ink-mute);
  font-weight: 600;
}
.tool__status {
  flex: 1 1 auto; min-width: 0;
  display: inline-flex; align-items: center; flex-wrap: wrap;
  gap: 0.4rem;
  font-size: 0.85rem; color: var(--ink-soft);
}
.tool__status--pending { color: var(--ink-mute); font-style: italic; }
.tool__status--running { color: var(--accent); font-style: italic; }
@keyframes tp-spin { to { transform: rotate(360deg); } }
.tp-spinner { display: inline-block; animation: tp-spin 1.5s linear infinite; }
.tool__status--mono { font-family: 'JetBrains Mono', ui-monospace, Menlo, monospace; font-size: 0.82rem; }
.tool__check {
  display: inline-flex; align-items: center; justify-content: center;
  width: 1rem; height: 1rem;
  border-radius: 50%;
  font-size: 0.7rem; font-weight: 700; line-height: 1;
}
.tool__check.ok {
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  color: var(--accent);
}
.tool__check.warn { background: #fdf3e7; color: var(--warn, #b26a1a); }
.tool__pill {
  display: inline-flex;
  padding: 0.05rem 0.5rem;
  border-radius: 999px;
  font-size: 0.78rem; font-weight: 600;
  border: 1px solid transparent;
}
.tool__pill--ok    { background: #e8f5e9; color: #2e6b2e; border-color: #b2dfb2; }
.tool__pill--warn  { background: #fdf3e7; color: var(--warn, #b26a1a); border-color: #f0d4ab; }
.tool__pill--mute  { background: var(--paper-deep); color: var(--ink-mute); border-color: var(--paper-rule); }

.tool__actions {
  display: inline-flex; align-items: center; gap: 0.45rem;
  flex: 0 0 auto;
}
.tool__url-input {
  flex: 0 1 16rem;
  background: var(--paper);
  border: 1px solid var(--accent);
  border-radius: 6px;
  padding: 0.3rem 0.55rem;
  font-size: 0.85rem;
  display: none;
  font-family: inherit;
}
.tool.is-url-open .tool__url-input { display: inline-block; }
/* Mirror .btn .btn-sm box metrics so the pen sits flush with the run
   buttons next to it (border 2px transparent + padding 0.3/0.8 + radius 2). */
.tool__url-toggle {
  display: inline-block;
  background: transparent;
  border: 2px solid var(--paper-rule);
  border-radius: 2px;
  padding: 0.3rem 0.6rem;
  color: var(--ink-mute);
  font-size: 0.85rem;
  font-weight: 600;
  letter-spacing: 0.01em;
  line-height: 1.2;
  font-family: var(--font);
  cursor: pointer;
}
.tool__url-toggle:hover { color: var(--accent); border-color: var(--accent); }
.tool.is-url-open .tool__url-toggle { background: var(--accent-soft); border-color: var(--accent); color: var(--accent); }
.tool__vpn {
  display: inline-flex; align-items: center; gap: 0.35rem;
  font-size: 0.78rem; color: var(--ink-mute);
  white-space: nowrap; cursor: pointer;
}
.tool__vpn input { accent-color: var(--accent); }
.tool__run-status {
  font-size: 0.78rem; color: var(--ink-soft); font-style: italic;
}


/* ── mobile: stack columns ─────────────────────────────────────── */
@media (max-width: 760px) {
  .app-header { padding: 0.6rem 1rem; }
  .app-nav { gap: 0.75rem; }
  .app-nav .nav-link-collapse { display: none; }
  .app-logout-label { display: none; }

  .ah__shot img { max-height: 150px; }
  .ah__name { font-size: 1.4rem; }
  .ah__notes { min-height: 60px; }
  .phase { padding: 1rem; }
  .phase__name { display: none; }
  ul.tools li.tool { flex-wrap: wrap; gap: 0.5rem; }
  .tool__label { flex-basis: 100%; }
  .tool__status { flex-basis: 100%; }
}
#expAmount { width: 110px; }

/* ════════════════════════════════════════════════════════════════════
 *  ASSESSMENT · Cockpit + Tabs  (Concept A)
 *
 *      ┌ COCKPIT (sticky) ─────────────────────────┐
 *      │ name · url        ◍score   [PDF]          │
 *      │ verdict chips…                            │
 *      │ Quick-Wins ①②③                           │
 *      └───────────────────────────────────────────┘
 *      [ tech↑scan ][ Kriterien n/N ][ Kunde & Report ]
 *
 *  Panels wrap the existing DOM; only new chrome is styled here.
 * ════════════════════════════════════════════════════════════════════ */

/* ── sticky wrapper: cockpit + tabbar pin together (permanent orientation,
      no fragile per-element offset math) ── */
.assess-sticky {
  position: sticky; top: var(--nav-h, 56px); z-index: 9;
  background: var(--paper-deep);
  margin: 0 0 1.25rem;
}

/* ── cockpit ── */
.cockpit {
  background: var(--paper);
  border: 1px solid var(--paper-rule);
  border-radius: 12px;
  box-shadow: 0 2px 10px rgba(29, 26, 23, 0.06);
  padding: 0.8rem 1rem;
  margin-top: 1.25rem;
  display: grid;
  grid-template-columns: 1fr auto auto;
  grid-template-areas:
    "id    score actions"
    "chips chips chips"
    "qw    qw    qw";
  gap: 0.55rem 1rem;
  align-items: center;
}
.ck-id     { grid-area: id; min-width: 0; display: flex; align-items: center; gap: 0.4rem 1rem; flex-wrap: wrap; }
.ck-id .ah__name { font-size: 1.3rem; }
.ck-id .ah__url  { max-width: 360px; }
.ck-score  { grid-area: score; display: flex; flex-direction: column; align-items: stretch; gap: 0; width: 340px; }
.ck-score__row { display: flex; align-items: center; gap: 0.55rem; }
.ck-score__row .sax { flex: 1; min-width: 0; }
.ck-score__num { font-size: 1.6rem; font-weight: 700; line-height: 1; color: var(--ink); font-variant-numeric: tabular-nums; letter-spacing: -0.02em;
  /* .sax = bar + 0.95rem pointer stage below; equal bottom margin re-centers
     the number on the bar itself */
  margin-bottom: 0.95rem; }
.ck-score__num.is-pos { color: var(--st-ok-fg); }
.ck-score__num.is-neg { color: var(--st-fail-fg); }
.ck-score__num--empty { color: var(--ink-mute); }
.ck-score__foot { display: flex; justify-content: space-between; align-items: baseline; gap: 0.2rem 0.6rem; flex-wrap: wrap;
  margin-top: -0.35rem; /* reclaim the empty tail of the pointer stage */ }
.ck-score__zone { font-size: 0.72rem; font-weight: 600; color: var(--ink-soft); text-align: right; }
.ck-score .ah__score-sub { margin: 0; font-size: 0.72rem; white-space: nowrap; }
.ck-actions { grid-area: actions; display: flex; flex-direction: column; align-items: stretch; gap: 0.3rem; }
.ck-fullreport { font-size: 0.76rem; color: var(--ink-mute); cursor: pointer; display: flex; align-items: center; gap: 0.3rem; }
.ck-chips { grid-area: chips; display: flex; flex-wrap: wrap; gap: 0.4rem; }
.ck-chip {
  appearance: none; font: inherit; cursor: pointer;
  display: inline-flex; align-items: center; gap: 0.35rem;
  font-size: 0.78rem; padding: 0.2rem 0.55rem; border-radius: 999px;
  background: var(--accent-tint); color: var(--ink-soft);
  border: 1px solid var(--paper-rule);
}
.ck-chip:hover { border-color: var(--accent-lift); }
.ck-chip b { font-weight: 600; color: var(--ink); }
.ck-chip.ok   { color: var(--accent); }
.ck-chip.ok b { color: var(--accent); }
.ck-chip.warn   { color: var(--red); }
.ck-chip.warn b { color: var(--red); }
.ck-qw { grid-area: qw; display: flex; flex-wrap: wrap; gap: 0.35rem 0.5rem; align-items: center; font-size: 0.8rem; }
.ck-qw-lbl { font-weight: 600; color: var(--ink-soft); }
.ck-qw a {
  display: inline-flex; align-items: center; gap: 0.3rem;
  padding: 0.12rem 0.5rem; border-radius: 6px;
  background: var(--paper-deep); color: var(--ink);
}
.ck-qw a:hover { background: var(--accent-soft); color: var(--accent); text-decoration: none; }
.ck-qw a b { color: var(--accent); font-weight: 700; }

/* Stammdaten block (Kunde & Report tab) */
.stammdaten-section { margin: 0 0 2rem; }
.stammdaten-section .ah__meta { margin-bottom: 1rem; }
.blocktitle-sd { font-size: 1.1rem; color: var(--ink); margin: 0 0 0.8rem; }

/* post-consent screenshot, relocated into the tech↑scan tab */
.tab-shot { display: inline-block; margin: 0 0 1.1rem; }

/* ── tab bar ── */
.tabbar {
  display: flex; gap: 0.25rem;
  background: var(--paper-deep);
  border-bottom: 2px solid var(--paper-rule);
  padding-top: 0.2rem;
  margin: 0.85rem 0 0;
}
.tab-btn {
  appearance: none; border: 0; background: none; cursor: pointer;
  font: inherit; font-weight: 600; font-size: 0.95rem;
  color: var(--ink-mute);
  padding: 0.6rem 1rem 0.55rem;
  border-radius: 8px 8px 0 0;
  border-bottom: 3px solid transparent; margin-bottom: -2px;
  display: inline-flex; align-items: center; gap: 0.45rem;
}
.tab-btn:hover { color: var(--ink); }
.tab-btn[aria-selected="true"] {
  color: var(--accent);
  border-bottom-color: var(--accent);
}
.tab-count {
  font-size: 0.72rem; font-weight: 600;
  padding: 0.05rem 0.4rem; border-radius: 999px;
  background: var(--accent-soft); color: var(--accent);
}
.tabpanel[hidden] { display: none; }

/* ── tech↑scan sub-tabs (secondary nav inside the tech tab) ── */
.subtabs { display: flex; flex-wrap: wrap; gap: 0.35rem; margin: 0 0 1.1rem; }
.subtab-btn {
  appearance: none; font: inherit; cursor: pointer;
  font-size: 0.82rem; font-weight: 600;
  padding: 0.32rem 0.75rem; border-radius: 999px;
  border: 1px solid var(--paper-rule); background: var(--paper);
  color: var(--ink-soft);
}
.subtab-btn:hover { border-color: var(--accent-lift); color: var(--ink); }
.subtab-btn[aria-selected="true"] { background: var(--accent); border-color: var(--accent); color: #fff; }
#tab-tech details.tech-panel.sub-off { display: none; }

/* ── Concept A · mobile (≤760px, house breakpoint) ── */
@media (max-width: 760px) {
  /* space beats stickiness on a phone — cockpit + tabs scroll away,
     only the app-header stays pinned */
  .assess-sticky { position: static; }

  .cockpit {
    grid-template-columns: 1fr auto;
    grid-template-areas:
      "id    id"
      "score actions"
      "chips chips"
      "qw    qw";
    padding: 0.7rem 0.8rem;
  }
  .ck-id .ah__name { font-size: 1.15rem; }
  .ck-id .ah__url  { max-width: 100%; flex: 1 1 100%; }
  .ck-score { width: auto; }
  .ck-score__num { font-size: 1.35rem; }

  .tabbar { overflow-x: auto; scrollbar-width: none; }
  .tabbar::-webkit-scrollbar { display: none; }
  .tab-btn { padding: 0.55rem 0.7rem 0.5rem; font-size: 0.88rem; white-space: nowrap; }

  .stammdaten-section .ah__meta { flex-wrap: wrap; gap: 0.75rem; }
}
