/* Sidebar */
:root {
  --sidebar-inline-space: max(calc(var(--inline-space) * 1.5), 1vw);
}

.sidebar__container {
  block-size: 100dvh;
  display: flex;
  flex-direction: column;
  max-block-size: 100dvh;
  position: relative;
}

.sidebar__close.sidebar__close {
  display: none;

  #sidebar.open & {
    @media (max-width: 1279.9px) {
      display: flex;
      position: absolute;
      inset-block-start: var(--block-space-half);
      inset-inline-end: var(--sidebar-inline-space);
      z-index: 4;
    }
  }
}

/* Rail (834-1279, closed): icon-only tool column; the room sections wait
   inside the expanded overlay */
@media (min-width: 834px) and (max-width: 1279.9px) {
  #sidebar:not(.open) {
    .sidebar__container {
      overflow: hidden;
    }

    .sidebar__workspace {
      display: none;
    }

    .sidebar__menu {
      /* clear the rail's pinned expand button */
      padding-block-start: calc(var(--block-space-half) + var(--btn-size) + var(--block-space-half));
      padding-inline: 6px;
    }

    .sidebar__menu-item {
      --btn-padding: var(--space-row) 0;

      justify-content: center;

      &.has-unread-activity::after,
      &.has-unread-dms::after {
        inset-block-start: 4px;
        inset-inline-end: 6px;
        transform: none;
      }
    }

    .sidebar__menu-label,
    .sidebar__menu-kbd {
      display: none;
    }

    /* The full room sections wait inside the expanded overlay, but the top of
       the main Rooms list previews here as compact glyph rows so unread rooms
       stay one glance away. Favorites, forums, DMs, section headers and row
       menus all collapse; the rows themselves are reused, so their live unread
       badges keep updating. */
    .rooms {
      gap: 2px;
      padding-inline: 6px;
    }

    /* Only the main Rooms list previews in the rail. Its list now lives inside
       the collapsible #rooms_section, so keep that wrapper and drop its header;
       favorites, forums, DMs and the hidden frame stay culled. */
    .rooms > *:not(#rooms_section) {
      display: none;
    }

    #rooms_section > *:not([data-collapsible-section-target="content"]) {
      display: none;
    }

    .rail-rooms .room-row:nth-child(n+5),
    .rail-rooms .room-row .room-row__menu-btn,
    .rail-rooms .room__name,
    .rail-rooms .muted-indicator {
      display: none;
    }

    .rail-rooms .room {
      --btn-padding: var(--space-row) 0;

      justify-content: center;
      position: relative;
    }

    .rail-rooms .notification-badge {
      position: absolute;
      inset-block-start: 2px;
      inset-inline-end: 4px;
    }

    .sidebar__footer {
      align-items: center;
      flex-direction: column;
      padding-inline: 6px;
    }

    /* The chip collapses to just the avatar in the rail */
    .sidebar__profile {
      flex: initial;
    }

    .sidebar__me { padding: 4px; }

    .sidebar__me-info,
    .sidebar__me-caret {
      display: none;
    }
  }
}

/* Workspace header: identity chip above the tool rows — logo tile, name over
   member counts, quiet settings gear */
.sidebar__workspace {
  align-items: center;
  color: var(--color-text);
  display: flex;
  gap: 10px;
  padding: 13px 14px;

  /* The drawer/overlay close button pins to the same corner — slide the
     gear clear of it while the sidebar is open below the docked breakpoint */
  #sidebar.open & {
    @media (max-width: 1279.9px) {
      padding-inline-end: calc(var(--btn-size) + var(--sidebar-inline-space));
    }
  }
}

.sidebar__workspace-logo {
  block-size: 32px;
  border-radius: 9px;
  display: block;
  flex-shrink: 0;
  inline-size: 32px;
  overflow: hidden;

  & img {
    block-size: 100%;
    display: block;
    inline-size: 100%;
    object-fit: cover;
  }
}

.sidebar__workspace-initial {
  align-items: center;
  background-color: var(--color-accent-brand);
  block-size: 100%;
  color: var(--color-text-reversed);
  display: flex;
  font-size: 0.875rem;
  font-weight: 700;
  justify-content: center;
  text-transform: uppercase;
}

.sidebar__workspace-info {
  display: flex;
  flex: 1;
  flex-direction: column;
  min-inline-size: 0;
}

