/* ═══════════════════════════════════════════════════════════════════════════
   Rava · Carbon — the shared shell for every internal surface
   v1.0 · 2026-09-06
   ───────────────────────────────────────────────────────────────────────────
   Kian, 2026-09-06: "I love what we did with research.rava.capital's look, I
   wished our other panels too should feel that way, the header menu and buttons
   are just beautiful — it was a rava look on carbon design system."

   research.rava.capital had grown that look inline, in one Python string. This
   file is that look lifted out and made shared, so panel, drive and research
   are one system rather than three sites that resemble each other.

   WHAT IS TAKEN FROM CARBON — structure only:
     · a 48px header of full-height cells divided by hairlines, nothing floating
     · square corners everywhere, flat surfaces, no shadow, no gradient
     · one hairline (1px) doing all separation work
     · a dense, uniform row rhythm
     · mono for anything a machine reads back: ids, sizes, addresses, times

   WHAT IS NOT TAKEN — the palette. Kian, asked directly, chose "Carbon
   structure, warm neutrals": Carbon's greys are cool (#161616 / #f4f4f4) and
   Rava's ground is warm. So the neutral ramp below is Rava's, the geometry is
   Carbon's, and productive-blue, its status colours and its shadows are absent.

   TWO ACCENTS, TWO JOBS — do not swap them:
     · ajori  — identity. The mark, the current page, an authority chip.
     · lajvard — action. Every CTA, and nothing else. Kian, 2026-09-06:
       "convert al C2A to Lajvard." ⚠ Blue was retired from brand canon in
       v7.0 (Colour Palette — Trust & Distinction) on collateral evidence;
       this ruling scopes it back in for interface actions. Registered — the
       canon block has not been rewritten on the strength of a chat line.

   ⚠ LOAD ORDER. Where Pico is present (the panel) this file loads AFTER
   pico.min.css and re-tunes it through --pico-* variables rather than fighting
   it with !important. Where it is not (research, and the Nextcloud theme which
   maps these tokens onto Nextcloud's own) it stands alone.
   ═══════════════════════════════════════════════════════════════════════════ */

/* ── 1 · type ────────────────────────────────────────────────────────────────
   Self-hosted, always. research.rava.capital pulls IBM Plex from
   fonts.googleapis.com, which is the one dependency the connectivity doctrine
   forbids: during an isolation window a colleague in Tehran reaches the server
   fine and the typeface not at all, so the page they meet is not the page that
   was designed. Both faces are served from our own /fonts.

   ⚠ IBM Plex Sans ships from Google as ONE VARIABLE FILE for 400/500/600 —
   verified, the three subset URLs return byte-identical files (sha256
   e2291e84…). One @font-face with a weight RANGE, not three faces. Declaring
   three would download the same 45 KB three times and still interpolate.

   The division of labour: Abar carries Farsi, Plex carries Latin and the mono.
   Plex is NOT given the Arabic range — it has no Persian glyphs, and letting it
   claim the range would silently drop the page to a fallback face. */
@font-face{font-family:"Abar Low";src:url("fonts/AbarLowFaNum-Regular.woff2") format("woff2");
  font-weight:400;font-style:normal;font-display:swap}
@font-face{font-family:"Abar Low";src:url("fonts/AbarLowFaNum-SemiBold.woff2") format("woff2");
  font-weight:600;font-style:normal;font-display:swap}
@font-face{font-family:"Abar Mid";src:url("fonts/AbarMidFaNum-Regular.woff2") format("woff2");
  font-weight:400;font-style:normal;font-display:swap}
@font-face{font-family:"Abar Mid";src:url("fonts/AbarMidFaNum-SemiBold.woff2") format("woff2");
  font-weight:600;font-style:normal;font-display:swap}
@font-face{font-family:"Abar Mid";src:url("fonts/AbarMidFaNum-Bold.woff2") format("woff2");
  font-weight:700;font-style:normal;font-display:swap}
@font-face{font-family:"Plex";src:url("fonts/IBMPlexSans-var.woff2") format("woff2");
  font-weight:100 700;font-style:normal;font-display:swap}
