/* ===========================================================================
   Customer portal — its own design system.

   The portal used to wear the ERP's clothes: a sidebar of fifteen links built
   for an accountant who lives in the tool. The person this is actually for is a
   plant compliance officer who opens it a few times a month, often on a phone,
   to answer three questions and leave:

       Am I all right?
       What do I have to do?
       Where is my work?

   Everything below serves answering those in that order. Density is not a
   virtue here — an occasional user needs air, plain language and one obvious
   next action per screen.

   The palette and the typeface come from the working prototype the client has
   already been shown, so the platform looks like the same company's product.
   =========================================================================== */

:root {
  /* Brand tokens come from brand.css, sampled from the approved logo.
     Loaded before this file so the values below can rely on them. */

  --ok: #297A44;
  --ok-tint: #E3F2E8;
  --warn: #B45309;
  --warn-tint: #FDF3E3;
  --bad: #B91C1C;
  --bad-tint: #FDEAEA;
  --info: #1D4ED8;
  --info-tint: #E8EEFC;

  /* Neutrals carry a slight green cast so they sit with the brand rather than
     fighting it. A pure grey next to this green reads cold. */
  --ink: #12211D;
  --ink-2: #4A5B56;
  --ink-3: #636F6B;
  --line: #DDE5E2;
  --line-soft: #EDF2F0;
  --bg: #F4F7F6;
  --card: #FFFFFF;
  /* The portal had no shadow token at all, so any rule reaching for one got
     nothing. */
  --shadow-1: 0 1px 2px rgba(11, 32, 22, .06);
  --shadow-2: 0 8px 28px rgba(11, 32, 22, .16);
  --card-alt: #FAFCFB;

  /* Names geopick.css expects. */
  --geo-bg:            #EDF2F0;
  --geo-border:        #DDE5E2;
  --geo-radius:        8px;
  --geo-pin:           #07730E;
  --geo-pin-halo:      rgba(255, 255, 255, .75);
  --geo-control-bg:    #FFFFFF;
  --geo-control-hover: #EDF2F0;
  --geo-control-ink:   #12211D;
  --geo-muted:         #636F6B;
  --geo-warn:          #B45309;

  /* Names combo.css expects. Mapped rather than duplicated, so a change to
     the portal palette carries into the dropdown without anyone remembering. */
  --combo-bg:          #FFFFFF;
  --combo-border:      #DDE5E2;
  --combo-radius:      8px;
  --combo-shadow:      0 8px 24px rgba(11, 32, 22, .12);
  --combo-text:        #12211D;
  --combo-muted:       #636F6B;
  --combo-active-bg:   #EDF2F0;
  --combo-active-text: #07730E;

  --r-sm: 8px;
  --r: 14px;
  --r-lg: 20px;
  --r-pill: 999px;

  /* Two-layer shadows: a tight contact shadow plus a wide soft one. A single
     blurred shadow reads as fog; this reads as a card resting on paper. */
  --sh-1: 0 1px 2px rgba(16, 32, 28, .06), 0 2px 8px rgba(16, 32, 28, .04);
  --sh-2: 0 1px 2px rgba(16, 32, 28, .07), 0 8px 24px rgba(16, 32, 28, .07);
  --sh-3: 0 2px 4px rgba(16, 32, 28, .08), 0 16px 40px rgba(16, 32, 28, .10);

  --ease: cubic-bezier(.22, .61, .36, 1);
}

[data-bs-theme="dark"] {
  /* The dropdown is a surface like any other and has to follow the theme. A
     token defined only in the light block renders white-on-white in dark —
     which is the failure this codebase has already had twice. */
  --geo-bg:            #101614;
  --geo-border:        #2A3532;
  --geo-pin:           #7FC47A;
  --geo-pin-halo:      rgba(0, 0, 0, .55);
  --geo-control-bg:    #172120;
  --geo-control-hover: #223029;
  --geo-control-ink:   #E8EFEC;
  --geo-muted:         #85938E;
  --geo-warn:          #E0A458;

  --combo-bg:          #172120;
  --combo-border:      #2A3532;
  --combo-shadow:      0 8px 24px rgba(0, 0, 0, .45);
  --combo-text:        #E8EFEC;
  --combo-muted:       #85938E;
  --combo-active-bg:   #223029;
  --combo-active-text: #A9D6A2;

  --ok: #5FC98A;
  --ok-tint: #12271B;
  --warn: #E0A458;
  --warn-tint: #2A2015;
  --bad: #F08A84;
  --bad-tint: #2C1817;
  --info: #7EA6F5;
  --info-tint: #16203A;

  --ink: #E8EFEC;
  --ink-2: #B4C1BC;
  --ink-3: #85938E;
  --line: #2A3532;
  --line-soft: #222B29;
  --bg: #101614;
  --card: #172120;
  --shadow-1: 0 1px 2px rgba(0, 0, 0, .35);
  --shadow-2: 0 8px 28px rgba(0, 0, 0, .55);
  --card-alt: #1C2725;

  --sh-1: 0 1px 2px rgba(0, 0, 0, .4);
  --sh-2: 0 2px 10px rgba(0, 0, 0, .45);
  --sh-3: 0 8px 30px rgba(0, 0, 0, .5);
}

/* --- base ---------------------------------------------------------------- */

.portal {
  font-family: 'Tajawal', 'Segoe UI', Tahoma, Arial, sans-serif;
  background: var(--bg);
  color: var(--ink);
  min-height: 100vh;
  -webkit-font-smoothing: antialiased;
  font-size: 15px;
  line-height: 1.6;
}

.portal * { box-sizing: border-box; }

/* Inline icons size to the surrounding text unless a component overrides it.
   Without this default, an icon dropped into a new context renders at the SVG
   default of 300x150 and destroys the layout — which is exactly what the back
   link in a page heading did. */
.portal svg { width: 1.15em; height: 1.15em; flex: 0 0 auto; vertical-align: -.18em; }

.portal h1, .portal h2, .portal h3 {
  margin: 0;
  font-weight: 800;
  letter-spacing: -.01em;
  color: var(--ink);
}
.portal h1 { font-size: clamp(21px, 3.2vw, 27px); }
.portal h2 { font-size: 18px; }
.portal h3 { font-size: 15px; font-weight: 700; }
.portal p { margin: 0; }
.portal a { color: var(--brand-dark); text-decoration: none; }
.portal a:hover { text-decoration: underline; }

.wrap {
  width: 100%;
  max-width: 1080px;
  margin: 0 auto;
  padding: 0 18px;
}

/* --- header -------------------------------------------------------------- */

.p-header {
  background: var(--card);
  border-bottom: 1px solid var(--line);
  position: sticky;
  top: 0;
  z-index: 40;
}

.p-header-in {
  display: flex;
  align-items: center;
  gap: 14px;
  height: 62px;
}

.p-brand {
  display: flex;
  align-items: center;
  gap: 10px;
  min-width: 0;
  color: var(--ink);
}
.p-brand:hover { text-decoration: none; }
.p-brand img { height: 30px; }
@media (max-width: 560px) { .p-brand img { height: 25px; } }
.p-brand-mark {
  width: 34px; height: 34px;
  border-radius: 10px;
  background: linear-gradient(140deg, var(--brand), var(--brand-darker));
  display: grid; place-items: center;
  color: #fff;
  flex: 0 0 auto;
}
.p-brand-mark svg { width: 19px; height: 19px; }
.p-brand-sub {
  font-size: 11px;
  font-weight: 600;
  color: var(--ink-3);
  line-height: 1.2;
  padding-inline-start: 10px;
  border-inline-start: 1px solid var(--line);
  white-space: nowrap;
}
@media (max-width: 480px) { .p-brand-sub { display: none; } }

