/* @operifex/web-next — COMPONENTS.
   Everything src/ui.js produces, plus the login screen. One rule per concept;
   pages never restyle these, they compose them. All colour comes from agentui
   tokens or tokens.css — no literal ever appears in this file. */

/* Per-page stylesheets. Each file below is owned by exactly ONE page module, so
   pages written in parallel never contend for a shared stylesheet. @import must
   precede every rule in this file — do not move these down. Adding a page means
   adding its file here AND nowhere else. */
@import url('./pages/chat.css');
@import url('./pages/landing.css');
@import url('./pages/library.css');
@import url('./pages/market.css');
/* pages/builder.css is gone with the Builder tab (WU-33) — chat's ladder is the
   way in to a build now, and its rung styles live in pages/chat.css. */
@import url('./pages/knowledge.css');
@import url('./pages/approvals.css');
@import url('./pages/schedules.css');
@import url('./pages/advanced.css');
@import url('./pages/settings.css');
@import url('./pages/marketing.css');
@import url('./pages/legal.css');

/* ============================ buttons ==================================== */
/* .ox-btn rides on agentui's .aui-btn (press state, disabled state, focus ring)
   and only tightens the geometry: 34px is compact-but-breathing for a
   professional tool, where agentui's 40px --hit is a touch target. Coarse
   pointers get the touch target back at the bottom of this block. */
.ox-btn {
  min-height: 34px;
  padding: 0 var(--sp-3);
  font-size: var(--ox-t-sm);
  font-weight: 550;
  border-radius: var(--rad-sm);
}
.ox-btn-label { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.ox-btn-subtle { background: var(--bg2); }
.ox-btn-subtle:hover { background: var(--bg3); }
.ox-btn-ghost { padding: 0 10px; }
.ox-btn-primary { font-weight: 600; }
.ox-btn-danger { font-weight: 550; }
@media (pointer: coarse) { .ox-btn { min-height: var(--hit); } }

/* ============================ badges ===================================== */
/* Pill, 11px, 2px/8px. Never more than two on a card — three is where a card
   stops being scannable (enforced in ui.js, not here). */
.ox-badge {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 2px 8px;
  border-radius: var(--rad-pill);
  font-size: var(--ox-t-2xs);
  font-weight: 600;
  line-height: 1.55;
  white-space: nowrap;
}
.ox-badge-ai { background: var(--accent-soft); color: var(--accent); }
.ox-badge-det { background: var(--bg3); color: var(--fg2); }
.ox-badge-verified { background: color-mix(in oklab, var(--ok), transparent 86%); color: var(--ok); }
.ox-badge-featured { background: var(--accent); color: var(--accent-fg); }
.ox-badge-ok { background: color-mix(in oklab, var(--ok), transparent 86%); color: var(--ok); }
.ox-badge-warn { background: color-mix(in oklab, var(--warn), transparent 86%); color: var(--warn); }
.ox-badge-err { background: color-mix(in oklab, var(--err), transparent 86%); color: var(--err); }
.ox-badge-neutral { background: var(--bg3); color: var(--fg2); }

/* ============================ chips ====================================== */
.ox-chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 5px 12px;
  border: 1px solid var(--line);
  border-radius: var(--rad-pill);
  background: var(--bg2);
  color: var(--fg);
  font: inherit;
  font-size: var(--ox-t-xs);
  font-weight: 500;
  cursor: default;
  transition: background var(--fast) var(--ease), border-color var(--fast) var(--ease), color var(--fast) var(--ease);
}
button.ox-chip { cursor: pointer; }
button.ox-chip:hover { border-color: var(--accent); color: var(--accent); background: var(--accent-soft); }
.ox-chip.is-active { border-color: transparent; background: var(--accent-soft); color: var(--accent); }

/* ============================ cards ====================================== */
/* --bg2 fill, 1px hairline, NO shadow at rest. The 1px lift + accent border on
   hover is the whole interaction: a resting drop shadow makes a grid of cards
   look like a pile of receipts. */
