/*
 * Ariana panel skin
 * ---------------------------------------------------------------------------
 * Loaded straight from public/ via a render hook, so it needs no Vite/npm build
 * on the customer's server. Everything here is presentation only.
 */

/* ---------------------------------------------------------------------------
 * The panel's typeface: Apple's system face on Apple's machines, Inter
 * everywhere else (invariant 263).
 *
 * The stack further down names `-apple-system` / `BlinkMacSystemFont` before
 * 'Inter'. On macOS, iOS and iPadOS those keywords ARE San Francisco — the
 * face the operating system itself is set in — served by the machine, so no
 * file is distributed and no licence is needed. Every other platform does
 * not know the keywords and falls straight through to Inter, the open face
 * drawn for the same job (small UI text) with the same skeleton. Vazirmatn
 * still leads the stack for the Arabic script only, by unicode-range, on
 * every platform — a Mac does not get to set Persian in its own face.
 *
 * Inter is self-hosted, NOT loaded from Google Fonts. Two reasons, both of
 * which matter for who Ariana is for: a request to fonts.googleapis.com on
 * every admin page view sends the operator's IP to a third party, which is a
 * GDPR problem German courts have already ruled on; and on a shared host in
 * Iran or behind a corporate proxy that request is often the slowest thing
 * on the page, or simply fails, leaving the panel in fallback type.
 *
 * One variable file per subset (weights 100–900 in ~48 KB for Latin); the
 * Latin-Extended file is fetched only by a page that prints such a letter.
 * font-display: swap so the panel is readable before the font arrives.
 *
 * Licensed under the SIL Open Font License 1.1; the full text ships beside the
 * files at ariana-assets/fonts/Inter-OFL.txt, which the licence requires.
 * ------------------------------------------------------------------------- */
@font-face {
    font-family: 'Inter';
    src: url('fonts/Inter-Variable-latin.woff2') format('woff2');
    font-weight: 100 900;
    font-style: normal;
    font-display: swap;
    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+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}

@font-face {
    font-family: 'Inter';
    src: url('fonts/Inter-Variable-latin-ext.woff2') format('woff2');
    font-weight: 100 900;
    font-style: normal;
    font-display: swap;
    unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}

/* ---------------------------------------------------------------------------
 * The type scale (invariant 264).
 *
 * Apple's text styles, adapted to the web: eight sizes, three weights, four
 * line heights, one tracking value for small capitals. Every font-size,
 * font-weight, line-height and letter-spacing in the panel's stylesheets is
 * one of these — before 1.72.5 there were thirty-five sizes between .58rem
 * and 2rem, ten weights up to 800 and fourteen line heights, which is what
 * made the panel read as "almost, but not" next to macOS.
 *
 *   caption 11 · footnote 12 · sub 13 · body 14 · callout 15
 *   title3 17 · title2 22 · title1 26            (px at the default root)
 *
 * Nothing goes under 11 px: Apple's own 10 pt footnote is a print size, and
 * Persian is unreadable there. Weights are 400, 500 and 600 — macOS UI does
 * not go heavier. Line heights are for LATIN; the Persian block below
 * replaces them, because Vazirmatn is a taller face with marks above and
 * below the line and sets badly in San Francisco's leading.
 * ------------------------------------------------------------------------- */
:root {
    --ar-fs-caption:  .6875rem;
    --ar-fs-footnote: .75rem;
    --ar-fs-sub:      .8125rem;
    --ar-fs-body:     .875rem;
    --ar-fs-callout:  .9375rem;
    --ar-fs-title3:   1.0625rem;
    --ar-fs-title2:   1.375rem;
    --ar-fs-title1:   1.625rem;

    --ar-lh-tight: 1.2;    /* titles                      */
    --ar-lh-ui:    1.35;   /* labels, cells, one-liners   */
    --ar-lh-text:  1.45;   /* help text, descriptions     */
    --ar-lh-prose: 1.6;    /* the editor, chat, release notes */

    --ar-tracking-caps: .03em;   /* small capitals only */
}

:root {
    /* ---- Ariana's palette ---------------------------------------------------
     * The deep indigo-violet the panel has had from the beginning. An external
     * design-system sheet was briefly treated as authoritative here and has been
     * removed at the owner's instruction; these are the product's own values.
     *
     * This block is the brand's fixed identity. Components must NOT reach into
     * it directly - they use the mode-aware --ar-* layer below, which is the only
     * layer that knows whether the panel is light or dark.
     * -------------------------------------------------------------------- */
    --ariana-purple-900: #14102b;   /* page behind the panel   */
    --ariana-purple-850: #191436;   /* cards, sidebar          */
    --ariana-purple-800: #1e1840;   /* raised                  */
    --ariana-purple-700: #2a2158;   /* selected                */
    --ariana-purple-600: #382c74;   /* strong border           */
    --ariana-purple-line: #332a5e;  /* hairline                */
    --ariana-accent:     #7c6cff;   /* the violet              */

    /* Status colours, chosen for contrast on both a violet panel and violet
     * paper rather than taken from a framework's defaults. */
    --ariana-success: #16A34A;
    --ariana-warning: #D97706;
    --ariana-danger:  #DC2626;
    --ariana-info:    #2563EB;

    /* Radii, so components stop inventing their own. */
    --ariana-r-sm: 4px;
    --ariana-r-md: 8px;
    --ariana-r-lg: 12px;
    --ariana-r-xl: 16px;
    --ariana-r-2xl: 24px;
    --ariana-r-full: 999px;
}

/* ---------------------------------------------------------------------------
 * Semantic tokens that FLIP WITH THE MODE.
 *
 * These were being used throughout the stylesheet - var(--ar-ink),
 * var(--ar-line), var(--ar-ink-dim) - and never defined. Where a fallback was
 * given the component silently rendered in dark-mode colours on a white panel;
 * where none was given the declaration was invalid and dropped entirely.
 *
 * The palette above (--ariana-*) is the brand's fixed values. This layer is the
 * one components must use, because it is the only one that knows which mode is
 * active. A component that reaches past it for a literal hex will be unreadable
 * in one of the two modes, which is exactly how the panel ended up with white
 * text on a white background.
 *
 * Ink pairs are chosen per mode rather than shared: a single mid-tone that
 * "works on both" fails contrast on both.
 * ------------------------------------------------------------------------- */
:root {
    /* ---- Light mode: "violet paper" -----------------------------------------
     * The same violet as the dark panel, lit from the front instead of the back.
     *
     * Surfaces are violet-tinted neutrals rather than grey or white, so the
     * product reads as the same product in either mode. Ink is a deep violet
     * black, not #000, so nothing in the interface is a colour that does not
     * belong to the family.
     *
     * Every pair below was measured, not chosen by eye. The worst combination in
     * the whole palette is 4.75:1 (muted ink on the accent wash) and everything
     * else clears WCAG AA with margin; ink and dim ink clear AAA on every
     * surface. The numbers are in the table at the end of this block.
     *
     * The accent had to become mode-specific. Ariana's #7c6cff reads at only
     * 3.86:1 on white - it fails as a light-mode fill and as link text - while a
     * violet dark enough for light mode (#6B57F0 and below) fails as text on the
     * dark panel. There is no single value that serves both, so each mode gets
     * the darkest violet that still looks like Ariana.
     * --------------------------------------------------------------------- */
    --ar-canvas:   #F5F3FC;   /* page behind the cards            */
    --ar-surface:  #FFFFFF;   /* cards, panels, table body        */
    --ar-sunken:   #F0EDF9;   /* inset: code, transcripts, thead  */
    --ar-chrome:   #EFEBFA;   /* sidebar                          */
    --ar-wash:     #E4DEFB;   /* selected / active                */

    --ar-line:         #E4E0F2;
    --ar-line-strong:  #CFC8E6;

    --ar-ink:      #15102C;   /* 18.38:1 on surface  AAA */
    --ar-ink-dim:  #3D3660;   /* 11.08:1 on surface  AAA */
    --ar-ink-mute: #574F7C;   /*  7.46:1 on surface  AAA; 6.43:1 on glass over the wash's brightest point */

    --ar-accent:      #5F49E8;  /* fills: white label reads 5.83:1  */
    --ar-accent-fill:       #5F49E8;
    --ar-accent-fill-hover: #533DDC;
    --ar-accent-ink:  #4A2FC4;  /* text and links: 8.42:1 on white  */
    --ar-accent-deep: #4C2BC4;  /* pressed / active                 */

    --ar-success-ink: #116932;
    --ar-warning-ink: #8A5205;
    --ar-warning-bg:  #FBF0DC;
    --ar-danger-ink:  #B91C1C;

    --ar-ring: rgba(95, 73, 232, .28);

    /* A tile inside a card: one step off the surface, in either mode. */
    --ar-tile:        #F7F5FD;
    --ar-tile-strong: #EFEBFA;

    /* Liquid Glass — the navigation layer's material (invariant 265). */
    --ar-glass-bg:       rgba(255, 255, 255, .62);
    --ar-glass-bg-thick: rgba(255, 255, 255, .88);
    --ar-glass-rim:      rgba(255, 255, 255, .95);
    --ar-glass-edge:     rgba(60, 45, 120, .13);
    --ar-glass-shadow:   0 1px 2px rgba(30, 20, 80, .05), 0 10px 30px -8px rgba(30, 20, 80, .14);
    --ar-ambient:
        radial-gradient(46rem 34rem at 0% 0%, rgba(124, 108, 255, .28), transparent 62%),
        radial-gradient(40rem 30rem at 0% 100%, rgba(56, 140, 255, .20), transparent 60%),
        radial-gradient(52rem 34rem at 100% -8%, rgba(200, 96, 255, .16), transparent 58%),
        radial-gradient(44rem 36rem at 80% 112%, rgba(20, 184, 166, .10), transparent 60%);
}

.dark {
    /* The panel Ariana has always had: deep indigo-violet surfaces. */
    --ar-canvas:   var(--ariana-purple-900);
    --ar-surface:  var(--ariana-purple-850);
    --ar-sunken:   rgba(0, 0, 0, .28);

    --ar-tile:        rgba(255, 255, 255, .035);
    --ar-tile-strong: rgba(255, 255, 255, .07);

    --ar-glass-bg:       rgba(22, 17, 47, .52);
    --ar-glass-bg-thick: rgba(24, 19, 54, .86);
    --ar-glass-rim:      rgba(255, 255, 255, .11);
    --ar-glass-edge:     rgba(255, 255, 255, .075);
    --ar-glass-shadow:   0 1px 2px rgba(0, 0, 0, .45), 0 14px 36px -10px rgba(0, 0, 0, .55);
    --ar-ambient:
        radial-gradient(46rem 34rem at 0% 0%, rgba(124, 108, 255, .42), transparent 62%),
        radial-gradient(40rem 30rem at 0% 100%, rgba(45, 120, 255, .30), transparent 60%),
        radial-gradient(52rem 34rem at 100% -8%, rgba(190, 80, 255, .22), transparent 58%),
        radial-gradient(44rem 36rem at 80% 112%, rgba(20, 184, 166, .12), transparent 60%);
    --ar-chrome:   var(--ariana-purple-850);
    --ar-wash:     rgba(124, 108, 255, .16);

    --ar-line:         var(--ariana-purple-line);
    --ar-line-strong:  var(--ariana-purple-600);

    --ar-ink:      #F4F2FC;   /* 15.86:1 on the panel  AAA */
    --ar-ink-dim:  #CFCAE8;   /* 11.10:1               AAA */
    --ar-ink-mute: #ADA7D0;   /*  7.71:1 on the panel; 6.33:1 on glass over the wash's brightest point */

    --ar-accent:      var(--ariana-accent);
    /* The fill under a WHITE label. The brand violet itself is 3.86:1 there. */
    --ar-accent-fill:       #6855F0;   /* 5.06:1 */
    --ar-accent-fill-hover: #5D49E6;
    --ar-danger-fill:       #CF2E2E;   /* 5.14:1 — Filament's danger-600 read 4.32 under white */
    --ar-danger-fill-hover: #C22727;
    /* The other status fills, measured under white on Filament's 600 shade:
       success 3.68, info 4.07, warning 4.17 (1.73.0). */
    --ar-success-fill:       #15803D;   /* 5.02:1 */
    --ar-success-fill-hover: #146C36;
    --ar-info-fill:          #2563EB;   /* 5.17:1 */
    --ar-info-fill-hover:    #1D55D6;
    --ar-warning-fill:       #B45309;   /* 5.02:1 */
    --ar-warning-fill-hover: #A24B08;
    --ar-accent-ink:  #B9AEFF;
    --ar-accent-deep: #9384FF;

    --ar-success-ink: #4ADE80;
    --ar-warning-ink: #FBBF24;
    --ar-warning-bg:  rgba(245, 158, 11, .12);
    --ar-danger-ink:  #F87171;

    --ar-ring: rgba(124, 108, 255, .38);
}

/* Vazirmatn (OFL), served locally — no third-party font host is contacted.
   The unicode-range is the whole trick: the browser downloads and uses these
   faces ONLY for Arabic-script characters, so Persian gets real typography
   while Latin text keeps the Latin face. That means Vazirmatn can sit first in
   the panel's own stack below instead of fighting it from another file —
   which is what went wrong the first time: `.fi-body textarea` here (0,1,1)
   outranked `.ariana-assistant__input` in assistant.css (0,1,0), so Persian
   typed into the chat composer kept falling back to a system face.

   size-adjust: Persian set beside San Francisco or Inter at the same
   font-size reads a size smaller — the Latin faces have a tall x-height and
   Vazirmatn's letters sit low with their marks above. 105% evens the two out
   for THESE glyphs only, in every place they appear, without touching a
   single Latin letter or any layout measured in em (invariant 264). */
@font-face {
    font-family: 'Vazirmatn';
    src: url('fonts/Vazirmatn-Regular.woff2') format('woff2');
    font-weight: 400;
    font-style: normal;
    font-display: swap;
    unicode-range: U+0600-06FF, U+0750-077F, U+08A0-08FF, U+FB50-FDFF, U+FE70-FEFF, U+200C-200D, U+FDFC, U+FDFD;
    size-adjust: 105%;
}

@font-face {
    font-family: 'Vazirmatn';
    src: url('fonts/Vazirmatn-Medium.woff2') format('woff2');
    font-weight: 500;
    font-style: normal;
    font-display: swap;
    unicode-range: U+0600-06FF, U+0750-077F, U+08A0-08FF, U+FB50-FDFF, U+FE70-FEFF, U+200C-200D, U+FDFC, U+FDFD;
    size-adjust: 105%;
}

/* 600 is the panel's heaviest weight (invariant 264), so without this face
   every Persian title fell on Bold — a full step heavier than the semibold
   Latin beside it. Same upstream build as the other three (v33.003). */
@font-face {
    font-family: 'Vazirmatn';
    src: url('fonts/Vazirmatn-SemiBold.woff2') format('woff2');
    font-weight: 600;
    font-style: normal;
    font-display: swap;
    unicode-range: U+0600-06FF, U+0750-077F, U+08A0-08FF, U+FB50-FDFF, U+FE70-FEFF, U+200C-200D, U+FDFC, U+FDFD;
    size-adjust: 105%;
}

@font-face {
    font-family: 'Vazirmatn';
    src: url('fonts/Vazirmatn-Bold.woff2') format('woff2');
    font-weight: 700;
    font-style: normal;
    font-display: swap;
    unicode-range: U+0600-06FF, U+0750-077F, U+08A0-08FF, U+FB50-FDFF, U+FE70-FEFF, U+200C-200D, U+FDFC, U+FDFD;
    size-adjust: 105%;
}

/* The panel typeface. Filament sets its own font stack on the body, so this
   has to be specific enough to win without !important on every element.
   Vazirmatn leads the stack for the Arabic script only (see the ranges
   above); every Latin glyph falls straight through to the Apple system face
   on Apple hardware and to Inter everywhere else (invariant 263). Feature
   settings are reset to normal: a stylistic set or character variant named
   here would redraw the system face on a Mac and pull Inter AWAY from San
   Francisco elsewhere (its cv11 is a single-storey "a"). */
.fi-body,
.fi-body input,
.fi-body select,
.fi-body textarea,
.fi-body button {
    font-family: 'Vazirmatn', -apple-system, BlinkMacSystemFont, 'Inter', ui-sans-serif, system-ui, 'Segoe UI', Roboto, sans-serif;
    font-feature-settings: normal;
}

/* RTL blocks also get a touch more line height — Arabic script needs it.
   The SAME stack as the LTR rule, on purpose: this used to name IRANSans and
   Tahoma after Vazirmatn, and Vazirmatn's faces are unicode-ranged to the
   Arabic script, so every DIGIT inside an RTL block fell through to the next
   font on the reader's machine. On a Mac with IRANSans installed that font
   draws Latin digits as Persian ones — an SEO score read «۵۱/۱۰۰» while the
   line beside it read "32/60" (field report, 1.68.9). Latin digits must come
   from the Latin face everywhere, whatever direction the block runs. */
[dir="rtl"] .fi-body,
.fi-body [dir="rtl"] {
    font-family: 'Vazirmatn', -apple-system, BlinkMacSystemFont, 'Inter', ui-sans-serif, system-ui, 'Segoe UI', Roboto, sans-serif;
    line-height: var(--ar-lh-text);
}

/* Persian, set for Vazirmatn (invariant 264).
 *
 * The scale above is San Francisco's leading. Vazirmatn needs more: its
 * letters carry dots and marks above and below the line, and at 1.35 two
 * lines of Persian touch. So wherever the text direction IS right-to-left —
 * by attribute, or resolved by dir="auto" from the first strong character,
 * which is what `:dir(rtl)` sees and an attribute selector cannot — the four
 * line heights are replaced, and everything that uses the tokens follows.
 *
 * Tracking is switched OFF there, with !important on purpose: Arabic script
 * is cursive, and letter-spacing — the small-capitals tracking, Inter's
 * negative tracking — opens or crushes the joins between letters. No Persian
 * text is ever tracked, whatever the component asked for.
 *
 * Two rules, not one list: a browser that does not know `:dir()` drops the
 * whole selector list it appears in, and the attribute form must survive. */
[dir="rtl"] .fi-body,
.fi-body [dir="rtl"] {
    --ar-lh-tight: 1.5;
    --ar-lh-ui:    1.7;
    --ar-lh-text:  1.8;
    --ar-lh-prose: 1.95;
    --ar-tracking-caps: 0em;
    letter-spacing: 0 !important;
}

.fi-body :dir(rtl) {
    --ar-lh-tight: 1.5;
    --ar-lh-ui:    1.7;
    --ar-lh-text:  1.8;
    --ar-lh-prose: 1.95;
    --ar-tracking-caps: 0em;
    letter-spacing: 0 !important;
}

/* An element that declares no line height of its own inherits a NUMBER from
   its left-to-right parent, not the token — so a Persian paragraph inside an
   English card would keep 1.45. :where() keeps this at zero specificity: it
   only fills the gap, and any component rule still wins. */
:where(.fi-body) :where(:dir(rtl)) {
    line-height: var(--ar-lh-text);
}

/* ===========================================================================
   1. Chrome — replace the default grey with a deep purple that sits with the
      dark dashboard instead of fighting it.
   ======================================================================== */

.dark .fi-topbar > nav,
.dark .fi-topbar nav.fi-topbar-nav,
.dark .fi-topbar {
    background-color: var(--ariana-purple-850) !important;
    border-bottom: 1px solid var(--ariana-purple-line) !important;
    box-shadow: 0 1px 0 0 rgba(255, 255, 255, .02);
}

.dark .fi-sidebar,
.dark .fi-sidebar-header,
.dark .fi-sidebar-nav {
    background-color: var(--ariana-purple-900) !important;
    border-color: var(--ariana-purple-line) !important;
}

.dark body,
.dark .fi-body,
.dark .fi-main-ctn {
    background-color: #100d21 !important;
}

/* Active sidebar item reads as brand, not default indigo-on-grey. */
.dark .fi-sidebar-item-active > .fi-sidebar-item-button,
.dark .fi-sidebar-item-active .fi-sidebar-item-label {
    background-color: var(--ariana-purple-700) !important;
    color: #fff !important;
}

.dark .fi-sidebar-item-button:hover {
    background-color: var(--ariana-purple-800) !important;
}

/* Cards and sections pick up the same family. A section Filament marks
   `not-contained` is a layout wrapper with no chrome of its own — the stats
   overview sits in one — and painting it made the four stat cards look like
   tiles glued onto one big card (field report, 1.68.9). Leave it transparent
   so the cards float on the page with the grid's own gap between them. */
/* Said outright as well as by exclusion: ariana-theme.css (Filament's asset
   channel) paints every .fi-section too, and it may sit either side of this
   file in the cascade (invariant 239). */
.fi-section.fi-section-not-contained {
    background-color: transparent !important;
    border: 0 !important;
    box-shadow: none !important;
}

.dark .fi-section:not(.fi-section-not-contained),
.dark .fi-wi-stats-overview-stat,
.dark .fi-ta-ctn,
.dark .fi-fo-field-wrp .fi-input-wrp {
    background-color: var(--ariana-purple-850) !important;
    border-color: var(--ariana-purple-line) !important;
}

.dark .fi-section-header,
.dark .fi-ta-header-ctn {
    border-color: var(--ariana-purple-line) !important;
}

/* ===========================================================================
   1b. Brand wordmark — "ARIANA" in the panel's own typeface, white on dark.
       Text only; Filament renders this view in place of a logo image.

       Set in the panel's own stack rather than a system serif: the wordmark
       needs no font licence and adds no download because the panel already
       loads this family.
   ======================================================================== */