@font-face{font-family:"Plex Mono";src:url("fonts/IBMPlexMono-Regular.woff2") format("woff2");
  font-weight:400;font-style:normal;font-display:swap}
@font-face{font-family:"Plex Mono";src:url("fonts/IBMPlexMono-Medium.woff2") format("woff2");
  font-weight:500;font-style:normal;font-display:swap}

/* ── 2 · tokens ──────────────────────────────────────────────────────────── */
:root{
  /* neutral ramp — warm, Rava's own */
  --r-bg:#FCFAF7;          /* the page ground */
  --r-layer:#F5F0E9;       /* a surface ON the ground: table head, field, chip */
  --r-raise:#FFFFFF;       /* the surface a row sits on inside a table */
  --r-hover:#EFE8DF;
  --r-line:#E5DDD3;        /* THE hairline. One weight, used everywhere. */
  --r-line-2:#D6CBBE;      /* only where two surfaces of equal value meet */
  --r-t1:#2E2724;          /* 14.1:1 — anything that must be read */
  --r-t2:#6B5F58;          /*  5.9:1 — secondary, still prose */
  --r-t3:#877B73;          /*  3.8:1 — meta only, never a sentence that matters */

  /* identity */
  --r-ajori:#A54324;       /* 5.9:1 on the ground */
  --r-ajori-ink:#FFF8EC;

  /* action — every CTA, and nothing else */
  --r-act:#2A4A6B;         /* white on it: 9.2:1 */
  --r-act-hover:#21405E;
  --r-act-line:#2A4A6B;
  --r-act-ink:#FFF8EC;
  --r-act-text:#2A4A6B;    /* the same blue used as a link/ghost colour */

  --r-danger:#8A2020;
  --r-danger-ink:#FFFFFF;

  /* geometry — square, and one header height the whole system agrees on */
  --r-head:48px;
  --r-radius:0;
  --r-pad:16px;
  --r-max:1100px;

  --r-fa:"Abar Low","Abar Mid",Tahoma,system-ui,sans-serif;
  --r-fa-mid:"Abar Mid","Abar Low",Tahoma,system-ui,sans-serif;
  --r-en:"Plex",system-ui,-apple-system,"Segoe UI",sans-serif;
  --r-mono:"Plex Mono",ui-monospace,SFMono-Regular,Menlo,monospace;
}

/* dark. ⚠ Every token above is redefined here — a token defined only in one
   scheme is how the panel once shipped near-black headings on charcoal. */
@media (prefers-color-scheme:dark){
  :root:not([data-theme=light]){
    --r-bg:#191614;
    /* ⚠ layer and raise must stay APART on dark. Set to the same value they
       collapse, and Carbon's row-group header — the cell that makes one folder
       read as one block without using colour — becomes invisible. On light the
       gap is free (#F5F0E9 on #FFFFFF); on dark it has to be built. */
    --r-raise:#1F1C1A;
    --r-layer:#262220;
    --r-hover:#2E2825;
    --r-line:#322C28;
    --r-line-2:#453D38;
    --r-t1:#EDE6E1;
    --r-t2:#A99C95;
    --r-t3:#7E736D;

    --r-ajori:#E08260;     /* ajori at its print value goes muddy on charcoal */

    /* ⚠ lajvard raw on this ground is 1.96:1 — the button would be a hole in
       the page. The fill is lifted until the BOUNDARY passes 3:1 and white on
       it still passes 4.5:1, and a lighter border guarantees the boundary
       regardless of what the fill is doing. */
    --r-act:#3E6592;
    --r-act-hover:#4A73A1;
    --r-act-line:#5C86B4;
    --r-act-text:#9CBFE0;  /* 9.4:1 — the link/ghost blue */

    --r-danger:#B33A34;
  }
}