.sidebar__workspace-name {
  font-size: 0.9375rem;
  font-weight: 700;
  letter-spacing: -0.01em;
  line-height: 1.25;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.sidebar__workspace-sub {
  color: var(--color-text-subtle);
  font-size: 0.71875rem;
  line-height: 1.3;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Tool block: full-width rows above the room sections */
.sidebar__menu {
  display: flex;
  flex-direction: column;
  gap: 2px;
  padding-block: calc(var(--block-space) + env(safe-area-inset-top)) var(--block-space-half);
  padding-inline: calc(var(--sidebar-inline-space) / 2);
}

.sidebar__menu-item {
  --btn-background: transparent;
  --btn-border-color: transparent;
  --btn-border-radius: var(--border-radius-md);
  /* Tool rows sit tighter than room rows (comp: 34px vs 40px) */
  --btn-padding: 7px 1.2ch;
  --hover-color: transparent;
  --hover-filter: none;

  color: var(--color-text-muted);
  display: flex;
  font-size: 0.875rem;
  gap: 1.2ch;
  justify-content: flex-start;
  position: relative;
  transition: background-color 150ms ease-out;

  /* Comp: hover tints the row, the label color holds */
  @media (any-hover: hover) {
    &:hover {
      background-color: var(--color-bg-hover);
    }
  }

  &:focus-visible {
    outline: 2px solid var(--color-accent-brand);
  }

  &.has-unread-activity::after,
  &.has-unread-dms::after {
    --size: 0.6em;

    aspect-ratio: 1;
    background-color: var(--color-accent-brand);
    block-size: var(--size);
    border-radius: calc(var(--size) * 2);
    content: "";
    flex-shrink: 0;
    inline-size: var(--size);
    position: absolute;
    inset-block-start: 50%;
    inset-inline-end: 1.2ch;
    transform: translateY(-50%);
  }
}

.sidebar__menu-label {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Row count riding each section label */
.sidebar__label-count {
  color: var(--color-text-subtle);
  font-size: 0.6875rem;
  font-weight: 600;
  opacity: 0.75;
}

/* Presence on 1:1 DM rows: the roster's connected signal as a corner dot */
.direct__avatar {
  overflow: visible;
  position: relative;
}

.direct__presence {
  border: 2px solid var(--color-bg-sunk);
  block-size: 10px;
  inline-size: 10px;
  inset-block-end: -1px;
  inset-inline-end: -1px;
  position: absolute;
}

/* Shortcut hint on the Search row — only where a keyboard is likely */
.sidebar__menu-kbd {
  border: 1px solid var(--color-border);
  border-radius: 5px;
  color: var(--color-text-subtle);
  display: none;
  font-family: inherit;
  font-size: 0.6875rem;
  margin-inline-start: auto;
  padding: 1px 5px;

  @media (hover: hover) and (pointer: fine) {
    display: inline-block;
  }
}

/* Chrome buttons (section add/menu, drawer close) sit quietly on the
   sidebar surface instead of as solid pills */
.sidebar__container .btn--small,
.sidebar__container .options-btn,
.sidebar__close.sidebar__close {
  --btn-background: transparent;
  --btn-border-color: transparent;
  --hover-color: transparent;
  --hover-filter: none;

  color: var(--color-text-muted);

  @media (any-hover: hover) {
    &:hover {
      background-color: var(--color-bg-hover);
      color: var(--color-text);
    }
  }
}

/* Section labels */
.sidebar__label {
  color: var(--color-text-subtle);
  font-size: 0.6875rem;
  letter-spacing: 0.07em;
}

/* Fixed 20px glyph column so #, lock, and forum glyphs all align the names
   at the same x (comp) */
.room__glyph {
  color: var(--color-text-subtle);
  display: inline-flex;
  inline-size: 20px;
  justify-content: center;
  margin-inline-end: 11px;
}

/* Footer: the signed-in user chip is the one trigger for the profile flyout. */
.sidebar__footer {
  align-items: center;
  background-color: var(--color-bg-sunk);
  border-block-start: 1px solid var(--color-border-dark);
  display: flex;
  inset-block-end: 0;
  margin-block-start: auto;
  padding-block: 8px calc(8px + env(safe-area-inset-bottom));
  padding-inline: calc(var(--sidebar-inline-space) / 2);
  position: sticky;
  z-index: 2;
}

.sidebar__profile {
  flex: 1;
  min-inline-size: 0;
}

.sidebar__me {
  align-items: center;
  border-radius: var(--border-radius-md);
  color: var(--color-text);
  cursor: pointer;
  display: flex;
  gap: 10px;
  inline-size: 100%;
  min-inline-size: 0;
  padding: 4px 6px;
  text-align: start;

  &[aria-expanded="true"] {
    background-color: var(--color-bg-hover);
  }

  &:focus-visible {
    outline: 2px solid var(--color-accent-brand);
    outline-offset: 2px;
  }

  @media (any-hover: hover) {
    &:hover {
      background-color: var(--color-bg-hover);
    }
  }
}

.sidebar__me-avatar {
  flex-shrink: 0;
  position: relative;
}

.sidebar__me-dot {
  block-size: 10px;
  border: 2px solid var(--color-bg-sunk);
  inline-size: 10px;
  inset-block-end: -2px;
  inset-inline-end: -2px;
  position: absolute;
  z-index: 1;
}

.sidebar__me-info {
  display: flex;
  flex-direction: column;
  flex: 1;
  min-inline-size: 0;
}

.sidebar__me-name {
  font-size: 0.84375rem;
  font-weight: 600;
  line-height: 1.25;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.sidebar__me-status {
  color: var(--color-text-subtle);
  font-size: 0.71875rem;
  line-height: 1.3;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.sidebar__me-caret {
  color: var(--color-text-subtle);
  display: flex;
  flex-shrink: 0;
  transform: rotate(180deg);

  & svg {
    block-size: 12px;
    inline-size: 12px;
  }
}

.sidebar__workspace-action {
  --btn-background: transparent;
  --btn-border-color: transparent;
  --btn-padding: 0.35em;
  --btn-size: 32px;
  --hover-color: transparent;
  --hover-filter: none;
  --icon-size: 18px;

  color: var(--color-text-muted);

  @media (any-hover: hover) {
    &:hover {
      background-color: var(--color-bg-hover);
      color: var(--color-text);
    }
  }
}


.sidebar__toggle {
  /* Vertically centered on the header bar it floats over */
  inset-block-start: calc((var(--navbar-height) - var(--btn-size)) / 2);
  inset-inline-end: calc(
    (var(--btn-size) + max(var(--inline-space), 1vw)) * -1
  );
  position: absolute;
  transition:
    inset-inline-end 300ms cubic-bezier(0.25, 1, 0.5, 1),
    border-color 300ms cubic-bezier(0.25, 1, 0.5, 1),
    background-color 300ms cubic-bezier(0.25, 1, 0.5, 1);
  z-index: 5;

  #sidebar:where(
      :not(.open):has(
        #sidebar_inbox [data-type="list_node"]:not([hidden]),
        #starred_rooms [data-type="list_node"]:not([hidden]) .unread,
        .direct.unread
      )
    )
    & {
    &::after {
      --size: 1em;

      aspect-ratio: 1;
      background-color: var(--color-text);
      block-size: var(--size);
      border-radius: calc(var(--size) * 2);
      content: "";
      flex-shrink: 0;
      inline-size: var(--size);
      inset-block-start: calc(var(--size) / -4);
      inset-inline-end: calc(var(--size) / -4);
      position: absolute;
    }
  }

  #sidebar:where(:not(.open):has(.badge, .direct.unread)) & {
    &::after {
      background-color: var(--color-negative);
    }
  }

  /* Drawer breakpoint: the toggle floats out over the light content header,
     not the dark rail (an open drawer hides it — the close X takes over). It
     lives inside #sidebar[data-contrast], whose scope repaints --color-text
     white; over the header that's an invisible glyph and dot on a white circle.
     Rebind --color-text to the page's own ink (theme-aware, and read by both the
     icon's currentColor and the unread ::after) and drop the button chrome so it
     reads as a borderless header glyph. */
  @media (max-width: 833.9px) {
    --btn-background: transparent;
    --btn-border-color: transparent;
    --color-text: oklch(var(--lch-ink));
    /* Same page-surface rebind for the hover pill, so it matches the rail's
       hover treatment below rather than the default glyph-darken. */
    --color-bg-hover: oklch(var(--lch-hover));

    @media (any-hover: hover) {
      &:hover {
        background-color: var(--color-bg-hover);
      }
    }
  }

  @media (min-width: 834px) and (max-width: 1279.9px) {
    --btn-background: transparent;
    --btn-border-color: transparent;
    --hover-color: transparent;
    --hover-filter: none;

    color: var(--color-text-muted);
    display: flex;
    inset-block-start: var(--block-space-half);
    inset-inline: 0;
    margin-inline: auto;
    position: absolute;

    @media (any-hover: hover) {
      &:hover {
        background-color: var(--color-bg-hover);
        color: var(--color-text);
      }
    }
  }

  @media (min-width: 1280px) {
    display: none;
    inset-block-start: var(--block-space);
  }

  .open & {
    inset-block-start: var(--block-space);

    @media (max-width: 1279.9px) {
      display: none;
      inset-inline-end: var(--sidebar-inline-space);

      & img {
        filter: invert(0);
      }

      @media (prefers-color-scheme: dark) {
        & img {
          filter: invert(100%);
        }
      }

      :root[data-theme="light"] & img {
        filter: invert(0);
      }

      :root[data-theme="dark"] & img {
        filter: invert(100%);
      }
    }
  }
}

/* Direct messages */
.directs {
  --column-gap: calc(var(--inline-space) / 1.5);

  display: flex;
  flex-direction: column;
  gap: 2px;
}

.directs--edit {
  display: grid;
  gap: var(--inline-space);
  grid-template-columns: repeat(auto-fit, minmax(140px, 1fr));
  grid-template-rows: min-content;
  place-items: center;

  .member {
    aspect-ratio: 1;
    block-size: auto;
    inline-size: 100%;
    max-inline-size: 200px;
    margin-inline: auto;
    place-content: center;
  }
}

.direct {
  --avatar-size: 1.75em;

  align-items: center;
  border-radius: var(--border-radius-md);
  color: var(--color-text-muted);
  display: flex;
  gap: 1ch;
  padding: var(--space-row) 1.2ch;
  position: relative;
  text-decoration: none;
  transition: background-color 150ms ease-out;

  /* The group stack is authored entirely in ch — box, tiles, and overlap
     offsets alike — so scaling its font-size shrinks the whole stack uniformly
     to sit inside the single-avatar footprint instead of overpowering it. */
  .avatar__group {
    font-size: 0.7em;
  }

  .avatar .avatar__group {
    .avatar {
      margin-inline: 0;
    }
  }

  /* Two overlapping tiles for a group DM; the upper tile is ringed in the
     sidebar ground so it reads as a separate avatar over the one behind it. */
  .avatar__group > :last-child .avatar {
    box-shadow: 0 0 0 2px var(--color-bg-sunk);
  }

  @media (any-hover: hover) {
    &:where(:not(:active):hover) {
      background-color: var(--color-bg-hover);
      color: var(--color-text);
    }
  }

  &:focus-visible {
    outline: 2px solid var(--color-accent-brand);
    outline-offset: 2px;
  }

  &.unread {
    color: var(--color-text);

    &::after {
      --size: 0.6em;

      aspect-ratio: 1;
      background-color: var(--color-accent-brand);
      block-size: var(--size);
      border-radius: calc(var(--size) * 2);
      content: "";
      flex-shrink: 0;
      inline-size: var(--size);
      margin-inline-start: auto;
    }
  }

  /* DM rows reuse the room-row unread badge; it replaces the plain dot */
  .notification-badge {
    background-color: var(--color-accent-brand);
    border-radius: 9px;
    color: var(--color-text-reversed);
    flex-shrink: 0;
    font-size: 0.6875rem;
    font-variant-numeric: tabular-nums;
    font-weight: 700;
    line-height: 1.4;
    margin-inline-start: auto;
    min-inline-size: 1.3em;
    padding: 1px 7px;
    text-align: center;
    animation: badge-in 200ms cubic-bezier(0.25, 1, 0.5, 1) both;
  }

  &.badge.unread::after {
    display: none;
  }
}

.direct__author {
  --column-gap: 0.3ch;

  .unread & {
    font-weight: 700;
  }
}

/* Rooms */
.rooms {
  --column-gap: 0.5em;
  --row-gap: 0.5em;

  /* Comp: a hairline separates the tool block from the room sections */
  border-block-start: 1px solid var(--color-border-dark);
  padding-top: var(--block-space-half);
  padding-bottom: var(--block-space-half);
  padding-inline: 8px;

  input {
    margin-bottom: var(--block-space);
    font-size: var(--font-size-small);
  }

  /* Rows stack flush — the 9px row padding is the breathing room (comp) */
  .rooms-list {
    padding-bottom: var(--block-space);
  }
}

.rooms__new-btn {
  position: relative;
  z-index: 4;
  border-radius: 0.5em;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  margin-top: 0;
  margin-bottom: calc(var(--block-space) * 2);
}

#favorites_section:not(:has(.room-row)) {
  display: none;
}

.favorites-toggle {
  all: unset;
  cursor: pointer;
  display: flex;
  align-items: center;
  gap: 0.35em;
  width: 100%;
}

/* Rooms and Direct messages carry header actions (⋯, ＋) beside the label, so
   their collapse toggle sizes to its content rather than filling the row. */
.sidebar__section-toggle {
  all: unset;
  cursor: pointer;
  display: flex;
  align-items: center;
  gap: 0.35em;
}

.favorites-toggle__icon {
  display: flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
  transition: transform 150ms cubic-bezier(0.25, 1, 0.5, 1);

  .icon {
    --icon-size: 0.55em;
    opacity: 0.5;
  }

  /* Non-collapsible sections (Forums) render this box empty to hold the caret
     column open so their label aligns with the collapsible headers. */
  &:empty {
    inline-size: 0.55em;
  }
}

.room-row {
  width: 100%;
  align-items: center;
  border-radius: 8px;
  min-block-size: 32px;
  transition: background-color 150ms ease-out;

  /* The whole row — star included — is one hover/current unit (comp) */
  @media (any-hover: hover) {
    &:hover {
      background-color: var(--color-bg-hover);
    }
  }

  &:has(.room[aria-current="page"]) {
    background-color: var(--color-selected);
  }

  /* The ⋯ trigger reveals on row hover/focus and stays while its menu is
     open; right-clicking the row opens the same menu (popover_controller). */
  .room-row__menu-btn {
    --btn-padding: 4px;

    border: 0;
    background: transparent;
    flex-shrink: 0;
    line-height: 1;
    margin-inline-end: 2px;

    @media (any-hover: hover) and (pointer: fine) {
      opacity: 0;
      transition: opacity 0.15s ease;
    }
  }

  &:hover .room-row__menu-btn,
  &:focus-within .room-row__menu-btn,
  .room-row__menu-btn[aria-expanded="true"] {
    opacity: 1;
  }

  .btn.everything,
  .btn.mentions,
  .btn.nothing,
  .btn.invisible {
    border: 0;
    padding: 0;
    background: transparent;
    flex-shrink: 0;
  }
}

.room {
  --btn-background: transparent;
  --btn-border-color: transparent;
  --btn-border-radius: 8px;
  --btn-padding: var(--space-row) 1.2ch;
  --hover-color: transparent;
  --hover-filter: none;

  color: var(--color-text-muted);
  font-size: 0.875rem;
  font-weight: normal;
  justify-content: start;
  max-inline-size: 100%;
  transition: background-color 150ms ease-out;

  &[aria-current="page"] {
    color: var(--color-accent-brand);
    font-weight: 600;
  }

  /* Unread count rides the accent, not red — red stays destructive-only */
  .notification-badge {
    margin-left: auto;
    flex-shrink: 0;
    background-color: var(--color-accent-brand);
    color: var(--color-text-reversed);
    font-size: 0.6875rem;
    font-variant-numeric: tabular-nums;
    font-weight: 700;
    line-height: 1.4;
    min-width: 1.3em;
    padding: 1px 7px;
    border-radius: 9px;
    text-align: center;
    animation: badge-in 200ms cubic-bezier(0.25, 1, 0.5, 1) both;
  }

  .muted-indicator {
    margin-left: auto;
    flex-shrink: 0;
    opacity: 0.3;
  }

  &.unread {
    color: var(--color-text);
    font-weight: 600;
  }

  &:active:not(:disabled) {
    background-color: var(--color-bg-hover);
    transform: none;
    transition: none;
  }

  time {
    opacity: 0.4;
    font-weight: 400;

    .sidebar__list:not(#shared_rooms) .room.unread &,
    .sidebar__list .room.unread.badge & {
      opacity: 1;
      font-weight: 700;
    }

    .sidebar__list .room.unread.badge & {
      padding-inline-start: calc(var(--inline-space) * 4 / 3);

      &::after {
        --size: 0.5em;

        aspect-ratio: 1;
        background-color: var(--color-negative);
        block-size: var(--size);
        border-radius: calc(var(--size) * 2);
        content: "";
        flex-shrink: 0;
        inline-size: var(--size);
        position: absolute;
        left: 0;
        top: 50%;
        transform: translateY(-50%);
      }
    }
  }
}

.room--current {
  --btn-border-radius: 0.5em;
  --hover-filter: none;
  --num-buttons: 1;

  cursor: pointer;
  min-block-size: var(--btn-size);

  .room__contents {
    .account-has-logo & {
      --num-buttons: 2;
    }

    max-inline-size: calc(
      100dvw - (var(--btn-size) * var(--num-buttons)) -
        (var(--btn-size) + max(var(--inline-space), 1vw)) -
        ((var(--inline-space) + 1.8em) * 2) - var(--sidebar-width) -
        var(--inline-space) * var(--num-buttons) - 1.2em
    );

    @media (max-width: 1024px) {
      --num-buttons: 2;

      .account-has-logo & {
        --num-buttons: 3;
      }
    }
  }
}

/* Searches */
.searches {
  #nav {
    align-items: start;
    column-gap: 0;
    padding-inline-end: 0;
  }

  .rooms {
    padding-block-start: var(--block-space);
  }

  .message--formatted .message__room {
    visibility: visible;
    display: inline-block;
  }
}

.searches__recents {
  --mask: linear-gradient(
    to left,
    oklch(0% 0 0 / 1) 97%,
    oklch(0% 0 0 / 0) 99%
  );

  -webkit-mask-image: var(--mask);
  display: none;
  mask-image: var(--mask);
  position: relative;

  @media (max-width: 1024px) {
    display: flex;
  }

  .room {
    max-inline-size: 20ch;

    &:first-child {
      margin-inline-start: var(--inline-space);
    }
  }

  .searches__btn {
    margin-inline-end: var(--inline-space-double);
  }
}

.searches__query {
  --btn-border-radius: 0.5em;

  min-block-size: var(--btn-size);
}

.searches__results {
  padding-block-start: var(--block-space);
}

/* Results page: the input rides at the top of the column (the palette is the
   entry point; this refines) and the results scroll beneath it. */
.searches__bar {
  padding: 12px var(--inline-space) 10px;
}

body.searches #main-content {
  justify-content: flex-start;
  overflow: hidden;
}

body.searches .searches__results {
  flex: 1 1 auto;
  min-block-size: 0;
  overflow-y: auto;
}

/* The generic empty state forces a 100vh flex column for the DM compose
   layout; under the top-mounted bar it should just fill the leftover column. */
body.searches .message-area:not(:has(.message)):not(:has(.dm-conversation)):not(:has(.thread-card)) {
  block-size: auto;
  flex: 1;
  min-block-size: 0;
}

.searches__input:required:invalid {
  ~ .searches__reset {
    display: none;
    visibility: hidden;
  }
}

#sidebar {
  &:has([open]) {
    [open] .options-btn {
      opacity: 1;
    }

    [open] .popup-menu {
      display: block;
    }
  }

  .options-btn {
    aspect-ratio: 1;
    block-size: 20px;
    border-radius: var(--border-radius-sm);
    inline-size: 20px;
    padding: 0;
  }

  .actions-menu {
    --arrow-size: 1.5em;
    --btn-size: 2em;

    inset: var(--btn-size) auto auto 50%;
    transform: translateX(-50%);
    transform-origin: top left;
    z-index: 100;
  }

  .actions-menu .action-btn {
    font-size: var(--font-size-small);
    --width: 100%;
    --btn-padding: calc(var(--inline-space) * 2 / 3) var(--inline-space);
    --btn-border-radius: calc(var(--arrow-size) / 2 - var(--inline-space-half));
    --busy-inset: calc(var(--inline-space) * 1.5);

    white-space: nowrap;
    justify-content: start;
    font-weight: 400;
  }
}