/* The office's full name is long enough to wrap on a 390px screen, which
   pushed the header to double height. One line, clipped — the mark carries the
   identity at that width anyway. */
.p-brand > span:not(.p-brand-mark) {
  min-width: 0;
  overflow: hidden;
}
.p-brand-name {
  display: block;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
@media (max-width: 420px) {
  .p-brand-name { max-width: 42vw; }
}

.p-header-actions { margin-inline-start: auto; display: flex; align-items: center; gap: 6px; }

.icon-btn {
  width: 38px; height: 38px;
  border-radius: 10px;
  border: 1px solid transparent;
  background: transparent;
  color: var(--ink-2);
  display: grid; place-items: center;
  cursor: pointer;
  transition: background .15s var(--ease), color .15s var(--ease);
}
.icon-btn:hover { background: var(--line-soft); color: var(--ink); }
.icon-btn svg { width: 19px; height: 19px; }

/* Show the icon for the theme you would switch *to*, not the one you are in. */
.t-dark { display: none; }
[data-bs-theme="dark"] .t-light { display: none; }
[data-bs-theme="dark"] .t-dark { display: block; }

.d-none-mobile { display: block; }
@media (max-width: 560px) { .d-none-mobile { display: none; } }

.p-user {
  display: flex; align-items: center; gap: 9px;
  padding-inline-start: 10px;
  margin-inline-start: 4px;
  border-inline-start: 1px solid var(--line);
}
.p-avatar {
  width: 32px; height: 32px;
  border-radius: 50%;
  background: var(--brand-tint);
  color: var(--brand-dark);
  display: grid; place-items: center;
  font-weight: 700; font-size: 13px;
  flex: 0 0 auto;
}
.p-user-name { font-size: 13px; font-weight: 600; line-height: 1.25; }
.p-user-org { font-size: 11px; color: var(--ink-3); line-height: 1.25; }

/* The name and the avatar open the account page. They were plain text and are
   links now, so they keep their own colour rather than taking the link green —
   the header is not a paragraph of links. */
a.p-avatar, a.p-user-name { color: inherit; text-decoration: none; }
a.p-avatar { color: var(--brand-dark); }
a.p-user-name:hover { text-decoration: underline; }

/* --- company switcher ------------------------------------------------------
   A person who owns three companies signs in once. The header line that used to
   be a static company name becomes the control that scopes the whole portal, so
   it stays exactly where the name was — the thing you read to know where you
   are is the thing you press to go elsewhere.

   Only rendered when there is more than one company: a single-company customer
   should never see a chooser with one entry in it. */

.p-orgs { position: relative; }
.p-orgs > summary {
  display: inline-flex; align-items: center; gap: 4px;
  cursor: pointer; list-style: none; border-radius: var(--r-sm);
}
.p-orgs > summary::-webkit-details-marker { display: none; }
.p-orgs > summary:hover { color: var(--brand-dark); }
.p-orgs-caret {
  width: 11px; height: 11px; flex: none;
  transition: transform var(--t, .15s) ease;
}
.p-orgs[open] .p-orgs-caret { transform: rotate(180deg); }

.p-orgs-menu {
  position: absolute; inset-block-start: calc(100% + 8px); inset-inline-start: 0;
  min-width: 264px; max-width: 320px; z-index: 60;
  /* --card, not --surface: the latter belongs to erp-base, which the portal
     does not load, so this menu had no background and could not be read
     against the page behind it. */
  background: var(--card); border: 1px solid var(--line);
  border-radius: var(--r); box-shadow: var(--shadow-2);
  padding: 6px; overflow: hidden;
}
.p-orgs-head {
  font-size: 10px; font-weight: 700; letter-spacing: .04em;
  color: var(--ink-3); padding: 6px 8px 4px;
}
.p-orgs-menu form { margin: 0; }

.p-org {
  display: flex; align-items: center; gap: 9px; width: 100%;
  padding: 8px; border: 0; border-radius: var(--r-sm);
  background: transparent; cursor: pointer; text-align: start;
  font: inherit; color: var(--ink);
}
.p-org:hover { background: var(--line-soft); }
.p-org.on { background: var(--brand-tint); }
.p-org-mark {
  display: grid; place-items: center; flex: none;
  width: 26px; height: 26px; border-radius: 50%;
  background: var(--line-soft); color: var(--ink-3);
}
.p-org.on .p-org-mark { background: var(--brand-dark); color: var(--brand-ink); }
.p-org-mark svg { width: 13px; height: 13px; }
.p-org-text { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.p-org-name {
  font-size: 12.5px; font-weight: 600; line-height: 1.3;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.p-org.on .p-org-name { color: var(--brand-dark); }
.p-org-sub { font-size: 10.5px; color: var(--ink-3); line-height: 1.3; }

/* The header is centred on a phone and the menu would run off the edge. */
@media (max-width: 640px) {
  .p-orgs-menu { inset-inline-start: auto; inset-inline-end: 0; }
}

/* --- navigation ----------------------------------------------------------
   Horizontal on desktop; a thumb-reachable bottom bar on phones. No sidebar:
   six destinations do not need one, and the space is better spent on content. */

.p-nav {
  background: var(--card);
  border-bottom: 1px solid var(--line);
  position: sticky;
  top: 62px;
  z-index: 39;
}
.p-nav-in {
  display: flex;
  gap: 2px;
  overflow-x: auto;
  scrollbar-width: none;
}
.p-nav-in::-webkit-scrollbar { display: none; }

.p-nav a {
  display: flex; align-items: center; gap: 7px;
  padding: 13px 14px;
  font-size: 13.5px; font-weight: 600;
  color: var(--ink-2);
  border-bottom: 2.5px solid transparent;
  white-space: nowrap;
  transition: color .15s var(--ease), border-color .15s var(--ease);
}
.p-nav a:hover { color: var(--ink); text-decoration: none; }
.p-nav a.on { color: var(--brand-dark); border-bottom-color: var(--brand); }
.p-nav a svg { width: 17px; height: 17px; }
.p-nav .badge-dot {
  width: 7px; height: 7px; border-radius: 50%;
  background: var(--bad);
  margin-inline-start: -3px;
}

.p-tabbar { display: none; }

@media (max-width: 720px) {
  .p-nav { display: none; }

  .p-tabbar {
    display: flex;
    position: fixed;
    inset-inline: 0;
    bottom: 0;
    z-index: 50;
    background: var(--card);
    border-top: 1px solid var(--line);
    padding-bottom: env(safe-area-inset-bottom);
    box-shadow: 0 -2px 12px rgba(16, 32, 28, .06);
  }
  .p-tabbar a {
    flex: 1;
    display: flex; flex-direction: column; align-items: center; gap: 3px;
    padding: 9px 4px 7px;
    font-size: 10.5px; font-weight: 600;
    color: var(--ink-3);
    position: relative;
  }
  .p-tabbar a:hover { text-decoration: none; }
  .p-tabbar a.on { color: var(--brand-dark); }
  .p-tabbar a svg { width: 21px; height: 21px; }
  .p-tabbar .badge-dot {
    position: absolute; top: 6px; inset-inline-end: 50%;
    transform: translateX(-14px);
    width: 7px; height: 7px; border-radius: 50%; background: var(--bad);
  }
  .p-main { padding-bottom: 78px; }
}

.p-main { padding: 22px 0 48px; }

/* --- page heading -------------------------------------------------------- */

.page-head { margin-bottom: 20px; }
.page-head .eyebrow {
  font-size: 12px; font-weight: 600; color: var(--brand-dark);
  text-transform: none; margin-bottom: 3px;
}
.page-head .sub { font-size: 13.5px; color: var(--ink-3); margin-top: 4px; }

/* --- cards --------------------------------------------------------------- */

.card {
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--r);
  box-shadow: var(--sh-1);
}
.card-pad { padding: 20px; }
/* Stacked cards in normal flow space themselves. A grid does not need this —
   it has gap — and is actively harmed by it: the margin applies to every card
   but the first, the row is sized by the first, and the rest lose exactly that
   margin off their height. On the quick actions that was one card 98px tall
   beside two of 84, which reads as a sizing bug and is really a spacing rule
   reaching somewhere it was never meant to go. */
.card + .card { margin-top: 14px; }
.grid > .card + .card, .flex > .card + .card { margin-top: 0; }

.card-head {
  display: flex; align-items: center; gap: 10px;
  padding: 15px 20px;
  border-bottom: 1px solid var(--line-soft);
}
.card-head h2, .card-head h3 { margin: 0; }
.card-head .spacer { margin-inline-start: auto; }

.grid { display: grid; gap: 14px; }
.grid-2 { grid-template-columns: repeat(auto-fit, minmax(300px, 1fr)); }
.grid-3 { grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); }
/* Cards in a row are the same height whatever their text runs to. Stated
   rather than left to the default, because a card that sets its own height for
   any reason silently stops matching its neighbours and the row goes ragged. */
.grid > .card { align-self: stretch; }

/* --- the readiness ring --------------------------------------------------
   A 270° arc rather than a full circle: the gap gives the number somewhere to
   sit and reads faster at a glance than a closed ring. pathLength="100" lets
   the dash offset be set straight from the percentage. */

.ring-wrap { display: flex; align-items: center; gap: 22px; flex-wrap: wrap; }

.ring { position: relative; width: 152px; height: 152px; flex: 0 0 auto; }
.ring svg { width: 100%; height: 100%; transform: rotate(0deg); }
.ring .track { stroke: var(--line-soft); }
.ring .fill {
  stroke: var(--tone, var(--brand));
  stroke-linecap: round;
  stroke-dasharray: 100;
  stroke-dashoffset: 100;
  animation: ring-fill 1.1s var(--ease) forwards;
  animation-delay: .15s;
}
@keyframes ring-fill { to { stroke-dashoffset: var(--gap); } }
@media (prefers-reduced-motion: reduce) {
  .ring .fill { animation: none; stroke-dashoffset: var(--gap); }
}

.ring-mid {
  position: absolute; inset: 0;
  display: flex; flex-direction: column;
  align-items: center; justify-content: center;
  padding-bottom: 14px;
}
.ring-num {
  font-size: 40px; font-weight: 800; line-height: 1;
  color: var(--tone, var(--brand));
  letter-spacing: -.02em;
}
.ring-cap { font-size: 11.5px; color: var(--ink-3); margin-top: 3px; }

.ring-tone-ok   { --tone: var(--ok); }
.ring-tone-warn { --tone: var(--warn); }
.ring-tone-bad  { --tone: var(--bad); }

.verdict { flex: 1; min-width: 200px; }
.verdict-title { font-size: 18px; font-weight: 800; margin-bottom: 6px; }
.verdict-note { font-size: 13px; color: var(--ink-2); line-height: 1.65; }

.count-strip {
  display: flex; flex-wrap: wrap; gap: 6px; margin-top: 12px;
}
.count-chip {
  display: inline-flex; align-items: center; gap: 5px;
  font-size: 12px; font-weight: 600;
  padding: 4px 10px;
  border-radius: var(--r-pill);
  background: var(--line-soft);
  color: var(--ink-2);
}
.count-chip i { width: 7px; height: 7px; border-radius: 50%; display: inline-block; }

/* --- axis bars ------------------------------------------------------------ */

.axes { display: grid; gap: 11px; }
.axis {
  display: grid;
  grid-template-columns: minmax(0, 1.15fr) minmax(70px, 1.5fr) 46px;
  align-items: center;
  gap: 12px;
}
.axis-name { font-size: 13px; color: var(--ink-2); }
.axis-track {
  height: 7px; border-radius: var(--r-pill);
  background: var(--line-soft); overflow: hidden;
}
.axis-track i {
  display: block; height: 100%; border-radius: var(--r-pill);
  background: var(--c, var(--brand));
  width: 0;
  animation: axis-grow .9s var(--ease) forwards;
}
@keyframes axis-grow { to { width: var(--w); } }
@media (prefers-reduced-motion: reduce) {
  .axis-track i { animation: none; width: var(--w); }
}
.axis-val {
  font-size: 12.5px; font-weight: 700; text-align: end;
  font-variant-numeric: tabular-nums; color: var(--c, var(--ink));
}

/* --- action list ---------------------------------------------------------
   The visual anchor of the home page. Everything else on that screen is
   reference; this is the part a customer can act on. */

.action {
  display: flex; align-items: flex-start; gap: 13px;
  padding: 15px 18px;
  border-bottom: 1px solid var(--line-soft);
  transition: background .15s var(--ease);
}
.action:last-child { border-bottom: 0; }
.action:hover { background: var(--card-alt); }

.action-mark {
  width: 36px; height: 36px; border-radius: 10px;
  display: grid; place-items: center; flex: 0 0 auto;
  background: var(--line-soft); color: var(--ink-2);
}
.action-mark svg { width: 18px; height: 18px; }
.action-bad  .action-mark { background: var(--bad-tint);  color: var(--bad); }
.action-warn .action-mark { background: var(--warn-tint); color: var(--warn); }
.action-ok   .action-mark { background: var(--ok-tint);   color: var(--ok); }
.action-info .action-mark { background: var(--info-tint); color: var(--info); }
/* The house colour, for actions that are simply the thing to do next rather
   than a warning about something. It was three identical style attributes on
   the quick-action cards, which put the colours out of reach of both themes
   and of this file. */
.action-brand .action-mark { background: var(--brand-tint); color: var(--brand-dark); }

.action-body { flex: 1; min-width: 0; }
/* Spans, so they need to be told to stack — otherwise the title and its
   context run together as one sentence. */
.action-title { display: block; font-size: 14px; font-weight: 600; line-height: 1.45; }
.action-meta { display: block; font-size: 12px; color: var(--ink-3); margin-top: 3px; }
.action-side { flex: 0 0 auto; display: flex; align-items: center; gap: 8px; }

/* --- chips --------------------------------------------------------------- */

.chip {
  display: inline-flex; align-items: center; gap: 5px;
  font-size: 11.5px; font-weight: 700;
  padding: 3px 10px;
  border-radius: var(--r-pill);
  white-space: nowrap;
}
.chip-ok   { background: var(--ok-tint);   color: var(--ok); }
.chip-warn { background: var(--warn-tint); color: var(--warn); }
.chip-bad  { background: var(--bad-tint);  color: var(--bad); }
.chip-info { background: var(--info-tint); color: var(--info); }
.chip-mute { background: var(--line-soft); color: var(--ink-3); }
.chip-brand{ background: var(--brand-tint);color: var(--brand-dark); }

/* --- buttons ------------------------------------------------------------- */

.btn {
  display: inline-flex; align-items: center; justify-content: center; gap: 7px;
  font-family: inherit;
  font-size: 14px; font-weight: 700;
  padding: 10px 18px;
  border-radius: var(--r-sm);
  border: 1px solid transparent;
  cursor: pointer;
  transition: transform .12s var(--ease), box-shadow .15s var(--ease),
              background .15s var(--ease);
}
.btn:hover { text-decoration: none; }
.btn:active { transform: translateY(1px); }
.btn svg { width: 17px; height: 17px; }

.btn-primary {
  background: var(--brand-dark); color: var(--brand-ink);
  box-shadow: 0 1px 2px rgba(16, 32, 28, .12);
}
.btn-primary:hover { background: var(--brand-darker); color: var(--brand-ink); }

.btn-soft { background: var(--brand-tint); color: var(--brand-dark); }
.btn-soft:hover { background: var(--brand-dark); color: var(--brand-ink); }

.btn-ghost { background: transparent; color: var(--ink-2); border-color: var(--line); }
.btn-ghost:hover { background: var(--line-soft); color: var(--ink); }

.btn-danger { background: transparent; color: var(--bad); border-color: var(--bad); }
.btn-danger:hover { background: var(--bad); color: var(--fill-ink); }

.btn-sm { font-size: 12.5px; padding: 7px 13px; }
.btn-lg { font-size: 15px; padding: 13px 24px; }
.btn-block { width: 100%; }

/* --- the exposure comparison ---------------------------------------------
   The whole point is the comparison, so the two figures sit side by side with
   the multiple between them. Four separate tiles buried the very thing the
   customer is meant to weigh. */

.compare {
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  gap: 16px;
  padding: 22px 20px;
}
.compare-side { text-align: center; }
.compare-label { font-size: 12px; color: var(--ink-3); margin-bottom: 5px; }
.compare-num {
  font-size: clamp(22px, 4.4vw, 30px); font-weight: 800; line-height: 1.1;
  letter-spacing: -.02em;
}
.compare-unit { font-size: 11.5px; color: var(--ink-3); margin-top: 3px; }
.compare-vs {
  width: 46px; height: 46px; border-radius: 50%;
  background: var(--warn-tint); color: var(--warn);
  display: grid; place-items: center;
  font-weight: 800; font-size: 14px;
  flex: 0 0 auto;
}
.compare-risk .compare-num { color: var(--bad); }
.compare-pay .compare-num { color: var(--ok); }

@media (max-width: 520px) {
  .compare { grid-template-columns: 1fr; gap: 12px; }
  .compare-vs { margin: 0 auto; }
}

/* --- stat tiles ---------------------------------------------------------- */

.stat {
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--r);
  padding: 15px 17px;
  box-shadow: var(--sh-1);
}
.stat-label { font-size: 12px; color: var(--ink-3); }
.stat-num {
  font-size: 25px; font-weight: 800; line-height: 1.2; margin-top: 2px;
  letter-spacing: -.02em;
}
.stat-sub { font-size: 11.5px; color: var(--ink-3); }
.stat-ok   .stat-num { color: var(--ok); }
.stat-warn .stat-num { color: var(--warn); }
.stat-bad  .stat-num { color: var(--bad); }

