.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);
  padding: var(--space-3) var(--space-5);
  min-height: 44px;
  border-radius: var(--radius-1);
  border: 1px solid transparent;
  font-family: var(--font-body);
  font-weight: var(--fw-bold);
  font-size: var(--fs-300);
  white-space: nowrap;
  cursor: pointer;
  transition:
    border-color var(--duration-fast) var(--ease-standard),
    background-color var(--duration-fast) var(--ease-standard),
    color var(--duration-fast) var(--ease-standard);
}

.btn:disabled {
  opacity: 0.5;
  cursor: not-allowed;
}

/* Sharp bevelled corner instead of a rounded/glowing treatment - the site's
   structural signature for "this is the primary action" (hero CTAs, primary
   buttons, the rank/identity chips), used sparingly rather than on every
   surface. Kept as its own class (not baked into --radius-*) so it stays
   opt-in per component. */
.bevel {
  clip-path: polygon(0 0, calc(100% - 12px) 0, 100% 12px, 100% 100%, 0 100%);
}
.bevel-lg {
  clip-path: polygon(0 0, calc(100% - 18px) 0, 100% 18px, 100% 100%, 0 100%);
}

/* Numeric readouts (ELO, K/D, prices, floats, timestamps) - monospaced with
   tabular figures so digits line up in columns, distinct from the display
   font used for headings/labels elsewhere. */
.num {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
}

.btn--primary {
  background: var(--color-accent);
  color: var(--color-text-on-accent);
  clip-path: polygon(0 0, calc(100% - 10px) 0, 100% 10px, 100% 100%, 0 100%);
}
.btn--primary:hover:not(:disabled),
.btn--primary:focus-visible:not(:disabled) {
  background: var(--color-accent-hover);
}
.btn--primary:active:not(:disabled) {
  background: var(--color-accent-strong);
}

.btn--secondary {
  background: transparent;
  border-color: var(--color-border-strong);
  color: var(--color-text);
}
.btn--secondary:hover:not(:disabled) {
  border-color: var(--color-accent);
  color: var(--color-text);
}

.btn--ghost {
  background: transparent;
  color: var(--color-text-muted);
}
.btn--ghost:hover:not(:disabled) {
  background: var(--color-accent-muted);
  color: var(--color-text);
}

.btn--sm {
  min-height: 36px;
  padding: var(--space-2) var(--space-4);
  font-size: var(--fs-200);
}
.btn--lg {
  min-height: 56px;
  padding: var(--space-4) var(--space-7);
  font-size: var(--fs-400);
}

.btn--icon {
  padding: 0;
  width: 44px;
}
.btn--icon.btn--sm {
  width: 36px;
}

/* Standalone square icon button (dashboard topline, mobile top bar) -
   distinct from .btn--icon, which is a sizing modifier on the full .btn
   component (border, min-height, etc.) rather than this bare shape. */
.icon-btn {
  width: 36px;
  height: 36px;
  border-radius: var(--radius-1);
  background: var(--color-surface);
  border: 1px solid var(--color-border);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  color: var(--color-text-muted);
  flex-shrink: 0;
}
.icon-btn svg {
  width: 17px;
  height: 17px;
  stroke: currentColor;
  stroke-width: 1.8px;
  fill: none;
}
.icon-btn:hover,
.icon-btn:focus-visible {
  color: var(--color-text);
  border-color: var(--color-border-strong);
}

@media (pointer: coarse) {
  .btn--sm {
    min-height: 44px;
  }
  .btn--icon.btn--sm {
    width: 44px;
  }
}

.btn svg {
  width: 1.2em;
  height: 1.2em;
  fill: currentColor;
  flex-shrink: 0;
}

.card {
  background: var(--color-surface);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-2);
  padding: var(--space-6);
  box-shadow: inset 3px 0 0 transparent;
  transition:
    border-color var(--duration-base) var(--ease-standard),
    box-shadow var(--duration-base) var(--ease-standard);
}
.card--interactive:hover,
.card--interactive:focus-visible {
  border-color: var(--color-border-strong);
  box-shadow: inset 3px 0 0 var(--color-accent);
}

.card--elevated {
  background: var(--color-surface-alt);
  border-radius: var(--radius-2);
  padding: var(--space-7);
  box-shadow: var(--shadow-2);
}

/* Rounded-square avatars (not circles) - the artifact's identicon treatment.
   Radius scales with size so small avatars (nav/lists) stay tight-cornered
   and large ones (podium/profile) read closer to a soft square. */
.avatar {
  --avatar-size: 44px;
  --avatar-radius: 9px;
  width: var(--avatar-size);
  height: var(--avatar-size);
  border-radius: var(--avatar-radius);
  overflow: hidden;
  flex-shrink: 0;
  display: grid;
  place-items: center;
  background: linear-gradient(180deg, color-mix(in srgb, var(--color-accent) 45%, var(--color-bg-elevated)) 0%, var(--color-bg) 100%);
  border: 1px solid var(--color-border-strong);
}
.avatar img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
.avatar--xs {
  --avatar-size: 28px;
  --avatar-radius: 7px;
}
.avatar--sm {
  --avatar-size: 36px;
  --avatar-radius: 7px;
}
.avatar--md {
  --avatar-size: 44px;
  --avatar-radius: 9px;
}
.avatar--lg {
  --avatar-size: 88px;
  --avatar-radius: 12px;
}
.avatar--xl {
  --avatar-size: 140px;
  border-radius: 14px;
  border: 2px solid var(--color-accent);
}

.avatar-stack {
  display: flex;
}
.avatar-stack .avatar {
  margin-left: -12px;
  border-color: var(--color-bg-elevated);
}
.avatar-stack .avatar:first-child {
  margin-left: 0;
}

.label {
  font-family: var(--font-body);
  font-size: var(--fs-100);
  font-weight: var(--fw-bold);
  text-transform: uppercase;
  letter-spacing: var(--tracking-wider);
  color: var(--color-text-faint);
}

/* Shared page-header pattern: eyebrow label above an h1, with page-level
   controls (search, tabs, buttons) aligned to its baseline on the right.
   Add alongside a page's existing header wrapper class - it only supplies
   layout + the h1 size, page-specific CSS can still layer small deltas. */
.page-head {
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: var(--space-4);
}
.page-head h1 {
  margin-top: var(--space-1);
}

