/* Eutropy brand tokens (2026 identity) */
:root {
    --eutropy-noir-vert: #050c0a;
    --eutropy-vert-profond: #0f261e;
    --eutropy-vert-moyen: #368e75;
    --eutropy-accent: #4dcdac;
    --eutropy-accent-hover: #69dcbf;
    --eutropy-vert-clair: #b2d6cb;
    --eutropy-blanc-vert: #e8efec;
    --font-heading: 'Outfit', sans-serif;
    --font-body: 'Inter', sans-serif;
    /* The whole header is derived from one number: the width the logo lockup
       renders at. The logo file is 1500x435, so its glyph footprint - which
       the brand guide's protection-zone rule defines as the clear space - is
       always width * 435/1500 = width * 0.29. Keeping the clear space tied to
       the width by calc() means the protection zone stays correct at any logo
       size instead of having to be re-derived by hand each time.

       Header height therefore = clear space + glyph + clear space = 0.87 *
       width (102px at the 118px desktop lockup, which matches the measured
       header). --nav-offset is that height plus a small gap, so anchored
       sections clear the navbar with the title fully visible. */
    --logo-width: 118px;
    --logo-clear-space: calc(var(--logo-width) * 0.29);
    --nav-offset: calc(var(--logo-width) * 0.87 + 12px);
    /* The scrolled header: same logo, less space above and below it, and where
       sections land under it. */
    --logo-compact-clear-space: calc(var(--logo-clear-space) * 0.78);
    --nav-offset-compact: calc(var(--logo-width) * 0.29 + var(--logo-compact-clear-space) * 2 + 12px);
    /* Mobile lockup renders 104px wide -> 104 * 0.29 = 30px. */
    --logo-clear-space-mobile: 30px;
}

/* Large screens: scale the lockup with the viewport so the header keeps pace
   with the hero type, which now grows past it. Everything above is derived
   from this one value, so the clear space and the anchor offset follow
   automatically and the protection zone stays proportionally correct.
   Solved so 1280px reproduces today's 118px exactly, capped at 180px. */
@media (min-width: 992px) {
    :root {
        --logo-width: clamp(118px, 9.219vw, 354px);
    }
}

/* Anchor targets (nav links, footer links, and the #section hash the language
   switch lands on) are covered by the fixed header without this, so you arrive
   at the section's body copy with its title hidden behind the navbar. */
section[id],
footer[id] {
    scroll-margin-top: var(--nav-offset-compact);
}

/* The removed slitslider plugin used to set this width via inline JS at
   runtime; now that the plugin is gone (single static slide, no carousel),
   it needs to be plain CSS so .slide-caption/.caption-content still have a
   real width to size themselves against instead of collapsing to 0. */
#slider, .sl-slider {
    width: 100%;
    height: 100%;
}

body, p, span, a, li, label, input, textarea, button {
    font-family: var(--font-body) !important;
}

/* Every dark background on the page comes from individual <section>
   elements, not from html/body itself - the actual base canvas underneath
   everything is the browser's default white. That's invisible during normal
   scrolling since sections tile edge-to-edge, but it flashes through during
   fast-scroll overscroll/rubber-band bounce, and during brief compositor lag
   (this page runs a lot of continuous animations - the rotating card
   borders, the body::before gradient, .stars). Giving html/body the same
   dark color as every section means that flash is the brand's dark green
   instead of white. */
html, body {
    background-color: var(--eutropy-noir-vert);
}

/* ===================================================================
   Preloader: ported from the Eutropy app's <Loading size="md" /> component
   (PSELAB/client-tauri/src/components/Loading.tsx + Loading.css), so the
   marketing site's loader matches the product's own loading spinner.
   =================================================================== */

#preloader {
    background-color: var(--eutropy-noir-vert);
    display: flex;
    align-items: center;
    justify-content: center;
}

.loading {
    display: flex;
    align-items: center;
    justify-content: center;
    gap: 10px;
    color: rgba(178, 214, 203, 0.58);
}

.loading__spinner {
    position: relative;
    display: flex;
    align-items: center;
    justify-content: center;
    flex: none;
}
.loading--md .loading__spinner {
    width: 72px;
    height: 72px;
}

.loading__ring {
    position: absolute;
    inset: 0;
    border-radius: 50%;
    border: 2.5px solid transparent;
    border-top-color: var(--eutropy-accent);
    border-right-color: var(--eutropy-accent);
    animation: loading-spin 1s linear infinite;
}
.loading__ring--inner {
    inset: 13%;
    border-top-color: transparent;
    border-right-color: transparent;
    border-bottom-color: var(--eutropy-accent-hover);
    border-left-color: var(--eutropy-accent-hover);
    opacity: 0.55;
    animation: loading-spin 1.4s linear infinite reverse;
}

.loading__glyph {
    position: relative;
    z-index: 1;
    animation: loading-pulse 1.4s ease-in-out infinite alternate;
}
.loading--md .loading__glyph {
    width: 40px;
    height: 40px;
}

@keyframes loading-spin {
    from { transform: rotate(0deg); }
    to   { transform: rotate(360deg); }
}

@keyframes loading-pulse {
    from { transform: scale(0.9);  opacity: 0.8; }
    to   { transform: scale(1.06); opacity: 1; }
}

h1, h2, h3, h4, h5, h6,
.section-title, .caption-title, .eutropy-brand, .btn-demo {
    font-family: var(--font-heading) !important;
    font-weight: 500;
}

section:not(#home) {
    background: var(--eutropy-noir-vert) !important;
}

/* ===================================================================
   Header: logo clear space + vertical alignment with the nav menu
   =================================================================== */

/* Match the sitewide .container padding (10% desktop / 15px mobile, see
   bootstrap.min.css and main.css) so the navbar's left/right extremities
   line up with every other section's content instead of using their own
   fixed offset. Bootstrap's .container:before/:after clearfix pseudo-elements
   (content:" "; display:table) still generate boxes once this container
   becomes display:flex below, and a flex container treats generated content
   as real flex items - with justify-content:space-between that silently
   split the free space into three equal gaps (before/after included as
   invisible 0-width items) instead of pinning content flush to the padded
   edges. Removing their content keeps them from partaking in the flex
   layout at all. */
#navigation .container::before,
#navigation .container::after {
    content: none !important;
}

#navigation .container {
    padding: 0 10% !important;
}

@media (max-width: 700px) {
    /* Mirrors main.css's own .container mobile override at this breakpoint. */
    #navigation .container {
        padding: 0 15px !important;
    }
}

#navigation .navbar-header {
    display: flex !important;
    align-items: center !important;
    float: none !important;
}

/* Same clearfix-vs-flex issue as .container above: main.css flexes
   .navbar-header with justify-content:space-between at mobile widths, and
   bootstrap's :before/:after clearfix boxes ride along as extra flex items
   there too, throwing off the logo/toggle-button spacing. */
#navigation .navbar-header::before,
#navigation .navbar-header::after {
    content: none !important;
}

/* Bootstrap gives .navbar-header/.navbar-collapse a -15px side margin
   below 768px (only reset back to 0 at >=768px) so they bleed past the
   container's own gutter on phones - a leftover from the old float-based
   navbar. That cancels out the container padding we just aligned to the
   rest of the site, so pin it to 0 at every width. */
#navigation .navbar-header,
#navigation .navbar-collapse {
    margin-left: 0 !important;
    margin-right: 0 !important;
}

.navbar-brand-container {
    display: flex !important;
    align-items: center !important;
}

.navbar-brand-container .navbar-brand {
    width: var(--logo-width) !important;
    max-width: var(--logo-width) !important;
    height: auto;
    display: block;
    /* Clear space above, below and to the right of the logo, isolating it from the nav menu */
    margin: var(--logo-clear-space) var(--logo-clear-space) var(--logo-clear-space) 0 !important;
    padding: 0 !important;
}

#navigation.animated-header,
#navigation.scrolled {
    padding: 0 !important;
}

/* Square off the header and its mobile dropdown. main.css rounds the bottom
   corners in five separate places (18px on .scrolled, 10px at <=991px, 15px
   on both the header and the dropdown at <=768px), which read as a floating
   card rather than a full-bleed bar. One override covers every state; it also
   lets the dropdown sit seamlessly against the header instead of the two
   rounded edges meeting. */
#navigation,
#navigation.scrolled,
#navigation.animated-header,
.navbar-inverse .navbar-collapse {
    border-radius: 0 !important;
}

/* Vertically align the logo block and the nav menu on one shared row on desktop */
@media (min-width: 992px) {
    #navigation .container {
        display: flex !important;
        align-items: center !important;
        justify-content: space-between !important;
    }
    #navigation .navbar-collapse {
        float: none !important;
        width: auto !important;
    }
    #navigation .navbar-nav {
        float: none !important;
        display: flex !important;
        align-items: center !important;
        margin: 0 !important;
    }

    /* The last nav item is the flag, and its <li> already ends exactly at the
       container's content edge - but the link's own right padding/margin
       (inherited from the text links, where that padding is wanted for the
       click target) inset the graphic ~21px further, reading as a gap the
       text links don't have. Text needs that breathing room; an image sitting
       against the edge does not, so drop it for this item only. */
    #nav > li:last-child > a.language-btn {
        padding-right: 0 !important;
        margin-right: 0 !important;
    }
}

@media (max-width: 768px) {
    /* main.css's own mobile rule for this selector sets flex:1, a
       max-width:calc(100% - 80px) cap and margin-right:20px - a leftover
       sizing recipe that no longer matches the toggle button's real width,
       so it left a stray gap before the toggle instead of the logo and
       toggle sitting flush against the header's padded edges. Reset it to
       a plain auto-sized flex item. */
    .navbar-brand-container {
        flex: 0 0 auto !important;
        max-width: none !important;
        margin-right: 0 !important;
    }
    /* Bigger, legible lockup on phones, with the brand guide's protection
       zone applied equally on all four sides (including the left, which
       previously ran flush to the container gutter). */
    .navbar-brand-container .navbar-brand {
        max-width: 104px !important;
        width: 104px !important;
        margin: var(--logo-clear-space-mobile) !important;
    }

    /* main.css pins the toggle button 15px in from the header's right edge
       with position:absolute - another leftover offset from when the header
       had no container padding of its own. The container now supplies that
       padding, so flush the toggle to the header's edge instead. */
    .navbar-toggle {
        right: 0 !important;
    }

    /* The mobile menu felt laggy because main.css runs a live backdrop-filter
       blur on both the fixed header and the dropdown *while* the dropdown's
       height is being animated open/closed - recomputing a blur every frame
       of a resize is expensive, especially on phone GPUs. Both backgrounds
       are already ~95% opaque black, so the blur was barely visible anyway;
       dropping it keeps the same look at a fraction of the cost.
       The dropdown no longer animates its height (see below), so the header
       itself has its blur back, matching wider screens; see "Phone header"
       further down. */
    .navbar-inverse .navbar-collapse {
        backdrop-filter: none !important;
        -webkit-backdrop-filter: none !important;
    }
}

