/* De vormgeving van de viewer.
 *
 * Eén stylesheet, geen framework, geen build. De hiërarchie is de vormgeving:
 *
 *   document              wit kaartje op een rustige achtergrond
 *   documentweergave      een vaste kop met drie tabbladen; per tabblad één
 *                         wit paneel: Overview, Text (de doorlopende tekst
 *                         met onderlijningen), Review (één regel per passage)
 *
 * Drie soorten uitkomst, drie visuele vormen -- en die zijn met opzet niet
 * alleen een kleur:
 *
 *   classificatie   gevulde indigo pil
 *   detectie        omlijnde badge met een gekleurde linkerrand
 *   symbool         kaart met een getekend frame
 *
 * De kleur van een detectiesoort komt van de server (palette.py) en staat als
 * inline stijl op badge, onderlijning en symboolkaart. Ze staat dus niet in dit
 * bestand: één tabel, drie plekken, en geen kans dat ze uit elkaar lopen.
 */

/* De kleuren zijn die van de graafpagina's (deploy/lezer/tokens.css): een warm
 * grijs papier, witte kaarten met een dunne rand, en één blauw accent. De
 * namen zijn die van de viewer gebleven; de waarden zijn overgenomen, zodat
 * wie van /graphs naar de viewer gaat op dezelfde site blijft.
 *
 * Drie thematoestanden, net als daar. Het lichte palet staat op kale
 * ``:root`` en is dus altijd volledig. Het donkere overschrijft alleen tokens,
 * twee keer: onder ``prefers-color-scheme: dark`` voor wie niets gekozen
 * heeft, en onder ``[data-theme="dark"]`` voor wie de knop gebruikte (theme.js).
 * De gardering ``:not([data-theme="light"])`` laat de knop ook de andere kant
 * op winnen. De keuze staat onder dezelfde sleutel als op /graphs en in de
 * lezers: één klik geldt voor de hele site. */

:root {
  color-scheme: light;

  --paper: #f7f6f4;
  --card: #fffffe;
  --ink: #12110f;
  --ink-soft: #625f58;
  --ink-light: #8a867d;
  --line: #e1ded6;
  --line-strong: #c6c2b6;

  --classification: #3049c0;
  --classification-fill: #e8ecfb;
  --classification-line: #c3cdf3;
  /* Tekst op een vlak in de accentkleur (primaire knop, gekozen taal). */
  --on-accent: #ffffff;

  --bluf-fill: #faf9f7;
  --bluf-line: #c6c2b6;

  --chunkzone: #efeee9;

  --warn: #8a3a12;
  --warn-fill: #fbeee5;

  /* Toestanden van een entity-SIDC-veld/-kaart (herbouwontwerp §4): gated is
   * geen fout maar een geblokkeerd codepad (neutraal/gedimd), conflicting is
   * een tegenspraak die niet beslecht wordt (rood, net als warn maar apart
   * benoemd zodat de twee niet per ongeluk hetzelfde ding lijken te zeggen).
   * unresolved hergebruikt --warn: "bewijs zonder veilige beslissing" is
   * dezelfde soort aandacht als de rest van --warn al draagt. */
  --gated: #625f58;
  --gated-fill: #efeee9;
  --conflict: #a3241f;
  --conflict-fill: #fbe6e4;

  /* Relevantie en "gedeeltelijk" in de zoekresultaten; vroeger letterlijke
   * kleuren in de regels zelf, en daardoor zonder donkere variant. */
  --good: #17632c;
  --caution: #7a5b12;
  --highlight: #ffe9a8;

  --overlay: rgba(18, 17, 15, .45);
  --shadow: 0 1px 2px rgba(0, 0, 0, .05), 0 8px 24px rgba(0, 0, 0, .06);
  --shadow-raised: 0 8px 28px rgba(0, 0, 0, .16);
  --round: 13px;
  --mono: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    color-scheme: dark;

    --paper: #131316;
    --card: #1b1b1e;
    --ink: #fbfbfc;
    --ink-soft: #b0afa8;
    --ink-light: #8a8983;
    --line: #34343b;
    --line-strong: #4d4d56;

    --classification: #8ba4ff;
    --classification-fill: #1a2140;
    --classification-line: #33407a;
    --on-accent: #10132a;

    --bluf-fill: #17171a;
    --bluf-line: #4d4d56;

    --chunkzone: #17171a;

    --warn: #f0b48a;
    --warn-fill: #33231a;

    --gated: #b0afa8;
    --gated-fill: #26262b;
    --conflict: #ec8e88;
    --conflict-fill: #3a201e;

    --good: #2f8a4a;
    --caution: #9a7a26;
    --highlight: #5a4a12;

    --overlay: rgba(0, 0, 0, .6);
    --shadow: 0 1px 2px rgba(0, 0, 0, .4), 0 8px 24px rgba(0, 0, 0, .35);
    --shadow-raised: 0 8px 28px rgba(0, 0, 0, .55);
  }
}

:root[data-theme="dark"] {
  color-scheme: dark;

  --paper: #131316;
  --card: #1b1b1e;
  --ink: #fbfbfc;
  --ink-soft: #b0afa8;
  --ink-light: #8a8983;
  --line: #34343b;
  --line-strong: #4d4d56;

  --classification: #8ba4ff;
  --classification-fill: #1a2140;
  --classification-line: #33407a;
  --on-accent: #10132a;

  --bluf-fill: #17171a;
  --bluf-line: #4d4d56;

  --chunkzone: #17171a;

  --warn: #f0b48a;
  --warn-fill: #33231a;

  --gated: #b0afa8;
  --gated-fill: #26262b;
  --conflict: #ec8e88;
  --conflict-fill: #3a201e;

  --good: #2f8a4a;
  --caution: #9a7a26;
  --highlight: #5a4a12;

  --overlay: rgba(0, 0, 0, .6);
  --shadow: 0 1px 2px rgba(0, 0, 0, .4), 0 8px 24px rgba(0, 0, 0, .35);
  --shadow-raised: 0 8px 28px rgba(0, 0, 0, .55);
}

* { box-sizing: border-box; }

/* Zonder deze regel wint `display: flex` van een klasse het van het
 * UA-voorschrift bij [hidden], en blijft een verborgen melding staan. */
[hidden] { display: none !important; }

body {
  margin: 0;
  background: var(--paper);
  color: var(--ink);
  font: 14.5px/1.55 -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
}

.wrap {
  max-width: 1080px;
  margin: 0 auto;
  padding: 0 24px;
}

/* De werkruimte is een tabel met filters ernaast, geen leestekst: het mag de
 * breedte van het scherm gebruiken (tabs.js zet data-tab op body).
 *
 * De omgevingsbalk is altijd zo breed, op elk tabblad. Ging ze mee met de
 * inhoud, dan brak ze op Collation en Assessment (1080 px) in twee regels en
 * op de andere twee niet: dezelfde knoppen sprongen bij elke tabwissel naar
 * een andere plek. Een balk die stilstaat weegt zwaarder dan randen die met
 * de inhoud gelijk lopen; de lezers op /graphs doen het net zo. */
body[data-tab="reconciliation"] .wrap,
body[data-tab="observations"] .wrap,
.environments .wrap { max-width: 1520px; }

.visually-hidden {
  position: absolute;
  width: 1px; height: 1px;
  padding: 0; margin: -1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
}

/* --------------------------------------------------------------- head --- */

.head { padding: 34px 0 22px; }

.head h1 {
  margin: 0;
  font-size: 26px;
  font-weight: 650;
  letter-spacing: -.02em;
}

.lead {
  margin: 6px 0 0;
  max-width: 64ch;
  color: var(--ink-soft);
}

/* ----------------------------------------------------------- semantic --- */

/* De semantische zoekbalk staat boven de gewone en ziet er anders uit: een
 * eigen vlak, een zichtbaar label en een knop. Dat verschil is functioneel --
 * dit veld stuurt een vraag naar een model en het veld eronder filtert de lijst
 * die er al is -- en het hoort daarom zichtbaar te zijn zonder de uitleg te
 * moeten lezen.
 */

.semantic {
  background: var(--card);
  border-bottom: 1px solid var(--line);
}

.semantic-inner {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  gap: 10px;
  padding-top: 16px;
  padding-bottom: 14px;
}

.semantic-field {
  display: flex;
  flex-direction: column;
  gap: 5px;
  flex: 1 1 320px;
  min-width: 0;
}

.semantic-label {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--classification);
}

.semantic-hint,
.semantic-status {
  flex: 1 1 100%;
  margin: 0;
  font-size: 13px;
  color: var(--ink-soft);
}

.semantic-status:empty { display: none; }

.semantic-status {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-top: 2px;
}

.semantic-status.error { color: var(--warn); }

.button.primary {
  color: var(--on-accent);
  background: var(--classification);
  border-color: var(--classification);
}

.button.primary:hover { color: var(--on-accent); border-color: var(--classification); filter: brightness(1.08); }
.button.primary[disabled] { opacity: .6; cursor: default; filter: none; }

/* -------------------------------------------------------- omgevingen --- */

/* De omgevingsbalk staat bovenaan en heeft een eigen vlak, omdat de vraag
 * "welke omgeving kijk ik?" boven elke andere vraag op deze pagina staat. Twee
 * theaters zien er verder identiek uit.
 *
 * Eén regel: de omgeving (de naam groot en vet in de selector zelf -- een
 * keuze in een select is makkelijk te missen, een naam in kopformaat niet),
 * de tabbladen, en rechts de knoppen. Vroeger drie lagen en 225 px; nu begint
 * elk tabblad bijna meteen met zijn inhoud. Op een smal scherm loopt ze over
 * in twee regels. */

.environments {
  position: relative;
  z-index: 30;
  background: var(--card);
  border-bottom: 1px solid var(--line);
}

.environments-inner {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  gap: 6px 10px;
  padding-top: 8px;
}

.environment-choice {
  display: flex;
  flex-direction: column;
  gap: 2px;
  /* Zo breed als de langste theaternaam, tot een grens: "ARDENT DEFENDER 26 -
   * TEST" viel in een vaste 250 px weg, en de naam is precies wat hier te
   * lezen moet zijn. Is er te weinig plaats, dan gaan de knoppen rechts naar
   * een tweede regel, niet de naam. */
  flex: 0 1 auto;
  min-width: 200px;
  max-width: 360px;
  padding-bottom: 8px;
}

.environment-label {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--ink-soft);
}

.environment-choice select {
  width: auto;
  max-width: 100%;
  padding-top: 5px;
  padding-bottom: 5px;
  font-size: 15px;
  font-weight: 700;
  color: var(--ink);
}

.environment-caption {
  display: flex;
  align-items: baseline;
  gap: 8px;
  min-width: 0;
}

.environment-kind {
  margin: 0;
  font-size: 11.5px;
  color: var(--ink-light);
  white-space: nowrap;
  text-overflow: ellipsis;
}

.environment-kind:not(:empty)::before { content: "·"; margin-right: 8px; }

.environments-spacer { flex: 1 1 0; }

.environment-actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: flex-end;
  gap: 6px;
  margin-left: auto;
  padding-bottom: 10px;
}

.environment-actions .language-switch { align-self: center; margin-bottom: 0; }

.environment-form {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 10px;
  padding-top: 8px;
  padding-bottom: 12px;
}

.environment-name { flex: 1 1 260px; }

.environment-name input {
  width: 100%;
  padding: 9px 12px;
  font: inherit;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 8px;
}