/* Compact "identity/hero" card used on the app dashboard/profile/project
   pages - a diagonal gradient background with an angular accent wedge
   bleeding in from the top-right corner. Not the full-bleed marketing
   hero (styles.css resets .hero/.hero-wedge entirely for that context). */
.hero {
  position: relative;
  overflow: hidden;
  background: linear-gradient(115deg, var(--color-surface) 0%, var(--color-bg-elevated) 61%);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-2);
}
.hero-wedge {
  position: absolute;
  top: 0;
  right: 0;
  width: 46%;
  height: 100%;
  background: linear-gradient(100deg, transparent 28%, var(--color-accent-muted) 100%);
  clip-path: polygon(38% 0, 100% 0, 100% 100%, 62% 100%);
  pointer-events: none;
}
.hero--accent .hero-wedge {
  background: linear-gradient(100deg, transparent 28%, var(--color-accent) 100%);
}
/* Optional extra texture/light for a card hero (app/profile/project - not
   the full-bleed marketing hero, which already has its own dot-grid via
   styles.css's .hero::before) - add alongside .hero-wedge, both aria-hidden.
   .hero-lines is a fine diagonal hairline pattern clipped to the exact same
   wedge shape as .hero-wedge itself, layered on top of its fill so the
   wedge reads as textured rather than a flat gradient block. .hero-glow is
   a soft accent light in the wedge's corner, giving the panel a light
   source instead of one uniform tint throughout. */
.hero-lines {
  position: absolute;
  inset: 0;
  clip-path: polygon(38% 0, 100% 0, 100% 100%, 62% 100%);
  background-image: repeating-linear-gradient(115deg, rgba(255, 255, 255, 0.035) 0px, rgba(255, 255, 255, 0.035) 1px, transparent 1px, transparent 26px);
  pointer-events: none;
}
.hero-glow {
  position: absolute;
  width: 420px;
  height: 420px;
  right: -120px;
  top: -180px;
  background: radial-gradient(circle, rgba(78, 130, 255, 0.28) 0%, transparent 70%);
  filter: blur(10px);
  pointer-events: none;
}
.hero-content {
  position: relative;
  z-index: 1;
}

.ticker {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: 1fr;
  border: 1px solid var(--color-border);
  background: var(--color-bg-elevated);
}
.ticker-item {
  padding: var(--space-5) var(--space-6);
  border-left: 1px solid var(--color-border);
  box-shadow: inset 3px 0 0 transparent;
  transition: box-shadow var(--duration-base) var(--ease-standard);
}
.ticker-item:first-child {
  border-left: none;
}
.ticker-item.is-highlighted {
  box-shadow: inset 3px 0 0 var(--color-accent);
}
.ticker-value {
  display: block;
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-weight: var(--fw-bold);
  font-size: var(--fs-600);
  color: var(--color-text);
  line-height: 1;
}
.ticker-label {
  display: block;
  margin-top: var(--space-2);
  font-family: var(--font-display);
  font-size: var(--fs-100);
  text-transform: uppercase;
  letter-spacing: var(--tracking-wider);
  color: var(--color-text-faint);
}
@media (max-width: 768px) {
  .ticker {
    grid-auto-flow: row;
  }
  .ticker-item {
    border-left: none;
    border-top: 1px solid var(--color-border);
  }
  .ticker-item:first-child {
    border-top: none;
  }
}

.tabs {
  display: flex;
  gap: var(--space-2);
  flex-wrap: wrap;
}

.tabs--underline {
  gap: var(--space-6);
  border-bottom: 1px solid var(--color-border);
}
.tabs--underline [role="tab"] {
  position: relative;
  padding: var(--space-3) 0;
  color: var(--color-text-faint);
  font-family: var(--font-body);
  font-size: var(--fs-300);
  font-weight: var(--fw-bold);
  transition: color var(--duration-base) var(--ease-standard);
}
.tabs--underline [role="tab"]::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  bottom: -1px;
  height: 2px;
  background: var(--color-accent);
  transform: scaleX(0);
  transform-origin: left;
  transition: transform var(--duration-base) var(--ease-standard);
}
.tabs--underline [role="tab"]:hover {
  color: var(--color-text);
}
.tabs--underline [role="tab"][aria-selected="true"] {
  color: var(--color-text);
}
.tabs--underline [role="tab"][aria-selected="true"]::after {
  transform: scaleX(1);
}

.tabs--pill [role="tab"] {
  padding: var(--space-2) var(--space-5);
  border-radius: var(--radius-1);
  border: 1px solid var(--color-border);
  background: var(--color-bg);
  color: var(--color-text-faint);
  font-family: var(--font-body);
  font-size: var(--fs-200);
  font-weight: var(--fw-bold);
  transition:
    background var(--duration-base) var(--ease-standard),
    color var(--duration-base) var(--ease-standard),
    border-color var(--duration-base) var(--ease-standard);
}
.tabs--pill [role="tab"][aria-selected="true"] {
  background: var(--color-accent-muted);
  border-color: var(--color-border-strong);
  color: var(--color-text);
}
.tabs--pill [role="tab"]:hover:not([aria-selected="true"]) {
  border-color: var(--color-accent-border);
  color: var(--color-text);
}

[role="tabpanel"]:focus:not(:focus-visible) {
  outline: none;
}
[role="tabpanel"][hidden] {
  display: none;
}

/* Pill toggle group for a small, mutually-exclusive filter (Matches page's
   Win/Loss/All, the Admin page's Open/All reports filter, ...) - moved here
   from matches.css since it was generic already, just first used there. */
.segmented {
  display: inline-flex;
  padding: 3px;
  gap: 2px;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-1);
  background: var(--color-bg-elevated);
}
.segmented-btn {
  padding: var(--space-1) var(--space-4);
  border-radius: var(--radius-1);
  color: var(--color-text-faint);
  font-family: var(--font-body);
  font-size: var(--fs-200);
  font-weight: var(--fw-bold);
  transition:
    background var(--duration-fast) var(--ease-standard),
    color var(--duration-fast) var(--ease-standard);
}
.segmented-btn:hover:not(.is-active) {
  color: var(--color-text);
}
.segmented-btn.is-active {
  background: var(--color-accent-muted);
  color: var(--color-text);
}