/* Everywhere the menu button shows (main.css shows it up to 991px), the menu is
   the same stacked, centred dropdown. Bootstrap only stacks below 768px, and
   lays the links out in a row above that. The .98 closes the gap with the
   desktop rules at 992px, which fractional widths can otherwise fall into. */
@media (max-width: 991.98px) {
    /* Removing the blur wasn't enough - the menu was still animating
       `height` (Bootstrap's default), which forces the browser to reflow
       the whole page on every frame. That's what actually reads as "lag",
       not just a cost added on top. Since the dropdown already overlays
       the page below the header instead of pushing it down, there's no
       reason to animate its size at all: take it out of document flow with
       position:absolute, force it to full height immediately (this also
       neutralizes the inline height Bootstrap's JS still sets - !important
       beats it), and animate opacity/transform instead. Both are
       GPU-composited and never touch layout, so open/close now feels
       instant instead of janky, matching what sites like Murex do. */
    .navbar-inverse .navbar-collapse {
        position: absolute !important;
        top: 100% !important;
        left: 0 !important;
        right: 0 !important;
        width: 100% !important;
        height: auto !important;
        transition: opacity 0.2s ease, transform 0.2s ease !important;
        opacity: 0;
        transform: translateY(-8px);
        pointer-events: none;
        /* main.css pushes the dropdown 10px clear of the header and pads it
           25px top/bottom, leaving a transparent sliver under the header plus
           a big empty band before the first link. Sit it flush against the
           header and keep only enough padding to breathe. */
        margin-top: 0 !important;
        padding: 10px 0 !important;
    }

    .navbar-inverse .navbar-collapse.in {
        opacity: 1;
        transform: translateY(0);
        pointer-events: auto;
    }

    /* The logo on the left, the button on the right. */
    #navigation .navbar-header {
        justify-content: space-between !important;
        width: 100% !important;
    }

    .navbar-toggle {
        display: block !important;
        visibility: visible !important;
    }

    .navbar-inverse .navbar-collapse.collapse {
        display: none !important;
    }

    .navbar-inverse .navbar-collapse.collapse.in,
    .navbar-inverse .navbar-collapse.collapsing {
        display: block !important;
    }

    .navbar-inverse .navbar-nav {
        float: none !important;
        margin: 0 !important;
        padding: 0 20px !important;
    }

    .navbar-inverse .navbar-nav > li {
        float: none !important;
        margin: 8px 0 !important;
        text-align: center !important;
    }

    .navbar-inverse .navbar-nav > li > a {
        display: block !important;
        width: 100% !important;
        margin: 5px 0 !important;
        text-align: center !important;
        border-radius: 8px !important;
    }

    .navbar-inverse .navbar-nav > li > a:hover,
    .navbar-inverse .navbar-nav > li > a:focus {
        transform: translateY(-2px) !important;
        box-shadow: 0 4px 12px rgba(77, 205, 172, 0.2) !important;
    }
}

/* Nav menu typography: Outfit, evenly spaced, small-caps rhythm for a premium feel */
.navbar-nav > li > a.nav-link {
    font-family: var(--font-heading) !important;
    font-weight: 500 !important;
    font-size: 14px !important;
    letter-spacing: 0.06em !important;
    text-transform: uppercase !important;
    color: var(--eutropy-blanc-vert) !important;
    padding: 10px 16px !important;
    transition: color 0.2s ease;
    /* main.css tints every link in the small-screen menu, except the one it marks
       as current, so the links looked inconsistent. */
    background: transparent !important;
}

.navbar-nav > li > a.nav-link:hover,
.navbar-nav > li > a.nav-link:focus {
    color: var(--eutropy-accent) !important;
    background: transparent !important;
}

/* Hero: flat Noir vert, the one dark section on the page. */
#home {
    background: var(--eutropy-noir-vert) !important;
    position: relative;
    overflow: hidden;
}

/* main.css darkens the hero with a 50% black overlay left from the old video. */
#home::before {
    content: none;
}

/* One semantic H1, two visual tiers inside it: a small keyword-rich kicker line,
   then the big brand-voice headline. Solves both the SEO (single strong H1) and
   the hierarchy complaint (kicker was reading bigger than the actual message). */
#home .caption-content .hero-title {
    margin: 0 auto 22px auto;
    max-width: 900px;
}

#home .caption-content .hero-kicker {
    display: block;
    color: var(--eutropy-accent) !important;
    font-family: var(--font-heading) !important;
    font-weight: 500 !important;
    letter-spacing: 0.12em;
    text-transform: uppercase;
    font-size: 15px !important;
    margin-bottom: 16px;
    /* main.css has a very old rule from the original slider template,
       `.caption-content span:first-child { margin-top: 100px; margin-left:
       20px; }`, meant for a hero copy structure that no longer exists.
       .hero-kicker is still literally the first span descendant of
       .caption-content (nested one level deeper, inside the h1), so it
       still matches: the top margin pushed the whole copy stack 100px
       below where it should start, and the left margin narrowed the
       eyebrow's box by 20px on one side only - which, once the copy is
       centred, put its centre 10px right of everything else in the
       column. Both were only ever neutralised inside the
       landscape-rotation media query, never for the normal hero. */
    margin-top: 0;
    margin-left: 0;
    /* Trailing letter-spacing sits after the final character, so a centred
       letterspaced line renders about half a letter-space left of true
       centre. text-indent of the same amount cancels it. */
    text-indent: 0.12em;
}

#home .caption-content .hero-headline {
    display: block;
    font-size: 4rem !important;
    line-height: 1.1 !important;
    /* Outfit Light, by choice: the chart's H1 weight is Medium (500). */
    font-weight: 300 !important;
    color: #ffffff !important;
}

/* ===================================================================
   Large-screen typography
   -------------------------------------------------------------------
   Every size on the page was a fixed value with no breakpoint above
   992px, so the type was byte-for-byte identical from a 1280px laptop
   to a 2560px monitor while the viewport doubled - the headline went
   from filling 47% of the screen to 24% of it, which is what reads as
   "too small" on a big display.

   Each clamp() is solved so its lower bound reproduces today's size at
   1280px exactly (nothing changes on current laptops) and grows from
   there to a hard ceiling, so it can't run away on ultrawide screens.
   Scoped to >=992px so phones, tablets and the landscape-rotation
   block are untouched; that block sits later in this file and keeps
   winning for rotated phones.

   Note: html has font-size:10px (bootstrap.min.css), so 1rem here is
   10px, not 16px - `4rem` on the headline was really 40px. These are
   px/clamp values to stay independent of that.
   =================================================================== */
@media (min-width: 992px) {
    #home .caption-content .hero-kicker {
        font-size: clamp(15px, 1.172vw, 45px) !important;
    }

    #home .caption-content .hero-headline {
        font-size: clamp(40px, 3.125vw, 120px) !important;
    }

    /* Same share of the viewport as at 1280px (900/1280 = 70.3vw), so the
       h1 keeps its proportions instead of collapsing to a narrow column. */
    #home .caption-content .hero-title {
        max-width: clamp(900px, 70.3vw, 2700px);
    }

    .section-title,
    .section-title h2 {
        font-size: clamp(22px, 1.719vw, 66px) !important;
    }

    /* Body copy inside the cards, and the intro paragraph under a few
       section titles (those carry an inline font-size/max-width from
       the markup, which an !important declaration still outranks).
       Scaling these at the same rate as everything else is what keeps
       the characters-per-line constant: the column and the type grow
       together, so the measure stays as readable as it is at 1280px. */
    .eutropy-card p {
        font-size: clamp(14px, 1.094vw, 42px);
    }

    /* .supporters-tagline declares its own font-size in a plain rule further
       down this file, which would win here on source order, so it is scaled
       with the rest of the below-the-fold text - search "Large-screen section
       chrome". */

    /* Header menu: the logo grows via --logo-width above, so the links have
       to keep pace or the nav reads as undersized next to it. The content
       column widens alongside them (below), so the lockup and the 7 items
       still fit on one row at the ceiling. */
    .navbar-nav > li > a.nav-link {
        font-size: clamp(14px, 1.094vw, 42px) !important;
        padding-left: clamp(16px, 1.25vw, 48px) !important;
        padding-right: clamp(16px, 1.25vw, 48px) !important;
    }

    /* The call-to-action was the one thing left at a fixed size, so it kept
       shrinking against everything around it. It also started out too small
       in absolute terms: main.css sets `font-size: 1.1rem`, which against
       this project's 10px root is 11px - smaller than the 14px nav links,
       for the page's primary action. The floor here raises it to 16px so it
       outweighs the menu, and it then scales at the same rate as the rest.

       border-radius is a large constant rather than a scaled value: the
       browser clamps a radius to half the box, so this stays a true pill at
       every size instead of the corners flattening as the button grows. */
    .btn-demo {
        font-size: clamp(16px, 1.25vw, 48px) !important;
        padding: clamp(14px, 1.094vw, 42px) clamp(36px, 2.813vw, 108px) !important;
        border-radius: 999px !important;
    }

    /* The form's submit button is full-width, so only its type and vertical
       padding need to scale - the horizontal padding is doing nothing. */
    .classy-contact-form .btn-demo {
        font-size: clamp(17px, 1.328vw, 51px) !important;
        padding: clamp(18px, 1.406vw, 54px) 0 !important;
    }

}

/* ===================================================================
   Hero: one centred column of copy
   -------------------------------------------------------------------
   The hero used to sit in a chain of absolutely positioned wrappers left
   over from a removed slider plugin (.sl-slider -> .slide-caption ->
   .caption-content). The chain goes back into normal flow below, and #home
   centres it vertically while growing past one screen if it has to.
   =================================================================== */

#home #slider {
    width: 100%;
}

/* Drawn by js/landing-gears.js, behind the copy. */
.landing-gears {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    z-index: 0;
    pointer-events: none;
}

.product-shot {
    display: block;
    width: 100%;
    height: auto;
    border-radius: 14px;
    box-shadow: 0 18px 40px -18px rgba(5, 12, 10, 0.6);
    background: #0b1512;
}

