
:root {
  color-scheme: light dark;
  --color-primary: #0b3d67;
  --color-primary-dark: #082a49;
  --color-accent: #b84c15;
  --bg: #f4f6f8;
  --bg-elevated: #ffffff;
  --text: #17212b;
  --text-muted: #57626d;
  --border: #dde2e7;
  --border-subtle: #e8ebee;
  --focus-ring: #0b3d67;
  --skip-bg: #121212;
  --skip-fg: #ffffff;
  --shadow: 0 1px 2px rgba(15, 23, 31, 0.06), 0 6px 16px rgba(15, 23, 31, 0.06);
  --radius-sm: 10px;
  --radius-lg: 12px;
  --space-1: 4px; --space-2: 8px; --space-3: 12px; --space-4: 16px;
  --space-5: 24px; --space-6: 32px;
  --not-confirmed-bg: #fff9ec;
  --not-confirmed-text: #7a5a00;
  --not-confirmed-border: #e0b400;
  /* The landing pages' hero band (boss order 2026-09-02: read like a real
     travel search site). A dedicated token pair, not --color-primary-dark
     reused: that token flips to a LIGHTER blue under prefers-color-scheme
     below (it is a hover/pressed shade there, not a background), which
     would leave white hero text unreadable against it in dark mode. */
  --hero-bg: #0b3d67;
  --hero-bg-alt: #082a49;
  --hero-text: #ffffff;
  /* The quiet fill behind a chip or a placeholder image. It used to be
     written only as a var() FALLBACK (var(--bg-muted, #f1f1f1)) with no
     token behind it, so it stayed light grey under prefers-color-scheme:
     dark while the text on it flipped to near-white - a pill nobody could
     read. Defined here, in both palettes, like every other colour. */
  --bg-muted: #eef1f4;
  /* Text drawn ON a --color-primary fill. White in the light palette; in the
     dark one --color-primary is a LIGHT blue (it has to be, to stay a legible
     link colour on a dark page), and white on it reads at about 2:1. Near
     black there instead. */
  --on-primary: #ffffff;
  /* The three answer tones a destination pill can carry. Same reason as
     every token above: one definition per palette, never a literal in a
     component, so dark mode flips them with the rest of the page. */
  --tone-go-bg: #e7f5ec;      --tone-go-text: #14532d;   --tone-go-border: #b7dfc5;
  --tone-wait-bg: #fdf3e0;    --tone-wait-text: #7a4b06; --tone-wait-border: #f0d9a8;
  --tone-stop-bg: #fdeceb;    --tone-stop-text: #7f1d1d; --tone-stop-border: #f2c2be;
}
@media (prefers-color-scheme: dark) {
  :root {
    --color-primary: #6fa8e0;
    --color-primary-dark: #9cc4ea;
    --color-accent: #ef9158;
    --bg: #10161d;
    --bg-elevated: #1a222b;
    --text: #e6ecf1;
    --text-muted: #9aa7b3;
    --border: #2b3641;
    --border-subtle: #232d37;
    --focus-ring: #8bbdec;
    --skip-bg: #e6ecf1;
    --skip-fg: #10161d;
    --shadow: 0 1px 2px rgba(0, 0, 0, 0.5), 0 8px 20px rgba(0, 0, 0, 0.4);
    --not-confirmed-bg: #362b0f;
    --not-confirmed-text: #f0c869;
    --not-confirmed-border: #a9791c;
    --hero-bg: #0a1420;
    --hero-bg-alt: #060d16;
    --hero-text: #eaf1f8;
    --bg-muted: #222c37;
    --on-primary: #0a1420;
    --tone-go-bg: #16301f;    --tone-go-text: #9fe0b6;   --tone-go-border: #2f5d3f;
    --tone-wait-bg: #362b0f;  --tone-wait-text: #f0c869; --tone-wait-border: #6f5316;
    --tone-stop-bg: #3a1c1a;  --tone-stop-text: #f3b0aa; --tone-stop-border: #6f312c;
  }
}
* { box-sizing: border-box; }
body {
  margin: 0; background: var(--bg); color: var(--text);
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
  font-size: clamp(0.95rem, 0.85rem + 0.4vw, 1.05rem);
  line-height: 1.5;
  overflow-x: hidden;
}
a { color: var(--color-primary); }
/* A reader who has told their machine to stop things moving has told us too.
   The site already answers prefers-color-scheme, print and :focus-visible;
   this was the one preference it was not listening to. */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
}
img { max-width: 100%; height: auto; }
.page-shell { max-width: 1080px; margin: 0 auto; padding: 0 clamp(12px, 3vw, 24px); }
header.site-header {
  display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between;
  gap: 8px; padding: 12px 0; border-bottom: 1px solid var(--border);
}
.site-name { font-weight: 700; text-decoration: none; color: var(--text); }
/* How many places are in hand, on every page. Ships hidden; /assets/site.js
   unhides it only when the count is real, so nothing here ever shows a
   zero. */