.ox-card {
  display: flex;
  flex-direction: column;
  gap: var(--sp-3);
  min-width: 0;
  padding: var(--sp-4);
  border: 1px solid var(--line);
  border-radius: var(--rad);
  background: var(--bg2);
  color: var(--fg);
  font: inherit;
  text-align: left;
}
.ox-card-btn {
  cursor: pointer;
  transition: transform var(--fast) var(--ease), border-color var(--fast) var(--ease), box-shadow var(--fast) var(--ease);
}
.ox-card-btn:hover { transform: translateY(-1px); border-color: var(--accent); box-shadow: var(--ox-lift); }
.ox-card-head { display: flex; align-items: flex-start; gap: var(--sp-3); min-width: 0; }
.ox-card-ic { flex: none; display: inline-flex; margin-top: 1px; color: var(--accent); }
.ox-card-txt { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: 2px; }
.ox-card-t { font-size: var(--ox-t-lg); font-weight: 650; letter-spacing: -0.005em; }
.ox-card-s { font-size: var(--ox-t-xs); line-height: 1.45; color: var(--fg2); }
.ox-card-badges { flex: none; display: flex; gap: var(--sp-1); }
.ox-card-foot {
  display: flex;
  align-items: center;
  gap: var(--sp-2);
  flex-wrap: wrap;
  padding-top: var(--sp-2);
  border-top: 1px solid var(--line);
}
.ox-card-meta { font-size: var(--ox-t-2xs); color: var(--fg2); }

/* ============================ expert tile ================================
   THE hero object. Everything here exists to make it feel like a THING you want
   to pick up: a real 40px icon tile on an accent-soft fill, a name at 15/650, a
   tagline clamped to exactly two lines so a grid of tiles keeps one baseline,
   and a footer that answers "what is it / how much of it is mine" at a glance. */
.ox-tile {
  display: flex;
  flex-direction: column;
  gap: var(--sp-3);
  width: 100%;
  min-width: 0;
  padding: var(--sp-4);
  border: 1px solid var(--line);
  border-radius: var(--rad-lg);
  background: var(--bg2);
  color: var(--fg);
  font: inherit;
  text-align: left;
  cursor: pointer;
  transition: transform var(--fast) var(--ease), border-color var(--fast) var(--ease), box-shadow var(--fast) var(--ease);
}
.ox-tile:hover { transform: translateY(-1px); border-color: var(--accent); box-shadow: var(--ox-lift); }
.ox-tile-head { display: flex; align-items: flex-start; gap: var(--sp-3); min-width: 0; }
.ox-tile-glyph {
  flex: none;
  width: 40px;
  height: 40px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: 11px;
  font-size: 20px;
  line-height: 1;
  background: var(--accent-soft);
  box-shadow: inset 0 0 0 1px var(--ox-glow);
}
.ox-tile-txt { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: 3px; }
.ox-tile-name { font-size: var(--ox-t-lg); font-weight: 650; letter-spacing: -0.008em; }
/* Two-line clamp: an unclamped tagline makes every tile in the grid a different
   height, which reads as broken rather than as varied. */
.ox-tile-tag {
  font-size: var(--ox-t-xs);
  line-height: 1.45;
  color: var(--fg2);
  display: -webkit-box;
  -webkit-line-clamp: 2;
  line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
}
.ox-tile-dot {
  flex: none;
  width: 8px;
  height: 8px;
  margin-top: 6px;
  border-radius: 50%;
  background: var(--accent);
  box-shadow: 0 0 0 3px var(--accent-soft);
}
.ox-tile-foot { display: flex; align-items: center; gap: 6px; min-width: 0; }
.ox-tile-n { font-size: var(--ox-t-2xs); color: var(--fg2); font-variant-numeric: tabular-nums; }