@media (min-width: 992px) {
    #home {
        display: flex !important;
        align-items: center;
        height: auto !important;
        min-height: 100vh !important;
        overflow: visible !important;
        /* The hero is in flow from the top, so it has to clear the fixed
           header itself instead of relying on the old centring. */
        padding: calc(var(--nav-offset) + 2.5vh) 0 5vh !important;
    }

    #home #slider,
    #home .sl-slider {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        height: auto !important;
    }

    #home #slider {
        overflow: visible !important;
    }

    #home .slide-caption {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        display: block !important;
        width: 100% !important;
        height: auto !important;
        min-height: 0 !important;
    }

    #home .caption-content {
        position: static !important;
        transform: none !important;
        min-height: 0 !important;
        /* main.css caps this at 85vh in its device-specific blocks, which
           would clip the shots rather than let the hero grow. */
        max-height: none !important;
        display: block !important;
        /* Same 10% gutter as .container, so the hero lines up with every
           section below it. */
        padding: 0 10% !important;
        /* One centre line for the whole copy stack. Left-aligned, the five
           elements had five different centres (eyebrow 504, headline 469,
           subtitle 459, button 357, proof 505) because each is a different
           width - so nothing agreed with anything. Centring gives the
           column a single axis, and puts the eyebrow visually on top of
           the headline it introduces rather than overhanging it by 51px. */
        text-align: center !important;
    }

    #home .caption-content .hero-copy {
        display: flex;
        flex-direction: column;
        /* Also makes every child shrink to its own content instead of
           stretching to the column - which is what un-stretches the proof
           line (it was a 628px capsule around 346px of text). */
        align-items: center;
        width: 100%;
    }

    /* ---- Type scale -------------------------------------------------
       The sitewide proportional scaling (see the large-screen block
       above) is right for section headings but overshoots for hero copy
       that is meant to be READ: it put the eyebrow at 22-30px and the
       body at 27-36px, both well past comfortable reading sizes. These
       override it for the hero only, on a scale built around the
       headline: a small letterspaced eyebrow, a dominant headline with
       tight leading and slight negative tracking (display type needs
       less air between lines and letters than body type), and body at
       17-23px with open 1.62 leading.

       Vertical rhythm is set in em rather than px or vw, so the spacing
       between elements scales with each element's own type size and the
       proportions hold at every viewport width instead of drifting. */

    #home .caption-content .hero-kicker {
        font-size: clamp(12px, 0.72vw, 19px) !important;
        letter-spacing: 0.18em;
        /* Matches the letter-spacing above - see the base rule for why. */
        text-indent: 0.18em;
        margin-bottom: 1.5em;
        opacity: 0.92;
    }

    /* The copy has the full page width now, so the headline can dominate it.
       The French line needs about 13.3x its font-size to stay on one line,
       which 4.2vw leaves well inside the 80vw column. */
    #home .caption-content .hero-headline {
        font-size: clamp(40px, 4.2vw, 110px) !important;
        line-height: 1.04 !important;
        letter-spacing: -0.025em;
    }

    #home .caption-content .hero-title {
        /* Any ch/em cap has to sit on .hero-headline, not here: the h1 has
           no font-size of its own and would resolve one against an
           inherited ~36px - an earlier pass did exactly that and capped
           the headline at 540px, forcing it to three lines. Here the h1
           just needs to shrink to its text and centre. */
        max-width: none;
        margin: 0 auto 0.55em auto;
    }

}

/* Short viewports: tighten the copy's rhythm and ease the display type down
   a step so the whole stack stays on one screen. */
@media (min-width: 992px) and (max-height: 900px) {
    #home {
        padding: calc(var(--nav-offset) + 1.5vh) 0 3.5vh !important;
    }

    #home .caption-content .hero-kicker {
        font-size: clamp(11px, 0.68vw, 16px) !important;
        margin-bottom: 1.2em;
    }

    #home .caption-content .hero-headline {
        font-size: clamp(36px, 3.6vw, 90px) !important;
    }

    #home .caption-content .hero-title {
        margin-bottom: 0.45em;
    }

}

@media (max-width: 991px) {
    /* One centred column that fills the screen. */
    #home {
        display: flex !important;
        align-items: center;
        height: auto !important;
        min-height: 100vh !important;
        overflow: visible !important;
        padding: calc(var(--nav-offset) + 16px) 0 32px !important;
    }

    #home #slider,
    #home .sl-slider {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        height: auto !important;
    }

    #home .slide-caption {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        display: block !important;
        width: 100% !important;
        height: auto !important;
        min-height: 0 !important;
    }

    #home .caption-content {
        position: static !important;
        transform: none !important;
        min-height: 0 !important;
        /* main.css's device-specific blocks cap this at 85vh (and the
           wrapper hides its overflow), which clipped the shots off the
           bottom of the hero instead of letting the section grow. */
        max-height: none !important;
        padding: 0 15px !important;
    }

    #home #slider {
        overflow: visible !important;
    }

    /* .hero-copy has to be a flex column here too, not just on desktop.
       Left as a plain block, its children fall back to normal flow - and
       the demo button (inline-block) and the proof line (inline-flex) are
       both inline-level, so they sit SIDE BY SIDE on one line wherever
       there is room for them. On a 375px phone the button is nearly full
       width so they happened to wrap and it looked fine, which is why this
       slipped through; at 768px the button is only 210px and the proof
       line lands directly beside it. Stacking them is the whole point. */
    #home .caption-content .hero-copy {
        display: flex;
        flex-direction: column;
        align-items: center;
    }

    /* ---- Mobile type scale -------------------------------------------
       The inherited sizes gave a 15px eyebrow against a 24px headline -
       a 1.6x ratio, so the eyebrow competed with the headline instead of
       introducing it. These restore a real hierarchy (roughly 1 : 2.5 :
       1.3) and open the body leading, so the copy stays readable on a
       phone rather than just small. vw-based between the bounds so it
       scales smoothly from a 320px phone up to the 991px breakpoint. */
    #home .caption-content .hero-kicker {
        font-size: clamp(11px, 3.2vw, 14px) !important;
        letter-spacing: 0.16em;
        margin-bottom: 1.4em;
    }

    #home .caption-content .hero-headline {
        font-size: clamp(30px, 8.2vw, 52px) !important;
        line-height: 1.08 !important;
        letter-spacing: -0.02em;
    }

    #home .caption-content .hero-title {
        margin: 0 auto 0.5em auto;
        max-width: none;
    }

}

/* ===================================================================
   Product section: boxes, then full-width rows of text and screenshot
   -------------------------------------------------------------------
   Each row spans the whole page: a text column and a larger column holding
   the screenshot, swapping sides from one row to the next.
   The 10vw padding lines the text up with the .container content above it.
   =================================================================== */
.product-feature {
    display: grid;
    grid-template-columns: minmax(0, 2fr) minmax(0, 3fr);
    margin-top: clamp(50px, 3.906vw, 150px);
}

.product-feature + .product-feature {
    margin-top: 0;
}

.product-feature--reversed {
    grid-template-columns: minmax(0, 3fr) minmax(0, 2fr);
}

.product-feature-text {
    align-self: center;
    text-align: left;
    padding: clamp(32px, 3.5vw, 130px) clamp(32px, 4vw, 150px) clamp(32px, 3.5vw, 130px) 10vw;
}

.product-feature--reversed .product-feature-text {
    padding-left: clamp(32px, 4vw, 150px);
    padding-right: 10vw;
}

.product-feature-title {
    font-size: clamp(24px, 1.875vw, 72px);
    line-height: 1.2;
    margin: 0 0 0.6em;
}

.product-feature-text p {
    font-size: clamp(16px, 1.25vw, 48px);
    line-height: 1.6;
    margin: 0;
}

.product-feature-visual {
    display: flex;
    align-items: center;
    /* Trial without the green. To bring it back:
       background: var(--eutropy-vert-moyen); */
    padding: clamp(32px, 3.5vw, 130px);
}

.product-feature--reversed .product-feature-visual {
    order: -1;
}

/* On the outer side the screenshot stops on the page's 10% margin, like the
   text, the table and every section above and below. */
@media (min-width: 992px) {
    .product-feature:not(.product-feature--reversed) .product-feature-visual {
        padding-right: 10vw;
    }

    .product-feature--reversed .product-feature-visual {
        padding-left: 10vw;
    }
}

/* Stacked on phones and tablets: text first, then the screenshot, in both rows.
   The side margins follow the page's containers: 10% down to 701px, 15px
   below (bootstrap.min.css and main.css). */
@media (max-width: 991px) {
    .product-feature,
    .product-feature--reversed {
        grid-template-columns: minmax(0, 1fr);
    }

    .product-feature-text,
    .product-feature--reversed .product-feature-text {
        padding: 32px 10%;
    }

    .product-feature-visual {
        padding: 24px 10%;
    }

    .product-feature--reversed .product-feature-visual {
        order: 0;
    }
}

@media (max-width: 700px) {
    .product-feature-text,
    .product-feature--reversed .product-feature-text {
        padding: 32px 15px;
    }

    .product-feature-visual {
        padding: 24px 15px;
    }
}

/* Integration, back in the normal column under those rows. */
.product-block {
    margin-top: clamp(40px, 3.125vw, 120px);
}

.product-subtitle {
    text-align: center;
    font-size: clamp(20px, 1.5vw, 58px);
    margin: 0;
}

/* Notre vision and Join us: a title and a short centred text. */
.vision-text,
.join-text {
    text-align: center;
    font-size: clamp(18px, 1.406vw, 54px);
    line-height: 1.6;
    max-width: 44em;
    margin: 0 auto;
}

/* ===================================================================
   Notre vision: the foundation model figure
   -------------------------------------------------------------------
   Three inputs, the model at the centre, three outputs: text and thin
   lines only. Everything is sized from --core, and the line columns are
   exactly 0.42 x --core, the proportions of their 84 x 200 drawings, so
   the lines keep their shape and meet the labels at every width.
   =================================================================== */
.foundation-figure {
    --core: clamp(180px, 17vw, 480px);
    margin: clamp(64px, 5.5vw, 212px) 0 0;
}

.foundation-diagram {
    display: grid;
    grid-template-columns: minmax(0, 1fr) calc(var(--core) * 0.42) var(--core) calc(var(--core) * 0.42) minmax(0, 1fr);
    align-items: stretch;
}

.foundation-list {
    display: grid;
    /* Centres the rows at 6%, 50% and 94% of the height, where the lines are
       drawn (y = 12, 100 and 188 of 200). */
    grid-template-rows: 12% 76% 12%;
    align-items: center;
    height: var(--core);
    margin: 0;
    padding: 0;
    list-style: none;
}

/* !important: a sitewide rule sets every <li> to Inter. */
.foundation-list li {
    font-family: var(--font-heading) !important;
    font-weight: 500;
    font-size: clamp(16px, 1.25vw, 48px);
    line-height: 1.25;
    color: var(--eutropy-vert-profond);
}

.foundation-list--in {
    text-align: right;
}

.foundation-list--out {
    text-align: left;
}

/* svg. in the selector: Bootstrap's svg:not(:root) hides overflow, which would
   cut the lines where they cross into the core's column. */
svg.foundation-lines {
    display: block;
    width: 100%;
    height: var(--core);
    overflow: visible;
    fill: none;
    stroke: var(--eutropy-vert-moyen);
    stroke-width: 1.25px;
    stroke-linecap: round;
    stroke-linejoin: round;
}

.foundation-lines path {
    vector-effect: non-scaling-stroke;
}

