:root {
  --bg: #fafaf8;
  --surface: #ffffff;
  --border: #e5e2da;
  --text: #1c1b19;
  --text-dim: #6b6a63;
  --brand: #0f7a5c;
  --brand-dark: #0b5c45;
  --accent: #e8a33d;
  --warn-text: #8a5310;
  --radius: 12px;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --bg: #15140f;
    --surface: #1e1d17;
    --border: #33322a;
    --text: #f1efe8;
    --text-dim: #a9a696;
    --brand: #2fbb8f;
    --brand-dark: #21a37c;
    --accent: #f0b955;
    --warn-text: #f0b955;
  }
}
:root[data-theme="dark"] {
  --bg: #15140f;
  --surface: #1e1d17;
  --border: #33322a;
  --text: #f1efe8;
  --text-dim: #a9a696;
  --brand: #2fbb8f;
  --brand-dark: #21a37c;
  --accent: #f0b955;
  --warn-text: #f0b955;
}

* { box-sizing: border-box; }
body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font: 16px/1.5 -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
}
.wrap { max-width: 1080px; margin: 0 auto; padding: 0 20px; }
a { color: var(--brand-dark); }

.site-header { border-bottom: 1px solid var(--border); }
.site-header .wrap { display: flex; align-items: center; justify-content: space-between; padding-block: 16px; }
.logo { font-weight: 800; font-size: 1.25rem; text-decoration: none; color: var(--text); }
.logo span { color: var(--brand); }
.site-header nav { display: flex; gap: 20px; }
.site-header nav a { text-decoration: none; color: var(--text-dim); font-weight: 600; font-size: 0.95rem; }

.currency-toggle { display: flex; align-items: center; gap: 8px; }
.fx-switch { display: flex; align-items: center; gap: 6px; font-size: 0.82rem; color: var(--text-dim); cursor: pointer; user-select: none; }
.fx-switch input { accent-color: var(--brand); width: 16px; height: 16px; cursor: pointer; }
#fx-currency {
  font-size: 0.82rem;
  padding: 4px 8px;
  border: 1px solid var(--border);
  border-radius: 6px;
  background: var(--surface);
  color: var(--text);
}
.price-fx { font-weight: 500; color: var(--text-dim); font-size: 0.85em; }

@media (max-width: 640px) {
  .site-header .wrap { flex-wrap: wrap; row-gap: 10px; }
  .currency-toggle { order: 3; width: 100%; justify-content: flex-end; }
}

.hero { padding-block: 56px 40px; text-align: center; }
.hero h1 { font-size: clamp(1.6rem, 4vw, 2.4rem); margin: 0 0 10px; }
.hero p { color: var(--text-dim); max-width: 560px; margin: 0 auto 28px; }

