/* Paardekooper Design — brand tokens, één bestand.
 *
 * REDESIGNRONDE "LEVEND" (2026-09-28). Dit bestand was tot deze ronde
 * `merkbasis/brand-tokens.css` LETTERLIJK, op de zelfgehoste `@font-face`-
 * regels na. Op Emiles expliciete opdracht (`03_redesign_2026-09/
 * 18_levend_2026-09-28/PLAN.md`, "Fonts en credits" + "Fundament") is de
 * typografie in deze ronde vervangen: Fraunces/Raleway/Jost → Bricolage
 * Grotesque/Boska/Schibsted Grotesk/IBM Plex Mono, met een nieuwe typeschaal
 * (mega/h1/h2/h3/lead/body/label) en vier kleurkandidaten als losse tokens.
 * Die opdracht staat UITDRUKKELIJK LOS van de Mainframe en van CLAUDE.md/
 * 00_masterplan: normaal zijn kleur en typografie voor déze site Mainframe-
 * eigendom (twee Claude-artefacten), maar deze ronde draait daarbuiten. Wil je
 * de oude merkbasis-typografie terug: `git log` op dit bestand.
 *
 * De KLEURTOKENS (colors.css hieronder) zijn in deze stap NIET aangeraakt —
 * het palet blijft de merkbasis, koper blijft de enige CTA-kleur (plan,
 * "Kleur"). Er zijn alleen vier KANDIDAAT-tokens bijgekomen die nog aan geen
 * enkele rol hangen; de keuze welke twee blijven is voor de art-director.
 *
 * Wil je een kleur wijzigen: wijzig dan wélke paletkleur een semantische rol
 * krijgt. Voeg nooit een hexwaarde toe die niet in de merkbasis of de vier
 * geteste kandidaten staat.
 */

/* ===== fonts.css — zelfgehost, tien bestanden, vier families =====
 *
 * Herkomst, licenties (OFL voor de drie Fontsource-families; Fontshare's ITF
 * Free Font License voor Boska — subsetten is daar met naam verboden, dus
 * Boska staat hier ongewijzigd) en de volledige rollentabel:
 * `public/fonts/HERKOMST.md`.
 */

/* --- Bricolage Grotesque — display: mega, h1, h2. Variabel op wght (200–800)
   ÉN wdth/font-stretch (75–100%): de mega-kop gebruikt een smallere stretch op
   grote schermen zonder een tweede bestand. --- */
@font-face {
  font-family: 'Bricolage Grotesque';
  src: url('/fonts/bricolage-grotesque-variable.woff2') format('woff2-variations');
  font-weight: 200 800;
  font-stretch: 75% 100%;
  font-style: normal;
  font-display: swap;
}
/* Fallback met CLS-correctie. Metrieken uit de woff2 gemeten (fontTools),
   size-adjust/ascent-override/descent-override berekend tegen Arial (de
   platform-fallback in de stack hieronder) volgens de gangbare formule
   (size-adjust = webfont-avgCharWidth ÷ fallback-avgCharWidth, genormaliseerd
   op unitsPerEm; ascent/descent-override = webfont-metriek ÷ size-adjust). */
@font-face {
  font-family: 'Bricolage Grotesque Fallback';
  src: local('Arial');
  size-adjust: 121.2%;
  ascent-override: 76.73%;
  descent-override: 22.28%;
}

/* --- Boska — de kop-serif, alleen h3. Echte cursief (font-style: italic),
   geen browser-schuinstand over de romein. FFL 2.0 verbiedt subsetten, dus
   deze twee bestanden zijn de ongewijzigde Fontshare-download. --- */
@font-face {
  font-family: 'Boska';
  src: url('/fonts/boska-regular.woff2') format('woff2');
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'Boska';
  src: url('/fonts/boska-500.woff2') format('woff2');
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'Boska';
  src: url('/fonts/boska-italic.woff2') format('woff2');
  font-weight: 400;
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: 'Boska Fallback';
  src: local('Georgia');
  size-adjust: 111.65%;
  ascent-override: 85.99%;
  descent-override: 22.39%;
}

/* --- Schibsted Grotesk — body en alle interfacetekst. Vier gewichten plus
   de echte italic op 400 (BRANDING vroeg om "zichtbaar karakter"; de italic
   is voor citaten en licht benadrukte zinnen in lopende tekst). --- */
@font-face {
  font-family: 'Schibsted Grotesk';
  src: url('/fonts/schibsted-grotesk-400.woff2') format('woff2');
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'Schibsted Grotesk';
  src: url('/fonts/schibsted-grotesk-400-italic.woff2') format('woff2');
  font-weight: 400;
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: 'Schibsted Grotesk';
  src: url('/fonts/schibsted-grotesk-500.woff2') format('woff2');
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'Schibsted Grotesk';
  src: url('/fonts/schibsted-grotesk-600.woff2') format('woff2');
  font-weight: 600;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'Schibsted Grotesk';
  src: url('/fonts/schibsted-grotesk-700.woff2') format('woff2');
  font-weight: 700;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'Schibsted Grotesk Fallback';
  src: local('Arial');
  size-adjust: 122.01%;
  ascent-override: 80.04%;
  descent-override: 21.13%;
}

/* --- IBM Plex Mono — labels, prijzen, chips en elk getal. Twee gewichten;
   `tabular-nums` blijft aan (dezelfde reden als eerst: een teller of bedrag
   mag niet verspringen tussen twee waarden). --- */
@font-face {
  font-family: 'IBM Plex Mono';
  src: url('/fonts/ibm-plex-mono-400.woff2') format('woff2');
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'IBM Plex Mono';
  src: url('/fonts/ibm-plex-mono-500.woff2') format('woff2');
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: 'IBM Plex Mono Fallback';
  src: local('Courier New');
  size-adjust: 99.66%;
  ascent-override: 102.85%;
  descent-override: 27.59%;
}