.environment-form-status {
  flex: 1 1 100%;
  margin: 0;
  font-size: 13px;
  color: var(--ink-soft);
}

.environment-form-status.error { color: var(--warn); }


/* -------------------------------------------------------------- tabs --- */

/* De tabbladen staan in de omgevingsbalk, na de naam van het theater: eerst
 * welk theater, dan wat je ermee doet. Een onderlijning op de rand van de
 * balk markeert het actieve tabblad; kleur alleen zou het niet dragen, het
 * gewicht ook. */

.tabs { align-self: flex-end; margin-left: 8px; min-width: 0; }

.tabs-inner {
  display: flex;
  gap: 2px;
  overflow-x: auto;
  scrollbar-width: none;
}

.tab {
  flex: none;
  padding: 10px 11px 11px;
  font: inherit;
  font-size: 14px;
  font-weight: 600;
  color: var(--ink-soft);
  background: none;
  border: 0;
  border-bottom: 3px solid transparent;
  border-radius: 6px 6px 0 0;
  cursor: pointer;
}

.tab:hover { color: var(--ink); background: color-mix(in srgb, var(--card) 50%, transparent); }

.tab[aria-selected="true"] {
  color: var(--classification);
  font-weight: 700;
  background: var(--paper);
  border-bottom-color: var(--classification);
}

.tab:focus-visible {
  outline: 2px solid var(--classification);
  outline-offset: -4px;
}

@media (max-width: 760px) {
  .environment-choice { flex: 1 1 100%; padding-bottom: 0; }
  .environments-spacer { display: none; }
  .tabs { order: 5; flex: 1 1 100%; margin-left: -6px; }
  /* Geen verborgen horizontale scroll: "Assessment" viel buiten beeld en
   * niets liet zien dat er meer was. */
  .tabs-inner { flex-wrap: wrap; overflow-x: visible; }
  .environment-actions { margin-left: 0; justify-content: flex-start; }
}

/* ---------------------------------------------------- uploaden --- */

/* Het uploadvlak hoort bij het theater erboven en staat daarom op hetzelfde
 * papier, als een kaart met een gestippelde rand: dat is de vorm die lezers
 * als "hier kun je iets neerzetten" herkennen. Tijdens het slepen krijgt het
 * de kleur van de omgevingsbalk. */

.ingest { background: var(--paper); padding-bottom: 14px; }

.ingest-drop {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 12px 18px;
  padding: 14px 18px;
  background: var(--card);
  border: 1.5px dashed var(--line-strong);
  border-radius: var(--round);
}

.ingest-drop.dragging {
  background: var(--classification-fill);
  border-color: var(--classification);
}

.ingest-text { flex: 1 1 320px; min-width: 0; }

.ingest-title {
  margin: 0 0 4px;
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--classification);
}

.ingest-hint {
  margin: 0;
  font-size: 13px;
  color: var(--ink-soft);
}

.ingest-files {
  list-style: none;
  margin: 10px 0 0;
  padding: 0;
  display: grid;
  gap: 4px;
}

.ingest-file {
  display: flex;
  flex-wrap: wrap;
  gap: 4px 10px;
  align-items: baseline;
  font-size: 13px;
}

.ingest-file-state {
  flex: 0 0 76px;
  font-weight: 620;
  color: var(--ink-soft);
}

.ingest-file.stored .ingest-file-state { color: var(--classification); }
.ingest-file.rejected .ingest-file-state,
.ingest-file.rejected .ingest-file-note { color: var(--warn); }

.ingest-file-name {
  min-width: 0;
  overflow-wrap: anywhere;
  color: var(--ink);
}

.ingest-file-note { color: var(--ink-soft); }

.ingest-pipeline {
  margin-top: 12px;
  padding: 14px 18px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--round);
}

.ingest-pipeline-head {
  display: flex;
  align-items: center;
  gap: 8px;
  margin: 0 0 10px;
  font-weight: 620;
  font-size: 14px;
}

.ingest-steps {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(100%, 240px), 1fr));
  gap: 6px 18px;
}

.ingest-step {
  display: flex;
  align-items: baseline;
  gap: 8px;
  font-size: 13px;
  color: var(--ink-soft);
}

.ingest-step-mark { flex: 0 0 1em; text-align: center; font-weight: 700; }
.ingest-step-label { flex: 1 1 auto; min-width: 0; }
.ingest-step-state { font-size: 12px; color: var(--ink-light); }

.ingest-step.running { color: var(--ink); }
.ingest-step.running .ingest-step-mark,
.ingest-step.done .ingest-step-mark { color: var(--classification); }
.ingest-step.failed,
.ingest-step.warning { color: var(--warn); }
.ingest-step.failed .ingest-step-state,
.ingest-step.warning .ingest-step-state { color: var(--warn); }

.ingest-error {
  margin: 10px 0 0;
  font-size: 13px;
  color: var(--warn);
}

.ingest-pipeline > .button { margin-top: 10px; }

/* De kennisbankmodus. De documentenlijst, de filters en de gewone zoekbalk
 * staan er niet -- ze zijn ``hidden`` in app.js en dat is geen stijlkeuze maar
 * een eigenschap van de omgeving. Wat hier staat, is alleen de vormgeving van
 * wat er wél is. */

.knowledge-result { padding-bottom: 6px; }

/* Eén kolom, en niet het raster van een documentkaart.
 *
 * ``.document-head`` is een grid van twee kolommen, omdat een document links
 * zijn titel heeft en rechts de knop naar het origineel. Een kennisbankresultaat
 * heeft die knop niet -- die route bestaat er niet -- en dan perst hetzelfde
 * raster de titel in een kolom van een paar woorden breed. */
.knowledge-result .document-head {
  display: block;
}

.knowledge-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 8px 12px;
  margin-bottom: 10px;
}

.knowledge-title {
  margin: 0;
  font-size: 16px;
  font-weight: 620;
  color: var(--ink);
}

/* ---------------------------------------------------------------- bar --- */

.bar {
  position: sticky;
  top: 0;
  z-index: 20;
  background: color-mix(in srgb, var(--paper) 88%, transparent);
  backdrop-filter: blur(8px);
  border-bottom: 1px solid var(--line);
}

.bar-inner {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 10px;
  padding-top: 12px;
  padding-bottom: 12px;
}

.search { flex: 1 1 240px; }
/* Zo breed als de langste keuze, en niet vast: in het Frans ("Toutes les
 * classifications") viel een vaste 190 px te kort. Krimpen mag nog steeds,
 * tot het minimum hieronder. */
.choice { flex: 0 1 auto; min-width: 150px; }
.choice select { width: auto; max-width: 100%; }
.choice.wide { flex: 0 1 auto; }

input[type="search"],
select {
  width: 100%;
  padding: 9px 12px;
  font: inherit;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 8px;
}

input[type="search"]:focus-visible,
select:focus-visible,
button:focus-visible,
a:focus-visible,
.mark:focus-visible {
  outline: 2px solid var(--classification);
  outline-offset: 2px;
  border-radius: 3px;
}

.count {
  margin: 0 0 0 auto;
  font-size: 13px;
  color: var(--ink-soft);
  white-space: nowrap;
}

/* ------------------------------------------------- loading / empty / error */

.notice {
  display: flex;
  align-items: center;
  gap: 10px;
  margin: 28px 0;
  padding: 20px 22px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--round);
  color: var(--ink-soft);
}

.notice.error {
  color: var(--warn);
  background: var(--warn-fill);
  border-color: color-mix(in srgb, var(--warn) 30%, transparent);
}

.notice button { margin-left: auto; }

/* Een melding met commando's erin.
 *
 * ``.notice`` is een flexrij met alles op één hoogte -- goed voor "laden…" met
 * een spinner ernaast, verkeerd voor een alinea met een codeblok eronder.
 * Draagt de melding een kop, dan wordt het een kolom. */
.notice .notice-head {
  margin: 0 0 8px;
  font-weight: 620;
  color: var(--ink);
}

.notice .notice-head ~ p {
  margin: 10px 0 8px;
}

.notice > div {
  flex: 1 1 auto;
  min-width: 0;
}

.commands {
  margin: 0;
  padding: 12px 14px;
  overflow-x: auto;
  font-family: var(--mono);
  font-size: 12.5px;
  line-height: 1.7;
  color: var(--ink);
  background: var(--chunkzone);
  border: 1px solid var(--line);
  border-radius: 8px;
  /* Selecteerbaar en over te typen; de regels worden niet afgebroken, want een
   * afgebroken commando is een commando dat verkeerd overgetikt wordt. */
  white-space: pre;
}

.notice .commands + p { margin-top: 12px; }
.notice .commands + button { margin: 12px 0 0; }

.spinner {
  width: 14px; height: 14px;
  flex: 0 0 auto;
  border: 2px solid var(--line-strong);
  border-top-color: var(--classification);
  border-radius: 50%;
  animation: spin .7s linear infinite;
}

@keyframes spin { to { transform: rotate(360deg); } }
@media (prefers-reduced-motion: reduce) { .spinner { animation-duration: 2.4s; } }

/* -------------------------------------------------------------- buttons --- */

.button {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 12px;
  font: inherit;
  font-size: 13px;
  font-weight: 500;
  line-height: 1.5;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 8px;
  cursor: pointer;
  text-decoration: none;
}

/* Zoals de knoppen op /graphs: de rand en de tekst nemen het accent aan. */
.button:hover { border-color: var(--classification); color: var(--classification); }
.button[disabled]:hover { border-color: var(--line-strong); color: var(--ink); }

/* ◐ -- dezelfde knop als op /graphs en in de lezers (theme.js). */
.theme-toggle {
  justify-content: center;
  min-width: 34px;
  padding-left: 8px;
  padding-right: 8px;
  font-size: 15px;
  line-height: 1.3;
}

/* ? -- de handleiding (/manual), in een nieuw venster. Zo smal als ◐: met
 * het woord erop liep de balk op 1280 px over in twee regels. De naam staat
 * in de tooltip en voor schermlezers. */
.manual-link {
  justify-content: center;
  min-width: 34px;
  padding-left: 8px;
  padding-right: 8px;
  font-size: 14px;
  font-weight: 700;
  line-height: 1.4;
}

.link-button {
  padding: 2px 0;
  font: inherit;
  font-size: 13px;
  font-weight: 550;
  color: var(--classification);
  background: none;
  border: 0;
  cursor: pointer;
}

.link-button:hover { text-decoration: underline; }

/* ------------------------------------------------------------ documents --- */

.list {
  list-style: none;
  margin: 24px 0 64px;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 14px;
}

.document {
  /* Zodat een document waar met #id naartoe gesprongen wordt niet onder de
   * plakkende balk verdwijnt. */
  scroll-margin-top: 68px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--round);
  overflow: hidden;
  transition: border-color .12s;
}

.document:hover { border-color: var(--line-strong); }

.document.open { border-color: var(--line-strong); }

.document-head {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: 10px 16px;
  align-items: start;
  padding: 16px 18px;
}

.document-title {
  display: flex;
  align-items: baseline;
  gap: 9px;
  margin: 0;
  grid-column: 1;
  grid-row: 1;
  font-size: 16.5px;
  font-weight: 620;
  letter-spacing: -.006em;
  text-align: left;
  color: inherit;
  background: none;
  border: 0;
  padding: 0;
  cursor: pointer;
  overflow-wrap: anywhere;
}

.document-title:hover .name { text-decoration: underline; }

.chevron {
  flex: 0 0 auto;
  width: 9px; height: 9px;
  margin-top: 5px;
  border-right: 2px solid var(--ink-light);
  border-bottom: 2px solid var(--ink-light);
  transform: rotate(-45deg);
  transition: transform .16s ease;
}