.ariana-brand__word {
    /* Vazirmatn first, as everywhere in the panel: its faces cover the Arabic
       script only, so "ARIANA" still sets in the Latin face while a Persian site
       name beside it gets the real face instead of the system fallback. */
    font-family: 'Vazirmatn', -apple-system, BlinkMacSystemFont, 'Inter', ui-sans-serif, system-ui, 'Segoe UI', Roboto, sans-serif;
    font-size: 1.3rem;
    font-weight: 800;
    /* Capitals need air between them to read as a wordmark rather than a
       shouted word; the size drops a little to compensate for the extra width
       so the topbar still fits the hamburger and the user menu. */
    letter-spacing: .16em;
    text-transform: uppercase;
    line-height: 1.75rem;
    white-space: nowrap;
    color: #0f1020;
}

.dark .ariana-brand__word {
    color: #ffffff;
}

/* The site name beside the wordmark: "ARIANA (We Case Study)". One step
   smaller and lighter than the wordmark, and without its wide tracking, so
   the eye reads the product first and the site as context. It is the panel's
   answer to "which of my sites am I in?" — the same question the browser tab
   title answers. */
.ariana-brand__site {
    margin-inline-start: .5rem;
    font-family: 'Vazirmatn', -apple-system, BlinkMacSystemFont, 'Inter', ui-sans-serif, system-ui, 'Segoe UI', Roboto, sans-serif;
    font-size: var(--ar-fs-callout, .9375rem);
    font-weight: 500;
    letter-spacing: normal;
    line-height: 1.75rem;
    white-space: nowrap;
    opacity: .72;
    color: inherit;
}

/* A long site name must never push the user menu off the topbar; below the
   sidebar breakpoint the wordmark alone identifies the panel. */
@media (max-width: 1023.98px) {
    .ariana-brand__site {
        display: none;
    }
}

.dark .ariana-brand__site {
    color: #ffffff;
}

:root:not(.dark) .ariana-brand__site {
    color: #0f1020;
}

/* The logo wrapper is height-constrained; let the text sit centred in it. */
.fi-logo {
    display: flex;
    align-items: center;
}

/* ===========================================================================
   1c. Tabs (the SEO / Advanced box in the post editor) — it kept the default
       slate panel while everything around it turned purple.
   ======================================================================== */

.dark .fi-tabs,
.dark .fi-fo-tabs,
.dark .fi-sc-tabs,
.dark .fi-tabs-content,
.dark .fi-sc-tabs-content {
    background-color: var(--ariana-purple-850) !important;
    border-color: var(--ariana-purple-line) !important;
}

.dark .fi-tabs-item {
    color: #b9b2e0 !important;
}

.dark .fi-tabs-item-active,
.dark .fi-tabs-item[aria-selected="true"] {
    background-color: var(--ariana-purple-700) !important;
    color: #ffffff !important;
}

/* Panels nested inside a section (SERP preview, SEO analysis) */
.dark .fi-fo-field-wrp .fi-sc-component,
.dark .fi-section .fi-section {
    background-color: transparent !important;
}

/* ===========================================================================
   1d. Dark-mode contrast pass
       Anything that assumes a light background would otherwise render dark
       text on our dark chrome. Readability matters on every screen, so these
       are stated explicitly rather than left to inherited defaults.
   ======================================================================== */

.dark .fi-section-header-heading,
.dark .fi-section-header-description,
.dark .fi-header-heading,
.dark .fi-header-subheading,
.dark .fi-breadcrumbs-item-label,
.dark .fi-fo-field-wrp-label,
.dark .fi-fo-field-wrp-hint,
.dark .fi-ta-header-heading,
.dark .fi-ta-text-item-label,
.dark .fi-ta-col-label,
.dark .fi-in-entry-label,
.dark .fi-wi-stats-overview-stat-label,
.dark .fi-wi-stats-overview-stat-value,
.dark .fi-modal-heading,
.dark .fi-dropdown-list-item-label {
    color: var(--ar-ink) !important;
}

.dark .fi-fo-field-wrp-helper-text,
.dark .fi-section-header-description,
.dark .fi-ta-empty-state-description,
.dark .fi-wi-stats-overview-stat-description {
    color: #a49dcd !important;
}

/* Inputs: force a readable value colour and placeholder. */
.dark .fi-input,
.dark .fi-fo-select select,
.dark .fi-fo-rich-editor .tiptap,
.dark .fi-fo-textarea textarea,
.dark textarea,
.dark input[type="text"],
.dark input[type="email"],
.dark input[type="url"],
.dark input[type="number"],
.dark input[type="password"],
.dark input[type="search"] {
    color: #f3f1fd !important;
    background-color: transparent !important;
}

.dark .fi-input::placeholder,
.dark textarea::placeholder,
.dark input::placeholder {
    color: #8b84b8 !important;
}

/* Select dropdowns render their own listbox — keep it dark, not white. */
.dark .fi-fo-select-option,
.dark .fi-dropdown-panel,
.dark .fi-modal-window {
    background-color: var(--ariana-purple-850) !important;
    color: var(--ar-ink) !important;
    border-color: var(--ariana-purple-line) !important;
}

/* Native option elements inherit the OS palette on some browsers. */
.dark select option {
    background-color: #1e1840;
    color: #f3f1fd;
}

/* Tables */
.dark .fi-ta-row:hover {
    background-color: rgba(124, 108, 255, .08) !important;
}

.dark .fi-ta-header-cell,
.dark .fi-ta-cell {
    color: #e6e2fa;
}

/* Badges and chips keep their semantic colour but need a readable label. */
.dark .fi-badge {
    color: #ffffff;
}

/* Prose blocks (help text, editor content) */
.dark .fi-prose,
.dark .prose,
.dark .fi-fo-rich-editor-content {
    color: #e9e6fb !important;
}

.dark .fi-prose :is(h1, h2, h3, h4, strong),
.dark .prose :is(h1, h2, h3, h4, strong) {
    color: #ffffff !important;
}

/* ===========================================================================
   2. Global search — matched to the "View site" pill that sits beside it:
      same 2.25rem height, same full radius, same line/ink/accent tokens, so
      the topbar reads as one row of controls instead of two unrelated
      widgets. If .ariana-viewsite (§10) changes shape, change this with it —
      panel_ui_suite asserts the two agree on height and radius.
   ======================================================================== */

.fi-global-search-field .fi-input-wrp {
    height: 2.25rem;
    align-items: center;
    background-color: transparent !important;
    border: 1px solid var(--ar-line) !important;
    border-radius: var(--ariana-r-full, 999px);
    box-shadow: none !important;
    transition: color .15s ease, border-color .15s ease, background-color .15s ease;
}

.fi-global-search-field .fi-input-wrp:hover {
    border-color: var(--ar-accent) !important;
    background-color: var(--ar-wash) !important;
}

.fi-global-search-field .fi-input-wrp:focus-within {
    border-color: var(--ar-accent) !important;
    background-color: transparent !important;
    box-shadow: 0 0 0 3px var(--ar-ring) !important;
}

/* The input INSIDE the pill must be chrome-free: ariana-theme.css gives every
   .dark .fi-input its own surface-2 box and an indigo focus glow — right for
   form fields, wrong here, where it rendered as a second, smaller lit box
   inside the transparent pill the moment the field was focused (1.61.1). The
   pill's wrapper carries all of the border, background and focus treatment;
   the input carries none, in either mode, in every state. */
.fi-global-search-field .fi-input-wrp input,
.dark .fi-global-search-field .fi-input-wrp input,
.fi-global-search-field .fi-input-wrp input:focus,
.dark .fi-global-search-field .fi-input-wrp input:focus {
    height: 100%;
    padding-block: 0;
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink);
    background-color: transparent !important;
    border: 0 !important;
    border-radius: inherit;
    box-shadow: none !important;
    outline: none !important;
}

.fi-global-search-field .fi-input-wrp input::placeholder {
    color: var(--ar-ink-dim) !important;
}

/* The magnifier tracks the pill's ink exactly like the View site icon. */
.fi-global-search-field .fi-input-wrp svg {
    color: var(--ar-ink-dim);
}

/* A hard 18rem floor is wider than the free space in a phone topbar, which
   pushed the whole bar sideways and took the layout with it. The floor now
   only applies once there is room for it. */
.fi-global-search-field {
    min-width: 0;
    width: 100%;
}

@media (min-width: 768px) {
    .fi-global-search-field {
        min-width: 18rem;
        width: auto;
    }
}

/* ===========================================================================
   3. Rich editor — the toolbar overflowed its column and collided with the
      sidebar. Let it wrap and give the writing area real breathing room.
   ======================================================================== */

.fi-fo-rich-editor .fi-fo-rich-editor-toolbar,
.fi-fo-rich-editor-toolbar {
    display: flex !important;
    flex-wrap: wrap !important;
    gap: .25rem;
    row-gap: .35rem;
    overflow: visible !important;
}

.dark .fi-fo-rich-editor-toolbar {
    background-color: var(--ariana-purple-800) !important;
    border-color: var(--ariana-purple-line) !important;
}

/* Visual separation between button groups. */
.fi-fo-rich-editor-toolbar > div {
    display: flex;
    flex-wrap: wrap;
    gap: .15rem;
}

.fi-fo-rich-editor .fi-fo-rich-editor-content,
.fi-fo-rich-editor .tiptap {
    min-height: 26rem;
    line-height: var(--ar-lh-prose, 1.6);
}

/* The editor sat inside a rounded wrapper but kept square corners of its own,
   so the two never lined up. Round the whole stack and clip the children.

   `overflow: clip`, NOT `hidden`. They look identical, but `hidden` makes the
   element a scroll container, and a scroll container is the box a
   `position: sticky` descendant sticks INSIDE — which silently reduced the
   sticky toolbar below to an ordinary one that scrolled away with the article.
   `clip` clips the corners without creating a scroll container, so the toolbar
   sticks to the viewport as intended. A browser too old for `clip` drops the
   declaration and simply does not round the corners of the stack; the toolbar
   and the content already round their own, so nothing looks broken. */
.fi-fo-rich-editor,
.fi-fo-rich-editor .fi-input-wrp {
    border-radius: 12px !important;
    overflow: clip;
}

.fi-fo-rich-editor-toolbar {
    border-top-left-radius: 12px;
    border-top-right-radius: 12px;
}

/* ---- The toolbar follows the writer down a long article ------------------
 *
 * Formatting a heading two thousand words into a post meant scrolling back to
 * the top of the editor, applying the format, and scrolling back down. The
 * toolbar now stays put.
 *
 * `top: 4rem` is not a guess: Filament's own `.fi-topbar-ctn` is
 * `sticky top-0` with `min-h-16`, so 4rem is exactly where it stops. The
 * z-index sits BELOW the topbar's 30 so the two never fight, and above the
 * editor content so text scrolls under the toolbar rather than over it.
 *
 * The background has to be opaque. The toolbar's own background was
 * transparent — fine when it sat on the card, unreadable once article text
 * scrolls beneath it — so both modes get the panel's surface colour here.
 * ---------------------------------------------------------------------- */
/* DESCENDANT, not a child combinator. The toolbar is NOT a direct child of
   .fi-fo-rich-editor. Filament's real markup is:

       .fi-fo-rich-editor.fi-input-wrp
         └ .fi-input-wrp-content-ctn
             └ div[wire:ignore]              <- the editor's Alpine root
                 ├ .fi-fo-rich-editor-toolbar
                 └ .fi-fo-rich-editor-main

   Written as `>` this rule matched NOTHING and the toolbar never stuck. The
   selector is now asserted against the real rendered DOM by
   tests/harness/editor_toolbar_suite.mjs, not against this file's text. */
.fi-fo-rich-editor .fi-fo-rich-editor-toolbar {
    position: sticky;
    top: 4rem;
    z-index: 20;
    background-color: var(--ar-surface);
    /* The 1px border alone leaves a hairline of article text visible between
       the toolbar and what is scrolling under it on fractional zoom levels. */
    box-shadow: 0 1px 0 0 var(--ar-line);
}

.dark .fi-fo-rich-editor .fi-fo-rich-editor-toolbar {
    background-color: var(--ariana-purple-800);
}

/* The dropdown menus the toolbar opens must paint above the article text that
   is now scrolling beneath the sticky bar. */
.fi-fo-rich-editor .fi-fo-rich-editor-toolbar .fi-dropdown-panel,
.fi-fo-rich-editor .fi-fo-rich-editor-dropdown-tool-menu {
    z-index: 31;
}

/* Inside a modal the scroll container is the modal window, not the page, so
   there is no topbar to clear and a 4rem offset would push the toolbar into
   the middle of the dialog. Modals keep the ordinary toolbar. */
.fi-modal-window .fi-fo-rich-editor .fi-fo-rich-editor-toolbar {
    position: static;
    box-shadow: none;
}

/* A short viewport has no room to give up: a sticky toolbar plus the topbar
   would leave a few lines of writing area. */
@media (max-height: 520px) {
    .fi-fo-rich-editor .fi-fo-rich-editor-toolbar {
        position: static;
        box-shadow: none;
    }
}

/* ---- Tables inside the editor -------------------------------------------
 *
 * Kept deliberately in step with App\Services\Front\ContentStyles::tables(),
 * which supplies the same borders, padding and header treatment on the public
 * site. The point of the pair is that a table looks the same in both places;
 * if one is changed the other has to be changed with it.
 * ---------------------------------------------------------------------- */
.fi-fo-rich-editor .tiptap table {
    width: 100%;
    border-collapse: collapse;
    margin-block: 1rem;
    table-layout: fixed;
}

.fi-fo-rich-editor .tiptap :is(th, td) {
    border: 1px solid var(--ar-line-strong);
    padding: .5rem .65rem;
    text-align: start;
    vertical-align: top;
    position: relative;
}

.fi-fo-rich-editor .tiptap th {
    background: var(--ar-sunken);
    font-weight: 600;
}

.fi-fo-rich-editor .tiptap .selectedCell::after {
    content: '';
    position: absolute;
    inset: 0;
    background: var(--ar-wash);
    pointer-events: none;
}

/* The column-resize handle tiptap draws between cells. */
.fi-fo-rich-editor .tiptap .column-resize-handle {
    position: absolute;
    inset-block: 0;
    inset-inline-end: -2px;
    width: 4px;
    background: var(--ar-accent);
    pointer-events: none;
}

.fi-fo-rich-editor .fi-fo-rich-editor-content,
.fi-fo-rich-editor .tiptap {
    border-bottom-left-radius: 12px;
    border-bottom-right-radius: 12px;
}

.fi-fo-rich-editor .tiptap:focus-visible,
.fi-fo-rich-editor .tiptap:focus {
    outline: none;
}

/* ===========================================================================
   4. Form layout — stop long values (author names, toggle labels) from
      shredding the narrow sidebar column.
   ======================================================================== */

.fi-fo-field-wrp .fi-fo-select .fi-input-wrp,
.fi-fo-field-wrp .choices__inner {
    min-width: 0;
}

.fi-fo-toggle-wrp,
.fi-fo-field-wrp label {
    word-break: normal;
    overflow-wrap: anywhere;
}

/* Upload diagnostics panel */
.ariana-diag {
    border: 1px solid var(--ar-line);
    border-radius: 12px;
    background: var(--ar-surface);
    margin-bottom: 1.25rem;
}

.ariana-diag summary {
    cursor: pointer;
    padding: .8rem 1rem;
    font-weight: 600;
    font-size: var(--ar-fs-body, .875rem);
    list-style: none;
    display: flex;
    align-items: center;
    gap: .6rem;
    color: var(--ar-ink);
}

.ariana-diag summary::-webkit-details-marker { display: none; }
.ariana-diag__ok  { color: var(--ar-success-ink); }
.ariana-diag__bad { color: var(--ar-danger-ink); }
.ariana-diag__chev { margin-left: auto; opacity: .55; font-weight: 500; font-size: var(--ar-fs-sub, .8125rem); }

.ariana-diag__body { padding: 0 1rem 1rem; display: grid; gap: .45rem; }

.ariana-diag__row {
    display: grid;
    grid-template-columns: 1.2rem minmax(9rem, auto) auto 1fr;
    gap: .6rem;
    align-items: baseline;
    font-size: var(--ar-fs-sub, .8125rem);
}

.ariana-diag__badge { font-weight: 600; }
.ariana-diag__badge.is-ok  { color: var(--ar-success-ink); }
.ariana-diag__badge.is-bad { color: var(--ar-danger-ink); }
.ariana-diag__label { color: var(--ar-ink-dim); }
.ariana-diag__value { color: var(--ar-ink); font-weight: 600; }
.ariana-diag__hint  { color: var(--ar-danger-ink); }

.ariana-actions {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: .6rem;
    margin-top: 1.1rem;
}

.ariana-upload-progress {
    display: flex;
    align-items: center;
    gap: .6rem;
    margin-top: 1rem;
    padding: .7rem .9rem;
    border-radius: 10px;
    border: 1px solid var(--ar-line);
    background: rgba(124, 108, 255, .08);
    font-size: var(--ar-fs-body, .875rem);
    color: var(--ar-ink-dim);
}

/* ===========================================================================
   5. Server status widget
   ======================================================================== */

.ariana-server__summary {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(11rem, 1fr));
    gap: .75rem;
}

.ariana-server__item {
    background: var(--ar-tile);
    border: 1px solid var(--ar-line);
    border-radius: 10px;
    padding: .7rem .85rem;
    min-width: 0;
}

.ariana-server__label {
    display: block;
    font-size: var(--ar-fs-footnote, .75rem);
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    opacity: .6;
    margin-bottom: .2rem;
}

.ariana-server__value {
    display: block;
    font-size: var(--ar-fs-body, .875rem);
    font-weight: 600;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}

.ariana-server__toggle {
    margin-top: .9rem;
}

.ariana-server__chev--open svg {
    transform: rotate(180deg);
    transition: transform .2s ease;
}

.ariana-server__details {
    margin-top: 1rem;
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(15rem, 1fr));
    gap: 1rem;
}

.ariana-server__group {
    border: 1px solid var(--ar-line);
    border-radius: 10px;
    padding: .85rem 1rem;
    min-width: 0;
}

.ariana-server__group-title {
    font-size: var(--ar-fs-footnote, .75rem);
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    opacity: .65;
    margin: 0 0 .55rem;
}

.ariana-server__rows {
    display: grid;
    grid-template-columns: minmax(6rem, auto) 1fr;
    gap: .3rem .8rem;
    margin: 0;
    font-size: var(--ar-fs-footnote, .75rem);
}

.ariana-server__rows dt {
    opacity: .6;
}

.ariana-server__rows dd {
    margin: 0;
    word-break: break-word;
}

[x-cloak] {
    display: none !important;
}

/* ===========================================================================
   6. About / update screen
   ======================================================================== */

.ariana-about__lead { color: var(--ar-ink-dim); line-height: var(--ar-lh-prose, 1.6); margin:0 0 1.1rem; max-width:70ch; }

.ariana-about__facts {
    display:grid; grid-template-columns:repeat(auto-fit,minmax(11rem,1fr));
    gap:.7rem; margin:0;
}
.ariana-about__facts > div {
    border:1px solid var(--ar-line); border-radius:10px; padding:.65rem .8rem;
    background:var(--ar-tile);
}
.ariana-about__facts dt { font-size: var(--ar-fs-footnote, .75rem); text-transform:uppercase; letter-spacing: var(--ar-tracking-caps, .03em); opacity:.6; }
.ariana-about__facts dd { margin:.15rem 0 0; font-weight: 600; font-size: var(--ar-fs-body, .875rem); }