.pick-badge {
  display: inline-block; padding: 6px 12px; border-radius: 999px;
  background: var(--color-primary); color: var(--on-primary);
  font-weight: 700; font-size: 0.9rem; text-decoration: none;
}
.pick-badge[hidden] { display: none; }
@media print { .pick-badge { display: none; } }
nav.site-nav ul, nav.lang-switch ul, footer.site-footer nav ul {
  list-style: none; display: flex; flex-wrap: wrap; gap: 12px; margin: 2px 0; padding: 0;
}
/* The padding is the tap target, not decoration. These are the only
   standalone navigation links on the site that were drawn at their bare line
   height - 20px tall, sitting 12px apart, which is under the 24px minimum a
   thumb needs and the four language links are exactly where a phone reader
   reaches first. `inline-block` is what lets the padding count. */
nav.site-nav a, nav.lang-switch a, footer.site-footer nav a {
  color: var(--text); text-decoration: none;
  display: inline-block; padding: 6px 2px;
}
footer.site-footer nav a { color: var(--text-muted); }
footer.site-footer nav a:hover, footer.site-footer nav a:focus-visible { color: var(--color-primary); }
/* The language you are already reading is a <span>, not a link, so it never
   picked up the padding the links beside it now carry - and sat a few pixels
   proud of the row. Same box, minus the tap target it does not need. */
.lang-current { font-weight: 700; display: inline-block; padding: 6px 2px; }
/* The language picker. It shipped once with no styling at all and read as
   "▶ KR한국어" in the corner: a disclosure triangle the browser drew, a flag
   emoji Windows renders as two bare letters, and nothing that looked like a
   button (boss, 2026-09-07: "한국말로 바꾸는 방법도 모르겠고"). It is a
   button now, with a globe drawn in the page and the language written out. */
details.lang-pick { position: relative; }
details.lang-pick > summary { list-style: none; cursor: pointer;
  display: inline-flex; align-items: center; gap: 7px; padding: 9px 14px;
  border: 1px solid var(--border); border-radius: 999px;
  background: var(--bg-elevated); font-weight: 600; }
details.lang-pick > summary::-webkit-details-marker { display: none; }
details.lang-pick > summary::marker { content: ""; }
details.lang-pick > summary:hover, details.lang-pick > summary:focus-visible {
  border-color: var(--color-primary); }
.lang-globe { flex: 0 0 auto; }
.lang-caret { color: var(--text-muted); font-size: 0.8em; }
.lang-menu { position: absolute; right: 0; top: calc(100% + 6px); z-index: 20;
  width: max(240px, 100%); max-height: 60vh; overflow-y: auto;
  background: var(--bg-elevated); border: 1px solid var(--border);
  border-radius: var(--radius-lg, 12px); box-shadow: var(--shadow);
  padding: var(--space-2, 8px); }
