/* One stylesheet, one file — which is what lets the Content-Security-Policy be
   `default-src 'self'` with no exception for inline styles. */

:root {
  color-scheme: light dark;

  --bg: #fbfaf7;
  --surface: #ffffff;
  --border: #d8d2c2;
  /* The edge of a control, as distinct from the edge of a card. WCAG 1.4.11
     asks for 3:1 on the visual boundary of a user interface component -- what
     tells you where a field begins -- and asks nothing of a decorative divider.
     --border is 1.5:1 against both backgrounds, which is right for the second
     job and not the first. Measured, not chosen by eye: this is the nearest
     colour to --border, at the same hue and saturation, that clears 3:1 against
     the page and a card both (3.19 and 3.06). */
  --control-border: #9e8f68;
  --text: #24211c;
  --muted: #6b665c;
  --accent: #7a3e12;
  --accent-text: #ffffff;
  --error-bg: #fdf0ec;
  --error-border: #e6b8a8;
  --error-text: #8a2c12;
  --badge-bg: #f1eee7;
  --badge-text: #4a463e;
  --open-bg: #eaf3ec;
  --open-text: #2f6b40;
  --repeat-bg: #f4ecdd;
  --repeat-text: #7a5410;
  --down: #2f6b40;
  --up: #8a2c12;

  --radius: 6px;
  --font: ui-sans-serif, system-ui, -apple-system, "Segoe UI", Roboto,
          "Helvetica Neue", Arial, "Noto Sans", sans-serif;
}

@media (prefers-color-scheme: dark) {
  :root {
    --bg: #16150f;
    --surface: #1e1d16;
    --border: #3b382f;
    --control-border: #6d6757;   /* 3.00 on a card, 3.25 on the page */
    --text: #ece8df;
    --muted: #9c968a;
    --accent: #d99a5f;
    --accent-text: #1a1811;
    --error-bg: #2c1a14;
    --error-border: #6a3626;
    --error-text: #f0b6a0;
    --badge-bg: #26241c;
    --badge-text: #b7b1a4;
    --open-bg: #1b2a1e;
    --open-text: #86c096;
    --repeat-bg: #2a2318;
    --repeat-text: #dfb469;
    --down: #86c096;
    --up: #e8a68d;
  }
}

* { box-sizing: border-box; }

body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font-family: var(--font);
  font-size: 16px;
  line-height: 1.5;
  -webkit-text-size-adjust: 100%;
}

.page {
  max-width: 62rem;
  margin: 0 auto;
  padding: 1.5rem 1rem 4rem;
}

/* --- header ------------------------------------------------------------- */

/* --- reaching things without a mouse ------------------------------------- */

/* Off screen but not hidden: display:none and visibility:hidden would take it
   out of the accessibility tree as well, which is the opposite of the point. */
.visually-hidden {
  position: absolute;
  width: 1px;
  height: 1px;
  margin: -1px;
  padding: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
  border: 0;
}

/* The skip link is the first thing focus reaches and is invisible until it
   does. Five focusable items sit in the header of every page. */
.skip {
  position: absolute;
  left: -9999px;
  top: 0;
  z-index: 10;
  padding: 0.6rem 0.9rem;
  background: var(--surface);
  color: var(--text);
  border: 1px solid var(--control-border);
  border-radius: 0 0 var(--radius) 0;
}

.skip:focus {
  left: 0;
}

/* Keyboard focus is visible on everything focusable, not only the handful of
   controls that had their own rule. :focus-visible rather than :focus, so a
   mouse click does not leave a ring behind. */
a:focus-visible,
button:focus-visible,
select:focus-visible,
input:focus-visible,
summary:focus-visible,
[tabindex]:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}

/* Which page you are on, for anyone who can see it. aria-current says the same
   thing to anyone who cannot. */
.site-header nav a.here {
  font-weight: 600;
  text-decoration: underline;
  text-underline-offset: 4px;
}

.site-header {
  display: flex;
  flex-wrap: wrap;
  gap: 0.75rem;
  align-items: baseline;
  justify-content: space-between;
  padding: 0.85rem 1rem;
  border-bottom: 1px solid var(--border);
  background: var(--surface);
}