/* ===== colors.css ===== */
:root{
  /* --- Primary --- */
  --pd-navy:#01213F;          /* primary text, headings, majority of surface */
  --pd-copper:#B1723F;        /* large areas, icons, decoration — never small text */
  --pd-copper-dark:#874D1F;   /* CTA text, links, in-copy accent */
  --pd-cream:#FDF7F0;         /* base background */

  /* --- Neutral --- */
  --pd-light-copper:#D6945B;  /* hover tint, no text */
  --pd-warm-gray:#A39A8C;     /* borders, fields, dividers */
  --pd-soft-cream:#F5F0E6;    /* layered backgrounds, card surfaces */
  --pd-pale-gray:#E5E1DB;     /* borders, form fields */
  --pd-charcoal:#2E2E2E;      /* captions, fine print — never a background */
  --pd-white:#FFFFFF;         /* cards, overlays, raised surfaces */

  /* --- Functional --- */
  --pd-focus:#874D1F;         /* focus ring on light grounds */
  --pd-focus-on-navy:#FDF7F0; /* focus ring on navy grounds */
  --pd-navy-hover:#244462;    /* hover / active on navy buttons and links */

  /* --- Status --- */
  --pd-success:#3c9a5f;
  --pd-warning:#d97d2b;
  --pd-error:#da5252;

  /* --- Semantic: surfaces --- */
  --pd-surface-page:var(--pd-cream);
  --pd-surface-sunken:var(--pd-soft-cream);
  --pd-surface-card:var(--pd-white);
  --pd-surface-inverse:var(--pd-navy);
  --pd-surface-accent:var(--pd-copper);

  /* --- Semantic: text --- */
  --pd-text-primary:var(--pd-navy);
  --pd-text-secondary:#4A5A6B;
  --pd-text-muted:var(--pd-charcoal);
  --pd-text-accent:var(--pd-copper-dark);
  --pd-text-on-navy:var(--pd-cream);
  --pd-text-on-navy-muted:#A9B6C4;
  --pd-text-on-copper:var(--pd-white);

  /* --- Semantic: lines --- */
  --pd-border:var(--pd-pale-gray);
  --pd-border-strong:var(--pd-warm-gray);
  --pd-border-accent:var(--pd-copper);
  --pd-border-on-navy:rgba(253,247,240,.18);
  --pd-rule-hairline:rgba(1,33,63,.10);

  /* --- Semantic: interaction --- */
  /* Sinds ronde "levend": de actiekleur IS de CTA-vulling (SPEC §1.1). */
  --pd-action:var(--pd-cta);
  --pd-action-hover:var(--pd-cta-hover);
  --pd-action-text:var(--pd-cta-tekst);
  --pd-link:var(--pd-copper-dark);
  --pd-link-hover:var(--pd-navy);

  /* --- Uitbreiding (redesignronde "levend", SPEC §1.1, art-director) ---
     Twee kleuren gekozen uit de vier kandidaten; mistblauw (koud, SaaS) en
     duinteal-licht (2,43:1 op crème) zijn afgewezen.
       amber     8,46:1 op navy, 5,13:1 op duinteal. ALLEEN OP DONKER: nadruk
                 in koppen, sterren, iconen in chips, labels op donker.
       duinteal  9,27:1 op crème (en crème erop 9,27:1). Tweede donker vlak,
                 scrimkleur van de probleemscènes, tekst-accent op crème. */
  --pd-amber:#E3B27A;
  --pd-duinteal:#1F4A47;

  /* Rollen voor de twee nieuwe kleuren. */
  --pd-accent-op-donker:var(--pd-amber);
  --pd-accent-op-licht:var(--pd-copper-dark);
  --pd-text-accent-teal:var(--pd-duinteal);
  --pd-surface-teal:var(--pd-duinteal);
  --pd-scrim-nacht:1,33,63;        /* navy als rgb-triplet */

  /* --- Duinmist (ronde "home en diensten lichter", 2026-10-04, plan 22 §1.1) ---
     De tweede lichte achtergrond naast crème: koel, licht grijsgroen, afgeleid
     van duinteal. Wisselt per sectie af met crème. Geen tweede accent: koper-
     donker blijft de enige actiekleur. Gemeten op #E4ECE8: navy 13,53:1,
     tekst-secondary #4A5A6B 5,89:1, koper-donker 5,61:1, koper 3,27:1 (alleen
     niet-tekst), crème-op-CTA-vulling blijft 6,34:1. */
  --pd-duinmist:#E4ECE8;
  --pd-surface-alt:var(--pd-duinmist);
  --pd-surface-alt-rgb:228,236,232;  /* rgb-triplet, voor rgba(var(...), a) en verlopen */

  /* --- CTA (SPEC §1.1): één vulling, overal. Koper-donker met crème tekst
     (6,34:1). Hover: #9A5A27, een mengsel van de twee koperkleuren, geen
     nieuwe paletkleur. Amber komt nooit op een knop. --- */
  --pd-cta:var(--pd-copper-dark);
  --pd-cta-hover:#9A5A27;
  --pd-cta-tekst:var(--pd-cream);
}

/* ===== typography.css =====
 *
 * REDESIGNRONDE "LEVEND" (2026-09-28) — vier rollen, geen drie meer. `serif`
 * is nieuw: Boska draagt alleen de h3, niet meer "Display – H3" als blok.
 * Elke rol krijgt zijn eigen CLS-veilige fallback (@font-face hierboven) vóór
 * de generieke systeemletter. */
