/* The Mehdi Zaidi module's own sheet (ADR-0015), linked on every page of a tenant with the
   module (SiteStylesheet) and never imported by app.js, so nobody else downloads it. Layout is
   Bootstrap's, in the markup: what lives here is the identity's colors, its type register and
   what moves. Nanum Pen Script is a module face, not a theme pair. */
@font-face {
    font-family: "Nanum Pen Script";
    font-style: normal;
    font-weight: 400;
    font-display: swap;
    src: url("../fonts/nanum-pen-script-400-_Y996b9.woff2") format("woff2");
}

/* Paper, card, sand and ink are the Buvard palette's surfaces, read from the theme. The band, the
   accent and the console's colors are the design's own, which ADR-0015 lets a signature carry;
   the template provisions light only. The accent is a fill and a stroke, never text on paper. */
:root {
    --mz-paper: var(--ap-bg);
    --mz-card: var(--ap-panel);
    --mz-sand: var(--ap-border);
    --mz-ink: var(--ap-text);
    --mz-band: #2346ff;
    --mz-band-deep: #1a35c9;
    --mz-band-muted: #d6ddff;
    --mz-band-soft: #dbe2ff;
    --mz-accent: #4be3b0;
    --mz-accent-soft: #7eeec7;
    --mz-note: var(--mz-band);
    --mz-ink-raised: #1d1940;
    --mz-ink-line: #2c2770;
    --mz-ink-dash: #3d377a;
    --mz-key: #a9b8ff;
    --mz-string: #7eeec7;
    --mz-error: #ff8fa3;
    --mz-comment: #8a85b3;
    --mz-mist: #b5b0d6;
    --mz-metal: #c9c6d8;
    --mz-paper-line: color-mix(in srgb, var(--mz-paper) 40%, transparent);
    --mz-ease: cubic-bezier(0.2, 0.8, 0.2, 1);
    --mz-curve: clamp(80px, 10vw, 160px);
    --mz-console-leading: 1.9;
}

/* ---- Site-wide: every page of the tenant ---- */

html {
    scroll-behavior: smooth;
}

::selection {
    background: var(--mz-accent);
    color: var(--mz-ink);
}

/* Paper grain over the page, under the navbar and every overlay Bootstrap stacks above 1000. */
body::after {
    content: "";
    position: fixed;
    inset: 0;
    z-index: 90;
    pointer-events: none;
    opacity: 0.06;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='180' height='180'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.8' numOctaves='3' stitchTiles='stitch'/%3E%3CfeColorMatrix type='saturate' values='0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
}

/* A section's band, and the navbar over it once app/mehdi-zaidi/chrome.js copies the tone. */
[data-mz-tone="band"] {
    background: var(--mz-band);
    color: var(--mz-paper);
}

[data-mz-tone="ink"] {
    background: var(--mz-ink);
    color: var(--mz-paper);
}

/* The navbar's border-bottom is a utility, so its color goes through the variable it reads. */
.site-nav {
    --bs-border-color: transparent;
    background-color: rgba(var(--ap-bg-rgb), 0.8);
    backdrop-filter: blur(12px);
    transition: transform 0.5s var(--mz-ease), color 0.35s ease, background-color 0.35s ease;
}

.site-nav.is-scrolled {
    box-shadow: none;
}

.site-nav.is-tucked {
    transform: translateY(-110%);
}

.site-nav .nav-link {
    letter-spacing: 0.06em;
}

.site-nav .nav-link:hover,
.site-nav .nav-link.is-active {
    --bs-border-color: var(--mz-band);
    color: var(--mz-band);
}

.nav-brand-text {
    font-size: 1rem;
    font-weight: 600;
    letter-spacing: -0.01em;
    text-transform: none;
}

.mz-clock {
    letter-spacing: 0.06em;
}

.mz-clock__dot {
    width: 7px;
    height: 7px;
    background: var(--mz-accent);
    animation: mz-pulse 2s ease-in-out infinite;
}

.site-nav[data-mz-tone="band"] {
    background-color: color-mix(in srgb, var(--mz-band) 84%, transparent);
}

.site-nav[data-mz-tone="ink"] {
    background-color: color-mix(in srgb, var(--mz-ink) 84%, transparent);
}

.site-nav:is([data-mz-tone="band"], [data-mz-tone="ink"], :has(.navbar-collapse.show)) :is(.nav-link, .navbar-brand, .nav-brand-text) {
    color: var(--mz-paper);
}

.site-nav:is([data-mz-tone="band"], [data-mz-tone="ink"], :has(.navbar-collapse.show)) .nav-link:is(:hover, .is-active) {
    --bs-border-color: var(--mz-accent);
    color: var(--mz-accent);
}

/* Below lg the menu is a pill reading « Menu » that opens a full-screen band-colored panel, the
   bar's brand and pill staying over it; app/mehdi-zaidi/chrome.js puts the clock at its foot. */
