/* ============================================================
   Sign-in overlay.

   There is almost nothing here on purpose. The overlay is a scrim, a
   close button and a frame; everything inside it — the figure and its
   face/hands/pills layers, the card, the country-code select, the
   segmented PIN and OTP boxes — is homepage_login.html rendering
   itself, with its own stylesheet, exactly as it does at its own
   address. Nothing in this file may restyle any of that, or the two
   would start to diverge, which is the whole thing this replaced.

   Sits above the watch overlay (100), its Close (110) and the nav
   drawer (130): it can be opened from any of them.
   ============================================================ */

/* ── the topbar Sign in button ────────────────────────────────
   Sits immediately left of the Join pill, and is deliberately the
   quieter of the two: Join is filled brand yellow, this is an outline
   in the topbar's own ink. Same height and radius so they read as one
   pair rather than two unrelated controls, and the weight difference
   is what carries the hierarchy — a second filled button here would
   make neither look like the one to press, which is exactly why this
   button did not exist before. Only mounted when signed out. */
.sgn-btn {
  display: flex;
  align-items: center;
  /* Every box metric here is the Join pill's, to the pixel: same
     min-height, same 8/16 padding, same 20px radius, same 14px type at
     the same 600. Two buttons side by side either look like a matched
     pair or like an accident, and the only difference that should read
     is WHICH ONE IS THE OFFER. */
  min-height: 40px;
  padding: 8px 16px;
  font-family: var(--font);
  font-size: 14px;
  font-weight: 600;
  white-space: nowrap;
  /* Filled, not a hairline on nothing. Transparent-on-transparent left
     this looking like a link that had wandered into a row of buttons,
     and next to a solid yellow pill it read as unfinished rather than
     as secondary. A real surface with a real edge gives it the same
     presence and lets the COLOUR carry the hierarchy: brand yellow is
     the thing being sold, the topbar's own ink is the way back in. */
  color: var(--text);
  background: var(--surface);
  border: 1px solid var(--line-strong);
  border-radius: 20px;
  cursor: pointer;
  transition: background var(--dur-hover) ease, border-color var(--dur-hover) ease;
}
.sgn-btn:hover { background: var(--surface-2); border-color: var(--text-2); }
.sgn-btn:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }

@media (max-width: 640px) {
  /* 44px on touch, per the platform minimum — the desktop 40 is a
     pointer size and must not be reused here. The label stays a word:
     an icon for "sign in" is a guess, and this is the control a
     returning member is hunting for.
     These are the Join pill's phone metrics exactly (join.css, same
     breakpoint): 44px tall, 8px/14px. The pair has to stay a pair at
     every width — two buttons that match on a desktop and drift apart
     on a phone look like a mistake precisely where they are biggest. */
  .sgn-btn { min-height: 44px; padding: 8px 14px; }
}
/* There is deliberately NO tighter rule below 400px. One existed while
   the signed-out corner still carried three controls and needed the
   room; removing the redundant blank profile seat gave back more than
   it ever saved, and the type must not shrink out of step with the pill
   beside it. Measured at 360: 44px burger + a 66px mark + a 156px pair
   + 32px of padding = 298. */

/* Three blocks, not two: system-default light stamps no data-theme at
   all, so it is only reachable through the media query. */