.lang-find { width: 100%; box-sizing: border-box; padding: 9px 11px;
  border: 1px solid var(--border); border-radius: 8px; font: inherit;
  background: var(--bg); color: var(--text); margin-bottom: 6px; }
nav.lang-switch .lang-menu ul { display: block; margin: 0; padding: 0; }
nav.lang-switch .lang-menu li { display: block; }
nav.lang-switch .lang-menu a, nav.lang-switch .lang-menu .lang-current {
  display: block; padding: 10px 11px; border-radius: 6px; }
nav.lang-switch .lang-menu a:hover, nav.lang-switch .lang-menu a:focus-visible {
  background: var(--bg-muted); }
nav.lang-switch .lang-menu li[hidden] { display: none; }
@media print { details.lang-pick { display: none; } }
main { padding: 16px 0 48px; }
h1 { font-size: clamp(1.3rem, 1.1rem + 1vw, 1.8rem); margin: 8px 0 4px; }
h2 { font-size: clamp(1.05rem, 0.95rem + 0.5vw, 1.3rem); margin: 32px 0 8px; }
h3 { font-size: clamp(0.95rem, 0.88rem + 0.3vw, 1.1rem); margin: 16px 0 6px; }
.table-wrap { width: 100%; overflow-x: auto; -webkit-overflow-scrolling: touch; }
table.data-table, table.changes-table {
  width: 100%; min-width: 480px; border-collapse: collapse;
}
table.data-table th, table.data-table td,
table.changes-table th, table.changes-table td {
  text-align: left; padding: 8px 10px; border-bottom: 1px solid var(--border-subtle);
  vertical-align: top;
}
/* /changes/ is one wide "Topic" column and three narrow ones. Left to the
   auto algorithm the three short ones took a third of the table each and the
   date wrapped mid-phrase; `width: 1%` plus nowrap is the ordinary way to
   tell a table a column only needs its own content. */
/* /changes/ is one wide "Topic" column and three narrow ones. Left to the
   auto algorithm the short ones took a third of the table each and the date
   wrapped mid-phrase; `width: 1%` is the ordinary way to tell a table a
   column only needs its own content. Only the DATE is told not to wrap - a
   from/to value can be a long string, and nowrap on those made one wide row
   push the rest of the table off the page. */
table.changes-table th:not(:first-child), table.changes-table td:not(:first-child) {
  width: 1%;
}
/* The HEADER, though, may never wrap. `width: 1%` shrinks the column to its
   content, and its content is a value like "156.01" - so the header above it
   ("Was", "Now") was squeezed narrower than one word and broke a character
   per line, straight down. Measured on /ko/changes/ 2026-09-07: unreadable.
   Percentages keep the wide first column wide; nowrap keeps every heading on
   one line whatever is under it. */
table.changes-table th { white-space: nowrap; }
table.changes-table th:first-child { width: 40%; }
table.changes-table th:nth-child(2), table.changes-table th:nth-child(3) { width: 15%; }
table.changes-table th:nth-child(4) { width: 20%; }
table.changes-table th:last-child, table.changes-table td:last-child {
  white-space: nowrap;
}
/* P2-2, 2026-09-07: a cell we could NOT check used to be the loudest thing
   on the page - amber background, amber border, amber text - so on the Japan
   page the three topics with no answer caught the eye before the ten with
   one. Emphasis belongs on what we know. A gap is still marked, and still
   says "not confirmed" in words (that is CLAUDE.md's rule and it does not
   move); it is just quiet now, and it sorts to the end of the grid. */
tr.not-confirmed th, tr.not-confirmed td { color: var(--text-muted); }
footer.site-footer {
  border-top: 1px solid var(--border); padding: 16px 0 32px; font-size: 0.85em; color: var(--text-muted);
}