.brand {
  font-weight: 650;
  letter-spacing: -0.01em;
  color: var(--text);
  text-decoration: none;
}

.site-header nav {
  display: flex;
  align-items: baseline;
  gap: 0.9rem;
}

.who { color: var(--muted); font-size: 0.9rem; }

.inline { display: inline; margin: 0; }

.linkish {
  border: 0;
  padding: 0;
  background: none;
  font: inherit;
  font-size: 0.9rem;
  color: var(--accent);
  cursor: pointer;
  text-decoration: underline;
  text-underline-offset: 2px;
}

/* --- login -------------------------------------------------------------- */

.login {
  max-width: 22rem;
  margin: 12vh auto 0;
  padding: 1.75rem;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
}

.login h1 {
  margin: 0 0 0.25rem;
  font-size: 1.25rem;
  letter-spacing: -0.01em;
}

.login .lede {
  margin: 0 0 1.5rem;
  color: var(--muted);
  font-size: 0.9rem;
}

.field { margin-bottom: 1rem; }

.field label {
  display: block;
  margin-bottom: 0.3rem;
  font-size: 0.85rem;
  font-weight: 550;
  color: var(--muted);
}

.field input,
.field select {
  width: 100%;
  padding: 0.55rem 0.65rem;
  font: inherit;
  color: var(--text);
  background: var(--bg);
  border: 1px solid var(--control-border);
  border-radius: var(--radius);
}

/* The selects were left to the browser's own border, which varies by platform
   and is not something the palette can promise anything about. Now they are
   drawn like every other field, and the same colour has to answer for them. */

.field input:focus-visible,
.field select:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 1px;
}

button.primary {
  width: 100%;
  padding: 0.6rem 1rem;
  font: inherit;
  font-weight: 550;
  color: var(--accent-text);
  background: var(--accent);
  border: 1px solid var(--accent);
  border-radius: var(--radius);
  cursor: pointer;
}

button.primary:hover { filter: brightness(1.08); }
button.primary:focus-visible { outline: 2px solid var(--text); outline-offset: 2px; }

/* --- notices ------------------------------------------------------------ */

.notice {
  padding: 0.75rem 0.9rem;
  margin-bottom: 1.25rem;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  background: var(--surface);
  font-size: 0.92rem;
}

.notice-error {
  background: var(--error-bg);
  border-color: var(--error-border);
  color: var(--error-text);
}

/* Why an object is waiting for a person. The same colours as the badge beside
   it, so the two read as one statement rather than two warnings. */
.notice-review {
  background: var(--error-bg);
  border-color: var(--error-border);
  color: var(--error-text);
}

/* Two auctions of the same thing running at once. Deliberately not the error
   palette: nothing is wrong, the reader is just about to read a list of prices
   as a sequence when it is not one. It explains, so it stays quiet. */
.notice-concurrent {
  font-size: 0.86rem;
  color: var(--muted);
  margin-bottom: 0.75rem;
}

.notice h1 { margin: 0 0 0.4rem; font-size: 1.05rem; }
.notice p  { margin: 0; }

/* --- placeholder content ------------------------------------------------ */

.card {
  padding: 1.25rem;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
}

.card h1 { margin-top: 0; font-size: 1.2rem; letter-spacing: -0.01em; }

.stats { display: flex; flex-wrap: wrap; gap: 1.5rem; margin: 1.25rem 0 0; padding: 0; list-style: none; }
.stats li { min-width: 7rem; }
.stats .n { display: block; font-size: 1.5rem; font-weight: 600; font-variant-numeric: tabular-nums; }
.stats .k { color: var(--muted); font-size: 0.85rem; }

.muted { color: var(--muted); }

/* --- filters ------------------------------------------------------------ */

.filters {
  padding: 1rem;
  margin-bottom: 1.25rem;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
}

.filters-row {
  display: flex;
  flex-wrap: wrap;
  gap: 0.75rem 1rem;
  align-items: flex-end;
}

.filters-row + .filters-row { margin-top: 0.85rem; }

.filters .field { margin-bottom: 0; }
.filters .field.grow { flex: 1 1 14rem; }