/* ── 3 · the ground ──────────────────────────────────────────────────────── */
*{box-sizing:border-box}
html,body{margin:0;min-height:100%}
body{
  background:var(--r-bg);color:var(--r-t1);
  font-family:var(--r-fa);
  font-size:15px;line-height:1.7;
  -webkit-font-smoothing:antialiased;
}
/* ⚠ Carbon tracks its body text +.16px. That is right for Latin and DAMAGING
   for Persian: letter-spacing inserts space between letters the script joins,
   so words visibly come apart. Tracking is applied to the English side only —
   and to the mono, which is Latin by definition. */
html[lang=en] body{font-family:var(--r-en);font-size:14px;line-height:1.5;letter-spacing:.16px}

/* ── 4 · anything a machine reads back ───────────────────────────────────────
   ⚠ Abar FaNum draws digits as PERSIAN numerals — right in Farsi prose, wrong
   for a uid, a port, a size or a hex. Mono AND an explicit ltr isolate, or
   "8773" and "uid=info" come back reordered inside the RTL run. */
.mono,code,kbd,samp{font-family:var(--r-mono);font-size:.86em;letter-spacing:0;
  direction:ltr;unicode-bidi:isolate;font-variant-numeric:tabular-nums}

/* ── 5 · the header ──────────────────────────────────────────────────────────
   The thing Kian named. It is not a bar with items floating in it: it is a row
   of FULL-HEIGHT CELLS separated by hairlines, so the divisions run the whole
   48px and the header reads as structure rather than decoration. Every child
   is 48px tall and its own hit target. */
.r-head{
  height:var(--r-head);display:flex;align-items:stretch;
  background:var(--r-bg);border-bottom:1px solid var(--r-line);
  position:sticky;top:0;z-index:20;
  /* ⚠ padding:0 is the whole trick, not a reset. Pico styles bare <header> with
     a block padding of 1rem; with box-sizing:border-box that leaves a 16px
     content box inside the 48px bar, so every cell stretched to 16px and the
     dividers ran a sixth of the height. The header still LOOKED roughly right
     in a screenshot and was wrong in the one way that matters — the divisions
     have to run the full 48px or the header is items in a bar again.
     Caught by measuring getBoundingClientRect, not by looking. */
  padding:0;margin:0;
}
.r-head a{color:inherit;text-decoration:none}

/* ⚠ The header's dividers use --r-line-2, the stronger rule, while every other
   hairline in the system uses --r-line. This is the one place where the line IS
   the design: at --r-line the cells stop reading as cells and the header goes
   back to being items floating in a bar, which is the thing it is not. */
.r-brand{
  display:flex;align-items:center;gap:10px;padding:0 var(--r-pad);
  border-inline-end:1px solid var(--r-line-2);
  font-family:var(--r-fa-mid);font-weight:600;font-size:15px;letter-spacing:0;
  white-space:nowrap;color:var(--r-t1);
}
html[lang=en] .r-brand{font-family:var(--r-en);font-weight:600;font-size:14px}
/* the mark. ⚠ Drawn, never the character "]" — a bracket glyph is mirrored by
   the bidi algorithm inside an RTL run, so a typed one turns around and faces
   away from the words it is meant to hold. Per Bracket Grammar, in Farsi the
   opening bracket sits on the RIGHT. */
.r-mark{height:22px;width:auto;color:var(--r-ajori);flex:none;display:block}
.r-brand em{font-style:normal;color:var(--r-t2);font-weight:400}
.r-brand em::before{content:"\00a0·\00a0"}

/* nav — one cell per destination, the current one carried by a 3px ajori rule
   on its top edge. Colour alone would not survive a monochrome print or a
   colour-blind reader; the rule is the signal, the colour agrees with it. */
.r-nav{display:flex;align-items:stretch;min-width:0;overflow-x:auto;scrollbar-width:none}
.r-nav::-webkit-scrollbar{display:none}
.r-nav a{
  display:flex;align-items:center;padding:0 var(--r-pad);
  color:var(--r-t2);font-size:14px;white-space:nowrap;
  border-inline-end:1px solid var(--r-line-2);
  box-shadow:inset 0 3px 0 transparent;
}
html[lang=en] .r-nav a{font-size:13px;letter-spacing:.16px}
.r-nav a:hover{background:var(--r-hover);color:var(--r-t1)}
.r-nav a[aria-current=page]{
  color:var(--r-t1);font-family:var(--r-fa-mid);font-weight:600;
  box-shadow:inset 0 3px 0 var(--r-ajori);
}
html[lang=en] .r-nav a[aria-current=page]{font-family:var(--r-en);font-weight:600}