.badge {
  display: inline-flex;
  align-items: center;
  gap: var(--space-1);
  padding: var(--space-1) var(--space-3);
  border-radius: var(--radius-full);
  font-family: var(--font-body);
  font-size: var(--fs-100);
  font-weight: var(--fw-bold);
  white-space: nowrap;
  flex-shrink: 0;
}
.badge--success {
  background: var(--color-success-muted);
  color: var(--color-success);
}
.badge--warning {
  background: var(--color-warning-muted);
  color: var(--color-warning);
}
.badge--danger {
  background: var(--color-danger-muted);
  color: var(--color-danger);
}
.badge--neutral {
  background: var(--color-surface-alt);
  color: var(--color-text-muted);
}

/* Rank-tier pill, same E/D/C/B/A/Star color language as the Profile page's
   .rank-readout-icon (js/profile.js sets the matching modifier there via
   CSUtil.rankGroupFor) - this is the compact table/list version of the same
   system, for anywhere a player's tier needs to show without the full
   rank-readout block (Leaderboard rows, match history rows). Set the
   modifier class via CSUtil.setRankGroupClass(el, 'tier-chip', group). */
.tier-chip {
  display: inline-flex;
  align-items: center;
  gap: var(--space-1);
  padding: 2px var(--space-2);
  border-radius: var(--radius-full);
  font-family: var(--font-mono);
  font-size: var(--fs-100);
  font-weight: var(--fw-bold);
  letter-spacing: 0.02em;
  white-space: nowrap;
}
.tier-chip--e { background: var(--rank-e-muted); color: var(--rank-e); }
.tier-chip--d { background: var(--rank-d-muted); color: var(--rank-d); }
.tier-chip--c { background: var(--rank-c-muted); color: var(--rank-c); }
.tier-chip--b { background: var(--rank-b-muted); color: var(--rank-b); }
.tier-chip--a { background: var(--rank-a-muted); color: var(--rank-a); }
.tier-chip--star { background: var(--rank-star-muted); color: var(--rank-star); }

/* Shared by Profile's Match History tab and the standalone Matches page -
   was duplicated near-verbatim in css/profile.css and css/matches.css. */
.matches-table-card {
  padding: var(--space-5);
}
.matches-footer {
  display: flex;
  justify-content: center;
  margin-top: var(--space-4);
}

.table-wrap {
  overflow-x: auto;
  border-radius: var(--radius-2);
  border: 1px solid var(--color-border);
}
.table {
  width: 100%;
  border-collapse: collapse;
  font-size: var(--fs-300);
}
.table caption {
  text-align: left;
  padding: var(--space-4);
}
.table th {
  text-align: left;
  padding: var(--space-3) var(--space-4);
  font-family: var(--font-body);
  font-size: var(--fs-100);
  text-transform: uppercase;
  letter-spacing: var(--tracking-wide);
  color: var(--color-text-faint);
  border-bottom: 1px solid var(--color-border);
  background: var(--color-bg-elevated);
  position: sticky;
  top: 0;
  z-index: var(--z-sticky);
}
.table th.num,
.table td.num {
  text-align: right;
}
.table td {
  padding: var(--space-3) var(--space-4);
  border-top: 1px solid var(--color-border);
  border-bottom: none;
  color: var(--color-text-muted);
}
.table tbody tr {
  box-shadow: inset 3px 0 0 transparent;
  transition:
    background var(--duration-fast) var(--ease-standard),
    box-shadow var(--duration-fast) var(--ease-standard);
}
.table tbody tr:first-child td {
  border-top: none;
}
.table tbody tr:hover {
  background: var(--color-surface-hover);
}
.table tbody tr.is-current-user {
  background: var(--color-accent-muted);
  box-shadow: inset 3px 0 0 var(--color-accent);
}

.modal-backdrop {
  position: fixed;
  inset: 0;
  background: rgba(3, 6, 12, 0.72);
  backdrop-filter: blur(4px);
  display: grid;
  place-items: center;
  padding: var(--space-5);
  z-index: var(--z-modal-backdrop);
  /* The panel already fades/scales in via modal-in below - without this,
     the dark backdrop behind it just snapped to full opacity instantly
     (display:none can't be transitioned), so the two pieces of the same
     open animation felt disconnected. */
  animation: modal-backdrop-in var(--duration-fast) var(--ease-standard);
}
.modal-backdrop[hidden] {
  display: none;
}
@keyframes modal-backdrop-in {
  from { opacity: 0; }
  to { opacity: 1; }
}
.modal-panel {
  width: min(560px, 100%);
  max-height: 90vh;
  overflow-y: auto;
  background: var(--color-surface);
  border: 1px solid var(--color-border-strong);
  border-radius: var(--radius-2);
  box-shadow: var(--shadow-3);
  padding: var(--space-7);
  position: relative;
  animation: modal-in var(--duration-base) var(--ease-decelerate);
}
@keyframes modal-in {
  from {
    opacity: 0;
    transform: translateY(12px) scale(0.98);
  }
  to {
    opacity: 1;
    transform: translateY(0) scale(1);
  }
}
.modal-close {
  position: absolute;
  top: var(--space-4);
  right: var(--space-4);
}
.modal-title {
  font-family: var(--font-display);
  font-size: var(--fs-500);
  font-weight: var(--fw-bold);
  margin-bottom: var(--space-2);
}

.field {
  display: grid;
  gap: var(--space-2);
}
.field-label {
  font-family: var(--font-display);
  font-size: var(--fs-200);
  text-transform: uppercase;
  letter-spacing: var(--tracking-wide);
  color: var(--color-text-muted);
}
.field-input,
.field select,
.field textarea {
  width: 100%;
  padding: var(--space-3) var(--space-4);
  border-radius: var(--radius-1);
  border: 1px solid var(--color-border);
  background: var(--color-bg-elevated);
  color: var(--color-text);
  font-size: var(--fs-300);
  transition:
    border-color var(--duration-base) var(--ease-standard),
    box-shadow var(--duration-base) var(--ease-standard);
}
.field-input:focus-visible,
.field select:focus-visible,
.field textarea:focus-visible {
  outline: none;
  border-color: var(--color-accent);
  box-shadow: 0 0 0 3px var(--color-accent-muted);
}
.field--error .field-input,
.field--error select,
.field--error textarea {
  border-color: var(--color-danger-border);
}
.field-hint {
  font-size: var(--fs-200);
  color: var(--color-text-faint);
}
.field-error-message {
  display: flex;
  align-items: center;
  gap: var(--space-1);
  font-size: var(--fs-200);
  color: var(--color-danger);
}