.filters select,
.filters input[type="date"] {
  padding: 0.45rem 0.5rem;
  font: inherit;
  font-size: 0.92rem;
  color: var(--text);
  background: var(--bg);
  border: 1px solid var(--control-border);
  border-radius: var(--radius);
}

.filters input { font-size: 0.92rem; padding: 0.45rem 0.55rem; }

.checkfield label {
  display: flex;
  gap: 0.4rem;
  align-items: center;
  margin: 0;
  font-size: 0.9rem;
  font-weight: 400;
  color: var(--text);
  white-space: nowrap;
}

.field.actions { display: flex; align-items: center; gap: 0.75rem; }
.field.actions button.primary { width: auto; padding: 0.45rem 1.1rem; }

.result-count { margin: 0 0 1rem; color: var(--muted); font-size: 0.92rem; }
.result-count strong { color: var(--text); font-variant-numeric: tabular-nums; }

/* --- object list -------------------------------------------------------- */

.objects { margin: 0; padding: 0; list-style: none; }

.object {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem 1.5rem;
  justify-content: space-between;
  padding: 0.9rem 1rem;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  margin-bottom: 0.6rem;
}

.object-main { flex: 1 1 20rem; min-width: 0; }

.object-title {
  margin: 0 0 0.35rem;
  font-size: 1rem;
  font-weight: 600;
  line-height: 1.35;
  /* A package lot's title is the whole inventory — five machines in one string.
     Clamped so one row cannot push the rest of the list off the screen; the
     detail page shows it in full. */
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
}
.object-title a { color: var(--text); text-decoration: none; }
.object-title a:hover { text-decoration: underline; text-underline-offset: 2px; }

/* The seller's own description, shown whole when the heading had to shorten it.
   Newlines are meaningful in these -- they separate a vehicle's mileage from
   its damage, or one machine in a lot from the next. */
.object-description {
  margin: 0.4rem 0 0.8rem;
  color: var(--muted);
  font-size: 0.95rem;
  line-height: 1.5;
}

.object-meta,
.object-where { margin: 0.2rem 0 0; font-size: 0.85rem; display: flex; flex-wrap: wrap; gap: 0.4rem; align-items: center; }

.object-figures {
  flex: 0 0 auto;
  text-align: right;
  min-width: 9rem;
}

.object-figures p { margin: 0; }