.document.open .chevron { transform: rotate(45deg); }

.document-meta {
  grid-column: 1;
  display: flex;
  flex-wrap: wrap;
  gap: 4px 10px;
  margin: 0;
  font-size: 13px;
  color: var(--ink-soft);
}

.document-meta span + span::before {
  content: "·";
  margin-right: 10px;
  color: var(--ink-light);
}

.document-actions {
  grid-column: 2;
  grid-row: 1;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  justify-content: flex-end;
}

/* Verwijderen. De knop in de kaartkop is rustig -- hij staat op elke kaart en
 * hoort niet de aandacht te trekken -- en pas de bevestiging is vol rood. */

.button.danger { color: var(--conflict); }
.button.danger:hover { color: var(--conflict); border-color: var(--conflict); }

.button.danger-solid {
  color: var(--on-accent);
  background: var(--conflict);
  border-color: var(--conflict);
}
.button.danger-solid:hover { color: var(--on-accent); filter: brightness(1.08); }
.button[disabled] { opacity: .6; cursor: default; }

.removal {
  grid-column: 1 / -1;
  margin: 2px 0 4px;
  padding: 12px 14px;
  background: var(--conflict-fill);
  border: 1px solid color-mix(in srgb, var(--conflict) 35%, transparent);
  border-radius: 8px;
}

.removal-head { margin: 0 0 4px; font-weight: 620; color: var(--ink); }
.removal-text { margin: 0 0 10px; font-size: 13px; color: var(--ink-soft); }
.removal-error { margin: 0 0 10px; font-size: 13px; color: var(--conflict); }
.removal-actions { display: flex; flex-wrap: wrap; gap: 8px; }

/* --------------------------------------------------------------- BLUF --- */
/* Boven de classificatiebadges en binnen de kaartkop. De badges blijven waar
 * ze stonden -- ze zijn niet naar een andere laag verhuisd, er is er een
 * bijgekomen.
 *
 * Een lopende alinea en geen pil: dit is de enige plek op het scherm met
 * doorlopende tekst, en die moet er ook zo uitzien. Vandaar de zachte vulling
 * met een liniaal ervoor, in plaats van een kader eromheen. */

.document-bluf {
  grid-column: 1 / -1;
  margin: 4px 0 0;
  padding: 9px 12px 10px;
  background: var(--bluf-fill);
  border-left: 3px solid var(--bluf-line);
  border-radius: 0 6px 6px 0;
}

.bluf-head {
  margin: 0 0 3px;
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .09em;
  text-transform: uppercase;
  color: var(--ink-soft);
}

.bluf-text {
  margin: 0;
  font-size: 14px;
  line-height: 1.6;
  color: var(--ink);
  overflow-wrap: anywhere;
}

/* Een BLUF die niet het hele document dekt: één stille regel eronder. */
.bluf-gap {
  margin: 6px 0 0;
  font-size: 12px;
  line-height: 1.5;
  color: var(--ink-soft);
}

/* Zonder BLUF geen leeg kader: alleen de stille regel die de rest van de
 * pagina ook gebruikt voor een lege staat. */
.document-bluf-none { grid-column: 1 / -1; margin: 4px 0 0; }

/* Een BLUF die gemaakt wordt of net mislukte: op de plek van de BLUF, in de
 * stille vorm van de andere statusregels. */
.bluf-job {
  grid-column: 1 / -1;
  display: flex;
  align-items: center;
  gap: 8px;
  margin: 4px 0 0;
  font-size: 13px;
  color: var(--ink-soft);
}

.bluf-job.error { color: var(--warn); }

.document-badges { grid-column: 1 / -1; margin: 2px 0 0; }
.label-notes {
  display: flex;
  flex-wrap: wrap;
  gap: 2px 14px;
  margin: 6px 0 0;
  font-size: 12.5px;
  color: var(--ink-light);
}
.label-note-kind { font-style: italic; }
/* Het enige geval dat om actie vraagt: een besluit dat niet meer geldt. */
.label-note.note-stale { color: var(--warn); }

.document-body {
  border-top: 1px solid var(--line);
  padding: 4px 18px 20px;
}

/* --------------------------------------------------------------- block --- */

.block { margin-top: 18px; }

.block-head.main {
  font-size: 13px;
  color: var(--ink);
  padding-bottom: 8px;
  border-bottom: 1px solid var(--line);
}

.block-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 10px;
  margin: 0 0 10px;
  font-size: 11.5px;
  font-weight: 700;
  letter-spacing: .085em;
  text-transform: uppercase;
  color: var(--ink-soft);
}

.block-head .aside {
  font-weight: 500;
  letter-spacing: 0;
  text-transform: none;
  font-size: 12.5px;
  color: var(--ink-light);
}

.rows { display: flex; flex-direction: column; gap: 8px; }

.row {
  display: grid;
  grid-template-columns: 190px 1fr;
  gap: 6px 14px;
  align-items: baseline;
}

.row-name { font-size: 13px; font-weight: 550; color: var(--ink-soft); }

@media (max-width: 620px) { .row { grid-template-columns: 1fr; } }

/* -------------------------------------------------------------- badges --- */

.badges {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  list-style: none;
  margin: 0;
  padding: 0;
}

/* De groepen stromen achter elkaar door; binnen een groep staat de
 * taxonomienaam vóór zijn labels.
 *
 * Gescheiden door witruimte en niet door een streep: bij het afbreken van een
 * regel zou die streep vooraan de volgende regel blijven staan, en dan lijkt
 * hij een opsommingsteken. De taxonomienaam is zelf al het scheidingsteken --
 * hij staat in kleine kapitalen tussen de gevulde pillen. */
.badge-groups {
  display: flex;
  flex-wrap: wrap;
  gap: 6px 22px;
}

.badge-group {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 5px 7px;
}

/* --ink-soft en niet --ink-light: dit is betekenisdragende tekst op 11 px, en
 * die moet contrast houden. Zelfde behandeling als de andere kopjes. */
.group-name {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-soft);
  white-space: nowrap;
}

.badge {
  display: inline-flex;
  align-items: baseline;
  gap: 6px;
  padding: 3px 9px;
  font-size: 12.5px;
  line-height: 1.45;
  border-radius: 6px;
  overflow-wrap: anywhere;
}

/* Classificatie: gevuld en indigo. Eén vorm voor alle taxonomieën. */
.badge.classification {
  color: var(--classification);
  background: var(--classification-fill);
  border: 1px solid var(--classification-line);
  font-weight: 550;
}

.badge .origin {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .045em;
  text-transform: uppercase;
  opacity: .72;
}

/* De kleur komt van de server en is gekozen voor lijnen, niet voor kleine
 * tekst op een donkere kaart (event-magenta haalde er 2,7:1). Donker:
 * voluit en lichter. */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .badge .origin { opacity: 1; filter: brightness(1.55); }
}
:root[data-theme="dark"] .badge .origin { opacity: 1; filter: brightness(1.55); }

/* De herkomst achter een dubbelzinnig classificatielabel. Ondergeschikt aan
 * het label ervoor: kleiner, lichter, gewone kapitalisatie. Nadrukkelijk niet
 * .origin hierboven -- dat is de vorm van de detectiebadge, en die blijft. */
.badge .qualifier {
  font-size: 11.5px;
  font-weight: 500;
  opacity: .68;
  white-space: nowrap;
}

/* Detectie: omlijnd, met een dikke linkerrand in de kleur van zijn soort --
 * dezelfde kleur als de onderlijning in de tekst. De soortnaam staat in de
 * rijkop ernaast en in de tooltip, dus de koppeling hangt niet aan kleur alleen. */
.badge.detection {
  color: var(--ink);
  background: transparent;
  border: 1px solid var(--line-strong);
  border-left-width: 3px;
}

.badge .times { font-size: 11.5px; color: var(--ink-light); }

.badge.detection.linked,
.symbol.linked {
  border-color: currentColor;
  background: color-mix(in srgb, currentColor 10%, transparent);
}

.none {
  margin: 0;
  font-size: 13px;
  color: var(--ink-light);
  font-style: italic;
}

.more { font-size: 12.5px; color: var(--ink-light); align-self: center; }

/* ----------------------------------------------------------- relations --- */

.relations {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 5px;
  font-size: 13.5px;
}

.relation {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 7px;
  overflow-wrap: anywhere;
}

.relation .verb {
  font-size: 12px;
  color: var(--ink-soft);
  background: var(--chunkzone);
  border: 1px solid var(--line);
  border-radius: 5px;
  padding: 1px 7px;
}

/* ------------------------------------------------------------- symbols --- */

/* Een raster en geen flexrij. Met `flex: 1 1 300px` bepaalde de laatste rij hoe
 * breed de kaarten werden, en bij drie kaarten naast elkaar bleef er naast een
 * symbool te weinig over voor een naam als "Movement and Manoeuvre - Infantry -
 * Mechanised Infantry with Main Gun System". `auto-fit` met een ondergrens van
 * 420px legt de kolombreedte vast in plaats van de kaartinhoud: twee kolommen
 * op een gewoon scherm, één zodra dat niet meer past. De `min(100%, …)` is er
 * voor smalle schermen -- zonder die zou 420px breder kunnen zijn dan de
 * pagina en zou er horizontaal gescrold moeten worden. */
.symbols {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(100%, 420px), 1fr));
  gap: 12px;
  list-style: none;
  margin: 0;
  padding: 0;
}

.symbol {
  display: flex;
  align-items: flex-start;
  gap: 14px;
  min-width: 0;
  /* Kaarten náást elkaar krijgen dezelfde hoogte; kaarten in een andere rij
   * niet. Anders zou één kaart met een lange naam het hele blok oprekken. */
  height: 100%;
  padding: 12px 14px 12px 11px;
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-left-width: 3px;
  border-radius: 8px;
}

/* De kolom voor het APP-6D-symbool, in de browser getekend door milsymbol uit
 * de SIDC die de server meestuurt. Is er geen code, of wijst milsymbol hem af,
 * dan bestaat dit element helemaal niet en is de kaart puur tekst -- geen leeg
 * kader en geen lege kolom.
 *
 * 112px is geen slag in de lucht: bij framemaat 52 is de breedste tekening die
 * de Land unit-pickerdata kan opleveren 109px. Elk symbool past er dus in op
 * ware grootte, en de rand eromheen houdt de namen op één lijn. */
.symbol-graphic {
  flex: 0 0 112px;
  min-width: 0;
  display: flex;
  justify-content: center;
  align-items: flex-start;
}

/* Geen vaste maat hier. De breedte en de hoogte staan als attribuut op de
 * <img> en komen van `getSize()`: de maten van de héle tekening, versierselen
 * meegerekend. Een symbool met echelonteken is hoger dan breed en een
 * pantsereenheid zonder juist breder dan hoog -- ze allebei in hetzelfde
 * vierkant leggen maakte het frame van het eerste stelselmatig kleiner.
 *
 * En daarom staat er hier met opzet géén `width: auto`. Een breedte in de CSS
 * -- ook `auto` -- overstemt het attribuut, en dan is een nog niet geladen
 * afbeelding 0 x 0 breed en springt de kaart op het moment dat zij binnenkomt.
 * Met alleen het attribuut is de ruimte al gereserveerd voordat er iets
 * geladen is, en dat is precies waarvoor die attributen bestaan.
 *
 * `max-width: 100%` is een vangnet: valt een tekening ooit buiten de kolom,
 * dan krimpt zij mee in plaats van de kaart open te breken. `height: auto`
 * hoort daarbij -- dat houdt de verhouding intact terwijl zij krimpt, en het
 * legt geen hoogte vast. */