.empty-state {
  display: grid;
  justify-items: center;
  gap: var(--space-3);
  padding: var(--space-9) var(--space-5);
  text-align: center;
  color: var(--color-text-muted);
}
.empty-state-icon {
  display: grid;
  place-items: center;
  width: 52px;
  height: 52px;
  border-radius: 13px;
  background: var(--color-surface-alt);
  color: var(--color-text-faint);
}
.empty-state-icon svg {
  width: 25px;
  height: 25px;
  fill: currentColor;
}
/* Outline variant for icons drawn as strokes rather than filled shapes
   (e.g. the Team panel's "widget disabled" notice). */
.empty-state-icon--outline svg {
  fill: none;
  stroke: currentColor;
  stroke-width: 1.6px;
  stroke-linecap: round;
  stroke-linejoin: round;
}
.empty-state-title {
  font-family: var(--font-display);
  font-size: var(--fs-400);
  font-weight: var(--fw-bold);
  color: var(--color-text);
}
.empty-state-body {
  max-width: 42ch;
}

.skeleton {
  position: relative;
  overflow: hidden;
  background: var(--color-surface-alt);
  border-radius: var(--radius-1);
}
/* .skeleton on an inline text element (a stat value before its fetch
   resolves) needs explicit box dimensions - it has no width/height of its
   own with no text content yet. Callers remove the "skeleton" class once
   real text is set (success or error), which also drops these. */
.ticker-value.skeleton,
.quick-value.skeleton {
  display: inline-block;
  width: 3.2em;
  height: 0.85em;
  vertical-align: middle;
  color: transparent;
}
.skeleton::after {
  content: "";
  position: absolute;
  inset: 0;
  background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.06), transparent);
  transform: translateX(-100%);
  animation: skeleton-shimmer 1.6s infinite;
}
@keyframes skeleton-shimmer {
  100% {
    transform: translateX(100%);
  }
}
@media (prefers-reduced-motion: reduce) {
  .skeleton::after {
    animation: none;
  }
}

.tooltip {
  position: absolute;
  pointer-events: none;
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-1);
  background: var(--color-bg-elevated);
  border: 1px solid var(--color-border-strong);
  box-shadow: var(--shadow-2);
  font-size: var(--fs-200);
  color: var(--color-text);
  opacity: 0;
  transform: translate(-50%, -100%) translateY(-8px) scale(0.96);
  transition:
    opacity var(--duration-fast) var(--ease-standard),
    transform var(--duration-fast) var(--ease-standard);
  z-index: var(--z-tooltip);
  white-space: nowrap;
}
.tooltip.is-visible {
  opacity: 1;
  transform: translate(-50%, -100%) translateY(-12px) scale(1);
}

.tooltip--wrap {
  white-space: normal;
  width: max-content;
  max-width: 160px;
  padding: var(--space-1) var(--space-2);
  font-size: var(--fs-100);
  line-height: 1.35;

  border-radius: var(--radius-1);
  border-color: var(--color-accent-border);
}

.tooltip--below {
  transform: translate(-50%, 0) translateY(-8px) scale(0.96);
}
.tooltip--below.is-visible {
  transform: translate(-50%, 0) translateY(4px) scale(1);
}

.toast {
  --toast-accent: var(--color-accent);
  --toast-accent-muted: var(--color-accent-muted);
  position: fixed;
  bottom: var(--space-6);
  right: var(--space-6);
  display: flex;
  align-items: center;
  gap: var(--space-3);
  max-width: 380px;
  padding: var(--space-3) var(--space-4);
  border-radius: var(--radius-2);
  background: var(--color-surface);
  border: 1px solid var(--color-border);
  box-shadow: var(--shadow-2);
  color: var(--color-text);
  font-size: var(--fs-200);
  line-height: 1.35;
  z-index: var(--z-toast);
  transform: translateY(12px) scale(0.98);
  opacity: 0;
  pointer-events: none;
  transition:
    transform var(--duration-base) var(--ease-decelerate),
    opacity var(--duration-base) var(--ease-decelerate);
}
.toast.is-visible {
  transform: translateY(0) scale(1);
  opacity: 1;
}
.toast-icon-wrap {
  flex-shrink: 0;
  display: grid;
  place-items: center;
  width: 28px;
  height: 28px;
  border-radius: var(--radius-full);
  background: var(--toast-accent-muted);
}
.toast-icon {
  width: 16px;
  height: 16px;
  fill: none;
  stroke: var(--toast-accent);
  stroke-width: 2px;
  stroke-linecap: round;
  stroke-linejoin: round;
}
.toast--success {
  --toast-accent: var(--color-success);
  --toast-accent-muted: var(--color-success-muted);
}
.toast--error {
  --toast-accent: var(--color-danger);
  --toast-accent-muted: var(--color-danger-muted);
}

.chat-bubble {
  max-width: 70%;
  padding: var(--space-3) var(--space-4);
  border-radius: var(--radius-2);
  font-size: var(--fs-300);
  line-height: 1.4;
}
.chat-bubble--theirs {
  background: var(--color-surface-alt);
  color: var(--color-text);
  border-bottom-left-radius: var(--radius-1);
  align-self: flex-start;
}
.chat-bubble--mine {
  background: var(--color-accent);
  color: var(--color-text-on-accent);
  border-bottom-right-radius: var(--radius-1);
  align-self: flex-end;
}
.chat-bubble-time {
  display: block;
  margin-top: var(--space-1);
  font-size: var(--fs-100);
  opacity: 0.7;
}

.elo-chart {
  position: relative;
  display: flex;
}

.elo-chart svg {
  width: 100%;
  height: 100%;
  overflow: visible;
}
.elo-chart-path {
  fill: none;
  stroke: var(--color-accent);
  stroke-width: 2.5;
  stroke-linecap: round;
  stroke-linejoin: round;
}
.elo-chart-fill {
  opacity: 0.22;
}
.elo-chart-grid-line {
  stroke: var(--color-border);
  stroke-width: 1;
}

.elo-chart-reveal {
  transform-box: fill-box;
  transform-origin: 0 0;
  transform: scaleX(0);
  animation: elo-reveal var(--duration-slow) var(--ease-decelerate) forwards;
}
@keyframes elo-reveal {
  to { transform: scaleX(1); }
}

.elo-chart-dot {
  fill: var(--color-bg-elevated);
  stroke: var(--color-accent);
  stroke-width: 2;
  transform-box: fill-box;
  transform-origin: center;
  transform: scale(var(--dot-cx, 1), var(--dot-cy, 1));
  transition:
    transform var(--duration-fast) var(--ease-standard),
    fill var(--duration-fast) var(--ease-standard);
}
.elo-chart-dot.is-active {
  fill: var(--color-accent);
  transform: scale(var(--dot-cx, 1), var(--dot-cy, 1)) scale(1.3);
}
.elo-chart-dot--latest {
  fill: var(--color-accent);
}

