/* ═══════════════════════════════════════════════════════════════════════════
   TYPEFACES — Geist and Geist Mono, self-hosted.

   THIS FILE IS DELIBERATELY OUTSIDE THE VITE PIPELINE, and is linked directly
   from the page (layouts/app.blade.php, and a render hook in
   DashboardPanelProvider for the panel). That looks like a step backwards from
   letting the bundler own it. It is not — it is the fix for a real failure that
   cost most of an afternoon, and the reasoning should survive the next person who
   tries to "clean this up".

   THE PROBLEM: the Vite dev server runs on :5173 while the app is served from
   :443, so ANY asset the bundler serves is cross-origin to the page. Stylesheets
   and scripts do not care — they load cross-origin without CORS. Fonts do: they
   are always fetched in CORS mode and are rejected outright unless the response
   carries Access-Control-Allow-Origin. So a bundled font works in the production
   build (same origin, hashed asset) and fails in development, or vice versa
   depending on how the url() is written.

   Every route through Vite hit some version of this:
     - `url('/fonts/…')`  -> resolves against :5173 in dev. Blocked.
     - `url('../fonts/…')` under resources/ -> Vite resolves it relative to the
       IMPORTING file, not the declaring one, so it resolved for app.css and
       silently did NOT for either Filament theme ("didn't resolve at build time"),
       shipping panel bundles pointing at nothing.
     - an `@fonts` alias fixed that, and the dev server still would not serve the
       file with a CORS header the browser accepted.

   THE FIX: serve the font CSS and the font files from the APP's own origin, from
   public/. The stylesheet is same-origin, its relative url()s resolve
   same-origin, and dev and production behave identically because neither
   involves the bundler. One plain file, no build coupling, no dev/prod skew.

   WHAT THIS COSTS: the files are not content-hashed, so a font swap needs the
   ?v= query in the <link> bumped to bust caches. That is the entire downside.

   HOW TO VERIFY, because nothing else is trustworthy: `getComputedStyle` reports
   the REQUESTED family, not the resolved one, so it says 'Geist' even when the
   face never loaded, and a screenshot of a good fallback is genuinely hard to
   tell apart. Use the CSS Font Loading API —
       [...document.fonts].map(f => [f.family, f.status])
   — where anything other than "loaded" after `await document.fonts.ready` means
   it did not load. Confirm by measuring: render a string in the webfont and again
   in a deliberately bogus family; equal widths mean you are seeing the fallback.

   WHY THESE TWO FACES: they are one matched superfamily. The mono is not a
   separate face chosen to sit near the sans — it shares the sans's skeleton, so a
   data readout and a headline read as the same voice doing different jobs. That
   matters here because CHEMDAS renders mono constantly and never as decoration:
   eyebrows, the wordmark, unit strings, CAS numbers, conversion factors, the spec
   bar's figures, and the whole Filament panel.

   They also replace a render-blocking fonts.googleapis.com stylesheet that sat
   directly in front of the LCP headline, plus a second fonts.bunny.net request
   the panel made on every authenticated page load. Nothing leaves our origin now,
   which also means no third party logs a visitor's IP before they have consented
   to anything — a question procurement reviewers do ask.

   VARIABLE FONTS: `font-weight: 100 900` declares the whole wght axis, so every
   weight the design uses (400/500/600/700/800) comes out of one request per
   family rather than five static files. 52 KB for both.

   `font-display: swap` paints immediately in the fallback and swaps on arrival —
   never a blank headline.

   THE FORMAT STRING IS `woff2`. `woff2-variations` is a dead proposal that
   current Chrome rejects, and it fails silently: the file still 200s and the page
   still renders in the fallback.

   The unicode-range is the Fontsource latin subset these files were cut to.
   Declaring it lets the browser skip the download entirely for text outside the
   range rather than fetching a font it cannot use.

   LICENCE: SIL Open Font License 1.1, full text beside these files in OFL.txt.
   The OFL requires the licence to travel with the fonts; "it's on GitHub" does
   not satisfy that. Do not delete it.
   ═══════════════════════════════════════════════════════════════════════════ */

@font-face {
    font-family: 'Geist';
    font-style: normal;
    font-weight: 100 900;
    font-display: swap;
    src: url('geist-latin-wght-normal.woff2') format('woff2');
    unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC,
        U+0304, U+0308, U+0329, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193,
        U+2212, U+2215, U+FEFF, U+FFFD;
}

@font-face {
    font-family: 'Geist Mono';
    font-style: normal;
    font-weight: 100 900;
    font-display: swap;
    src: url('geist-mono-latin-wght-normal.woff2') format('woff2');
    unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC,
        U+0304, U+0308, U+0329, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193,
        U+2212, U+2215, U+FEFF, U+FFFD;
}