@media (max-width: 991.98px) {
    .site-nav {
        --bs-navbar-toggler-padding-x: 1rem;
        --bs-navbar-toggler-padding-y: 0;
        --bs-navbar-toggler-border-color: currentcolor;
        --bs-navbar-toggler-border-radius: var(--bs-border-radius-pill);
    }

    /* A blur or a transform on the bar would make it the panel's containing block. */
    .site-nav:has(.navbar-collapse.show) {
        background-color: transparent;
        color: var(--mz-paper);
        backdrop-filter: none;
        transform: none;
    }

    :root:has(.site-nav .navbar-collapse.show) {
        overflow: hidden;
    }

    .site-nav :is(.navbar-brand, .navbar-toggler) {
        position: relative;
        z-index: 1031;
    }

    .site-nav .navbar-toggler {
        display: inline-flex;
        align-items: center;
        gap: 0.625rem;
        min-height: 44px;
        border-width: 1.5px;
        color: inherit;
        font-family: var(--ap-font-mono);
        font-size: 0.72rem;
        font-weight: 700;
        letter-spacing: 0.08em;
        text-transform: uppercase;
    }

    .site-nav .navbar-toggler::after {
        content: "Menu" / "";
    }

    .site-nav .navbar-toggler[aria-expanded="true"]::after {
        content: "Fermer" / "";
    }

    .site-nav .navbar-toggler-icon {
        width: 14px;
        height: 7px;
        border-block: 1.5px solid currentcolor;
        background-image: none;
    }

    .site-nav .navbar-collapse {
        position: fixed;
        inset: 0;
        z-index: 1030;
        flex-direction: column;
        align-items: stretch;
        gap: 0.25rem;
        padding: 110px 1.5rem 2.25rem;
        background: var(--mz-band);
    }

    .site-nav .navbar-collapse.show {
        display: flex;
    }

    .site-nav .navbar-collapse.collapsing {
        transition: none;
    }

    .site-nav .navbar-collapse .nav-link {
        padding: 0;
        font-family: var(--ap-font-body);
        font-size: clamp(2.6rem, 12vw, 4rem);
        font-weight: 600;
        line-height: 1.08;
        letter-spacing: -0.045em;
        text-transform: none;
    }

    /* The call to action reads as the panel's last link, in the accent. */
    .site-nav .navbar-collapse .btn-accent {
        --bs-btn-padding-x: 0;
        --bs-btn-padding-y: 0;
        --bs-btn-font-size: clamp(2.6rem, 12vw, 4rem);
        --bs-btn-font-weight: 600;
        --bs-btn-line-height: 1.08;
        --bs-btn-bg: transparent;
        --bs-btn-border-color: transparent;
        --bs-btn-color: var(--mz-accent);
        --bs-btn-hover-bg: transparent;
        --bs-btn-hover-border-color: transparent;
        --bs-btn-hover-color: var(--mz-paper);
        --bs-btn-active-bg: transparent;
        --bs-btn-active-border-color: transparent;
        --bs-btn-active-color: var(--mz-paper);
        font-family: var(--ap-font-body);
        letter-spacing: -0.045em;
        text-align: start;
        text-transform: none;
    }

    .mz-menu-foot {
        --bs-border-color: var(--mz-paper-line);
        color: var(--mz-band-muted);
    }
}

@media (max-width: 991.98px) and (prefers-reduced-motion: no-preference) {
    .site-nav .navbar-collapse.show {
        animation: mz-menu 0.65s cubic-bezier(0.6, 0, 0.2, 1);
    }

    .site-nav .navbar-collapse.show :is(.nav-item, .mz-menu-foot) {
        animation: mz-lift 0.52s var(--mz-ease) 0.16s backwards;
    }

    .site-nav .navbar-collapse.show .nav-item:nth-child(2) {
        animation-delay: 0.215s;
    }

    .site-nav .navbar-collapse.show .nav-item:nth-child(3) {
        animation-delay: 0.27s;
    }

    .site-nav .navbar-collapse.show :is(.nav-item:nth-child(n + 4), .mz-menu-foot) {
        animation-delay: 0.325s;
    }
}

.site-footer {
    --bs-border-color: transparent;
    background: var(--mz-band);
    color: var(--mz-band-muted);
}

.site-footer .meta-line {
    --bs-border-color: var(--mz-paper-line);
    color: var(--mz-band-muted);
}

.site-footer :is(a, .nav-brand-text) {
    color: var(--mz-paper);
}

.site-footer a:hover {
    color: var(--mz-accent);
}

.site-footer :is(.text-muted-ap, .eyebrow) {
    color: var(--mz-band-muted);
}

/* The house display face is a heavy uppercase (components.css): this template is the same
   family in sentence case, and the reach is right because this sheet loads nowhere else. */
.display-title {
    font-weight: 600;
    letter-spacing: -0.04em;
    text-transform: none;
}

/* The house button is a tracked mono capital on the accent; this one is an ink pill. */
.btn-accent {
    --bs-btn-padding-x: 1.5rem;
    --bs-btn-padding-y: 0.95rem;
    --bs-btn-font-size: 0.78rem;
    --bs-btn-bg: var(--ap-text);
    --bs-btn-border-color: var(--ap-text);
    --bs-btn-color: var(--ap-bg);
    --bs-btn-hover-bg: var(--mz-band);
    --bs-btn-hover-border-color: var(--mz-band);
    --bs-btn-hover-color: var(--mz-paper);
    --bs-btn-active-bg: var(--mz-band);
    --bs-btn-active-border-color: var(--mz-band);
    --bs-btn-active-color: var(--mz-paper);
    letter-spacing: 0.04em;
    text-transform: none;
}

.btn-accent.btn-sm {
    --bs-btn-font-size: 0.72rem;
}

.mz-btn-paper {
    --bs-btn-bg: var(--mz-paper);
    --bs-btn-border-color: var(--mz-paper);
    --bs-btn-color: var(--mz-ink);
    --bs-btn-hover-bg: var(--mz-accent);
    --bs-btn-hover-border-color: var(--mz-accent);
    --bs-btn-hover-color: var(--mz-ink);
    --bs-btn-active-bg: var(--mz-accent);
    --bs-btn-active-border-color: var(--mz-accent);
    --bs-btn-active-color: var(--mz-ink);
}

/* ---- Shared by the module's sections ---- */

.mz-hand {
    font-family: "Nanum Pen Script", cursive;
    font-weight: 400;
    line-height: 1;
}

.mz-note {
    font-size: clamp(2rem, 3vw, 2.8rem);
    color: var(--mz-note);
    rotate: -4deg;
    transform-origin: 0 50%;
}

[data-mz-tone="band"] .mz-note {
    color: var(--mz-paper);
}

[data-mz-tone="ink"] .mz-note {
    color: var(--mz-accent);
}

.mz-title {
    font-size: clamp(3.2rem, 7vw, 7.2rem);
    line-height: 0.88;
    letter-spacing: -0.055em;
    text-wrap: balance;
}

.mz-label {
    font-size: 0.76rem;
    letter-spacing: 0.08em;
    color: var(--ap-muted);
}