/* The two opposing rings of the page loader, slowed down to suit a figure
   that stays on screen. */
.foundation-core {
    position: relative;
    display: flex;
    align-items: center;
    justify-content: center;
    width: var(--core);
    height: var(--core);
}

.foundation-ring {
    position: absolute;
    inset: 0;
    border-radius: 50%;
    border: 2px solid rgba(54, 142, 117, 0.16);
    border-top-color: var(--eutropy-vert-moyen);
    border-right-color: var(--eutropy-vert-moyen);
    animation: loading-spin 9s linear infinite;
}

.foundation-ring--inner {
    inset: 13.5%;
    border-color: rgba(77, 205, 172, 0.2);
    border-bottom-color: var(--eutropy-accent);
    border-left-color: var(--eutropy-accent);
    animation-duration: 13s;
    animation-direction: reverse;
}

.foundation-glyph {
    width: 46%;
    height: auto;
}

@media (prefers-reduced-motion: reduce) {
    .foundation-ring {
        animation: none;
    }
}

.foundation-caption {
    text-align: center;
    margin-top: clamp(56px, 4.722vw, 182px);
}

.foundation-title {
    font-size: clamp(20px, 1.719vw, 66px);
    line-height: 1.25;
    color: var(--eutropy-vert-profond);
    margin: 0 auto 0.5em;
    /* One line wherever it fits; balanced lines where it has to wrap. */
    text-wrap: balance;
}

/* !important on the font: a sitewide rule sets every <span> to Inter. */
.foundation-highlight {
    font-family: var(--font-heading) !important;
    color: var(--eutropy-vert-moyen);
}

.foundation-caption p {
    font-size: clamp(16px, 1.25vw, 48px);
    line-height: 1.6;
    color: var(--eutropy-vert-profond);
    margin: 0;
    text-wrap: balance;
}

/* Too narrow for three columns of text: one vertical arrow runs down through the
   core. The first and last labels sit at its two ends, centred on it, and the
   others branch off it to the left and right, with the same angled lines as the
   wide layout.

   Each half is one drawing, on the list's background, rather than separate pieces:
   every line then has the same thickness and the junctions are exact. It is drawn
   for centred rows 34px tall and side rows 52px tall, so the heights of li must
   stay in step with it. */
@media (max-width: 900px) {
    .foundation-figure {
        --core: 190px;
    }

    .foundation-diagram {
        grid-template-columns: minmax(0, 1fr);
        justify-items: center;
    }

    svg.foundation-lines {
        display: none;
    }

    .foundation-list {
        display: block;
        width: 100%;
        max-width: 560px;
        height: auto;
        background-position: center top;
        background-repeat: no-repeat;
    }

    .foundation-list--in {
        padding-bottom: 40px;
        background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='99' height='178' viewBox='0 0 99 178' fill='none' stroke='%23368e75' stroke-width='1.25' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M49.5 36V172M97.5 60H73.5L49.5 82M1.5 112H25.5L49.5 134M44.5 165.5L49.5 172L54.5 165.5'/%3E%3C/svg%3E");
    }

    .foundation-list--out {
        padding-top: 32px;
        background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='99' height='170' viewBox='0 0 99 170' fill='none' stroke='%23368e75' stroke-width='1.25' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M49.5 6V134M49.5 36L25.5 58H1.5M49.5 88L73.5 110H97.5M7.5 54.5L1.5 58L7.5 61.5M91.5 106.5L97.5 110L91.5 113.5M44.5 127.5L49.5 134L54.5 127.5'/%3E%3C/svg%3E");
    }

    .foundation-list li {
        display: flex;
        align-items: center;
        width: 50%;
        height: 52px;
        font-size: 17px;
        text-wrap: balance;
    }

    /* The two ends of the main line. */
    .foundation-list--in li:nth-child(1),
    .foundation-list--out li:nth-child(3) {
        justify-content: center;
        width: 100%;
        height: 34px;
        text-align: center;
    }

    .foundation-list--in li:nth-child(3),
    .foundation-list--out li:nth-child(1) {
        justify-content: flex-end;
        text-align: right;
    }

    .foundation-list li:nth-child(2) {
        flex-direction: row-reverse;
        justify-content: flex-end;
        margin-left: 50%;
        text-align: left;
    }

    /* Keeps the text clear of the branch drawn behind this space. */
    .foundation-list--in li:nth-child(n + 2)::after,
    .foundation-list--out li:nth-child(-n + 2)::after {
        content: "";
        flex: none;
        width: 58px;
    }

    /* Labels wrap on their own here, so no forced line breaks. */
    .foundation-list br {
        display: none;
    }
}

/* One benefit per box, ticked, under a short rule. Selectors carry p.card-benefit
   to outrank the sitewide .eutropy-card p rules; !important on the font because
   another sitewide rule forces <p> to Inter.

   Boxes in a row share the same four row heights (icon, title, sentence, benefit)
   through subgrid, so the rules and ticks line up across them however long each
   text runs. Browsers without subgrid push the benefit to the foot of the box. */
.eutropy-card--benefit {
    display: flex;
    flex-direction: column;
}

.eutropy-card p.card-benefit {
    display: flex;
    align-items: flex-start;
    gap: 0.55em;
    margin: auto 0 0;
    padding-top: 1em;
    font-family: var(--font-heading) !important;
    font-size: clamp(18px, 1.406vw, 54px);
    line-height: 1.3;
    border-top: 1px solid rgba(54, 142, 117, 0.25);
}

.eutropy-card p.card-benefit::before {
    content: "";
    flex: none;
    width: 1.05em;
    height: 1.3em;
    background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='none' stroke='%23368e75' stroke-width='2.6' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3.5 10.5 8 15l8.5-10'/%3E%3C/svg%3E") center / contain no-repeat;
}

/* Keeps the rule clear of the sentence above it when the sentence is the longest. */
.eutropy-card--benefit > p:not(.card-benefit) {
    margin-bottom: 1.2em;
}

@supports (grid-template-rows: subgrid) {
    .card-grid.card-grid--benefits {
        row-gap: 0;
    }

    .eutropy-card--benefit {
        display: grid;
        grid-row: span 4;
        grid-template-rows: subgrid;
        row-gap: 0;
    }

    .eutropy-card p.card-benefit {
        margin: 0;
    }

    /* With the row gap gone, this is what spaces boxes that stack. */
    @media (max-width: 991px) {
        .eutropy-card--benefit:not(:last-child) {
            margin-bottom: 30px;
        }
    }
}

/* The link to the job offers page, under the Join us text. Vert profond, since
   Vert moyen would be too faint at this size on the section's Blanc vert. */
.join-text--link {
    margin-top: 0.75em;
}

.join-text--link a {
    color: var(--eutropy-vert-profond);
    font-weight: 400;
    text-decoration: underline;
}

.join-text--link a:hover,
.join-text--link a:focus {
    color: var(--eutropy-vert-moyen);
}

/* ===================================================================
   Product section: comparison with other types of maintenance
   -------------------------------------------------------------------
   Built to make one column win: Eutropy is a raised Noir vert column with
   the glyph on top, standing out of a white card whose other columns stay
   quiet. Marks use the brand guide's semantic colours (red f9441d, orange
   f99a1d) and Vert moyen, each with its own shape so colour is never the only
   signal. --cap is how far the dark column rises above and below the card.

   It resizes like an image: everything inside is sized in cqw, a percentage of
   the .comparison box's own width, so the proportions are the same at every
   screen size. The values are what looked right at full screen, where that box
   is 951px wide (1cqw = 9.51px).
   =================================================================== */
.product-feature--comparison {
    --cap: 1.962cqw;
    /* With the table's rise, this gives the same gap as between the section's
       other parts: about 100px on a 1440px screen. */
    margin-top: clamp(72px, 6vw, 230px);
}

.product-feature--comparison .product-feature-visual {
    padding-bottom: 0;
}

/* Centred on the white card, like the text beside the screenshots. The column
   also holds the --cap above the card and the legend below it, so the same
   amounts are added here to keep the two middles level. */
.product-feature--comparison .product-feature-text {
    padding-top: 0.972vw;
    padding-bottom: 2.38vw;
}

.product-feature--comparison .product-feature-visual {
    padding-top: 0;
}

.product-feature--comparison .product-feature-visual {
    padding-left: 0;
    padding-right: 10vw;
}

.comparison {
    width: 100%;
    container-type: inline-size;
}

.comparison-table {
    width: 100%;
    margin-top: var(--cap);
    table-layout: fixed;
    border-collapse: separate;
    border-spacing: 0;
    background: #ffffff;
    border-radius: 1.682cqw;
    box-shadow: 0 2.734cqw 6.309cqw -3.575cqw rgba(15, 38, 30, 0.45);
    font-size: 1.472cqw;
    color: var(--eutropy-vert-profond);
}

.comparison-table th,
.comparison-table td {
    padding: 1.262cqw 0.842cqw;
    border-bottom: 1px solid rgba(15, 38, 30, 0.08);
    text-align: center;
    vertical-align: middle;
    line-height: 1.3;
}

/* Column widths: the label, three quiet columns, and a wider Eutropy. */
.comparison-table tr > :first-child {
    width: 42%;
    padding-left: 3.085cqw;
    padding-right: 1.401cqw;
    text-align: left;
}

.comparison-table tr > .comparison-eutropy {
    width: 16%;
}

.comparison-table thead th {
    font-family: var(--font-heading);
    font-weight: 500;
    font-size: 2.051cqw;
    color: rgba(15, 38, 30, 0.72);
}

/* All-caps label: Outfit Light, as the guide asks. */
.comparison-table thead th:first-child {
    font-weight: 300;
    text-transform: uppercase;
    letter-spacing: 0.1em;
    color: var(--eutropy-vert-profond);
}

.comparison-table tbody th {
    font-weight: 400;
    font-size: 2.051cqw;
}

.comparison-table tbody tr:last-child > * {
    border-bottom: 0;
}

/* ---- The Eutropy column ------------------------------------------------ */
.comparison-table .comparison-eutropy {
    position: relative;
    background: var(--eutropy-noir-vert);
    color: var(--eutropy-blanc-vert);
    border-bottom-color: rgba(232, 239, 236, 0.12);
}

.comparison-table thead .comparison-eutropy {
    font-weight: 700;
    font-size: 2.524cqw;
    color: #ffffff;
}

/* Rises above and below the card. */
.comparison-table thead .comparison-eutropy::before,
.comparison-table tbody tr:last-child .comparison-eutropy::after {
    content: "";
    position: absolute;
    left: 0;
    right: 0;
    height: var(--cap);
    background: var(--eutropy-noir-vert);
}

.comparison-table thead .comparison-eutropy::before {
    bottom: 100%;
    border-radius: 1.682cqw 1.682cqw 0 0;
}