.price {
  font-size: 1.05rem;
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.from-price, .when, .source { font-size: 0.8rem; }
.when .soon { margin-left: 0.35rem; color: var(--accent); }

.change {
  margin-left: 0.35rem;
  font-size: 0.8rem;
  font-weight: 600;
  white-space: nowrap;
}
.change.down { color: var(--down); }
.change.up   { color: var(--up); }

/* --- badges ------------------------------------------------------------- */

.badge {
  display: inline-block;
  padding: 0.1rem 0.45rem;
  font-size: 0.75rem;
  font-weight: 600;
  line-height: 1.5;
  border-radius: 999px;
  border: 1px solid transparent;
  white-space: nowrap;
}

.badge-announced { background: var(--badge-bg);  color: var(--badge-text);  border-color: var(--border); }
.badge-open      { background: var(--open-bg);   color: var(--open-text);   border-color: var(--open-text); }
.badge-cancelled { background: var(--error-bg);  color: var(--error-text);  border-color: var(--error-border); }
.badge-sold      { background: var(--open-bg);   color: var(--open-text);   border-color: var(--open-text); }
.badge-unsold    { background: var(--badge-bg);  color: var(--muted);       border-color: var(--border); }
.badge-neutral   { background: var(--badge-bg);  color: var(--muted);       border-color: var(--border); }
.badge-repeat    { background: var(--repeat-bg); color: var(--repeat-text); border-color: var(--repeat-text); }
.badge-review    { background: var(--error-bg);  color: var(--error-text);  border-color: var(--error-border); }

/* --- pagination --------------------------------------------------------- */

.pager {
  display: flex;
  gap: 1.25rem;
  align-items: baseline;
  justify-content: center;
  margin-top: 1.5rem;
  font-size: 0.92rem;
}

.pager a { color: var(--accent); }
.pager .disabled { color: var(--muted); opacity: 0.5; }

/* --- object detail ------------------------------------------------------ */

.crumbs { margin: 0 0 1rem; font-size: 0.9rem; }
.crumbs a { color: var(--accent); }

.object-detail h1 {
  margin: 0 0 0.5rem;
  font-size: 1.4rem;
  letter-spacing: -0.015em;
  line-height: 1.25;
  overflow-wrap: break-word;
}

.section-heading { margin: 2rem 0 0.75rem; font-size: 1.05rem; }

.trajectory, .identity { margin-top: 1.5rem; }
.trajectory h2, .identity h2 { margin: 0 0 0.5rem; font-size: 0.95rem; }

.rounds { margin: 0 0 0.75rem; padding: 0; list-style: none; }

.rounds li {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem 0.9rem;
  align-items: baseline;
  padding: 0.4rem 0;
  border-bottom: 1px solid var(--border);
}
.rounds li:last-child { border-bottom: 0; }

.round-no    { min-width: 1.5rem; color: var(--muted); font-variant-numeric: tabular-nums; }
.round-price { font-weight: 600; font-variant-numeric: tabular-nums; min-width: 7rem; }
.round-date  { margin-left: auto; font-size: 0.85rem; }

.keys { margin: 0; padding: 0; list-style: none; font-size: 0.88rem; }
.keys li { display: flex; gap: 0.6rem; align-items: baseline; padding: 0.2rem 0; }
.keys code {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 0.85em;
  padding: 0.05rem 0.3rem;
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: 4px;
}

.auction { margin-bottom: 0.85rem; }
.auction-header h3 { margin: 0 0 0.25rem; font-size: 1rem; display: flex; gap: 0.5rem; align-items: center; flex-wrap: wrap; }
.auction-header p { margin: 0 0 0.75rem; }

.facts {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(9.5rem, 1fr));
  gap: 0.6rem 1.25rem;
  margin: 0.75rem 0 0;
}
.facts dt { color: var(--muted); font-size: 0.78rem; }
.facts dd { margin: 0.1rem 0 0; font-size: 0.92rem; font-variant-numeric: tabular-nums; }

.history { margin-top: 1rem; }
.history summary { cursor: pointer; font-size: 0.88rem; color: var(--accent); }
.history summary:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }

.versions { margin: 0.75rem 0 0; padding-left: 1.1rem; }
.versions li { margin-bottom: 0.85rem; }
.versions p { margin: 0.1rem 0; }
.version-when { font-size: 0.88rem; }

.provenance {
  overflow-wrap: anywhere;
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 0.75rem;
}

.small { font-size: 0.85rem; }

/* --- narrow screens ----------------------------------------------------- */

@media (max-width: 34rem) {
  .object { flex-direction: column; gap: 0.5rem; }
  .object-figures { text-align: left; }
  .round-date { margin-left: 0; width: 100%; }
  .filters-row { gap: 0.6rem 0.8rem; }
}

/* --- files -------------------------------------------------------------- */

.gallery {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem;
  margin: 1rem 0 0;
  padding: 0;
  list-style: none;
}

.gallery img {
  display: block;
  width: 9rem;
  height: 6.5rem;
  object-fit: cover;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  background: var(--bg);
}

.gallery a:focus-visible img { outline: 2px solid var(--accent); outline-offset: 2px; }

.attachments { margin: 1rem 0 0; padding: 0; list-style: none; font-size: 0.9rem; }
.attachments li { display: flex; gap: 0.5rem; align-items: baseline; padding: 0.15rem 0; }
.attachments a { color: var(--accent); }

/* --- navigation --------------------------------------------------------- */

.site-header nav a { color: var(--accent); text-decoration: none; font-size: 0.9rem; }
.site-header nav a:hover { text-decoration: underline; text-underline-offset: 2px; }

.site-header nav .count {
  display: inline-block;
  min-width: 1.2rem;
  padding: 0 0.3rem;
  margin-left: 0.15rem;
  font-size: 0.72rem;
  font-weight: 700;
  line-height: 1.35;
  text-align: center;
  color: var(--accent-text);
  background: var(--accent);
  border-radius: 999px;
}

/* --- changes feed ------------------------------------------------------- */