[data-mz-tone="band"] .mz-label {
    color: var(--mz-band-muted);
}

.mz-lede {
    max-width: 30ch;
    font-size: 1.1rem;
    line-height: 1.5;
    color: var(--ap-muted);
}

[data-mz-tone="band"] .mz-lede {
    color: var(--mz-band-muted);
}

[data-mz-tone="ink"] .mz-lede {
    color: var(--mz-mist);
}

.mz-underline {
    padding-bottom: 2px;
    border-bottom: 2px solid var(--mz-accent);
    color: var(--ap-text);
    transition: color 0.25s ease;
}

.mz-underline:hover {
    color: var(--mz-band);
}

/* Bootstrap's badge, re-skinned through its variables. They go on the badge itself, which
   declares its own and would shadow a parent's; the border utility reads --bs-border-color. */
.mz-chips > .badge {
    --bs-badge-padding-x: 0.65rem;
    --bs-badge-padding-y: 0.32rem;
    --bs-badge-font-size: 0.7rem;
    --bs-badge-font-weight: 400;
    --bs-badge-color: currentcolor;
    --bs-border-color: var(--mz-chip-line, currentcolor);
    font-family: var(--ap-font-mono);
}

/* A section app/mehdi-zaidi/timeline.js or stack.js pins: the runway is as tall as the pinned
   window plus the distance the scroll drives, and the window sticks while the runway passes. */
.is-pinned [data-mz-runway] {
    height: calc(var(--mz-travel, 0px) + 100vh);
}

.is-pinned [data-mz-pin] {
    position: sticky;
    top: 0;
    height: 100vh;
    overflow: hidden;
}

/* ---- ouverture ---- */

/* The navbar (70px) above and the band's curve below: what is left of the first screen is the opener's. */
.ouverture {
    min-height: calc(100svh - var(--mz-curve) - 70px);
}

/* Two outlined code marks behind the opener, running up under the navbar and down under the curve. */
.ouverture__marks {
    top: -90px;
    bottom: calc(-1 * var(--mz-curve));
}

.ouverture__mark {
    line-height: 0.8;
    color: transparent;
}

.ouverture__mark--tag {
    right: -4vw;
    bottom: -6vw;
    font-size: clamp(220px, 40vw, 620px);
    letter-spacing: -0.06em;
    -webkit-text-stroke: 1.5px color-mix(in srgb, var(--mz-band) 20%, transparent);
    rotate: 6deg;
}

.ouverture__mark--braces {
    left: -2vw;
    bottom: -4vw;
    font-size: clamp(200px, 32vw, 500px);
    letter-spacing: -0.08em;
    -webkit-text-stroke: 1.5px color-mix(in srgb, var(--mz-ink) 12%, transparent);
    rotate: -8deg;
    transform-origin: 30% 60%;
}

/* One line per part at every width: the smallest size keeps the longest part on a phone. */
.ouverture__title {
    font-size: clamp(2.1rem, 5.4vw, 5.8rem);
    line-height: 0.9;
    letter-spacing: -0.055em;
}

/* At line-height 0.9 the next line's ascenders start 0.21em under the baseline: the wave
   starts just below the baseline and stays inside that gap when the title wraps. */
.ouverture__underline {
    left: -2%;
    bottom: -0.165em;
    width: 96%;
    height: 0.2em;
    overflow: visible;
}

.ouverture__underline path {
    fill: none;
    stroke: var(--mz-accent);
    stroke-width: 6;
    stroke-linecap: round;
    stroke-dasharray: 1;
}

.ouverture__tagline {
    font-size: clamp(0.74rem, 0.9vw, 0.86rem);
    letter-spacing: 0.08em;
    color: var(--ap-muted);
}

.ouverture__portrait {
    width: min(100%, 23.75rem);
    aspect-ratio: 4 / 5;
    rotate: 2.5deg;
}

.ouverture__frame {
    border-radius: 0.5rem;
    background: var(--mz-sand);
    box-shadow: 0 34px 60px -34px color-mix(in srgb, var(--mz-ink) 50%, transparent);
}

.ouverture__tape {
    top: -1rem;
    width: 8rem;
    height: 2.125rem;
    margin-left: -4rem;
    background: color-mix(in srgb, var(--mz-accent) 82%, transparent);
    box-shadow: 0 2px 6px color-mix(in srgb, var(--mz-ink) 12%, transparent);
    rotate: -5deg;
}

/* Pulled further out of the frame from lg up: on a phone, the gutter has no room for it. */
.ouverture__badge {
    left: -0.25rem;
    bottom: -3rem;
    width: clamp(6.25rem, 26vw, 7.75rem);
    height: clamp(6.25rem, 26vw, 7.75rem);
    rotate: -14deg;
}

.ouverture__disc {
    fill: var(--mz-ink);
}

.ouverture__ring {
    font-size: 8.6px;
    letter-spacing: 1.6px;
    fill: var(--mz-paper);
}

.ouverture__initials {
    font-size: 26px;
    fill: var(--mz-accent);
    text-anchor: middle;
}

.ouverture__cue {
    bottom: 1.5rem;
    font-size: 0.7rem;
    letter-spacing: 0.1em;
    color: var(--ap-muted);
}

.ouverture__cue-line {
    width: 1.5px;
    height: 34px;
    background: var(--ap-text);
}

@media (min-width: 992px) {
    .ouverture__badge {
        left: -3.25rem;
    }
}

/* `translate` and `rotate`, not `transform`, which app/mehdi-zaidi/opening.js owns on the
   portrait and the text column; the portrait's entrance holds `translate` until it ends. */