.symbol-image {
  display: block;
  flex: 0 1 auto;
  height: auto;
  max-width: 100%;
  object-fit: contain;
}

.symbol-text { min-width: 0; flex: 1 1 auto; }

.symbol-name {
  font-size: 13.5px;
  font-weight: 600;
  line-height: 1.35;
  overflow-wrap: anywhere;
}

.symbol-source {
  margin-top: 2px;
  font-size: 12.5px;
  color: var(--ink-soft);
  overflow-wrap: anywhere;
}

.symbol-source q { font-style: italic; }

.symbol-summary {
  margin: 3px 0 0;
  font-size: 12px;
  color: var(--ink-light);
  overflow-wrap: anywhere;
}

.symbol-details { margin-top: 5px; }

.symbol-props {
  margin: 6px 0 0;
  font-size: 12px;
  color: var(--ink-soft);
  display: grid;
  grid-template-columns: auto 1fr;
  gap: 1px 8px;
}

.symbol-props dt { color: var(--ink-light); }
.symbol-props dd { margin: 0; overflow-wrap: anywhere; }

.symbol-note {
  margin: 6px 0 0;
  font-size: 12px;
  font-style: italic;
  color: var(--ink-light);
}

/* De release-gate op de kaart zelf: een voorstel is zichtbaar een voorstel
 * (W7), en bewijs dat voorbij de preview ligt zegt dat ook (W8). */
.symbol-flag {
  margin-left: 6px;
  padding: 1px 6px;
  border: 1px solid var(--ink-light);
  border-radius: 999px;
  font-size: 10px;
  font-style: normal;
  font-weight: 600;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--ink-light);
  white-space: nowrap;
}

.symbol-origin {
  font-size: 11px;
  color: var(--ink-light);
}

/* Toestanden van één veld op een assignmentkaart (ABSENT/UNRESOLVED/
 * CONFLICTING blijven zichtbaar onderscheiden, nooit plat naar "geen
 * waarde" -- herbouwontwerp §4). VALUE draagt geen eigen kleur: dat is de
 * neutrale, gewone rij. */
.symbol-props dd.state-absent { color: var(--ink-light); font-style: italic; }
.symbol-props dd.state-unresolved { color: var(--warn); }
.symbol-props dd.state-conflicting { color: var(--conflict); font-weight: 600; }

/* De statuschip zelf (gated/unresolved/conflicting op de kaartkop): dezelfde
 * pilvorm als .symbol-flag, met een kleur per toestand in plaats van de
 * neutrale grijstint. */
.symbol-flag.state-gated {
  color: var(--gated);
  background: var(--gated-fill);
  border-color: transparent;
}
.symbol-flag.state-unresolved {
  color: var(--warn);
  background: var(--warn-fill);
  border-color: transparent;
}
.symbol-flag.state-conflicting {
  color: var(--conflict);
  background: var(--conflict-fill);
  border-color: transparent;
}

/* Freshness (herbouwontwerp §6): een stale materialisatie mag niet stil als
 * actueel ogen. Dezelfde --warn-kleur als de rest van de interface voor
 * "aandacht nodig", maar als volle balk boven het document -- dit geldt voor
 * alles eronder, niet voor één kaart. */
.freshness-banner {
  margin: 0 0 12px;
  padding: 8px 12px;
  border-radius: 6px;
  background: var(--warn-fill);
  color: var(--warn);
  font-size: 13px;
}

/* Twee regels onder elkaar, elk met hun eigen toestand: de opgeslagen
 * detecties en de gematerialiseerde lagen. Ze los tonen is het hele punt --
 * ze hebben elk hun eigen oplossing (detect_chunks respectievelijk
 * resolve_layers) en één samengevatte melding zou dat verbergen. */
.freshness-row {
  margin: 6px 0 0;
  line-height: 1.5;
}

.freshness-label { font-weight: 600; }

/* CURRENT/FRESH krijgen geen eigen kleur: ze verschijnen alleen in de banner,
 * en die verschijnt alleen als er íets mis is. */
.symbol-flag.state-stale {
  color: var(--conflict);
  background: var(--conflict-fill);
  border-color: transparent;
}
.symbol-flag.state-unknown {
  color: var(--gated);
  background: var(--gated-fill);
  border-color: transparent;
}

/* Het legacy-archief (detection_sidc): standaard ingeklapt en zichtbaar
 * gedimd, zodat het nooit met de primaire sectie erboven te verwarren is. */
.legacy-section {
  margin-top: 14px;
  padding-top: 10px;
  border-top: 1px dashed var(--line);
  color: var(--ink-light);
}
.legacy-section summary {
  cursor: pointer;
  font-size: 13px;
  font-weight: 600;
  color: var(--ink-soft);
}
.legacy-section .symbols { margin-top: 8px; }

.marker-token {
  font-weight: 600;
  font-family: ui-monospace, "SF Mono", Menlo, monospace;
}

/* De gematerialiseerde objectenlijst: de entity_sidc-kaarten en het
 * legacy-archief, op documentniveau. */
.entities {
  margin: 8px 0 0;
  padding: 0;
  list-style: none;
  display: flex;
  flex-direction: column;
  gap: 10px;
}

.entity {
  display: flex;
  align-items: flex-start;
  gap: 14px;
  min-width: 0;
  padding: 8px 10px;
  border: 1px solid var(--line);
  border-radius: 6px;
}

.symbol summary,
.entity summary {
  font-size: 12px;
  color: var(--ink-light);
  cursor: pointer;
}

.symbol details code,
.entity details code {
  display: inline-block;
  margin-top: 3px;
  font-size: 12px;
  letter-spacing: .04em;
  overflow-wrap: anywhere;
}

/* ------------------------------------------------------ document view --- */
/*
 * Eén document als eigen weergave (app.js documentView). Zolang het open is,
 * wijkt alles wat bij de lijst hoort: de kop, het uploadvlak, de twee
 * zoekvelden, de filterbalk en de lijst zelf. De kop van het document blijft
 * bovenaan staan, met de tabbladen erin: wie in de tekst leest, kan altijd
 * terug naar Overview of Review zonder te scrollen.
 */

body.document-focus #panel-collation > .head,
body.document-focus #ingest,
body.document-focus #semantic-bar,
body.document-focus #filter-bar,
body.document-focus #review-queue,
body.document-focus #list,
body.document-focus #status { display: none !important; }

.docview { padding: 14px 0 72px; }

.docview-head {
  position: sticky;
  top: 0;
  z-index: 20;
  margin: 0 -24px;
  padding: 12px 24px 0;
  background: color-mix(in srgb, var(--paper) 94%, transparent);
  backdrop-filter: blur(8px);
  border-bottom: 1px solid var(--line);
}

.docview-bar {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 8px 14px;
}

.docview-back { flex: 0 0 auto; }

.docview-title {
  flex: 1 1 280px;
  min-width: 0;
  margin: 0;
  font-size: 19px;
  font-weight: 650;
  line-height: 1.3;
  letter-spacing: -.008em;
  color: var(--ink);
  overflow-wrap: anywhere;
}

.docview-bar .document-actions { flex-wrap: wrap; }
.docview-head .document-meta { margin-top: 6px; }
.docview-head .removal { margin-top: 10px; }

.docview-tabs {
  display: flex;
  gap: 2px;
  margin-top: 8px;
  overflow-x: auto;
}

.docview-tab {
  flex: 0 0 auto;
  padding: 8px 14px 9px;
  font: inherit;
  font-size: 14px;
  font-weight: 600;
  color: var(--ink-soft);
  background: none;
  border: 0;
  border-bottom: 2px solid transparent;
  cursor: pointer;
  white-space: nowrap;
}

.docview-tab:hover { color: var(--ink); }
.docview-tab.active { color: var(--classification); border-bottom-color: var(--classification); }
.docview-tab:focus-visible { outline: 2px solid var(--classification); outline-offset: -3px; border-radius: 6px; }

.docview > .bluf,
.docview > .bluf-job,
.docview > .document-badges { margin-top: 14px; }

.docview-panel {
  margin-top: 16px;
  padding: 18px 20px 22px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--round);
}

.docview-panel > .block:first-child,
.docview-panel > :first-child { margin-top: 0; }

.docview-complete {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 12px;
  margin: 10px 0 0;
  font-size: 13px;
}

/* Wat naar de tekst wijst: een badge, een relatie, een symboolkaart. */
.jumpable { cursor: pointer; }
.badge.jumpable:hover,
.relation.jumpable:hover { background: var(--classification-fill); }
.jumpable:focus-visible { outline: 2px solid var(--classification); outline-offset: 2px; }
.symbol-jump { margin-left: 8px; font-size: 12.5px; }

/* Text: het document als doorlopende tekst. Het passagenummer staat in de
 * marge, een sectiekop alleen waar de sectie verandert. */
.docview-text > .legend {
  margin: 0 0 8px;
  padding-bottom: 12px;
  border-bottom: 1px solid var(--line);
}

.reading { max-width: 860px; }

.reading-passage {
  display: grid;
  grid-template-columns: 60px minmax(0, 1fr);
  gap: 12px;
  padding: 6px 0;
  border-top: 1px solid color-mix(in srgb, var(--line) 60%, transparent);
  scroll-margin-top: calc(var(--docview-head, 150px) + 56px);
  border-radius: 8px;
}

.reading-passage.flash { background: color-mix(in srgb, var(--highlight) 45%, transparent); }

.reading-margin {
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 2px;
  padding-top: 7px;
  font-size: 12px;
  color: var(--ink-light);
  text-align: right;
}

.reading-number { font-weight: 700; color: var(--ink-soft); font-variant-numeric: tabular-nums; }
.reading-pages { font-size: 11.5px; }
.reading-review { font-size: 12px; }

.reading-text {
  margin: 0;
  font-size: 15px;
  /* Ruim, zodat gestapelde onderlijningen elkaar en de volgende regel niet
   * raken. Dit getal hoort bij de offsets onderaan dit bestand. */
  line-height: 2.15;
  color: var(--ink);
  overflow-wrap: anywhere;
}

.reading-markers { margin: 0 0 4px; font-size: 12.5px; color: var(--ink-soft); }
.mark.flash { background: var(--highlight); border-radius: 3px; }

.reading-more { display: flex; flex-direction: column; align-items: center; gap: 6px; margin-top: 18px; }
.reading-end { margin: 22px 0 0 72px; font-size: 13px; color: var(--ink-light); }

/* Review: voortgang en één regel per passage. */
.review-progress { margin: 0 0 6px; }
.review-progress-head { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 12px; margin: 0 0 8px; font-size: 14px; }

.progress-bar {
  display: flex;
  height: 10px;
  overflow: hidden;
  background: var(--gated-fill);
  border: 1px solid var(--line);
  border-radius: 999px;
}

.progress-part { flex-basis: 0; min-width: 3px; }
.progress-complete { background: var(--good); }
.progress-partial { background: var(--caution); }
.progress-stale { background: var(--warn); }
.progress-unreviewed { background: transparent; }

.review-actions { display: flex; flex-wrap: wrap; gap: 8px; margin: 14px 0 4px; }
.review-notes { margin: 10px 0 0; padding-left: 18px; font-size: 13px; color: var(--warn); }
.passage-filter { display: flex; flex-wrap: wrap; gap: 6px; margin: 18px 0 8px; }