/* Update preview card */
.ariana-upd {
    border:1px solid var(--ar-line); border-radius:14px;
    background:linear-gradient(180deg, rgba(124,108,255,.10), transparent 60%), var(--ariana-purple-850);
    padding:1.4rem 1.5rem; margin-bottom:1.25rem;
}
.ariana-upd.is-blocked { background:var(--ar-surface); border-color:#7f3a4a; }

.ariana-upd__head { display:flex; align-items:center; gap:.9rem; flex-wrap:wrap; margin-bottom:.9rem; }

.ariana-upd__badge {
    /* Footnote, not caption: at 11px the measured audit counts it as too
       small to read (1.80.0 — it shows only while an update is on offer,
       which is why no earlier audit met it). */
    font-size: var(--ar-fs-footnote, .75rem); font-weight: 600; letter-spacing: var(--ar-tracking-caps, .03em);
    /* mode-agnostic: white on a solid accent fill, correct in both modes */
    padding:.28rem .6rem; border-radius:6px; color:#fff;
}
.ariana-upd__badge--major { background:#dc2626; }
.ariana-upd__badge--minor { background: var(--ariana-accent); }
.ariana-upd__badge--patch { background:#0e9f6e; }

.ariana-upd__jump { font-size: var(--ar-fs-title3, 1.0625rem); color: var(--ar-ink-dim); display:flex; align-items:center; gap:.5rem; }
.ariana-upd__arrow { opacity:.5; }
.ariana-upd__to { color: var(--ar-ink); }

.ariana-upd__meta { display:flex; gap:1.1rem; flex-wrap:wrap; font-size: var(--ar-fs-footnote, .75rem); color: var(--ar-ink-mute); margin-bottom:1.1rem; }
.ariana-upd__mig { color: var(--ar-warning-ink); }

.ariana-upd__title {
    font-size: var(--ar-fs-footnote, .75rem); text-transform:uppercase; letter-spacing: var(--ar-tracking-caps, .03em);
    opacity:.65; margin:0 0 .55rem;
}
/* Filament ships Tailwind's preflight, which resets every <ul> to
   list-style:none. A release-notes list without markers reads as a wall of
   sentences, so the marker is restored explicitly — and the indent is
   logical, so a Persian panel indents from the right. */
.ariana-upd__notes {
    margin: 0 0 1.2rem;
    padding-inline-start: 1.25rem;
    list-style: disc outside;
    color: var(--ar-ink);
    line-height: var(--ar-lh-prose, 1.6);
    font-size: var(--ar-fs-body, .875rem);
}

.ariana-upd__notes li::marker { color: var(--ar-accent, #7c6cff); }
.ariana-upd__notes li { margin-bottom:.3rem; }

/* The first four notes always show; the rest wait behind this (1.80.0). The
   list gives up its bottom margin to the button, so the gap to what follows
   is the same whether there is more to read or not. */
.ariana-upd__notes--more { margin-bottom: .35rem; }
.ariana-upd__more {
    display: inline-flex; align-items: center;
    min-block-size: 1.75rem;
    margin: 0 0 1.2rem; padding: 0;
    border: 0; background: none; cursor: pointer;
    color: var(--ar-accent-ink);
    font: inherit; font-size: var(--ar-fs-body, .875rem); font-weight: 600;
    line-height: var(--ar-lh-text, 1.45);
}
.ariana-upd__more:hover { text-decoration: underline; }
.ariana-upd__more:focus-visible { outline: 2px solid var(--ar-accent, #7c6cff); outline-offset: 2px; border-radius: 4px; }

.ariana-upd__blocked { color: var(--ar-danger-ink); font-size: var(--ar-fs-body, .875rem); line-height: var(--ar-lh-text, 1.45); margin:0 0 1.1rem; }

.ariana-upd__actions { display:flex; flex-wrap:wrap; gap:.6rem; }

.ariana-upd__safety {
    margin:1.2rem 0 0; padding-top:.9rem; border-top:1px solid var(--ar-line);
    color:#8b84b8; font-size: var(--ar-fs-footnote, .75rem); line-height: var(--ar-lh-text, 1.45);
}
.ariana-upd__safety code {
    background:var(--ar-tile-strong); padding:.05rem .35rem; border-radius:4px; font-size: var(--ar-fs-footnote, .75rem);
}
.ariana-upd__signed { color: var(--ar-success-ink, #0e9f6e); }

/* The hub block (1.71.0): "a newer release is out" and the automatic switch */
.ariana-hub--available {
    border:1px solid var(--ar-line); border-radius:12px;
    background:linear-gradient(180deg, rgba(124,108,255,.10), transparent 60%);
    padding:1.1rem 1.25rem; margin-bottom:1rem;
}
.ariana-hub__date { font-size: var(--ar-fs-footnote, .75rem); color: var(--ar-ink-mute); }
.ariana-hub__current { margin:0 0 .6rem; color: var(--ar-ink); font-size: var(--ar-fs-callout, .9375rem); }
.ariana-hub__status { margin:0 0 1rem; font-size: var(--ar-fs-footnote, .75rem); color: var(--ar-ink-mute); line-height: var(--ar-lh-text, 1.45); }
.ariana-hub__error { display:block; color: var(--ar-danger-ink); font-size: var(--ar-fs-sub, .8125rem); line-height: var(--ar-lh-text, 1.45); margin:.4rem 0 .8rem; }
.ariana-hub__toggle {
    display:flex; gap:.75rem; align-items:flex-start; cursor:pointer;
    padding-top:.9rem; border-top:1px solid var(--ar-line);
}
.ariana-hub__toggle > span { display:flex; flex-direction:column; gap:.2rem; }
.ariana-hub__toggle b { font-size: var(--ar-fs-body, .875rem); color: var(--ar-ink); }
.ariana-hub__toggle small { font-size: var(--ar-fs-footnote, .75rem); color: var(--ar-ink-mute); line-height: var(--ar-lh-text, 1.45); max-width:70ch; }


/* ===========================================================================
   7. Tablet and phone
   ---------------------------------------------------------------------------
   The panel was built and checked at desktop width, and everything below is
   what that assumption cost on a smaller screen. Three failures account for
   almost all of it:

     1. A fixed `min-width` inside a flex row cannot shrink, so it pushes its
        parent wider than the viewport. One offender anywhere produces a
        horizontally scrolling page, and the sticky topbar then scrolls away
        from the content underneath it.
     2. A flex or grid ITEM defaults to `min-width: auto`, meaning it refuses
        to shrink below its content. A long author name, a category chip list
        or an unbroken URL therefore widens the whole row rather than wrapping.
        `min-width: 0` is the fix, and it has to be stated explicitly.
     3. Multi-column grids with no stacking breakpoint. At 360px a four-column
        row gives each column ~70px, which is narrower than the words in it.

   Breakpoints match Filament's own (640 / 768 / 1024 / 1280) so nothing here
   fights the framework's `sm:` / `md:` / `lg:` utilities. They stop .02px short
   of each one: `min-width: 640px` and `max-width: 640px` are BOTH true at
   exactly 640px, which makes that single viewport width render unlike either
   side of it. Ending at 639.98px removes the overlap without leaving a gap.
   ======================================================================== */

/* ---- 7.1 Overflow containment -------------------------------------------
   Applied at every width, not only on small screens: an element that cannot
   shrink is a latent bug on a desktop too, it just has more room to hide in. */

.fi-main,
.fi-main-ctn,
.fi-page,
.fi-section,
.fi-section-content,
.fi-fo-field-wrp,
.fi-ta-ctn {
    min-width: 0;
}

/* Cells hold user content of unknown length: a pasted URL with no spaces in it
   has no break opportunity at all unless one is granted. */
.fi-ta-cell,
.fi-ta-text-item-label,
.fi-in-entry-content,
.ariana-serp__url,
.ariana-serp__desc,
.ariana-server__rows dd {
    overflow-wrap: anywhere;
}

/* ---- 7.2 Tables ----------------------------------------------------------
   A data table cannot be made to fit a phone, so it scrolls - but it has to
   scroll INSIDE its own card rather than dragging the page with it. */

.fi-ta-ctn {
    overflow-x: auto;
    -webkit-overflow-scrolling: touch;
    overscroll-behavior-x: contain;
}

@media (max-width: 1023.98px) {
    /* Tighter cells put roughly one more column on screen before scrolling. */
    .fi-ta-header-cell,
    .fi-ta-cell {
        padding-inline: .625rem;
    }

    /* The title column is the one a person is actually looking for; stop it
       collapsing to a two-word sliver while a badge column keeps its width. */
    .fi-ta-cell:first-child,
    .fi-ta-header-cell:first-child {
        padding-inline-start: .875rem;
    }
}

/* Secondary columns, marked on the resource rather than guessed at from
   position, so the header and the cell always disappear together and the
   table stays aligned. */
@media (max-width: 1279px) {
    .ariana-col-xl { display: none !important; }
}

@media (max-width: 1023px) {
    .ariana-col-lg { display: none !important; }
}

@media (max-width: 639px) {
    .ariana-col-md { display: none !important; }
}

/* The filter/search row above a table stacks instead of squeezing. */
@media (max-width: 639.98px) {
    .fi-ta-header-ctn .fi-ta-actions,
    .fi-ta-header-ctn > div {
        flex-wrap: wrap;
    }

    .fi-ta-search-field {
        width: 100%;
    }
}

/* ---- 7.3 Page chrome ----------------------------------------------------- */

@media (max-width: 1023.98px) {
    .fi-main {
        padding-inline: 1rem;
    }
}

@media (max-width: 639.98px) {
    .fi-main {
        padding-inline: .75rem;
        padding-block: 1rem;
    }

    .fi-header-heading {
        font-size: var(--ar-fs-title2, 1.375rem);
        line-height: var(--ar-lh-tight, 1.2);
    }

    /* Page-level action buttons sit under the heading rather than beside it,
       where they had about 90px to share. */
    .fi-header {
        flex-direction: column;
        align-items: stretch;
        gap: .75rem;
    }

    .fi-header-actions {
        flex-wrap: wrap;
    }

    .fi-section-content,
    .fi-section-header {
        padding: 1rem;
    }
}

@media (max-width: 480px) {
    /* Wide capitals with generous tracking crowd a 360px topbar, so both come
       down together rather than letting the wordmark wrap or clip. */
    .ariana-brand__word {
        font-size: 1.05rem;
        letter-spacing: .1em;
    }
}

/* ---- 7.4 Forms ----------------------------------------------------------- */

@media (max-width: 639.98px) {
    /* A button that is 40% of a phone's width is hard to hit and looks
       accidental. Full width is both easier and more deliberate. */
    .ariana-actions > .fi-btn,
    .ariana-actions > .fi-btn-ctn,
    .ariana-upd__actions > .fi-btn,
    .ariana-upd__actions > .fi-btn-ctn {
        width: 100%;
        justify-content: center;
    }

    .ariana-actions__note {
        order: 99;
    }

    /* Every interactive control clears the 44px touch target guideline. */
    .fi-btn,
    .fi-tabs-item,
    .fi-sidebar-item-button,
    .fi-dropdown-list-item {
        min-height: 2.75rem;
    }

    .fi-input,
    .fi-select-input,
    .fi-fo-textarea textarea {
        /* Anything under 16px makes iOS Safari zoom the page on focus, and it
           never zooms back out. */
        font-size: 16px;
    }
}

/* ---- Tab strips: fade and page, never scroll ------------------------------
   Settings carries eleven tabs and a laptop fits about seven. The browser's
   answer is a horizontal scrollbar: a grey bar under the tabs, a hard cut at
   the edge, and no sign that anything follows. Ariana's answer is the pattern
   every modern app uses — the overflowing edge fades out and a round chevron
   appears there to page the strip along.

   The buttons come from panel-tabs.js, which also sets the two data
   attributes below. The stylesheet alone still degrades correctly: with no
   JavaScript the strip simply scrolls, exactly as it did before. */
.fi-tabs {
    overflow-x: auto;
    -webkit-overflow-scrolling: touch;
    scroll-behavior: smooth;

    /* The scrollbar is replaced by the fade, not merely hidden: the fade and
       the chevron together carry the same information more quietly. */
    scrollbar-width: none;
    -ms-overflow-style: none;
}

.fi-tabs::-webkit-scrollbar {
    width: 0;
    height: 0;
}

.fi-tabs > * {
    flex-shrink: 0;
}

/* The host is whatever element wraps the strip — the schema tabs container,
   the list page's tab column, the sub-navigation bar. It only ever gains a
   positioning context, so no layout it already had can shift. */
.ariana-tabnav-host {
    position: relative;
}

/* display:contents so the injected wrapper contributes no box of its own:
   the two buttons position against the host, and a flex or grid host counts
   the same children it did before the script ran. */
.ariana-tabnav {
    display: contents;
}

.ariana-tabnav__btn {
    position: absolute;

    /* The host contains the tab panels as well as the strip, so the centre
       line comes from the script, which measures the strip itself. The 50%
       fallback only applies in the instant before the first measurement. */
    top: var(--ariana-tabnav-y, 50%);
    z-index: 5;
    display: none;
    align-items: center;
    justify-content: center;
    width: 1.75rem;
    height: 1.75rem;
    padding: 0;
    border: 1px solid var(--ar-line, rgba(255, 255, 255, .12));
    border-radius: 999px;
    background: var(--ar-surface, #1b1636);
    color: inherit;
    opacity: .85;
    cursor: pointer;
    pointer-events: auto;
    transform: translateY(-50%);
    box-shadow: 0 2px 10px rgba(0, 0, 0, .35);
    transition: opacity .15s ease, background-color .15s ease, transform .15s ease;
}

.ariana-tabnav__btn:hover {
    opacity: 1;
    background: var(--ar-wash, rgba(124, 108, 255, .16));
}

.ariana-tabnav__btn:active {
    transform: translateY(-50%) scale(.94);
}

.ariana-tabnav__btn:focus-visible {
    outline: 2px solid var(--ar-accent, #7c6cff);
    outline-offset: 2px;
    opacity: 1;
}

.ariana-tabnav__btn svg {
    width: .85rem;
    height: .85rem;
}

/* Logical placement: "previous" sits at the start of the strip, which is the
   right-hand side in Persian and Arabic. inset-inline handles that with no
   RTL-specific rule. */
.ariana-tabnav__btn--prev {
    inset-inline-start: .125rem;
}

.ariana-tabnav__btn--next {
    inset-inline-end: .125rem;
}

/* The chevron is drawn pointing towards the start; the "next" one is the same
   glyph mirrored, and in RTL both mirror again. */
.ariana-tabnav__btn--next svg {
    transform: scaleX(-1);
}

[dir="rtl"] .ariana-tabnav__btn--prev svg {
    transform: scaleX(-1);
}

[dir="rtl"] .ariana-tabnav__btn--next svg {
    transform: none;
}

/* Only the side that actually has hidden tabs shows a button. */
.ariana-tabnav-host[data-ariana-tabs="start"] > .ariana-tabnav > .ariana-tabnav__btn--prev,
.ariana-tabnav-host[data-ariana-tabs="both"] > .ariana-tabnav > .ariana-tabnav__btn--prev,
.ariana-tabnav-host[data-ariana-tabs="end"] > .ariana-tabnav > .ariana-tabnav__btn--next,
.ariana-tabnav-host[data-ariana-tabs="both"] > .ariana-tabnav > .ariana-tabnav__btn--next {
    display: inline-flex;
}

/* The fade. data-ariana-fade is physical (left/right) because a mask gradient
   has no logical form; panel-tabs.js resolves the direction before setting
   it, so this stylesheet never has to guess. */
.ariana-tabnav-host[data-ariana-fade="right"] > .fi-tabs {
    -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 3.5rem), transparent 100%);
    mask-image: linear-gradient(to right, #000 calc(100% - 3.5rem), transparent 100%);
}

.ariana-tabnav-host[data-ariana-fade="left"] > .fi-tabs {
    -webkit-mask-image: linear-gradient(to right, transparent 0, #000 3.5rem);
    mask-image: linear-gradient(to right, transparent 0, #000 3.5rem);
}

.ariana-tabnav-host[data-ariana-fade="left right"] > .fi-tabs {
    -webkit-mask-image: linear-gradient(to right, transparent 0, #000 3.5rem, #000 calc(100% - 3.5rem), transparent 100%);
    mask-image: linear-gradient(to right, transparent 0, #000 3.5rem, #000 calc(100% - 3.5rem), transparent 100%);
}

/* Room for the button so it never covers a label at the very edge. */
.ariana-tabnav-host[data-ariana-tabs="start"] > .fi-tabs,
.ariana-tabnav-host[data-ariana-tabs="both"] > .fi-tabs {
    scroll-padding-inline-start: 2.25rem;
}

.ariana-tabnav-host[data-ariana-tabs="end"] > .fi-tabs,
.ariana-tabnav-host[data-ariana-tabs="both"] > .fi-tabs {
    scroll-padding-inline-end: 2.25rem;
}

@media (max-width: 767.98px) {
    .fi-tabs-item {
        white-space: nowrap;
    }

    /* On a touch screen the finger is the affordance; the fade stays, the
       buttons would only cover tabs on a narrow strip. */
    .ariana-tabnav__btn {
        display: none !important;
    }
}

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

    .ariana-tabnav__btn {
        transition: none;
    }
}

/* The rich editor reserved 26rem of height, which is most of a phone screen
   before a single toolbar button is drawn. */
@media (max-width: 767.98px) {
    .fi-fo-rich-editor .fi-fo-rich-editor-content,
    .fi-fo-rich-editor .tiptap {
        min-height: 16rem;
    }

    .fi-fo-rich-editor-toolbar {
        padding: .35rem;
        gap: .2rem;
    }

    .fi-fo-rich-editor-toolbar .fi-icon-btn {
        padding: .35rem;
    }
}

/* ---- 7.5 Ariana components ---------------------------------------------- */

@media (max-width: 639.98px) {
    /* Four columns at 360px gave each label about 70px. */
    .ariana-diag__row {
        grid-template-columns: 1.2rem 1fr;
        row-gap: .15rem;
    }

    .ariana-diag__value,
    .ariana-diag__hint {
        grid-column: 2;
    }

    .ariana-diag summary {
        flex-wrap: wrap;
        row-gap: .25rem;
    }

    .ariana-diag__chev {
        margin-left: 0;
    }

    .ariana-upd {
        padding: 1rem;
        border-radius: 12px;
    }

    .ariana-upd__jump {
        font-size: var(--ar-fs-callout, .9375rem);
    }

    .ariana-upd__meta {
        gap: .5rem 1rem;
    }

    .ariana-server__summary {
        grid-template-columns: 1fr 1fr;
    }

    .ariana-server__details {
        grid-template-columns: 1fr;
    }

    /* The SEO / Readability score pair, and the analysis panel generally. */
    .ariana-grid-2 {
        grid-template-columns: 1fr;
    }

    .ariana-serp {
        padding: .75rem;
    }

    .ariana-counts {
        flex-wrap: wrap;
        gap: .35rem 1rem;
    }

    .ariana-issues__item {
        flex-direction: column;
        align-items: flex-start;
        gap: .375rem;
    }

    /* A 12px link is not a comfortable target; give it room without changing
       how it looks. */
    .ariana-issues__link {
        display: inline-flex;
        align-items: center;
        min-height: 2.25rem;
    }

    .ariana-about__facts {
        grid-template-columns: 1fr 1fr;
    }
}

@media (max-width: 420px) {
    .ariana-server__summary,
    .ariana-about__facts {
        grid-template-columns: 1fr;
    }

    /* Label above value, so neither is truncated to initials. */
    .ariana-server__rows {
        grid-template-columns: 1fr;
        gap: .1rem;
    }

    .ariana-server__rows dt {
        margin-top: .4rem;
    }

    /* The nowrap + ellipsis that keeps these tidy on desktop hides most of a
       long value on a narrow one. */
    .ariana-server__value {
        white-space: normal;
        overflow-wrap: anywhere;
    }
}

/* ---- 7.6 Media library grid --------------------------------------------- */

@media (max-width: 1023.98px) {
    .ariana-media-grid {
        grid-template-columns: repeat(auto-fill, minmax(110px, 1fr));
    }
}

@media (max-width: 480px) {
    .ariana-media-grid {
        grid-template-columns: repeat(auto-fill, minmax(96px, 1fr));
        gap: .5rem;
    }
}

/* ---- 7.6b Visual media picker -------------------------------------------
 *
 * The field, and the dialog it teleports into <body>. Everything is written
 * with logical properties — inset-inline, margin-inline, text-align: start —
 * so the whole picker mirrors in Persian and Arabic without a second sheet.
 * ---------------------------------------------------------------------- */

/* THE FIELD MEASURES ITSELF, NOT THE WINDOW
   -----------------------------------------
   The picker sits in the post form's narrow side column, so a viewport media
   query says nothing useful about the space it actually has: on a laptop the
   window is wide while this column is ~300px. The field is therefore an
   inline-size container and its own rules respond to ITS width.

   What went wrong without that: the row was `nowrap`, the button carried
   `white-space: nowrap`, and the text column had `min-width: 0` with
   `overflow-wrap: anywhere` — so the text was the only part that could give,
   and "No featured image chosen" collapsed into a one-letter-per-line
   column. The text column now has a real floor (`min-inline-size`), and when
   the container cannot honour it the layout switches to stacked instead of
   crushing anything. */
.ariana-mediapicker {
    container-type: inline-size;
    container-name: ariana-picker;
}

.ariana-mediapicker__current {
    display: flex;
    align-items: center;
    flex-wrap: wrap;              /* fallback where container queries are absent */
    gap: .75rem;
    padding: .7rem;
    border: 1px solid var(--ar-line);
    border-radius: 12px;
    background: var(--ar-surface);
}

.ariana-mediapicker__thumb {
    flex: 0 0 auto;
    width: 76px;
    height: 76px;
    border-radius: 10px;
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
    overflow: hidden;
    display: flex;
    align-items: center;
    justify-content: center;
    color: var(--ar-ink-mute);
}

.ariana-mediapicker__thumb img {
    width: 100%;
    height: 100%;
    object-fit: cover;
}

.ariana-mediapicker__summary {
    /* A floor, not zero: below this the row restacks (see the container
       query) rather than squeezing the label letter by letter. */
    flex: 1 1 9rem;
    min-inline-size: 9rem;
}

.ariana-mediapicker__name {
    margin: 0;
    font-weight: 600;
    font-size: var(--ar-fs-body, .875rem);
    color: var(--ar-ink);
    overflow-wrap: anywhere;
}

.ariana-mediapicker__meta {
    margin: .2rem 0 0;
    font-size: var(--ar-fs-footnote, .75rem);
    color: var(--ar-ink-mute);
    overflow-wrap: anywhere;
}

.ariana-mediapicker__warn {
    margin: .25rem 0 0;
    font-size: var(--ar-fs-footnote, .75rem);
    color: var(--ar-warning-ink);
}

.ariana-mediapicker__buttons {
    display: flex;
    flex-direction: column;
    gap: .35rem;
    flex: 0 0 auto;
}

/* Narrow column: thumbnail and text keep their row, the buttons take a full
   line of their own and split it evenly — same height, same radius, same gap
   as everywhere else, and it mirrors in RTL because nothing here is
   left/right. */
@container ariana-picker (max-width: 26rem) {
    .ariana-mediapicker__current {
        display: grid;
        grid-template-columns: auto 1fr;
        align-items: center;
        column-gap: .75rem;
        row-gap: .6rem;
    }

    .ariana-mediapicker__summary {
        flex: initial;
        min-inline-size: 0;       /* the grid track already guarantees room */
    }

    .ariana-mediapicker__buttons {
        grid-column: 1 / -1;
        flex-direction: row;
    }

    .ariana-mediapicker__buttons .ariana-mediapicker__btn {
        flex: 1 1 0;
        white-space: normal;      /* it has the width now; no need to overflow */
    }
}

/* Very narrow (a phone, or a collapsed column): the thumbnail leads its own
   row so the label always has the full width. */
@container ariana-picker (max-width: 17rem) {
    .ariana-mediapicker__current {
        grid-template-columns: 1fr;
        justify-items: start;
    }

    .ariana-mediapicker__buttons { grid-column: auto; inline-size: 100%; }
}

.ariana-mediapicker__btn {
    appearance: none;
    border: 1px solid transparent;
    border-radius: 9px;
    padding: .4rem .75rem;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    cursor: pointer;
    background: var(--ar-accent-fill);
    color: #fff;
    white-space: nowrap;
}

.ariana-mediapicker__btn:disabled {
    opacity: .5;
    cursor: not-allowed;
}

.ariana-mediapicker__btn--quiet {
    background: transparent;
    color: var(--ar-ink-dim);
    border-color: var(--ar-line-strong);
}

/* ---- the dialog ---- */

.ariana-mediapicker__overlay {
    position: fixed;
    inset: 0;
    /* Above Filament's own modals (z-40) so the picker opened from inside the
       editor's insert-image dialog is not painted underneath it. */
    z-index: 60;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 1.25rem;
}

.ariana-mediapicker__backdrop {
    position: absolute;
    inset: 0;
    background: rgba(10, 8, 24, .62);
}

.ariana-mediapicker__dialog {
    position: relative;
    display: flex;
    flex-direction: column;
    width: min(1040px, 100%);
    max-height: min(760px, 92dvh);
    border-radius: 16px;
    background: var(--ar-surface);
    border: 1px solid var(--ar-line);
    box-shadow: 0 24px 60px rgba(0, 0, 0, .35);
    overflow: hidden;
}

.ariana-mediapicker__head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 1rem;
    padding: .85rem 1rem;
    border-bottom: 1px solid var(--ar-line);
}

.ariana-mediapicker__head h2 {
    margin: 0;
    font-size: var(--ar-fs-callout, .9375rem);
    font-weight: 600;
    color: var(--ar-ink);
}

.ariana-mediapicker__close {
    appearance: none;
    border: 0;
    background: transparent;
    color: var(--ar-ink-dim);
    font-size: var(--ar-fs-title2, 1.375rem);
    line-height: 1;
    cursor: pointer;
    padding: .15rem .4rem;
}

.ariana-mediapicker__search {
    padding: .7rem 1rem;
    border-bottom: 1px solid var(--ar-line);
}

.ariana-mediapicker__search input {
    width: 100%;
    padding: .5rem .7rem;
    border-radius: 9px;
    border: 1px solid var(--ar-line-strong);
    background: var(--ar-sunken);
    color: var(--ar-ink);
    font-size: var(--ar-fs-body, .875rem);
}

.ariana-mediapicker__body {
    display: grid;
    grid-template-columns: minmax(0, 1fr) 300px;
    gap: 0;
    min-height: 0;
    flex: 1 1 auto;
}

.ariana-mediapicker__grid-ctn {
    min-width: 0;
    overflow-y: auto;
    padding: 1rem;
}

.ariana-mediapicker__grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(122px, 1fr));
    gap: .65rem;
}

.ariana-mediapicker__tile {
    position: relative;
    appearance: none;
    padding: 0;
    cursor: pointer;
    border: 2px solid transparent;
    border-radius: 10px;
    background: var(--ar-sunken);
    overflow: hidden;
    text-align: start;
}

.ariana-mediapicker__tile.is-active {
    border-color: var(--ar-accent);
}

.ariana-mediapicker__tile img {
    display: block;
    width: 100%;
    aspect-ratio: 1 / 1;
    object-fit: cover;
}

.ariana-mediapicker__tile-name {
    display: block;
    padding: .3rem .4rem;
    /* A file's name is read, not counted: the footnote size, not the
       caption one kept for counters and badges (11.7 px measured, 1.73.0). */
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-ui, 1.35);
    color: var(--ar-ink-dim);
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

.ariana-mediapicker__tile-flag {
    position: absolute;
    inset-block-start: .3rem;
    inset-inline-end: .3rem;
    width: 1.05rem;
    height: 1.05rem;
    border-radius: 50%;
    background: var(--ar-warning-ink);
    color: #fff;
    font-size: var(--ar-fs-caption, .6875rem);
    font-weight: 600;
    line-height: 1.05rem;
    text-align: center;
}

.ariana-mediapicker__side {
    border-inline-start: 1px solid var(--ar-line);
    padding: 1rem;
    overflow-y: auto;
    background: var(--ar-canvas);
}

.ariana-mediapicker__preview {
    border-radius: 10px;
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
    overflow: hidden;
    margin-block-end: .5rem;
}

.ariana-mediapicker__preview img {
    display: block;
    width: 100%;
    max-height: 190px;
    object-fit: contain;
}

.ariana-mediapicker__fields {
    display: flex;
    flex-direction: column;
    gap: .55rem;
    margin-block-start: .75rem;
}

.ariana-mediapicker__fields label {
    display: flex;
    flex-direction: column;
    gap: .2rem;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    color: var(--ar-ink-dim);
}

.ariana-mediapicker__fields :is(input, textarea) {
    width: 100%;
    padding: .4rem .55rem;
    border-radius: 8px;
    border: 1px solid var(--ar-line-strong);
    background: var(--ar-surface);
    color: var(--ar-ink);
    font-size: var(--ar-fs-sub, .8125rem);
    font-weight: 400;
    resize: vertical;
}

.ariana-mediapicker__note {
    margin: .6rem 0 0;
    font-size: var(--ar-fs-footnote, .75rem);
    color: var(--ar-ink-mute);
}

.ariana-mediapicker__more {
    margin-block-start: .85rem;
}

/* "Used in" under an ALT field — the articles that print that language's
   ALT of the file (invariant 262), on the file's page and in the picker's
   pane. Titles keep their own direction. */
.ariana-alt-usage,
.ariana-mediapicker__usage {
    display: inline;
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-text, 1.45);
}

.ariana-mediapicker__usage {
    display: block;
    margin: .3rem 0 0;
    color: var(--ar-ink-mute);
}

.ariana-alt-usage__label {
    color: var(--ar-ink-mute);
}

.ariana-alt-usage__link,
.ariana-mediapicker__usage a {
    color: var(--ar-accent-ink);
    font-weight: 500;
    text-decoration: underline;
    text-underline-offset: 2px;
    unicode-bidi: plaintext;
}

.ariana-mediapicker__usage a + a::before {
    content: " · ";
    color: var(--ar-ink-mute);
    text-decoration: none;
    display: inline-block;
}

.ariana-alt-usage__sep {
    color: var(--ar-ink-mute);
}

.ariana-mediapicker__foot {
    display: flex;
    justify-content: flex-end;
    gap: .5rem;
    padding: .75rem 1rem;
    border-top: 1px solid var(--ar-line);
}

@media (max-width: 820px) {
    .ariana-mediapicker__body {
        grid-template-columns: minmax(0, 1fr);
    }

    .ariana-mediapicker__side {
        border-inline-start: 0;
        border-top: 1px solid var(--ar-line);
    }

    .ariana-mediapicker__current {
        flex-wrap: wrap;
    }

    .ariana-mediapicker__buttons {
        flex-direction: row;
        width: 100%;
    }
}

/* ---- 7.7 Modals ---------------------------------------------------------- */

@media (max-width: 639.98px) {
    /* A centred modal with desktop margins leaves a sliver of content; on a
       phone it should behave like a sheet. */
    .fi-modal-window {
        margin: 0;
        max-height: 100dvh;
        border-radius: 14px 14px 0 0;
    }

    .fi-modal-content {
        padding: 1rem;
    }

    .fi-modal-footer-actions {
        flex-direction: column-reverse;
        align-items: stretch;
        gap: .5rem;
    }

    .fi-modal-footer-actions .fi-btn {
        width: 100%;
        justify-content: center;
    }
}

/* ---- 7.8 Landscape phones ------------------------------------------------
   A short viewport turns generous vertical rhythm into scrolling. */

@media (max-height: 480px) and (orientation: landscape) {
    .fi-fo-rich-editor .fi-fo-rich-editor-content,
    .fi-fo-rich-editor .tiptap {
        min-height: 12rem;
    }

    .fi-main {
        padding-block: .75rem;
    }
}

/* ---- Generated theme prompt preview -------------------------------------- */

.ariana-prompt__text {
    width: 100%;
    font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-text, 1.45);
    padding: .85rem;
    border-radius: 10px;
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
    color: var(--ar-ink);
    resize: vertical;
    white-space: pre;
    overflow-wrap: normal;
    overflow-x: auto;
}

.ariana-prompt__hint {
    margin: .5rem 0 0;
    font-size: var(--ar-fs-footnote, .75rem);
    color: var(--ar-ink-dim);
}

/* ===========================================================================
   9. Media file cards
      A file with no picture still has to be identifiable at a glance, and the
      thing people scan a library for is the format. So the extension is the
      icon rather than a caption under a generic document glyph.

      Tones are stated twice: the darker value carries the light panel, the
      lighter value the dark one. Setting a single mid-tone would have left the
      label under-contrasted on one of them.
   ======================================================================== */

.ariana-filecard {
    --file-size: 56px;
    --file-accent: #64748b;
    --file-tint: rgba(100, 116, 139, .12);

    position: relative;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex: 0 0 auto;
    width: var(--file-size);
    height: var(--file-size);
    border-radius: 10px;
    overflow: hidden;
    background: var(--file-tint);
    border: 1px solid color-mix(in srgb, var(--file-accent) 34%, transparent);
    color: var(--file-accent);
}

/* Images keep the same footprint and radius as the icon cards so rows do not
   jump in height when the library mixes pictures and documents. */
.ariana-filecard--image {
    object-fit: cover;
    background: var(--ar-sunken);
    border-color: var(--ar-line);
    color: inherit;
}

.ariana-filecard__sheet {
    position: absolute;
    width: 62%;
    height: 62%;
    opacity: .3;
}

.ariana-filecard__ext {
    position: relative;
    font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
    font-size: calc(var(--file-size) * .21);
    font-weight: 600;
    letter-spacing: var(--ar-tracking-caps, .03em);
    line-height: 1;
    text-transform: uppercase;
}

/* Light panel: 600-level tones, dark enough to read on a pale tint. */
.ariana-filecard--pdf   { --file-accent: #dc2626; --file-tint: rgba(220, 38, 38, .10); }
.ariana-filecard--doc   { --file-accent: #2563eb; --file-tint: rgba(37, 99, 235, .10); }
.ariana-filecard--sheet { --file-accent: #16a34a; --file-tint: rgba(22, 163, 74, .10); }
.ariana-filecard--slide { --file-accent: #ea580c; --file-tint: rgba(234, 88, 12, .10); }
.ariana-filecard--zip   { --file-accent: #ca8a04; --file-tint: rgba(202, 138, 4, .10); }
.ariana-filecard--code  { --file-accent: #0891b2; --file-tint: rgba(8, 145, 178, .10); }
.ariana-filecard--text  { --file-accent: #475569; --file-tint: rgba(71, 85, 105, .10); }
.ariana-filecard--media { --file-accent: #7c3aed; --file-tint: rgba(124, 58, 237, .10); }
/* Audio: teal, distinct from video's violet so the two are told apart at a
   glance in a mixed library, and away from the panel's own accent. */
.ariana-filecard--audio { --file-accent: #0d9488; --file-tint: rgba(13, 148, 136, .10); }
.ariana-filecard--font  { --file-accent: #db2777; --file-tint: rgba(219, 39, 119, .10); }

/* Dark panel: 400-level tones on a deeper tint. */
.dark .ariana-filecard--pdf   { --file-accent: #f87171; --file-tint: rgba(248, 113, 113, .13); }
.dark .ariana-filecard--doc   { --file-accent: #60a5fa; --file-tint: rgba(96, 165, 250, .13); }
.dark .ariana-filecard--sheet { --file-accent: #4ade80; --file-tint: rgba(74, 222, 128, .13); }
.dark .ariana-filecard--slide { --file-accent: #fb923c; --file-tint: rgba(251, 146, 60, .13); }
.dark .ariana-filecard--zip   { --file-accent: #fbbf24; --file-tint: rgba(251, 191, 36, .13); }
.dark .ariana-filecard--code  { --file-accent: #22d3ee; --file-tint: rgba(34, 211, 238, .13); }
.dark .ariana-filecard--text  { --file-accent: #cbd5e1; --file-tint: rgba(203, 213, 225, .11); }
.dark .ariana-filecard--media { --file-accent: #c084fc; --file-tint: rgba(192, 132, 252, .13); }
.dark .ariana-filecard--audio { --file-accent: #2dd4bf; --file-tint: rgba(45, 212, 191, .13); }
.dark .ariana-filecard--font  { --file-accent: #f472b6; --file-tint: rgba(244, 114, 182, .13); }
.dark .ariana-filecard--other { --file-accent: #94a3b8; --file-tint: rgba(148, 163, 184, .11); }

/* color-mix is recent. Where it is unsupported the border simply falls back to
   the panel line colour instead of disappearing. */
@supports not (border-color: color-mix(in srgb, red 30%, transparent)) {
    .ariana-filecard { border-color: var(--ar-line); }
}

/* The edit screen shows the same card at a larger size, next to the metadata. */
.ariana-filepreview {
    display: flex;
    align-items: center;
    gap: 1rem;
}

.ariana-filepreview__meta {
    display: flex;
    flex-direction: column;
    gap: .15rem;
    min-width: 0;
}

.ariana-filepreview__name {
    font-weight: 600;
    word-break: break-all;
}

.ariana-filepreview__sub {
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink-dim);
}

/* ===========================================================================
   10. "View site" topbar link
      Present on every screen so leaving the panel to look at the result is
      never a hunt through the menu. Quiet by default - it sits beside the
      search field and must not compete with it - and only picks up the brand
      colour on hover.
   ======================================================================== */

.ariana-viewsite {
    display: inline-flex;
    align-items: center;
    gap: .4rem;
    height: 2.25rem;
    padding: 0 .75rem;
    /* No margin. The link now sits inside .fi-topbar-end, which already applies
       a column-gap; adding a margin on top of it made this one control sit
       differently from everything else in the topbar. */
    border-radius: var(--ariana-r-full, 999px);
    border: 1px solid var(--ar-line);
    font-size: var(--ar-fs-sub, .8125rem);
    font-weight: 500;
    line-height: 1;
    white-space: nowrap;
    color: var(--ar-ink-dim);
    text-decoration: none;
    transition: color .15s ease, border-color .15s ease, background-color .15s ease;
}

/* The Clear caches pill is a <button> inside a <form> wearing the same class:
   strip the user-agent button styling so the two pills are pixel twins. */
.ariana-viewsite--button {
    background: none;
    cursor: pointer;
    font-family: inherit;
    margin: 0;
}

.ariana-viewsite-form {
    display: contents;
}

.ariana-viewsite:hover,
.ariana-viewsite:focus-visible {
    color: var(--ar-ink);
    border-color: var(--ar-accent);
    background: var(--ar-wash);
}

.ariana-viewsite:focus-visible {
    outline: 2px solid var(--ar-accent);
    outline-offset: 2px;
}

.ariana-viewsite__icon {
    width: 1rem;
    height: 1rem;
    flex: 0 0 auto;
}

/* On a narrow screen the icon carries the meaning on its own; the topbar has
   no room for the word next to the search field. */
@media (max-width: 767px) {
    .ariana-viewsite__label { display: none; }
    .ariana-viewsite { padding: 0 .55rem; }
}

/* ===========================================================================
   11. Mail test log
      A failed mail configuration is the single most common support request a
      CMS receives, and the usual answer - "could not send email" - starts a
      guessing game. This box is sized to hold the real answer: what was tried,
      what the server said, and which likely cause it is.
   ======================================================================== */

.ariana-maillog {
    border: 1px solid var(--ar-line);
    border-radius: 12px;
    background: var(--ar-sunken);
    padding: 1rem;
    font-size: var(--ar-fs-sub, .8125rem);
}

.ariana-maillog--ok  { border-color: rgba(34, 197, 94, .38); }
.ariana-maillog--bad { border-color: rgba(239, 68, 68, .38); }

.ariana-maillog--empty {
    display: flex;
    align-items: flex-start;
    gap: .65rem;
    color: var(--ar-ink-dim);
}

.ariana-maillog--empty p { margin: 0; line-height: var(--ar-lh-text, 1.45); }

.ariana-maillog__emptyicon {
    width: 1.1rem;
    height: 1.1rem;
    flex: 0 0 auto;
    margin-top: .1rem;
    opacity: .7;
}

.ariana-maillog__head {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: .6rem;
    margin-bottom: .6rem;
}

.ariana-maillog__badge {
    padding: .15rem .55rem;
    border-radius: 999px;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 500;
    letter-spacing: normal;
    text-transform: uppercase;
}

.ariana-maillog__badge.is-ok  { background: rgba(34, 197, 94, .16);  color: var(--ar-success-ink); }
.ariana-maillog__badge.is-bad { background: rgba(239, 68, 68, .16);  color: var(--ar-danger-ink); }

.ariana-maillog__stage { color: var(--ar-ink); font-weight: 500; }
.ariana-maillog__time  { margin-inline-start: auto; color: var(--ar-ink-mute); font-size: var(--ar-fs-footnote, .75rem); }

.ariana-maillog__summary {
    margin: 0 0 .75rem;
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-ink);
}

.ariana-maillog__hint {
    display: flex;
    gap: .55rem;
    padding: .7rem .8rem;
    margin-bottom: .85rem;
    border-radius: 8px;
    border: 1px solid rgba(245, 158, 11, .3);
    background: var(--ar-warning-bg);
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-warning-ink);
}

.ariana-maillog__hinticon { width: 1rem; height: 1rem; flex: 0 0 auto; margin-top: .15rem; color: var(--ariana-warning); }

.ariana-maillog__block { margin-top: .85rem; }

.ariana-maillog__label {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: .5rem;
    margin-bottom: .35rem;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 500;
    letter-spacing: var(--ar-tracking-caps, .03em);
    text-transform: uppercase;
    color: var(--ar-ink-mute);
}

.ariana-maillog__note { text-transform: none; letter-spacing: 0; font-weight: 400; opacity: .75; }

.ariana-maillog__grid {
    display: grid;
    grid-template-columns: minmax(6rem, auto) 1fr;
    gap: .2rem .9rem;
    margin: 0;
}

.ariana-maillog__grid dt { color: var(--ar-ink-dim); }
.ariana-maillog__grid dd { margin: 0; color: var(--ar-ink); word-break: break-all; }

.ariana-maillog__errors {
    margin: 0;
    padding-inline-start: 1.25rem;
    list-style: disc outside;
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-danger-ink);
}

.ariana-maillog__errors li { margin-bottom: .2rem; word-break: break-word; }

/* The transcript is the one place a horizontal scrollbar is correct: wrapping
   an SMTP line would break the > / < alignment that makes it readable. */
.ariana-maillog__pre {
    margin: 0;
    max-height: 22rem;
    overflow: auto;
    padding: .75rem;
    border-radius: 8px;
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
    font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-text, 1.45);
    white-space: pre;
    color: var(--ar-ink);
}

/* The publish-box action row: full width, primary first, cancel quiet. */
.ariana-publish-actions {
    padding-top: .35rem;
    border-top: 1px solid var(--ar-line);
    margin-top: .25rem;
}

/* ===========================================================================
   12. Table header band, and theme screenshots

      THE HEADER BAND
      Filament gives the actions column a <th> with the classes
      `fi-ta-actions-header-cell fi-ta-empty-header-cell` - note that it does
      NOT carry `fi-ta-header-cell`. Any rule written against that class
      therefore skips it, and the header reads as a bar that stops short of the
      table's right edge, with a bare gap above the row buttons.

      So the band is painted on the ROW, not on the labelled cells. Every <th>
      is covered including the unlabelled one, and it stays covered if Filament
      renames a cell class.
   ======================================================================== */

.fi-ta-table > thead > tr > th {
    background-color: var(--ar-sunken);
    border-bottom: 1px solid var(--ar-line);
}

.dark .fi-ta-table > thead > tr > th {
    background-color: rgba(255, 255, 255, .035);
}

/* Filament sizes the empty actions header to 4px, which is fine when nothing is
   painted on it and wrong once something is. It takes its width from the row
   buttons beneath it instead. */
.fi-ta-table > thead > tr > th.fi-ta-empty-header-cell {
    width: auto;
    min-width: 0;
}

/* Round the band with the card ONLY when it is actually the top of the card.
   Filament marks such a table `fi-ta-ctn-with-header`, but that class tracks the
   table's heading rather than its toolbar, so the presence of a toolbar is also
   tested directly. Either one means the header row is a middle band, and
   rounding it there produced curved corners sitting under a straight-edged bar
   — which is what made the list pages look unfinished. */
.fi-ta-ctn:not(.fi-ta-ctn-with-header):not(:has(.fi-ta-header-ctn)) .fi-ta-table > thead > tr > th:first-child {
    border-start-start-radius: var(--ariana-r-lg, 12px);
}

.fi-ta-ctn:not(.fi-ta-ctn-with-header):not(:has(.fi-ta-header-ctn)) .fi-ta-table > thead > tr > th:last-child {
    border-start-end-radius: var(--ariana-r-lg, 12px);
}

/* ---- 12b. Resource tabs joined to the table card -------------------------
   A list page rendered three stacked bars: the status tabs, the search and
   filter toolbar, and the header row — three separate slabs, only some of them
   rounded, with a grid gap between the first two. They are one control surface
   and now read as one card.

   The DOM does not co-operate: the tabs live in their own grid column
   (.fi-sc-tabs) and the table in the next one, so they cannot simply be given
   one border. Instead the tabs become the card's TOP segment — rounded above,
   square below, bottom border removed — and the table card below it drops its
   own top rounding and pulls up to meet it. The seam disappears and the two
   read as a single panel.

   Scoping matters more than it looks. `.fi-sc-tabs` is the generic schema tabs
   component: the Settings form uses it too. Scoping this to `.fi-page-content`
   therefore caught Settings as well, and the negative margin that closes the
   seam on a list page pulled the Save button up onto the card there (1.13.1).
   The rules are keyed on the resource LIST page instead, so the Settings form,
   the post editor's SEO/Advanced box and every other tab strip are untouched.
   ======================================================================== */

.fi-resource-list-records-page:has(.fi-sc-tabs) .fi-sc-tabs {
    background-color: var(--ar-sunken);
    border: 1px solid var(--ar-line);
    border-bottom: 0;
    border-start-start-radius: var(--ariana-r-lg, 12px);
    border-start-end-radius: var(--ariana-r-lg, 12px);
    border-end-start-radius: 0;
    border-end-end-radius: 0;
    padding-inline: .25rem;
}

.dark .fi-resource-list-records-page:has(.fi-sc-tabs) .fi-sc-tabs {
    background-color: rgba(255, 255, 255, .035);
    border-color: var(--ariana-purple-line);
}

/* Close the grid gap between the two columns so the segments meet. Filament's
   schema grid uses `gap: calc(var(--spacing) * 6)` with --spacing: .25rem, so
   the gap is read from its own variables rather than hard-coded: if Filament
   retunes its spacing scale, the seam follows instead of splitting open. */
.fi-resource-list-records-page:has(.fi-sc-tabs) .fi-sc-tabs {
    margin-bottom: calc(var(--spacing, .25rem) * -6);
}

/* The card is no longer the top of the stack. */
.fi-resource-list-records-page:has(.fi-sc-tabs) .fi-ta-ctn {
    border-start-start-radius: 0;
    border-start-end-radius: 0;
}

/* One line between the tabs and the toolbar, not two. The toolbar sits inside
   .fi-ta-main rather than directly in the card, so this is a descendant rule —
   checked against the rendered page, not assumed from the template. */
.fi-resource-list-records-page:has(.fi-sc-tabs) .fi-ta-ctn .fi-ta-header-ctn {
    border-top: 0;
}

/* The tab strip itself carries no second background now that its wrapper is
   the segment; and its items sit on the seam rather than floating above it. */
.fi-resource-list-records-page:has(.fi-sc-tabs) .fi-tabs {
    background-color: transparent;
    border: 0;
    box-shadow: none;
}

/* ---- Theme screenshots --------------------------------------------------- */

.ariana-themeshot {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex: 0 0 auto;
    width: 96px;
    height: 64px;
    border-radius: var(--ariana-r-md, 8px);
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
    object-fit: cover;
    overflow: hidden;
}

.ariana-themeshot--empty {
    color: var(--ar-ink-mute);
}

.ariana-themeshot--empty svg {
    width: 1.6rem;
    height: 1.6rem;
}

/* ===========================================================================
   13. Light mode — "violet paper"
       Ariana's dark panel is a deep indigo-violet. Light mode is the same
       violet lit from the front: violet-tinted neutrals rather than grey, a
       darker violet accent so it can carry white text and pass AA as link
       text, and a deep violet-black ink so nothing on screen is a colour from
       outside the family.

       Scoped with :root:not(.dark) rather than left unscoped, because Filament
       toggles `dark` on <html>. An unscoped rule would bleed into the dark
       panel and undo the theme above.

       DELIBERATELY NOT a dark sidebar on a light page. Someone who switches to
       light mode wants a light interface; handing back a dark slab defeats the
       reason they switched, and it becomes a third theme to maintain that
       fights the topbar for attention.
   ======================================================================== */

/* ---- 13.1 Canvas and chrome --------------------------------------------- */

:root:not(.dark) body,
:root:not(.dark) .fi-body,
:root:not(.dark) .fi-main-ctn {
    background-color: var(--ar-canvas);
    color: var(--ar-ink);
}

:root:not(.dark) .fi-sidebar,
:root:not(.dark) .fi-sidebar-nav,
:root:not(.dark) .fi-sidebar-header {
    background-color: var(--ar-chrome);
    border-color: var(--ar-line);
}

:root:not(.dark) .fi-topbar,
:root:not(.dark) .fi-topbar > nav,
:root:not(.dark) .fi-topbar nav.fi-topbar-nav {
    background-color: var(--ar-surface);
    border-bottom: 1px solid var(--ar-line);
}

/* Section headings in the sidebar: quiet, but not so quiet they stop grouping. */
:root:not(.dark) .fi-sidebar-group-label {
    color: var(--ar-ink-mute);
    letter-spacing: var(--ar-tracking-caps, .03em);
}

:root:not(.dark) .fi-sidebar-item-label {
    color: var(--ar-ink-dim);
}

:root:not(.dark) .fi-sidebar-item-button:hover {
    background-color: var(--ar-sunken);
}

:root:not(.dark) .fi-sidebar-item-button:hover .fi-sidebar-item-label {
    color: var(--ar-ink);
}

/* The active item. The dark panel marks it with a glow; on paper the same job
   is done by an accent wash and a solid left edge - a border reads at a glance
   where a background tint alone can be missed. */
:root:not(.dark) .fi-sidebar-item-active > .fi-sidebar-item-button {
    background-color: var(--ar-wash);
    box-shadow: inset 3px 0 0 0 var(--ar-accent);
}

:root:not(.dark) .fi-sidebar-item-active .fi-sidebar-item-label {
    color: var(--ar-accent-ink);
    font-weight: 600;
}

:root:not(.dark) .fi-sidebar-item-active .fi-icon {
    color: var(--ar-accent-ink);
}

/* ---- 13.2 Cards and content -------------------------------------------- */

:root:not(.dark) .fi-section:not(.fi-section-not-contained),
:root:not(.dark) .fi-ta-ctn,
:root:not(.dark) .fi-wi-stats-overview-stat,
:root:not(.dark) .fi-dropdown-panel,
:root:not(.dark) .fi-modal-window {
    background-color: var(--ar-surface);
    border-color: var(--ar-line);
}

:root:not(.dark) .fi-section-header,
:root:not(.dark) .fi-ta-header-ctn {
    border-color: var(--ar-line);
}

:root:not(.dark) .fi-header-heading,
:root:not(.dark) .fi-section-header-heading,
:root:not(.dark) .fi-ta-header-heading,
:root:not(.dark) .fi-modal-heading {
    color: var(--ar-ink);
}

:root:not(.dark) .fi-header-subheading,
:root:not(.dark) .fi-section-header-description,
:root:not(.dark) .fi-ta-empty-state-description,
:root:not(.dark) .fi-fo-field-wrp-helper-text,
:root:not(.dark) .fi-fo-field-wrp-hint {
    color: var(--ar-ink-mute);
}

:root:not(.dark) .fi-breadcrumbs-item-label {
    color: var(--ar-ink-mute);
}

:root:not(.dark) .fi-breadcrumbs-item:last-child .fi-breadcrumbs-item-label {
    color: var(--ar-ink-dim);
}

/* ---- 13.3 Tables -------------------------------------------------------- */

:root:not(.dark) .fi-ta-header-cell,
:root:not(.dark) .fi-ta-col-label {
    color: var(--ar-ink-dim);
}

:root:not(.dark) .fi-ta-cell {
    color: var(--ar-ink);
}

:root:not(.dark) .fi-ta-row:hover {
    /* A 7.8% luminance step: findable while tracking across a wide row, and
       quiet enough that scrolling a long list is not a strobe. */
    background-color: #F7F5FD;
}

:root:not(.dark) .fi-ta-row + .fi-ta-row {
    border-top-color: var(--ar-line);
}

/* ---- 13.4 Inputs -------------------------------------------------------- */

:root:not(.dark) .fi-input-wrp,
:root:not(.dark) .fi-fo-field-wrp .fi-input-wrp {
    background-color: var(--ar-surface);
    border-color: var(--ar-line-strong);
}

:root:not(.dark) .fi-input-wrp:focus-within {
    border-color: var(--ar-accent);
    box-shadow: 0 0 0 3px var(--ar-ring);
}

:root:not(.dark) .fi-input,
:root:not(.dark) .fi-fo-select select,
:root:not(.dark) textarea {
    color: var(--ar-ink);
}

:root:not(.dark) .fi-input::placeholder,
:root:not(.dark) textarea::placeholder {
    color: var(--ar-ink-mute);
}

:root:not(.dark) .fi-fo-field-wrp-label,
:root:not(.dark) .fi-in-entry-label {
    color: var(--ar-ink-dim);
}

/* ---- 13.5 Tabs ---------------------------------------------------------- */

:root:not(.dark) .fi-tabs {
    background-color: var(--ar-sunken);
}

:root:not(.dark) .fi-tabs-item-label {
    color: var(--ar-ink-dim);
}

:root:not(.dark) .fi-tabs-item-active,
:root:not(.dark) .fi-tabs-item[aria-selected="true"] {
    background-color: var(--ar-surface);
    box-shadow: 0 1px 2px rgba(27, 20, 54, .08);
}

:root:not(.dark) .fi-tabs-item-active .fi-tabs-item-label,
:root:not(.dark) .fi-tabs-item[aria-selected="true"] .fi-tabs-item-label {
    color: var(--ar-accent-ink);
    font-weight: 600;
}

/* ---- 13.6 Stats widgets ------------------------------------------------- */

:root:not(.dark) .fi-wi-stats-overview-stat-label {
    color: var(--ar-ink-mute);
}

:root:not(.dark) .fi-wi-stats-overview-stat-value {
    color: var(--ar-ink);
}

:root:not(.dark) .fi-wi-stats-overview-stat-description {
    color: var(--ar-ink-dim);
}

/* ---- 13.7 Prose and links ---------------------------------------------- */

:root:not(.dark) .fi-prose,
:root:not(.dark) .fi-fo-rich-editor-content {
    color: var(--ar-ink);
}

:root:not(.dark) .fi-prose :is(h1, h2, h3, h4) {
    color: var(--ar-ink);
}

:root:not(.dark) .fi-prose a,
:root:not(.dark) .fi-link-label {
    color: var(--ar-accent-ink);
}

/* ---- 13.8 The brand wordmark ------------------------------------------- */

:root:not(.dark) .ariana-brand__word {
    color: var(--ar-ink);
}

/* ---- 13.9 Keyboard focus ----------------------------------------------- */

:root:not(.dark) :focus-visible {
    outline-color: var(--ar-accent);
}

/* ===========================================================================
   AI credit card — the dashboard's only money figure.
   Sized to sit beside "Needs attention" as an equal, not as a stray stat.
   ======================================================================== */

/* EQUAL HEIGHT, NOT MERELY ADJACENT
   Two widgets sharing a dashboard row must end at the same line. Filament's
   grid items already stretch, but a section only fills the cell if it is
   told to — so the card is a full-height column and its body pushes the
   footer note to the bottom. */
.fi-wi-widget { block-size: 100%; }
.fi-wi-widget > .fi-section { block-size: 100%; }

.ariana-credit {
    display: flex;
    flex-direction: column;
    gap: .45rem;
    block-size: 100%;
}

.ariana-credit__spacer { flex: 1 1 auto; min-block-size: .25rem; }

.ariana-credit__figure {
    font-size: var(--ar-fs-title1, 1.625rem);
    font-weight: 600;
    line-height: var(--ar-lh-tight, 1.2);
    margin: 0;
}

.ariana-credit__figure--good  { color: #4ade80; }
.ariana-credit__figure--warn  { color: #fbbf24; }
.ariana-credit__figure--bad   { color: #f87171; }
.ariana-credit__figure--neutral { color: #efeaff; }
.ariana-credit__figure--muted { color: rgba(239, 234, 255, .55); font-size: var(--ar-fs-title2, 1.375rem); }

.ariana-credit__meta { margin: 0; font-size: var(--ar-fs-footnote, .75rem); opacity: .68; }
.ariana-credit__hint { margin: .2rem 0 0; font-size: var(--ar-fs-footnote, .75rem); opacity: .55; line-height: var(--ar-lh-text, 1.45); }
.ariana-credit__label { font-size: var(--ar-fs-footnote, .75rem); opacity: .75; }

.ariana-credit__entry {
    display: flex;
    align-items: center;
    gap: .35rem;
    border-radius: .65rem;
    border: 1px solid rgba(124, 108, 255, .35);
    padding-inline: .6rem;
    background: rgba(124, 108, 255, .06);
}

.ariana-credit__currency { opacity: .6; font-size: var(--ar-fs-body, .875rem); }

.ariana-credit__input {
    flex: 1;
    min-inline-size: 0;
    border: 0;
    background: transparent;
    padding-block: .5rem;
    font-size: var(--ar-fs-callout, .9375rem);
    color: inherit;
}

.ariana-credit__input:focus { outline: none; }

.ariana-credit__actions { display: flex; gap: .4rem; }

.ariana-credit__save {
    border: 0;
    cursor: pointer;
    border-radius: .6rem;
    background: var(--ar-accent-fill);
    color: #fff;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    padding: .45rem .8rem;
    align-self: flex-start;
}

.ariana-credit__save:hover { background: var(--ar-accent-fill-hover); }

.ariana-credit__cancel,
.ariana-credit__link {
    border: 0;
    background: transparent;
    cursor: pointer;
    color: inherit;
    opacity: .65;
    font-size: var(--ar-fs-footnote, .75rem);
    padding: .45rem .2rem;
    align-self: flex-start;
    text-align: start;
}

.ariana-credit__cancel:hover,
.ariana-credit__link:hover { opacity: 1; text-decoration: underline; }

/* ==========================================================================
   Media library — grid layout, video tiles and the file preview dialog
   (1.48.0)

   Every rule here uses logical properties (inline-start/end, margin-inline,
   text-align: start) rather than left/right, so the whole of it mirrors in
   Persian and the other RTL locales without a second stylesheet — the same
   rule the media picker above already follows.
   ========================================================================== */

/* --- the picker's non-image tiles ---------------------------------------- */

/* A video with no poster frame, or any file that is not a picture. The sheet
   fills the same square an <img> would, so a mixed grid stays on one baseline
   instead of stepping up and down row by row. */
.ariana-mediapicker__tile-sheet {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 100%;
    aspect-ratio: 1 / 1;
    background: var(--ar-sunken);
    color: var(--ar-ink-dim);
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    letter-spacing: var(--ar-tracking-caps, .03em);
}

/* The play glyph is centred on the artwork, not on the whole tile: the tile
   also holds the filename strip underneath, and centring on that would sit the
   triangle low and off the picture. */
.ariana-mediapicker__tile-play,
.ariana-mediagrid__play {
    position: absolute;
    inset-block-start: 0;
    inset-inline-start: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 100%;
    /* Matches the 1/1 artwork box above the name strip. */
    aspect-ratio: 1 / 1;
    font-size: var(--ar-fs-title2, 1.375rem);
    color: #fff;
    text-shadow: 0 1px 6px rgba(0, 0, 0, .55);
    pointer-events: none;
}

.ariana-mediapicker__preview video {
    display: block;
    width: 100%;
    max-height: 190px;
    background: #000;
}

.ariana-mediapicker__preview audio {
    display: block;
    width: 100%;
    padding: .75rem;
}

/* --- the library grid ---------------------------------------------------- */

/*  THE CELL, NOT JUST THE CARD
    Filament wraps every grid record in its own chrome: a `.fi-ta-record` with
    padding and a border, a selection checkbox rendered as a "content prefix"
    that shifts the content sideways, and a `<button>` wrapper around the
    clickable area. 1.48.1 styled only the card INSIDE that chrome, so the card
    was offset by the checkbox, overflowed the record's right edge, and every
    card ended up a different height.

    So the record itself becomes the card. Its chrome is neutralised here in one
    place rather than worked around inside the Blade, and the card partial stays
    a plain, self-contained piece of markup.                                   */

.fi-ta-content-grid > .fi-ta-record {
    position: relative;
    display: flex;
    flex-direction: column;
    /* Equal height across a row regardless of how long a filename runs or
       whether a card carries the "no ALT text" line. */
    height: 100%;
    padding: 0;
    overflow: hidden;
    border-radius: 12px;
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
}

/* The checkbox is a content prefix, which shifts everything after it inline.
   Taken out of flow and floated over the artwork instead. */
.fi-ta-content-grid > .fi-ta-record > .fi-ta-record-checkbox {
    position: absolute;
    inset-block-start: .45rem;
    inset-inline-start: .45rem;
    z-index: 2;
    margin: 0;
}

/* Flex column all the way down, not block.
   The height has to be handed from the grid item to the card, or the card stops
   at its content and the action bar of a card with a "no ALT text" line sits a
   line lower than its neighbour's. A flex column also stretches its children to
   full width, so this carries the horizontal fix as well. */
/* The action bar is a CHILD of the content container, not a sibling of it, so
   the container is what has to place it: one row that takes the space left
   over, then one that takes what it needs. `grid-template-rows: 1fr auto` says
   that outright, where a flex chain left the leftover space distributed between
   the card and the bar and the bars in a row ended up at different heights. */
.fi-ta-content-grid > .fi-ta-record > .fi-ta-record-content-ctn {
    display: grid;
    grid-template-rows: 1fr auto;
    gap: 0;
    padding: 0;
    width: 100%;
    min-width: 0;
    min-height: 0;
    flex: 1 1 auto;
}

/* Every wrapper from here down is a single full-height row, so the card
   inherits the whole cell instead of stopping at its own content. */
.fi-ta-content-grid > .fi-ta-record > .fi-ta-record-content-ctn > div,
.fi-ta-content-grid .fi-ta-record-content > .fi-grid-col,
.fi-ta-content-grid .fi-ta-stack,
.fi-ta-content-grid .fi-ta-stack > .fi-grid-col,
.fi-ta-content-grid .fi-ta-col {
    display: grid;
    grid-template-rows: 1fr;
    /* minmax(0, 1fr), not an implicit auto column. An auto track sizes to its
       CONTENT, so the card came out as wide as whatever image was inside it —
       82px for a small logo, 152px for a photograph — and a row of cards was
       never uniform. minmax(0, …) also lets the track shrink below the
       content's minimum, which is what stops a wide image forcing it open. */
    grid-template-columns: minmax(0, 1fr);
    align-content: stretch;
    /* Filament's stack carries fi-align-start, which stops its children
       stretching. Restated here, or the card sizes to its content. */
    justify-items: stretch;
    align-items: stretch;
    width: 100%;
    min-width: 0;
    min-height: 0;
    max-width: none;
    gap: 0;
}

/* The clickable wrapper is a <button>: it arrives with button padding, centred
   text and a fixed intrinsic width. All three have to go. */
.fi-ta-content-grid .fi-ta-record-content {
    display: grid;
    grid-template-rows: 1fr;
    height: 100%;
    width: 100%;
    padding: 0;
    margin: 0;
    border: 0;
    background: transparent;
    text-align: start;
    cursor: pointer;
}

/* The sort keys are rendered because Filament only sorts by a VISIBLE column,
   but they must occupy nothing. Hiding the inner element alone left three empty
   column wrappers stacked under every card. */
.ariana-mediagrid__sortkey,
.fi-ta-content-grid .fi-ta-col:has(> .ariana-mediagrid__sortkey) {
    display: none;
}

.ariana-mediagrid__card {
    display: flex;
    flex-direction: column;
    height: 100%;
    min-height: 0;
    /* Explicit, not inherited. A percentage width resolves against a parent
       with a definite width; leaving the card to stretch implicitly is what
       let a 1694px-wide photograph size its own card and burst the frame. */
    width: 100%;
    max-width: 100%;
    min-width: 0;
    justify-self: stretch;
    /* No border or background of its own: the record cell above provides both,
       and two nested frames read as a mistake. */
}

.ariana-mediagrid__art {
    position: relative;
    /* A fixed square, so a row of cards is level whatever shape the files are.
       flex-shrink: 0 keeps it square when the card is stretched taller than its
       content by a neighbour with a longer name. */
    aspect-ratio: 1 / 1;
    flex: 0 0 auto;
    width: 100%;
    /* The cap is what actually contains an oversized image: without it the box
       takes the picture's intrinsic width and the aspect ratio makes it that
       tall as well. */
    max-width: 100%;
    min-width: 0;
    background: color-mix(in srgb, var(--ar-line) 35%, transparent);
    overflow: hidden;
}

.ariana-mediagrid__image {
    display: block;
    width: 100%;
    height: 100%;
    /* cover, so a portrait photograph and a landscape one fill the same box.
       A small image is scaled up rather than left as a stamp in the corner. */
    object-fit: cover;
}

.ariana-mediagrid__sheet {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 100%;
    height: 100%;
}

.ariana-mediagrid__duration {
    position: absolute;
    inset-block-end: .35rem;
    inset-inline-end: .35rem;
    padding: .1rem .35rem;
    border-radius: 5px;
    background: rgba(0, 0, 0, .72);
    color: #fff;
    font-size: var(--ar-fs-caption, .6875rem);
    font-variant-numeric: tabular-nums;
    line-height: var(--ar-lh-ui, 1.35);
}

.ariana-mediagrid__badge {
    position: absolute;
    inset-block-start: .4rem;
    inset-inline-end: .4rem;
    padding: .1rem .38rem;
    border-radius: 5px;
    font-size: var(--ar-fs-caption, .6875rem);
    font-weight: 600;
    line-height: var(--ar-lh-text, 1.45);
    color: #fff;
}

.ariana-mediagrid__badge--busy { background: #6b7280; }
.ariana-mediagrid__badge--bad  { background: #b91c1c; }
.ariana-mediagrid__badge--warn { background: #b45309; }

.ariana-mediagrid__body {
    display: flex;
    flex-direction: column;
    gap: .15rem;
    padding: .5rem .6rem;
    flex: 1 1 auto;
    min-width: 0;
}

.ariana-mediagrid__name {
    margin: 0;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    line-height: var(--ar-lh-ui, 1.35);
    color: var(--ar-ink);
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    text-align: start;
}

.ariana-mediagrid__meta {
    display: flex;
    flex-wrap: wrap;
    gap: .3rem;
    margin: 0;
    font-size: var(--ar-fs-caption, .6875rem);
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-ink-dim);
    text-align: start;
}

.ariana-mediagrid__meta span + span::before {
    content: "\00b7";
    margin-inline-end: .3rem;
}

.ariana-mediagrid__alt {
    margin: 0;
    font-size: var(--ar-fs-caption, .6875rem);
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-warning-ink, #f59e0b);
    text-align: start;
}

/* The action bar: one menu button, pinned to the bottom edge of the card so
   the bars line up across a row even when the names above them wrap. */
.fi-ta-content-grid .fi-ta-actions {
    display: flex;
    flex: 0 0 auto;
    width: 100%;
    margin: 0;
    padding: .45rem .6rem;
    border-block-start: 1px solid var(--ar-line);
    /* end, not flex-end: the bar has to mirror in Persian like everything
       else on this screen. */
    justify-content: end;
}

/* --- the preview dialog -------------------------------------------------- */

.ariana-filemodal {
    display: flex;
    flex-direction: column;
    gap: .85rem;
}

.ariana-filemodal__stage {
    display: flex;
    align-items: center;
    justify-content: center;
    border-radius: 12px;
    border: 1px solid var(--ar-line);
    background: var(--ar-sunken);
    overflow: hidden;
    padding: .5rem;
}

.ariana-filemodal__video {
    display: block;
    width: 100%;
    max-height: 62vh;
    background: #000;
    border-radius: 8px;
}

.ariana-filemodal__audio { width: 100%; }

.ariana-filemodal__image {
    display: block;
    max-width: 100%;
    max-height: 62vh;
    object-fit: contain;
    border-radius: 8px;
}

.ariana-filemodal__facts {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(9rem, 1fr));
    gap: .5rem .9rem;
    margin: 0;
}

.ariana-filemodal__facts dt {
    font-size: var(--ar-fs-footnote, .75rem);
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    color: var(--ar-ink-dim);
    text-align: start;
}

.ariana-filemodal__facts dd {
    margin: 0;
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink);
    word-break: break-word;
    text-align: start;
}

.ariana-filemodal__note {
    margin: 0;
    padding: .5rem .65rem;
    border-radius: 8px;
    border-inline-start: 3px solid var(--ar-warning-ink, #f59e0b);
    background: rgba(245, 158, 11, .08);
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-ink-dim);
    text-align: start;
}

.ariana-filemodal__url {
    display: flex;
    flex-direction: column;
    gap: .3rem;
    font-size: var(--ar-fs-caption, .6875rem);
    color: var(--ar-ink-dim);
    text-align: start;
}

.ariana-filemodal__urlrow {
    display: flex;
    gap: .4rem;
    align-items: stretch;
}

/* Sibling controls share height, radius and border by declaring them once for
   both. The input and the button are different elements with different default
   box models, and letting each keep its own is exactly how a two-pixel
   misalignment appears in a row like this. */
.ariana-filemodal__urlrow input,
.ariana-filemodal__copy {
    height: 2.3rem;
    box-sizing: border-box;
    border-radius: 8px;
    border: 1px solid var(--ar-line);
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-ui, 1.35);
}

.ariana-filemodal__urlrow input {
    flex: 1 1 auto;
    min-width: 0;
    padding-inline: .6rem;
    background: var(--ar-sunken);
    color: var(--ar-ink);
    font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
    text-align: start;
    /* URLs are read left-to-right even in a mirrored panel. */
    direction: ltr;
}

.ariana-filemodal__copy {
    flex: 0 0 auto;
    padding-inline: .85rem;
    cursor: pointer;
    background: var(--ar-accent-fill);
    border-color: var(--ar-accent);
    color: #fff;
    font-weight: 600;
    white-space: nowrap;
}

.ariana-filemodal__copy:hover { filter: brightness(1.08); }

/* The grid's sort keys.
   Filament only offers — and only APPLIES — a sort for a column that is both
   sortable and visible, and a grid has no column headers to click. So the
   three sortable columns are rendered into every card and hidden here: the
   card already shows the name, the size and the date, and repeating them would
   be noise. display:none also removes them from the accessibility tree, which
   is correct — they carry no information the card does not already announce. */
.ariana-mediagrid__sortkey { display: none; }

/* ==========================================================================
   The video quality / encoding speed sliders (Settings → Media)

   Two matched controls, each on its own line at the field's full width, each
   carrying a labelled scale. (Side by side until 1.73.0: half a card could
   not hold five labels at a readable size — invariant 145.)

   The track is FLUSH with its label and with every other control on the
   screen — no inset. An earlier attempt indented it to make room for the end
   labels, which fixed the overflow and broke the alignment: the track no
   longer started where its own label did, or where the text input below it
   did, and that reads as sloppier than the problem it solved.

   Instead the two END labels are clamped. noUiSlider centres every label on
   its value (`transform: translate(-50%, 50%)`), so the ones at 0% and 100%
   hang half their own width past the track. Those two are re-anchored to the
   inside — the only two that can overflow, and the only two that are touched.
   The hook is the inline `left: 0%` / `left: 100%` noUiSlider writes itself.
   ========================================================================== */

.ariana-videoslider {
    /* The scale is absolutely positioned and contributes no height of its own;
       without this the helper sentence underneath sits on top of it. Sized
       for 12.75 px labels (1.73.0): 2rem left 1.5 px under them, and the
       phone's 1.85rem let them touch the sentence. */
    margin-block-end: 2.25rem;
}

.ariana-videoslider .noUi-value {
    font-size: var(--ar-fs-footnote);
    line-height: 1.4;
    letter-spacing: .01em;
    color: var(--ar-ink-dim);
    white-space: nowrap;
}

/* The two labels that would otherwise leave the field. The Y half of the
   transform repeats Filament's own (translate(-50%, 50%)); only the X anchor
   changes, so the scale keeps sitting exactly where the rest of it sits. */
.ariana-videoslider .noUi-value[style*="left: 0%"] {
    transform: translate(0, 50%);
}

.ariana-videoslider .noUi-value[style*="left: 100%"] {
    transform: translate(-100%, 50%);
}

/* RTL: Filament flips the base anchor to translate(50%, 50%), so the two ends
   swap which side they would overflow on. */
[dir="rtl"] .ariana-videoslider .noUi-value[style*="left: 0%"] {
    transform: translate(0, 50%);
}

[dir="rtl"] .ariana-videoslider .noUi-value[style*="left: 100%"] {
    transform: translate(-100%, 50%);
}

/* Tick marks: shorter and quieter than the noUiSlider default, which is drawn
   for a light background and reads as heavy on the panel's deep purple. */
.ariana-videoslider .noUi-marker {
    background: color-mix(in srgb, currentColor 28%, transparent);
}

.ariana-videoslider .noUi-marker-large {
    height: 8px;
    background: color-mix(in srgb, currentColor 45%, transparent);
}

.ariana-videoslider .noUi-marker-normal {
    height: 4px;
}

@media (max-width: 640px) {
    /* A phone's track is about 260 px: five labels at a readable size cannot
       share it. The two ends stay; the sentence under the slider names every
       position as the handle moves. */
    .ariana-videoslider .noUi-value:not([style*="left: 0%"]):not([style*="left: 100%"]) {
        display: none;
    }
}

/* ==========================================================================
   THE WORKING MARK — one spinner for every wait in Ariana
   ==========================================================================

   Every surface that waits on an AI provider already had a progress bar, and
   a progress bar is a poor answer to the only question an operator actually
   asks while waiting: "is this still alive, or has it hung?" A bar that has
   not moved for twenty seconds looks exactly like a bar that never will —
   and podcast generation legitimately pauses for a minute at a time when the
   speech service asks it to.

   So: one mark, used identically on the Assistant, Auto Pilot, Podcasts, the
   SEO Analyzer and the article's audio dialog. It turns while work is in
   flight and stops the moment the work does — a failed run renders a
   different block entirely, and a browser that has gone offline is caught by
   `wire:offline.class`, which is the one case where the page cannot know
   that nothing is happening any more.

   Motion is opt-out: under prefers-reduced-motion the mark holds still and
   dims instead, so the same markup still says "working" without moving. */

@keyframes ariana-working-spin {
    to { transform: rotate(360deg); }
}

@keyframes ariana-working-pulse {
    50% { opacity: .35; }
}

.ariana-working-mark {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    inline-size: 1.1em;
    block-size: 1.1em;
    flex: 0 0 auto;
    color: rgb(124, 108, 255);
    vertical-align: -.15em;
}

.ariana-working-mark svg {
    inline-size: 100%;
    block-size: 100%;
    animation: ariana-working-spin 1.1s linear infinite;
    transform-origin: 50% 50%;
}

/* A Filament section can carry the same meaning through its own icon. */
.ariana-working .fi-section-header-icon svg,
.ariana-working .fi-icon svg {
    animation: ariana-working-spin 1.1s linear infinite;
    transform-origin: 50% 50%;
}

/* Offline: the poll cannot reach the server, so nothing is progressing and
   the mark must stop claiming otherwise. Applied by wire:offline.class. */
.ariana-working-mark--stalled svg,
.ariana-working--stalled .fi-section-header-icon svg {
    animation: none;
    opacity: .4;
}

.ariana-working-offline {
    display: inline-flex;
    align-items: center;
    gap: .35rem;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    color: #D97706;
}

@media (prefers-reduced-motion: reduce) {
    .ariana-working-mark svg,
    .ariana-working .fi-section-header-icon svg,
    .ariana-working .fi-icon svg {
        animation: ariana-working-pulse 1.8s ease-in-out infinite;
    }
}

/* ---------------------------------------------------------------------------
 * Site health (System → Site health) — one glanceable table.
 *
 * The first version stacked seven Filament sections and read as a wall of
 * prose; the owner's verdict was that a person should see what is fine and
 * what is broken in one look, with the remedy unmistakable. So: a table with
 * a colour-coded status column, problems sorted first, and each remedy in
 * its own tinted "How to fix" strip under its row — steps numbered, the cron
 * line rendered exactly once as selectable code.
 *
 * Everything is drawn with the --ar-* semantic tokens above, so both modes
 * come for free; the status tints are color-mix washes of the ink tokens so
 * no literal hex can drift out of the palette. Logical properties for RTL.
 * ------------------------------------------------------------------------- */
.ariana-health__summary {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: .5rem;
    margin-block-end: 1rem;
}

.ariana-health__summary-actions {
    display: flex;
    gap: .5rem;
    margin-inline-start: auto;
}

/* ---- Site health: page status (the UrlAudit tiles and their modals) ---- */

.ariana-audit { margin-block-end: 1.5rem; }

.ariana-audit__tiles {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(7.5rem, 1fr));
    gap: .75rem;
}

/* Filament wraps a modal's trigger in its own div, so the button has to
   be told to fill the grid cell — or the clickable tiles come out narrower
   than the plain ones beside them (measured, 1.67.0). */
.ariana-audit__tiles .fi-modal-trigger { display: block; block-size: 100%; }

.ariana-audit__tile {
    display: flex;
    flex-direction: column;
    align-items: flex-start;
    gap: .1rem;
    inline-size: 100%;
    block-size: 100%;
    padding: .8rem .95rem;
    border: 1px solid var(--ar-line);
    border-radius: .75rem;
    background: var(--ar-surface);
    color: var(--ar-ink);
    text-align: start;
    font: inherit;
}

.ariana-audit__tile--opens { cursor: pointer; transition: border-color .15s ease, transform .15s ease; }
.ariana-audit__tile--opens:hover { border-color: var(--ar-ink-mute); transform: translateY(-1px); }

.ariana-audit__count { font-size: var(--ar-fs-title2, 1.375rem); font-weight: 600; line-height: var(--ar-lh-tight, 1.2); }

.ariana-audit__label {
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    letter-spacing: var(--ar-tracking-caps, .03em);
    text-transform: uppercase;
}

.ariana-audit__caption { font-size: var(--ar-fs-footnote, .75rem); color: var(--ar-ink-mute); }

.ariana-audit__tile--quiet .ariana-audit__count,
.ariana-audit__tile--quiet .ariana-audit__label { color: var(--ar-ink-mute); }

.ariana-audit__tile--ok {
    border-color: color-mix(in srgb, var(--ar-success-ink) 45%, transparent);
    background: color-mix(in srgb, var(--ar-success-ink) 7%, var(--ar-surface));
}
.ariana-audit__tile--ok .ariana-audit__count { color: var(--ar-success-ink); }

.ariana-audit__tile--warning {
    border-color: color-mix(in srgb, var(--ar-warning-ink) 45%, transparent);
    background: color-mix(in srgb, var(--ar-warning-ink) 7%, var(--ar-surface));
}
.ariana-audit__tile--warning .ariana-audit__count { color: var(--ar-warning-ink); }

.ariana-audit__tile--problem {
    border-color: color-mix(in srgb, var(--ar-danger-ink) 45%, transparent);
    background: color-mix(in srgb, var(--ar-danger-ink) 7%, var(--ar-surface));
}
.ariana-audit__tile--problem .ariana-audit__count { color: var(--ar-danger-ink); }

.ariana-audit__hint,
.ariana-audit__more {
    margin: .75rem 0 0;
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink-mute);
}

.ariana-audit__codes {
    display: flex;
    flex-wrap: wrap;
    gap: .5rem 1rem;
    margin: 0 0 .75rem;
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink-dim);
}

.ariana-audit__listwrap {
    max-block-size: 60vh;
    overflow: auto;
    border: 1px solid var(--ar-line);
    border-radius: .5rem;
}

.ariana-audit__list {
    width: 100%;
    border-collapse: collapse;
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink);
}

.ariana-audit__list th,
.ariana-audit__list td {
    padding: .45rem .7rem;
    text-align: start;
    border-block-end: 1px solid var(--ar-line);
    vertical-align: top;
}

.ariana-audit__list thead th {
    position: sticky;
    inset-block-start: 0;
    background: var(--ar-surface);
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    color: var(--ar-ink-mute);
}

.ariana-audit__list tbody tr:last-child td { border-block-end: 0; }

.ariana-audit__url { word-break: break-all; direction: ltr; text-align: start; }
.ariana-audit__url a { color: var(--ar-ink); text-decoration: underline; text-underline-offset: 2px; }

/* ---- Site health: the two weekly performance widgets ------------------- */
/* Logical properties throughout for RTL, same as the health table below.   */

.ariana-perf__bar,
.ariana-audit__bar {
    display: flex;
    align-items: center;
    gap: .75rem;
    flex-wrap: wrap;
    margin-block-end: .75rem;
}

.ariana-perf__bar-title,
.ariana-audit__bar-title {
    font-weight: 600;
    color: var(--ar-ink);
}

.ariana-perf__bar-note,
.ariana-audit__bar-note {
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink-mute);
    flex: 1 1 auto;
}

.ariana-perf {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(20rem, 1fr));
    gap: 1rem;
    margin-block-end: 1.5rem;
}

.ariana-perf__card {
    background: var(--ar-surface);
    border: 1px solid var(--ar-line);
    border-radius: .75rem;
    padding: 1rem 1.15rem;
    display: flex;
    flex-direction: column;
    gap: .75rem;
}

.ariana-perf__head {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: .75rem;
}

.ariana-perf__title {
    margin: 0;
    font-size: var(--ar-fs-callout, .9375rem);
    font-weight: 600;
    color: var(--ar-ink);
}

.ariana-perf__link {
    font-size: var(--ar-fs-sub, .8125rem);
    color: var(--ar-ink-dim);
    text-decoration: none;
    white-space: nowrap;
}

.ariana-perf__link:hover { text-decoration: underline; }

.ariana-perf__head-actions {
    display: inline-flex;
    align-items: center;
    gap: .5rem;
}

.ariana-perf__refresh {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    inline-size: 1.6rem;
    block-size: 1.6rem;
    padding: 0;
    border: 1px solid var(--ar-line);
    border-radius: 50%;
    background: transparent;
    color: var(--ar-ink-dim);
    cursor: pointer;
    transition: color .15s ease, border-color .15s ease, transform .15s ease;
}

.ariana-perf__refresh svg {
    inline-size: .85rem;
    block-size: .85rem;
}

.ariana-perf__refresh:hover {
    color: var(--ar-ink);
    border-color: var(--ar-ink-mute);
    transform: rotate(40deg);
}

.ariana-perf__refresh:disabled { opacity: .6; cursor: default; }

/* Queued or running: the icon itself says so. */
.ariana-perf__refresh--busy svg { animation: ariana-perf-spin 1.4s linear infinite; }

@keyframes ariana-perf-spin { to { transform: rotate(360deg); } }

@media (prefers-reduced-motion: reduce) {
    .ariana-perf__refresh--busy svg { animation: none; }
    .ariana-perf__refresh:hover { transform: none; }
}

.ariana-perf__scores {
    display: flex;
    align-items: center;
    gap: 1.1rem;
    flex-wrap: wrap;
}

.ariana-perf__score {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: .3rem;
}

.ariana-perf__ring {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    inline-size: 3.25rem;
    block-size: 3.25rem;
    border-radius: 50%;
    border: 3px solid var(--ar-line);
    font-size: var(--ar-fs-title3, 1.0625rem);
    font-weight: 600;
    color: var(--ar-ink);
}

.ariana-perf__ring--good {
    color: var(--ar-success-ink);
    border-color: color-mix(in srgb, var(--ar-success-ink) 55%, transparent);
    background: color-mix(in srgb, var(--ar-success-ink) 8%, transparent);
}

.ariana-perf__ring--meh {
    color: var(--ar-warning-ink);
    border-color: color-mix(in srgb, var(--ar-warning-ink) 55%, transparent);
    background: color-mix(in srgb, var(--ar-warning-ink) 8%, transparent);
}

.ariana-perf__ring--poor {
    color: var(--ar-danger-ink);
    border-color: color-mix(in srgb, var(--ar-danger-ink) 55%, transparent);
    background: color-mix(in srgb, var(--ar-danger-ink) 8%, transparent);
}

.ariana-perf__score-label {
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    color: var(--ar-ink-mute);
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
}

.ariana-perf__metrics {
    display: flex;
    gap: 1rem;
    margin: 0;
    margin-inline-start: auto;
}

.ariana-perf__metrics div { text-align: center; }

.ariana-perf__metrics dt {
    font-size: var(--ar-fs-caption, .6875rem);
    font-weight: 600;
    letter-spacing: var(--ar-tracking-caps, .03em);
    color: var(--ar-ink-mute);
}

.ariana-perf__metrics dd {
    margin: .1rem 0 0;
    font-size: var(--ar-fs-body, .875rem);
    font-weight: 600;
    color: var(--ar-ink-dim);
    font-variant-numeric: tabular-nums;
}

.ariana-perf__meta {
    margin: 0;
    font-size: var(--ar-fs-footnote, .75rem);
    color: var(--ar-ink-mute);
}

.ariana-perf__empty {
    margin: 0;
    font-size: var(--ar-fs-body, .875rem);
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-ink-mute);
}

.ariana-perf__error {
    margin: 0;
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-text, 1.45);
    color: var(--ar-danger-ink);
    background: color-mix(in srgb, var(--ar-danger-ink) 7%, transparent);
    border-radius: .5rem;
    padding: .45rem .6rem;
}

.ariana-health__pill {
    display: inline-flex;
    align-items: center;
    font-size: var(--ar-fs-sub, .8125rem);
    font-weight: 600;
    padding: .3rem .75rem;
    border-radius: 999px;
    border: 1px solid transparent;
}

.ariana-health__pill--problem {
    color: var(--ar-danger-ink);
    background: color-mix(in srgb, var(--ar-danger-ink) 10%, transparent);
    border-color: color-mix(in srgb, var(--ar-danger-ink) 25%, transparent);
}

.ariana-health__pill--warning {
    color: var(--ar-warning-ink);
    background: color-mix(in srgb, var(--ar-warning-ink) 10%, transparent);
    border-color: color-mix(in srgb, var(--ar-warning-ink) 25%, transparent);
}

.ariana-health__pill--ok {
    color: var(--ar-success-ink);
    background: color-mix(in srgb, var(--ar-success-ink) 10%, transparent);
    border-color: color-mix(in srgb, var(--ar-success-ink) 25%, transparent);
}

.ariana-health__tablewrap {
    background: var(--ar-surface);
    border: 1px solid var(--ar-line);
    border-radius: .75rem;
    overflow: hidden;
}

.ariana-health__table {
    width: 100%;
    border-collapse: collapse;
    font-size: var(--ar-fs-body, .875rem);
    color: var(--ar-ink);
}

.ariana-health__table thead th {
    text-align: start;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    color: var(--ar-ink-mute);
    background: var(--ar-sunken);
    padding: .6rem 1rem;
    border-block-end: 1px solid var(--ar-line);
}

.ariana-health__col-status { inline-size: 8.5rem; }
.ariana-health__col-name   { inline-size: 13rem; }

.ariana-health__row > td,
.ariana-health__row > th {
    padding: .8rem 1rem;
    border-block-start: 1px solid var(--ar-line);
    vertical-align: top;
}

.ariana-health__row:first-child > td,
.ariana-health__row:first-child > th { border-block-start: 0; }

.ariana-health__name {
    text-align: start;
    font-weight: 600;
    white-space: nowrap;
}

.ariana-health__detail {
    color: var(--ar-ink-dim);
    line-height: var(--ar-lh-text, 1.45);
    white-space: pre-line; /* detail may carry deliberate line breaks */
}

.ariana-health__badge {
    display: inline-flex;
    align-items: center;
    gap: .4rem;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    padding: .25rem .6rem;
    border-radius: 999px;
    white-space: nowrap;
}

.ariana-health__dot {
    inline-size: .45rem;
    block-size: .45rem;
    border-radius: 999px;
    background: currentColor;
}

.ariana-health__badge--ok {
    color: var(--ar-success-ink);
    background: color-mix(in srgb, var(--ar-success-ink) 12%, transparent);
}

.ariana-health__badge--warning {
    color: var(--ar-warning-ink);
    background: color-mix(in srgb, var(--ar-warning-ink) 12%, transparent);
}

.ariana-health__badge--problem {
    color: var(--ar-danger-ink);
    background: color-mix(in srgb, var(--ar-danger-ink) 12%, transparent);
}

/* The remedy strip: visually attached to its row by the shared tint and an
   accent edge on the reading side. */
.ariana-health__fixrow > td { padding: 0; border-block-start: 0; }

.ariana-health__fix {
    margin: 0 1rem .9rem;
    padding: .75rem .9rem;
    border-radius: .5rem;
    border-inline-start: 3px solid currentColor;
}

.ariana-health__fixrow--problem .ariana-health__fix {
    color: var(--ar-danger-ink);
    background: color-mix(in srgb, var(--ar-danger-ink) 7%, transparent);
}

.ariana-health__fixrow--warning .ariana-health__fix {
    color: var(--ar-warning-ink);
    background: color-mix(in srgb, var(--ar-warning-ink) 8%, transparent);
}

.ariana-health__fix-title {
    display: block;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    margin-block-end: .35rem;
}

.ariana-health__fix-body {
    margin: 0;
    color: var(--ar-ink-dim);
    line-height: var(--ar-lh-text, 1.45);
    white-space: pre-line; /* the numbered steps arrive as \n lines */
}

.ariana-health__code {
    margin-block-start: .6rem;
    padding: .6rem .75rem;
    border-radius: .45rem;
    background: var(--ar-sunken);
    border: 1px solid var(--ar-line);
    color: var(--ar-ink);
    font-size: var(--ar-fs-footnote, .75rem);
    line-height: var(--ar-lh-text, 1.45);
    overflow-x: auto;
    direction: ltr;        /* a shell command is LTR even on an RTL panel */
    text-align: left;
    user-select: all;      /* one click selects the whole line to copy */
}

/* Narrow screens: the table becomes stacked cards. Each row keeps its badge
   beside the check name; the detail flows underneath at full width. */
@media (max-width: 640px) {
    .ariana-health__table thead { display: none; }

    .ariana-health__row {
        display: grid;
        grid-template-columns: 1fr auto;
        gap: .15rem .75rem;
        padding: .8rem 1rem;
        border-block-start: 1px solid var(--ar-line);
    }

    .ariana-health__row:first-child { border-block-start: 0; }

    .ariana-health__row > td,
    .ariana-health__row > th {
        display: block;
        padding: 0;
        border: 0;
    }

    .ariana-health__name   { order: 1; white-space: normal; }
    .ariana-health__status { order: 2; justify-self: end; }
    .ariana-health__detail { order: 3; grid-column: 1 / -1; margin-block-start: .25rem; }

    .ariana-health__fixrow { display: block; }
    .ariana-health__fixrow > td { display: block; }
    .ariana-health__fix { margin: 0 .75rem .8rem; }

    .ariana-health__summary-actions {
        margin-inline-start: 0;
        inline-size: 100%;
    }
}

/* Labels over the health page's code blocks: which artifact is which.
   Added when "paste the line" sent five schedule stars into cPanel's
   Command field — the two blocks must announce their destination. */
.ariana-health__code-label {
    display: block;
    margin-block-start: .6rem;
    font-size: var(--ar-fs-footnote, .75rem);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: var(--ar-tracking-caps, .03em);
    color: var(--ar-ink-mute);
}

.ariana-health__code--muted { opacity: .72; }

/* ===========================================================================
   Filament's components, on the type scale (invariant 264).

   Filament sets its own sizes and weights — a 30 px page title at 620 with
   -0.025em tracking, bold table titles, 520 buttons, badges tracked at
   -0.05em. These are the places an operator reads all day, so they are
   brought onto the same eight sizes and three weights as Ariana's own
   components. `.fi-body` in front is the specificity that beats Filament's
   single-class rules wherever the two files sit in <head>; tracking is
   `normal` because San Francisco tracks itself and Inter's tracking arrives
   from the provider for the machines that use Inter.
   ======================================================================== */

/* 1.3, not the tight 1.2: a page title is usually the RECORD's title, and on a
   Persian site that is "Edit <a Persian headline>" — a left-to-right line
   (it starts with "Edit", so :dir(rtl) never sees it) that wraps to two lines
   of Vazirmatn Bold. At 1.2 the marks of the second line touch the first. */
.fi-body .fi-header-heading {
    font-size: var(--ar-fs-title1);
    font-weight: 600;
    line-height: 1.3;
    letter-spacing: normal;
}

.fi-body .fi-header-subheading {
    font-size: var(--ar-fs-callout);
    font-weight: 400;
    line-height: var(--ar-lh-text);
}

.fi-body .fi-section-header-heading,
.fi-body .fi-modal-heading,
.fi-body .fi-ta-header-heading {
    font-size: var(--ar-fs-title3);
    font-weight: 600;
    line-height: var(--ar-lh-tight);
    letter-spacing: normal;
}

.fi-body .fi-section-header-description,
.fi-body .fi-modal-description,
.fi-body .fi-ta-header-description,
.fi-body .fi-fo-field-wrp-helper-text,
.fi-body .fi-sc-text {
    font-size: var(--ar-fs-sub);
    font-weight: 400;
    line-height: var(--ar-lh-text);
}

.fi-body .fi-fo-field-wrp-label,
.fi-body .fi-fo-field-label-content {
    font-size: var(--ar-fs-body);
    font-weight: 500;
    line-height: var(--ar-lh-ui);
}

/* The sidebar is read from further away than anything else on the page and
   all day long: 14 px, not macOS's 13 pt — a Mac's sidebar is a hand's width
   from the content it lists, a web panel's is across a 27-inch window (field
   report, 1.72.5: "too small, lost its readability"). A group heading is a
   ROW here — collapsed, the headings are the whole navigation — so it is set
   like one: the item's size, semibold, sentence case, the secondary ink, and
   never faded (invariant 266). */
.fi-body .fi-sidebar-item-label {
    font-size: var(--ar-fs-body);
    font-weight: 500;
    line-height: var(--ar-lh-ui);
}

.fi-body .fi-sidebar-group-label {
    font-size: var(--ar-fs-body);
    font-weight: 600;
    letter-spacing: normal;
    text-transform: none;
    color: var(--ar-ink-dim);
    opacity: 1;
}

.fi-body .fi-btn {
    font-size: var(--ar-fs-body);
    font-weight: 500;
    letter-spacing: normal;
}

.fi-body .fi-badge {
    font-size: var(--ar-fs-footnote);
    font-weight: 500;
    letter-spacing: normal;
}

.fi-body .fi-ta-header-cell,
.fi-body .fi-ta-header-cell-label {
    font-size: var(--ar-fs-footnote);
    font-weight: 600;
    letter-spacing: normal;
    text-transform: none;
}

.fi-body .fi-ta-cell,
.fi-body .fi-ta-text-item-label {
    font-size: var(--ar-fs-body);
    line-height: var(--ar-lh-ui);
}

/* A table's title column was 700. macOS lists set the primary line in
   medium; Persian then lands on Vazirmatn Medium instead of its Bold, which
   is far too heavy for a row of thirty titles. */
.fi-body .fi-ta-cell,
.fi-body .fi-ta-text-item-label,
.fi-body .fi-ta-text-item {
    font-weight: 500;
}

.fi-body .fi-tabs-item-label,
.fi-body .fi-dropdown-list-item-label {
    font-size: var(--ar-fs-body);
    font-weight: 500;
}

.fi-body .fi-pagination-overview,
.fi-body .fi-breadcrumbs-item-label,
.fi-body .fi-link {
    font-size: var(--ar-fs-sub);
    font-weight: 500;
}

/* What is typed is read as closely as what is printed. 14 px on a pointer
   device; the 16 px mobile rule above still wins where iOS would zoom. */
@media (hover: hover) and (pointer: fine) {
    .fi-body .fi-input,
    .fi-body .fi-select-input,
    .fi-body .fi-fo-textarea textarea {
        font-size: var(--ar-fs-body);
    }
}

.fi-body .fi-wi-stats-overview-stat-label {
    font-size: var(--ar-fs-sub);
    font-weight: 500;
}

.fi-body .fi-wi-stats-overview-stat-value {
    font-size: var(--ar-fs-title1);
    font-weight: 600;
    line-height: var(--ar-lh-tight);
    letter-spacing: normal;
}

.fi-body .fi-wi-stats-overview-stat-description {
    font-size: var(--ar-fs-footnote);
    font-weight: 400;
    line-height: var(--ar-lh-text);
    align-items: flex-start;
}

.fi-body .fi-no-notification-title,
.fi-body .fi-in-entry-label {
    font-size: var(--ar-fs-sub);
    font-weight: 600;
}

.fi-body .fi-no-notification-body {
    font-size: var(--ar-fs-sub);
    line-height: var(--ar-lh-text);
}

/* ===========================================================================
   Liquid Glass — the navigation layer (invariant 265)

   macOS 26 introduced the material and macOS 27 "Golden Gate" corrected it:
   less transparency by default, darker edges, brighter highlights, and a
   continuous bar under the controls when content scrolls beneath them. The
   rules Apple gives for it are the ones kept here:

   - Glass is for the layer that FLOATS — the top bar, the sidebar, tab
     strips, menus, notifications, dialogs. Never for content: cards, tables,
     forms and lists stay solid, because content is what the glass exists to
     let through, and text on a moving backdrop is not readable.
   - Glass never samples glass. The material sits on the OUTER element of
     each bar; everything inside it is transparent.
   - It needs something to sample. The page carries a fixed ambient wash
     (`--ar-ambient`) behind everything, so the material has colour to bend
     even over an empty page.
   - The user's settings win. "Reduce transparency" and "Increase contrast"
     turn every glass surface into the solid one it replaced, and a browser
     without backdrop-filter never gets the translucent tint at all.

   Cost: backdrop-filter runs on a handful of fixed elements, never on a
   list item and never animated.
   ======================================================================== */

/* The ambient wash. A fixed pseudo-element, not background-attachment: fixed,
   which repaints the whole page on every scroll frame. */
.fi-body::before {
    content: '';
    position: fixed;
    inset: 0;
    z-index: -1;
    pointer-events: none;
    background-image: var(--ar-ambient);
}

/* The main column painted a solid canvas over the body; the wash has to show. */
.dark .fi-main-ctn,
:root:not(.dark) .fi-main-ctn {
    background-color: transparent !important;
}

@supports ((backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px))) {
    /* ---- the top bar: Golden Gate's continuous bar ----------------------- */
    .dark .fi-topbar,
    :root:not(.dark) .fi-topbar {
        background-color: var(--ar-glass-bg) !important;
        -webkit-backdrop-filter: blur(24px) saturate(180%);
        backdrop-filter: blur(24px) saturate(180%);
        border-bottom: 1px solid var(--ar-glass-edge) !important;
        box-shadow: inset 0 1px 0 0 var(--ar-glass-rim), 0 10px 30px -18px rgba(0, 0, 0, .45);
    }

    .dark .fi-topbar > nav,
    .dark .fi-topbar nav.fi-topbar-nav,
    :root:not(.dark) .fi-topbar > nav,
    :root:not(.dark) .fi-topbar nav.fi-topbar-nav {
        background-color: transparent !important;
        border-bottom: 0 !important;
        box-shadow: none;
    }

    /* ---- the sidebar ------------------------------------------------------ */
    .dark .fi-sidebar,
    :root:not(.dark) .fi-sidebar {
        background-color: var(--ar-glass-bg) !important;
        -webkit-backdrop-filter: blur(28px) saturate(180%);
        backdrop-filter: blur(28px) saturate(180%);
        border-inline-end: 1px solid var(--ar-glass-edge) !important;
        box-shadow: inset -1px 0 0 0 var(--ar-glass-rim);
    }

    .dark .fi-sidebar-header,
    .dark .fi-sidebar-nav,
    :root:not(.dark) .fi-sidebar-header,
    :root:not(.dark) .fi-sidebar-nav {
        background-color: transparent !important;
    }

    /* ---- what opens above the page ---------------------------------------- */
    /* A notification is glass only when it FLOATS — a toast. The same
       component is printed `fi-inline` inside the notifications panel, which
       is itself a glass sheet: there it is a row of content, and glass on
       glass gave every row its own border, corner and shadow under the
       panel's header — "a message on top of a message" (field report,
       1.72.11). */
    .fi-body .fi-dropdown-panel,
    .fi-body .fi-no-notification:not(.fi-inline),
    .fi-body .fi-global-search-results-ctn {
        background-color: var(--ar-glass-bg-thick) !important;
        -webkit-backdrop-filter: blur(24px) saturate(180%);
        backdrop-filter: blur(24px) saturate(180%);
        border: 1px solid var(--ar-glass-edge) !important;
        box-shadow: inset 0 1px 0 0 var(--ar-glass-rim), var(--ar-glass-shadow) !important;
        border-radius: 14px;
    }

    /* A dialog carries a form, so it takes the THICK material: the page stays
       a presence behind it, never a pattern under the text. */
    .fi-body .fi-modal-window {
        background-color: var(--ar-glass-bg-thick) !important;
        -webkit-backdrop-filter: blur(30px) saturate(180%);
        backdrop-filter: blur(30px) saturate(180%);
        border: 1px solid var(--ar-glass-edge);
        box-shadow: inset 0 1px 0 0 var(--ar-glass-rim), var(--ar-glass-shadow);
    }
}

/* The user's settings win over the material. */
@media (prefers-reduced-transparency: reduce), (prefers-contrast: more) {
    .fi-body::before {
        display: none;
    }

    .dark .fi-topbar,
    .dark .fi-sidebar,
    .dark .fi-body .fi-dropdown-panel,
    .dark .fi-body .fi-no-notification:not(.fi-inline),
    .dark .fi-body .fi-global-search-results-ctn,
    .dark .fi-body .fi-modal-window,
    :root:not(.dark) .fi-topbar,
    :root:not(.dark) .fi-sidebar,
    :root:not(.dark) .fi-body .fi-dropdown-panel,
    :root:not(.dark) .fi-body .fi-no-notification:not(.fi-inline),
    :root:not(.dark) .fi-body .fi-global-search-results-ctn,
    :root:not(.dark) .fi-body .fi-modal-window {
        background-color: var(--ar-surface) !important;
        -webkit-backdrop-filter: none;
        backdrop-filter: none;
        border-color: var(--ar-line-strong) !important;
    }
}

/* The scroll edge effect: content softens where it meets the bar instead of
   colliding with its edge (HIG, Liquid Glass). A short fade of the canvas
   colour under the top bar; it carries no pointer events and no blur. */
.fi-body .fi-topbar {
    position: relative;
}

.fi-body .fi-topbar::after {
    content: '';
    position: absolute;
    inset-inline: 0;
    top: 100%;
    height: 14px;
    pointer-events: none;
    background: linear-gradient(to bottom, color-mix(in srgb, var(--ar-canvas) 55%, transparent), transparent);
}

/* Increase Contrast: the HIG asks for a variant with "a significantly higher
   amount of visual differentiation", not only solid bars. Secondary ink steps
   up to the primary-dim, hairlines to the strong line. */
@media (prefers-contrast: more) {
    :root,
    .dark {
        --ar-ink-mute: var(--ar-ink-dim);
        --ar-line: var(--ar-line-strong);
    }

    .fi-body .fi-topbar::after {
        display: none;
    }
}

/* ---- Golden Gate's shapes ------------------------------------------------
   Larger, continuous corners, concentric from the outside in: a card is 16,
   what sits inside it 12 or 10, a control 10, a chip a capsule. */
.fi-body .fi-section:not(.fi-section-not-contained),
.fi-body .fi-ta-ctn,
.fi-body .fi-wi-stats-overview-stat {
    border-radius: 16px;
}

.fi-body .fi-input-wrp,
.fi-body .fi-btn {
    border-radius: 10px;
}

.fi-body .fi-badge {
    border-radius: 999px;
}

/* ===========================================================================
   The Golden Gate pass (invariant 266)

   1.72.4–1.72.7 changed the panel a piece at a time and the owner sent each one
   back. This block is the whole-panel pass that followed: every page, dark
   and light, MEASURED — computed size and the contrast of every text node
   against its real background — and then looked at beside macOS 27's own
   System Settings. Three findings drove it:

   - "Too small" was mostly "too dim". The sizes were macOS's; the inks were
     not. macOS sets nearly everything in the primary label colour; Ariana set
     most things in a muted violet on violet, and one rule multiplied that by
     opacity .55 (the sidebar's group headings measured 2.81:1).
   - Dark glass over a flat dark canvas is invisible. The material only reads
     when there is colour behind it, which is what a desktop wallpaper does
     for a Mac window. The ambient wash is now strong where the glass is —
     along the leading and top edges — and the sidebar floats over it as an
     inset, rounded panel, as macOS 26–27 draws it.
   - Content cards are not glass, but they are not slabs either: a slightly
     translucent surface with a hairline and an inner highlight lets the
     wash tint them without ever putting moving content under text.
   ======================================================================== */

/* Everything in the panel is rem-based — Filament's utilities, the type
   scale, the spacing — so the root is the one lever that enlarges ALL of it
   in proportion, on every page, including the ones no rule here names.
   106.25% makes the 14 px reading size 14.9 px and the 13 px secondary 13.8:
   the sizes Apple's own web apps use, where macOS's 13 pt assumes a laptop at
   arm's length. The 16 px mobile input stays a literal 16 px. */
html {
    font-size: 106.25%;
}

/* ---- the sidebar: an inset glass panel ----------------------------------
   One geometry, stated once. The panel's corner is R and everything inside it
   keeps a gap G from its edge, so a row's corner is R − G: concentric, the way
   macOS nests a selection inside a sidebar. 1.72.8 had R = 20, a 12 px gap on
   the left, 12 + an 11 px scrollbar gutter on the right and 10 px row corners
   — three numbers that agreed with nothing, which is exactly what the owner
   saw: a highlight that sat off-centre with corners that fought the panel's,
   and a scrollbar sliced by the rounded corner (field report, 1.72.8).

   The gap is PADDING ON THE PANEL, not on the scrolling list, so the list's
   box — and any scrollbar it shows — begins G inside the curve. */
.fi-body .fi-sidebar.fi-main-sidebar {
    --ar-sb-radius: 20px;
    --ar-sb-gap: 8px;
    /* R − G − the 1 px border the gap is measured inside of = 11 px */
    --ar-sb-row-radius: calc(var(--ar-sb-radius) - var(--ar-sb-gap) - 1px);
}

@media (min-width: 1024px) {
    .fi-body .fi-sidebar.fi-main-sidebar {
        margin-block: .625rem;
        margin-inline-start: .625rem;
        top: calc(4rem + .625rem);
        height: calc(100dvh - 4rem - 1.25rem);
        padding: var(--ar-sb-gap);
        border-radius: var(--ar-sb-radius);
        border: 1px solid var(--ar-glass-edge) !important;
        box-shadow: inset 0 1px 0 0 var(--ar-glass-rim), var(--ar-glass-shadow);
        overflow: hidden;
        position: sticky;
    }
}

.fi-body .fi-sidebar-nav {
    padding: 0;
    gap: .5rem;
    /* Where the overlay thumb below is not available, the scrollbar is a thin
       one with a gutter on BOTH sides, so the rows stay centred. */
    scrollbar-width: thin;
    scrollbar-gutter: stable both-edges;
}

@media (max-width: 1023.98px) {
    .fi-body .fi-sidebar-nav {
        padding: var(--ar-sb-gap);
    }
}

/* No native scrollbar. The list is long — every group is open unless the
   person closed it (invariant 268) — and inside a rounded glass panel a native
   bar is cut by the corner and takes a column out of the rows. 1.72.9 drew a
   thumb in CSS, but a stylesheet cannot know how long the list is, so its
   length meant nothing. panel-sidebar.js draws the thumb instead: its LENGTH
   is the visible share of the list and its POSITION the scroll position, it
   lives in the panel's gap clear of the corners, and it shows only while the
   list scrolls or the pointer is over the sidebar. The list's top and bottom
   edges also FADE where rows continue — scroll-driven, so a list that fits
   has no fade. Browsers without scroll-driven animation keep the thin native
   scrollbar and get no drawn thumb. */
@property --ar-sb-fade-top {
    syntax: '<length>';
    inherits: false;
    initial-value: 0px;
}

@property --ar-sb-fade-bottom {
    syntax: '<length>';
    inherits: false;
    initial-value: 0px;
}

@supports (animation-timeline: scroll()) {
    .fi-body .fi-sidebar-nav {
        scrollbar-width: none;
        scrollbar-gutter: auto;
        -webkit-mask-image: linear-gradient(to bottom, transparent 0, #000 var(--ar-sb-fade-top), #000 calc(100% - var(--ar-sb-fade-bottom)), transparent 100%);
        mask-image: linear-gradient(to bottom, transparent 0, #000 var(--ar-sb-fade-top), #000 calc(100% - var(--ar-sb-fade-bottom)), transparent 100%);
        animation: ar-sb-fades linear both;
        animation-timeline: scroll(self block);
    }

    .fi-body .fi-sidebar-nav::-webkit-scrollbar {
        display: none;
    }

    .fi-body .fi-sidebar.fi-main-sidebar > .ariana-sb-thumb {
        position: absolute;
        top: 0;
        inset-inline-end: 2px;
        width: 4px;
        border-radius: 999px;
        background: color-mix(in srgb, var(--ar-ink) 38%, transparent);
        opacity: 0;
        pointer-events: none;
        transition: opacity .25s ease;
        will-change: transform;
    }

    .fi-body .fi-sidebar.fi-main-sidebar > .ariana-sb-thumb.is-visible {
        opacity: 1;
    }

    @keyframes ar-sb-fades {
        0%   { --ar-sb-fade-top: 0px;  --ar-sb-fade-bottom: 36px; }
        6%   { --ar-sb-fade-top: 36px; --ar-sb-fade-bottom: 36px; }
        94%  { --ar-sb-fade-top: 36px; --ar-sb-fade-bottom: 36px; }
        100% { --ar-sb-fade-top: 36px; --ar-sb-fade-bottom: 0px; }
    }
}

/* Without scroll-driven animation the native scrollbar is there: no drawn one. */
.fi-body .ariana-sb-thumb {
    display: none;
}

@supports (animation-timeline: scroll()) {
    .fi-body .fi-sidebar.fi-main-sidebar > .ariana-sb-thumb {
        display: block;
    }
}

/* A group opening and closing: quick, and not at all for someone who asked
   for less motion. */
.fi-body .fi-sidebar-group-collapse-btn .fi-icon,
.fi-body .fi-sidebar-group-btn .fi-icon-btn .fi-icon {
    transition: transform .18s ease;
}

@media (prefers-reduced-motion: reduce) {
    .fi-body .fi-sidebar-group-collapse-btn .fi-icon,
    .fi-body .fi-sidebar-group-btn .fi-icon-btn .fi-icon {
        transition: none;
    }
}

/* Rows: 36 px tall (a 28 px macOS row, scaled for a pointer AND a finger),
   corners concentric with the panel, the primary ink. A group heading is a
   ROW here — collapsed, the headings are the whole navigation — so it reads
   like one: the same size as an item, semibold, in the secondary ink, never
   faded. */
.fi-body .fi-sidebar-item-btn,
.fi-body .fi-sidebar-group-btn,
.fi-body .fi-sidebar-group-dropdown-trigger-btn {
    min-height: 2.125rem;
    padding: .3rem .625rem;
    border-radius: var(--ar-sb-row-radius, 11px);
    gap: .7rem;
}

.fi-body .fi-sidebar-group-items {
    gap: 2px;
    padding-block-end: .375rem;
}

/* Groups are open by default, so each is a short list with its own heading:
   a little air between them, none wasted. */
.fi-body .fi-sidebar-nav-groups {
    gap: .5rem;
}

/* Filament pulls the group list 8 px OUT on both sides (-mx-2) so that a row's
   text lines up with the nav's old 24 px padding. Inside the panel that margin
   cancelled the gap exactly: the highlight ran to the panel's edge and its
   corner was cut by the panel's curve. The gap is the panel's padding now, and
   nothing reaches across it. */
.fi-body .fi-sidebar-nav-groups {
    margin-inline: 0;
}

.fi-body .fi-sidebar-item-label {
    color: var(--ar-ink);
}

.fi-body .fi-sidebar-group-btn .fi-icon,
.fi-body .fi-sidebar-item-btn .fi-icon {
    color: var(--ar-accent-ink);
}

.fi-body .fi-sidebar-group-collapse-btn .fi-icon,
.fi-body .fi-sidebar-group-btn > .fi-icon-btn .fi-icon {
    color: var(--ar-ink-mute);
}

.fi-body .fi-sidebar-item-btn:hover,
.fi-body .fi-sidebar-group-btn:hover,
.fi-body .fi-sidebar-group-dropdown-trigger-btn:hover {
    background-color: color-mix(in srgb, var(--ar-ink) 7%, transparent) !important;
}

.fi-body .fi-sidebar-item.fi-active > .fi-sidebar-item-btn,
.fi-body .fi-sidebar-item-active > .fi-sidebar-item-btn {
    background-color: color-mix(in srgb, var(--ar-accent) 26%, transparent) !important;
    box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--ar-accent) 34%, transparent);
}

.fi-body .fi-sidebar-item.fi-active .fi-sidebar-item-label,
.fi-body .fi-sidebar-item-active .fi-sidebar-item-label {
    color: var(--ar-ink) !important;
    font-weight: 600;
}

/* ---- content cards: tinted by the wash, never glass ---------------------- */
.dark .fi-body .fi-section:not(.fi-section-not-contained),
.dark .fi-body .fi-ta-ctn,
.dark .fi-body .fi-wi-stats-overview-stat {
    background-color: color-mix(in srgb, var(--ar-surface) 82%, transparent) !important;
    border: 1px solid rgba(255, 255, 255, .075) !important;
    box-shadow: inset 0 1px 0 0 rgba(255, 255, 255, .055), 0 12px 32px -18px rgba(0, 0, 0, .7) !important;
}

:root:not(.dark) .fi-body .fi-section:not(.fi-section-not-contained),
:root:not(.dark) .fi-body .fi-ta-ctn,
:root:not(.dark) .fi-body .fi-wi-stats-overview-stat {
    background-color: color-mix(in srgb, var(--ar-surface) 88%, transparent) !important;
    border: 1px solid rgba(60, 45, 120, .09) !important;
    box-shadow: inset 0 1px 0 0 rgba(255, 255, 255, .9), 0 10px 28px -18px rgba(40, 25, 110, .28) !important;
}

/* ---- text roles Filament colours with its grey scale ---------------------
   Headings and values take the primary ink; descriptions, helper text and
   placeholders the secondary or tertiary — never a grey chosen for a grey
   panel. */
.fi-body .fi-header-heading,
.fi-body .fi-section-header-heading,
.fi-body .fi-modal-heading,
.fi-body .fi-ta-header-heading,
.fi-body .fi-wi-stats-overview-stat-value,
.fi-body .fi-ta-text-item,
.fi-body .fi-fo-field-label-content,
.fi-body .fi-in-entry-label {
    color: var(--ar-ink);
}

.fi-body .fi-header-subheading,
.fi-body .fi-section-header-description,
.fi-body .fi-modal-description,
.fi-body .fi-ta-header-description,
.fi-body .fi-wi-stats-overview-stat-label,
.fi-body .fi-ta-header-cell,
.fi-body .fi-ta-header-cell-label,
.fi-body .fi-breadcrumbs-item-label,
.fi-body .fi-pagination-overview {
    color: var(--ar-ink-dim);
}

.fi-body .fi-wi-stats-overview-stat-description,
.fi-body .fi-input::placeholder,
.fi-body .fi-fo-textarea textarea::placeholder {
    color: var(--ar-ink-mute);
}

/* The version line under every page was 11.2 px at half opacity. */
.fi-body .fi-main-ctn > div[style*="opacity"] {
    font-size: var(--ar-fs-footnote) !important;
    opacity: .8 !important;
    color: var(--ar-ink-mute);
}

/* A filled primary button. Filament picks the shade for its fill by its own
   contrast rule and lands on a violet where a white label measures 4.21:1
   (dark) — and its palette generator normalises lightness per shade, so a
   different brand hex changes nothing. The fill is stated instead: the same
   violet at 5.06:1, in both modes. Outlined and link buttons carry no
   fi-bg-color-* class and are untouched. */
.fi-body .fi-btn.fi-color-primary[class*="fi-bg-color-"] {
    background-color: var(--ar-accent-fill) !important;
    color: #fff !important;
}

.fi-body .fi-btn.fi-color-primary[class*="fi-bg-color-"]:hover {
    background-color: var(--ar-accent-fill-hover) !important;
}

/* The destructive button in dark mode: Filament's danger-600 under white text
   is 4.32:1. Light mode keeps Filament's dark ink on the pale red. */
.dark .fi-btn.fi-color-danger[class*="fi-bg-color-"] {
    background-color: var(--ar-danger-fill) !important;
}

.dark .fi-btn.fi-color-danger[class*="fi-bg-color-"]:hover {
    background-color: var(--ar-danger-fill-hover) !important;
}

/* The same for the other status buttons (1.73.0). The page crawl never saw
   them: Retry on About, Run now and Resume on Backup, Continue on the
   importer and the repairs on Site health only exist in a state — a failed
   step, a stalled run. In dark mode each is white on Filament's 600 shade
   (success 3.68:1, info 4.07, warning 4.17); in light mode success is its
   900 ink on the 400 fill, 4.37. */
.dark .fi-btn.fi-color-success[class*="fi-bg-color-"] {
    background-color: var(--ar-success-fill) !important;
}

.dark .fi-btn.fi-color-success[class*="fi-bg-color-"]:hover {
    background-color: var(--ar-success-fill-hover) !important;
}

.dark .fi-btn.fi-color-info[class*="fi-bg-color-"] {
    background-color: var(--ar-info-fill) !important;
}

.dark .fi-btn.fi-color-info[class*="fi-bg-color-"]:hover {
    background-color: var(--ar-info-fill-hover) !important;
}

.dark .fi-btn.fi-color-warning[class*="fi-bg-color-"] {
    background-color: var(--ar-warning-fill) !important;
}

.dark .fi-btn.fi-color-warning[class*="fi-bg-color-"]:hover {
    background-color: var(--ar-warning-fill-hover) !important;
}

:root:not(.dark) .fi-btn.fi-color-success[class*="fi-bg-color-"] {
    color: var(--color-950) !important;   /* 6.87:1 on the 400 fill */
}

/* The chips of a multiple select: Filament's select.js writes the 600 shade
   for their label where every other badge takes 700 — 3.93:1 for the brand
   violet on the chip's pale fill in light mode. */
:root:not(.dark) .fi-body .fi-select-input-value-badges-ctn .fi-badge.fi-color {
    --text: var(--color-700);
}

/* A plain text button — Reset in a table's filters and columns, Select all
   and Deselect all on the selection bar — measured 19.72 px tall. The action
   links already have their 24 px target (below); these are Filament's bare
   link component, a <button>, with no action wrapper. Inline links in a
   sentence (an <a>) are exempt, as everywhere. */
.fi-body button.fi-link {
    min-height: 1.5rem;
}

/* The sign-in card is Filament's gray-900, lighter than the panel the muted
   ink was measured on: the captcha's hint read 4.28:1 there in dark mode. */
.dark .fi-simple-main .fi-sc-text,
.dark .fi-simple-main .fi-fo-field-wrp-helper-text {
    color: var(--ar-ink-dim);
}

/* Pointer targets: macOS's minimum is 20 × 20. Filament's checkbox and the
   little "clear" button inside a select measured 17. */
.fi-body .fi-checkbox-input,
.fi-body .fi-radio-input {
    width: 1.25rem;
    height: 1.25rem;
}

.fi-body .fi-select-input-value-remove-btn {
    min-width: 1.25rem;
    min-height: 1.25rem;
}

/* The file-type chip on a media card was 11.76 px. */
.fi-body .ariana-filecard__ext {
    font-size: var(--ar-fs-footnote);
}

/* Filament's "grey" is not grey here. The panel's grey is generated from a
   violet (#6E6A8C) and the generator keeps the chroma, so the shades Filament
   uses for secondary text came out as SATURATED LIGHT VIOLET: on the light
   panel descriptions measured 2.98:1, placeholders 2.29:1, helper text 4.16:1,
   grey badges 3.93:1, on nearly every page. The text shades are restated —
   near-neutral, and dark (or light) enough to pass — and every Filament
   component that reads them follows, including ones no rule here names.
   Borders and fills use 50–300 and 800–950 and are untouched. */
:root:not(.dark) {
    --gray-400: oklch(0.55 0.055 289.9);   /*  4.9:1 on white — placeholders */
    --gray-500: oklch(0.49 0.065 289.9);   /*  6.3:1 — descriptions          */
    --gray-600: oklch(0.43 0.075 289.9);   /*  8.0:1 — helper text           */
    --gray-700: oklch(0.36 0.075 289.9);
}

.dark {
    --gray-400: oklch(0.82 0.04 289.9);    /* secondary text on the dark panel */
    --gray-500: oklch(0.74 0.05 289.9);    /* placeholders                     */
}

/* Placeholders and "nothing here" cells are still text. */
.fi-body .fi-ta-placeholder,
.fi-body .fi-select-input-placeholder,
.fi-body .fi-input-wrp-label {
    color: var(--ar-ink-mute);
}

.fi-body .fi-ta-text-description,
.fi-body .fi-sc-text,
.fi-body .fi-fo-field-wrp-helper-text,
.fi-body .filepond--drop-label label {
    color: var(--ar-ink-mute);
}

/* The version line: muted ink, no opacity on top of it. */
.fi-body .fi-main-ctn > div[style*="opacity"] {
    opacity: 1 !important;
}

/* Status words in fixed colours failed on the light panel (#16A34A is 3.26:1
   on white). The mode-aware status inks exist for exactly this. */
.fi-body .ariana-backup__note--ok {
    color: var(--ar-success-ink) !important;
}

.fi-body .ariana-diag__chev {
    opacity: 1;
    color: var(--ar-ink-mute);
}

:root:not(.dark) .ariana-filecard--sheet { --file-accent: #11692f; }
:root:not(.dark) .ariana-filecard--audio { --file-accent: #0b6b62; }

/* Scrollbars, as macOS draws them: a thin rounded thumb on a TRANSPARENT
   track. The default track painted a dark stripe down the inside of the glass
   sidebar, and a grey one beside every table on the light panel. */
.fi-body,
.fi-body * {
    scrollbar-width: thin;
    scrollbar-color: color-mix(in srgb, var(--ar-ink) 26%, transparent) transparent;
}

.fi-body ::-webkit-scrollbar {
    width: 10px;
    height: 10px;
}

.fi-body ::-webkit-scrollbar-track {
    background: transparent;
}

.fi-body ::-webkit-scrollbar-thumb {
    background-color: color-mix(in srgb, var(--ar-ink) 26%, transparent);
    border-radius: 999px;
    border: 3px solid transparent;
    background-clip: content-box;
}

.fi-body ::-webkit-scrollbar-thumb:hover {
    background-color: color-mix(in srgb, var(--ar-ink) 42%, transparent);
}

/* ---- controls sit on the line they belong to --------------------------
   Filament aligns a section's icon and a toggle to the TOP of their text
   (flex-start, so a wrapped heading or label keeps the control on its first
   line) and centres them by assuming its own metrics: a 24 px heading line
   and a 20 px label line. The type scale (264) made the heading line 1.2 em
   and the label line 1.35 em, and every section icon and inline toggle
   dropped ~2 px below its words. The metrics are put back in terms of the
   scale, not by hand-tuned pixels.

   The heading's line box is never shorter than the large icon beside it
   (Persian, at 1.5 em, already is); the medium icon is nudged to the middle
   of that box the way Filament nudges the small one. */
.fi-body .fi-section-header:has(> .fi-icon) .fi-section-header-heading {
    line-height: max(calc(var(--ar-lh-tight) * 1em), 1.5rem);
}

.fi-body .fi-section-header > .fi-icon.fi-size-md {
    margin-top: .125rem;
}

/* The toggle's negative block margin is the difference between the label's
   line and its own height — whatever the scale says the label's line is. */
.fi-body .fi-fo-field-label > .fi-fo-toggle,
.fi-body .fi-fo-field-label-ctn > .fi-fo-toggle {
    margin-block: calc((var(--ar-fs-body) * var(--ar-lh-ui) - 1.5rem) / 2);
}

/* The 20 px checkbox and radio (below) sit in Filament's margins for a 16 px
   box: a checkbox-list option or a radio option — a 1.5 rem line — needs
   (1.5 − 1.25) / 2; a checkbox on a field label needs the same difference
   against the label's own line. Measured +2.4 px on every permission in the
   role editor before this. */
.fi-body .fi-fo-checkbox-list-option > .fi-checkbox-input,
.fi-body .fi-fo-radio-label > .fi-radio-input {
    margin-top: .125rem;
}

.fi-body .fi-fo-field-label > .fi-checkbox-input,
.fi-body .fi-fo-field-label-ctn > .fi-checkbox-input {
    margin-top: calc((var(--ar-fs-body) * var(--ar-lh-ui) - 1.25rem) / 2);
}

/* A stat's description wraps on a four-column dashboard, and Filament centres
   its trend icon on the whole block — mid-air between lines two and three
   (measured 9.7 and 18.8 px off). The icon belongs to the first line: the
   row is top-aligned and the icon is dropped to that line's centre by the
   scale's own line, the same arithmetic as the toggle above. */
.fi-body .fi-wi-stats-overview-stat-description > .fi-icon {
    margin-top: calc((var(--ar-fs-footnote) * var(--ar-lh-text) - 1.25rem) / 2);
}

/* A text action ("Code", "See details") measured 19.9 px tall — a hair under
   the 20 px pointer minimum. Its label is baseline-aligned in Filament, and a
   lone baseline item sits at the TOP of a flex line: the moment the link is
   taller than one line of text the icon (centred) drops below the word
   (1.72.8–1.72.12: 3.75 px, on every Edit and Delete in every table). The
   label is centred with the icon; the 24 px target stays. */
.fi-body .fi-ac-link-action {
    min-height: 1.5rem;
}

.fi-body .fi-link > .fi-link-label {
    align-self: center;
}

/* A group the person CLOSED can be the one that holds the current page. Its
   heading then carries the "you are here": the primary ink on a faint accent
   wash. */
.fi-body .fi-sidebar-group.fi-active.fi-collapsed > .fi-sidebar-group-btn {
    background-color: color-mix(in srgb, var(--ar-accent) 13%, transparent);
}

.fi-body .fi-sidebar-group.fi-active.fi-collapsed > .fi-sidebar-group-btn .fi-sidebar-group-label {
    color: var(--ar-ink);
}

/* ---- the notifications panel ---------------------------------------------
   One glass sheet; inside it, a plain list. Rows are flat — no fill, border,
   corner or shadow of their own — separated by a hairline, with the unread
   ones carrying a faint accent wash and Filament's own leading bar. The header
   is part of the sheet, not a second band laid over the first row. */
.fi-body .fi-no-database .fi-no-notification.fi-inline {
    background-color: transparent !important;
    -webkit-backdrop-filter: none;
    backdrop-filter: none;
    border: 0 !important;
    border-radius: 0;
    box-shadow: none !important;
}

.fi-body .fi-no-database .fi-no-notification-read-ctn,
.fi-body .fi-no-database .fi-no-notification-unread-ctn {
    border-block-end: 1px solid var(--ar-line);
}

.fi-body .fi-no-database .fi-no-notification-unread-ctn {
    background-color: color-mix(in srgb, var(--ar-accent) 9%, transparent);
}

/* The header is sticky and the rows scroll UNDER it, so it cannot be clear:
   the sheet's own tint again, blurring what passes beneath — the scroll edge
   effect, not a second band. */
.fi-body .fi-no-database .fi-modal-header {
    background-color: var(--ar-surface) !important;
    border-block-end: 1px solid var(--ar-line);
    box-shadow: none;
}

/* Translucent only where the blur exists — the rule every glass surface here
   follows (invariant 265): without backdrop-filter the header stays solid. */
@supports ((backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px))) {
    .fi-body .fi-no-database .fi-modal-header {
        background-color: color-mix(in srgb, var(--ar-surface) 86%, transparent) !important;
        -webkit-backdrop-filter: blur(20px) saturate(160%);
        backdrop-filter: blur(20px) saturate(160%);
    }
}

@media (prefers-reduced-transparency: reduce), (prefers-contrast: more) {
    .fi-body .fi-no-database .fi-modal-header {
        background-color: var(--ar-surface) !important;
        -webkit-backdrop-filter: none;
        backdrop-filter: none;
    }
}

/* Filament lets the rows bleed to the sheet's edges with a negative margin on
   the list's box, which is wider than the sheet by design. With styled (always
   present) scrollbars that width became a horizontal scrollbar along the
   bottom of the panel. */
.fi-body .fi-no-database .fi-modal-window {
    overflow-x: hidden;
}

/* The sign-up form's fixed fields (1.85.3): locked rows beneath the
   operator's own, in Filament's repeater-item markup so they read as the
   list above; only the layout, the lock and the reason are ours. */
.fi-body .ariana-fixed-fields {
    display: grid;
    gap: 1rem;
    margin: 0;
    padding: 0;
    list-style: none;
}

.fi-body .ariana-fixed-fields__lock {
    inline-size: 1.125rem;
    block-size: 1.125rem;
    flex: none;
    color: var(--ar-ink-mute);
}

.fi-body .ariana-fixed-fields__why {
    margin-inline-start: auto;
    color: var(--ar-ink-mute);
    font-size: var(--ar-fs-sub);
    line-height: var(--ar-lh-ui);
}

/* A collapsed repeater item INSIDE an open one (a menu's sub-items, 1.86.3,
   invariant 331) had no arrow at all. Filament hides the "expand" arrow with
   `.fi-fo-repeater-item:not(.fi-collapsed) .…-expand-action` — a descendant
   selector, so the OPEN parent hid its closed child's arrow too, while the
   child's own `.fi-collapsed` hid the other one. The row looked uneditable;
   operators deleted it and built it again. The item's own header decides. */
.fi-body .fi-fo-repeater-item.fi-collapsed > .fi-fo-repeater-item-header .fi-fo-repeater-item-header-expand-action {
    pointer-events: auto;
    opacity: 1;
}