@media (prefers-reduced-motion: no-preference) {
    .ouverture__part {
        animation: mz-rise 0.95s var(--mz-ease) backwards;
    }

    .ouverture__title > :nth-child(1) {
        animation-delay: 0.19s;
    }

    .ouverture__title > :nth-child(2) {
        animation-delay: 0.26s;
    }

    .ouverture__title > :nth-child(3) {
        animation-delay: 0.33s;
    }

    .ouverture__underline path {
        animation: mz-draw 0.85s cubic-bezier(0.6, 0, 0.3, 1) 0.95s backwards;
    }

    .ouverture__portrait {
        animation: mz-lift 1.1s var(--mz-ease) 0.35s backwards;
    }

    .ouverture__cue-line {
        animation: mz-cue 2.2s cubic-bezier(0.6, 0, 0.3, 1) infinite;
    }
}

/* ---- vague ---- */

/* Overlapping the band by a pixel, so no hairline of the ground shows between the two. */
.vague__curve {
    height: var(--mz-curve);
    margin-bottom: -1px;
}

.vague__curve path {
    fill: var(--mz-band);
}

.marquee--vague {
    padding-block: clamp(4px, 1vw, 16px) clamp(24px, 4vw, 56px);
}

.marquee--vague .marquee__group {
    animation-duration: 60s;
}

.marquee--vague .marquee__word {
    gap: clamp(18px, 2.4vw, 36px);
    padding-right: clamp(18px, 2.4vw, 36px);
    font-size: clamp(1.5rem, 3.2vw, 2.8rem);
    font-weight: 600;
    line-height: 1.2;
    letter-spacing: -0.03em;
}

.marquee--vague .marquee__word:nth-child(even) {
    color: transparent;
    -webkit-text-stroke: 1.5px var(--mz-paper);
}

.marquee--vague .marquee__dot {
    width: auto;
    height: auto;
    background: none;
    font-family: var(--ap-font-mono);
    font-size: 0.7em;
    font-style: normal;
    font-weight: 400;
    color: var(--mz-accent);
    -webkit-text-stroke: 0;
}

.marquee--vague .marquee__dot::before {
    content: "/";
}

/* ---- parcours ---- */

.parcours__window {
    overflow-x: auto;
    padding-bottom: 1rem;
    scroll-snap-type: x proximity;
    scrollbar-color: var(--mz-accent) transparent;
}

.parcours__track {
    width: max-content;
    height: clamp(470px, 76vh, 700px);
}

.parcours__intro {
    width: clamp(290px, 36vw, 560px);
    padding-right: clamp(10px, 3vw, 60px);
}

.parcours__heading {
    font-size: clamp(2.4rem, 4.4vw, 4.6rem);
    line-height: 0.98;
    letter-spacing: -0.04em;
    text-wrap: balance;
}

.parcours__body {
    max-width: 40ch;
    font-size: 1.05rem;
    line-height: 1.55;
    color: var(--mz-band-muted);
}

.parcours__note {
    font-size: 2.1rem;
}

/* An outlined card, then a filled one, and the last on the accent. */
.parcours__card {
    --mz-chip-line: color-mix(in srgb, var(--mz-paper) 50%, transparent);
    width: clamp(270px, 30vw, 440px);
    height: clamp(400px, 64vh, 580px);
    padding: clamp(22px, 2.4vw, 34px);
    border: 1.5px solid var(--mz-paper-line);
    border-radius: 1.5rem;
    scroll-snap-align: center;
}

.parcours__card:nth-of-type(even) {
    border-color: transparent;
    background: var(--mz-band-deep);
}

.parcours__card:last-of-type {
    --mz-chip-line: var(--mz-ink);
    border-color: transparent;
    background: var(--mz-accent);
    color: var(--mz-ink);
}

.parcours__year {
    font-size: clamp(4.6rem, 9vw, 8.6rem);
    line-height: 0.8;
    letter-spacing: -0.06em;
    color: transparent;
    -webkit-text-stroke: 1.5px var(--mz-paper);
}

.parcours__card:last-of-type .parcours__year {
    color: var(--mz-ink);
    -webkit-text-stroke: 0;
}

.parcours__card-title {
    font-size: clamp(1.5rem, 2.2vw, 2.1rem);
    line-height: 1.05;
    letter-spacing: -0.025em;
}

.parcours__card-text {
    line-height: 1.55;
    color: var(--mz-band-muted);
}

.parcours__card:last-of-type .parcours__card-text {
    color: var(--mz-ink);
}

.parcours__outro {
    width: clamp(280px, 30vw, 440px);
    padding-left: clamp(10px, 2vw, 30px);
}

.parcours__outro-note {
    font-size: clamp(2.6rem, 4vw, 3.6rem);
    line-height: 0.9;
}

.parcours__outro-title {
    font-size: clamp(1.8rem, 2.8vw, 2.8rem);
    line-height: 1.02;
    letter-spacing: -0.035em;
    text-wrap: balance;
}

.parcours__progress {
    color: var(--mz-band-muted);
}

/* The bar only means something once the script drives it. */
.parcours:not(.is-pinned) .parcours__progress {
    visibility: hidden;
}

.parcours__bar {
    height: 2px;
    background: color-mix(in srgb, var(--mz-paper) 22%, transparent);
}

.parcours__fill {
    background: var(--mz-accent);
    transform: scaleX(0);
    transform-origin: 0 50%;
}

.parcours.is-pinned .parcours__window {
    overflow: visible;
    padding-bottom: 0;
    scroll-snap-type: none;
}

.parcours.is-pinned .parcours__track {
    will-change: transform;
}

/* ---- projets ---- */

/* The band color behind the sheet is the band it rises over: its corners and, while it grows,
   its sides. The sheet pads itself because the section's own padding would show that band. */
.projets {
    background: var(--mz-band);
}

.projets__sheet {
    padding-block: clamp(72px, 9vw, 130px) clamp(2rem, 4vw, 4rem);
    border-radius: clamp(28px, 4vw, 56px) clamp(28px, 4vw, 56px) 0 0;
    background: var(--ap-bg);
    color: var(--ap-text);
    transform-origin: 50% 0;
}

.projets__heading {
    font-size: clamp(2.6rem, 6vw, 6.2rem);
    line-height: 0.95;
    letter-spacing: -0.045em;
}