.comparison-table tbody tr:last-child .comparison-eutropy::after {
    top: 100%;
    border-radius: 0 0 1.682cqw 1.682cqw;
}

.comparison-glyph {
    display: block;
    width: 4.206cqw;
    height: auto;
    margin: 0 auto 0.3em;
}

/* ---- Marks ------------------------------------------------------------- */
.comparison-mark {
    display: inline-block;
    width: 3.365cqw;
    height: 3.365cqw;
    border-radius: 50%;
    vertical-align: middle;
    background-position: center;
    background-repeat: no-repeat;
    background-size: 62%;
}

.comparison-mark--yes {
    background-color: rgba(54, 142, 117, 0.14);
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='none' stroke='%23368e75' stroke-width='3' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M4 10.5 8.2 15 16 5.5'/%3E%3C/svg%3E");
}

.comparison-mark--partly {
    background-color: rgba(249, 154, 29, 0.16);
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='none' stroke='%23f99a1d' stroke-width='3' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M5 10h10'/%3E%3C/svg%3E");
}

.comparison-mark--no {
    background-color: rgba(249, 68, 29, 0.11);
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='none' stroke='%23f9441d' stroke-width='3' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M5.5 5.5l9 9M14.5 5.5l-9 9'/%3E%3C/svg%3E");
}

.comparison-eutropy .comparison-mark--yes {
    width: 3.925cqw;
    height: 3.925cqw;
    background-color: var(--eutropy-accent);
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='none' stroke='%23050c0a' stroke-width='3.2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M4 10.5 8.2 15 16 5.5'/%3E%3C/svg%3E");
}

/* ---- Legend ------------------------------------------------------------ */
.comparison-legend {
    display: flex;
    flex-wrap: wrap;
    gap: 0.631cqw 2.103cqw;
    margin: 1.962cqw 0 0;
    padding: 0;
    list-style: none;
}

.comparison-legend li {
    display: flex;
    align-items: center;
    gap: 0.736cqw;
    font-size: 1.962cqw;
    color: var(--eutropy-vert-profond);
}

.comparison-legend .comparison-mark {
    width: 1.45em;
    height: 1.45em;
}

/* Stacked: both parts take the same side margins as the .container above them,
   10% on tablets and 15px on phones. */
@media (max-width: 991px) {
    .product-feature--comparison {
        margin-top: 64px;
    }

    .product-feature--comparison .product-feature-text {
        padding: 0 10% 12px;
    }

    .product-feature--comparison .product-feature-visual {
        padding: 0 10%;
    }
}

@media (max-width: 700px) {
    .product-feature--comparison .product-feature-text {
        padding: 0 15px 12px;
    }

    .product-feature--comparison .product-feature-visual {
        padding: 0 15px;
    }
}

/* ===================================================================
   Product section: the three integration steps
   -------------------------------------------------------------------
   Side by side, split by thin vertical lines, with the step numbers large
   in Vert moyen. The list is a real <ol>, so screen readers announce the
   numbers; the large ones are drawn for the eye only.
   =================================================================== */
.integration-steps {
    display: grid;
    grid-template-columns: repeat(3, minmax(0, 1fr));
    margin: clamp(28px, 2.5vw, 96px) 0 0;
    padding: 0;
    list-style: none;
}

.integration-step {
    padding: 0 clamp(20px, 2.5vw, 96px);
    border-left: 1.5px solid rgba(54, 142, 117, 0.45);
}

.integration-step:first-child {
    padding-left: 0;
    border-left: 0;
}

.integration-step:last-child {
    padding-right: 0;
}

/* !important: a sitewide rule sets every <span> to Inter. */
.integration-number {
    display: block;
    font-family: var(--font-heading) !important;
    font-weight: 500;
    font-size: clamp(48px, 4.444vw, 170px);
    line-height: 1;
    color: var(--eutropy-vert-moyen);
    margin-bottom: 0.25em;
}

.integration-step p {
    margin: 0;
    font-size: clamp(16px, 1.25vw, 48px);
    line-height: 1.5;
    color: var(--eutropy-vert-profond);
}

/* On computer screens the steps descend like a staircase, each one further right
   and lower than the last. */
@media (min-width: 992px) {
    .integration-steps {
        --step-drop: clamp(36px, 3.472vw, 134px);
        align-items: start;
    }

    .integration-step:nth-child(2) {
        margin-top: var(--step-drop);
    }

    .integration-step:nth-child(3) {
        margin-top: calc(var(--step-drop) * 2);
    }
}

/* Too narrow for three columns of reading text, so the steps stack here, with
   the separators turning horizontal. */
@media (max-width: 767px) {
    .integration-steps {
        grid-template-columns: minmax(0, 1fr);
    }

    .integration-step,
    .integration-step:first-child,
    .integration-step:last-child {
        padding: 22px 0;
        border-left: 0;
        border-top: 1.5px solid rgba(54, 142, 117, 0.45);
    }

    .integration-step:first-child {
        padding-top: 0;
        border-top: 0;
    }

    .integration-step:last-child {
        padding-bottom: 0;
    }
}

/* The steps rise one after the other: js/integration-steps.js adds these classes.
   Each delay is shorter than the rise, so the movement carries from one to the next.
   The transition belongs to the risen state only, so the hiding itself is instant. */
.integration-steps--reveal .integration-step {
    opacity: 0;
    transform: translateY(clamp(28px, 2.5vw, 96px));
}

.integration-steps--reveal .integration-step.is-risen {
    opacity: 1;
    transform: none;
    transition: opacity 0.7s ease-out, transform 0.7s cubic-bezier(0.22, 1, 0.36, 1);
}

.integration-steps--reveal .integration-step.is-risen:nth-child(2) {
    transition-delay: 0.5s;
}

.integration-steps--reveal .integration-step.is-risen:nth-child(3) {
    transition-delay: 1s;
}

/* Stacked, each step rises on its own as it reaches the screen. */
@media (max-width: 767px) {
    .integration-steps--reveal .integration-step.is-risen:nth-child(n) {
        transition-delay: 0s;
    }
}

@media print {
    .integration-steps--reveal .integration-step {
        opacity: 1;
        transform: none;
    }
}

/* The vision text, in three steps: the problem, the conviction, the ambition.
   Each is a labelled, left-aligned paragraph with a green line down its left
   side. The column is centred under the title, with a reading width of 44em
   plus the line and its gap. */
.vision-steps {
    --vision-gap: clamp(18px, 1.667vw, 64px);
    --vision-line-width: clamp(2px, 0.208vw, 8px);
    --vision-line: var(--vision-line-width) solid var(--eutropy-vert-moyen);
    display: flex;
    flex-direction: column;
    gap: clamp(36px, 3.333vw, 128px);
    font-size: clamp(18px, 1.406vw, 54px);
    max-width: calc(44em + var(--vision-gap) + var(--vision-line-width));
    margin: 0 auto;
}

.vision-step {
    width: 100%;
    box-sizing: border-box;
    padding-left: var(--vision-gap);
    border-left: var(--vision-line);
    text-align: left;
}

/* Small all-caps label, Outfit Light, as the chart sets for H6 and below.
   !important: main.css styles the section's headings. */
.vision-label {
    font-family: var(--font-heading) !important;
    font-weight: 300 !important;
    font-size: 0.8em !important;
    line-height: 1.2 !important;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: var(--eutropy-vert-moyen) !important;
    margin: 0 0 0.75em !important;
}

.vision-step .vision-text {
    max-width: none;
    margin: 0;
    text-align: inherit;
}

/* ===================================================================
   Header: a slightly thinner bar once the page scrolls
   -------------------------------------------------------------------
   js/header-theme.js sets .nav-compact. The logo and the menu keep their size:
   only the space above and below the logo shrinks, which is what sets the
   height of the bar. That space then sits under the brand guide's protection
   zone (0.29 x logo width), a deliberate choice for the scrolled state. The bar
   is fixed, so the page underneath does not move.
   =================================================================== */
#navigation .navbar-brand-container .navbar-brand {
    transition: margin 0.25s ease;
}

#navigation.nav-compact .navbar-brand-container .navbar-brand {
    margin-top: var(--logo-compact-clear-space) !important;
    margin-bottom: var(--logo-compact-clear-space) !important;
}

@media (max-width: 768px) {
    #navigation.nav-compact .navbar-brand-container .navbar-brand {
        margin-top: calc(var(--logo-clear-space-mobile) * 0.78) !important;
        margin-bottom: calc(var(--logo-clear-space-mobile) * 0.78) !important;
    }
}

#navigation.nav-measuring .navbar-brand-container .navbar-brand {
    transition: none;
}

@media (prefers-reduced-motion: reduce) {
    #navigation .navbar-brand-container .navbar-brand {
        transition: none;
    }
}

/* ===================================================================
   Phone header at the top of the page
   -------------------------------------------------------------------
   main.css gives the phone header (768px and under) a dark background, a
   green bottom line and a shadow at all times, so a line split the header
   from the hero before anything had moved. On wider screens the bar stays
   clear over the hero until the page scrolls. Do the same here: nothing
   until .scrolled. The line keeps its width and only turns transparent, so
   the bar does not change height when it appears.
   Once scrolled, the bar takes the wider screens' values (main.css
   #navigation.scrolled): 92% near-black with the content behind it blurred,
   instead of main.css's phone-only 95% black with no blur.
   =================================================================== */
@media (max-width: 768px) {
    #navigation:not(.scrolled):not(.nav-light) {
        background: none !important;
        box-shadow: none !important;
        border-bottom-color: transparent !important;
        backdrop-filter: none !important;
        -webkit-backdrop-filter: none !important;
    }

    #navigation.scrolled:not(.nav-light),
    #navigation:not(.nav-light):has(.navbar-collapse.in) {
        background: rgba(10, 10, 10, 0.92) !important;
        box-shadow: 0 4px 24px rgba(0, 0, 0, 0.18) !important;
        border-bottom: 1.5px solid rgba(77, 205, 172, 0.18) !important;
        backdrop-filter: blur(10px) !important;
        -webkit-backdrop-filter: blur(10px) !important;
    }
}

/* ===================================================================
   Hero: text on the left, one gear on the right
   -------------------------------------------------------------------
   The copy is left-aligned on the page's 10% gutter, with the gear drawn
   on the right by js/landing-gears.js, which keeps it clear of the text.
   =================================================================== */
#home .caption-content {
    text-align: left !important;
}

#home .caption-content .hero-copy {
    align-items: flex-start;
}

#home .caption-content .hero-title {
    margin-left: 0;
    margin-right: 0;
}

/* The indent only corrected the centring of the letterspaced line. */
#home .caption-content .hero-kicker {
    text-indent: 0 !important;
}

@media (min-width: 992px) {
    #home .caption-content .hero-headline {
        font-size: clamp(44px, 4.4vw, 114px) !important;
    }
}