/* Contrast treatment — a scope, not a theme: rebinds the semantic tokens
   inside the sidebar only, so it reads dark in both light and dark modes.
   Dormant until the shell sets data-contrast on #sidebar. */
#sidebar[data-contrast="true"] {
  --color-bg: oklch(21% 0.010 277);
  --color-bg-raised: oklch(24% 0.012 271);
  --color-bg-sunk: oklch(21% 0.010 277);
  --color-bg-hover: oklch(26.5% 0.013 273);
  --color-text: oklch(100% 0 0);
  --color-text-lighter: oklch(92.7% 0.009 265);
  --color-text-muted: oklch(73% 0.017 263);
  --color-text-subtle: oklch(57.2% 0.020 264);
  --color-border-dark: oklch(28.2% 0.013 273);
  --color-selected: oklch(100% 0 0 / 0.10);
  /* The workspace accent, lifted for the dark ground (colors.css sets the
     per-accent lift on :root). */
  --color-accent-brand: oklch(var(--lch-accent-lift));
}

/* Scrollbar: the global rule (base.css) sets `scrollbar-color` explicitly on
   every element via `*`, so a value only inherited from the sidebar root loses
   the cascade on the real scroll container (.sidebar__container). Target the
   scope's descendants directly to beat `*` — a hue-neutral translucent white
   that recedes into the dark rail in both modes. Width stays thin (inherited). */