/* --- facility switcher ---------------------------------------------------- */

.site-tabs { display: flex; gap: 8px; flex-wrap: wrap; margin-bottom: 16px; }
.site-tab {
  display: flex; align-items: center; gap: 9px;
  padding: 9px 14px;
  border-radius: var(--r-pill);
  border: 1px solid var(--line);
  background: var(--card);
  font-size: 13px; font-weight: 600;
  color: var(--ink-2);
  transition: all .15s var(--ease);
}
.site-tab:hover { border-color: var(--brand); color: var(--ink); text-decoration: none; }
.site-tab.on {
  background: var(--brand-dark); border-color: var(--brand-dark); color: var(--brand-ink);
}
.site-tab .dot { width: 8px; height: 8px; border-radius: 50%; }

/* --- segmented control ---------------------------------------------------- */

.seg {
  display: inline-flex; gap: 3px; padding: 3px;
  background: var(--line-soft); border-radius: var(--r-sm);
  overflow-x: auto; max-width: 100%;
  scrollbar-width: none;
}
.seg::-webkit-scrollbar { display: none; }
.seg a {
  padding: 7px 13px;
  border-radius: 6px;
  font-size: 12.5px; font-weight: 600;
  color: var(--ink-2);
  white-space: nowrap;
  transition: background .15s var(--ease), color .15s var(--ease);
}
.seg a:hover { color: var(--ink); text-decoration: none; }
.seg a.on { background: var(--card); color: var(--ink); box-shadow: var(--sh-1); }