:root { --sgn-scrim: color-mix(in srgb, #17101c 18%, transparent); }
@media (prefers-color-scheme: light) {
  :root:not([data-theme="dark"]) { --sgn-scrim: color-mix(in srgb, #fffae7 30%, transparent); }
}
:root[data-theme="light"] { --sgn-scrim: color-mix(in srgb, #fffae7 30%, transparent); }

.sgn {
  position: fixed;
  inset: 0;
  z-index: 150;
  display: none;
  align-items: center;
  justify-content: center;
  padding: 0;
}
.sgn.open { display: flex; }
.sgn::before {
  content: "";
  position: fixed;
  inset: 0;
  /* Dimmed, never blacked out. The library stays legible behind the
     card — that is the point of asking here rather than sending them to
     another page, and a solid ground would have made the two
     indistinguishable. The embedded page draws no ground of its own
     (html.embed), so this is the only scrim in play. */
  /* Barely there. The code wall inside the frame does most of the
     separating now, and stacking a heavy scrim under it took the
     library back out of view — which was the whole complaint.
     Tinted with the ground it sits on: ink over the dark library,
     cream over the light one. A dark wash over cream reads as grime. */
  background: var(--sgn-scrim);
}
body.sgn-open { overflow: hidden; }

.sgn-close {
  position: fixed;
  top: 14px;
  right: 16px;
  z-index: 2;
  display: grid;
  place-items: center;
  width: 40px;
  height: 40px;
  color: #fff;
  background: rgba(0, 0, 0, 0.55);
  border: none;
  border-radius: 50%;
  cursor: pointer;
}
.sgn-close:hover { background: rgba(0, 0, 0, 0.75); }
.sgn-close:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }

/* Full-bleed. The login page composes the figure against the viewport —
   the head breaks the card's top edge, the hands come out over the form
   — so boxing it into a small panel would crop exactly the parts that
   make it look like itself. It gets the screen, the same as it would at
   its own URL. */
.sgn-shell {
  position: relative;
  z-index: 1;
  width: 100%;
  height: 100%;
}
.sgn-frame {
  width: 100%;
  height: 100%;
  border: 0;
  display: block;
  /* A brand-new document paints the UA's white canvas for a frame or two
     before its own stylesheet is parsed — and this page ends up
     transparent, so it has no ground of its own to cover that with.
     That was the white flash on open, and on close it was the same
     frame being torn down while still on screen.

     visibility, NOT opacity. An opacity fade is an animated value, and
     an animated value does not advance while the document is hidden —
     a frame gated on one can be left invisible for reasons that have
     nothing to do with whether it loaded. visibility applies the moment
     it is set, in any state. */
  visibility: hidden;
  background: transparent;
}
.sgn-frame.ready { visibility: visible; }



/* ── the waiting room ─────────────────────────────────────────
   Until the login page inside the frame has loaded, the frame is a
   transparent full-bleed element over an 18% scrim — and a press that
   produces that is indistinguishable from a press that did nothing. On
   a phone, where the ~130 KB login document plus supabase-js, wall.js,
   the figure and its fonts can take seconds, the viewer read it exactly
   that way: the tier list still on screen, every button in it dead
   (every later press was landing on the invisible frame). So the
   overlay shows a card of its own the instant it opens, keeps the frame
   out of the hit-test until there is something in it to press, and past
   a deadline — or on an error — says so and offers the page itself.
   Tokens, not colours: this sits over the library in both themes. */
.sgn-wait {
  position: absolute;
  left: 50%; top: 50%;
  transform: translate(-50%, -50%);
  z-index: 1;                    /* above the shell/frame, below Close */
  display: none;
  flex-direction: column;
  align-items: center;
  gap: 14px;
  width: min(320px, calc(100% - 48px));
  padding: 22px 22px 20px;
  font-family: var(--font);
  color: var(--text);
  text-align: center;
  background: var(--surface);
  border: 1px solid var(--line-strong);
  border-radius: 16px;
  box-shadow: 0 24px 80px rgba(0, 0, 0, 0.35);
}
.sgn.sgn-loading .sgn-wait,
.sgn.sgn-failed .sgn-wait { display: flex; }
/* Nothing to press in there yet, so nothing in there may take the press:
   a tap on the ground is "never mind" (shell click → close), not a tap
   swallowed by a document that has not painted. */
.sgn.sgn-loading .sgn-frame,
.sgn.sgn-failed .sgn-frame { pointer-events: none; }
.sgn-wait-msg { margin: 0; font-size: 15px; font-weight: 600; line-height: 1.4; }
/* The Eon mark (styled by the inline CSS in index.html) says "working";
   once the frame has failed the message and the buttons take over. */
.sgn.sgn-failed .eon-load { display: none; }
.sgn-wait-btns { display: none; flex-direction: column; gap: 8px; width: 100%; }
.sgn.sgn-failed .sgn-wait-btns { display: flex; }
.sgn-wait-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  min-height: 44px;
  padding: 8px 16px;
  font-family: var(--font);
  font-size: 14px;
  font-weight: 600;
  color: var(--text);
  background: var(--surface-2);
  border: 1px solid var(--line-strong);
  border-radius: 22px;
  text-decoration: none;
  cursor: pointer;
}
.sgn-wait-btn:hover { border-color: var(--text-2); }
.sgn-wait-btn:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }
/* The way out that always works — the page itself, at its own address,
   filled like the offer so it reads as the thing to press. */
.sgn-wait-go { color: var(--cta-ink); background: var(--cta); border-color: transparent; }
.sgn-wait-go:hover { opacity: 0.88; }