:root{
  --pd-font-display:'Bricolage Grotesque', 'Bricolage Grotesque Fallback', Arial, sans-serif;   /* mega, h1, h2 */
  --pd-font-serif:'Boska', 'Boska Fallback', Georgia, serif;                                     /* h3, echte cursief */
  --pd-font-body:'Schibsted Grotesk', 'Schibsted Grotesk Fallback', Arial, sans-serif;            /* body + UI text */
  --pd-font-mono:'IBM Plex Mono', 'IBM Plex Mono Fallback', 'Courier New', monospace;             /* labels, prijzen, chips, elk getal */
  /* --pd-font-accent blijft bestaan als alias: elke bestaande regel die hem
     leest (eyebrows, knoplabels, metadata) krijgt zo automatisch de mono-rol
     die in deze ronde diezelfde plek inneemt — zonder de tientallen losse
     aanroepen in de secties handmatig te moeten vinden. */
  --pd-font-accent:var(--pd-font-mono);

  --pd-weight-display:600;
  --pd-weight-display-strong:700;
  --pd-weight-serif:400;
  --pd-weight-serif-italic:400;
  --pd-weight-body:400;
  --pd-weight-body-medium:500;
  --pd-weight-body-semibold:600;
  --pd-weight-body-bold:700;
  --pd-weight-accent:500;
  --pd-weight-mono:400;
  --pd-weight-mono-medium:500;

  /* TYPEROLLEN — SPEC §1.4 (art-director, 2026-09-28), letterlijk. Fluid van
     390 naar 1440px. Elke rol heeft maat, regelhoogte, spatiëring, gewicht en
     (voor Bricolage) een breedte op de wdth-as. */
  --pd-size-mega:clamp(3.75rem,.964rem + 11.43vw,11.25rem);       /* 60 → 180 */
  --pd-size-h1:clamp(2.75rem,1.543rem + 4.952vw,6rem);            /* 44 → 96 */
  --pd-size-h2:clamp(2.25rem,1.507rem + 3.048vw,4.25rem);         /* 36 → 68 */
  --pd-size-h3:clamp(1.5rem,1.221rem + 1.143vw,2.25rem);          /* 24 → 36 */
  --pd-size-lead:clamp(1.25rem,1.111rem + .571vw,1.625rem);       /* 20 → 26 */
  --pd-size-body:clamp(1.0625rem,1.016rem + .19vw,1.1875rem);     /* 17 → 19 */
  --pd-size-label:clamp(.8125rem,.789rem + .095vw,.875rem);       /* 13 → 14 */
  --pd-size-knop:1.0625rem;
  /* Oude namen, nu aliassen, zodat bestaande regels blijven werken. */
  --pd-size-display:var(--pd-size-mega);
  --pd-size-small:0.875rem;
  --pd-size-caption:0.8125rem;

  --pd-lh-mega:.88;
  --pd-lh-display:.88;
  --pd-lh-h1:.95;
  --pd-lh-h2:1;
  --pd-lh-h3:1.1;
  --pd-lh-citaat:1.15;
  --pd-lh-lead:1.4;
  --pd-lh-body:1.55;
  --pd-lh-small:1.5;
  --pd-lh-caption:1.4;

  --pd-tracking-mega:-.035em;
  --pd-tracking-h1:-.03em;
  --pd-tracking-h2:-.025em;
  --pd-tracking-display:-.025em;
  --pd-tracking-label:.02em;
  --pd-tracking-body:0;

  /* wdth-as van Bricolage (font-stretch) en de gewichten per rol. */
  --pd-stretch-mega:75%;
  --pd-stretch-h1:80%;
  --pd-stretch-h2:85%;
  --pd-stretch-display:85%;
  --pd-weight-mega:700;
  --pd-weight-h1:650;
  --pd-weight-h2:600;
  /* Boska 500 (`boska-500.woff2`, Boska Medium) draagt de h3 (SPEC §1.4). */
  --pd-weight-h3:500;
  /* Nadruk in een Bricolage-kop: wght +100 (SPEC §1.4). */
  --pd-weight-nadruk-plus:100;

  /* PRINT / DECK SCALE — ongewijzigd. Dit is de merkbasis-trap voor media die
     niet reflowen (offertes, facturen, social exports); die documenten horen
     bij de Mainframe-huisstijl, niet bij deze redesignronde, en gebruiken dus
     nog steeds de oude drie-familietrap via hun eigen stylesheet. */
  --pd-print-size-display:51px;  --pd-print-lh-display:56px;
  --pd-print-size-h1:38px;       --pd-print-lh-h1:44px;
  --pd-print-size-h2:28px;       --pd-print-lh-h2:34px;
  --pd-print-size-h3:21px;       --pd-print-lh-h3:26px;
  --pd-print-size-body:16px;     --pd-print-lh-body:26px;
  --pd-print-size-small:14px;    --pd-print-lh-small:21px;
  --pd-print-size-caption:13px;  --pd-print-lh-caption:18px;

  /* Eyebrow / overline / label — mono nu, wide tracking, uppercase. */
  --pd-size-eyebrow:var(--pd-size-label);   --pd-lh-eyebrow:1.3;
  /* Sinds ronde "levend": labels in sentence case, ls .02em (SPEC §1.4). */
  --pd-tracking-eyebrow:.02em;

  /* Numerals. IBM Plex Mono heeft tabular lining figures van zichzelf, maar
     de eigenschap blijft expliciet staan: elke figuur die in een kolom, een
     totaal, een prijs of een teller staat mag niet verspringen tussen twee
     waarden. */
  --pd-numeric-tabular:tabular-nums;
  --pd-numeric-proportional:proportional-nums;
}