.elo-chart-live-ring {
  fill: none;
  stroke: var(--color-accent);
  stroke-width: 2;
  transform-box: fill-box;
  transform-origin: center;
  animation: elo-live-pulse 2400ms var(--ease-standard) infinite;
}
@keyframes elo-live-pulse {
  0% { transform: scale(var(--dot-cx, 1), var(--dot-cy, 1)); opacity: 0.6; }
  100% { transform: scale(calc(var(--dot-cx, 1) * 2.6), calc(var(--dot-cy, 1) * 2.6)); opacity: 0; }
}

@media (prefers-reduced-motion: reduce) {
  .elo-chart-live-ring {
    animation: none;
    opacity: 0;
  }
}

.elo-chart-crosshair {
  stroke: var(--color-border-strong);
  stroke-width: 1;
  opacity: 0;
  pointer-events: none;
  transition: opacity var(--duration-fast) var(--ease-standard);
}
.elo-chart-crosshair-dot {
  fill: var(--color-accent);
  stroke: var(--color-bg-elevated);
  stroke-width: 2;
  opacity: 0;
  pointer-events: none;
  transform-box: fill-box;
  transform-origin: center;
  transform: scale(var(--dot-cx, 1), var(--dot-cy, 1));
  transition: opacity var(--duration-fast) var(--ease-standard);
}
.elo-chart-crosshair.is-visible,
.elo-chart-crosshair-dot.is-visible {
  opacity: 1;
}
.elo-chart-hit-area {
  cursor: crosshair;
}

.chart-legend {
  display: grid;
  gap: var(--space-2);
}

.chart-legend--breakdown {
  padding-top: var(--space-4);
  margin-top: var(--space-2);
  border-top: 1px solid var(--color-border);
}
.chart-legend-heading {
  font-family: var(--font-display);
  font-size: var(--fs-100);
  font-weight: var(--fw-medium);
  text-transform: uppercase;
  letter-spacing: var(--tracking-wide);
  color: var(--color-text-faint);
  margin-bottom: var(--space-1);
}
.chart-legend-item {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  font-family: var(--font-display);
  font-size: var(--fs-200);
  font-weight: var(--fw-medium);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--color-text-muted);
}
.chart-legend-item strong {
  margin-left: auto;
  font-family: var(--font-display);
  font-size: var(--fs-500);
  font-weight: var(--fw-bold);
  color: var(--color-text);
}
.chart-legend-swatch {
  width: 10px;
  height: 10px;
  border-radius: 50%;
  flex-shrink: 0;
}

.radar-chart-block {
  margin-bottom: var(--space-3);
}

.radar-series-legend {
  display: flex;
  justify-content: center;
  gap: var(--space-4);
  margin-bottom: var(--space-3);
  font-size: var(--fs-100);
  color: var(--color-text-muted);
}
.radar-series-legend-item {
  display: flex;
  align-items: center;
  gap: var(--space-2);
}
.radar-series-legend-swatch {
  width: 16px;
  height: 0;
  border-top: 2px solid;
  flex-shrink: 0;
}
.radar-series-legend-swatch--dashed {
  border-top-style: dashed;
}

.radar-chart {
  width: var(--radar-size, 220px);
  max-width: 100%;
  aspect-ratio: 1 / 1;
  margin-inline: auto;
}
.radar-chart-svg {
  position: relative;
}
.radar-chart-svg svg {
  width: 100%;
  height: 100%;
  overflow: visible;
}

.radar-chart-grid-ring {
  fill: none;
  stroke: var(--color-border);
  stroke-width: 1;
  transform-box: view-box;
  transform-origin: 130px 130px;
}
.radar-chart-spoke {
  stroke: var(--color-border);
  stroke-width: 1;
  transform-box: view-box;
  transform-origin: 130px 130px;
}

.radar-chart-area {
  stroke-width: 2;
  stroke-linejoin: round;
  transform-box: view-box;
  transform-origin: 130px 130px;
  transition: filter var(--duration-fast) var(--ease-standard), stroke-width var(--duration-fast) var(--ease-standard);
}
.radar-chart-area--emphasis {
  fill-opacity: 0.22;
  filter: drop-shadow(0 0 5px var(--radar-series-color, transparent));
}
.radar-chart-area--muted {
  fill-opacity: 0.05;
  stroke-width: 1.5;
  stroke-dasharray: 4 3;
}
.radar-chart-area.is-active {
  stroke-width: 2.5;
}
.radar-chart-area--emphasis.is-active {
  filter: drop-shadow(0 0 6px var(--radar-series-color));
}

.radar-chart-vertex {
  stroke: var(--color-bg-elevated);
  stroke-width: 2;
  transform-box: fill-box;
  transform-origin: center;
}

.radar-chart-tick {
  fill: var(--color-text-faint);
  font-family: var(--font-body);
  font-size: 9px;
  font-weight: var(--fw-medium);
  dominant-baseline: middle;
}

.radar-chart-label {
  fill: var(--color-text);
  font-family: var(--font-display);
  font-size: 11px;
  font-weight: var(--fw-semibold, var(--fw-bold));
  text-transform: uppercase;
  letter-spacing: 0.04em;
  transition: fill var(--duration-fast) var(--ease-standard);
}

.radar-chart-axis {
  cursor: pointer;
  outline: none;
}
.radar-chart-hit {
  fill: transparent;
}
.radar-chart-vertex {
  transition: transform var(--duration-fast) var(--ease-standard);
}
.radar-chart-axis:focus-visible .radar-chart-hit {
  fill: var(--color-accent-muted);
}
.radar-chart-axis.is-hovered .radar-chart-vertex {
  transform: scale(1.7);
}
.radar-chart-axis.is-hovered .radar-chart-label {
  fill: var(--color-text);
}

.radar-chart-tooltip-title {
  display: block;
  margin-bottom: var(--space-1);
}
.radar-chart-tooltip-row {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  color: var(--color-text-muted);
}
.radar-chart-tooltip-row + .radar-chart-tooltip-row {
  margin-top: 2px;
}
.radar-chart-tooltip-row strong {
  color: var(--color-text);
  margin-left: auto;
}
.radar-chart-tooltip-dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  flex-shrink: 0;
}