.r-gap{flex:1;min-width:8px}

/* the meta side — who you are, the language, the way out. Same cell grammar,
   mirrored: the hairline sits on the leading edge instead of the trailing one. */
.r-meta{display:flex;align-items:stretch;font-size:13px}
.r-meta > *{
  display:flex;align-items:center;padding:0 var(--r-pad);
  border-inline-start:1px solid var(--r-line-2);color:var(--r-t2);white-space:nowrap;
}
.r-meta a:hover{background:var(--r-hover);color:var(--r-t1)}
.r-meta .r-lang{font-family:var(--r-en);font-size:12px;letter-spacing:.16px}

/* ── 6 · the body ────────────────────────────────────────────────────────── */
.r-main{max-width:var(--r-max);margin:0 auto;padding:28px var(--r-pad) 56px}
.r-main > h1,.r-main > hgroup > h1{font-size:22px}
h1,h2,h3,h4{font-family:var(--r-fa-mid);font-weight:600;letter-spacing:0;line-height:1.45}
html[lang=en] :is(h1,h2,h3,h4){font-family:var(--r-en);letter-spacing:-.01em}
h2{font-size:19px;margin:0 0 2px}
h3{font-size:16px}
.r-sub{color:var(--r-t3);font-size:13px;margin:0 0 22px}
html[lang=en] .r-sub{font-family:var(--r-mono);font-size:12px;letter-spacing:.16px}

/* ── 7 · buttons ─────────────────────────────────────────────────────────────
   Three, and only three. A page that needs a fourth is a page that has not
   decided what it wants the reader to do.

     .r-btn         the action. Lajvard, square, ivory text.
     .r-btn.ghost   a real but secondary action — outline, no fill.
     .r-btn.danger  quiet until hovered, then unmistakable.

   ⚠ 40px minimum height and 3px of focus offset are not stylistic. Below 40 the
   controls in a dense table stop being reliable targets on a phone, and a focus
   ring drawn flush against a square edge is invisible on a hairline border. */
.r-btn{
  display:inline-flex;align-items:center;justify-content:center;gap:.4em;
  min-height:40px;padding:0 16px;
  font-family:var(--r-fa-mid);font-weight:600;font-size:14px;line-height:1;
  border-radius:var(--r-radius);cursor:pointer;
  background:var(--r-act);border:1px solid var(--r-act-line);color:var(--r-act-ink);
  transition:background .12s linear,border-color .12s linear,color .12s linear;
}
html[lang=en] .r-btn{font-family:var(--r-en);letter-spacing:.16px}
.r-btn:hover{background:var(--r-act-hover);border-color:var(--r-act-hover);color:var(--r-act-ink)}
.r-btn:focus-visible{outline:2px solid var(--r-act-text);outline-offset:2px}
.r-btn[disabled],.r-btn[aria-disabled=true]{opacity:.45;cursor:not-allowed}

.r-btn.ghost{background:transparent;border-color:var(--r-act-line);color:var(--r-act-text)}
.r-btn.ghost:hover{background:var(--r-act);border-color:var(--r-act);color:var(--r-act-ink)}

.r-btn.quiet{background:transparent;border-color:var(--r-line-2);color:var(--r-t2)}
.r-btn.quiet:hover{background:var(--r-hover);border-color:var(--r-t3);color:var(--r-t1)}

.r-btn.danger{background:transparent;border-color:var(--r-line-2);color:var(--r-t2)}
.r-btn.danger:hover{background:var(--r-danger);border-color:var(--r-danger);color:var(--r-danger-ink)}

.r-btn.sm{min-height:32px;padding:0 10px;font-size:13px}

/* ── 8 · table ───────────────────────────────────────────────────────────────
   Carbon's data table, kept to its structure: a hairline box, a quiet head, one
   row rhythm, every column locked to one edge so the eye runs straight down it.
   The wrapper scrolls, never the page — a wide table must not send the whole
   document sideways on a phone. */