/* ============================ list rows ================================== */
.ox-rowwrap { display: flex; align-items: center; gap: var(--sp-2); min-width: 0; }
.ox-rowwrap > .ox-row { flex: 1 1 auto; }
.ox-row {
  display: flex;
  align-items: center;
  gap: var(--sp-3);
  width: 100%;
  min-width: 0;
  padding: 9px var(--sp-3);
  border: 1px solid var(--line);
  border-radius: var(--rad);
  background: var(--bg2);
  color: var(--fg);
  font: inherit;
  text-align: left;
}
.ox-row-btn { cursor: pointer; transition: border-color var(--fast) var(--ease), background var(--fast) var(--ease); }
.ox-row-btn:hover { border-color: var(--accent); background: var(--ox-hover); }
.ox-row-ic { flex: none; display: inline-flex; color: var(--fg2); }
.ox-row-txt { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: 1px; }
.ox-row-t { font-size: var(--ox-t-sm); font-weight: 550; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.ox-row-s { font-size: 12px; color: var(--fg2); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.ox-row-m { flex: none; font-size: var(--ox-t-2xs); color: var(--fg2); font-variant-numeric: tabular-nums; }
.ox-row-a { flex: none; display: flex; align-items: center; gap: var(--sp-1); }

/* ============================ key / value ================================ */
.ox-kv {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--sp-3);
  padding: 5px 0;
  font-size: var(--ox-t-sm);
}
.ox-kv-k { color: var(--fg2); flex: none; }
.ox-kv-v { font-weight: 500; text-align: right; min-width: 0; overflow-wrap: anywhere; }

/* ============================ stat tile ================================== */
.ox-stat {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 0;
  padding: var(--sp-3) var(--sp-4);
  border: 1px solid var(--line);
  border-radius: var(--rad);
  background: var(--bg2);
}
.ox-stat-v { font-size: 24px; font-weight: 650; line-height: 1.15; letter-spacing: -0.02em; font-variant-numeric: tabular-nums; }
.ox-stat-l { font-size: var(--ox-t-xs); color: var(--fg2); }
.ox-stat-h { font-size: var(--ox-t-2xs); color: var(--fg2); opacity: 0.8; }

/* ============================ meter ====================================== */
.ox-meter { display: flex; flex-direction: column; gap: 6px; min-width: 0; }
.ox-meter-top { display: flex; align-items: baseline; justify-content: space-between; gap: var(--sp-2); }
.ox-meter-l { font-size: var(--ox-t-xs); color: var(--fg2); }
.ox-meter-n { font-size: var(--ox-t-2xs); color: var(--fg2); font-variant-numeric: tabular-nums; }
.ox-meter-track { height: 6px; border-radius: var(--rad-pill); background: var(--bg3); overflow: hidden; }
.ox-meter-fill { height: 100%; border-radius: inherit; background: var(--accent); transition: width var(--med) var(--ease); }

/* ============================ skeleton =================================== */
.ox-skel { display: flex; flex-direction: column; gap: 10px; }
.ox-skel-bar {
  height: 12px;
  border-radius: var(--rad-pill);
  background: linear-gradient(90deg, var(--bg2), var(--bg3), var(--bg2));
  background-size: 200% 100%;
  animation: ox-shimmer 1.4s linear infinite;
}
@keyframes ox-shimmer { to { background-position: -200% 0; } }

/* ============================ field / toggle / segmented ================= */
.ox-field { gap: 6px; }
.ox-field-l { font-size: var(--ox-t-xs); font-weight: 550; color: var(--fg2); }
.ox-field-h { font-size: var(--ox-t-2xs); line-height: 1.5; color: var(--fg2); opacity: 0.85; }

.ox-toggle { display: flex; align-items: center; gap: var(--sp-3); min-width: 0; }
.ox-toggle-txt { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: 1px; }
.ox-toggle-l { font-size: var(--ox-t-sm); font-weight: 550; }
.ox-toggle-h { font-size: var(--ox-t-2xs); line-height: 1.45; color: var(--fg2); }
.ox-switch { flex: none; }

.ox-seg {
  display: inline-flex;
  gap: 2px;
  padding: 3px;
  border: 1px solid var(--line);
  border-radius: var(--rad);
  background: var(--bg3);
}
.ox-seg-btn {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 5px 12px;
  border: 0;
  border-radius: var(--rad-sm);
  background: transparent;
  color: var(--fg2);
  font: inherit;
  font-size: var(--ox-t-sm);
  font-weight: 550;
  cursor: pointer;
  transition: background var(--fast) var(--ease), color var(--fast) var(--ease);
}
.ox-seg-btn:hover { color: var(--fg); }
/* The selected segment RISES out of the recessed track — that depth flip is
   what makes a segmented control legible without a border on the active item. */
.ox-seg-btn[aria-pressed="true"] { background: var(--bg2); color: var(--fg); box-shadow: var(--ox-lift-sm); }

/* ============================ empty state ================================
   A NEW account starts empty by design, so this is a primary screen, not a
   fallback. Capped at 420px, centred, generous vertical rhythm, and the two
   real on-ramps as buttons. */
.ox-empty {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--sp-3);
  max-width: 420px;
  margin: var(--sp-7) auto;
  padding: var(--sp-5) var(--sp-4);
  text-align: center;
}
.ox-empty-ic { color: var(--fg2); opacity: 0.4; line-height: 0; }
.ox-empty-t { margin: 0; font-size: 16px; font-weight: 650; letter-spacing: -0.01em; }
.ox-empty-b { margin: 0; font-size: var(--ox-t-sm); line-height: 1.55; color: var(--fg2); }
.ox-empty-a { display: flex; flex-wrap: wrap; justify-content: center; gap: var(--sp-2); margin-top: var(--sp-2); }