/* ===== spacing.css ===== */
:root{
  --pd-space-0:0;
  --pd-space-1:4px;
  --pd-space-2:8px;
  --pd-space-3:12px;
  --pd-space-4:16px;
  --pd-space-5:24px;
  --pd-space-6:32px;
  --pd-space-7:48px;
  --pd-space-8:64px;
  --pd-space-9:96px;
  --pd-space-10:128px;
  --pd-space-11:160px;

  /* Semantic rhythm */
  --pd-gap-inline:var(--pd-space-2);      /* icon ↔ label */
  --pd-gap-stack:var(--pd-space-4);       /* paragraph rhythm */
  --pd-gap-group:var(--pd-space-6);       /* related blocks */
  --pd-pad-card:var(--pd-space-6);
  --pd-pad-card-tight:var(--pd-space-5);
  --pd-section-y:var(--pd-space-9);       /* editorial section breathing room */
  --pd-section-y-tight:var(--pd-space-8);

  /* --- Dichtheid (redesignronde "levend", 2026-09-28) — plan "Fundament".
     Sectiepadding als één vloeiende trap in plaats van vaste spring-punten,
     zodat er minder witruimte "hangt" op tussenmaten. --pd-density-tight is
     geen plan-getal — het plan geeft alleen de gewone trap; dit is een
     proportionele afleiding (≈ 65% van de gewone trap) voor secties die de
     sectiebouwer bewust dichter wil zetten (bijv. de componentanatomie).
     Art-director bevestigt of aanpast in pakket 1+. */
  --pd-density-section-y:clamp(3rem,2.3rem + 3vw,5.5rem);
  /* SPEC §1.3: sectiepadding, de onderkant is 1,15× de bovenkant. */
  --pd-sectie-y:var(--pd-density-section-y);
  --pd-sectie-y-onder:calc(var(--pd-density-section-y) * 1.15);
  --pd-density-section-y-tight:clamp(2rem,1.5rem + 2vw,3.5rem);
}

/* ===== radius.css ===== */
:root{
  /* Restrained geometry: hairlines and near-square corners.
     Only avatars/tags go fully round. */
  --pd-radius-0:0;
  /* Sinds ronde "levend" (SPEC §1.3): alles wat begrensd is krijgt 6px. */
  --pd-radius-sm:6px;
  --pd-radius-md:6px;
  --pd-radius-lg:6px;
  /* SPEC §1.3: 6px voor alles wat begrensd is (knoppen, chips, kaarten,
     inputs, beeld in kaarten), 0 voor fullbleed-beeld en de uitsneden van de componentanatomie. */
  --pd-radius:6px;
  --pd-radius-fullbleed:0;
  --pd-radius-xl:10px;      /* app-icon scale only */
  --pd-radius-pill:999px;
  --pd-radius-circle:50%;

  --pd-border-width:1px;
  --pd-border-width-strong:2px;
  --pd-rule-width:1px;
}

/* ===== elevation.css ===== */
:root{
  /* Shadows are navy-tinted, low and rare. A hairline border is the default
     way to separate a surface; shadow is reserved for overlays. */
  --pd-shadow-none:none;
  --pd-shadow-xs:0 1px 2px rgba(1,33,63,.05);
  --pd-shadow-sm:0 2px 8px rgba(1,33,63,.06);
  --pd-shadow-md:0 8px 24px rgba(1,33,63,.08);
  --pd-shadow-lg:0 24px 64px rgba(1,33,63,.14);
  --pd-shadow-focus:0 0 0 2px var(--pd-cream),0 0 0 4px var(--pd-focus);
  --pd-shadow-focus-on-navy:0 0 0 2px var(--pd-navy),0 0 0 4px var(--pd-focus-on-navy);
}

/* ===== curve.css ===== */
/* THE SWEEP — de veeg.
 *
 * The brand's signature form. It replaces the angular geometry the retired
 * beeldmerk carried: the horse mark is built from continuous ribbon sweeps,
 * so the identity's shape language is curved, never chamfered. There is no
 * 45 degree and no 60 degree diagonal anywhere in this system.
 *
 * The sweep appears in exactly three places and nowhere else:
 *   1. one continuous hairline that threads a page from section to section
 *   2. one full-bleed curved division between a light and a dark ground
 *   3. movement — elements travel along an arc, never a straight line
 *
 * Corners stay square. Radius does not soften what the sweep already softens;
 * surfaces that carry the sweep are shaped by the curve itself.
 *
 * Static media: the sweep carries SOCIAL only. Letterhead, business cards and
 * documents stay rectangular and quiet — see readme.md, Visual foundations.
 */
:root{
  /* 1 — the threading line */
  --pd-veeg-stroke:1.5px;
  --pd-veeg-ink:var(--pd-copper);
  --pd-veeg-ink-on-dark:var(--pd-light-copper);
  --pd-veeg-ink-quiet:rgba(177,114,63,.38);

  /* 2 — the curved division. depth is how far the arc rises, spread is how
     wide it is; a larger spread reads shallower and calmer. */
  --pd-veeg-depth:clamp(32px,5vw,88px); 
  --pd-veeg-spread:70%;
  /* ALWAYS use the elliptical two-value form, so depth drives the rise:
       border-radius: 70% 70% 0 0 / 88px 88px 0 0;
     A single-value percentage makes the vertical radius a share of the height,
     which turns the arc into a dome. Utilities .pd-veeg-crest / -trough /
     -edge-left in base.css do this for you. */
  --pd-veeg-clip-crest:ellipse(140% 100% at 50% 0%); 
  --pd-veeg-clip-trough:ellipse(140% 100% at 50% 100%); 

  /* 3 — movement on an arc. Asymmetric easing: slow to leave, decisive on
     arrival, which is what makes a plain translate read as a curve. */
  --pd-veeg-ease:cubic-bezier(.34,.06,.14,1); 
  --pd-veeg-arc-rise:8px;

  /* Intensity dial. The agreed setting is "clear but calm": unmistakable once
     you look, never the loudest thing on the page. One threading line per
     page, one curved division per page. */
  --pd-veeg-presence:.62; 
}