.r-box{border:1px solid var(--r-line);overflow-x:auto;background:var(--r-raise)}
.r-table{width:100%;border-collapse:collapse;margin:0;font-size:14px}
html[lang=en] .r-table{font-size:13px}
.r-table :is(input,select,button,textarea){border-radius:var(--r-radius)}
.r-table thead th{
  background:var(--r-layer);color:var(--r-t2);
  font-family:var(--r-fa-mid);font-weight:600;font-size:12.5px;
  text-align:start;white-space:nowrap;
  padding:11px var(--r-pad);border-bottom:1px solid var(--r-line);
}
html[lang=en] .r-table thead th{font-family:var(--r-en);font-size:11.5px;letter-spacing:.32px;text-transform:uppercase}
.r-table :is(td,tbody th){
  padding:10px var(--r-pad);text-align:start;vertical-align:middle;
  border-bottom:1px solid var(--r-line);background:var(--r-raise);
}
.r-table tbody tr:last-child :is(td,th){border-bottom:0}
.r-table tbody tr:hover :is(td,th){background:var(--r-hover)}
.r-table td.num,.r-table th.num{font-family:var(--r-mono);font-size:12px;color:var(--r-t3);
  white-space:nowrap;width:1%;letter-spacing:0;direction:ltr;unicode-bidi:isolate}

/* ── 9 · small parts ─────────────────────────────────────────────────────── */
/* a tag is a fact about a row — never a button, so never a pill */
.r-tag{display:inline-flex;align-items:center;gap:.3em;
  font-family:var(--r-mono);font-size:10.5px;letter-spacing:.32px;text-transform:uppercase;
  color:var(--r-t3);background:var(--r-layer);border:1px solid var(--r-line);
  padding:2px 7px;border-radius:var(--r-radius);white-space:nowrap}
.r-tag.key{background:var(--r-ajori);border-color:var(--r-ajori);color:var(--r-ajori-ink)}
.r-tag.soft{background:transparent;border-color:var(--r-ajori);color:var(--r-ajori)}
.r-tag.warn{background:transparent;border-color:var(--r-danger);color:var(--r-danger)}
/* Farsi inside a tag cannot be uppercased or tracked, and Abar is the only face
   that has the glyphs */
html[lang=fa] .r-tag{font-family:var(--r-fa-mid);text-transform:none;letter-spacing:0;font-size:12px}

/* a message is a line with a coloured edge, not a coloured box — it can carry a
   generated password and must stay readable, not decorative */
.r-note{border:1px solid var(--r-line);background:var(--r-raise);
  padding:11px var(--r-pad);font-size:14px;margin:0 0 18px}
.r-note.soft{border-inline-start:3px solid var(--r-act-text)}
.r-note.warn{border-inline-start:3px solid var(--r-danger)}

.r-empty{padding:44px var(--r-pad);color:var(--r-t3);text-align:center;
  background:var(--r-layer);line-height:1.8}

.r-help{margin-top:32px;padding:var(--r-pad);border:1px solid var(--r-line);
  color:var(--r-t3);font-size:13.5px;line-height:1.9;max-width:660px}
.r-help b{color:var(--r-t2);font-weight:600}

.r-foot{max-width:var(--r-max);margin:0 auto;padding:18px var(--r-pad) 40px;
  border-top:1px solid var(--r-line);color:var(--r-t3);font-size:13px}

.r-sr{position:absolute;width:1px;height:1px;overflow:hidden;clip:rect(0 0 0 0);white-space:nowrap}

/* ── 10 · phone ──────────────────────────────────────────────────────────────
   The header does not collapse into a menu. It keeps its cells and scrolls —
   three destinations do not earn a hamburger, and a scrolling row of cells
   stays honest about how many there are. */
@media (max-width:640px){
  :root{--r-pad:12px}
  .r-head{position:static}
  .r-brand em{display:none}
  .r-meta .r-who{display:none}
  .r-main{padding-top:20px}
}
