/* Panacea Portal.
   Palette taken from the client's own live site, not invented:
     #568187 teal     the "panacea" wordmark and every heading on panaceaclinics.com
     #aea391 taupe    the spiral mark
     #837a69 deep taupe
     #584c38 bronze
   Everything below is derived from those four. Nothing here is MINA navy: this
   is Panacea's desk and it should look like Panacea, not like us. */

:root {
  --teal:#568187; --teal-deep:#2E4A50; --teal-deeper:#1B2F34; --teal-mid:#3E6067;
  --teal-soft:#7FA5AA; --teal-pale:#EDF4F4; --teal-line:#CEE0E1;

  --taupe:#AEA391; --taupe-deep:#837A69; --taupe-pale:#F6F3EE; --taupe-line:#E6DED2;
  --bronze:#584C38;

  --ink:#22383D; --muted:#55696D; --faint:#93A6A9;
  --line:#E2E7E5; --paper:#FFFFFF; --paper-2:#F6F4F0;

  --ok:#3F7D5C; --stale:#96692E; --alert:#A9453B;

  --sans:"Plus Jakarta Sans","SF Pro Text",-apple-system,BlinkMacSystemFont,sans-serif;
  --brand:"Outfit","Plus Jakarta Sans",-apple-system,sans-serif;
  --pill:999px; --r:14px; --r-lg:20px;
  --shadow:0 1px 2px rgba(34,56,61,.05), 0 8px 24px -12px rgba(34,56,61,.16);
  --shadow-lg:0 24px 60px -28px rgba(27,47,52,.42);
}

* { box-sizing:border-box; }
html,body { margin:0; padding:0; }

/* ------------------------------------------------- added to the home screen

   Five things that separate a web page from something that feels like an app.
   All four pages get them, and all four were verified on a simulated notch
   rather than assumed.

   1. html carries the masthead colour. In standalone iOS rubber-bands past the
      end of the page and shows whatever is BEHIND the body. With html
      transparent that was a flash of white above a dark teal masthead on every
      over-scroll. body keeps its own paper colour, so only the bounce sees this.

   2. overscroll-behavior stops the bounce propagating to the page at all. There
      is no pull-to-refresh in standalone, so nothing is lost.

   3. text-size-adjust stops iOS inflating body text when the phone is rotated
      into landscape, which otherwise breaks every line length on the page.

   4. tap-highlight off. The default is a grey box over whatever you touched,
      which no native app does. The buttons already have their own press state.

   5. See the inputs section for the one that actually bites: a field under 16px
      makes iOS ZOOM THE WHOLE PAGE when you tap it. */
html {
  background: var(--teal-deeper);
  -webkit-text-size-adjust: 100%;
  text-size-adjust: 100%;
}
html, body { overscroll-behavior-y: none; }

body {
  font-family:var(--sans); color:var(--ink); background:var(--paper-2);
  font-size:15px; line-height:1.6; -webkit-font-smoothing:antialiased;
  -webkit-tap-highlight-color: transparent;
}

/* Nothing in the furniture should be selectable on a long press, which on a
   phone reads as a bug rather than a feature. Message bodies and the client's
   own text stay selectable, because a client copying a reference out of a
   thread is a real thing people do. */
.top, .tabs, .btn, .pill, .lg-cap, .overline { -webkit-user-select:none; user-select:none; }
a { color:var(--teal); }
button, input, select, textarea { font-family:inherit; font-size:inherit; color:inherit; }

/* ---------------------------------------------------------------- shell */
.top {
  background:
    radial-gradient(120% 180% at 12% -40%, rgba(174,163,145,.22) 0%, transparent 58%),
    linear-gradient(180deg, var(--teal-deeper) 0%, var(--teal-deep) 100%);
  color:#fff; position:sticky; top:0; z-index:40;
  border-bottom:1px solid rgba(206,224,225,.15);
  box-shadow:0 10px 30px -22px rgba(27,47,52,.9);
}
.top-in {
  max-width:1120px; margin:0 auto; padding:20px 22px;
  display:flex; align-items:center; gap:22px;
}
.top .spacer { flex:1; }
.who { font-size:.86rem; color:var(--teal-pale); }
.wrap { max-width:1120px; margin:0 auto; padding:26px 22px 80px; }