.radar-chart-grid-ring {
  opacity: 0;
  transform: scale(0);
  animation: radar-grow var(--duration-slow) var(--ease-spring) forwards;
}
.radar-chart-spoke {
  opacity: 0;
  transform: scale(0);
  animation: radar-grow var(--duration-base) var(--ease-spring) forwards;
  animation-delay: 120ms;
}
.radar-chart-area {
  opacity: 0;
  transform: scale(0);
  animation: radar-grow var(--duration-slow) var(--ease-spring) forwards;
  animation-delay: 220ms;
}
.radar-chart-vertex {
  opacity: 0;
  animation: radar-pop var(--duration-base) var(--ease-spring) forwards;
}
.radar-chart-tick {
  opacity: 0;
  animation: radar-fade var(--duration-base) var(--ease-standard) forwards;
}
.radar-chart-label {
  opacity: 0;
  animation: radar-fade var(--duration-base) var(--ease-standard) forwards;
  animation-delay: 380ms;
}

@keyframes radar-fade {
  from { opacity: 0; }
  to { opacity: 1; }
}
@keyframes radar-grow {
  from { opacity: 0; transform: scale(0); }
  to { opacity: 1; transform: scale(1); }
}
@keyframes radar-pop {
  from { opacity: 0; transform: scale(0.4); }
  to { opacity: 1; transform: scale(1); }
}

html.js .reveal {
  opacity: 0;
  transform: translateY(16px);
}

html.js .reveal.is-visible {
  animation: cs-reveal-in var(--duration-slow) var(--ease-decelerate) forwards;
  animation-delay: var(--reveal-delay, 0ms);
}
@keyframes cs-reveal-in {
  from {
    opacity: 0;
    transform: translateY(16px);
  }
  to {
    opacity: 1;
    transform: translateY(0);
  }
}
/* Shared wordmark treatment for every brand mark on the site - the marketing
   header and auth header's .brand (css/styles.css, css/login.css), the
   sidebar's .sidebar-logo, and the phone topbar's .mobile-topbar-brand
   (both css/app.css). Centralized here (components.css loads on every page)
   instead of duplicated per file, since it's one visual treatment, not a
   layout concern - sizing/spacing differences between those contexts stay
   in their own files. Was flat near-white text plus a solid-color accent
   word with a bare, undecorated icon - just looked like a label, not a
   brand mark, next to the rest of the site's gradient/glow language (the
   ambient blue radial-gradient behind the whole page in css/styles.css, the
   uppercase+tracked labels used everywhere from table headers to nav
   groups). This brings the wordmark in line with both. */
.brand-text,
.sidebar-logo-text,
.mobile-topbar-brand span {
  text-transform: uppercase;
  letter-spacing: var(--tracking-wide);
}
.brand-text-accent,
.sidebar-logo-text-accent {
  background: linear-gradient(120deg, var(--color-brand-strike) 0%, var(--color-accent-hover) 100%);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.brand img,
.sidebar-logo img,
.mobile-topbar-brand img {
  filter: drop-shadow(0 0 8px rgba(36, 106, 214, 0.45));
  transition:
    filter var(--duration-base) var(--ease-standard),
    transform var(--duration-base) var(--ease-standard);
}
.brand:hover img,
.brand:focus-visible img,
.sidebar-logo:hover img,
.sidebar-logo:focus-visible img,
.mobile-topbar-brand:hover img,
.mobile-topbar-brand:focus-visible img {
  filter: drop-shadow(0 0 14px rgba(77, 157, 255, 0.7));
  transform: scale(1.06);
}
@media (prefers-reduced-motion: reduce) {
  .brand img,
  .sidebar-logo img,
  .mobile-topbar-brand img {
    transition: none;
  }
}

@media (prefers-reduced-motion: reduce) {
  .reveal {
    opacity: 1;
    transform: none;
    animation: none;
  }
}

/* Currency-rate freshness indicator - the small (i) next to the currency
   picker on the Skins Database (css/csdb.css) and Inventory (css/
   inventory.css) pages. Shared here (not duplicated per page) since both
   render the identical element/behavior, driven by js/util.js's
   describeFxMeta(). Deliberately quiet at rest (faint, low-contrast) so it
   doesn't compete with the currency value itself - only the .is-stale state
   (live rates unreachable, showing a cached/approximate number instead)
   takes on a color worth noticing. The tooltip text (title attribute, set
   in JS) carries the actual "updated Xh ago" detail; this is just the
   at-a-glance signal that something is or isn't fresh. */
.currency-field {
  position: relative;
  display: inline-flex;
  align-items: center;
}
.currency-rates-info {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  margin-left: 0.3rem;
  padding: 0;
  border: none;
  background: none;
  color: var(--color-text-faint);
  border-radius: var(--radius-full);
  cursor: help;
  flex-shrink: 0;
}
.currency-rates-info svg {
  width: 15px;
  height: 15px;
  stroke: currentColor;
  stroke-width: 1.8px;
  fill: none;
}
.currency-rates-info:hover,
.currency-rates-info:focus-visible {
  color: var(--color-text-muted);
}
.currency-rates-info.is-stale {
  color: var(--color-warning);
}
.currency-rates-info.is-stale:hover,
.currency-rates-info.is-stale:focus-visible {
  color: var(--color-warning);
  opacity: 0.8;
}
/* -- Custom select (CSUtil.enhanceSelect) --------------------------------
   Styled replacement for a native <select>'s unthemeable dropdown popup,
   built by CSUtil.enhanceSelect (js/util.js). Shared by the Skins Database
   (css/csdb.css) and the CSGO Exchange (css/exchange.css) so both pages'
   filter dropdowns are identical; the real <select> it mirrors is kept in
   the DOM but visually hidden. */

select.cs-select--visually-hidden {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0, 0, 0, 0);
  white-space: nowrap;
  border: 0;
}

.cs-select {
  position: relative;
  width: 100%;
}

.cs-select-trigger {
  width: 100%;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  background: color-mix(in srgb, var(--color-surface-alt) 60%, transparent);
  border: 1px solid color-mix(in srgb, var(--color-border-strong) 50%, transparent);
  border-radius: var(--radius-1);
  color: var(--color-text);
  padding: 10px 12px;
  font-size: 13px;
  font-family: inherit;
  font-weight: 600;
  cursor: pointer;
  transition: border-color 180ms ease, background 180ms ease;
}

