/* chat/03_list_and_empty.css
 * ------------------------------------------------------------
 * Split 3 of 10 from web/account/css/chat.css (CLAUDE.md §8.16 — see
 * 01_tokens_reset.css's header for the split's background; loaded third
 * in chat.html, right after the shell/top-bar file).
 *
 * Covers: the conversation list screen (list_view.js, list_row.js —
 * search bar, section headings, list rows, unread styling, the unread
 * badge) and the empty/loading/error states (empty_state.js — including
 * the skeleton shimmer rows shown while a list is still loading).
 * ------------------------------------------------------------ */

/* ===== List screen (list_view.js, list_row.js, empty_state.js) ===== */

.chat-list-view {
  height: 100%;
  display: flex;
  flex-direction: column;
}

.chat-list-view__search-bar { flex: 0 0 auto; padding: 8px 14px; }

.chat-list-view__search {
  width: 100%;
  border-radius: 20px;
  padding: 9px 16px;
  background: var(--chat-composer-field);
  font-size: 14.5px;
}
.chat-list-view__search::placeholder { color: var(--chat-bubble-muted); }

.chat-list-view__content {
  /* THE scroll region for this screen — see the file header. */
  flex: 1 1 auto;
  min-height: 0;
  overflow-y: auto;
}
/* The keyed-list container list_view.js binds createKeyedList to
   (rows + the contacts heading, in document order) — a plain block is
   correct, the rows themselves carry their own padding/layout. */
.chat-list-view__list { display: block; }

.chat-list-heading {
  padding: 16px 16px 6px;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--chat-bubble-muted);
}

.chat-list-row {
  display: flex;
  width: 100%;
  align-items: center;
  gap: 12px;
  padding: 10px 14px;
  text-align: left;
}
.chat-list-row:hover { background: var(--chat-wash-soft); }

.chat-list-row__avatar { flex-shrink: 0; }

.chat-list-row__body {
  flex: 1 1 auto;
  min-width: 0;
  display: flex;
  flex-direction: column;
  gap: 3px;
}

.chat-list-row__top,
.chat-list-row__bottom {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 8px;
}

.chat-list-row__name {
  font-size: 15px;
  font-weight: 600;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
/* An unread row's name/preview brighten from the muted resting state to
   the surface's full-strength text colour — the same visual promotion
   WhatsApp uses, and legible without relying on the badge colour alone
   (kravspec §12.5's colour-is-not-the-only-signal point). */
.chat-list-row.is-unread .chat-list-row__name { font-weight: 800; }

.chat-list-row__time {
  flex-shrink: 0;
  font-size: 12px;
  color: var(--chat-bubble-muted);
}

.chat-list-row__preview {
  flex: 1 1 auto;
  min-width: 0;
  font-size: 13.5px;
  color: var(--chat-bubble-muted);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.chat-list-row.is-unread .chat-list-row__preview { color: var(--chat-bubble-text); }

/* badgeEl uses the native `hidden` attribute (list_row.js), not a class —
   `display` must therefore only ever be set on the `:not([hidden])`
   compound, or this rule's specificity would beat the UA stylesheet's
   `[hidden]{display:none}` and the badge would never actually hide. */
.chat-list-row__badge {
  min-width: 20px;
  height: 20px;
  padding: 0 6px;
  border-radius: 10px;
  background: var(--green);
  color: var(--chat-bubble-text);
  font-size: 11px;
  font-weight: 700;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
}
.chat-list-row__badge:not([hidden]) { display: inline-flex; }

/* ===== Empty / loading / error states (empty_state.js) ===== */

.chat-empty-state {
  height: 100%;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  text-align: center;
  gap: 8px;
  padding: 60px 28px;
  color: var(--chat-bubble-muted);
}

.chat-empty-state__title { font-size: 15px; font-weight: 700; color: var(--chat-bubble-text); }
/* An error state's title picks up the surface's one error colour, so
   "something went wrong" reads as a warning at a glance and not as an
   ordinary empty list. */
.chat-empty-state--error .chat-empty-state__title { color: var(--error); }
.chat-empty-state__body { font-size: 13.5px; max-width: 260px; }

.chat-empty-state__action {
  margin-top: 6px;
  padding: 10px 20px;
  border-radius: 20px;
  background: var(--chat-outgoing-bubble);
  color: var(--chat-bubble-text);
  font-weight: 700;
  font-size: 13.5px;
}
.chat-empty-state__action:hover { filter: brightness(1.1); }

/* The skeleton is `aria-hidden` (empty_state.js) — purely decorative, so
   it is safe for the shimmer to be a plain visual effect with nothing for
   assistive tech to skip past. */
.chat-empty-state__skeleton { padding: 4px 14px; }

.chat-empty-state__skeleton-row {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 10px 0;
}

.chat-empty-state__skeleton-avatar {
  flex-shrink: 0;
  width: 44px; height: 44px;
  border-radius: 50%;
  background: var(--chat-wash-medium);
  animation: chat-shimmer 1.4s ease-in-out infinite;
}

.chat-empty-state__skeleton-lines {
  flex: 1 1 auto;
  display: flex;
  flex-direction: column;
  gap: 8px;
}

.chat-empty-state__skeleton-line {
  height: 10px;
  width: 40%;
  border-radius: 5px;
  background: var(--chat-wash-medium);
  animation: chat-shimmer 1.4s ease-in-out infinite;
}
.chat-empty-state__skeleton-line--wide { width: 75%; }

@keyframes chat-shimmer {
  0%, 100% { opacity: .5; }
  50% { opacity: 1; }
}