/* --- accordion (the 49-item register) -------------------------------------
   Forty-nine rows in one flat table is a wall. Grouped by axis, with the
   groups that have problems open by default, it becomes readable. */

.acc { border: 1px solid var(--line); border-radius: var(--r); overflow: hidden; background: var(--card); }
.acc + .acc { margin-top: 10px; }
.acc-head {
  display: flex; align-items: center; gap: 11px;
  padding: 14px 17px;
  cursor: pointer;
  list-style: none;
  transition: background .15s var(--ease);
}
.acc-head::-webkit-details-marker { display: none; }
.acc-head:hover { background: var(--card-alt); }
.acc-title { font-size: 14px; font-weight: 700; flex: 1; }
.acc-chev {
  width: 18px; height: 18px; color: var(--ink-3);
  transition: transform .2s var(--ease);
}
details[open] .acc-chev { transform: rotate(180deg); }
.acc-body { border-top: 1px solid var(--line-soft); }

.ob {
  padding: 14px 17px;
  border-bottom: 1px solid var(--line-soft);
}
.ob:last-child { border-bottom: 0; }
.ob-top { display: flex; align-items: flex-start; gap: 10px; }
.ob-title { font-size: 13.5px; font-weight: 600; flex: 1; line-height: 1.5; }
.ob-grid {
  display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
  gap: 4px 16px; margin-top: 9px;
}
.ob-fact { font-size: 12px; color: var(--ink-3); }
.ob-fact b { color: var(--ink-2); font-weight: 600; }

/* --- timeline ------------------------------------------------------------- */

.tl { position: relative; padding-inline-start: 26px; }
.tl::before {
  content: ""; position: absolute;
  inset-inline-start: 7px; top: 8px; bottom: 8px;
  width: 2px; background: var(--line);
}
.tl-item { position: relative; padding-bottom: 20px; }
.tl-item:last-child { padding-bottom: 0; }
.tl-item::before {
  content: ""; position: absolute;
  inset-inline-start: -25px; top: 4px;
  width: 14px; height: 14px; border-radius: 50%;
  background: var(--card); border: 2.5px solid var(--line);
}
.tl-done::before   { background: var(--ok);   border-color: var(--ok); }
.tl-active::before { border-color: var(--brand); box-shadow: 0 0 0 4px var(--brand-tint); }
.tl-block::before  { background: var(--bad);  border-color: var(--bad); }
.tl-label { font-size: 13.5px; font-weight: 600; }
.tl-meta { font-size: 12px; color: var(--ink-3); margin-top: 2px; }

/* --- progress ------------------------------------------------------------- */

.prog { height: 8px; border-radius: var(--r-pill); background: var(--line-soft); overflow: hidden; }
.prog i {
  display: block; height: 100%; border-radius: var(--r-pill);
  background: linear-gradient(90deg, var(--brand), var(--brand-dark));
  width: 0;
  animation: axis-grow .9s var(--ease) forwards;
}