/* ---- cards, badges, tabs and the data table read as cards -------------- */
.card, table.data-table tr {
  background: var(--bg-elevated); border: 1px solid var(--border);
  border-radius: var(--radius-lg); box-shadow: var(--shadow);
}
table.data-table { border-collapse: separate; border-spacing: 0; min-width: 0; width: 100%; }
table.data-table thead {
  position: absolute; width: 1px; height: 1px; overflow: hidden;
  clip: rect(0 0 0 0); white-space: nowrap; border: 0; padding: 0; margin: -1px;
}
table.data-table tbody {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: var(--space-4);
}
table.data-table tr {
  display: flex; flex-direction: column; gap: 6px; padding: var(--space-4);
  scroll-margin-top: 64px; min-width: 0;
}
table.data-table tr.not-confirmed {
  background: var(--bg); border-color: var(--border-subtle); box-shadow: none;
  order: 20;
}
/* P3-3: the three that decide a trip are wider than the rest. Everything
   here is one grid, so this is `grid-column: span 2` on a grid whose columns
   are auto-filled - on a phone there is only one column and the span
   collapses on its own. */
@media (min-width: 700px) {
  table.data-table tr#topic-entry:not(.not-confirmed),
  table.data-table tr#topic-safety:not(.not-confirmed),
  table.data-table tr#topic-money:not(.not-confirmed) { grid-column: span 2; }
  table.data-table tr#topic-entry .c-value,
  table.data-table tr#topic-safety .c-value,
  table.data-table tr#topic-money .c-value { font-size: 1.25em; }
}
/* `display: block`, never `flex`. A flex cell makes every child a flex ITEM,
   so a value that is ordinarily one line of running text - the places page's
   `<a>Tokyo Tower</a> (<a>Wikipedia</a>)` - was broken into four stacked
   lines, one of them a lone "(". Block keeps the caption above the value
   (the ::before is block too) and lets the value itself flow as text. */
table.data-table tbody th, table.data-table td {
  display: block; padding: 0; border: 0; text-align: left; }
/* A card a person reads, not a row of a database.
 *
 * It used to print five captions on every card - TOPIC, VALUE, UNIT, SOURCE,
 * CHECKED - above five values, so the answer a reader came for sat third in
 * a stack of labels written for whoever built the table (boss, 2026-09-07:
 * "니가 알아보기좋게 만들지말고 사람이 사용하기좋게 바꿔").
 *
 * Now the topic IS the caption, the value is the answer and is the biggest
 * thing on the card, and where it came from and when sit quietly at the
 * bottom on one line. The <td>s keep their data-label either way, so
 * anything reading the markup still sees a labelled table.
 */
table.data-table td::before, table.data-table th::before { content: none; }
table.data-table .c-topic {
  font-size: 0.82em; font-weight: 600; color: var(--text-muted);
  text-transform: uppercase; letter-spacing: 0.03em;
}
/* A caption every table now carries, for a reader who cannot see which
   heading it sits under. Off the screen, never `display: none` - that would
   take it away from a screen reader too. */
.visually-hidden {
  position: absolute; width: 1px; height: 1px; overflow: hidden;
  clip: rect(0 0 0 0); white-space: nowrap; border: 0; padding: 0; margin: -1px;
}
table.data-table td.c-value { font-size: 1.05em; line-height: 1.45; }
table.data-table td.c-unit { display: none; }
table.data-table td.c-source, table.data-table td.c-checked {
  font-size: 0.8em; color: var(--text-muted);
}
/* Where it came from and when, pushed to the bottom of the card and kept
   quiet. `order` moves them without moving the markup, so the table still
   reads topic, value, unit, source, checked to anything parsing it. */
table.data-table td.c-checked { order: 8; margin-top: auto; padding-top: 6px; }
table.data-table td.c-source { order: 9; }
/* A cell whose whole value is the em-dash placeholder. It still ships in the
   markup - the table stays a real table with every column in every row - but
   the card view hides it rather than printing a captioned "UNIT / —" on ten
   of thirteen cards, which is noise, not an answer. A cell we DID check and
   found empty is a different thing and never gets this class. */
table.data-table td.empty { display: none; }
/* The city row on a country page. Buttons, not a bulleted list: this is the
   second click of the walk the whole site is now built around, and it has to
   look like something you press. */
