/* Paper Island — shared design language.
   ────────────────────────────────────────────────────────────────────────────
   Ground: a records office at night. Dark, but layered rather than flat — surfaces
   step up toward the reader the way paper stacks on a desk.

   Colour comes from the subject. Singapore's Master Plan assigns land uses a
   standing colour convention — residential in warm orange, commercial in blue,
   business in mauve, parks in green, water in pale blue. Each registry takes its
   accent from the part of that key its subject belongs to. This is an
   INTERPRETATION of the convention, not a reproduction of URA's published key,
   and DESIGN.md says so.

   Type: one serif for voice, one mono for anything countable. No web fonts —
   a page about public records should not need a CDN to render. */

:root{
  /* ground: four steps, warmed slightly so it reads as paper stock not screen */
  --bg:#0c0e11;
  --bg-1:#12151a;          /* raised card */
  --bg-2:#181c23;          /* panel, sheet */
  --bg-3:#1f242c;          /* pressed / selected */
  --rule:#262b34;
  --hair:#1c2029;

  /* ink */
  --ink:#ece7dd;
  --dim:#948f87;
  --faint:#827d74;        /* was #5d5a54 (2.8:1) — below AA. Now 4.73:1 on the ground. */

  /* registry accents, from the land-use convention */
  --tide:#3e9c8f;          /* water                */
  --ceiling:#e09a5f;       /* residential          */
  --ledger:#5c93c4;        /* commercial           */
  --roll:#9c86c4;          /* business             */
  --minutes:#c4726e;       /* civic and community  */
  --absences:#8f8a80;      /* reserve site         */

  /* the accent of the current page — set per page via body[data-reg] */
  --accent:var(--dim);
  --accent-dim:#3a3f48;

  /* data encodings. The Tide's warm/cool pair is semantic (filling vs emptying)
     and must never be re-hued for decoration. */
  --warm:#f0a447; --warm-hi:#ff7a3d;
  --cool:#5aa9e6; --cool-hi:#3f7fd0;

  --serif:'Iowan Old Style',Palatino,'Palatino Linotype',Georgia,serif;
  --mono:ui-monospace,'SF Mono',Menlo,Consolas,monospace;

  --pad:16px;
}
body[data-reg="tide"]     { --accent:var(--tide);     --accent-dim:#1e3d3a }
body[data-reg="ceiling"]  { --accent:var(--ceiling);  --accent-dim:#4a3524 }
body[data-reg="ledger"]   { --accent:var(--ledger);   --accent-dim:#20344a }
body[data-reg="roll"]     { --accent:var(--roll);     --accent-dim:#372f4a }
body[data-reg="minutes"]  { --accent:var(--minutes);  --accent-dim:#452626 }
body[data-reg="absences"] { --accent:var(--absences); --accent-dim:#33322e }

*{box-sizing:border-box}
html{-webkit-text-size-adjust:100%}
body{margin:0;background:var(--bg);color:var(--ink);font-family:var(--serif);
  -webkit-font-smoothing:antialiased;overscroll-behavior-y:none}
button{font:inherit;color:inherit;background:none;border:none;cursor:pointer;
  -webkit-tap-highlight-color:transparent}
a{color:inherit}
:focus-visible{outline:2px solid var(--accent);outline-offset:3px;border-radius:3px}

/* ── masthead ────────────────────────────────────────────────────────────────
   One row, one job. The wordmark IS the way home, so there is no separate back
   link and no "Index" chip duplicating it. What used to sit at the right of this
   row — "Master Plan 2025", "GeBIZ · 2021–2026" — was page content wearing
   chrome's clothes; it now lives with the title as an eyebrow. */
.masthead{display:flex;align-items:center;gap:14px;
  margin:0 calc(var(--pad) * -1);padding:0 var(--pad);
  border-bottom:1px solid var(--hair)}
.wordmark{flex:none;font-family:var(--mono);font-size:10px;letter-spacing:.2em;
  text-transform:uppercase;color:var(--dim);text-decoration:none;
  display:inline-flex;align-items:center;min-height:44px;white-space:nowrap}
.wordmark:hover{color:var(--ink)}
.wordmark span{color:var(--faint)}

.switch{display:flex;gap:1px;overflow-x:auto;scrollbar-width:none;flex:1;min-width:0;
  justify-content:flex-end;-webkit-overflow-scrolling:touch}
.switch::-webkit-scrollbar{display:none}
.switch a{flex:none;font-family:var(--mono);font-size:10px;letter-spacing:.11em;
  text-transform:uppercase;color:var(--faint);text-decoration:none;
  display:flex;align-items:center;min-height:42px;padding:0 9px;
  white-space:nowrap;border-bottom:2px solid transparent;
  transition:color .15s,border-color .15s}
.switch a:hover{color:var(--dim)}
.switch a[aria-current="page"]{color:var(--accent);border-bottom-color:var(--accent)}

/* the eyebrow: what this page is reading from, stated as content */
.eyebrow{font-family:var(--mono);font-size:10px;letter-spacing:.16em;text-transform:uppercase;
  color:var(--accent);margin:14px 0 0}

h1{margin:5px 0 0;font-size:29px;font-weight:400;letter-spacing:-.02em;line-height:1.06;
  text-wrap:balance}
h1 em{font-style:italic;color:var(--dim)}
/* the subtitle used to live inside the h1 and wrapped raggedly on four of seven
   phone pages. Its own line, its own size. */
.subtitle{margin:2px 0 0;font-size:17px;font-style:italic;color:var(--dim);
  letter-spacing:-.01em;line-height:1.2}
/* a rule in the page's own colour, so you always know which registry you are in */
h1::after{content:"";display:block;width:30px;height:2px;background:var(--accent);
  margin-top:11px;border-radius:2px}
h1:has(+ .subtitle)::after{display:none}
.subtitle::after{content:"";display:block;width:30px;height:2px;background:var(--accent);
  margin-top:9px;border-radius:2px}
/* the index belongs to no single registry, so its rule carries all of them */
body:not([data-reg]) h1::after,body[data-reg=""] h1::after{width:120px;background:linear-gradient(
  90deg,var(--tide) 0 20%,var(--ceiling) 20% 40%,var(--ledger) 40% 60%,
  var(--roll) 60% 80%,var(--minutes) 80% 100%)}
.dek{margin:9px 0 0;font-size:13px;line-height:1.55;color:var(--dim);max-width:36em}
.wrap{padding:calc(env(safe-area-inset-top) + 4px) var(--pad)
      calc(env(safe-area-inset-bottom) + 44px);max-width:860px;margin:0 auto}

/* ── section furniture ──────────────────────────────────────────────────────── */
h2.sec{font-family:var(--mono);font-size:10px;letter-spacing:.18em;text-transform:uppercase;
  color:var(--faint);margin:34px 0 12px;font-weight:400;
  border-top:1px solid var(--rule);padding-top:13px}
h2.sec::first-letter{color:var(--accent)}
.prose{font-size:14.5px;line-height:1.65;color:var(--dim);margin:11px 0;max-width:38em}
.prose strong{color:var(--ink);font-weight:400}
.prose em{font-style:italic}

/* ── headline figures ───────────────────────────────────────────────────────── */
.figures{display:flex;flex-wrap:wrap;gap:18px 24px;margin:20px 0 4px}
.fig{flex:1;min-width:118px}
.fig span{display:block;font-family:var(--mono);font-size:10px;letter-spacing:.13em;
  text-transform:uppercase;color:var(--faint);margin-bottom:5px}
.fig b{font-family:var(--mono);font-size:24px;font-weight:400;font-variant-numeric:tabular-nums;
  letter-spacing:-.03em;display:block;line-height:1.02;color:var(--ink)}
.fig i{font-style:normal;font-size:11.5px;color:var(--dim);display:block;margin-top:4px}

/* ── lists ──────────────────────────────────────────────────────────────────── */
.rows{list-style:none;margin:0;padding:0}
.rows li{display:flex;align-items:baseline;gap:10px;padding:9px 0;
  border-bottom:1px solid var(--hair);font-size:14px}
.rows li:last-child{border-bottom:none}
/* Two-line row: a headline value and a wrapped detail line under it. Used by the award search
   and agency concentration on /ledger, the self-description on /roll, and the arrivals-against-
   permitted-density table on /ceiling. It MUST override `.rows li{display:flex}` above — as a
   flex item the detail span sits beside the headline instead of under it, and flex items do not
   wrap, so a long description pushes the row past the viewport. That shipped once already and
   the mobile-overflow gate caught it. Lives here, not in one page's <style>, because three pages
   use it now. */
/* .rows .v carries mono detail strings whose length is data-dependent: the audit line
   for Attention tripled when its pair list went 3 -> 9 and overflowed /sources at 723px
   in a 390px viewport. A value column must wrap, because its width is not ours to fix. */
.rows li.awrow{display:block;overflow-wrap:anywhere}
.awrow b{font-variant-numeric:tabular-nums}
.awdesc{display:block;font-size:12.5px;opacity:.72;margin-top:2px}
.rows .n{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.rows .v{overflow-wrap:anywhere;min-width:0;font-family:var(--mono);font-size:12px;color:var(--dim);font-variant-numeric:tabular-nums;
  /* `flex:none` (= 0 0 auto) refused to shrink, so a long value ran past the viewport:
     the audit line for Attention tripled when its pairs went 3 -> 9 and /sources overflowed
     to 723px in a 390px window. Shrink allowed, grow still off, so short values keep their
     intrinsic width. Adding flex-shrink EARLIER in this same block does nothing — `flex`
     is a shorthand and resets it. */
  flex:0 1 auto}
.rows .sub{font-family:var(--mono);font-size:10px;color:var(--faint);flex:none}
.rows .bar{height:3px;background:var(--accent);opacity:.65;border-radius:3px;flex:none;
  align-self:center;min-width:3px}
.rows.tall li{display:block;padding:12px 0}
.rows.tall .n{white-space:normal;font-size:14.5px;line-height:1.4}
.rows.tall .meta{font-family:var(--mono);font-size:10px;letter-spacing:.06em;color:var(--faint);
  margin-top:5px;text-transform:uppercase;border:none;padding:0}

/* ── controls ───────────────────────────────────────────────────────────────── */
.seg{display:inline-flex;border:1px solid var(--rule);border-radius:999px;overflow:hidden;
  margin:4px 0;background:var(--bg-1)}
.seg button{display:inline-flex;align-items:center;min-height:44px;padding:0 16px;
  font-family:var(--mono);font-size:10px;letter-spacing:.1em;
  text-transform:uppercase;color:var(--dim);transition:background .15s,color .15s}
.seg button[aria-pressed="true"]{background:var(--accent-dim);color:var(--ink)}

/* ── charts ─────────────────────────────────────────────────────────────────── */
canvas.chart{display:block;width:100%;margin:14px 0 2px}

/* ── provenance ─────────────────────────────────────────────────────────────── */
.meta{font-family:var(--mono);font-size:10.5px;line-height:1.85;color:var(--faint);
  border-top:1px solid var(--rule);margin-top:24px;padding-top:13px;word-break:break-word}
.meta b{color:var(--dim);font-weight:400}
.warnbox{border:1px solid var(--accent-dim);background:var(--bg-1);border-radius:10px;
  padding:13px 14px;margin:16px 0;font-size:13px;line-height:1.55;color:var(--dim)}
.warnbox b{display:block;font-family:var(--mono);font-size:10px;letter-spacing:.14em;
  text-transform:uppercase;color:var(--accent);margin-bottom:6px;font-weight:400}

/* ── registry index (the hub) ───────────────────────────────────────────────── */
.reg{list-style:none;margin:18px 0 0;padding:0;display:grid;gap:10px}
.reg li{border:1px solid var(--rule);border-radius:12px;background:var(--bg-1);
  overflow:hidden;transition:border-color .18s,background .18s}
.reg li:hover{border-color:var(--accent-dim);background:var(--bg-2)}
.reg a,.reg .off{display:grid;grid-template-columns:1fr;gap:10px;padding:15px 15px 13px;
  text-decoration:none}
.reg .off{opacity:.45;cursor:default}
.reg .t{font-size:19.5px;line-height:1.15;letter-spacing:-.01em}
.reg .t em{font-style:italic;color:var(--dim)}
.reg .b{font-size:13px;color:var(--dim);margin-top:6px;line-height:1.5;max-width:34em}
.reg .f{font-family:var(--mono);font-size:10px;letter-spacing:.1em;text-transform:uppercase;
  color:var(--faint);margin-top:9px}
.reg .f s{text-decoration:none;color:var(--accent)}
/* live miniature drawn from the registry's own data */
.reg canvas{display:block;width:100%;height:52px;margin-top:4px;opacity:.95}
.reg li[data-reg="tide"]    {--accent:var(--tide);    --accent-dim:#1e3d3a}
.reg li[data-reg="ceiling"] {--accent:var(--ceiling); --accent-dim:#4a3524}
.reg li[data-reg="ledger"]  {--accent:var(--ledger);  --accent-dim:#20344a}
.reg li[data-reg="roll"]    {--accent:var(--roll);    --accent-dim:#372f4a}
.reg li[data-reg="minutes"] {--accent:var(--minutes); --accent-dim:#452626}
.reg li[data-reg="absences"]{--accent:var(--absences);--accent-dim:#33322e}
@media (min-width:640px){ .reg{grid-template-columns:1fr 1fr} }

/* ── sheet ──────────────────────────────────────────────────────────────────── */
.sheet{position:fixed;inset:auto 0 0 0;max-height:76%;overflow-y:auto;background:var(--bg-2);
  border-top:1px solid var(--rule);border-radius:16px 16px 0 0;
  padding:18px var(--pad) calc(env(safe-area-inset-bottom) + 24px);
  transform:translateY(101%);transition:transform .28s cubic-bezier(.22,1,.36,1);z-index:20;
  box-shadow:0 -24px 60px rgba(0,0,0,.6)}
.sheet.open{transform:translateY(0)}
.sheet h3{margin:0;font-size:21px;font-weight:400;letter-spacing:-.01em}
.sheet .subtle{font-family:var(--mono);font-size:10px;letter-spacing:.12em;text-transform:uppercase;
  color:var(--faint);margin-top:6px}
.close{position:absolute;top:8px;right:8px;font-size:20px;color:var(--faint);line-height:1;
  display:grid;place-items:center;width:44px;height:44px;border-radius:999px}
.close:hover{color:var(--ink);background:var(--bg-3)}
.scrim{position:fixed;inset:0;background:rgba(0,0,0,.55);opacity:0;pointer-events:none;
  transition:opacity .28s;z-index:15}
.scrim.on{opacity:1;pointer-events:auto}

/* ── footer ─────────────────────────────────────────────────────────────────── */
.foot{margin-top:38px;border-top:1px solid var(--rule);padding-top:15px;
  font-family:var(--mono);font-size:10px;letter-spacing:.12em;text-transform:uppercase;
  color:var(--faint);display:flex;flex-wrap:wrap;gap:7px 16px}
.foot a{text-decoration:none;display:inline-flex;align-items:center;min-height:40px}
.foot a:hover{color:var(--dim)}

#boot{position:fixed;inset:0;display:grid;place-items:center;background:var(--bg);z-index:40;
  font-family:var(--mono);font-size:10px;letter-spacing:.2em;text-transform:uppercase;
  color:var(--faint);text-align:center;padding:24px}
#boot.gone{display:none}

@media (min-width:760px){
  h1{font-size:40px} .subtitle{font-size:21px} .dek{font-size:14px} .fig b{font-size:28px}
  .sheet{max-width:540px;left:auto;right:16px;bottom:16px;border-radius:16px;max-height:74%}
}
@media (prefers-reduced-motion:reduce){
  .sheet,.scrim,.reg li,.seg button{transition:none}
}