/* --- messages ------------------------------------------------------------- */

.thread { display: flex; flex-direction: column; gap: 12px; }
.bubble {
  max-width: 82%;
  padding: 11px 15px;
  border-radius: var(--r);
  font-size: 13.5px;
  line-height: 1.65;
}
.bubble-office {
  background: var(--brand-tint); color: var(--ink);
  align-self: flex-start;
  border-end-start-radius: 4px;
}
.bubble-me {
  background: var(--line-soft); color: var(--ink);
  align-self: flex-end;
  border-end-end-radius: 4px;
}
.bubble-who { font-size: 11px; color: var(--ink-3); margin-bottom: 4px; font-weight: 600; }

/* --- notes / callouts ------------------------------------------------------ */

.note {
  display: flex; gap: 11px;
  padding: 13px 16px;
  border-radius: var(--r);
  background: var(--card-alt);
  border: 1px solid var(--line);
  font-size: 12.5px; line-height: 1.7; color: var(--ink-2);
}
.note svg { width: 17px; height: 17px; flex: 0 0 auto; margin-top: 2px; color: var(--ink-3); }
.note-warn { background: var(--warn-tint); border-color: transparent; color: #6B3F08; }
.note-warn svg { color: var(--warn); }
.note-bad  { background: var(--bad-tint);  border-color: transparent; color: #7A1616; }
.note-bad svg { color: var(--bad); }
.note-ok   { background: var(--ok-tint);   border-color: transparent; color: #1D4F21; }
.note-ok svg { color: var(--ok); }
.note-brand{ background: var(--brand-tint);border-color: transparent; color: var(--brand-darker); }
.note-brand svg { color: var(--brand-dark); }

[data-bs-theme="dark"] .note-warn,
[data-bs-theme="dark"] .note-bad,
[data-bs-theme="dark"] .note-ok,
[data-bs-theme="dark"] .note-brand { color: var(--ink); }

/* Legal disclaimers. Quieter than a callout — they must be present and legible
   without shouting on every screen they appear. */
.fineprint {
  font-size: 11.5px; line-height: 1.7; color: var(--ink-3);
  padding: 11px 14px;
  border-inline-start: 2px solid var(--line);
  background: var(--card-alt);
  border-radius: 0 var(--r-sm) var(--r-sm) 0;
}

/* --- tables (kept only where genuinely tabular) ---------------------------- */

.tbl-wrap { overflow-x: auto; border-radius: var(--r); }
table.t { width: 100%; border-collapse: collapse; font-size: 13px; }
table.t th {
  text-align: start; font-size: 11.5px; font-weight: 600; color: var(--ink-3);
  padding: 11px 15px; border-bottom: 1px solid var(--line);
  white-space: nowrap; background: var(--card-alt);
}
table.t td {
  padding: 12px 15px; border-bottom: 1px solid var(--line-soft);
  vertical-align: middle;
}
table.t tr:last-child td { border-bottom: 0; }
table.t td.num { text-align: end; font-variant-numeric: tabular-nums; white-space: nowrap; }
table.t tbody tr { transition: background .12s var(--ease); }
table.t tbody tr:hover { background: var(--card-alt); }

/* --- forms ---------------------------------------------------------------- */

.field { margin-bottom: 15px; }
.field label {
  display: block; font-size: 13px; font-weight: 600;
  color: var(--ink-2); margin-bottom: 6px;
}
.field .hint { font-size: 11.5px; color: var(--ink-3); margin-top: 5px; }

.input, .portal select, .portal textarea {
  width: 100%;
  font-family: inherit; font-size: 14px;
  color: var(--ink);
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: var(--r-sm);
  padding: 11px 13px;
  transition: border-color .15s var(--ease), box-shadow .15s var(--ease);
}
.input:focus, .portal select:focus, .portal textarea:focus {
  outline: none;
  border-color: var(--brand);
  box-shadow: 0 0 0 3px var(--brand-tint);
}
.portal textarea { min-height: 96px; resize: vertical; line-height: 1.6; }
.portal select {
  appearance: none;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%237B8A85' stroke-width='2.2' stroke-linecap='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E");
  background-repeat: no-repeat;
  background-position: left 12px center;
  background-size: 17px;
  padding-inline-end: 13px;
  padding-inline-start: 38px;
}

.pick { display: flex; flex-wrap: wrap; gap: 8px; }
.pick input { position: absolute; opacity: 0; pointer-events: none; }
.pick label {
  padding: 9px 15px;
  border: 1px solid var(--line);
  border-radius: var(--r-pill);
  background: var(--card);
  font-size: 13px; font-weight: 600; color: var(--ink-2);
  cursor: pointer; margin: 0;
  transition: all .15s var(--ease);
}
.pick label:hover { border-color: var(--brand); }
.pick input:checked + label {
  background: var(--brand-dark); border-color: var(--brand-dark); color: var(--brand-ink);
}
.pick input:focus-visible + label { box-shadow: 0 0 0 3px var(--brand-tint); }

/* File field.

   The native control renders its button and "no file chosen" text in the
   browser's own language, which in an otherwise entirely Arabic interface reads
   as a broken page. The real input is hidden and driven by the label. */
.filefield input[type="file"] {
  position: absolute;
  width: 1px; height: 1px;
  opacity: 0;
  overflow: hidden;
}
.filefield label.filebtn {
  display: flex; align-items: center; gap: 10px;
  padding: 11px 14px;
  border: 1px dashed var(--line);
  border-radius: var(--r-sm);
  background: var(--card);
  cursor: pointer;
  font-size: 13.5px; font-weight: 600; color: var(--ink-2);
  margin: 0;
  transition: border-color .15s var(--ease), background .15s var(--ease);
}
.filefield label.filebtn:hover { border-color: var(--brand); background: var(--brand-tint); }
.filefield input[type="file"]:focus-visible + label.filebtn {
  border-color: var(--brand);
  box-shadow: 0 0 0 3px var(--brand-tint);
}
.filefield .filename {
  flex: 1; min-width: 0;
  font-weight: 500; color: var(--ink-3);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.filefield.has-file label.filebtn { border-style: solid; border-color: var(--brand); }
.filefield.has-file .filename { color: var(--ink); font-weight: 600; }

.check { display: flex; align-items: center; gap: 9px; cursor: pointer; }
.check input { width: 18px; height: 18px; accent-color: var(--brand-dark); }
.check span { font-size: 13.5px; color: var(--ink-2); }

/* --- empty states --------------------------------------------------------- */

.empty { text-align: center; padding: 44px 20px; }
.empty-art {
  width: 62px; height: 62px; margin: 0 auto 14px;
  border-radius: 50%;
  background: var(--brand-tint);
  display: grid; place-items: center;
  color: var(--brand-dark);
}
.empty-art svg { width: 27px; height: 27px; }
.empty-title { font-size: 15px; font-weight: 700; margin-bottom: 5px; }
.empty-text { font-size: 13px; color: var(--ink-3); max-width: 340px; margin: 0 auto 16px; }

/* --- misc ----------------------------------------------------------------- */

.row-link { color: inherit; }
.row-link:hover { text-decoration: none; }

.flex { display: flex; align-items: center; gap: 10px; }
.flex > span > .action-title,
.flex > span > .action-meta { display: block; }
.between { display: flex; align-items: center; justify-content: space-between; gap: 12px; flex-wrap: wrap; }
.mt-s { margin-top: 8px; } .mt-m { margin-top: 16px; } .mt-l { margin-top: 26px; }
.muted { color: var(--ink-3); }
.small { font-size: 12.5px; }
.nowrap { white-space: nowrap; }

.section-label {
  font-size: 12px; font-weight: 700; color: var(--ink-3);
  margin: 26px 0 11px;
  display: flex; align-items: center; gap: 9px;
}
.section-label::after {
  content: ""; flex: 1; height: 1px; background: var(--line);
}

.skip {
  position: absolute; inset-inline-start: -9999px;
  background: var(--brand-dark); color: var(--brand-ink);
  padding: 10px 16px; border-radius: 0 0 var(--r-sm) 0; z-index: 100;
}
.skip:focus { inset-inline-start: 0; }

.portal :focus-visible {
  outline: 2px solid var(--brand);
  outline-offset: 2px;
  border-radius: 4px;
}

@media print {
  .p-header, .p-nav, .p-tabbar, .btn { display: none !important; }
  .card { box-shadow: none; break-inside: avoid; }
  .portal { background: #fff; }
}

/* --- marketing banner -------------------------------------------------------
   Shown in the two moments where a customer is looking at nothing: before
   signing in, and after signing in with no request, offer or project open.
   Those are the only unpaid advertising the office owns.

   It sits on the brand field so it reads as the company speaking, and it is
   visually distinct from the compliance surfaces above it — a customer must
   never mistake a promotion for a finding about their facility. */

.mk {
  border-radius: var(--r-lg);
  padding: 26px 24px;
  margin-bottom: 20px;
}
.mk-head { max-width: 640px; position: relative; z-index: 1; }
.mk-eyebrow {
  font-size: 12px; font-weight: 700; letter-spacing: .02em;
  opacity: .82; margin-bottom: 6px;
}
.mk-title {
  font-size: clamp(19px, 3vw, 25px); font-weight: 800; line-height: 1.4;
  letter-spacing: -.01em;
}
.mk-body { font-size: 13.5px; line-height: 1.85; opacity: .92; margin-top: 8px; }

.mk-cards {
  display: grid; gap: 12px; margin-top: 20px;
  grid-template-columns: repeat(auto-fit, minmax(215px, 1fr));
  position: relative; z-index: 1;
}
.mk-card {
  background: rgba(255, 255, 255, .12);
  border: 1px solid rgba(255, 255, 255, .18);
  border-radius: var(--r);
  padding: 14px 16px;
  backdrop-filter: blur(2px);
}
.mk-card-ico {
  width: 32px; height: 32px; border-radius: 9px;
  background: rgba(255, 255, 255, .16);
  display: grid; place-items: center; margin-bottom: 10px;
}
.mk-card-ico svg { width: 17px; height: 17px; }
.mk-fig {
  font-size: 27px; font-weight: 800; line-height: 1.1; letter-spacing: -.02em;
}
.mk-fig-note { font-size: 11.5px; opacity: .78; margin-bottom: 8px; }
.mk-card-t { font-size: 14px; font-weight: 700; line-height: 1.45; }
.mk-card-b { font-size: 12.5px; line-height: 1.8; opacity: .88; margin-top: 5px; }

.mk-cta {
  display: inline-flex; align-items: center; gap: 7px;
  margin-top: 11px; font-size: 12.5px; font-weight: 700;
  color: #fff; text-decoration: underline; text-underline-offset: 3px;
}
.mk-actions {
  display: flex; gap: 10px; flex-wrap: wrap; margin-top: 20px;
  position: relative; z-index: 1;
}
.mk-btn {
  background: #fff; color: #07730E;  /* pinned: the field is dark green in both themes */
  padding: 11px 20px; border-radius: var(--r-sm);
  font-size: 14px; font-weight: 700;
  display: inline-flex; align-items: center; gap: 7px;
}
.mk-btn:hover { background: #F2F7F1; color: #07730E; text-decoration: none; }
.mk-btn-ghost {
  background: transparent; color: #fff;
  border: 1px solid rgba(255, 255, 255, .45);
}
.mk-btn-ghost:hover { background: rgba(255, 255, 255, .12); color: #fff; }

/* A quieter variant for the sign-in column, where width is short and the card
   grid would crush. */
.mk-slim { padding: 18px 20px; }
.mk-slim .mk-title { font-size: 18px; }
.mk-slim .mk-body { font-size: 12.5px; margin-top: 6px; }
.mk-slim .mk-cards { grid-template-columns: 1fr; gap: 7px; margin-top: 14px; }
/* One line per card: icon, an optional figure, and the headline. The body copy
   is what makes the full variant tall, and it is the part a visitor scanning a
   sign-in screen will not read anyway. */
.mk-slim .mk-card {
  display: flex; align-items: center; gap: 10px;
  padding: 9px 12px;
}
.mk-slim .mk-card-ico { width: 26px; height: 26px; margin: 0; }
.mk-slim .mk-card-ico svg { width: 14px; height: 14px; }
.mk-slim .mk-card-b,
.mk-slim .mk-fig-note { display: none; }
.mk-slim .mk-fig {
  font-size: 15px; font-weight: 800; min-width: 34px; order: 3;
  margin-inline-start: auto; text-align: end;
}
.mk-slim .mk-card-t { font-size: 12.5px; font-weight: 600; line-height: 1.4; }

/* --- link-coloured components ----------------------------------------------
   `.portal a` is one class plus one element (0,1,1). A component class such as
   `.btn-primary` is one class (0,1,0). The link rule therefore outranked it,
   and any button rendered as an <a> took the link colour for its text — brand
   green on a brand-green fill, a contrast ratio of 1.00:1 and literally
   invisible. Buttons written as <button> were unaffected, which is why the
   sign-in screen looked fine and the rest did not.

   Re-stating each variant under `.portal` (0,2,0) puts it back above the link
   rule without weakening the default link colour. Anything added later that
   sets a colour on a component must do the same. */

.portal .btn-primary,
.portal .btn-primary:hover     { color: var(--brand-ink); }
.portal .btn-soft              { color: var(--brand-dark); }
.portal .btn-soft:hover        { color: var(--brand-ink); }
.portal .btn-ghost             { color: var(--ink-2); }
.portal .btn-ghost:hover       { color: var(--ink); }
.portal .btn-danger            { color: var(--bad); }
.portal .btn-danger:hover      { color: var(--fill-ink); }

.portal .mk-btn,
.portal .mk-btn:hover          { color: #07730E; }
.portal .mk-btn-ghost,
.portal .mk-btn-ghost:hover    { color: #fff; }
.portal .mk-cta                { color: #fff; }

.portal .skip                  { color: var(--brand-ink); }
.portal .site-tab              { color: var(--ink-2); }
.portal .site-tab.on           { color: var(--brand-ink); }
.portal .seg a                 { color: var(--ink-2); }
.portal .seg a.on              { color: var(--ink); }
.portal .p-nav a               { color: var(--ink-2); }
.portal .p-nav a.on            { color: var(--brand-dark); }
.portal .p-tabbar a            { color: var(--ink-3); }
.portal .p-tabbar a.on         { color: var(--brand-dark); }


/* --- work waiting in another company ---------------------------------------
   Reads as an alert, not as navigation: it appears only when something in a
   company you are not currently looking at needs you, and pressing it both
   switches company and takes you there. Amber rather than red — it is someone
   waiting on you, not a breach. */

.xco-form { margin: 0 0 12px; }
.xco {
  display: flex; align-items: center; gap: 11px; width: 100%;
  padding: 11px 13px; text-align: start; cursor: pointer;
  font: inherit; color: var(--ink);
  background: var(--warn-tint); border: 1px solid var(--warn);
  border-radius: var(--r);
}
.xco:hover { background: var(--warn); color: var(--fill-ink); }
.xco:hover .xco-what, .xco:hover .xco-go { color: inherit; }
.xco-ico { display: grid; place-items: center; flex: none; color: var(--warn); }
.xco:hover .xco-ico { color: inherit; }
.xco-ico svg { width: 17px; height: 17px; }
.xco-text { display: flex; flex-direction: column; gap: 1px; min-width: 0; flex: 1; }
.xco-name { font-size: 13px; font-weight: 700; line-height: 1.3; }
.xco-what { font-size: 11.5px; color: var(--ink-2); line-height: 1.35; }
.xco-go {
  display: inline-flex; align-items: center; gap: 5px; flex: none;
  font-size: 11.5px; font-weight: 600; color: var(--warn);
}
.xco-go svg { width: 13px; height: 13px; }

@media (max-width: 560px) {
  .xco-go span, .xco-go { font-size: 0; }
  .xco-go svg { width: 15px; height: 15px; }
}

/* --- signature pad ---------------------------------------------------------
   Sized like a signature line on paper rather than like a drawing app: wide,
   short, with a ruled baseline. The hint sits inside and disappears on the
   first stroke, so an empty pad never looks like a signed one. */

.sigpad {
  position: relative;
  height: 150px;
  border: 1px dashed var(--line);
  border-radius: var(--r);
  background: var(--card-alt);
  overflow: hidden;
  touch-action: none;          /* or a finger scrolls the page instead of signing */
}
.sigpad::after {
  content: ""; position: absolute; inset-inline: 22px; inset-block-end: 38px;
  border-block-end: 1px solid var(--line);
}
.sigpad canvas { position: absolute; inset: 0; width: 100%; height: 100%; cursor: crosshair; }
.sigpad-hint {
  position: absolute; inset-block-end: 12px; inset-inline-start: 24px;
  font-size: 12px; color: var(--ink-3); pointer-events: none;
}
.sigpad-tools {
  display: flex; align-items: center; gap: 12px;
  margin-block-start: 8px; flex-wrap: wrap;
}

/* The signature as recorded, shown back to whoever signed it. */
.sig-proof { display: flex; gap: 14px; align-items: center; flex-wrap: wrap; }
.sig-proof img {
  height: 64px; max-width: 240px; object-fit: contain;
  background: #fff; border: 1px solid var(--line); border-radius: var(--r-sm);
  padding: 4px;
}
.sig-seal {
  font-family: ui-monospace, "SF Mono", Menlo, Consolas, monospace;
  font-size: 11px; letter-spacing: .02em; color: var(--ink-2);
  background: var(--line-soft); border-radius: var(--r-sm); padding: 3px 7px;
  direction: ltr; display: inline-block; unicode-bidi: isolate;
}

/* The `hidden` attribute only works while nothing outranks it. The UA sets
   [hidden] { display: none }, which any author rule setting `display` beats —
   so a component styled `display: flex` ignores it and shows anyway. This bit
   a hidden note that was meant to appear only once a site had been chosen. */
[hidden] { display: none !important; }

/* --- sparkline -------------------------------------------------------------
   The portal loads only brand.css and this file, so the copy of these rules in
   platform.css never applied here: the customer's telemetry chart rendered as a
   zero-height strip with its caption underneath, which reads as padding rather
   than as a missing chart. Nothing catches that — the page returns 200, the
   text is all present, and the contrast audit has no text to measure.

   Kept deliberately plain. It answers "is this trending up" at a glance; the
   numbers above it are where a figure is actually read. */

.spark {
  display: flex;
  align-items: flex-end;
  gap: 3px;
  height: 56px;
  padding-block-start: 4px;
}
.spark > i {
  flex: 1 1 0;
  min-width: 2px;
  min-height: 2px;
  border-radius: 2px 2px 0 0;
  background: var(--brand-dark);
  opacity: .55;
  transition: opacity .12s var(--ease);
}
.spark > i:hover { opacity: 1; }

/* A day that contained a doubtful reading, or one over the limit. Red rather
   than a shade of the brand, because it means something different in kind. */
.spark > i.over { background: var(--bad); opacity: 1; }


/* --- the portfolio header --------------------------------------------------
   A client with several sites opens this page to find out *which* one wants
   them. So the sites are all present and small, with the overall figure beside
   them, and any one of them expands into detail below on a press.

   Deliberately not a chart. Six numbers and six bars are read faster than any
   visualisation of six numbers, and the bar is doing the comparison the eye
   would otherwise have to do. */

.pf {
  display: grid;
  grid-template-columns: minmax(180px, 220px) 1fr;
  gap: 12px;
  margin-bottom: 14px;
}

.pf-all {
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 2px;
  padding: 14px 16px;
  border: 1px solid var(--line);
  border-radius: var(--r);
  background: var(--card);
  text-align: start;
}
.pf-all:hover { border-color: var(--brand); text-decoration: none; }
.pf-all.on { border-color: var(--brand-dark); box-shadow: inset 0 0 0 1px var(--brand-dark); }
.pf-all-k { font-size: 11.5px; color: var(--ink-3); }
.pf-all-v { font-size: 30px; font-weight: 800; line-height: 1.05; }
.pf-all-x { font-size: 11px; color: var(--ink-3); }

.pf-sites { display: grid; gap: 6px; align-content: center; }

.pf-site {
  display: grid;
  grid-template-columns: 68px 1fr auto;
  align-items: center;
  gap: 10px;
  padding: 7px 12px;
  border: 1px solid var(--line);
  border-radius: var(--r-sm);
  background: var(--card);
  color: var(--ink);
}
.pf-site:hover { border-color: var(--brand); text-decoration: none; }
.pf-site.on {
  border-color: var(--brand-dark);
  background: var(--brand-tint);
  box-shadow: inset 0 0 0 1px var(--brand-dark);
}
.pf-name {
  font-size: 12.5px; font-weight: 600; line-height: 1.3;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.pf-val { font-size: 13.5px; font-weight: 800; font-variant-numeric: tabular-nums; }

.pf-bar {
  display: block; height: 7px; border-radius: 4px;
  background: var(--line-soft); overflow: hidden;
}
.pf-bar > i { display: block; height: 100%; border-radius: 4px; }

/* The status tones, shared by the bar fill and the figure beside it, so the
   colour means the same thing in both places. */
.tone-ok   { color: var(--ok); }
.tone-warn { color: var(--warn); }
.tone-bad  { color: var(--bad); }
.pf-bar > i.tone-ok   { background: var(--ok); }
.pf-bar > i.tone-warn { background: var(--warn); }
.pf-bar > i.tone-bad  { background: var(--bad); }

/* Says plainly that the page has narrowed, because a filtered list that does
   not say it is filtered is how someone concludes they have no work. */
.pf-filter {
  display: flex; align-items: center; gap: 9px; flex-wrap: wrap;
  padding: 9px 13px; margin-bottom: 14px;
  font-size: 12.5px;
  background: var(--brand-tint);
  border-radius: var(--r-sm);
}
.pf-filter svg { width: 15px; height: 15px; flex: none; color: var(--brand-dark); }
.pf-filter a { margin-inline-start: auto; font-weight: 600; }

/* The zoom: the chosen site's detail arrives rather than simply being there.
   Small and quick — it marks the transition, it is not a performance. */
@media (prefers-reduced-motion: no-preference) {
  .pf-zoom { animation: pf-in .22s var(--ease) both; }
  @keyframes pf-in {
    from { opacity: 0; transform: scale(.985) translateY(-4px); }
    to   { opacity: 1; transform: none; }
  }
}

@media (max-width: 700px) {
  .pf { grid-template-columns: 1fr; }
  .pf-site { grid-template-columns: 52px 1fr auto; }
}


/* --- the offer document, as the customer reads it --------------------------
   The same text the office wrote, in the portal's own type rather than a
   facsimile of Word. A customer reading a quotation on a phone is better served
   by their own line lengths than by a reproduction of an A4 page. */

.doc-read { line-height: 1.9; }
.doc-read h2 { font-size: 20px; margin: 0 0 14px; }
.doc-read h3 { font-size: 16px; margin: 22px 0 8px; color: var(--brand-dark); }
.doc-read h4 { font-size: 14.5px; margin: 18px 0 6px; }
.doc-read p, .doc-read li { margin: 0 0 9px; }
.doc-read ul, .doc-read ol { padding-inline-start: 22px; }

.doc-read table {
  width: 100%; border-collapse: collapse; margin: 10px 0 18px; font-size: 13px;
}
.doc-read th, .doc-read td {
  border: 1px solid var(--line); padding: 8px 10px;
  text-align: start; vertical-align: top;
}
.doc-read th { background: var(--line-soft); font-weight: 700; }

/* Wide tables scroll inside their own container rather than pushing the page
   sideways — a quotation table on a phone is otherwise unreadable. */
.doc-read table { display: block; overflow-x: auto; white-space: nowrap; }
.doc-read td, .doc-read th { white-space: normal; min-width: 90px; }

/* An unfilled blank, if one ever reaches a customer. It should look like the
   mistake it is rather than like ordinary text. */
.doc-read .doc-blank {
  background: var(--warn-tint); color: var(--warn);
  padding: 0 3px; border-radius: 2px;
}

/* --- the company heading on شركاتي ومنشآتي ---------------------------------
   A company name was set in .section-label: 12px, weight 700, and the muted
   ink meant for a caption. It is the title of everything under it, and at that
   size it was read as a divider and skipped. */

.org-title {
  display: flex;
  align-items: center;
  gap: 9px;
  flex-wrap: wrap;
  margin: 26px 0 11px;
  font-size: 19px;
  font-weight: 700;
  line-height: 1.35;
  color: var(--ink);
}
.org-title .chip { font-size: 11px; font-weight: 700; }

/* --- the public legal documents -------------------------------------------
   Terms, privacy and the disclaimers, on the signed-out shell. Long prose
   rather than an interface, so it gets a reading measure and headings that
   separate clauses — a wall of justified Arabic at interface size is a
   document people scroll past rather than read. */

.legal { max-inline-size: 68ch; }

.legal h1 {
  font-size: 24px;
  font-weight: 700;
  line-height: 1.3;
  margin: 0 0 4px;
  color: var(--ink);
}

.legal h2 {
  font-size: 16px;
  font-weight: 700;
  line-height: 1.4;
  margin: 26px 0 8px;
  color: var(--ink);
}

.legal p,
.legal li {
  font-size: 15px;
  line-height: 1.85;
  color: var(--ink-2);
}

.legal ul { padding-inline-start: 20px; margin: 10px 0; }
.legal li { margin-bottom: 7px; }
.legal strong { color: var(--ink); }
.legal em { font-style: normal; text-decoration: underline; text-underline-offset: 3px; }

/* The confidentiality clauses, read in the moment somebody wants to see a
   price. Numbered and spaced so the eye can land on one — the version before
   this was a single paragraph, which is the shape of text people skip. */
.undertaking { padding-inline-start: 22px; margin: 12px 0 4px; }
.undertaking li {
  margin-bottom: 11px;
  line-height: 1.8;
  color: var(--ink-2);
  font-size: 14.5px;
}
.undertaking li::marker { color: var(--ink-3); font-weight: 700; }

/* --- an account with no company ------------------------------------------
   Shown at the top of every portal page while the account belongs to no
   company. The button is the answer to the sentence beside it, so it sits on
   the same line and stays visible; on a phone it drops under the text at full
   width rather than squeezing the sentence into a column. */

.p-nocompany { align-items: center; margin-bottom: 18px; }
.p-nocompany-text { flex: 1 1 auto; }
.p-nocompany .btn { flex: 0 0 auto; }
@media (max-width: 560px) {
  .p-nocompany { flex-wrap: wrap; }
  .p-nocompany .btn { width: 100%; }
}

/* --- the portal's error page --------------------------------------------- */
.p-error { max-width: 520px; margin: 6vh auto; text-align: center; }
.p-error-code { font-size: 48px; font-weight: 800; color: var(--ink-3); line-height: 1; }
.p-error p { margin: 14px 0 20px; color: var(--ink-2); }

/* --- the account page -----------------------------------------------------
   The account code leads, set large in the mono face so 0 and O, 1 and l
   cannot be confused when it is read out, and selected whole by one click. */

.p-acc { display: flex; align-items: center; gap: 16px; }
.p-acc-text { flex: 1 1 auto; }
.p-acc-label { font-size: 12px; color: var(--ink-3); }
.p-acc-code {
  font-family: "IBM Plex Mono", ui-monospace, monospace;
  font-size: 26px; font-weight: 700; letter-spacing: .04em;
  color: var(--brand-dark); margin: 4px 0 6px;
  user-select: all;
}

/* A value shown in the form's rhythm but not editable. */
.p-readonly {
  padding: 10px 12px; border-radius: var(--r-sm);
  background: var(--card-alt); border: 1px dashed var(--line);
  color: var(--ink-2);
}

.p-kv {
  display: grid; grid-template-columns: max-content 1fr;
  gap: 8px 20px; margin: 0 0 16px;
}
.p-kv dt { color: var(--ink-3); font-size: 12.5px; }
.p-kv dd { margin: 0; color: var(--ink); font-size: 13px; }

/* --- the two front doors -----------------------------------------------------
   erp.wtc.sa (the office) and portal.wtc.sa (clients) share the sign-in shell,
   auth/_shell.html. The office's stands on the brand field, the deep diagonal
   green of the business card, with the white logo: a member of staff knows at
   once which side this is, and a client who typed the wrong name can see it is
   not theirs. The clients' stays on the light page they will meet inside, with
   a label naming it. On a laptop, where one name serves both, neither applies.

   White on the field's lightest green (#0A8512) measures 4.8:1, so the text on
   it stays white rather than muted; the office label darkens the field under it
   rather than lightening it, which would drop white text below 4.5:1. */

.door-head { text-align: center; margin-bottom: 26px; }
.door-head .door-chip { display: flex; width: max-content; margin: 14px auto 0; font-size: 12px; }
.portal h1.door-title { font-size: 21px; line-height: 1.35; margin: 0 0 18px; }
/* .portal h1 sets the size at (0,1,1); this needs (0,2,1) to be read at all. */

body.portal.door-office { background: var(--brand-field); background-attachment: fixed; }
body.door-office .door-chip {
  background: rgba(0, 0, 0, .24);
  color: #fff;
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, .35);
}
body.door-office p.door-tagline,
body.door-office p.door-foot,
body.door-office p.door-foot a { color: #fff; }
body.door-office p.door-foot a { text-decoration: underline; text-underline-offset: 2px; }
body.door-office .card { box-shadow: 0 18px 48px rgba(1, 30, 4, .35); }