.passage-rows { list-style: none; margin: 0; padding: 0; border-top: 1px solid var(--line); }

.passage-row {
  display: grid;
  grid-template-columns: 52px minmax(0, 1.4fr) minmax(0, 1fr) auto auto;
  align-items: center;
  gap: 6px 14px;
  min-height: 42px;
  padding: 6px 4px;
  border-bottom: 1px solid var(--line);
  font-size: 13.5px;
}

.passage-row:hover { background: color-mix(in srgb, var(--paper) 70%, transparent); }
.passage-row-number { font-weight: 700; color: var(--ink-soft); font-variant-numeric: tabular-nums; }
.passage-row-where { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; color: var(--ink); }
.passage-row-found { font-size: 13px; color: var(--ink-soft); font-variant-numeric: tabular-nums; }
.passage-row-state { display: flex; flex-wrap: wrap; gap: 4px; justify-content: flex-end; }
.passage-row-actions { display: flex; align-items: center; gap: 10px; justify-content: flex-end; white-space: nowrap; }


.review-chip.state-complete { color: var(--good); border-color: var(--good); background: transparent; }
.review-chip.state-partial { color: var(--caution); border-color: var(--caution); background: transparent; }
.review-chip.state-stale { color: var(--warn); border-color: var(--warn); background: var(--warn-fill); }
.review-chip.state-unreviewed { color: var(--ink-soft); border-color: var(--line-strong); background: transparent; }

@media (max-width: 760px) {
  /* Op een smal scherm zou de vaste kop een derde van het beeld innemen. */
  .docview-head { position: static; margin: 0 -16px; padding: 10px 16px 0; }
  .docview-title { flex-basis: 100%; font-size: 17px; }
  .docview-panel { padding: 14px 14px 18px; }
  .reading-passage { grid-template-columns: 40px minmax(0, 1fr); gap: 8px; scroll-margin-top: 16px; }
  .reading-end { margin-left: 48px; }
  .passage-row { grid-template-columns: 44px minmax(0, 1fr) auto; }
  .passage-row-found { grid-column: 2 / -1; }
  .passage-row-state { grid-column: 2; justify-content: flex-start; }
  .passage-row-actions { grid-column: 3; }
}

/* ---------------------------------------------------- markeringen in tekst */
/*
 * Onderlijnen en niet arceren: een achtergrondvlak maakt de tekst zwaarder te
 * lezen en laat overlappende detecties in elkaar overlopen.
 *
 * `border-bottom` en niet `text-decoration`, want een element draagt maar één
 * onderstreping. Geneste elementen stapelen wél: elk niveau krijgt een eigen
 * `padding-bottom`, dus de binnenste detectie tekent zijn lijn dicht bij de
 * tekst en de buitenste eronder. Zo blijven ze allebei zichtbaar.
 */

.mark {
  /* De kleur komt als inline stijl van de server; `currentColor` laat de rand
   * hem volgen zonder hem hier te herhalen. */
  border-bottom: 2px solid currentColor;
  padding-bottom: 2px;
}

.mark[data-depth="1"] { padding-bottom: 6px; }
.mark[data-depth="2"] { padding-bottom: 10px; }
.mark[data-depth="3"] { padding-bottom: 14px; }
.mark[data-depth="4"] { padding-bottom: 18px; }

.mark:hover,
.mark.linked {
  background: color-mix(in srgb, currentColor 14%, transparent);
  border-radius: 2px;
}

/* Een markering met een symbool krijgt een dubbele lijn: kleur alleen is niet
 * genoeg om "hier hoort een symbool bij" over te brengen. */
.mark.has-symbol { border-bottom-style: double; border-bottom-width: 4px; }

.mark-text { color: var(--ink); }

.legend {
  display: flex;
  flex-wrap: wrap;
  gap: 4px 12px;
  margin: 9px 0 0;
  padding: 0;
  list-style: none;
  font-size: 12px;
  color: var(--ink-soft);
}

.legend li { display: inline-flex; align-items: center; gap: 5px; }

.legend .swatch {
  width: 14px;
  height: 0;
  border-bottom: 2px solid currentColor;
  display: inline-block;
}

/* ------------------------------------------------------ search evidence --- */

/* Waarom een document in de uitslag staat.
 *
 * Dit blok staat in de kaartkop, onder de badges, zodat het zichtbaar is zonder
 * het document te openen -- dat is het hele punt van zoeken op betekenis.
 *
 * Het heeft een eigen kop en een eigen achtergrond, en dat is de kern van de
 * wijziging: de badges eronder (Strategic, Intelligence, Force Protection) zijn
 * eigenschappen van het *document* en niet de reden dat het gevonden is. Zolang
 * ze er hetzelfde uitzagen, las een lezer ze als de reden. Nu is er één blok
 * dat "search evidence" heet en één dat "document metadata" is, en het verschil
 * is te zien zonder het te hoeven weten.
 */

.evidence {
  margin-top: 12px;
  padding: 11px 13px 12px;
  border: 1px solid var(--line);
  border-radius: 9px;
  background: var(--bluf-fill);
}

.evidence-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 12px;
  margin-bottom: 9px;
}

.evidence-title {
  margin: 0;
  font-size: 11.5px;
  font-weight: 700;
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-light);
}

/* De woorden die werkelijk in de passage gevonden zijn. Geen uitleg van een
 * model -- een vaststelling over de tekst. Zie service.py. */
.evidence-concepts {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 6px;
  margin: 0;
}

.evidence-why {
  margin: 6px 0 2px;
  font-size: 0.92em;
}

.evidence-why-label {
  display: inline-block;
  font-weight: 600;
  margin-bottom: 2px;
}

.evidence-why-partial .evidence-why-label { color: var(--caution); }
.evidence-why-semantic .evidence-why-label { color: var(--ink-soft); }

.evidence-reasons {
  margin: 0;
  padding-left: 1.2em;
}

.evidence-reasons li { margin: 1px 0; }

.evidence-duplicates {
  margin: 4px 0 0;
  font-size: 0.88em;
  color: var(--ink-soft);
}

.evidence-concepts-label {
  font-size: 11.5px;
  color: var(--ink-light);
}

.concept {
  padding: 1px 7px;
  border: 1px solid var(--classification);
  border-radius: 999px;
  font-size: 11.5px;
  font-weight: 600;
  color: var(--classification);
  background: var(--paper);
}

/* De relevantie als band. Het percentage staat erachter en is kleiner: het is
 * de bijzaak, de band is de hoofdzaak. Zie models.relevance_band. */
.relevance {
  display: inline-flex;
  align-items: baseline;
  gap: 5px;
  padding: 1px 8px;
  border-radius: 999px;
  font-size: 11px;
  font-weight: 660;
  letter-spacing: .02em;
}

.relevance-value { font-weight: 500; opacity: .75; font-variant-numeric: tabular-nums; }

.relevance-high   { background: var(--good); color: #fff; }
.relevance-medium { background: var(--caution); color: #fff; }
.relevance-low    { background: var(--line); color: var(--ink-soft); }

/* Het gevonden woord in de passage. Een achtergrond en geen kleurwissel: de
 * tekst eromheen blijft leesbaar, en bij afdrukken of in hoog contrast
 * verdwijnt de markering niet. */
mark.hit {
  padding: 0 1px;
  border-radius: 3px;
  background: var(--highlight);
  color: inherit;
  font-weight: 640;
}

.passages {
  display: grid;
  gap: 8px;
  margin-top: 12px;
}

.passage {
  padding: 10px 13px;
  background: var(--paper);
  border: 1px solid var(--line);
  border-left: 3px solid var(--classification);
  border-radius: 8px;
}

.evidence .passage + .passage { margin-top: 8px; }

.passage-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 10px;
  margin: 0 0 5px;
}

.passage-label {
  font-size: 11.5px;
  font-weight: 640;
  letter-spacing: .03em;
  text-transform: uppercase;
  color: var(--classification);
}

.passage-where {
  font-size: 12.5px;
  color: var(--ink-light);
}

.passage-text {
  margin: 0;
  font-size: 14px;
  color: var(--ink);
}

/* ----------------------------------------------------------------------- */

@media (max-width: 700px) {
  .wrap { padding: 0 16px; }
  .document-head { grid-template-columns: 1fr; }
  .document-actions { grid-column: 1; grid-row: auto; justify-content: flex-start; }
  .count { margin-left: 0; width: 100%; }
  .semantic-inner { align-items: stretch; }
  .semantic-field { flex: 1 1 100%; }
  .semantic-inner .button { flex: 1 1 auto; justify-content: center; }
  /* Op een telefoon is een symboolkaart nog zo'n 305px breed. Een kolom van
   * 112px laat daar te weinig over voor een naam als "Movement and Manoeuvre -
   * Special Operations Forces (SOF) - Ground"; met 88px scheelt dat twee
   * regels, en het symbool krimpt via max-width mee met behoud van zijn
   * verhouding in plaats van afgesneden te worden. */
  .symbol { gap: 10px; padding: 10px 11px 10px 9px; }
  .symbol-graphic { flex-basis: 88px; }
}

/* Een melding bij de rangorde (bijvoorbeeld: de reranker faalde, de resultaten
 * staan zonder rangorde). Gewone tekst, onopvallend maar leesbaar. */
.ranking-notice {
  margin: 0.25rem 0 0;
  font-size: 0.85rem;
  color: var(--ink-soft);
  font-style: italic;
}

/* ------------------------------------------------ waarnemingslogboek --- */

/* Reconciliation en Observations (workspace.js). Bovenaan één regel met wat dit
 * overzicht is; daaronder de balk die blijft staan (zoeken, weergave, en waar
 * de lezer is); dan links de filters en rechts de lijst. Een waarneming is een
 * regel: tijd, de zin, het document, het model. De entiteiten zijn omlijnd met
 * de kleur van hun soort, zoals de detectiebadges in Collation. */

.workspace-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 4px 16px;
  padding-top: 16px;
  padding-bottom: 10px;
}

.workspace-title {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 14px;
  min-width: 0;
}

.workspace-title h1 {
  margin: 0;
  font-size: 22px;
  letter-spacing: -.01em;
}

.workspace-summary {
  margin: 0;
  font-size: 13.5px;
  color: var(--ink-soft);
}

.summary-badge {
  display: inline-block;
  margin-right: 2px;
  padding: 0 7px;
  font-size: 11.5px;
  font-weight: 700;
  line-height: 1.6;
  letter-spacing: .03em;
  color: var(--classification);
  background: var(--classification-fill);
  border: 1px solid var(--classification-line);
  border-radius: 5px;
}

/* De balk: blijft bovenaan staan, en draagt zoeken, de weergave, de
 * hulpmiddelen en op de tweede regel het aantal, de actieve filters en waar
 * de lezer is. */

.workspace-bar-inner {
  display: grid;
  grid-template-columns: minmax(220px, 1fr) auto auto;
  grid-template-areas:
    "search views tools"
    "status status status";
  align-items: center;
  gap: 8px 12px;
  padding-top: 10px;
  padding-bottom: 8px;
}

.workspace-search { grid-area: search; position: relative; min-width: 0; }
.views { grid-area: views; }
.workspace-tools { grid-area: tools; display: flex; gap: 6px; align-items: center; }
.workspace-status {
  grid-area: status;
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px 10px;
  min-height: 24px;
}

.workspace-search input {
  width: 100%;
  padding: 8px 12px;
  font: inherit;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 8px;
}

.workspace-search input:focus-visible { outline: 2px solid var(--classification); outline-offset: 1px; }