@media (min-width: 992px) and (max-height: 900px) {
    #home .caption-content .hero-headline {
        font-size: clamp(40px, 4vw, 92px) !important;
    }
}

/* Upright screens, from phones to a 13-inch iPad held upright: the copy sits
   in the upper part of the screen and the gear goes below it (see
   js/landing-gears.js). Below 992px the headline size is set in
   light-theme.css, the largest that keeps it on its lines. */
@media (orientation: portrait) {
    #home {
        align-items: flex-start;
        padding-top: calc(var(--nav-offset) + 9vh) !important;
    }
}

/* Below 992px the copy starts where the logo starts, and ends as far from
   the right edge. The header's container is padded 10% down to 701px and
   15px below that, and on phones (768px and under) the logo adds its
   protection zone on top. .caption-content is a size container so the
   headline can be sized against this column (see light-theme.css). */
@media (max-width: 991px) {
    #home .caption-content {
        padding: 0 10% !important;
        container-type: inline-size;
    }

    #home .caption-content .hero-copy {
        width: 100%;
        max-width: none !important;
        margin: 0 !important;
    }
}

@media (max-width: 768px) {
    #home .caption-content {
        padding: 0 calc(10% + var(--logo-clear-space-mobile)) !important;
    }
}

@media (max-width: 700px) {
    #home .caption-content {
        padding: 0 calc(15px + var(--logo-clear-space-mobile)) !important;
    }
}

/* main.css centres the phone button at 90% of the column. With the text
   left-aligned it would start inset from it, so it takes the full column. */
@media (max-width: 768px) {
    #home #demo-scroll-btn {
        margin-left: 0 !important;
        margin-right: 0 !important;
        max-width: 100% !important;
    }
}

/* In a window wider than tall the gear sits beside the text, so the button
   keeps its own width there instead of running across that room. */
@media (max-width: 768px) and (orientation: landscape) and (min-height: 501px) {
    #home #demo-scroll-btn {
        width: auto !important;
    }
}

/* The content column deliberately has NO cap.

   It used to be capped (1560px, later a shallow ramp), on the reasoning
   that an uncapped 10% gutter would run ~80 characters per line at 2560px.
   That was true only while the type was a fixed size: at 2560px the cap
   left the column at 58% of the screen against 80% on a laptop, and since
   the header lives in this column too, that single rule was the biggest
   reason the page still looked shrunken on a large monitor - the reason
   200% browser zoom "fixed" it, since zoom drops the viewport back under
   the cap.

   Now that the type scales at the same rate as the viewport, the measure
   and the type grow together and the characters-per-line stays constant at
   the 1280px value, so the cap no longer buys anything. Leaving .container
   on its plain 10% gutter keeps the layout proportional at every width -
   and keeps the navbar, sections and footer sharing one set of edges. */

/* main.css has a leftover rule from the original template's old "About" bio
   layout: `#about { height: 570px !important; }`. We reused the #about id
   for the new 3-card pillars section, and on mobile those cards stack to
   ~900px tall - far more than that old fixed cap. Because a later legacy
   rule also forces `overflow: visible !important` on #about at mobile
   widths, the extra content isn't clipped, it spills straight out the
   bottom and visually overlaps whatever section comes next -
   this is the "cards flying" bug. Let the section size to its real content
   instead of an unrelated old fixed height. */
#about {
    height: auto !important;
}

/* Reusable card grid used by Pillars, Product, Integration, Realizations.

   Below 992px the column count is intrinsic: auto-fit packs in as many
   columns of at least --card-min as fit, which is the right behaviour while
   the type is a fixed size - the cards reflow from 1 up to 2 as the phone
   turns into a tablet. Each section keeps the minimum it used to carry as an
   inline style, so the sub-992px layout is byte-for-byte what it was.

   At >=992px the count is PINNED instead (see the large-screen block above).
   auto-fit is actively wrong up there: it holds columns at their minimum and
   adds more of them as the screen grows, while the type scales with vw. The
   two then move in opposite directions - measured on #product, a 1280px
   laptop gave 3 columns of 317px at 14px type (~33 characters per line) and a
   2560px monitor gave 6 columns of 314px at 28px type (~15 characters per
   line, cards 1022px tall). Identical column width, double the type. Pinning
   the count lets the columns widen with the viewport at the same rate as the
   type, so the measure stays constant - the same reasoning that took the cap
   off .container. */
.card-grid {
    display: grid;
    /* 280px, not the 240px #product used to carry inline. At 240px the same
       too-many-narrow-columns problem showed up one tier down: at 991px
       #product still packed 3 columns of 240px at 14px type - 21 characters
       per line, as cramped as the desktop bug this replaced - while #about
       and the integration grid had already dropped to 2 across on their larger
       minimums. 280px puts all three on 2 columns from 992px down to the
       phone, so the tablet tier has one rhythm instead of three. */
    --card-min: 280px;
    grid-template-columns: repeat(auto-fit, minmax(var(--card-min), 1fr));
    gap: 30px;
    margin-top: 40px;
}

.eutropy-card {
    background: rgba(77, 205, 172, 0.06);
    border: 1px solid rgba(77, 205, 172, 0.25);
    border-radius: 14px;
    padding: 30px;
    text-align: left;
}

/* Internal spacing in em rather than px, so it tracks each element's own type
   size once that starts scaling at >=992px instead of staying pinned at a
   laptop value. These are the exact px values they replace at today's sizes
   (16/20, 12/24, 14/12), so nothing moves below the breakpoint. */
/* The icon sits in a FIXED-height row, and the margin below it is fixed too.
   Both used to follow the icon's own font-size, and the three "how it works"
   cards do not share one: the first uses an inline SVG at 3.2rem while the
   other two use Font Awesome at 2rem. Measured, that pushed the first card's
   title 30px below the other two - the three headings were not on one line.
   Sizing the ROW rather than the glyph aligns them whatever icon a card
   carries. (Any box that needs its own icon size overrides this and
   is unaffected.) */
.eutropy-card .card-icon {
    color: var(--eutropy-accent);
    font-size: 2rem;
    display: flex;
    align-items: center;
    height: clamp(32px, 2.5vw, 96px);
    margin-bottom: clamp(16px, 1.25vw, 48px);
}

/* The one hand-drawn inline SVG among otherwise Font Awesome glyphs. An SVG
   drawn to its viewBox at width:1em reads optically smaller than an FA glyph
   at the same font-size, so it carried an inline font-size:3.2rem (32px, 1.6x
   the 20px around it) to compensate. Inline styles can't be scaled by the
   large-screen block below - it stayed at 32px while the FA icons grew to
   40px, inverting the correction it exists to make - so it moves to a class
   that the breakpoint can pick up. Same 32px here. */
.eutropy-card .card-icon--svg {
    font-size: 3.2rem;
}

.eutropy-card h3, .eutropy-card h4 {
    color: var(--eutropy-accent);
    margin: 0 0 0.5em 0;
}

.eutropy-card p {
    color: var(--eutropy-vert-clair);
    line-height: 1.6;
    margin: 0;
}

.eutropy-card .card-tag {
    display: inline-block;
    background: rgba(77, 205, 172, 0.15);
    color: var(--eutropy-accent);
    font-size: 12px;
    font-weight: 600;
    letter-spacing: 1px;
    text-transform: uppercase;
    padding: 0.333em 0.833em;
    border-radius: 20px;
    margin-bottom: 1.167em;
}

/* ===================================================================
   Large-screen card grid and card chrome
   -------------------------------------------------------------------
   Placed here, after the base rules above, on purpose: a media query
   contributes nothing to specificity, so `.card-grid` inside one does
   NOT beat a plain `.card-grid` that appears later in the file. An
   earlier version of this sat up in the large-screen typography block
   and silently lost every declaration that the base rules also set
   (columns, padding, radius, icon and tag size) - the only one that
   appeared to work was the h3 size, and only because the base rule
   happens not to declare font-size.

   Pinning the column count is the fix for the real bug: auto-fit holds
   columns at their minimum and adds more of them as the screen grows,
   while the type scales with vw, so the two move in opposite
   directions. Measured on #product before this: 1280px gave 3 columns
   of 317px at 14px type (~33 characters per line), 2560px gave 6
   columns of 314px at 28px type (~15 characters per line, cards 1022px
   tall) - the same column width carrying double the type.

   Three across is what #about and the integration grid already resolved to on
   their own (3 cards each, so auto-fit capped them there); only
   #product broke, because it has 6. Driving all three from one rule
   means a 4th card added to any of them can't quietly bring the bug
   back. minmax(0, 1fr) rather than plain 1fr: a 1fr track floors at
   min-content, so a single long unbreakable word could otherwise push
   its column past its share and overflow the row.

   The single-card demo grid keeps its inline grid-template-columns,
   which outranks this - that one is meant to be one column.
   =================================================================== */
@media (min-width: 992px) {
    .card-grid {
        grid-template-columns: repeat(var(--card-cols, 3), minmax(0, 1fr));
        gap: clamp(30px, 2.344vw, 90px);
    }

    /* Same floor/ceiling convention as the typography block: the floor
       reproduces today's 1280px value exactly, the ceiling is 3x it.
       Without this the chrome stayed at laptop pixel sizes while the body
       copy scaled - at 2560px the h3 sat at 24px against 28px body text,
       so the heading rendered SMALLER than the paragraph it introduces.

       Padding ramps more gently than the type (1.7vw, not the 2.344vw its
       floor implies): it comes off the measure twice per card, and at the
       full rate it clawed back a chunk of the width that pinning the
       columns had just recovered. */
    .eutropy-card {
        padding: clamp(30px, 1.7vw, 65px);
        border-radius: clamp(14px, 1.094vw, 42px);
    }

    .eutropy-card .card-icon {
        font-size: clamp(20px, 1.563vw, 60px);
    }

    /* 2.5vw is exactly 1.6x the 1.563vw above, so the optical correction
       described at .card-icon--svg holds at every width instead of only at
       1280px. */
    .eutropy-card .card-icon--svg {
        font-size: clamp(32px, 2.5vw, 96px);
    }

    .eutropy-card h3,
    .eutropy-card h4 {
        font-size: clamp(24px, 1.875vw, 72px);
    }

    .eutropy-card .card-tag {
        font-size: clamp(12px, 0.938vw, 36px);
    }
}

/* Lock to 3 columns on desktop and center a lone leftover card in the last
   row (e.g. 7 cards = two full rows of 3 + 1), instead of stranding it on
   the left under an otherwise empty row. */

/* Demo section: persuasive two-column layout instead of a lonely centered form */
.demo-section {
    background: var(--eutropy-noir-vert) !important;
    padding: 80px 0 !important;
}

/* The demo links go to the top of the section, so the intro sentence shows.
   This keeps older links to #demo-form clear of the fixed header. */
#demo-form {
    scroll-margin-top: 100px;
}