/* ===== texture.css ===== */
/* GRAIN.
 *
 * One shared noise texture, inline as a data URI so it costs no request and
 * no external host — the flagship site runs a strict CSP, and keeping the
 * texture inline is what lets it exist there at all.
 *
 * Grain is what stops large flat cream and navy fields from reading as a
 * default UI kit. Full-bleed grounds only: never on a card, never behind
 * body text at small sizes, never over photography.
 */
:root{
  --pd-grain-url:url("data:image/svg+xml,%3Csvg%20xmlns%3D%27http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%27%20width%3D%27180%27%20height%3D%27180%27%3E%3Cfilter%20id%3D%27n%27%3E%3CfeTurbulence%20type%3D%27fractalNoise%27%20baseFrequency%3D%270.82%27%20numOctaves%3D%273%27%20stitchTiles%3D%27stitch%27%2F%3E%3CfeColorMatrix%20type%3D%27saturate%27%20values%3D%270%27%2F%3E%3C%2Ffilter%3E%3Crect%20width%3D%27180%27%20height%3D%27180%27%20filter%3D%27url%28%23n%29%27%2F%3E%3C%2Fsvg%3E"); 
  --pd-grain-opacity-light:.035; 
  --pd-grain-opacity-dark:.055; 
  --pd-grain-tile:180px;
  /* Ronde "levend" (SPEC §1.2): één vaste grain-laag over de hele pagina,
     `body::after`, een PNG-tegel (zwart-witte spikkels op alpha,
     `scripts/grain-tegel.mjs`). Geen blend-mode, geen SVG-filter. */
  --pd-grain-png:url('/textuur/grain-256.png');
  --pd-grain-png-tile:256px;
  --pd-grain-licht:.06;
  --pd-grain-donker:.09;
}

/* ===== motion.css ===== */
:root{
  --pd-duration-instant:100ms; 
  --pd-duration-fast:160ms; 
  --pd-duration-base:240ms; 
  --pd-duration-slow:400ms; 
  --pd-duration-reveal:640ms; 

  /* Refined ease-out. No bounce, no overshoot, no spring. */
  --pd-ease:cubic-bezier(.22,.61,.20,1); 
  --pd-ease-in:cubic-bezier(.55,.06,.68,.19); 
  --pd-ease-inout:cubic-bezier(.45,.05,.30,1); 

  --pd-transition-color:color var(--pd-duration-fast) var(--pd-ease),background-color var(--pd-duration-fast) var(--pd-ease),border-color var(--pd-duration-fast) var(--pd-ease);
}
@media (prefers-reduced-motion:reduce){
  :root{--pd-duration-fast:0ms; 
    --pd-duration-base:0ms; 
    --pd-duration-slow:0ms; 
    --pd-duration-reveal:0ms; }
}

/* ===== layout.css ===== */
:root{
  --pd-container:1200px;
  --pd-container-narrow:760px;   /* editorial measure */
  --pd-container-wide:1440px;
  --pd-gutter:24px;
  --pd-gutter-lg:48px;
  --pd-grid-columns:12;
  --pd-measure:62ch;             /* max line length for body copy — plan "Fundament/Dichtheid" */
  --pd-header-height:80px;

  /* --- Grid, drie breedtes (redesignronde "levend", plan "Fundament/
     Dichtheid": "een grid met drie breedtes: full-bleed, wide 1680 en
     content 1320"). Losse namen naast de bestaande --pd-container*-tokens
     omdat `.pd-container` (utilities.css) nog hardcoded op 1200px zit — dat
     is componentwerk voor de sectiebouwer, geen fundament. Deze drie zijn
     klaar om in te lezen zodra dat gebeurt. */
  --pd-grid-full:none;           /* full-bleed: geen max-width */
  --pd-grid-wide:1680px;
  --pd-grid-content:1320px;

  /* SPEC §1.3, letterlijk. */
  --pd-rand:clamp(1rem,.625rem + 1.6vw,2.5rem);   /* 16px op 390 */
  --pd-wide:1680px;
  --pd-content:1320px;
  --pd-kolom-gap:clamp(1rem,.5rem + 1.5vw,2rem);
  --pd-kolommen:4;               /* 4 op <768, 6 vanaf 768, 12 vanaf 1024 */

  /* Z-schaal (SPEC §1.3). */
  --pd-z-media:0;
  --pd-z-inhoud:10;
  --pd-z-chips:20;
  --pd-z-stapel-labels:30;
  --pd-z-header:40;
  --pd-z-menu:50;
  --pd-z-grain:60;

  /* Logo system */
  --pd-logo-clearspace:.5;        /* × mark height on every side */
  --pd-logo-min-height-mark:24px;
  --pd-logo-min-height-lockup:32px;
  --pd-logo-min-width-horizontal:160px;
}

/* ===== base.css =====
 * REDESIGNRONDE "LEVEND": de typerollen uit SPEC §1.4, site-breed. h1/h2 op
 * Bricolage (eigen wdth/wght/lh/ls per rol), h3/h4 op Boska. Nadruk in een
 * Bricolage-kop gebeurt in Bricolage zelf (`<em>`/`.pd-nadruk`: wght +100 en
 * koper-donker op licht, amber op donker), nooit met een Boska-woord. */