.compact-choice select { padding-top: 7px; padding-bottom: 7px; }
.compact-choice[hidden] { display: none; }

.views {
  display: inline-flex;
  padding: 3px;
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 9px;
}

.view {
  display: inline-flex;
  align-items: baseline;
  gap: 6px;
  padding: 5px 11px;
  font: inherit;
  font-size: 13.5px;
  font-weight: 600;
  color: var(--ink-soft);
  background: none;
  border: 0;
  border-radius: 6px;
  cursor: pointer;
  white-space: nowrap;
}

.view:hover { color: var(--ink); }

.view[aria-selected="true"] {
  color: var(--classification);
  background: var(--classification-fill);
}

.view:focus-visible { outline: 2px solid var(--classification); outline-offset: 1px; }

.view-count {
  font-size: 12px;
  font-weight: 550;
  color: var(--ink-light);
  font-variant-numeric: tabular-nums;
}

.view[aria-selected="true"] .view-count { color: var(--classification); }

.workspace-status .count { margin: 0; font-size: 13px; color: var(--ink-soft); white-space: nowrap; }

.chips { display: flex; flex-wrap: wrap; gap: 6px; align-items: center; }

.chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  max-width: 280px;
  padding: 1px 4px 1px 9px;
  font: inherit;
  font-size: 12.5px;
  font-weight: 600;
  color: var(--classification);
  background: var(--classification-fill);
  border: 1px solid var(--classification-line);
  border-radius: 999px;
  cursor: pointer;
}

.chip > span:first-child { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }

.chip-x {
  display: inline-grid;
  place-items: center;
  width: 18px;
  height: 18px;
  font-size: 14px;
  line-height: 1;
  border-radius: 50%;
}

.chip:hover .chip-x { background: var(--classification-line); }
.chip:focus-visible { outline: 2px solid var(--classification); outline-offset: 1px; }

.period {
  margin: 0 0 0 auto;
  font-size: 13px;
  font-weight: 650;
  color: var(--ink);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 40%;
}

.filters-toggle { display: none; }

/* Suggesties onder het zoekveld: entiteiten, met soort en aantallen. */

.suggestions {
  position: absolute;
  z-index: 40;
  top: calc(100% + 4px);
  left: 0;
  right: 0;
  max-height: 60vh;
  margin: 0;
  padding: 4px;
  overflow: auto;
  list-style: none;
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 10px;
  box-shadow: var(--shadow-raised);
}

.suggestion-head {
  padding: 6px 10px 4px;
  font-size: 11.5px;
  color: var(--ink-light);
}

.suggestion {
  display: flex;
  flex-direction: column;
  gap: 1px;
  padding: 7px 10px 7px 12px;
  border-left: 3px solid var(--kind, var(--line-strong));
  border-radius: 6px;
  cursor: pointer;
}

.suggestion.is-active,
.suggestion:hover { background: var(--classification-fill); }

.suggestion-name { font-size: 14px; font-weight: 650; color: var(--ink); }
.suggestion-meta { font-size: 12px; color: var(--ink-soft); }

/* De uitleg: de procesbalk, open op verzoek. */

.stages-box {
  margin: 0 0 12px;
  padding: 14px 16px 12px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--round);
  box-shadow: var(--shadow);
}

.stages {
  display: grid;
  grid-template-columns: repeat(6, minmax(0, 1fr));
  margin: 0;
  padding: 0;
  list-style: none;
}

.stage {
  position: relative;
  display: grid;
  grid-template-rows: auto auto 1fr;
  gap: 3px;
  padding: 0 10px 8px 0;
}

.stage:not(:last-child)::after {
  content: "";
  position: absolute;
  top: 10px;
  left: 24px;
  right: 2px;
  height: 2px;
  background: var(--line-strong);
}

.stage.is-done:not(:last-child)::after { background: var(--classification); }

.stage-dot {
  position: relative;
  z-index: 1;
  display: inline-grid;
  place-items: center;
  width: 22px;
  height: 22px;
  font-size: 12px;
  font-weight: 800;
  line-height: 1;
  color: var(--card);
  background: var(--card);
  border: 2px solid var(--line-strong);
  border-radius: 50%;
}

.stage.is-done .stage-dot { background: var(--classification); border-color: var(--classification); }

.stage.is-marked .stage-dot {
  border-color: var(--classification);
  background: linear-gradient(90deg, var(--classification) 50%, var(--card) 50%);
}

.stage-name { font-size: 13.5px; font-weight: 650; color: var(--ink); }
.stage.is-off .stage-name { color: var(--ink-light); font-weight: 550; }
.stage-text { font-size: 12.5px; line-height: 1.4; color: var(--ink-soft); }
.stage.is-off .stage-text { color: var(--ink-light); }

.stage.is-current .stage-name {
  justify-self: start;
  margin-left: -6px;
  padding: 0 6px;
  color: var(--classification);
  background: var(--classification-fill);
  border-radius: 5px;
}

.stages-note {
  max-width: 88ch;
  margin: 8px 0 0;
  padding-top: 10px;
  border-top: 1px solid var(--line);
  font-size: 13px;
  line-height: 1.5;
  color: var(--ink-soft);
}

/* Filters links, lijst rechts. De filters blijven staan en scrollen op zich. */

.workspace-main {
  display: grid;
  grid-template-columns: 236px minmax(0, 1fr);
  gap: 24px;
  align-items: start;
  padding-top: 16px;
  padding-bottom: 60px;
}

.workspace-content { min-width: 0; }

.facets {
  position: sticky;
  top: var(--workspace-bar, 96px);
  max-height: calc(100vh - var(--workspace-bar, 96px) - 12px);
  overflow: auto;
  padding: 2px 6px 16px 2px;
  scrollbar-width: thin;
}

.facets-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  margin-bottom: 6px;
}

.facets-title {
  margin: 0;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--ink-soft);
}

.facet {
  margin: 0 0 14px;
  padding: 10px 0 0;
  border: 0;
  border-top: 1px solid var(--line);
  min-width: 0;
}

.facet-title {
  display: flex;
  justify-content: space-between;
  width: 100%;
  padding: 0;
  margin-bottom: 6px;
  font-size: 13px;
  font-weight: 650;
  color: var(--ink);
}

.facet-clear {
  padding: 0;
  font: inherit;
  font-size: 12px;
  font-weight: 500;
  color: var(--classification);
  background: none;
  border: 0;
  cursor: pointer;
}

.facet-options { margin: 0; padding: 0; list-style: none; }

.facet-option {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 2px 0;
}

.facet-option input { flex: none; margin: 0; accent-color: var(--classification); }

.facet-option label {
  display: flex;
  flex: 1 1 auto;
  justify-content: space-between;
  gap: 8px;
  min-width: 0;
  font-size: 13px;
  color: var(--ink);
  cursor: pointer;
}

/* Twee regels en dan pas afkappen: "Samengevoegd over documenten heen" of
 * "Acceptée comme connaissance" pasten niet op één regel. */
.facet-label {
  display: -webkit-box;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
  overflow: hidden;
  overflow-wrap: anywhere;
}
.facet-count { flex: none; font-size: 12px; color: var(--ink-light); font-variant-numeric: tabular-nums; }
.facet-option.is-zero label { color: var(--ink-light); }

.facet-more { margin-top: 4px; font-size: 12.5px; }

.facet-search {
  width: 100%;
  margin: 0 0 6px;
  padding: 5px 8px;
  font: inherit;
  font-size: 13px;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--line-strong);
  border-radius: 6px;
}

.facet-range { display: flex; flex-direction: column; gap: 4px; font-size: 13px; }
.facet-range input { width: 100%; accent-color: var(--classification); }
.facet-range-value { font-weight: 600; color: var(--ink); }
.facet-note { margin: 4px 0 0; font-size: 12px; line-height: 1.4; color: var(--ink-light); }

/* Het histogram: jaren, of de maanden van het gekozen jaar. */

.histogram {
  margin: 0 0 14px;
  padding: 10px 14px 8px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--round);
  box-shadow: var(--shadow);
}

.histogram-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 2px 12px;
  margin-bottom: 6px;
}

.histogram-crumbs { display: flex; align-items: baseline; gap: 6px; font-size: 13.5px; font-weight: 600; }
.histogram-crumbs .link-button { font-weight: 600; }
.histogram-crumbs .is-current { color: var(--ink); text-decoration: none; cursor: default; }
.crumb-sep { color: var(--ink-light); }
.crumb-current { color: var(--ink); }
.histogram-note { font-size: 12px; color: var(--ink-light); }

.histogram-bars {
  display: flex;
  align-items: stretch;
  gap: 3px;
  height: 64px;
}

.histogram-bin {
  display: flex;
  flex: 1 1 0;
  flex-direction: column;
  min-width: 0;
  padding: 0;
  font: inherit;
  background: none;
  border: 0;
  border-radius: 4px;
  cursor: pointer;
}

.histogram-bin:disabled { cursor: default; }

.histogram-bar-area {
  display: flex;
  flex: 1 1 auto;
  align-items: flex-end;
  padding: 0 2px;
  border-radius: 4px 4px 0 0;
}

.histogram-bin:not(:disabled):hover .histogram-bar-area { background: var(--classification-fill); }

.histogram-bar {
  width: 100%;
  min-height: 0;
  background: color-mix(in srgb, var(--classification) 55%, var(--card));
  border-radius: 3px 3px 0 0;
}

.histogram-bin.is-selected .histogram-bar { background: var(--classification); }
.histogram-bin.is-empty .histogram-bar { background: transparent; }

.histogram-label {
  padding-top: 3px;
  font-size: 11px;
  line-height: 1.2;
  color: var(--ink-soft);
  text-align: center;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: clip;
  border-top: 1px solid var(--line-strong);
}

.histogram-bin.is-selected .histogram-label { color: var(--classification); font-weight: 700; }
.histogram-short { display: none; }
.histogram-bin:focus-visible { outline: 2px solid var(--classification); outline-offset: 1px; }

.histogram-gap {
  align-self: flex-end;
  flex: 0 0 18px;
  padding-bottom: 1px;
  font-size: 12px;
  color: var(--ink-light);
  text-align: center;
}

/* De lijst. Alleen de items in beeld staan in de DOM, absoluut geplaatst; de
 * hoogte van de lijst is die van alles samen. */

.list-head { margin: 0 0 8px; }

.list-note,
.obs-empty {
  margin: 0 0 8px;
  font-size: 13px;
  color: var(--ink-soft);
}

.observation-log {
  position: relative;
  overflow-anchor: none;
  contain: layout;
}

.vitem {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
}

.obs-period {
  display: flex;
  align-items: baseline;
  gap: 10px;
  padding: 14px 4px 6px;
}

.obs-period-dot {
  align-self: center;
  width: 10px;
  height: 10px;
  border: 2px solid var(--classification);
  border-radius: 50%;
  background: var(--card);
}

.obs-period-label { font-size: 15px; font-weight: 700; color: var(--ink); }
.obs-period-count { font-size: 12.5px; color: var(--ink-light); }

/* Een waarneming: dicht één regel, open een kaartje. */

.obs-entry {
  display: grid;
  grid-template-columns: 118px minmax(0, 1fr) minmax(0, 160px) 40px 26px;
  align-items: center;
  gap: 10px;
  padding: 6px 8px 6px 12px;
  background: var(--card);
  border: 1px solid var(--line);
  border-top-width: 0;
  cursor: pointer;
}

.obs-period + .obs-entry,
.vitem.obs-entry:first-child { border-top-width: 1px; }