.cs-select-trigger:hover {
  border-color: color-mix(in srgb, var(--color-accent-hover) 32%, transparent);
}

.cs-select-trigger:focus-visible {
  outline: none;
  box-shadow: 0 0 0 2px color-mix(in srgb, var(--color-accent-hover) 15%, transparent);
}

.cs-select-trigger[aria-expanded="true"] {
  background: color-mix(in srgb, var(--color-surface-alt) 85%, transparent);
  border-color: var(--color-accent);
  border-bottom-color: transparent;
  border-radius: var(--radius-1) var(--radius-1) 0 0;
  box-shadow: inset 0 -2px 0 0 var(--color-accent);
}

.cs-select-chevron {
  flex-shrink: 0;
  color: var(--color-accent-hover);
  font-size: 18px;
  transition: transform 180ms ease;
}

.cs-select-trigger[aria-expanded="true"] .cs-select-chevron {
  transform: rotate(180deg);
}

.cs-select-list {
  position: absolute;
  top: 100%;
  left: 0;
  right: 0;
  z-index: var(--z-dropdown);
  background: var(--color-surface-alt);
  border: 1px solid var(--color-accent);
  border-top: none;
  border-radius: 0 0 var(--radius-1) var(--radius-1);
  max-height: 260px;
  overflow-y: auto;
  list-style: none;
  margin: 0;
  padding: 4px;
  box-shadow: 0 16px 32px rgba(0, 0, 0, 0.5);
  animation: cs-select-dropdown-in var(--duration-fast) var(--ease-decelerate);
}
@keyframes cs-select-dropdown-in {
  from { opacity: 0; transform: translateY(-4px); }
  to { opacity: 1; transform: translateY(0); }
}

.cs-select-option {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  min-height: 44px;
  padding: 9px 10px;
  border-radius: var(--radius-1);
  font-size: 13px;
  font-weight: 600;
  color: var(--color-text);
  cursor: pointer;
  box-sizing: border-box;
  transition: background 120ms ease;
}

.cs-select-option:hover {
  background: color-mix(in srgb, var(--color-accent-hover) 12%, transparent);
}

.cs-select-option:focus-visible {
  outline: none;
  box-shadow: inset 0 0 0 2px var(--color-accent);
}

.cs-select-option.is-selected {
  background: color-mix(in srgb, var(--color-accent-hover) 8%, transparent);
  color: var(--color-text);
}

.cs-select-check {
  width: 14px;
  height: 14px;
  fill: none;
  stroke: var(--color-accent);
  stroke-width: 2.5px;
  stroke-linecap: round;
  stroke-linejoin: round;
  opacity: 0;
  flex-shrink: 0;
}

.cs-select-option.is-selected .cs-select-check {
  opacity: 1;
}