#sidebar[data-contrast="true"] * {
  scrollbar-color: oklch(100% 0 0 / 0.20) transparent;
}

/* Anchored popovers (row ⋯ menu, profile flyout) render in the top layer but
   inherit custom properties from their DOM home inside the contrast sidebar,
   which would paint them dark. They are page-surface menus, so rebind the
   tokens the contrast scope overrode back to the theme primitives — white in
   light mode, converging with the sidebar again in dark. */
#sidebar[data-contrast="true"] .anchored-popover {
  --color-bg: oklch(var(--lch-white));
  --color-bg-raised: oklch(var(--lch-raise));
  --color-bg-sunk: oklch(var(--lch-sunk));
  --color-bg-hover: oklch(var(--lch-hover));
  --color-text: oklch(var(--lch-ink));
  --color-text-lighter: oklch(var(--lch-ink-1));
  --color-text-muted: oklch(var(--lch-ink-2));
  --color-text-subtle: oklch(var(--lch-ink-3));
  --color-border: oklch(var(--lch-line-2));
  --color-border-dark: oklch(var(--lch-line));
  --color-selected: oklch(var(--lch-accent-bg));
  --color-accent-brand: oklch(var(--lch-accent));
}

/* Cold-start skeleton for the lazy sidebar frame (users/sidebars/_skeleton).
   Theme-agnostic bars (text colour at low alpha reads on light or dark ground);
   a gentle pulse, disabled under reduced-motion. */