.demo-alt-contact {
    text-align: center;
    font-size: 13px;
    /* main.css sets `p { line-height: 25px }`, a pixel value - this one wrapped
       to three overlapping lines inside the form card at 2560px. 1.923 x 13px
       reproduces the current 25px exactly. */
    line-height: 1.923;
    color: var(--eutropy-vert-clair);
    margin: 14px 0 0;
}

.demo-alt-contact a {
    color: var(--eutropy-accent);
    font-weight: 600;
    text-decoration: none;
}

.demo-alt-contact a:hover {
    text-decoration: underline;
}

/* One sentence above the form, which stands alone in the centre of the page. */
.demo-intro {
    text-align: center;
    font-size: clamp(18px, 1.406vw, 54px);
    line-height: 1.6;
    max-width: 56em;
    margin: 0 auto clamp(28px, 2.5vw, 96px);
    /* Fills each line, but never leaves a single word alone on the last one. */
    text-wrap: pretty;
}

.demo-form-card {
    background: rgba(77, 205, 172, 0.06);
    border: 1px solid rgba(77, 205, 172, 0.25);
    border-radius: 16px;
    padding: 36px;
    max-width: clamp(760px, 59.4vw, 2280px);
    margin: 0 auto;
}

/* The form already gets its card look from .demo-form-card above; strip the
   legacy .classy-contact-form panel styling so it stops nesting a second,
   visually redundant card inside it. */
.demo-form-card .classy-contact-form {
    background: none !important;
    border: none !important;
    box-shadow: none !important;
    padding: 0 !important;
    margin: 0 !important;
    max-width: 100% !important;
    width: 100% !important;
}

/* "(optional)" hint next to the Message label: same size as the label but
   muted, so required vs. optional fields are visually distinguishable. */
.form-optional {
    color: var(--eutropy-vert-moyen);
    font-weight: 400;
    text-transform: none;
    letter-spacing: normal;
}

/* Message is optional and usually short — shrink its default box so it
   doesn't dominate the card with empty space; still resizable if needed. */
.demo-form-card textarea.form-control {
    min-height: 64px !important;
    padding-top: 12px !important;
    padding-bottom: 12px !important;
}

@media (max-width: 900px) {
    .demo-form-card {
        padding: 24px;
    }
}

/* Minimal fix for horizontal scrolling in Chrome/Edge */
/* Only targets the specific elements causing the issue */

/* Fix home slider caption content - the main culprit */
#home .caption-content {
    width: 100% !important;
    max-width: 100% !important;
    box-sizing: border-box !important;
}

/* Fix stars effect overflow */
.stars {
    max-width: 100vw !important;
    overflow: hidden !important;
}

/* Fix contact form center */
.contact-form-center {
    width: 100% !important;
    max-width: 100% !important;
    box-sizing: border-box !important;
}

/* Beautiful About Dropdown Menu Styling */
.navbar-inverse .dropdown-menu {
    background: rgba(0, 0, 0, 0.95) !important;
    border: 2px solid #4dcdac !important;
    border-radius: 12px !important;
    box-shadow: 0 8px 32px rgba(77, 205, 172, 0.3) !important;
    backdrop-filter: blur(15px) !important;
    -webkit-backdrop-filter: blur(15px) !important;
    padding: 8px 0 !important;
    margin-top: 8px !important;
    min-width: 200px !important;
    animation: dropdownFadeIn 0.3s ease-out !important;
}

@keyframes dropdownFadeIn {
    from {
        opacity: 0;
        transform: translateY(-10px) scale(0.95);
    }
    to {
        opacity: 1;
        transform: translateY(0) scale(1);
    }
}

.navbar-inverse .dropdown-menu > li > a {
    color: #ffffff !important;
    padding: 12px 20px !important;
    font-family: var(--font-heading) !important;
    font-weight: 500 !important;
    font-size: 16px !important;
    text-decoration: none !important;
    display: block !important;
    transition: all 0.3s ease !important;
    border-radius: 8px !important;
    margin: 4px 8px !important;
    position: relative !important;
    overflow: hidden !important;
}

.navbar-inverse .dropdown-menu > li > a:before {
    content: '' !important;
    position: absolute !important;
    top: 0 !important;
    left: -100% !important;
    width: 100% !important;
    height: 100% !important;
    background: linear-gradient(90deg, transparent, rgba(77, 205, 172, 0.2), transparent) !important;
    transition: left 0.5s ease !important;
}

.navbar-inverse .dropdown-menu > li > a:hover:before {
    left: 100% !important;
}

.navbar-inverse .dropdown-menu > li > a:hover,
.navbar-inverse .dropdown-menu > li > a:focus {
    background: rgba(77, 205, 172, 0.15) !important;
    color: #4dcdac !important;
    transform: translateX(5px) !important;
    box-shadow: 0 4px 12px rgba(77, 205, 172, 0.2) !important;
}

.navbar-inverse .dropdown-menu > li > a:active {
    background: rgba(77, 205, 172, 0.25) !important;
    transform: translateX(3px) scale(0.98) !important;
}

/* Dropdown arrow styling */
.navbar-inverse .dropdown-toggle .caret {
    border-top-color: #ffffff !important;
    border-bottom-color: #ffffff !important;
    transition: all 0.3s ease !important;
}

.navbar-inverse .dropdown:hover .caret {
    border-top-color: #4dcdac !important;
    border-bottom-color: #4dcdac !important;
    transform: rotate(180deg) !important;
}

/* Mobile dropdown styling */
@media (max-width: 991px) {
    .navbar-inverse .dropdown-menu {
        position: static !important;
        float: none !important;
        width: 100% !important;
        margin-top: 0 !important;
        box-shadow: none !important;
        border: 1px solid rgba(77, 205, 172, 0.3) !important;
        border-radius: 8px !important;
        background: rgba(77, 205, 172, 0.1) !important;
        margin: 8px 0 !important;
    }
    
    .navbar-inverse .dropdown-menu > li > a {
        padding: 15px 20px !important;
        font-size: 15px !important;
        margin: 2px 0 !important;
        border-radius: 6px !important;
    }
    
    .navbar-inverse .dropdown-menu > li > a:hover {
        transform: translateX(0) !important;
        background: rgba(77, 205, 172, 0.2) !important;
    }
}

/* Language button with flags styling */
.navbar-inverse .navbar-nav > li > a.language-btn {
    background: transparent !important;
    border: none !important;
    border-radius: 0 !important;
    margin-left: 0 !important;
    padding: 15px 20px !important;
    font-size: 16px !important;
    position: relative !important;
    vertical-align: middle !important;
    line-height: 1.42857143 !important;
}

.navbar-inverse .navbar-nav > li > a.language-btn img {
    /* Scales with the rest of the header on large screens; the clamp floor
       reproduces the previous fixed 20x15 exactly, and height follows width
       so the flag keeps its 4:3 ratio instead of stretching. Declared here
       rather than in the large-screen block above because this selector is
       the most specific one for the flag - a separate rule there would lose
       the cascade to it no matter the source order. */
    width: clamp(20px, 1.5625vw, 60px) !important;
    height: auto !important;
    aspect-ratio: 4 / 3;
    border-radius: 2px !important;
    vertical-align: middle !important;
}

.navbar-inverse .navbar-nav > li > a.language-btn:hover {
    background: transparent !important;
    color: #4dcdac !important;
}

/* Prevent video interaction on mobile browsers */
.video-background {
    pointer-events: none !important;
    -webkit-user-select: none !important;
    -moz-user-select: none !important;
    -ms-user-select: none !important;
    user-select: none !important;
}

.video-background::-webkit-media-controls {
    display: none !important;
}

.video-background::-webkit-media-controls-panel {
    display: none !important;
}

.video-background::-webkit-media-controls-play-button {
    display: none !important;
}

.video-background::-webkit-media-controls-start-playback-button {
    display: none !important;
}

/* Mobile Performance Optimizations */
@media (max-width: 768px) {
    /* Reduce animations on mobile for better performance */
    .wow {
        animation-duration: 0.6s !important;
    }
    
    /* Optimize video for mobile */
    .video-background {
        transform: scale(1.1) !important;
        filter: brightness(0.7) !important;
    }
    
    /* Reduce complex shadows on mobile */
    .navbar-inverse .dropdown-menu {
        box-shadow: 0 4px 16px rgba(77, 205, 172, 0.2) !important;
    }
    
    /* Optimize partner logos scrolling */
    .partners-logos-scroll {
        animation-duration: 20s !important;
    }
    
    /* Reduce backdrop blur on mobile for performance */
    .navbar-inverse .dropdown-menu {
        backdrop-filter: none !important;
        -webkit-backdrop-filter: none !important;
        background: rgba(0, 0, 0, 0.9) !important;
    }
}

/* Supporters: just the logos, no card and no wrapper tile - the boxed look
   read as disconnected from a plain "trusted by" logo strip, and the tile
   divs weren't doing anything a flex row on the images themselves can't do.
   Logos keep their original colors (no grayscale/invert), with a brightness/
   contrast lift so darker marks (UTC, Fondation UTC) stay legible without a
   card behind them for contrast. A short tagline below explains what the
   logos mean instead of a section heading above them. */
.partners-grid {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: center;
    gap: 44px 56px;
    max-width: 1000px;
    margin: 0 auto;
}

.partners-grid img {
    max-height: 46px;
    width: auto;
    object-fit: contain;
    filter: brightness(1.35) contrast(1.05);
    opacity: 0.88;
    transition: opacity 0.25s ease, transform 0.25s ease, filter 0.25s ease;
}

.partners-grid img:hover {
    opacity: 1;
    filter: brightness(1.45) contrast(1.1);
    transform: scale(1.06);
}

.supporters-tagline {
    text-align: center;
    font-size: 15px;
    /* Same inherited 25px pixel leading; 1.667 x 15px is that same 25px. */
    line-height: 1.667;
    color: var(--eutropy-vert-clair);
    margin: 28px auto 0;
}

/* ===================================================================
   Large-screen section chrome (Benefits, Team, and the three strays)
   -------------------------------------------------------------------
   Deliberately at the END of the file, after every base rule it
   overrides. A media query adds nothing to specificity, so a rule
   inside one loses to an equally specific plain rule that comes later
   in the source - which is exactly how the Benefits and Team sections
   ended up half-scaled. An audit comparing computed font-size at
   1280px against 2560px found 15 text styles frozen at their laptop
   size while the rest of the page doubled. In the Team section that
   produced the visible split the report was about: the bios ran at
   28px (they scale) directly above a 14px role label and an 18px
   mission line (they don't), and next door the Benefits cards sat at
   a flat 16px under a 44px heading.

   Same convention as the typography block up top: the floor is exactly
   today's 1280px value, so nothing moves on a laptop, and the ceiling
   is 3x the floor.

   Still frozen after this block, deliberately left alone: the demo form
   internals (labels, inputs, buttons).
   The form needs its control padding and heights scaled in step with
   the text or the fields overflow, which is a bigger change than this.
   =================================================================== */