.search-card {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 18px;
  max-width: 640px;
  margin: 0 auto;
  text-align: left;
}
.modes { display: flex; gap: 8px; margin-bottom: 14px; flex-wrap: wrap; }
.mode {
  border: 1px solid var(--border);
  background: transparent;
  color: var(--text-dim);
  border-radius: 999px;
  padding: 6px 14px;
  font-weight: 600;
  font-size: 0.85rem;
  cursor: pointer;
}
.mode.active { background: var(--brand); border-color: var(--brand); color: #fff; }

.fields { display: grid; grid-template-columns: 1fr 1fr auto auto; gap: 10px; align-items: end; }
.date-field { display: flex; flex-direction: column; gap: 6px; font-size: 0.8rem; color: var(--text-dim); font-weight: 600; }
.date-field input {
  padding: 10px 12px;
  border: 1px solid var(--border);
  border-radius: 8px;
  background: var(--bg);
  color: var(--text);
  font-size: 0.95rem;
}
@media (max-width: 560px) { .date-field { width: 100%; } }
.autocomplete { position: relative; }
.autocomplete-control { position: relative; display: block; }
.autocomplete-control input { width: 100%; padding-right: 28px; }
.autocomplete-arrow {
  position: absolute;
  right: 10px;
  top: 50%;
  transform: translateY(-50%);
  color: var(--text-dim);
  font-size: 0.75rem;
  pointer-events: none;
}
.suggestions {
  position: absolute;
  top: 100%;
  left: 0;
  right: 0;
  z-index: 20;
  margin: 4px 0 0;
  padding: 4px;
  list-style: none;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: 8px;
  box-shadow: 0 8px 20px rgba(0, 0, 0, 0.12);
  max-height: 220px;
  overflow-y: auto;
}
/* Below the point where .fields stacks vertically, an open dropdown
   floating on top of the page would sit directly over the next field
   (From's dropdown over To, To's dropdown over the Search button) and
   silently steal taps meant for them. Keep it in normal document flow
   instead so it pushes the rest of the form down rather than covering it. */
@media (max-width: 560px) {
  .suggestions {
    position: static;
    margin-top: 6px;
    box-shadow: none;
  }
}
.suggestions li {
  padding: 8px 10px;
  border-radius: 6px;
  cursor: pointer;
  font-size: 0.9rem;
  color: var(--text);
}
.suggestions li:hover, .suggestions li.active { background: var(--bg); }
@media (max-width: 560px) { .fields { grid-template-columns: 1fr; } }
.fields label { display: flex; flex-direction: column; gap: 6px; font-size: 0.8rem; color: var(--text-dim); font-weight: 600; }
.fields input {
  padding: 10px 12px;
  border: 1px solid var(--border);
  border-radius: 8px;
  background: var(--bg);
  color: var(--text);
  font-size: 0.95rem;
}
.btn-search {
  background: var(--brand);
  color: #fff;
  border: none;
  border-radius: 8px;
  padding: 11px 20px;
  font-weight: 700;
  cursor: pointer;
}
.btn-search:hover { background: var(--brand-dark); }

.recent-searches { max-width: 640px; margin: 12px auto 0; text-align: left; display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.recent-searches[hidden] { display: none; }
.recent-label { font-size: 0.8rem; color: var(--text-dim); font-weight: 600; }
.recent-chips { display: flex; gap: 6px; flex-wrap: wrap; }
.recent-chip {
  background: var(--surface);
  border: 1px solid var(--border);
  color: var(--text);
  border-radius: 999px;
  padding: 4px 12px;
  font-size: 0.8rem;
  cursor: pointer;
}
.recent-chip:hover { border-color: var(--brand); color: var(--brand-dark); }

#results-section { padding-block: 32px 8px; }
.results-top { display: flex; align-items: center; justify-content: space-between; gap: 12px; flex-wrap: wrap; }
.results-actions { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.share-btn {
  display: inline-block;
  background: var(--surface);
  color: var(--text);
  border: 1px solid var(--border);
  border-radius: 8px;
  padding: 6px 12px;
  font-size: 0.82rem;
  font-weight: 600;
  cursor: pointer;
  text-decoration: none;
}
.share-btn:hover { border-color: var(--brand); color: var(--brand-dark); }
.view-toggle { display: inline-flex; border: 1px solid var(--border); border-radius: 8px; overflow: hidden; }
.view-btn {
  background: var(--surface);
  color: var(--text-dim);
  border: none;
  padding: 6px 12px;
  font-size: 0.82rem;
  font-weight: 600;
  cursor: pointer;
}
.view-btn + .view-btn { border-left: 1px solid var(--border); }
.view-btn.active { background: var(--brand); color: #fff; }

.results-grid { display: grid; gap: 12px; grid-template-columns: repeat(auto-fill, minmax(290px, 1fr)); margin-top: 16px; }
.result-card {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 16px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.result-card .price { color: var(--accent); font-weight: 700; margin: 0; }

/* Card header: mode badge + operator name/verified mark. */
.rc-head { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.rc-head .badge { margin: 0; }
.rc-operator { font-weight: 700; font-size: 0.92rem; }

/* The journey timeline -- departure point, a track (duration + line +
   optional via-city), arrival point. This is the shape every real
   provider we reviewed (Busbora, Abood, Satco...) uses instead of a
   single dense text line, so it's the standard here too. */
.rc-journey { display: flex; align-items: center; gap: 10px; }
.rc-point { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.rc-point-end { align-items: flex-end; text-align: right; }
.rc-time { font-size: 1.15rem; font-weight: 800; line-height: 1.15; white-space: nowrap; }
.rc-time sup { font-size: 0.6em; color: var(--accent); font-weight: 800; margin-left: 2px; }
/* Departure and destination towns: the second thing the eye should land
   on after the times -- full-contrast and bold, not a dim caption. They
   wrap between words ("Dar es / Salaam") rather than overflowing. */
.rc-city { font-size: 1rem; font-weight: 700; color: var(--text); line-height: 1.25; }
.rc-date { font-size: 0.68rem; color: var(--text-dim); opacity: 0.8; white-space: nowrap; }
.rc-stand { font-size: 0.66rem; color: var(--text-dim); opacity: 0.7; white-space: normal; word-break: break-word; max-width: 110px; }
/* A pickup/dropoff at a stop outside the town -- the listed time is for
   that stop. Shown in both views (it sits inside the city cell). */
.rc-away { display: block; font-size: 0.66rem; font-weight: 700; color: var(--warn-text); white-space: normal; word-break: break-word; max-width: 130px; }
.rc-point-end .rc-away { margin-left: auto; }

.rc-track { flex: 1; min-width: 56px; display: flex; flex-direction: column; align-items: center; gap: 3px; }
.rc-duration { font-size: 0.7rem; color: var(--text-dim); font-weight: 700; white-space: nowrap; }
.rc-line { display: flex; align-items: center; width: 100%; }
.rc-dot { width: 6px; height: 6px; border-radius: 50%; background: var(--border); flex: none; }
.rc-dot:first-child { background: var(--brand); }
.rc-bar { flex: 1; height: 1px; background: var(--border); }
.rc-via { font-size: 0.66rem; color: var(--text-dim); white-space: nowrap; }

.rc-foot { display: flex; align-items: center; justify-content: space-between; gap: 12px; padding-top: 10px; border-top: 1px solid var(--border); }
.rc-foot .btn-out { margin: 0; }

/* List view: a real column table, not a card -- every field (mode,
   operator, departure time/city/date, duration, via-city, arrival
   time/city/date, price, action) gets its own column, nothing hidden.
   Nested `display: contents` on rc-head/rc-journey/rc-point/rc-track/
   rc-foot promotes their children straight into the grid without
   duplicating markup between this view and Cards view. journeyHtml()
   always emits the same fixed shape (missing data shows "—", never a
   different structure) specifically so every row contributes the same
   number of grid cells and columns stay aligned.
   Columns are fixed/capped widths rather than sized to content -- long
   text (an operator name, a city) wraps onto a second line within its
   own column instead of forcing the whole row wider than the page, and
   every column is left-aligned (including price and the action button)
   so the eye reads straight down each column, not zig-zagging between
   left- and right-aligned fields. */
.results-grid.view-list { display: flex; flex-direction: column; gap: 8px; }
.results-grid.view-list .result-card {
  display: grid;
  grid-template-columns:
    76px                 /* mode badge */
    minmax(90px, 120px)  /* operator */
    56px                 /* departure time (allow room for a "+1" day-offset superscript) */
    minmax(88px, 120px)  /* departure city */
    44px                 /* departure date */
    46px                 /* duration */
    minmax(60px, 90px)   /* via city */
    56px                 /* arrival time (same allowance) */
    minmax(88px, 120px)  /* arrival city */
    44px                 /* arrival date */
    minmax(90px, 120px)  /* price */
    minmax(90px, 120px); /* action */
  align-items: start;
  gap: 6px 10px;
  padding: 10px 12px;
}
/* Direct-child combinators, not descendant selectors -- a connection
   card nests its own rc-head/rc-journey/rc-foot one level deeper inside
   each .connection-leg, and those must keep their normal card layout
   (not explode into the outer row's grid) rather than being caught by
   this rule too. */
.results-grid.view-list .result-card > .rc-head,
.results-grid.view-list .result-card > .rc-journey,
.results-grid.view-list .result-card > .rc-journey > .rc-point,
.results-grid.view-list .result-card > .rc-journey > .rc-track,
.results-grid.view-list .result-card > .rc-foot { display: contents; }
.results-grid.view-list .rc-line { display: none; } /* decorative only -- not a data column */
/* Pickup/dropoff stand names have no dedicated column in the fixed
   12-track list-view grid (same reasoning as .price-fx below: adding
   more mandatory tracks pushes the row wider than the page on a normal
   desktop). Cards view keeps showing them. */
.results-grid.view-list .rc-stand { display: none; }
/* Left-align every column, including the ones that are right-aligned
   or centered by default in Cards view. */
.results-grid.view-list .rc-point-end { text-align: left; }
.results-grid.view-list .rc-track { align-items: flex-start; }
.results-grid.view-list .rc-foot .price { text-align: left; }
.results-grid.view-list .rc-foot .btn-out { justify-self: start; }
/* Wrap instead of forcing the column (and the whole row) wider. rc-time
   is deliberately excluded -- a clock reading should never break
   mid-digit, and its column is sized to fit "08:01" plus a "+1" sup. */
.results-grid.view-list .rc-operator,
.results-grid.view-list .rc-date,
.results-grid.view-list .rc-duration,
.results-grid.view-list .rc-via,
.results-grid.view-list .rc-foot .price,
.results-grid.view-list .rc-foot .btn-out { white-space: normal; word-break: break-word; }
/* Town names wrap between words only -- never "Sumbawan-ga". */
.results-grid.view-list .rc-city { white-space: normal; word-break: normal; overflow-wrap: normal; }
.results-grid.view-list .connection-card { display: block; }
.results-grid.view-list .connection-card > * + * { margin-top: 10px; }
/* Browsers now apply justify-items to block layout too, so the mobile
   list-view `justify-items: start` below would shrink every part of a
   connection card to its content width. Extra class = wins at any width. */
.results-grid.view-list .result-card.connection-card { justify-items: normal; }
/* The 12-column table needs ~960px once town names are full-size; below
   that each row stacks into readable groups instead of squeezing names. */
@media (max-width: 960px) {
  .results-grid.view-list .result-card {
    grid-template-columns: 1fr;
    justify-items: start;
  }
  /* Undo the desktop list-view `display: contents` explicitly (not via
     `revert`, which would fall back to the browser default rather than
     these elements' own flex layout) so the stacked mobile card reads
     top-to-bottom in logical groups instead of one long flat list. */
  .results-grid.view-list .rc-head,
  .results-grid.view-list .rc-journey,
  .results-grid.view-list .rc-foot { display: flex; }
  .results-grid.view-list .rc-point,
  .results-grid.view-list .rc-track { display: flex; flex-direction: column; }
  .results-grid.view-list .rc-line { display: flex; }
}
.badge {
  display: inline-block;
  font-size: 0.7rem;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .04em;
  color: var(--text-dim);
  border: 1px solid var(--border);
  border-radius: 6px;
  padding: 2px 6px;
  margin-bottom: 8px;
  margin-right: 4px;
}
/* Modes stay mixed together in one list (not grouped into separate
   sections) -- color + icon on the badge and a left-border accent on the
   card are enough to tell them apart at a glance while scanning. */
.badge-bus   { color: #9a5b13; border-color: #e8c391; background: rgba(232, 163, 61, 0.14); }
.badge-boat  { color: #0b5c8a; border-color: #8fc3e0; background: rgba(15, 122, 176, 0.12); }
.badge-train { color: #0b5c45; border-color: #8fd6bc; background: rgba(15, 122, 92, 0.14); }
.badge-plane { color: #6a3d9a; border-color: #cbb3e8; background: rgba(122, 61, 176, 0.12); }
.result-card.mode-bus, .connection-leg.mode-bus     { border-left: 3px solid #e8a33d; }
.result-card.mode-boat, .connection-leg.mode-boat    { border-left: 3px solid #1a86c2; }
.result-card.mode-train, .connection-leg.mode-train   { border-left: 3px solid #0f7a5c; }
.result-card.mode-plane, .connection-leg.mode-plane   { border-left: 3px solid #8a4fc2; }
#empty-state { color: var(--text-dim); }
.route-request-form { margin-top: 16px; max-width: 480px; }
.route-request-label { margin: 0 0 8px; font-size: 0.9rem; }
.route-request-row { display: flex; gap: 8px; flex-wrap: wrap; }
.route-request-row input {
  flex: 1;
  min-width: 180px;
  padding: 10px 12px;
  border: 1px solid var(--border);
  border-radius: 8px;
  background: var(--surface);
  color: var(--text);
  font-size: 0.9rem;
}
.route-request-row button {
  background: var(--brand);
  color: #fff;
  border: none;
  border-radius: 8px;
  padding: 10px 16px;
  font-weight: 700;
  font-size: 0.85rem;
  cursor: pointer;
}
.route-request-row button:hover { background: var(--brand-dark); }
.route-request-status { margin-top: 8px; font-size: 0.85rem; color: var(--brand-dark); }

.verified-mark { color: var(--brand); font-weight: 700; }
/* Seat class under the operator name. Inside .rc-operator (not its own
   cell) so list view's column grid keeps the same number of cells. */
.rc-class { display: block; font-size: 0.75rem; font-weight: 600; color: var(--text-dim); }

.connection-card { grid-column: 1 / -1; }
.connections-more {
  grid-column: 1 / -1;
  background: var(--surface);
  color: var(--brand-dark);
  border: 1px dashed var(--border);
  border-radius: var(--radius);
  padding: 12px;
  font-weight: 700;
  font-size: 0.85rem;
  cursor: pointer;
}
.connections-more:hover { border-color: var(--brand); }
.connection-card .route { font-size: 1.1rem; font-weight: 700; }
.connection-card .route strong { color: var(--brand-dark); }
.connection-leg {
  display: flex;
  flex-direction: column;
  gap: 10px;
  border-top: 1px solid var(--border);
  padding-top: 10px;
  margin-top: 10px;
}
.connection-leg .rc-foot { padding-top: 0; border-top: none; }
.connection-leg .price { color: var(--accent); font-weight: 700; margin: 0; }
.connection-leg .btn-out { margin-right: 0; white-space: nowrap; }

/* Sort control above the connections list. */
.conn-toolbar { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; margin-top: 12px; }
.conn-toolbar[hidden] { display: none; }
.conn-toolbar label { font-size: 0.82rem; font-weight: 600; color: var(--text-dim); }
.conn-toolbar select {
  padding: 7px 10px;
  border: 1px solid var(--border);
  border-radius: 8px;
  background: var(--surface);
  color: var(--text);
  font: inherit;
  font-size: 0.85rem;
  font-weight: 600;
  max-width: 100%;
}
.conn-toolbar select:focus-visible { outline: 2px solid var(--brand); outline-offset: 1px; }
.conn-count { font-size: 0.8rem; color: var(--text-dim); }

.conn-head { display: flex; align-items: center; justify-content: space-between; gap: 8px; flex-wrap: wrap; }
.conn-head .badge { margin-bottom: 0; }
.conn-tags { display: flex; gap: 6px; flex-wrap: wrap; }
.conn-tag {
  font-size: 0.7rem;
  font-weight: 700;
  color: var(--brand-dark);
  background: rgba(15, 122, 92, 0.1);
  border: 1px solid rgba(15, 122, 92, 0.3);
  border-radius: 999px;
  padding: 2px 8px;
}
.connection-card .route { margin: 0; }

/* The comparable figures for one connection. Whatever the list is sorted
   by gets the brand outline. */
.conn-stats {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(128px, 1fr));
  gap: 8px;
}
.conn-stat {
  display: flex;
  flex-direction: column;
  gap: 1px;
  padding: 7px 10px;
  border: 1px solid var(--border);
  border-radius: 8px;
  min-width: 0;
}
.conn-stat.is-sort { border-color: var(--brand); box-shadow: inset 0 0 0 1px var(--brand); }
.conn-stat-label { font-size: 0.66rem; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; color: var(--text-dim); }
.conn-stat.is-sort .conn-stat-label { color: var(--brand-dark); }
.conn-stat-value { font-size: 0.95rem; font-weight: 800; white-space: nowrap; }
.conn-stat-value sup { font-size: 0.6em; color: var(--accent); margin-left: 1px; }
.conn-stat-sub { font-size: 0.72rem; color: var(--text-dim); overflow-wrap: anywhere; }
.conn-price { color: var(--accent); }
.conn-price .price-fx { display: block; font-size: 0.72rem; font-weight: 600; color: var(--text-dim); }

.conn-notes { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 4px; font-size: 0.8rem; color: var(--text-dim); }
.conn-notes li { padding-left: 18px; position: relative; }
.conn-notes li::before { content: "!"; position: absolute; left: 0; top: 1px; width: 13px; height: 13px; border-radius: 50%; background: var(--accent); color: #1c1b19; font-size: 0.62rem; font-weight: 800; line-height: 13px; text-align: center; }

.not-found { padding-block: 64px 48px; text-align: center; }
.not-found h1 { margin: 0 0 10px; }
.not-found p { color: var(--text-dim); }

.info-grid { display: grid; gap: 16px; grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); padding-block: 36px; }
.info-card { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 18px; }
.info-card h3 { margin: 0 0 8px; }
.info-card p { color: var(--text-dim); font-size: 0.9rem; margin: 0 0 12px; }
.btn-out {
  display: inline-block;
  text-decoration: none;
  font-weight: 700;
  font-size: 0.85rem;
  color: var(--brand-dark);
  margin-right: 12px;
}
.btn-out-unavailable {
  color: var(--text-dim);
  font-weight: 500;
  font-style: italic;
}

#popular-routes { padding-block: 8px 40px; }
#popular-routes h2 { font-size: 1.1rem; margin-bottom: 12px; }
.route-links { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 8px 10px; }
.route-links a {
  display: inline-block;
  padding: 8px 14px;
  border: 1px solid var(--border);
  border-radius: 999px;
  color: var(--text);
  text-decoration: none;
  font-size: 0.85rem;
  background: var(--surface);
}
.route-links a:hover { border-color: var(--brand); color: var(--brand-dark); }

.route-intro { color: var(--text-dim); max-width: 70ch; margin: 0 0 20px; }

.related-routes { margin: 32px 0 12px; }
.related-routes h3 { font-size: 1rem; margin: 0 0 12px; }
.related-routes ul { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 8px 10px; }
.related-routes a {
  display: inline-block;
  padding: 8px 14px;
  border: 1px solid var(--border);
  border-radius: 999px;
  color: var(--text);
  text-decoration: none;
  font-size: 0.85rem;
  background: var(--surface);
}
.related-routes a:hover { border-color: var(--brand); color: var(--brand-dark); }

.route-map { margin: 32px 0 0; }
.route-map h3 { font-size: 1rem; margin: 0 0 10px; }
/* isolation keeps Leaflet's high z-index panes under the search suggestions. */
#route-map { height: 340px; border: 1px solid var(--border); border-radius: var(--radius); background: var(--surface); overflow: hidden; isolation: isolate; }
#route-map.route-map-failed { display: flex; align-items: center; justify-content: center; }
#route-map.route-map-failed::after { content: "The map couldn't load. Use \"View on Google Maps\" above instead."; color: var(--text-dim); font-size: 0.85rem; padding: 16px; text-align: center; }
.route-map-legend { list-style: none; margin: 8px 0 0; padding: 0; display: flex; flex-wrap: wrap; gap: 4px 16px; font-size: 0.8rem; color: var(--text-dim); }
.route-map-legend li { display: flex; align-items: center; gap: 6px; }
.route-map-note { margin: 4px 0 0; font-size: 0.75rem; color: var(--text-dim); }
.route-map-swatch { display: inline-block; width: 22px; border-top: 4px solid; }
.route-map-swatch.is-straight { border-top-width: 3px; border-top-style: dashed; }
.swatch-bus { border-color: #e8a33d; }
.swatch-boat { border-color: #1a86c2; }
.swatch-train { border-color: #0f7a5c; }
.swatch-plane { border-color: #8a4fc2; }
@media (max-width: 560px) { #route-map { height: 260px; } }

.route-facts { margin: 32px 0 0; max-width: 75ch; }
.route-facts h3 { font-size: 1rem; margin: 0 0 10px; }
.route-facts ul { margin: 0; padding-left: 1.2em; color: var(--text-dim); font-size: 0.9rem; }
.route-facts li { margin: 4px 0; }
.route-facts strong { color: var(--text); }

.all-routes { padding-block: 8px 40px; }
.all-routes h2 { font-size: 1.1rem; margin: 0 0 8px; }
.all-routes-index { display: flex; flex-wrap: wrap; gap: 4px 14px; margin: 0 0 8px; font-size: 0.85rem; }
.all-routes-index a { color: var(--brand-dark); font-weight: 600; text-decoration: none; }
.all-routes-index a:hover { text-decoration: underline; }
.all-routes-group { margin-top: 24px; scroll-margin-top: 16px; }
.all-routes-group h3 { font-size: 1rem; margin: 0 0 10px; }

.site-footer { border-top: 1px solid var(--border); margin-top: 24px; }
.site-footer .wrap { padding-block: 24px; color: var(--text-dim); font-size: 0.8rem; }
.site-footer p { margin: 0 0 6px; }
.site-footer .footer-links a { color: var(--brand-dark); font-weight: 600; }