/* ============================ page-level utilities ======================= */
/* A responsive object grid pages can reach for instead of inventing one each.
   min() keeps a single narrow column from overflowing on a phone. */
.ox-grid {
  display: grid;
  gap: var(--sp-4);
  grid-template-columns: repeat(auto-fill, minmax(min(268px, 100%), 1fr));
}
.ox-grid-wide { grid-template-columns: repeat(auto-fill, minmax(min(340px, 100%), 1fr)); }
.ox-section { display: flex; flex-direction: column; gap: var(--sp-3); min-width: 0; }
.ox-section-h { display: flex; align-items: baseline; justify-content: space-between; gap: var(--sp-3); }
.ox-section-t { font-size: var(--ox-t-lg); font-weight: 650; letter-spacing: -0.008em; }

/* ============================ login ======================================
   The first screen anyone sees. One centred card on a single soft accent bloom;
   nothing else on the page, because the only decision here is one email field. */
.ox-login {
  position: relative;
  height: 100%;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: var(--sp-5);
  overflow: auto;
  background: var(--bg);
}
/* The bloom sits BEHIND the card, not above it: anchored to the top of the
   container it read as an unexplained smudge in the upper-left. Decorative only,
   so it must never intercept the field's clicks. */
.ox-login-glow {
  position: absolute;
  top: 50%;
  left: 50%;
  width: min(900px, 140vw);
  height: min(720px, 110vh);
  transform: translate(-50%, -50%);
  pointer-events: none;
  background: radial-gradient(ellipse at center, var(--ox-glow), transparent 66%);
}
.ox-login-card {
  position: relative;
  width: 100%;
  max-width: 392px;
  display: flex;
  flex-direction: column;
  gap: var(--sp-4);
  padding: var(--sp-6) var(--sp-5) var(--sp-5);
  border: 1px solid var(--line);
  border-radius: var(--rad-lg);
  background: var(--bg2);
  box-shadow: var(--ox-pop);
}
.ox-login-brand { display: flex; align-items: center; gap: var(--sp-2); }
.ox-login-word { font-size: 16px; font-weight: 650; letter-spacing: -0.012em; }
.ox-login-head { display: flex; flex-direction: column; gap: var(--sp-1); }
.ox-login-t { margin: 0; font-size: var(--ox-t-title); font-weight: 650; line-height: 1.25; letter-spacing: -0.015em; }
.ox-login-sub { margin: 0; font-size: var(--ox-t-sm); line-height: 1.5; color: var(--fg2); }
.ox-login-form { display: flex; flex-direction: column; gap: var(--sp-3); }
.ox-login-msg { font-size: var(--ox-t-xs); line-height: 1.45; color: var(--err); }
.ox-login-msg:empty { display: none; }
.ox-login-hint { font-size: var(--ox-t-2xs); line-height: 1.45; color: var(--fg2); }
/* The pending-access notice (D-DEP-4): shown only when the gateway's invite gate
   redirected a refused invitee here with `?access=pending`. Deliberately styled
   as INFORMATION and not as an error — `--accent` and the surface tint, never
   `--err` — because nothing failed: a request was received and is being decided.
   Tokens only (the theme gate forbids colour literals here), and it inherits the
   card's own gap for spacing so it adds no layout of its own. */