*,*::before,*::after{box-sizing:border-box}
body{margin:0;background:var(--pd-surface-page);color:var(--pd-text-primary);font-family:var(--pd-font-body);font-size:var(--pd-size-body);line-height:var(--pd-lh-body);font-weight:var(--pd-weight-body);-webkit-font-smoothing:antialiased;text-wrap:pretty}
/* Grain (SPEC §1.2): één vaste laag, boven alles (z 60), klikt nergens op. */
body::after{content:"";position:fixed;inset:0;pointer-events:none;z-index:var(--pd-z-grain);background-image:var(--pd-grain-png);background-size:var(--pd-grain-png-tile);background-repeat:repeat;opacity:var(--pd-grain-licht)}
h1,h2{font-family:var(--pd-font-display);color:var(--pd-text-primary);margin:0}
h3,h4{font-family:var(--pd-font-serif);font-weight:var(--pd-weight-h3);color:var(--pd-text-primary);letter-spacing:0;margin:0}
h1{font-size:var(--pd-size-h1);line-height:var(--pd-lh-h1);letter-spacing:var(--pd-tracking-h1);font-weight:var(--pd-weight-h1);font-stretch:var(--pd-stretch-h1)}
h2{font-size:var(--pd-size-h2);line-height:var(--pd-lh-h2);letter-spacing:var(--pd-tracking-h2);font-weight:var(--pd-weight-h2);font-stretch:var(--pd-stretch-h2)}
h3{font-size:var(--pd-size-h3);line-height:var(--pd-lh-h3)}
:is(h1,h2) :is(em,.pd-nadruk){font-style:normal;font-weight:calc(var(--pd-weight-h2) + var(--pd-weight-nadruk-plus));color:var(--pd-accent-op-licht)}
h1 :is(em,.pd-nadruk){font-weight:calc(var(--pd-weight-h1) + var(--pd-weight-nadruk-plus))}
[data-pd-donker] :is(h1,h2) :is(em,.pd-nadruk){color:var(--pd-accent-op-donker)}
p{margin:0}
a{color:var(--pd-link);text-decoration:none;border-bottom:1px solid color-mix(in srgb,var(--pd-copper-dark) 40%,transparent);transition:var(--pd-transition-color)}
a:hover{color:var(--pd-link-hover);border-bottom-color:var(--pd-navy)}
:focus-visible{outline:2px solid var(--pd-focus);outline-offset:2px}
.pd-mega{font-family:var(--pd-font-display);font-size:var(--pd-size-mega);line-height:var(--pd-lh-mega);letter-spacing:var(--pd-tracking-mega);font-stretch:var(--pd-stretch-mega);font-weight:var(--pd-weight-mega)}
.pd-display{font-family:var(--pd-font-display);font-size:var(--pd-size-display);line-height:var(--pd-lh-display);letter-spacing:var(--pd-tracking-display)}
.pd-eyebrow{font-family:var(--pd-font-mono);font-size:var(--pd-size-label);line-height:var(--pd-lh-eyebrow);letter-spacing:var(--pd-tracking-label);text-transform:none;font-weight:var(--pd-weight-mono-medium);color:var(--pd-text-accent);font-variant-numeric:tabular-nums}
.pd-label{font-family:var(--pd-font-mono);font-size:var(--pd-size-label);letter-spacing:var(--pd-tracking-label);font-weight:var(--pd-weight-mono-medium);text-transform:none;font-variant-numeric:tabular-nums}
.pd-citaat{font-family:var(--pd-font-serif);font-style:italic;font-weight:400;line-height:var(--pd-lh-citaat);padding-bottom:.08em}
.pd-small{font-size:var(--pd-size-small);line-height:var(--pd-lh-small)}
.pd-caption{font-size:var(--pd-size-caption);line-height:var(--pd-lh-caption);color:var(--pd-text-muted)}
.pd-lead{font-family:var(--pd-font-body);font-size:var(--pd-size-lead);line-height:var(--pd-lh-lead);font-weight:400;color:var(--pd-text-secondary)}
.pd-num{font-family:var(--pd-font-mono);font-variant-numeric:var(--pd-numeric-tabular)}
.pd-grain{position:relative;isolation:isolate}
.pd-grain::after{content:"";position:absolute;inset:0;pointer-events:none;background-image:var(--pd-grain-url);background-size:var(--pd-grain-tile);opacity:var(--pd-grain-opacity-light)}
.pd-grain-dark::after{opacity:var(--pd-grain-opacity-dark)}
.pd-veeg-line{display:block;width:100%;height:var(--pd-veeg-depth);border:0;border-top:var(--pd-veeg-stroke) solid var(--pd-veeg-ink);border-radius:var(--pd-veeg-spread) var(--pd-veeg-spread) 0 0 / var(--pd-veeg-depth) var(--pd-veeg-depth) 0 0;opacity:var(--pd-veeg-presence)}
/* The curved division. Elliptical radius is required: a single-value percentage
   makes the VERTICAL radius a percentage of height, which turns the arc into a
   dome and leaves --pd-veeg-depth unused. */
.pd-veeg-crest{border-radius:var(--pd-veeg-spread) var(--pd-veeg-spread) 0 0 / var(--pd-veeg-depth) var(--pd-veeg-depth) 0 0}
.pd-veeg-trough{border-radius:0 0 var(--pd-veeg-spread) var(--pd-veeg-spread) / 0 0 var(--pd-veeg-depth) var(--pd-veeg-depth)}
.pd-veeg-edge-left{border-radius:var(--pd-veeg-depth) 0 0 var(--pd-veeg-depth) / var(--pd-veeg-spread) 0 0 var(--pd-veeg-spread)}