.projets__intro {
    max-width: 34ch;
    font-size: 1.05rem;
    line-height: 1.55;
}

.projets__media {
    border-radius: 1rem;
    background: var(--mz-sand);
    transition: transform 0.35s var(--mz-ease);
}

.projets__media--wide {
    --bs-aspect-ratio: 62.5%;
    border-radius: 1.25rem;
    box-shadow: 0 44px 80px -54px color-mix(in srgb, var(--mz-ink) 55%, transparent);
}

.projets__meta {
    letter-spacing: 0.05em;
    color: var(--ap-muted);
}

.projets__featured-title {
    font-size: clamp(3rem, 6vw, 5.6rem);
    line-height: 0.9;
    letter-spacing: -0.05em;
}

.projets__card-title {
    font-size: clamp(1.5rem, 2vw, 1.9rem);
    line-height: 1.05;
    letter-spacing: -0.03em;
}

.projets__body {
    max-width: 46ch;
    font-size: 1.05rem;
    line-height: 1.55;
    color: var(--ap-muted);
}

.projets__note {
    font-size: 1.8rem;
}

/* Padding, not margin: the row's vertical gutter is the columns' margin-top. */
@media (min-width: 992px) {
    .projets__grid > :nth-child(3n + 2) {
        padding-top: min(7vw, 110px);
    }

    .projets__grid > :nth-child(3n) {
        padding-top: min(3vw, 44px);
    }
}

/* ---- pile ---- */

.pile {
    --mz-travel: 70vh;
}

/* Pinned below lg, the stacked layout hangs just under the navbar: centered in the window,
   it opened a half-screen of paper under the projects. From lg up it is centered. */
@media (max-width: 991.98px) {
    .pile.is-pinned [data-mz-pin] {
        padding-top: 5rem;
    }
}

.pile__wrap {
    transform-origin: 50% 0;
}

.pile__layer {
    width: 100%;
    padding: clamp(11px, 1.4vw, 17px) clamp(16px, 2vw, 26px);
    border-radius: 0.875rem;
}

/* The border utility reads its color and width from these, so the pill is drawn in ink. */
.pile__count {
    --bs-border-color: currentcolor;
    --bs-border-width: 1.5px;
}

.pile__note {
    font-size: clamp(1.8rem, 2.6vw, 2.4rem);
}

/* Tinted from the layer's own text color, so it reads on the light and the dark layers alike. */
.pile__icon {
    width: clamp(28px, 2.4vw, 36px);
    aspect-ratio: 1;
    background: color-mix(in srgb, currentcolor 10%, transparent);
}

.pile__name {
    font-size: clamp(1.1rem, 1.7vw, 1.55rem);
    letter-spacing: -0.02em;
}

/* Counted from the bottom, which is how a stack is built: the colors stay put whatever the
   number of layers, and each one is a little narrower than the one it rests on. */
.pile__layer:nth-last-child(1) {
    border: 2px solid var(--ap-text);
}

.pile__layer:nth-last-child(2) {
    width: 96%;
    background: var(--mz-band-soft);
    color: var(--mz-ink);
}

.pile__layer:nth-last-child(3) {
    width: 92%;
    background: var(--mz-band-deep);
    color: var(--mz-paper);
}

.pile__layer:nth-last-child(4) {
    width: 88%;
    background: var(--mz-sand);
    color: var(--mz-ink);
}

.pile__layer:nth-last-child(5) {
    width: 84%;
    background: var(--mz-ink);
    color: var(--mz-paper);
}

.pile__layer:nth-last-child(6) {
    width: 80%;
    background: var(--mz-band);
    color: var(--mz-paper);
}

.pile__layer:nth-last-child(7) {
    width: 76%;
    background: var(--mz-accent);
    color: var(--mz-ink);
}

.pile__layer:nth-last-child(8) {
    width: 72%;
    background: var(--mz-sand);
    color: var(--mz-ink);
}

/* ---- scene ---- */

/* app/mehdi-zaidi/stage.js tilts the top edge as the section arrives and moves the spot. */
.scene {
    clip-path: polygon(0 120px, 100% 0, 100% 100%, 0 100%);
}

.scene__photo {
    top: -12%;
    height: 124%;
    max-width: none;
    object-position: 45% 38%;
    filter: grayscale(0.35) contrast(1.08) brightness(0.9);
}

.scene__tint {
    background: var(--mz-band-deep);
    mix-blend-mode: color;
    opacity: 0.55;
}

.scene__shade {
    background:
        linear-gradient(180deg, transparent 60%, var(--mz-ink) 100%),
        radial-gradient(85% 70% at 0% 100%, color-mix(in srgb, var(--mz-ink) 92%, transparent) 0%, color-mix(in srgb, var(--mz-ink) 62%, transparent) 50%, color-mix(in srgb, var(--mz-ink) 12%, transparent) 100%),
        linear-gradient(color-mix(in srgb, var(--mz-ink) 22%, transparent), color-mix(in srgb, var(--mz-ink) 22%, transparent));
}

.scene__spot {
    --mz-spot-x: 50%;
    --mz-spot-y: 40%;
    background: radial-gradient(520px circle at var(--mz-spot-x) var(--mz-spot-y), color-mix(in srgb, var(--mz-accent-soft) 18%, transparent) 0%, transparent 38%, color-mix(in srgb, var(--mz-ink) 60%, transparent) 78%);
}

.scene__text {
    padding-top: clamp(16rem, 28vw, 24rem);
}

.scene__badge {
    width: clamp(220px, 21vw, 280px);
    transform-origin: 24px 0;
}

.scene__lanyard {
    width: 22px;
    height: clamp(140px, 20vh, 220px);
    margin-left: 13px;
    background: var(--mz-accent);
}

.scene__badge:nth-child(even) .scene__lanyard {
    height: clamp(200px, 28vh, 300px);
    background: var(--mz-band-soft);
}