/* ---------------------------------------------------------------- type */
h1 { font-family:var(--brand); font-size:1.6rem; font-weight:700; letter-spacing:-.018em; margin:0 0 4px; }
h2 { font-family:var(--brand); font-size:1.05rem; font-weight:600; margin:0 0 10px; }
.sub { color:var(--muted); margin:0 0 22px; }
.overline {
  font-size:.68rem; font-weight:700; letter-spacing:.11em; text-transform:uppercase;
  color:var(--faint); margin:0 0 8px;
}

/* ---------------------------------------------------------------- cards */
.card {
  background:var(--paper); border:1px solid var(--line); border-radius:22px;
  box-shadow:0 1px 2px rgba(34,56,61,.04), 0 18px 44px -30px rgba(27,47,52,.30);
  padding:22px; margin-bottom:16px;
}
.card.tight { padding:16px 18px; }

/* ---------------------------------------------------------------- buttons */
.btn {
  display:inline-flex; align-items:center; justify-content:center; gap:8px;
  border-radius:var(--pill); border:1.5px solid transparent; cursor:pointer;
  font-weight:700; font-size:.92rem; padding:11px 22px; background:var(--teal-deep);
  color:#fff; transition:transform .14s ease, background .14s ease, box-shadow .14s ease;
  text-decoration:none; white-space:nowrap;
  box-shadow:0 10px 22px -14px rgba(27,47,52,.85);
}
.btn:hover { background:var(--teal); transform:translateY(-1px);
             box-shadow:0 14px 26px -14px rgba(27,47,52,.9); }
.btn:active { transform:none; }
.btn[disabled] { opacity:.5; cursor:not-allowed; transform:none; }
.btn.ghost { background:transparent; color:var(--teal-deep); border-color:var(--line); box-shadow:none; }
.btn.ghost:hover { background:var(--teal-pale); border-color:var(--teal-line); }
.btn.sm { padding:7px 15px; font-size:.84rem; }
.btn.danger { background:var(--alert); }
.btn.go { background:var(--ok); }

/* ---------------------------------------------------------------- forms */
label.f { display:block; margin:0 0 16px; }
label.f > span {
  display:block; font-size:.8rem; font-weight:700; color:var(--muted);
  margin-bottom:6px; letter-spacing:.01em;
}
label.f .hint { display:block; font-weight:500; color:var(--faint); font-size:.78rem; margin-top:-4px; margin-bottom:6px; }
/* A hint that belongs to the control ABOVE it, not below. Sits tight under its
   own select so a reader is never guessing which of two dropdowns it explains. */
label.f .underhint {
  display:block; font-weight:500; color:var(--faint); font-size:.78rem;
  line-height:1.5; margin:7px 2px 0; min-height:1.2em;
}
.inp, select.inp, textarea.inp {
  width:100%; padding:12px 14px; border:1.5px solid var(--line); border-radius:var(--r);
  background:var(--paper); transition:border-color .14s ease, box-shadow .14s ease;
}

/* THE ONE THAT ACTUALLY BITES ON A PHONE.
   iOS Safari ZOOMS THE ENTIRE PAGE IN when you focus an input whose font-size
   is under 16px, and it does not zoom back out afterwards. The body font here
   is 15px, so every field inherited 15px and tapping Username threw the layout
   sideways on every iPhone. There is no way to opt out of that behaviour short
   of disabling zoom entirely, which would be an accessibility failure. The only
   correct fix is to make the field 16px on touch devices.
   Desktop keeps 15px, where the problem does not exist. */
@media (hover: none) and (pointer: coarse) {
  .inp, select.inp, textarea.inp { font-size: 16px; }
}
.inp:focus, select.inp:focus, textarea.inp:focus {
  outline:none; border-color:var(--teal-soft); box-shadow:0 0 0 4px rgba(127,165,170,.26);
}
textarea.inp { min-height:130px; resize:vertical; line-height:1.6; }
.row2 { display:grid; grid-template-columns:1fr 1fr; gap:0 16px; }
@media (max-width:640px){ .row2 { grid-template-columns:1fr; } }