.feed-head {
  display: flex;
  flex-wrap: wrap;
  gap: 0.75rem 1.5rem;
  align-items: flex-start;
  justify-content: space-between;
  margin-bottom: 1.25rem;
}

.feed-head h1 { margin: 0 0 0.2rem; font-size: 1.25rem; letter-spacing: -0.01em; }
.feed-head p { margin: 0; }

button.primary.compact { width: auto; padding: 0.4rem 0.9rem; font-size: 0.9rem; }

.changes { margin: 0; padding: 0; list-style: none; }

.change {
  padding: 0.75rem 1rem;
  margin-bottom: 0.5rem;
  background: var(--surface);
  border: 1px solid var(--border);
  border-left: 3px solid var(--border);
  border-radius: var(--radius);
}

/* An unread change is marked on the edge rather than by a different background:
   the row stays legible and the whole list does not become a wall of colour. */
.change.unseen { border-left-color: var(--accent); }

.change p { margin: 0; }
.change-when { display: flex; gap: 0.5rem; align-items: center; }
.change-what { margin: 0.2rem 0 0.3rem; display: flex; flex-wrap: wrap; gap: 0.4rem; align-items: center; }
.change-what a { color: var(--text); font-weight: 600; }

.change-detail { margin: 0.2rem 0 0.4rem; padding-left: 1.1rem; font-size: 0.9rem; }
.change-detail li { margin: 0.1rem 0; font-variant-numeric: tabular-nums; }

/* An inference is marked differently from anything the source said: dashed,
   because the shape itself should say "not certain" before the word is read. */
.badge-inferred {
  background: transparent;
  color: var(--muted);
  border: 1px dashed var(--muted);
  font-weight: 500;
}

/* --- review queue ------------------------------------------------------- */

.page-title { margin: 0 0 0.3rem; font-size: 1.25rem; letter-spacing: -0.01em; }

.tabs {
  display: flex;
  flex-wrap: wrap;
  gap: 0.25rem;
  margin: 1.25rem 0 1rem;
  border-bottom: 1px solid var(--border);
}

.tabs a {
  padding: 0.45rem 0.8rem;
  font-size: 0.9rem;
  color: var(--muted);
  text-decoration: none;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}

.tabs a.current { color: var(--text); border-bottom-color: var(--accent); font-weight: 600; }
.tabs a:hover { color: var(--text); }

.review-list { margin: 0; padding: 0; list-style: none; }

.review-item {
  display: flex;
  flex-wrap: wrap;
  gap: 1rem 1.5rem;
  justify-content: space-between;
  padding: 0.9rem 1rem;
  margin-bottom: 0.6rem;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius);
}

.review-what { flex: 1 1 22rem; min-width: 0; }
.review-what h2 { margin: 0 0 0.25rem; font-size: 1rem; font-weight: 600; line-height: 1.35; }
.review-what p { margin: 0.15rem 0; }
.review-what .keys { margin-top: 0.4rem; }

.review-actions { flex: 0 1 22rem; }
.review-actions label { display: block; margin-bottom: 0.25rem; color: var(--muted); }
.review-actions select {
  width: 100%;
  margin-bottom: 0.5rem;
  padding: 0.4rem 0.5rem;
  font: inherit;
  font-size: 0.88rem;
  color: var(--text);
  background: var(--bg);
  border: 1px solid var(--control-border);
  border-radius: var(--radius);
}

.auction-links { display: flex; flex-wrap: wrap; gap: 0.75rem; align-items: baseline; }

.lot-note { font-size: 0.78rem; }

/* --- price trajectory --------------------------------------------------- */

.price-path {
  display: flex;
  gap: 0.35rem;
  align-items: center;
  justify-content: flex-end;
  flex-wrap: wrap;
  font-size: 0.78rem;
  font-variant-numeric: tabular-nums;
}

.spark { flex: 0 0 auto; overflow: visible; }
.spark.down { color: var(--down); }
.spark.up   { color: var(--up); }
/* A price that held is neither. Drawn in the secondary text colour, which is
   what every other "nothing to report" on the row uses. */
.spark.flat { color: var(--muted); }

@media (max-width: 34rem) {
  .price-path { justify-content: flex-start; }
}