/* ===== onderhoud.css — de tijdelijke "website wordt herbouwd"-pagina =====
 *
 * Emile, 2026-10-03: tot de nieuwe site af is, staat live alleen deze pagina.
 * `scripts/onderhoud.mjs` plakt dit bestand achter `src/styles/tokens.css`,
 * dus de kleuren, letters, de grain (`body::after`), de koppen en de focusring
 * komen uit de tokens. Hier staat alleen de indeling van deze ene pagina, en
 * geen enkele kleur die niet als token bestaat.
 *
 * Weg zodra Emile expliciet zegt dat de onderhoudspagina weg mag (zie de kop
 * van `scripts/onderhoud.mjs`).
 *
 * ── HET WOORD "OPNIEUW" ──────────────────────────────────────────────────
 * Emiles tweede ronde (03-10): het woord typografisch anders zetten, het hele
 * scherm vullen op desktop, en een 21st.dev-component uit zijn bookmarks.
 *
 * Typografie: hetzelfde variabele Bricolage-bestand als de rest van de kop,
 * maar op de andere uiteinden van de assen. De regel erboven staat op 80%
 * breedte en gewicht 650 (de h1-rol), "opnieuw." op 100% breedte en 800, zo
 * groot dat het van rand tot rand loopt. De nadruk blijft daarmee in Bricolage
 * zelf (tokens, base.css: nooit een Boska-woord in een Bricolage-kop).
 * Daarbovenop valt elke letter binnen op gewicht 200, een dunne lijn als een
 * bouwtekening, en groeit het hele woord daarna in één beweging naar 800 tot
 * het de breedte van het scherm vult: eerst getekend, dan gebouwd. (Een
 * omtrek met -webkit-text-stroke is geprobeerd en afgevallen: die laat de
 * overlappende contouren van het variabele font zien, zichtbaar in de e.)
 *
 * Component: 21st.dev "Drop Text" van hyperiux
 * (https://21st.dev/@hyperiux/components/drop-text, Emiles lijst
 * "PaardekooperDesign website components"). De waarden zijn letterlijk die van
 * het origineel: variant "drop", per letter, staggerFrom "random",
 * yOffset −115, startOpacity 0, duration 0,5 s, stagger 0,05 s,
 * ease power2.out (= easeOutCubic, cubic-bezier(.33,1,.68,1)), lineHeight 1
 * in het origineel. Afwijkingen, elk afgedwongen:
 *   1. Geen React en geen GSAP: deze pagina heeft geen framework en geen
 *      enkel script (CSP zonder script-src). De gsap.fromTo is hier een
 *      CSS-@keyframes met dezelfde begin- en eindwaarden.
 *   2. "random" is in GSAP elke keer een nieuwe volgorde. Zonder script is het
 *      één vaste, door elkaar gegooide volgorde (de --pd-ond-d per letter).
 *   3. Geen style-attributen per letter (CSP: style-src-attr 'none'). De
 *      beginstand staat in de keyframes, de vertraging per letter in
 *      :nth-child-regels.
 *   4. yOffset −115px is bij de 6vw van het origineel ruim 1,3 keer de
 *      lettergrootte. Hier is het woord vier keer zo groot, dus staat de val
 *      als −1,3em, zodat hij even groot oogt.
 *   5. Het origineel wacht met document.fonts.ready tot de letter er is. Dat
 *      kan zonder script niet; de font wordt vooraf geladen (preload in de
 *      kop) en de val begint pas na 0,15 s.
 *   6. Toegankelijkheid: losse letters leest een schermlezer soms als
 *      "o p n i e u w". De letters zijn daarom aria-hidden, en het woord staat
 *      er heel naast als verborgen tekst (.pd-ond-sr).
 *   7. Merkkleuren in plaats van fontColor #ffffff op #101113, en de
 *      section-wrapper met min-h-screen is hier de pagina zelf (.pd-ond).
 *   8. prefers-reduced-motion: het origineel zet de letters direct op hun
 *      plek; hier staat de animatie alleen in een no-preference-mediaquery,
 *      dus wie minder beweging vraagt, ziet het gevulde woord meteen.
 */

/* ── Pagina ─────────────────────────────────────────────────────────────── */
body{overflow-x:clip}

.pd-ond{
  min-height:100vh;
  min-height:100dvh;
  display:grid;
  grid-template-rows:auto 1fr;
  padding:var(--pd-rand);
}

.pd-ond-kop{padding-block:var(--pd-space-2)}

/* 202 × 52 is de echte maat van het bestand; nooit smaller dan de 160px
   minimumbreedte van het horizontale logo (tokens: --pd-logo-min-width-horizontal). */
.pd-ond-logo{
  display:block;
  width:clamp(var(--pd-logo-min-width-horizontal),40vw,202px);
  height:auto;
}

/* De inhoud staat onderaan het scherm, het woord loopt van rand tot rand. De
   containerquery meet de breedte binnen de paginarand, zodat "opnieuw." daar
   precies in past. */
.pd-ond-hoofd{
  align-self:end;
  container-type:inline-size;
  padding-top:var(--pd-space-8);
}

/* ── De kop ─────────────────────────────────────────────────────────────── */
.pd-ond-h1{display:block}

.pd-ond-regel{
  display:block;
  max-width:14ch;
  text-wrap:balance;
}

/* Breedte van "opnieuw." op 100% en 800, met de spatiëring hieronder = 3,84 ×
   de lettergrootte (gemeten in Chrome met de woff2, 03-10). Delen door 3,80
   laat de zichtbare letters van rand tot rand lopen: de zijkanten van de o en
   de punt zijn wit. De hoogtegrens houdt het woord op een breed maar laag
   scherm binnen beeld. */
.pd-ond-woord{
  display:block;
  font-size:calc((100vw - 2 * var(--pd-rand)) / 3.8);
  font-size:min(calc(100cqi / 3.8), 46vh);
  font-weight:800;
  font-stretch:100%;
  line-height:.8;
  letter-spacing:-.03em;
  color:var(--pd-copper-dark);
  margin-top:.06em;
  margin-left:-.04em; /* de linkerflank van de o optisch op de rand */
  padding-bottom:.12em; /* ruimte voor de staart van de p onder de krappe regel */
}

.pd-ond-sr{
  position:absolute;
  width:1px;
  height:1px;
  overflow:hidden;
  clip-path:inset(50%);
  white-space:nowrap;
}

.pd-ond-letters{
  display:block;
  white-space:pre;
  user-select:none;
}

.pd-ond-letter{display:inline-block}