ul.city-list { list-style: none; margin: 8px 0 0; padding: 0; display: flex;
  flex-wrap: wrap; gap: var(--space-2, 8px); }
ul.city-list a { display: block; padding: 10px 16px; border-radius: 999px;
  border: 1px solid var(--border); background: var(--bg-elevated);
  color: var(--color-primary); text-decoration: none; font-weight: 600; }
ul.city-list a:hover, ul.city-list a:focus-visible { border-color: var(--color-primary); }
/* The date a value was written down, under the value. Quieter than the
   answer and never hidden: it is the difference between "we fetched this
   today" and "somebody checked this in 2021", and the reader is owed it. */
.cell-note { display: block; font-size: 0.78em; color: var(--text-muted); }
[id] { scroll-margin-top: 64px; }

.tab-bar {
  position: sticky; top: 0; z-index: 5; display: flex; gap: var(--space-2);
  overflow-x: auto; -webkit-overflow-scrolling: touch; background: var(--bg);
  border-bottom: 1px solid var(--border); padding: var(--space-2) 0;
  margin: var(--space-3) 0 var(--space-4); max-width: 100%;
}
.tab-bar a {
  flex: 0 0 auto; padding: 6px 14px; border-radius: 999px; border: 1px solid var(--border);
  background: var(--bg-elevated); color: var(--text); text-decoration: none; white-space: nowrap;
}
.tab-bar a:hover, .tab-bar a:focus-visible { border-color: var(--color-primary); color: var(--color-primary); }

.badge-row { display: flex; flex-wrap: wrap; gap: var(--space-2); margin: var(--space-2) 0 var(--space-4); }
.badge {
  display: inline-flex; align-items: center; gap: 4px; background: var(--bg-elevated);
  border: 1px solid var(--border); border-radius: 999px; padding: 6px 12px;
  font-size: 0.85em; color: var(--text); max-width: 100%; overflow-wrap: anywhere;
}
.badge b { color: var(--color-accent); }
.badge.badge-unconfirmed {
  background: var(--not-confirmed-bg); color: var(--not-confirmed-text);
  border-color: var(--not-confirmed-border);
}