/* ---------------------------------------------------------------- pills */
.pill {
  display:inline-flex; align-items:center; gap:6px; border-radius:var(--pill);
  padding:5px 12px; font-size:.74rem; font-weight:700; letter-spacing:.02em;
  background:var(--teal-pale); color:var(--teal-deep); border:1px solid var(--teal-line);
  white-space:nowrap;
}
.pill.new      { background:var(--taupe-pale); border-color:var(--taupe-line); color:var(--bronze); }
.pill.progress { background:var(--teal-pale); border-color:var(--teal-line); color:var(--teal-deep); }
.pill.waiting  { background:#FBEFED; border-color:#F0D4CF; color:var(--alert); }
.pill.done     { background:#EAF4EE; border-color:#C0DFCD; color:var(--ok); }
.pill.closed   { background:#F1F2F0; border-color:var(--line); color:var(--muted); }
.pill.urgent   { background:var(--alert); border-color:var(--alert); color:#fff; }
.pill.internal { background:#F1F2F0; border-color:var(--line); color:var(--muted); }
.pill.draft    { background:var(--taupe-pale); border-color:var(--taupe-line); color:var(--bronze); }

/* Which company looks after this practice. Quiet, but never absent. */
.pill.ag       { background:transparent; border-color:var(--line); color:var(--faint);
                 font-weight:600; letter-spacing:.04em; text-transform:uppercase;
                 font-size:.64rem; padding:4px 9px; }

/* ---------------------------------------------------------------- list */
.tk {
  display:flex; align-items:flex-start; gap:14px; padding:17px 19px;
  border:1px solid var(--line); border-radius:18px; background:var(--paper);
  margin-bottom:10px; cursor:pointer; text-decoration:none; color:inherit;
  box-shadow:0 1px 2px rgba(34,56,61,.04);
  transition:border-color .14s ease, box-shadow .14s ease, transform .14s ease;
}
.tk:hover {
  border-color:var(--teal-soft); transform:translateY(-1px);
  box-shadow:0 1px 2px rgba(34,56,61,.05), 0 16px 32px -20px rgba(27,47,52,.36);
}
.tk .body { flex:1; min-width:0; }
.tk .subj { font-weight:700; margin-bottom:3px; font-size:1.02rem; letter-spacing:-.011em; }
.tk .meta { font-size:.82rem; color:var(--muted); }
.tk .rt { display:flex; flex-direction:column; align-items:flex-end; gap:7px; }
.tk .rt .pills { display:flex; gap:6px; flex-wrap:wrap; justify-content:flex-end; }
.tk .ago { font-size:.75rem; color:var(--faint); }
.ref { font-family:ui-monospace,"SF Mono",monospace; font-size:.78rem; color:var(--faint); }
@media (max-width:560px) {
  .tk { flex-direction:column; gap:10px; }
  .tk .rt { align-items:flex-start; width:100%; }
  .tk .rt .pills { justify-content:flex-start; }
}

/* ---------------------------------------------------------------- thread */
.msg { display:flex; gap:12px; margin-bottom:18px; }
.msg .av {
  width:34px; height:34px; border-radius:50%; flex:0 0 auto; display:flex;
  align-items:center; justify-content:center; font-weight:800; font-size:.78rem;
  background:var(--taupe-pale); color:var(--bronze); border:1px solid var(--taupe-line);
  box-shadow:0 4px 10px -6px rgba(27,47,52,.45);
}
.msg.agency .av { background:var(--teal-deep); color:#fff; border-color:var(--teal-deep); }
.msg.system .av { background:var(--paper-2); color:var(--faint); border-color:var(--line); }
.msg .bub { flex:1; min-width:0; }
.msg .hd { font-size:.8rem; color:var(--muted); margin-bottom:5px; display:flex; gap:9px; align-items:center; flex-wrap:wrap; }
.msg .hd b { color:var(--ink); }
.msg .tx {
  background:var(--paper); border:1px solid var(--line); border-radius:16px;
  padding:13px 16px; white-space:pre-wrap; word-wrap:break-word;
}
.msg.agency .tx { background:var(--teal-pale); border-color:var(--teal-line); }
.msg.system .tx { background:var(--paper-2); color:var(--muted); font-size:.9rem; }
.msg.pending .tx { background:var(--taupe-pale); border-color:var(--taupe-line); border-style:dashed; }
.msg.internal .tx { background:#F4F6F5; border-color:var(--line); border-style:dashed; color:var(--muted); }

/* ---------------------------------------------------------------- misc */
.err {
  background:#FBEFED; border:1px solid #F0D4CF; color:var(--alert);
  border-radius:var(--r); padding:11px 14px; margin-bottom:14px; font-size:.9rem;
}
.okmsg {
  background:#EAF4EE; border:1px solid #C0DFCD; color:var(--ok);
  border-radius:var(--r); padding:11px 14px; margin-bottom:14px; font-size:.9rem;
}
/* A quiet standing notice, not an error. Used for the confidentiality note on
   the request form, which must be present but must not look like a warning. */
.note {
  background:var(--taupe-pale); border:1px solid var(--taupe-line); color:var(--bronze);
  border-radius:var(--r); padding:12px 15px; margin-bottom:18px; font-size:.85rem;
  line-height:1.55;
}
.note b { color:var(--bronze); }
.files { display:flex; flex-wrap:wrap; gap:8px; margin-top:10px; }
.file {
  display:inline-flex; align-items:center; gap:7px; font-size:.82rem;
  background:var(--paper-2); border:1px solid var(--line); border-radius:var(--pill);
  padding:6px 13px; text-decoration:none; color:var(--teal-deep); font-weight:600;
}
.file:hover { background:var(--teal-pale); border-color:var(--teal-line); }
.tabs { display:flex; gap:6px; margin-bottom:18px; flex-wrap:wrap; }
.tab {
  border:1.5px solid var(--line); background:var(--paper); border-radius:var(--pill);
  padding:7px 16px; font-size:.85rem; font-weight:700; cursor:pointer; color:var(--muted);
}
.tab.on { background:var(--teal-deep); border-color:var(--teal-deep); color:#fff; }
.hide { display:none !important; }
.spin { display:inline-block; width:15px; height:15px; border:2px solid rgba(255,255,255,.4);
  border-top-color:#fff; border-radius:50%; animation:sp .7s linear infinite; }
@keyframes sp { to { transform:rotate(360deg); } }
.muted { color:var(--muted); }
.small { font-size:.84rem; }
hr.sep { border:0; border-top:1px solid var(--line); margin:22px 0; }

/* ---------------------------------------------------------------- greeting */
.greet {
  font-family:var(--brand); font-weight:700; letter-spacing:-.022em;
  font-size:1.62rem; margin:0 0 4px; color:var(--ink);
}
.greet .light { color:var(--muted); font-weight:600; }

/* ---------------------------------------------------------------- empty */
.empty {
  background:var(--paper); border:1px dashed var(--teal-line); border-radius:22px;
  padding:64px 26px; text-align:center; color:var(--faint);
}
.empty .ic {
  width:54px; height:54px; margin:0 auto 16px; border-radius:50%;
  background:var(--teal-pale); border:1px solid var(--teal-line);
  display:flex; align-items:center; justify-content:center;
  font-size:24px; color:var(--teal-deep);
}
.empty h2 { color:var(--ink); margin-bottom:6px; }
.empty p { margin:0 auto; max-width:34ch; }

/* ============================================================== the lockup

   Three marks, not two, and that is the point.

   Panacea leads because it is their portal. Then a hairline, then BOTH of the
   companies that actually serve this group: MINA Medical Marketing looks after
   Panacea Clinic, Dental Marketing Canada looks after the three dental brands.
   A masthead naming only one would be wrong for three practices out of four,
   and this whole account is built around never conflating those businesses.

   Everything stays legible down to 320px. Below 720 all three drop to their
   icons, because three wordmarks side by side on a phone means three
   illegible wordmarks. */

.lockup { display:flex; align-items:center; gap:17px; text-decoration:none; min-width:0; }
.lockup img { display:block; width:auto; }

/* Their mark. Source file is 258x72, so 34px on screen is 2x retina exactly.
   Do not size it above 36px: there is no larger asset and it would soften. */
.lg-client { height:34px; filter:drop-shadow(0 2px 8px rgba(0,0,0,.28)); }

.lg-div {
  width:1px; height:36px; flex:0 0 auto; border-radius:1px;
  background:linear-gradient(180deg, transparent, rgba(206,224,225,.40), transparent);
}

.lg-house { display:flex; flex-direction:column; gap:6px; min-width:0; }
.lg-cap {
  font-size:.56rem; font-weight:700; letter-spacing:.19em; text-transform:uppercase;
  color:var(--teal-pale); opacity:.62; white-space:nowrap; line-height:1;
}
.lg-agencies { display:flex; align-items:center; gap:15px; }
.lg-agencies img { height:20px; opacity:.95; }
.lg-dot {
  width:3px; height:3px; border-radius:50%; flex:0 0 auto;
  background:rgba(206,224,225,.45);
}

/* Icon-only variants, hidden until the breakpoint. The element is named in the
   selector on purpose: `.lockup img` is (0,1,1) and a bare class is (0,1,0),
   so a bare rule would lose to it and the icons would render at full natural
   size beside the wordmarks on desktop. That exact bug cost a pass on 432. */
.lockup img.lg-client-icon,
.lockup img.lg-mina-icon,
.lockup img.lg-dmc-icon { display:none; }

@media (max-width:720px) {
  .top-in { padding:12px 16px; gap:10px; }
  .lockup { gap:11px; }
  /* `.lockup img` is (0,1,1). A bare `.lg-client { display:none }` is (0,1,0)
     and LOSES to it, so the full wordmark kept rendering on a phone beside the
     icon and the two collided with the buttons. The hide rule has to carry the
     element, exactly like the icon rules above. `.lg-house` is a span, so it
     does not need it, but it is written the same way so the pattern is obvious
     to whoever reads this next. */
  .lockup img.lg-client { display:none; }
  .lockup .lg-house { display:none; }
  .lockup img.lg-client-icon { display:block; height:31px;
                               filter:drop-shadow(0 2px 8px rgba(0,0,0,.28)); }
  .lockup img.lg-mina-icon,
  .lockup img.lg-dmc-icon { display:block; height:26px; opacity:.95; }
  .lg-div { height:28px; }
  .who { display:none; }
  .wrap { padding:20px 16px 70px; }
  /* Three icons plus two buttons is a lot for 360px. The actions shrink first,
     because a button can afford to be smaller and a logo cannot. */
  .top .btn.sm { padding:7px 12px; font-size:.8rem; }
}
@media (max-width:400px) {
  .top-in { padding:13px 12px; gap:8px; }
  .lockup { gap:9px; }
  .lockup img.lg-client-icon { height:27px; }
  .lockup img.lg-mina-icon,
  .lockup img.lg-dmc-icon { height:22px; }
  .lg-div { height:23px; }
  .top .btn.sm { padding:6px 10px; font-size:.75rem; letter-spacing:-.01em; }
  .wrap { padding:18px 13px 60px; }
}
@media (max-width:340px) {
  /* At 320 there is genuinely not room for three marks and two buttons. The
     two agency icons drop and the client's mark stays, because the client's
     mark is the one a client needs to recognise. Ours are on every other
     screen of this portal and in the footer credit on this one. */
  .lockup img.lg-mina-icon,
  .lockup img.lg-dmc-icon,
  .lockup .lg-div { display:none; }
  .lockup img.lg-client-icon { height:26px; }
  .top .btn.sm { padding:6px 9px; font-size:.72rem; }
}

/* ------------------------------------------------------- login lockup */
.auth-lockup {
  display:flex; flex-direction:column; align-items:center; gap:24px;
  margin-bottom:28px;
}
.auth-client { height:58px; width:auto; display:block;
               filter:drop-shadow(0 4px 14px rgba(0,0,0,.34)); }
.auth-rule {
  width:150px; height:1px; border-radius:1px;
  background:linear-gradient(90deg, transparent, rgba(206,224,225,.38), transparent);
}
.auth-house { display:flex; flex-direction:column; align-items:center; gap:13px; }
/* Both agency marks are lockups of their own, an icon plus type, and both sit
   at roughly 75% ink within their canvas. Matching total height therefore
   matches them optically too. 26px is the floor at which the MINA tagline stops
   being noise. */
.auth-agencies { display:flex; align-items:center; gap:26px; }
.auth-agencies img { height:26px; width:auto; display:block; opacity:.95; }
.auth-agencies .lg-dot {
  width:3px; height:3px; border-radius:50%; flex:0 0 auto;
  background:rgba(206,224,225,.40);
}
@media (max-width:480px) {
  .auth-client { height:46px; }
  .auth-agencies img { height:21px; }
  .auth-agencies { gap:18px; }
  .auth-rule { width:110px; }
}

/* ------------------------------------------------------- footer credit */
.credit {
  text-align:center; margin-top:40px; padding-top:22px;
  border-top:1px solid var(--line); color:var(--faint); font-size:.78rem;
  line-height:1.7;
}
.credit b { color:var(--muted); font-weight:700; }

/* ------------------------------------------------------- phone refinements */
@media (max-width:720px) {
  /* The primary action sits beside the heading on desktop. On a phone it should
     be a full width tap target directly under the intro. */
  #new-btn { width:100%; margin:4px 0 4px !important; padding:14px 22px; }
  .greet { font-size:1.42rem; }
  .sub { margin-bottom:16px; }
  .tabs { margin-bottom:14px; }
  .credit { margin-top:30px; font-size:.74rem; }
}

/* Nothing may ever scroll the page sideways. */
html, body { max-width:100%; overflow-x:hidden; }

/* ============================================ iOS home screen safe areas

   Added to the home screen the manifest sets display:standalone and the meta
   sets apple-mobile-web-app-status-bar-style to black-translucent, which draws
   the page UNDERNEATH the status bar. Without the insets below the masthead
   sits behind the clock, the wifi icon and the battery.

   `viewport-fit=cover` in the viewport meta is what makes env() resolve at all.
   It is set on all three pages; without it every inset is zero and none of this
   does anything.

   THE INSETS GO THROUGH CUSTOM PROPERTIES, NOT env() DIRECTLY.

   Two reasons, both practical. A value used in eight places should be named
   once. And env() cannot be overridden, so a rule written with env() inline is
   UNTESTABLE: there is no way to simulate a notch and look at the result. With
   a token, a test can set --sat to 59px and photograph the clearance, which is
   exactly how the padding below was checked rather than assumed. */

:root {
  --sat: env(safe-area-inset-top, 0px);
  --sab: env(safe-area-inset-bottom, 0px);
  --sal: env(safe-area-inset-left, 0px);
  --sar: env(safe-area-inset-right, 0px);
  --gut: 22px;
}

/* The top inset goes on `.top`, NOT on `.top-in`. Padding the outer element
   means the teal gradient fills the status bar strip behind the clock, which is
   what makes it look deliberate. Padding the inner one leaves a pale band above
   the header instead. */
.top { padding-top: var(--sat); }

.top-in {
  padding-left:  max(var(--gut), var(--sal));
  padding-right: max(var(--gut), var(--sar));
}

.wrap {
  padding-left:  max(var(--gut), var(--sal));
  padding-right: max(var(--gut), var(--sar));
  padding-bottom: calc(80px + var(--sab));
}

@media (max-width:720px) {
  :root { --gut: 16px; }
  .wrap { padding-bottom: calc(70px + var(--sab)); }
}
@media (max-width:400px) {
  :root { --gut: 13px; }
  .wrap { padding-bottom: calc(60px + var(--sab)); }
}

/* ------------------------------------- THE NON NOTCHED iPHONE GAP

   env() alone is NOT enough, and this is the bug that was actually reported.

   On an iPhone WITH a notch or Dynamic Island, standalone + black-translucent
   gives env(safe-area-inset-top) of 47 to 59px and everything above works.

   On an iPhone WITHOUT one, an SE or an 8, iOS still draws a 20px status bar
   OVER the page, but env(safe-area-inset-top) reports ZERO. So the masthead got
   no padding at all and the logo sat underneath the clock and the battery.
   Nothing in the meta tags is wrong; the inset is simply not reported on those
   devices, and a layout that trusts it has a hole in it.

   The floor below closes that. max() means a notched phone keeps its real, much
   larger inset and only the devices that report nothing get the 20px they need.

   Scoped two ways so nothing else is touched:
     - display-mode: standalone, so a browser tab, where the real status bar is
       above the viewport rather than over it, is unaffected.
     - @supports (-webkit-touch-callout: none), which is true only on iOS
       Safari. Android standalone puts the status bar ABOVE the viewport and
       correctly reports a zero inset, so forcing a band there would be a
       20px strip of nothing. */

@media (display-mode: standalone) {
  @supports (-webkit-touch-callout: none) {
    .top { padding-top: max(var(--sat), 20px); }
    body.auth { padding-top: calc(24px + max(var(--sat), 20px)); }
  }
}
@media (display-mode: standalone) and (max-height: 700px) {
  @supports (-webkit-touch-callout: none) {
    body.auth { padding-top: calc(16px + max(var(--sat), 20px)); }
  }
}
@media (display-mode: standalone) and (max-height: 580px) {
  @supports (-webkit-touch-callout: none) {
    body.auth { padding-top: calc(12px + max(var(--sat), 20px)); }
  }
}

/* ======================================================= the login screen

   It does not use .top and .wrap, it centres a card in the viewport, so it
   carries its own insets and its own height behaviour.

   TWO BUGS LIVED HERE AND BOTH MADE IT SCROLL ON A PHONE.

   1. `min-height:100vh`. On mobile Safari 100vh is the viewport height WITHOUT
      the address bar and toolbar, which is TALLER than what you can actually
      see. So the page was always taller than the screen and always scrolled,
      even on a phone with room to spare. `100dvh` is the dynamic height that
      accounts for the browser chrome. The 100vh line stays first as the
      fallback for anything that does not know dvh.

   2. `align-items:center` on the body. When content is taller than the
      container, a centred flex item overflows in BOTH directions and the top
      of it becomes unreachable: you cannot scroll up to the logo because the
      overflow above the container is not scrollable. The fix is auto margins
      on the item, which centre it when there is room and collapse to zero when
      there is not, so it top-aligns and the whole card stays reachable.

   Measured before the fix: the card needed 620px of viewport and an iPhone SE
   in Safari gives about 553. The height tiers below bring it under 500. */

body.auth {
  min-height: 100vh;
  min-height: 100dvh;
  display: flex;
  justify-content: center;
  align-items: flex-start;
  padding-top:    calc(24px + var(--sat));
  padding-bottom: calc(24px + var(--sab));
  padding-left:   max(24px, var(--sal));
  padding-right:  max(24px, var(--sar));
}

/* Centres when it fits, top-aligns when it does not. Never clips the logo. */
body.auth > .box { margin-block: auto; }

/* ------------------------------------------------- short screens

   Tiered on HEIGHT, not width, because this is a vertical fit problem. A tall
   phone keeps the generous spacing; only a short one gets compressed, and the
   safe-area part of the padding is never compressed because that is physical
   hardware, not taste. */

@media (max-height: 700px) {
  body.auth {
    padding-top:    calc(16px + var(--sat));
    padding-bottom: calc(16px + var(--sab));
  }
  .auth-lockup { gap: 15px; margin-bottom: 18px; }
  .auth-client { height: 48px; }
  .auth-house { gap: 9px; }
  .auth-agencies img { height: 22px; }
  .auth-agencies { gap: 20px; }
  .auth-rule { width: 120px; }
  .panel { padding: 24px 24px; }
  .panel label.f { margin-bottom: 13px; }
  .foot { margin-top: 15px; }
}

@media (max-height: 580px) {
  body.auth {
    padding-top:    calc(12px + var(--sat));
    padding-bottom: calc(12px + var(--sab));
  }
  .auth-lockup { gap: 11px; margin-bottom: 14px; }
  .auth-client { height: 40px; }
  .auth-house { gap: 7px; }
  .auth-agencies img { height: 19px; }
  .auth-agencies { gap: 16px; }
  .auth-rule { width: 96px; }
  .panel { padding: 19px 20px; }
  .panel h2 { font-size: 1rem; margin-bottom: 2px; }
  .panel .sub { margin-bottom: 14px !important; }
  .panel label.f { margin-bottom: 11px; }
  .panel .inp { padding: 10px 13px; }
  /* The strapline is the one thing here that carries no function. It is the
     first to go, and only once the screen is genuinely short. */
  .foot { display: none; }
}

@media (max-height: 470px) {
  /* Landscape on a phone. Nothing fits at this height, so stop pretending and
     let it scroll cleanly from the top rather than compressing into mush. */
  .auth-lockup { gap: 9px; margin-bottom: 12px; }
  .auth-client { height: 34px; }
  .auth-rule { display: none; }
  .auth-agencies img { height: 17px; }
}