/* Twee delen, "op" en "nieuw.". Op een breed scherm staan ze op één regel en
   bestaat het afbreekstreepje niet; staand (telefoon, tablet) breekt het woord
   na "op-", zodat het twee keer zo hoog kan en het scherm vult. */
.pd-ond-deel{display:inline}
.pd-ond-streep{display:none}

/* ── Drop Text: de val, dan de groei ────────────────────────────────────── */
/* Vaste, door elkaar gegooide volgorde (afwijking 2): o p n i e u w . */
.pd-ond-l1{--pd-ond-d:.30s}
.pd-ond-l2{--pd-ond-d:.45s}
.pd-ond-streep{--pd-ond-d:.55s}
.pd-ond-l3{--pd-ond-d:.20s}
.pd-ond-l4{--pd-ond-d:.50s}
.pd-ond-l5{--pd-ond-d:.35s}
.pd-ond-l6{--pd-ond-d:.15s}
.pd-ond-l7{--pd-ond-d:.40s}
.pd-ond-l8{--pd-ond-d:.25s}

@media (prefers-reduced-motion:no-preference){
  .pd-ond-letter{
    animation:pd-ond-val .5s cubic-bezier(.33,1,.68,1) var(--pd-ond-d) both;
  }
  /* Op de letters samen, niet per letter: groeit elke letter op zijn eigen
     moment, dan duwen de buren elkaar zijwaarts en schokt het woord. */
  .pd-ond-letters{
    animation:pd-ond-groei .9s cubic-bezier(.65,0,.35,1) 1.05s both;
  }
}

@keyframes pd-ond-val{
  from{opacity:0;transform:translate3d(0,-1.3em,0)}
  to{opacity:1;transform:none}
}

@keyframes pd-ond-groei{
  from{font-weight:200}
  to{font-weight:800}
}

/* ── Onderrand: tekst en e-mail ─────────────────────────────────────────── */
.pd-ond-onder{
  display:grid;
  gap:var(--pd-space-5);
  margin-top:var(--pd-space-6);
  padding-top:var(--pd-space-5);
  border-top:var(--pd-rule-width) solid var(--pd-rule-hairline);
}

.pd-ond-lead{
  max-width:36ch;
  text-wrap:balance;
}

.pd-ond-mail{
  font-size:var(--pd-size-lead);
  line-height:var(--pd-lh-lead);
  font-weight:var(--pd-weight-body-medium);
}

/* Navy met een koperen onderstreping; koper is hier decoratie, geen tekst
   (tokens: koper nooit voor kleine tekst). Hover naar koper-donker, 6,3:1 op crème. */
.pd-ond-mail a{
  display:inline-block;
  color:var(--pd-text-primary);
  border-bottom:var(--pd-border-width-strong) solid var(--pd-copper);
  padding-bottom:2px;
  overflow-wrap:anywhere;
  transition:var(--pd-transition-color);
}
.pd-ond-mail a:hover{
  color:var(--pd-link);
  border-bottom-color:var(--pd-copper-dark);
}
.pd-ond-mail a:active{transform:translateY(1px)}

/* Desktop: de eerste regel op één lijn, tekst links en e-mail rechts onder het woord. */
@media (min-width:1024px){
  .pd-ond-regel{max-width:none}
  .pd-ond-onder{
    grid-template-columns:1fr auto;
    align-items:end;
  }
  .pd-ond-mail{text-align:right}
}

/* ── Staand scherm: telefoon en tablet ─────────────────────────────────────
   Emile, 03-10: 70% kijkt op de telefoon, dus ook daar het hele scherm. De
   kop staat direct onder het logo, de uitleg eronder en het e-mailadres
   onderaan, binnen duimbereik. "opnieuw." breekt na "op-" en gaat staand naar het smalle
   uiteinde van de breedte-as (75%): een staand scherm krijgt een smalle
   letter, een liggend scherm een brede. Zo wordt het woord zo hoog als het
   scherm toelaat.

   Smal en zwaar lopen de letters op de spatiëring van liggend (−.03em) in
   elkaar (de u en de w raakten), dus staand +.01em. Gemeten in Chrome (03-10)
   op 800: "nieuw." op 75% met +.01em = 2,24 × de lettergrootte; "onze
   website" in de kopregel = 4,03 ×.
   Het woord krijgt de kleinste van twee maten: de breedte (100cqi / 2,28) of
   de hoogte die overblijft, namelijk 100svh min de vaste delen (logo, randen,
   onderrand: ± 22,5rem) en de twee kopregels, gedeeld door de twee regels van
   .8 plus de .12em eronder. Op een kleine iPhone wint de hoogte en past alles
   zonder scrollen; op een grote wint de breedte. */
@media (max-width:1023px) and (orientation:portrait){
  .pd-ond-hoofd{
    --pd-ond-regel:max(var(--pd-size-h1),min(15cqi,6rem,8svh));
    align-self:stretch;
    display:flex;
    flex-direction:column;
    padding-top:clamp(var(--pd-space-6),7svh,var(--pd-space-9));
  }
  .pd-ond-regel{
    font-size:var(--pd-ond-regel);
    max-width:none;
  }
  .pd-ond-woord{
    font-stretch:75%;
    letter-spacing:.01em;
    font-size:max(4rem,min(calc(100cqi / 2.28),calc((100svh - 22.5rem - 1.9 * var(--pd-ond-regel)) / 1.72)));
  }
  .pd-ond-deel{display:block}
  .pd-ond-streep{display:inline-block}
  /* De uitleg hoort bij de kop en staat er direct onder; het e-mailadres
     staat alleen onderaan, binnen duimbereik. De lucht ertussen scheidt de
     boodschap van de actie. */
  .pd-ond-onder{
    flex:1;
    display:flex;
    flex-direction:column;
  }
  .pd-ond-mail{margin-top:auto}
}