.chip-row { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); margin: var(--space-3) 0; }
.chip {
  font: inherit; cursor: pointer; background: var(--bg-elevated); border: 1px solid var(--border);
  border-radius: 999px; padding: 6px 14px; color: var(--text);
}
.chip[aria-pressed="true"] { background: var(--color-primary); border-color: var(--color-primary); color: #fff; }
.chip:focus-visible { outline: 3px solid var(--focus-ring); outline-offset: 2px; }
.search-count { font-size: 0.85em; color: var(--text-muted); }

.search-panel {
  display: grid; gap: var(--space-3); background: var(--bg-elevated); border: 1px solid var(--border);
  border-radius: var(--radius-lg); box-shadow: var(--shadow); padding: var(--space-5);
  margin: var(--space-4) 0 var(--space-5);
}
.search-field { display: flex; flex-direction: column; gap: 4px; font-weight: 600; min-width: 0; }
.search-field select, .search-field input {
  padding: 10px 12px; font-size: 1rem; border: 1px solid var(--border); border-radius: 8px;
  background: var(--bg-elevated); color: var(--text); width: 100%; box-sizing: border-box;
}
.search-button {
  padding: 12px 20px; font-size: 1rem; font-weight: 700; border: 0; border-radius: 8px;
  background: var(--color-primary); color: var(--on-primary); cursor: pointer;
}
.search-button:hover, .search-button:focus-visible { background: var(--color-primary-dark); }
@media (min-width: 640px) { .search-panel { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 900px) {
  .search-panel { grid-template-columns: repeat(4, 1fr) auto; align-items: end; }
}

@media print {
  .tab-bar, .search-panel, .chip-row, nav.lang-switch, .skip-link { display: none; }
  table.data-table tbody { display: block; }
  table.data-table tr { box-shadow: none; break-inside: avoid; margin-bottom: 8px; }
}
/* Accessibility and phone-safety rules the news template also carries
   (dist/.../all/index.html) - copied for the same reasons, not reinvented:
   a keyboard user needs a way past the header on every page, a focus ring
   has to be visible against this page's own background, and a wide table or
   a long unbroken value must not become the thing that puts a horizontal
   scrollbar on the page itself. */
:focus-visible { outline: 3px solid var(--focus-ring); outline-offset: 3px; }
.skip-link {
  position: absolute; top: 0; left: 0; z-index: 20; padding: 10px 14px;
  background: var(--skip-bg); color: var(--skip-fg); transform: translateY(-120%);
}
.skip-link:focus-visible { transform: translateY(0); }
.page-shell, header.site-header, .nav { min-width: 0; }
/* `break-word`, never `anywhere`. Both break a long unbroken value rather
   than letting it push a sideways scrollbar onto the page, which is the
   whole point of the rule - but `anywhere` also shrinks a cell's MIN-CONTENT
   width to a single character, and the auto table algorithm then hands
   /changes/ a 37px "Checked" column and prints the word one letter per line.
   `break-word` leaves intrinsic sizing alone, so the table measures its
   columns by their words the way it should. */
body, td, th, a { overflow-wrap: break-word; }
/* Every table this site writes is already inside `.table-wrap`, which is the
   box that scrolls sideways. This rule used to say `display: block` as well,
   and that was the bug: a `display: block` table drops its own column
   algorithm, so /changes/ handed "Checked" a 37px column and the word came
   out one letter per line, 19,000px tall. Cap the width, let the table lay
   itself out, and leave the scrolling to the wrapper. */
table { max-width: 100%; }
pre { max-width: 100%; overflow-x: auto; }
/* The brand mark and the page menu, so neither collapses illegibly on a
   narrow phone: the mark never wraps mid-word and the menu scrolls inside
   its own box - two links today, never the reason the PAGE itself gets a
   sideways scrollbar. */
.brand { white-space: nowrap; flex: 0 0 auto; }
.nav {
  display: flex; flex-wrap: nowrap; gap: 12px; max-width: 100%;
  overflow-x: auto; -webkit-overflow-scrolling: touch;
}
.nav > a { flex: 0 0 auto; white-space: nowrap; padding: 2px 0; color: var(--text); text-decoration: none; }

.reviews-widget { margin-top: 32px; padding-top: 8px; border-top: 1px solid var(--border); }
.reviews-disclosure { font-size: 0.85em; color: var(--text-muted); }
.reviews-list { list-style: none; margin: 12px 0; padding: 0; }
.reviews-list li { padding: 8px 0; border-bottom: 1px solid var(--border-subtle); }
.reviews-list p { margin: 4px 0 0; }
.reviews-form fieldset { border: none; padding: 0; margin: 12px 0; }
.reviews-form legend { padding: 0; font-weight: 700; }
.reviews-star { display: inline-flex; align-items: center; gap: 4px; margin: 4px 12px 4px 0; }
.reviews-form label[for="reviews-comment"] { display: block; margin: 8px 0; }
.reviews-form textarea {
  display: block; width: 100%; max-width: 100%; box-sizing: border-box;
  margin-top: 4px; padding: 10px 12px; font: inherit;
  border: 1px solid var(--border); border-radius: 8px;
  background: var(--bg-elevated); color: var(--text);
}
.reviews-hint { font-size: 0.8em; color: var(--text-muted); margin: 4px 0 8px; }
.reviews-form button {
  padding: 12px 20px; border: 0; border-radius: 8px; font-weight: 700;
  background: var(--color-primary); color: var(--on-primary);
  font-size: 1rem; cursor: pointer;
}
.reviews-form button:hover, .reviews-form button:focus-visible {
  background: var(--color-primary-dark); }
.reviews-status:empty { display: none; }