.cs-rarity-opt--consumer { color: #a0a7b4; }
.cs-rarity-opt--industrial { color: #5c9dff; }
.cs-rarity-opt--mil-spec { color: #3b82f6; }
.cs-rarity-opt--restricted { color: #8b5cf6; }
.cs-rarity-opt--classified { color: #d946ef; }
.cs-rarity-opt--covert { color: #ef4444; }
.cs-rarity-opt--contraband { color: #f59e0b; }

/* -- Results bar --------------------------------------------------------
   The "Showing 1-50 of 5,806 results" footer under the Skins Database's
   table (views/pages/csdb.ejs) and the CSGO Exchange's grid
   (views/pages/exchange.ejs): a results count on the left, and on the
   right the Currency/Show pickers plus the Prev/Next pager.

   Both pages had their own copy of this (css/csdb.css's .db-pagination/
   .db-per-page/.db-pager-btn and css/exchange.css's .exch-* equivalents),
   written separately and drifted apart - the Exchange's controls had no
   min-height, so its "36" chip sat visibly shorter than the Skins
   Database's identical one; it used --font-display with letter-spacing
   against the other's --font-body; it painted pager text at full
   --color-text rather than --color-text-muted, so "Next" read as much
   louder; and it had lost the :focus-visible and :active states along the
   way. One copy here instead, same reasoning as .cs-select above: these
   two toolbars are the same component, so they should be the same code. */

.cs-resultsbar {
  display: flex;
  justify-content: space-between;
  align-items: center;
  flex-wrap: wrap;
  row-gap: 10px;
  padding: 14px 18px;
  border-top: 1px solid color-mix(in srgb, var(--color-border-strong) 25%, transparent);
  background: color-mix(in srgb, var(--color-bg) 30%, transparent);
  font-size: 12px;
  color: var(--color-text-muted);
  font-weight: 600;
}

.cs-resultsbar-label {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  color: var(--color-text-muted);
  font-weight: 600;
}

/* Small icon-chip prefix, same accent-tinted-box language as the
   dashboard's stat tiles - a bit of visual weight on the one number this
   toolbar exists to report, instead of a bare text label. */
.cs-resultsbar-label::before {
  content: "";
  width: 22px;
  height: 22px;
  border-radius: 6px;
  flex-shrink: 0;
  background: var(--color-accent-muted);
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%236394ff' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Crect x='3' y='3' width='7' height='7' rx='1'/%3E%3Crect x='14' y='3' width='7' height='7' rx='1'/%3E%3Crect x='3' y='14' width='7' height='7' rx='1'/%3E%3Crect x='14' y='14' width='7' height='7' rx='1'/%3E%3C/svg%3E");
  background-repeat: no-repeat;
  background-position: center;
  background-size: 13px 13px;
}

.cs-resultsbar-controls {
  display: flex;
  align-items: center;
  gap: 16px;
}

/* One labelled control - "Currency [ USD $ ]", "Show [ 50 ]". */
.cs-resultsbar-field {
  display: flex;
  align-items: center;
  gap: 8px;
  color: var(--color-text-muted);
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.03em;
}

/* The real <select> is visually hidden once CSUtil.enhanceSelect has run,
   so this only ever shows if js/util.js failed to load - styled anyway so
   that fallback isn't a raw browser widget in the middle of the toolbar. */
.cs-resultsbar-field select {
  background: color-mix(in srgb, var(--color-bg) 55%, transparent);
  border: 1px solid color-mix(in srgb, var(--color-border-strong) 50%, transparent);
  color: var(--color-text);
  padding: 6px 10px;
  border-radius: var(--radius-1);
  font-size: 12px;
  font-weight: 700;
  cursor: pointer;
  font-family: var(--font-display);
}
.cs-resultsbar-field select:focus {
  outline: none;
  border-color: color-mix(in srgb, var(--color-accent-hover) 48%, transparent);
  box-shadow: 0 0 0 2px color-mix(in srgb, var(--color-accent-hover) 10%, transparent);
}

/* .cs-select defaults to width:100%, built for the full-width sidebar
   filter panels - here, in a compact inline toolbar row, that would
   stretch it to fill the row instead of sitting as a chip beside its
   label. */
.cs-resultsbar-field .cs-select {
  width: auto;
}

/* .cs-select-trigger is sized/coloured for those sidebar filters (10px/12px
   padding, 13px text, a surface-alt fill). Dropped into this compact row
   next to Prev/Next, that mismatch in height and tone is what made it look
   bolted-on. Match .cs-pager-btn's box model exactly - same background and
   border tokens, same 44px min-height - so Currency, Show and Prev/Next
   all read as one row of controls. */
.cs-resultsbar-field .cs-select-trigger {
  min-height: 44px;
  box-sizing: border-box;
  padding: 8px 14px;
  background: color-mix(in srgb, var(--color-bg) 55%, transparent);
  font-size: 12.5px;
  font-weight: 700;
  font-family: var(--font-body);
}
.cs-resultsbar-field .cs-select-trigger:hover {
  background: color-mix(in srgb, var(--color-accent-hover) 15%, transparent);
  color: var(--color-accent-hover);
}

/* The shared chevron is a bright, oversized accent arrow - built to stand
   out as the only visual cue in a sidebar's plain-text filter rows. Next
   to Prev/Next's plain labels that reads louder than everything around it;
   keep it quiet until the trigger is actually hovered or open. */
.cs-resultsbar-field .cs-select-chevron {
  color: inherit;
  font-size: 14px;
}
.cs-resultsbar-field .cs-select-trigger[aria-expanded="true"] .cs-select-chevron {
  color: var(--color-accent-hover);
}

/* This toolbar is pinned to the FOOT of the table/grid, so the shared
   drop-down direction (top:100%) opens straight into the bottom edge of
   the viewport - the list gets clipped, or pushes the page taller, exactly
   where there is least room for it. Flipped to open upward, which is
   always the right direction here, with the trigger's open-state seam
   moved to its top edge to match.

   The width overrides are separate from that: .cs-select-list is
   left:0;right:0 by default, an exact stretch to match .cs-select's width,
   which is now narrow (the override above). That squeezed "USD $"/"BRL R$"
   into a box too narrow to fit on one line, wrapping every option into two
   stacked rows. Left-aligned to the trigger but free to grow as wide as
   its longest option needs, capped so it can never push the page
   sideways. */
.cs-resultsbar-field .cs-select-list {
  top: auto;
  bottom: 100%;
  border-top: 1px solid var(--color-accent);
  border-bottom: none;
  border-radius: var(--radius-1) var(--radius-1) 0 0;
  box-shadow: 0 -16px 32px rgba(0, 0, 0, 0.5);
  animation: cs-resultsbar-dropdown-in var(--duration-fast) var(--ease-decelerate);
  right: auto;
  width: max-content;
  min-width: 100%;
  max-width: min(220px, calc(100vw - 40px));
}
@keyframes cs-resultsbar-dropdown-in {
  from { opacity: 0; transform: translateY(4px); }
  to { opacity: 1; transform: translateY(0); }
}
/* Users who've asked for less motion get an opacity-only fade - the 4px
   translate is decorative, not load-bearing (the dropdown lands in exactly
   the same final spot either way). Also covers the base .cs-select-list
   animation (see cs-select-dropdown-in above), which the earlier
   prefers-reduced-motion blocks in this file don't touch. */
@media (prefers-reduced-motion: reduce) {
  .cs-select-list,
  .cs-resultsbar-field .cs-select-list {
    animation: none;
  }
}
.cs-resultsbar-field .cs-select-trigger[aria-expanded="true"] {
  border-radius: 0 0 var(--radius-1) var(--radius-1);
  border-top-color: transparent;
  border-bottom-color: var(--color-accent);
  box-shadow: inset 0 2px 0 0 var(--color-accent);
}

/* Same reasoning as the trigger above: .cs-select-option's 44px min-height
   is a touch target sized for long rarity/collection names. For this short
   list of currency codes and page sizes it just pads every row out with
   empty space, making the popup look oversized next to the small trigger
   that opens it. */
.cs-resultsbar-field .cs-select-option {
  min-height: 0;
  padding: 7px 10px;
  font-size: 12.5px;
}

.cs-pager {
  display: flex;
  gap: 8px;
}

.cs-pager-btn {
  min-height: 44px;
  background: color-mix(in srgb, var(--color-bg) 55%, transparent);
  border: 1px solid color-mix(in srgb, var(--color-border-strong) 50%, transparent);
  color: var(--color-text-muted);
  padding: 8px 14px;
  border-radius: var(--radius-1);
  font-size: 12.5px;
  cursor: pointer;
  font-family: var(--font-body);
  font-weight: 700;
  transition: color 200ms ease, background-color 200ms ease, border-color 200ms ease, box-shadow 200ms ease, transform 200ms ease, opacity 200ms ease;
  box-sizing: border-box;
}
.cs-pager-btn:hover:not(:disabled) {
  background: color-mix(in srgb, var(--color-accent-hover) 15%, transparent);
  border-color: color-mix(in srgb, var(--color-accent-hover) 40%, transparent);
  color: var(--color-accent-hover);
}
.cs-pager-btn:focus-visible {
  outline: none;
  border-color: color-mix(in srgb, var(--color-accent-hover) 50%, transparent);
  box-shadow: 0 0 0 2px color-mix(in srgb, var(--color-accent-hover) 25%, transparent);
}
.cs-pager-btn:active:not(:disabled) {
  background: color-mix(in srgb, var(--color-accent-hover) 25%, transparent);
}
.cs-pager-btn:disabled {
  opacity: 0.4;
  cursor: not-allowed;
}

@media (pointer: coarse) {
  .cs-resultsbar-field select {
    padding-top: 12px;
    padding-bottom: 12px;
  }
  /* Give touch users back a comfortable tap target on the compact rows
     above, without reverting to the oversized 44px sidebar sizing. */
  .cs-resultsbar-field .cs-select-option {
    min-height: 40px;
  }
}

@media (max-width: 560px) {
  .cs-resultsbar-controls {
    flex-wrap: wrap;
    row-gap: 10px;
  }
}
