@use '../tokens' as t;

// Overflow is contained here, never on <body>.
.scroller {
  @include t.custom-scrollbar;
  max-inline-size: 100%;
  overflow-x: auto;
  border: 1px solid t.role('line');
  border-radius: t.radius(lg);
  background: t.role('surface');

  &:focus-visible {
    outline: t.stroke(thick) solid t.role('accent');
    outline-offset: calc(-1 * #{t.stroke(thick)});
  }
}

.table {
  inline-size: 100%;
  border-collapse: separate;
  border-spacing: 0;
  font-size: t.text(sm);
  // Cells decide their own width; the scroller handles the excess.
  white-space: nowrap;

  :global(th),
  :global(td) {
    @include t.padding-inline(t.space(4));
    // Logical alignment, so numbers stay trailing in both directions.
    text-align: start;
    border-block-end: 1px solid t.role('line');
    vertical-align: middle;
  }

  :global(th) {
    color: t.role('fg-strong');
    font-weight: t.weight(semibold);
    background: t.role('bg-soft');
  }

  :global(tbody tr:last-child td) {
    border-block-end: 0;
  }
}

.caption {
  @include t.padding-inline(t.space(4));
  padding-block: t.space(3);
  color: t.role('fg-muted');
  font-size: t.text(xs);
  text-align: start;
  caption-side: top;
}

.srOnly {
  @include t.visually-hidden;
}

.density-comfortable :global(th),
.density-comfortable :global(td) {
  padding-block: t.space(3);
}

.density-compact :global(th),
.density-compact :global(td) {
  padding-block: t.space(1);
}

.sticky :global(thead th) {
  position: sticky;
  inset-block-start: 0;
  z-index: t.z(sticky);
}

.striped :global(tbody tr:nth-child(even) td) {
  background: t.role('bg-soft', 0.6);
}

// The first column stays at the inline start while the scroller moves the rest. A sticky cell
// needs an opaque background or the scrolled cells show through it; the edge line is a border,
// not an inset shadow, because a border is logical and mirrors under RTL by itself.
.table[data-sticky-first] :global(:is(th, td):first-child) {
  position: sticky;
  inset-inline-start: 0;
  z-index: t.z(raised);
  background-color: t.role('surface');
  border-inline-end: 1px solid t.role('line');
}

.table[data-sticky-first] :global(th:first-child) {
  background-color: t.role('bg-soft');
}

// The corner cell is sticky on both axes, so it must sit above both the header row and the column.
.sticky[data-sticky-first] :global(thead th:first-child) {
  z-index: t.z(sticky);
}

.sticky[data-sticky-first] :global(thead th:not(:first-child)) {
  z-index: t.z(raised);
}

// A striped row keeps its stripe on the pinned cell: the translucent stripe laid over the opaque
// surface, so the stripe shows and the scrolled cells still do not.
.striped[data-sticky-first] :global(tbody tr:nth-child(even) td:first-child) {
  background: linear-gradient(t.role('bg-soft', 0.6), t.role('bg-soft', 0.6)), t.role('surface');
}