@media (min-width: 992px) {

    .supporters-tagline {
        font-size: clamp(15px, 1.172vw, 45px);
    }

    /* ---- #supporters (partner logos) ----------------------------------- */
    .partners-grid {
        gap: clamp(44px, 3.438vw, 132px) clamp(56px, 4.375vw, 168px);
        max-width: clamp(1000px, 78.13vw, 3000px);
    }

    /* The logos are the content of this section, and a flat 46px ceiling left
       them as a row of stamps on a large monitor. */
    .partners-grid img {
        max-height: clamp(46px, 3.594vw, 138px);
    }

    /* ---- Demo section: the form itself --------------------------------- */
    /* These selectors mirror main.css's own so they win on source order -
       custom-styles.css is the later sheet. The controls are the reason this
       section was left out of the previous pass: scaling label and input text
       without scaling padding, gaps and the textarea's min-height in the same
       step makes the fields overflow their own boxes. All of it moves
       together here. Floors reproduce main.css's values exactly (its rules
       are in rem against this project's 10px root, so 1.15rem = 11.5px). */
    .demo-form-card {
        padding: clamp(36px, 2.813vw, 108px);
        border-radius: clamp(16px, 1.25vw, 48px);
    }

    .contact-grid-form .contact-grid-fields {
        gap: clamp(18px, 1.406vw, 54px) clamp(32px, 2.5vw, 96px);
        margin-bottom: clamp(18px, 1.406vw, 54px);
    }

    .contact-grid-form .form-group label {
        font-size: clamp(11.5px, 0.898vw, 34.5px);
        margin-bottom: clamp(8px, 0.625vw, 24px);
    }

    .contact-grid-form .form-group input.form-control,
    .contact-grid-form textarea.form-control {
        font-size: clamp(11.8px, 0.922vw, 35.4px);
        padding: clamp(18px, 1.406vw, 54px) clamp(10px, 0.781vw, 30px);
    }

    /* The base rule for this one carries !important, so the override has to
       as well. max-height is raised in step or a scaled-up textarea would be
       capped below its own min-height. */
    .demo-form-card textarea.form-control {
        min-height: clamp(64px, 5vw, 192px) !important;
        max-height: clamp(220px, 17.19vw, 660px) !important;
        padding-top: clamp(12px, 0.938vw, 36px) !important;
        padding-bottom: clamp(12px, 0.938vw, 36px) !important;
    }

    .demo-alt-contact {
        font-size: clamp(13px, 1.016vw, 39px);
        margin-top: 1.077em;
    }
}

/* Hero "Demander une démo" button: the same colours as the demo form's button.
   main.css changes color/gradient/shadow on hover and at several breakpoints;
   an ID selector beats those class rules. Plain :focus keeps the normal colours:
   a clicked link stays focused, and would otherwise look hovered when the visitor
   comes back to the top of the page. */
#demo-scroll-btn,
#demo-scroll-btn:focus,
#demo-scroll-btn:active,
#demo-scroll-btn:visited {
    background: var(--eutropy-vert-moyen) !important;
    color: #ffffff !important;
    box-shadow: none !important;
    transform: none !important;
    text-decoration: none !important;
}

#demo-scroll-btn:hover,
#demo-scroll-btn:focus-visible {
    background: var(--eutropy-accent) !important;
    color: var(--eutropy-noir-vert) !important;
    box-shadow: none !important;
    transform: none !important;
    text-decoration: none !important;
}

/* "Book a Demo" / "Réserver une démo" submit button in the demo form: same
   fix as above, since clicking it keeps :focus active and main.css darkens
   the background on hover/focus. */
.classy-contact-form .btn-demo,
.classy-contact-form .btn-demo:hover,
.classy-contact-form .btn-demo:focus,
.classy-contact-form .btn-demo:active,
.classy-contact-form .btn-demo:visited {
    background: #4dcdac !important;
    color: #fff !important;
    box-shadow: 0 2px 12px #4dcdac33 !important;
    transform: none !important;
    text-decoration: none !important;
}

/* Footer: glyph on the left, socials in the centre, legal line on the right.
   Vert moyen background with white text and the white glyph, the version the
   brand guide shows on a green background. */
#footer {
    background: var(--eutropy-vert-moyen) !important;
    border-top: none;
    padding: clamp(24px, 1.875vw, 72px) 0 !important;
}

/* Equal outer columns keep the socials on the true centre of the page, however
   long the legal line is. */
.footer-content {
    display: grid;
    grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr);
    align-items: center;
    gap: 20px 32px;
    max-width: 100%;
}

.footer-brand {
    display: block;
    justify-self: start;
    line-height: 0;
}

.footer-logo {
    width: clamp(44px, 3.4vw, 130px);
    height: auto;
}

/* main.css gives this a margin and a row layout from an older footer. */
.footer-content .footer-social {
    flex-direction: column;
    gap: clamp(10px, 0.781vw, 30px);
    margin: 0 !important;
}

#footer .footer-social-title {
    font-family: var(--font-heading) !important;
    font-weight: 500;
    font-size: clamp(15px, 1.172vw, 45px);
    line-height: 1.2;
    color: #ffffff;
    margin: 0;
}

.footer-social-links {
    gap: clamp(10px, 0.781vw, 30px);
}

.footer-social-link {
    background: #ffffff;
    border: none;
    color: var(--eutropy-vert-profond);
    width: clamp(34px, 2.656vw, 102px);
    height: clamp(34px, 2.656vw, 102px);
    font-size: clamp(15px, 1.172vw, 45px);
}

.footer-social-link:hover,
.footer-social-link:focus {
    background: var(--eutropy-blanc-vert);
    color: var(--eutropy-noir-vert);
    box-shadow: none;
}

#footer .footer-copyright {
    justify-self: end;
    text-align: right;
    font-family: var(--font-body);
    font-weight: 400;
    font-size: clamp(14px, 1.094vw, 42px);
    line-height: 1.5;
    color: #ffffff;
    margin: 0;
}

@media (max-width: 768px) {
    .footer-content {
        grid-template-columns: minmax(0, 1fr);
        justify-items: center;
        gap: 16px !important;
    }

    .footer-brand,
    #footer .footer-copyright {
        justify-self: center;
        text-align: center;
    }
}

/* Critical mobile optimizations */
@media (max-width: 480px) {
    /* Disable expensive animations on very small screens */
    .wow {
        animation: none !important;
    }

    /* Simplify gradients for better performance */
    .autonomous-section {
        background: rgba(77, 205, 172, 0.15) !important;
    }
}

/* Rotation fix for the hero: main.css has several old landscape media queries
   targeting `.caption-content h2` / `.caption-content p`, selectors from a
   previous hero layout. The hero markup here uses .hero-kicker/.hero-headline
   instead, so those old rules never touch it, and
   none of them change #home's own fixed `height: 100vh` + `overflow: hidden`
   (main.css). On phones like the Galaxy A51 or Pixel 7, rotating to landscape
   flips the viewport width to the long axis (~830-915px) - past every
   `max-width` mobile breakpoint above, so this file's desktop-sized hero text
   still applies - while the height collapses to ~360-420px. The result: the
   centered hero content is taller than #home's box, and the overflow (in
   particular the "Un retour sur investissement..." proof pill, last in the
   stack) gets clipped instead of the page scrolling. Keyed on max-height +
   orientation (not max-width) so the width flip on rotation can't skip it.
   Placed last so it wins the cascade over the unconditional desktop rules
   above (same selectors, same !important, later source order). */
@media (max-height: 500px) and (orientation: landscape) {
    #home {
        height: auto !important;
        min-height: 100vh !important;
        overflow: visible !important;
        padding: 90px 0 24px !important;
    }

    /* The block above put .caption-content back in flow, but its two ancestors
       from the old slider template were left absolutely positioned:
       `.sl-slider { position: absolute }` (main.css) and `.slide-caption
       { position: absolute; top: 0; height: 100% }`. With .sl-slider out of
       flow the #slider wrapper collapsed to 0 height, and because #home is a
       centering flex container that 0-height box got parked on the hero's
       vertical centre line - so the whole hero stack started halfway down the
       section and ran off the bottom (measured: text began 230px into a 393px
       viewport and overflowed 49px past #home, landing on top of the next
       section's title). Putting the chain back in normal flow lets #home size
       to its content, so the hero sits properly inside its own section and
       #about follows immediately after it. */
    #home #slider,
    #home .sl-slider {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        height: auto !important;
    }

    #home .slide-caption {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        display: block !important;
        width: 100% !important;
        height: auto !important;
        min-height: 0 !important;
    }

    #home .caption-content {
        position: relative !important;
        top: auto !important;
        left: auto !important;
        transform: none !important;
        min-height: auto !important;
        padding: 0 20px !important;
        /* Several old device-specific landscape rules in main.css (the "S20
           Ultra" family, width/height-gated) still set a stray margin-bottom
           (50-70px) on plain `.caption-content`. Their range happens to
           include Galaxy A51/Pixel 7 landscape dimensions, and since this
           block never declared margin-bottom, their !important leaked
           through and left a large empty gap before the next section.
           #home .caption-content has higher specificity than their bare
           .caption-content selector, so declaring it here (even at 0)
           reliably wins over all of them. */
        margin-bottom: 0 !important;
        /* main.css also has a much older leftover rule from the original
           slit-slider template: `.caption-content { display: table-cell;
           height: 100% !important; }`. That height resolves to a box far
           shorter than the actual stacked content (kicker/headline/subtitle/
           button/proof pill), so with overflow:visible the last elements
           just spill out below their own parent's box - visually still on
           screen, but not counted in its height, which is what left the gap
           before the next section even after the margin-bottom fix above. */
        height: auto !important;
        /* Same story for max-height: the old device-specific blocks also cap
           it (25-80vh depending on which one matches), independently of the
           height property above, so it has to be neutralized separately. */
        max-height: none !important;
    }

    #home .caption-content .hero-kicker {
        font-size: 12px !important;
        margin-bottom: 8px !important;
        /* main.css has a very old rule from the original slider template,
           `.caption-content span:first-child { margin-top: 100px; }`, meant
           for a hero copy structure that no longer exists. .hero-kicker is
           still literally the first span descendant of .caption-content
           (nested one level deeper, inside the h1), so it still matches and
           that 100px still applies - by itself enough to push the rest of
           the stack (button, proof pill) below a short landscape viewport. */
        margin-top: 0 !important;
    }

    #home .caption-content .hero-headline {
        font-size: 1.8rem !important;
        line-height: 1.15 !important;
    }

    /* The screenshots used to be laid out side by side here so a rotated
       phone did not have to scroll through two stacked panels. They are
       hidden below 992px now (see the <=991px block), and every viewport
       this query matches is narrower than that, so no rule for them is
       needed - a rotated phone gets the same text-only hero as an upright
       one. */
}