.obs-entry:hover { background: color-mix(in srgb, var(--classification-fill) 45%, var(--card)); }

.obs-entry.is-open {
  grid-template-columns: 118px minmax(0, 1fr) 26px;
  align-items: start;
  padding-top: 10px;
  padding-bottom: 10px;
  cursor: default;
  background: var(--card);
}

.observation-log[data-view="timeline"] .obs-entry,
.observation-log[data-view="documents"] .obs-entry { border-top-width: 1px; margin-top: -1px; }

.obs-entry.is-accepted { box-shadow: inset 3px 0 0 var(--classification); }

.obs-time {
  font: 12px/1.5 ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  color: var(--ink);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.obs-entry.is-open .obs-time { white-space: normal; overflow-wrap: anywhere; padding-top: 2px; }

.obs-time.none { font-family: inherit; font-style: italic; color: var(--ink-light); }

.obs-end {
  display: block;
  margin-top: 2px;
  font-size: 11.5px;
  font-style: normal;
  color: var(--ink-soft);
}

.obs-entry.is-line .obs-end { display: none; }

.obs-body { min-width: 0; }

.obs-statement {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 5px 8px;
  margin: 0;
}

/* Dicht: de zin op één regel als ze past, anders op twee -- het voorwerp van
 * een relatie mag niet wegvallen achter een lang onderwerp. Wat dan nog niet
 * past (de laatste rollen van een event), valt weg; open staat alles. */
.obs-entry.is-line .obs-statement {
  gap: 3px 8px;
  max-height: 3.3em;
  overflow: hidden;
}

.obs-entry.is-line .obs-statement > * { flex: none; max-width: 100%; }
.obs-entry.is-line .obs-entity { overflow: hidden; text-overflow: ellipsis; }

.obs-roles { display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px 14px; margin: 6px 0 0; }

.obs-source {
  font-size: 12.5px;
  color: var(--ink-soft);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.obs-confidence {
  font-size: 12px;
  color: var(--ink-light);
  text-align: right;
  font-variant-numeric: tabular-nums;
}

.row-toggle {
  width: 24px;
  height: 24px;
  padding: 0;
  background: none;
  border: 0;
  border-radius: 5px;
  cursor: pointer;
}

.row-toggle::before {
  content: "";
  display: block;
  width: 7px;
  height: 7px;
  margin: 0 auto;
  border-right: 2px solid var(--ink-soft);
  border-bottom: 2px solid var(--ink-soft);
  transform: translateY(-2px) rotate(45deg);
}

.row-toggle[aria-expanded="true"]::before { transform: translateY(2px) rotate(-135deg); }
.row-toggle:hover { background: var(--classification-fill); }
.row-toggle:focus-visible { outline: 2px solid var(--classification); }

.obs-entity {
  display: inline-flex;
  align-items: baseline;
  gap: 5px;
  padding: 0 7px;
  font-size: 13.5px;
  font-weight: 560;
  line-height: 1.55;
  border: 1px solid var(--line-strong);
  border-left: 3px solid var(--kind, var(--line-strong));
  border-radius: 6px;
  background: var(--card);
  white-space: nowrap;
}

.obs-entry.is-open .obs-entity { white-space: normal; overflow-wrap: anywhere; }

.obs-entity.missing { color: var(--ink-light); border-left-color: var(--line-strong); }

button.obs-entity {
  margin: 0;
  font: inherit;
  font-size: 13.5px;
  font-weight: 560;
  color: var(--ink);
  text-align: left;
  cursor: pointer;
}

.obs-entry.is-open button.obs-entity { flex-direction: column; align-items: flex-start; gap: 0; }
button.obs-entity:hover { background: var(--classification-fill); }
button.obs-entity:focus-visible { outline: 2px solid var(--classification); outline-offset: 2px; }

.obs-entity.is-focus {
  background: var(--classification-fill);
  border-color: var(--classification);
  box-shadow: 0 0 0 1px var(--classification);
}

.obs-entity.is-open { border-style: dashed; border-left-style: solid; }

.obs-entity-source { font-size: 12px; font-weight: 450; font-style: italic; color: var(--ink-soft); }

.obs-entity-mark {
  padding: 0 5px;
  font-size: 10.5px;
  font-weight: 700;
  font-style: normal;
  line-height: 1.55;
  color: var(--classification);
  background: var(--classification-fill);
  border-radius: 4px;
  white-space: nowrap;
}

.obs-entity-mark.open { color: var(--warn); background: var(--warn-fill); }

.obs-relation { font-size: 13px; font-style: italic; color: var(--ink-soft); white-space: nowrap; }
.obs-relation::before { content: "→ "; font-style: normal; }

.obs-activity {
  font-size: 11.5px;
  font-weight: 700;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--ink-soft);
}

.obs-role, .obs-attribute { display: inline-flex; align-items: baseline; gap: 5px; }
.obs-role-name { font-size: 12px; color: var(--ink-light); }
.obs-attribute-value { font-size: 13px; color: var(--ink); }

.obs-meta {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 12px;
  margin: 8px 0 0;
  font-size: 12.5px;
  color: var(--ink-light);
}

.obs-document {
  color: var(--classification);
  font-weight: 550;
  text-decoration: none;
  overflow-wrap: anywhere;
}

.obs-document:hover { text-decoration: underline; }

.obs-flag {
  padding: 0 7px;
  font-size: 11.5px;
  font-weight: 650;
  border-radius: 5px;
  white-space: nowrap;
}

.obs-entry.is-line .obs-body { display: flex; align-items: center; gap: 8px; min-width: 0; }
.obs-entry.is-line .obs-inline-flag { flex: none; }
.obs-entry.is-line .obs-body > .obs-statement { flex: 1 1 auto; min-width: 0; }

.obs-flag.accepted {
  color: var(--classification);
  background: var(--classification-fill);
  border: 1px solid var(--classification-line);
}

.obs-flag.reviewed,
.obs-flag.note {
  color: var(--gated);
  background: var(--gated-fill);
  border: 1px solid var(--line);
}

/* Per document: een kop die open- en dichtklapt. */

.doc-head {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: center;
  gap: 0 12px;
  margin-top: 6px;
  padding: 8px 12px 8px 6px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: 8px;
}

.doc-head.is-open {
  margin-top: 12px;
  border-radius: 8px 8px 0 0;
  background: var(--classification-fill);
  border-color: var(--classification-line);
}

.doc-toggle {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  min-width: 0;
  padding: 2px 4px;
  font: inherit;
  font-size: 14.5px;
  font-weight: 650;
  color: var(--ink);
  text-align: left;
  background: none;
  border: 0;
  border-radius: 5px;
  cursor: pointer;
}

.doc-toggle:focus-visible { outline: 2px solid var(--classification); }

.doc-chevron {
  flex: none;
  width: 7px;
  height: 7px;
  border-right: 2px solid var(--ink-soft);
  border-bottom: 2px solid var(--ink-soft);
  transform: rotate(-45deg);
}

.doc-toggle[aria-expanded="true"] .doc-chevron { transform: rotate(45deg); }
.doc-name { overflow-wrap: anywhere; }
.doc-meta {
  grid-column: 1 / -1;
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 2px 10px;
  margin: 0 0 0 23px;
  font-size: 12.5px;
  color: var(--ink-soft);
}
.doc-open { font-size: 12.5px; font-weight: 600; color: var(--classification); text-decoration: none; }
.doc-open:hover { text-decoration: underline; }

/* Entiteiten: een tabel. */

.entity-head,
.entity-row {
  display: grid;
  grid-template-columns: minmax(0, 2fr) minmax(0, 1fr) 92px 104px minmax(0, 1.5fr);
  align-items: center;
  gap: 12px;
}

.entity-head {
  padding: 6px 12px;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: .03em;
  text-transform: uppercase;
  color: var(--ink-soft);
  border-bottom: 1px solid var(--line-strong);
}

.entity-sort {
  display: inline-flex;
  gap: 4px;
  padding: 0;
  font: inherit;
  color: inherit;
  letter-spacing: inherit;
  text-transform: inherit;
  text-align: left;
  background: none;
  border: 0;
  cursor: pointer;
}

.entity-sort.number { justify-content: flex-end; }
.entity-sort.is-current { color: var(--classification); }

.entity-row {
  width: 100%;
  min-height: 44px;
  padding: 7px 12px;
  font: inherit;
  font-size: 13.5px;
  color: var(--ink);
  text-align: left;
  background: var(--card);
  border: 0;
  border-bottom: 1px solid var(--line);
  cursor: pointer;
}

.entity-row:hover,
.entity-row.is-focus { background: var(--classification-fill); }
.entity-row:focus-visible { outline: 2px solid var(--classification); outline-offset: -2px; }

.entity-row-name { display: flex; align-items: center; gap: 8px; min-width: 0; font-weight: 600; overflow-wrap: anywhere; }
.entity-row-bar { flex: none; align-self: stretch; width: 3px; border-radius: 2px; background: var(--kind, var(--line-strong)); }
.entity-row-type { color: var(--ink-soft); font-size: 12.5px; }
.entity-row-number { text-align: right; font-variant-numeric: tabular-nums; }
.entity-row-identity { font-size: 12.5px; color: var(--ink-soft); }
.entity-row-identity.is-merged { color: var(--classification); font-weight: 600; }
.entity-row-identity.is-open { color: var(--warn); font-weight: 600; }

/* De entiteit in de kijker. */

.focus {
  margin: 0 0 14px;
  padding: 12px 16px;
  background: var(--card);
  border: 1px solid var(--classification-line);
  border-left: 4px solid var(--kind, var(--classification));
  border-radius: var(--round);
  box-shadow: var(--shadow);
}

.focus.is-open { border-color: var(--line-strong); border-left-color: var(--warn); }

.focus-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px 16px;
}

.focus-heading { flex: 1 1 auto; min-width: 0; }

.focus-kicker {
  margin: 0;
  font-size: 11.5px;
  font-weight: 700;
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-soft);
}

.focus-title { margin: 1px 0 0; font-size: 20px; font-weight: 700; line-height: 1.25; overflow-wrap: anywhere; }
.focus-where { margin: 0; font-size: 13px; color: var(--ink-soft); }
.focus-where .is-current { color: var(--ink); font-weight: 650; text-decoration: none; }

.focus-verdict { max-width: 90ch; margin: 8px 0 0; font-size: 13.5px; line-height: 1.5; color: var(--ink); }
.focus.is-open .focus-verdict strong { color: var(--warn); }

.focus-details { margin-top: 6px; font-size: 13px; }
.focus-details summary { color: var(--classification); font-weight: 600; cursor: pointer; }

.focus-facts {
  display: grid;
  grid-template-columns: max-content minmax(0, 1fr);
  gap: 6px 16px;
  margin: 10px 0 2px;
}

.focus-fact { display: contents; }
.focus-fact dt { font-size: 12.5px; font-weight: 600; color: var(--ink-soft); }

.focus-fact dd {
  display: flex;
  flex-wrap: wrap;
  gap: 4px 6px;
  margin: 0;
  font-size: 13px;
  color: var(--ink);
  overflow-wrap: anywhere;
}

.focus-spelling,
.focus-candidate {
  padding: 0 7px;
  font: inherit;
  font-size: 12.5px;
  line-height: 1.6;
  color: var(--ink);
  background: var(--paper);
  border: 1px solid var(--line);
  border-radius: 5px;
  white-space: pre-wrap;
}