/* `.ox-login-expired` is the sibling notice for a SPENT magic link
   (routes/auth.ts::SIGNIN_FAILED_PATH). Same box, and deliberately the same
   `--accent` rather than `--err`: a single-use link being single-use is the
   design working, not a failure, and painting it red tells someone their account
   is broken when all they need is a fresh link. It shares this rule rather than
   copying it so the two notices cannot drift apart visually. */
.ox-login-pending,
.ox-login-expired {
  padding: var(--sp-3);
  border: 1px solid var(--line);
  border-left: 2px solid var(--accent);
  /* --rad, not the nonexistent --r-2 this used to name: with no fallback that
     token resolved to nothing and the notice rendered SQUARE inside a
     --rad-lg card. The radius ladder is --rad-sm / --rad / --rad-lg, and a
     block nested in a card takes the middle rung. */
  border-radius: var(--rad);
  background: var(--bg2);
  font-size: var(--ox-t-xs);
  line-height: 1.5;
  color: var(--fg2);
}
.ox-login-pending strong,
.ox-login-expired strong { color: var(--fg); font-weight: 650; }
.ox-login-foot {
  display: flex;
  align-items: flex-start;
  gap: 6px;
  padding-top: var(--sp-3);
  border-top: 1px solid var(--line);
  font-size: var(--ox-t-2xs);
  line-height: 1.45;
  color: var(--fg2);
}
.ox-login-foot .aui-ic { flex: none; margin-top: 1px; opacity: 0.7; }
.ox-login-ok { display: flex; align-items: center; gap: var(--sp-2); color: var(--ok); font-size: var(--ox-t-sm); font-weight: 550; }

/* ====================== demo-data notice (WU-6c) ========================= */
/* ONE rule set for BOTH mount sites — inside the shell's Art. 50 strip and
   inside the sign-in card — because src/ui.js::demoNotice() is the only thing
   that emits these classes. Tokens only: no literal colour appears here, and
   `--warn` is the token that already means "true, and you need to know it".
   It sits on `.ox-disclosure`'s own `gap`, so no margin is invented. */
.ox-demo {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 1px 7px;
  border: 1px solid var(--warn);
  border-radius: 999px;   /* a pill; there is no radius token for "fully round" */
  color: var(--warn);
  font-weight: 600;
  flex: 0 1 auto;
  min-width: 0;
}
.ox-demo .aui-ic { flex: none; opacity: 0.85; }
/* IT WRAPS, IT NEVER TRUNCATES. This shipped for one screenshot round as
   `white-space:nowrap; text-overflow:ellipsis`, and at 390px the sentence became
   "Dados de demonst…" — the pill still SAID demo, but the half that does the
   actual work ("nada aqui é real" / "nothing here is real") was the half thrown
   away. A notice that degrades to its own decoration is not a notice, so it is
   allowed to become two lines on a phone exactly like the Art. 50 line beside
   it already does. Found by reading the mobile PNG; no DOM test can see it. */
.ox-demo-l { min-width: 0; }
/* In the sign-in card it is its own block above the fold of the footer, not an
   inline tail, because the card is a column and there is nothing to sit beside. */
.ox-login-card > .ox-demo { align-self: flex-start; }

/* ============================ reduced motion ============================= */
@media (prefers-reduced-motion: reduce) {
  .ox-card-btn:hover,
  .ox-tile:hover { transform: none; }
  .ox-skel-bar { animation: none; }
}