.sidebar-skeleton {
  display: flex;
  flex-direction: column;
  gap: 4px;
  padding-block: 8px;
  padding-inline: var(--sidebar-inline-space);
}

.sidebar-skeleton__row {
  align-items: center;
  display: flex;
  gap: 10px;
  padding-block: 7px;
}

.sidebar-skeleton__glyph,
.sidebar-skeleton__bar {
  animation: skeleton-pulse 1.4s ease-in-out infinite;
  background: color-mix(in oklch, var(--color-text) 14%, transparent);
  border-radius: 6px;
}

.sidebar-skeleton__glyph {
  block-size: 20px;
  flex-shrink: 0;
  inline-size: 20px;
}

.sidebar-skeleton__bar {
  block-size: 12px;
  inline-size: 60%;
}

.sidebar-skeleton__row:nth-child(2) .sidebar-skeleton__bar { inline-size: 44%; }
.sidebar-skeleton__row:nth-child(3) .sidebar-skeleton__bar { inline-size: 68%; }
.sidebar-skeleton__row:nth-child(4) .sidebar-skeleton__bar { inline-size: 38%; }

@keyframes skeleton-pulse {
  0%, 100% { opacity: 0.5; }
  50% { opacity: 1; }
}

@media (prefers-reduced-motion: reduce) {
  .sidebar-skeleton__glyph,
  .sidebar-skeleton__bar {
    animation: none;
  }
}