button.focus-candidate { cursor: pointer; color: var(--classification); }
button.focus-candidate:hover { background: var(--classification-fill); border-color: var(--classification-line); }
.focus-candidate.static { color: var(--ink-soft); }
.focus-more { align-self: center; font-size: 12.5px; color: var(--ink-light); }
.focus-evidence { font-size: 12.5px; color: var(--ink-soft); }

/* ---------------------------------------------------- smalle schermen --- */

@media (max-width: 1100px) {
  .workspace-bar-inner {
    grid-template-columns: minmax(0, 1fr) auto;
    grid-template-areas:
      "search search"
      "views tools"
      "status status";
  }
}

/* Onder 900 px verdwijnt de zijbalk; "Filters" klapt hem boven de lijst open. */
@media (max-width: 900px) {
  .workspace-main { grid-template-columns: minmax(0, 1fr); gap: 0; }
  .filters-toggle { display: inline-flex; }
  .facets {
    display: none;
    position: static;
    max-height: none;
    margin-bottom: 14px;
    padding: 12px 14px 4px;
    background: var(--card);
    border: 1px solid var(--line);
    border-radius: var(--round);
  }
  .workspace.show-facets .facets { display: block; }
  .stages { grid-template-columns: minmax(0, 1fr); gap: 2px; }
  .stage { grid-template-columns: 22px minmax(0, 1fr); grid-template-rows: auto auto; column-gap: 10px; padding: 0 0 8px; }
  .stage-dot { grid-row: 1 / span 2; }
  .stage:not(:last-child)::after { top: 22px; bottom: -2px; left: 10px; right: auto; width: 2px; height: auto; }
  .entity-head, .entity-row { grid-template-columns: minmax(0, 1fr) 70px 80px; }
  .entity-head > :nth-child(2), .entity-row > :nth-child(2),
  .entity-head > :nth-child(5), .entity-row > :nth-child(5) { display: none; }
}

@media (max-width: 640px) {
  /* Op een telefoon blijft de balk niet staan: vier regels bovenaan elk
   * scherm laten voor de lijst bijna niets over. */
  .workspace-bar { position: static; }
  .workspace-head { padding-top: 12px; }
  .workspace-summary { font-size: 12.5px; }
  .workspace-tools { flex-wrap: wrap; }
  .workspace-tools .button, .compact-choice select { padding: 6px 9px; font-size: 13px; }
  .compact-choice { flex: 1 1 auto; min-width: 0; }
  .histogram-long { display: none; }
  .histogram-short { display: inline; }
  .histogram-note { display: none; }
  .histogram-bars { height: 52px; gap: 2px; }
  .views { width: 100%; }
  .view { flex: 1 1 0; justify-content: center; padding: 5px 6px; }
  .workspace-bar-inner { grid-template-areas: "search search" "views views" "tools tools" "status status"; }
  .period { display: none; }
  .obs-entry { grid-template-columns: minmax(0, 1fr) 26px; gap: 2px 8px; padding: 6px 6px 6px 10px; }
  .obs-entry .obs-time { grid-column: 1; }
  .obs-entry .obs-body { grid-column: 1; }
  .obs-entry .row-toggle { grid-column: 2; grid-row: 1 / span 2; align-self: center; }
  .obs-entry .obs-source, .obs-entry .obs-confidence { display: none; }
  .obs-entry.is-open { grid-template-columns: minmax(0, 1fr) 26px; }
  .focus-facts { grid-template-columns: minmax(0, 1fr); gap: 2px; }
  .focus-fact dd { margin-bottom: 6px; }
  .histogram-label { font-size: 10px; }
}

/* ------------------------------------------------ de taalkeuze --- */

/* NL, FR, EN helemaal rechts in de omgevingsbalk (i18n.js). Op een pagina
 * zonder die balk staat ze in een eigen strook bovenaan. */

.language-switch {
  display: inline-flex;
  align-self: center;
  margin-bottom: 2px;
  border: 1px solid var(--line-strong);
  border-radius: 8px;
  overflow: hidden;
  background: var(--card);
}

.language-option {
  padding: 4px 8px;
  border: 0;
  background: transparent;
  color: var(--ink-soft);
  font: inherit;
  font-size: 12px;
  font-weight: 650;
  letter-spacing: .04em;
  cursor: pointer;
}

.language-option + .language-option { border-left: 1px solid var(--line-strong); }

.language-option:hover { color: var(--ink); }

.language-option[aria-pressed="true"] {
  background: var(--classification);
  color: var(--on-accent);
}

.language-option:focus-visible {
  outline: 2px solid var(--classification);
  outline-offset: -2px;
}

.language-strip {
  display: flex;
  justify-content: flex-end;
  align-items: center;
  gap: 8px;
  padding: 8px 24px;
  background: var(--card);
  border-bottom: 1px solid var(--line);
}

.environment-reality {
  display: flex;
  gap: 14px;
  margin: 0;
  padding: 0;
  border: 0;
  font-size: 14px;
}

.environment-reality label { display: inline-flex; align-items: center; gap: 6px; cursor: pointer; }

/* De oefenband. Geel zoals een oefenmarkering op papier, en in beide thema's
   even luid: ze mag niet wegvallen tegen een donkere achtergrond. */
.exercise-band {
  background: #f2c230;
  color: #1d1600;
  border-bottom: 2px solid #8a6a00;
}

.exercise-band-inner {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 4px 14px;
  padding-top: 6px;
  padding-bottom: 6px;
  font-size: 14px;
}

.exercise-band-mark { letter-spacing: 0.08em; }
.exercise-band-scenario { font-weight: 600; }
.exercise-band-note { flex: 1 1 auto; }
.exercise-band-link { color: inherit; font-weight: 600; }

.exercise-band-help-toggle {
  padding: 0;
  border: 0;
  background: none;
  color: inherit;
  font: inherit;
  text-decoration: underline;
  cursor: pointer;
}
.exercise-band-help-toggle::before { content: "ⓘ "; text-decoration: none; }

.exercise-band-help {
  padding-bottom: 10px;
  font-size: 14px;
  line-height: 1.45;
}
.exercise-band-help-lead { margin: 2px 0 4px; font-weight: 600; }
.exercise-band-help ul { margin: 0; padding-left: 20px; }
.exercise-band-help li + li { margin-top: 2px; }

/* De scenariopagina (scenario.html). */
.scn-main { display: grid; grid-template-columns: minmax(0, 1fr); gap: 18px; padding-bottom: 48px; }
.scn-card { min-width: 0; background: var(--card); border: 1px solid var(--line); border-radius: 10px; padding: 16px 18px; }
.scn-card h2 { margin: 0 0 8px; font-size: 18px; }
.scn-card h3 { margin: 18px 0 6px; font-size: 15px; }
.scn-hint { margin: 4px 0 8px; font-size: 13px; color: var(--ink-soft); }
.scn-bad, .scn-error { color: var(--warn); }
.scn-form { display: grid; grid-template-columns: repeat(auto-fill, minmax(200px, 1fr)); gap: 10px 14px; margin-top: 8px; }
.scn-form label { display: grid; gap: 4px; font-size: 13px; color: var(--ink-soft); }
.scn-form input, .scn-form select {
  padding: 7px 10px; font: inherit; color: var(--ink); background: var(--card);
  border: 1px solid var(--line-strong); border-radius: 8px; min-width: 0;
}
.scn-wide { grid-column: 1 / -1; }
.scn-actions { grid-column: 1 / -1; display: flex; align-items: center; gap: 12px; flex-wrap: wrap; }
.scn-status { font-size: 13px; color: var(--ink-soft); }
.scn-table-wrap { overflow-x: auto; }
.scn-table { width: 100%; border-collapse: collapse; font-size: 13px; }
.scn-table th, .scn-table td { text-align: left; padding: 5px 8px; border-bottom: 1px solid var(--line); vertical-align: top; }

/* De kennisbank: zoeken in de werkelijkheid, de oefening of beide. */
.knowledge-reality { display: inline-flex; align-items: center; gap: 8px; font-size: 14px; color: var(--ink-soft); }
.knowledge-reality select {
  padding: 7px 10px; font: inherit; color: var(--ink); background: var(--card);
  border: 1px solid var(--line-strong); border-radius: 8px;
}
.knowledge-reality > span { white-space: nowrap; }
.knowledge-reality-note { margin-left: 8px; }
.exercise-badge {
  display: inline-block; padding: 1px 8px; border-radius: 4px; font-size: 12px; font-weight: 700;
  letter-spacing: 0.08em; background: #f2c230; color: #1d1600; border: 1px solid #8a6a00;
}
.scn-retract { padding: 3px 10px; font-size: 12px; }
.scn-retracted { color: var(--ink-soft); font-style: italic; }

/* ------------------------------------------------------------ account --- */

/* De naam in de balk, met "Your account", "Users" en "Sign out" eronder
 * (session.js). */
.session-menu { position: relative; }

.session-name {
  list-style: none;
  white-space: nowrap;
}

.session-name::-webkit-details-marker { display: none; }
.session-name::after { content: "▾"; font-size: 12px; color: var(--ink-soft); }

.session-pop {
  position: absolute;
  right: 0;
  top: calc(100% + 6px);
  z-index: 40;
  min-width: 190px;
  display: flex;
  flex-direction: column;
  padding: 6px;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: 10px;
  box-shadow: var(--shadow-raised);
}

.session-who {
  display: flex;
  flex-direction: column;
  margin: 0 0 4px;
  padding: 6px 10px 8px;
  font-size: 13px;
  border-bottom: 1px solid var(--line);
}

.session-who span { color: var(--ink-soft); font-size: 12px; }

.session-pop a,
.session-pop button {
  display: block;
  padding: 7px 10px;
  font: inherit;
  font-size: 13.5px;
  text-align: left;
  color: var(--ink);
  text-decoration: none;
  background: none;
  border: 0;
  border-radius: 6px;
  cursor: pointer;
}

.session-pop a:hover,
.session-pop button:hover { background: var(--chunkzone); color: var(--classification); }

/* Wat je rol niet mag, zie je niet: session.js zet op body de rechten die
 * ontbreken (data-cannot), een knop draagt het recht dat hij vraagt
 * (data-needs). Gemak en geen grens: de server weigert het hoe dan ook
 * (webapp/account_routes.py). */
body[data-cannot~="review"] [data-needs="review"],
body[data-cannot~="annotate"] [data-needs="annotate"],
body[data-cannot~="collate"] [data-needs="collate"],
body[data-cannot~="adjudicate"] [data-needs="adjudicate"],
body[data-cannot~="publish"] [data-needs="publish"],
body[data-cannot~="manage"] [data-needs="manage"] { display: none !important; }

/* Alleen voor wie het mag zien, dus zonder data-needs: session.js zet ze. */
.admin-link { font-weight: 600; }
.read-only-badge {
  align-self: center;
  padding: 2px 8px;
  border: 1px solid var(--line, currentColor);
  border-radius: 999px;
  font-size: 12px;
  opacity: 0.8;
  white-space: nowrap;
}
/* Verificatiestatus van een referentiekoppeling (core 0.10.0). */
.focus-verification { font-size: 12px; color: var(--ink-soft); }
.focus-verification.verification-verified { color: var(--good); }
.focus-verification.verification-disputed { color: var(--conflict); }
.focus-verification.verification-unverified, .focus-verification.verification-stale { color: var(--warn); }

/* Wie een materieelmodel gebruikt (workspace.js, reference_operators.py). */
.focus-operator { display: inline-block; margin: 0 8px 2px 0; }
.focus-operator.ended { color: var(--ink-light); }