.scene__lanyard span {
    writing-mode: vertical-rl;
    font-size: 0.58rem;
    line-height: 22px;
    letter-spacing: 0.22em;
    color: var(--mz-ink);
}

.scene__clip {
    width: 12px;
    height: 26px;
    margin-left: 18px;
    border-radius: 6px 6px 3px 3px;
    background: linear-gradient(90deg, #8e8aa6, #e4e2ee 50%, #8e8aa6);
}

.scene__ring {
    z-index: 2;
    width: 20px;
    height: 20px;
    margin: -4px 0 -23px 14px;
    border: 3px solid var(--mz-metal);
}

.scene__card {
    aspect-ratio: 5 / 7;
    border-radius: 6px;
    background: var(--mz-card);
    color: var(--mz-ink);
    box-shadow: 0 40px 70px -30px rgba(0, 0, 0, 0.7);
}

.scene__art-main {
    fill: var(--mz-accent);
}

.scene__art-cut {
    fill: var(--mz-band);
}

.scene__badge:nth-child(even) .scene__art-main {
    fill: var(--mz-band);
}

.scene__badge:nth-child(even) .scene__art-cut {
    fill: var(--mz-accent);
}

.scene__hole {
    z-index: 1;
    left: 17px;
    top: 6px;
    width: 14px;
    height: 14px;
    background: var(--mz-ink);
}

.scene__event {
    padding: 34px 18px 0;
}

.scene__badge:nth-child(even) .scene__event {
    color: var(--mz-paper);
}

.scene__logo {
    width: 40px;
    height: 40px;
    border-radius: 8px;
    background: color-mix(in srgb, var(--mz-ink) 12%, transparent);
}

.scene__badge:nth-child(even) .scene__logo {
    background: color-mix(in srgb, var(--mz-paper) 16%, transparent);
}

.scene__event-name {
    font-size: clamp(1rem, 1.3vw, 1.15rem);
    letter-spacing: -0.02em;
}

.scene__place {
    font-size: 0.64rem;
    letter-spacing: 0.06em;
}

.scene__who {
    top: 44%;
    bottom: 24%;
}

.scene__speaker {
    font-size: clamp(1.3rem, 1.9vw, 1.75rem);
    letter-spacing: -0.03em;
    text-wrap: balance;
}

.scene__talk {
    font-size: 0.88rem;
    line-height: 1.25;
    color: var(--ap-muted);
    text-wrap: balance;
}

.scene__foot {
    height: 15%;
    padding: 0 16px 0 18px;
    color: var(--mz-paper);
}

.scene__badge:nth-child(even) .scene__foot {
    color: var(--mz-ink);
}

.scene__role {
    font-size: 0.74rem;
    letter-spacing: 0.2em;
}

.scene__replay {
    padding: 6px 11px;
    background: var(--mz-ink);
    color: var(--mz-paper);
    font-size: 0.66rem;
}

.scene__replay:hover {
    background: var(--mz-band);
    color: var(--mz-paper);
}

/* Each badge sways on its cord; app/mehdi-zaidi/stage.js adds the scroll's push on `transform`. */
@media (prefers-reduced-motion: no-preference) {
    .scene__badge {
        --mz-sway: 0.7deg;
        animation: mz-sway 6.3s ease-in-out infinite alternate;
    }

    .scene__badge:nth-child(even) {
        animation-delay: -4.2s;
    }
}

/* ---- salle ---- */

.salle__card {
    width: clamp(230px, 24vw, 320px);
    aspect-ratio: 3 / 4;
    padding: clamp(20px, 2vw, 28px);
    border-radius: 1.375rem;
    background: var(--mz-band);
    color: var(--mz-paper);
    box-shadow: 0 30px 60px -36px color-mix(in srgb, var(--mz-ink) 60%, transparent);
}

.salle__card:nth-child(even) {
    background: var(--mz-accent);
    color: var(--mz-ink);
}

.salle__card.salle__card--cta {
    background: var(--mz-ink);
    color: var(--mz-paper);
}

.salle__kicker {
    font-size: 0.7rem;
    letter-spacing: 0.06em;
}

.salle__logo {
    width: min(100%, clamp(96px, 10vw, 140px));
    aspect-ratio: 1;
    background: color-mix(in srgb, var(--mz-paper) 16%, transparent);
    font-size: clamp(3.5rem, 6vw, 5rem);
}

.salle__card:nth-child(even) .salle__logo {
    background: color-mix(in srgb, var(--mz-ink) 12%, transparent);
}

.salle__title {
    font-size: clamp(1.8rem, 2.6vw, 2.5rem);
    line-height: 0.95;
    letter-spacing: -0.04em;
}

.salle__mark {
    font-size: clamp(7rem, 11vw, 10rem);
    color: var(--mz-accent);
}

.salle__cta {
    color: inherit;
}

.salle__card--cta:hover .salle__cta {
    color: var(--mz-accent);
}

/* Below md the cards share one row, each over the one before it, and app/mehdi-zaidi/fan.js
   fans them as it does on a wide screen. The overlap is a share of the row, about 30% of a card. */
@media (max-width: 767.98px) {
    .salle__card {
        flex: 1 1 0;
        min-width: 0;
        max-width: 42vw;
    }

    .salle__card + .salle__card {
        margin-left: -9%;
    }

    .salle__title {
        font-size: 1.25rem;
    }

    .salle__mark {
        font-size: 5rem;
    }
}

/* ---- requete ---- */

.requete__link {
    --bs-border-color: color-mix(in srgb, var(--mz-paper) 30%, transparent);
    font-size: 0.86rem;
    color: var(--mz-paper);
}

.requete__link:hover {
    color: var(--mz-accent);
}

/* An .http file in an editor: every line of the request and of its body is numbered in a
   gutter. A line app/mehdi-zaidi/request.js keeps hidden is not displayed, so not counted. */
.requete__console {
    --bs-border-color: var(--mz-ink-line);
    counter-reset: mz-line;
    border: 1px solid var(--mz-ink-line);
    border-radius: 1.25rem;
    background: var(--mz-ink);
    color: var(--mz-comment);
    font-size: clamp(0.8rem, 1vw, 0.9rem);
    line-height: var(--mz-console-leading);
    box-shadow: 0 40px 80px -40px color-mix(in srgb, var(--mz-ink) 70%, transparent);
}

.requete__dot {
    width: 0.7rem;
    height: 0.7rem;
    background: var(--mz-accent);
}

.requete__dot:nth-child(2) {
    background: var(--mz-mist);
}

.requete__dot:nth-child(3) {
    background: var(--mz-key);
}

.requete__file {
    font-size: 0.85em;
}

.requete__lines {
    padding-left: calc(1.5rem + 4ch);
}

/* The rows of the tenant form, single page or one fieldset per step (blocks/form/_fields). */
.requete__line,
.requete :is(.public-form__fields, .form-steps__panel) > .mb-3 {
    position: relative;
    counter-increment: mz-line;
}

.requete__line::before,
.requete :is(.public-form__fields, .form-steps__panel) > .mb-3::before {
    content: counter(mz-line, decimal-leading-zero);
    position: absolute;
    left: -4ch;
    color: var(--mz-ink-dash);
}

.requete__line {
    color: var(--mz-paper);
}

.requete__blank {
    min-height: calc(var(--mz-console-leading) * 1em);
}

.requete__header,
.requete__muted,
.requete__missing {
    color: var(--mz-comment);
}

/* A button once the script runs (it cycles the verb), a label before. */
.requete__verb {
    --bs-badge-padding-x: 0.5rem;
    --bs-badge-padding-y: 0.25rem;
    --bs-badge-font-size: 0.74rem;
    --bs-badge-color: var(--mz-ink);
    --bs-badge-border-radius: 6px;
    border: 0;
    background: var(--mz-accent);
    font-family: inherit;
    vertical-align: 0.1em;
}

button.requete__verb {
    cursor: pointer;
}

.requete__verb[data-mz-verb="GET"] {
    background: var(--mz-key);
}

.requete__verb[data-mz-verb="PUT"] {
    background: var(--mz-band-soft);
}

.requete__verb[data-mz-verb="PATCH"] {
    background: var(--mz-mist);
}

.requete__verb[data-mz-verb="DELETE"] {
    background: var(--mz-error);
}

/* The tenant form, written as the JSON body of the request: the rows stay Bootstrap's, so
   validation, the help text and the in-place answer work as on any other page. */
.requete :is(.public-form__fields, .form-steps__panel)::before,
.requete :is(.public-form__fields, .form-steps__panel)::after {
    display: block;
    margin-left: -4ch;
    white-space: pre;
    counter-increment: mz-line;
}

.requete :is(.public-form__fields, .form-steps__panel)::before {
    content: counter(mz-line, decimal-leading-zero) "  {";
}

.requete :is(.public-form__fields, .form-steps__panel)::after {
    content: counter(mz-line, decimal-leading-zero) "  }";
}

.requete :is(.public-form__fields, .form-steps__panel) > .mb-3 {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    column-gap: 0.5ch;
    padding-left: 2ch;
}

.requete .form-label {
    margin: 0;
    font-weight: 400;
    color: var(--mz-key);
}

.requete .form-label::before {
    content: "\"";
}

.requete .form-label::after,
.requete .form-label.required::after {
    content: "\": \"" / "";
    color: var(--mz-comment);
    font-weight: 400;
}

.requete .form-label.required::after {
    content: "\"*: \"" / "";
}

.requete .public-form .form-control,
.requete .public-form .form-select {
    order: 1;
    flex: 1 1 10ch;
    width: auto;
    min-width: 8ch;
    padding: 0 2px;
    border: 0;
    border-bottom: 1px dashed var(--mz-ink-dash);
    border-radius: 0;
    background-color: transparent;
    color: var(--mz-string);
    font-family: inherit;
    font-size: inherit;
    line-height: inherit;
    box-shadow: none;
}

.requete .public-form textarea.form-control {
    flex-basis: 100%;
    margin-top: 0.25rem;
    padding: 0.6rem 0.75rem;
    border: 1px dashed var(--mz-ink-dash);
    border-radius: 0.625rem;
    background-color: var(--mz-ink-raised);
    line-height: 1.6;
}

.requete .public-form .form-control:focus,
.requete .public-form .form-select:focus {
    border-color: var(--mz-accent);
    box-shadow: none;
}

.requete .public-form .form-control::placeholder {
    color: var(--mz-comment);
}

.requete :is(.public-form__fields, .form-steps__panel) > .mb-3:has(> .form-control, > .form-select)::after {
    content: "\",";
    order: 2;
}

.requete :is(.invalid-feedback, .form-text) {
    order: 3;
    flex-basis: 100%;
    font-size: 0.85em;
}

.requete .invalid-feedback {
    color: var(--mz-error);
}

.requete .form-text {
    color: var(--mz-comment);
}

.requete :is(.invalid-feedback, .form-text)::before {
    content: "// " / "";
}

.requete .form-control[aria-invalid="true"] {
    border-color: var(--mz-error);
}

/* A checkbox is a boolean: its key, the box, true or false, and its sentence as a comment.
   The key is the field's own, which the script reads off the control's name. */
.requete .form-check {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    column-gap: 1ch;
    min-height: 0;
    margin: 0;
    padding: 0;
}

.requete .form-check[data-mz-key]::before {
    content: "\"" attr(data-mz-key) "\":";
    color: var(--mz-key);
}

.requete .form-check .form-check-input {
    order: 1;
    float: none;
    flex-shrink: 0;
    margin: 0;
    border-color: var(--mz-key);
    background-color: transparent;
}

.requete .form-check .form-check-input:checked {
    border-color: var(--mz-accent);
    background-color: var(--mz-accent);
}

.requete .form-check::after {
    content: "false";
    order: 2;
    color: var(--mz-band-soft);
}

.requete .form-check:has(.form-check-input:checked)::after {
    content: "true";
}

.requete .form-check-label {
    order: 3;
    flex-basis: 100%;
    color: var(--mz-comment);
}

.requete .form-check-label::before {
    content: "// " / "";
}

.requete .public-form form {
    display: flex;
    flex-direction: column;
}

.requete .btn-accent {
    --bs-btn-bg: var(--mz-accent);
    --bs-btn-border-color: var(--mz-accent);
    --bs-btn-color: var(--mz-ink);
    --bs-btn-hover-bg: var(--mz-accent-soft);
    --bs-btn-hover-border-color: var(--mz-accent-soft);
    --bs-btn-hover-color: var(--mz-ink);
    --bs-btn-active-bg: var(--mz-accent-soft);
    --bs-btn-active-border-color: var(--mz-accent-soft);
    --bs-btn-active-color: var(--mz-ink);
    --bs-btn-disabled-bg: var(--mz-accent);
    --bs-btn-disabled-border-color: var(--mz-accent);
    --bs-btn-disabled-color: var(--mz-ink);
}

.requete .btn-accent[data-mz-shortcut] .arrow {
    display: none;
}

.requete .btn-accent[data-mz-shortcut]::after {
    content: attr(data-mz-shortcut);
    margin-left: 0.6em;
    padding: 0.05em 0.45em;
    border: 1px solid color-mix(in srgb, var(--mz-ink) 35%, transparent);
    border-radius: 4px;
    font-weight: 400;
}

.requete__response {
    border-top: 1px dashed var(--mz-ink-line);
    white-space: pre-wrap;
    overflow-wrap: anywhere;
}

.requete__status {
    font-weight: 700;
    color: var(--mz-key);
}

.requete__status::before {
    content: "";
    display: inline-block;
    width: 0.5rem;
    height: 0.5rem;
    margin-right: 0.6rem;
    border-radius: 50%;
    background: currentcolor;
    vertical-align: 0.1em;
}

.requete__status.is-error {
    color: var(--mz-error);
}

.requete__k {
    color: var(--mz-key);
}

.requete__s {
    color: var(--mz-string);
}

.requete__n {
    color: var(--mz-band-soft);
}

/* Without the script, the server's own answers still read as one: a 422 over a rejected form,
   a 201 over the thank-you. The script replaces both with a full response. */
.requete .public-form:has(.is-invalid)::before {
    content: "HTTP/3 422 Unprocessable Entity";
    display: block;
    margin-bottom: 0.5rem;
    color: var(--mz-error);
    font-weight: 700;
}

.requete__payload :has(> .confirm-badge)::before {
    content: "HTTP/3 201 Created";
    color: var(--mz-key);
    font-weight: 700;
}

.requete .confirm-badge {
    display: none;
}

.requete__payload :has(> .confirm-badge) :is(.h4, .text-muted-ap) {
    margin: 0;
    font-family: inherit;
    font-size: inherit;
    font-weight: 400;
    color: var(--mz-string);
}

.requete .public-form .text-muted-ap {
    color: var(--mz-comment);
}

/* ---- Webby, the easter egg app/mehdi-zaidi/webby.js lowers on a thread ---- */

.mz-webby {
    right: clamp(1rem, 12vw, 12rem);
    z-index: 1060;
    width: 8rem;
    transform-origin: 50% 0;
    will-change: transform;
    cursor: pointer;
}

/* The accent marks the thread on the band and the ink, the halo keeps his legs on the paper. */
.mz-webby__thread {
    width: 2px;
    height: 0;
    background: var(--mz-accent);
    transition: height 0.7s ease-in;
}

.mz-webby.is-down .mz-webby__thread {
    height: 34vh;
    transition: height 1.3s cubic-bezier(0.34, 1.56, 0.64, 1);
}

.mz-webby__spider {
    margin-top: -0.25rem;
    filter: drop-shadow(0 0 2px var(--mz-paper)) drop-shadow(0 10px 14px color-mix(in srgb, var(--mz-ink) 35%, transparent));
}

@media (prefers-reduced-motion: no-preference) {
    .mz-webby.is-down {
        --mz-sway: 4deg;
        animation: mz-sway 2.6s ease-in-out infinite alternate;
    }
}

@media (prefers-reduced-motion: reduce) {
    .mz-webby__thread,
    .mz-webby.is-down .mz-webby__thread {
        transition: none;
    }
}

/* ---- signature ---- */

/* app/mehdi-zaidi/letters.js fits the size to the measure; 12vw is what shows before it does. */
.signature__name {
    padding-bottom: 0.06em;
    font-size: 12vw;
    font-weight: 400;
    line-height: 0.86;
    letter-spacing: -0.05em;
}

/* ---- Motion ---- */

@keyframes mz-rise {
    from {
        opacity: 0;
        translate: 0 0.5em;
        rotate: 3deg;
    }
}

@keyframes mz-lift {
    from {
        opacity: 0;
        translate: 0 40px;
    }
}

@keyframes mz-draw {
    from {
        stroke-dashoffset: 1;
    }
}

@keyframes mz-pulse {
    50% {
        opacity: 0.25;
    }
}

@keyframes mz-menu {
    from {
        clip-path: circle(0% at 92% 4%);
    }

    to {
        clip-path: circle(150% at 92% 4%);
    }
}

/* Swings to either side of rest by --mz-sway, played `alternate`. */
@keyframes mz-sway {
    from {
        rotate: calc(-1 * var(--mz-sway));
    }

    to {
        rotate: var(--mz-sway);
    }
}

@keyframes mz-cue {
    0% {
        transform: scaleY(0);
        transform-origin: 50% 0;
    }

    50% {
        transform: scaleY(1);
        transform-origin: 50% 0;
    }

    50.1% {
        transform-origin: 50% 100%;
    }

    100% {
        transform: scaleY(0);
        transform-origin: 50% 100%;
    }
}

@media (prefers-reduced-motion: reduce) {
    html {
        scroll-behavior: auto;
    }

    .mz-clock__dot {
        animation: none;
    }
}
