/* ═══════════════════════════════════════════════════════════════════════════
   ECO-MAX-VI · 2026-09-08 · Визуал-агент VI — состояния/a11y боевого MAX
   Зона: единая система пустых состояний (иконка + заголовок + подсказка +
   действие), скелетоны загрузки в каноне (shimmer), оффлайн-баннер
   «Нет соединения — переподключаемся…», a11y-слой (focus-visible кольца,
   контраст). Презентационный слой: API/БД/?v=-логика не тронуты.
   Канон: #f6f8fc/#ffffff/#0f172a/#516180/#1a56db; тёмная
   #0b1220/#111c2e/#edf3ff/#6b96ff; Onest. Соседи: va–vj не тронуты.
   ═══════════════════════════════════════════════════════════════════════════ */

/* ---------- 0. Локальные токены VI ---------- */

:root {
  --vi-skel-base: var(--surface-2);
  --vi-skel-hi: color-mix(in srgb, var(--surface-2) 55%, var(--surface));
  --vi-ico-bg: var(--brand-soft);
  --vi-ico-fg: var(--accent);
  --vi-banner-bg: rgba(255, 255, 255, 0.96);
  --vi-banner-ink: var(--text);
  --vi-banner-line: var(--border);
  --vi-focus: var(--accent);
}

html[data-theme="dark"] {
  --vi-banner-bg: rgba(17, 28, 46, 0.97);
  --vi-banner-ink: var(--text);
  --vi-banner-line: #223049;
  --vi-focus: #6b96ff;
}

/* ---------- 1. Единая система пустых состояний ---------- */
/* Иконка-медальон + заголовок + подсказка + действие. Один ритм на всех
   экранах: чаты, лента, звонки, клипы, настройки, поиск, пустой тред. */

.vi-empty {
  margin: auto;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  text-align: center;
  gap: 6px;
  padding: 36px 24px;
  max-width: 340px;
  animation: vi-fade-in 0.32s ease-out both;
}

.vi-empty[hidden] {
  display: none !important;
}

.vi-empty__ico {
  width: 64px;
  height: 64px;
  border-radius: 20px;
  display: grid;
  place-items: center;
  background: var(--vi-ico-bg);
  color: var(--vi-ico-fg);
  margin-bottom: 10px;
}

.vi-empty__ico svg {
  width: 28px;
  height: 28px;
  display: block;
}

.vi-empty__title {
  font-size: 15px;
  font-weight: 600;
  letter-spacing: -0.01em;
  color: var(--text);
}

.vi-empty__hint {
  font-size: 13px;
  line-height: 1.5;
  color: var(--text-muted);
  max-width: 270px;
}

.vi-empty__actions {
  display: flex;
  gap: 8px;
  margin-top: 14px;
  flex-wrap: wrap;
  justify-content: center;
}

.vi-empty__btn {
  height: 38px;
  padding: 0 18px;
  border-radius: 12px;
  border: 0;
  background: var(--accent);
  color: #fff;
  font: inherit;
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  transition: transform 0.16s ease, filter 0.16s ease;
}

.vi-empty__btn:hover {
  filter: brightness(1.07);
}

.vi-empty__btn:active {
  transform: scale(0.97);
}

html[data-theme="dark"] .vi-empty__btn {
  background: var(--accent);
  color: #0b1220;
}

.vi-empty__btn--ghost {
  background: var(--accent-soft);
  color: var(--accent);
}

html[data-theme="dark"] .vi-empty__btn--ghost {
  color: var(--accent);
}

/* Вариант без действия и компактный (внутри панелей) */
.vi-empty--bare {
  padding: 28px 18px;
}

.vi-empty--bare .vi-empty__ico {
  width: 56px;
  height: 56px;
  border-radius: 18px;
}

@keyframes vi-fade-in {
  from {
    opacity: 0;
    transform: translateY(6px);
  }
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

/* ---------- 2. Пустой тред: «Выберите чат» → каноничное состояние ---------- */
/* Ставится eco-max-vi.js как узел .vi-empty в #messages (flex, margin:auto).
   Пока узла нет — служебный текст скина остаётся как фолбэк. */

#messages .vi-empty--nochat {
  margin: auto;
}

/* На время загрузки треда прячем карточку «Начните общение» (анти-флеш),
   скелетон ставит eco-max-vi.js */

#messages.vi-thread-loading .thread-empty {
  visibility: hidden;
}

/* ---------- 3. Скелетоны загрузки (shimmer в каноне maxi) ---------- */

.vi-skel {
  background: linear-gradient(
    90deg,
    var(--vi-skel-base) 25%,
    var(--vi-skel-hi) 45%,
    var(--vi-skel-base) 65%
  );
  background-size: 600px 100%;
  animation: vi-shimmer 1.3s infinite linear;
  border-radius: 10px;
}

@keyframes vi-shimmer {
  from {
    background-position: 300px 0;
  }
  to {
    background-position: -300px 0;
  }
}

/* 3а. Скелетон треда: пузыри-каркасы в потоке #messages */

.vi-skel--thread {
  margin: auto 0;
  display: flex;
  flex-direction: column;
  gap: 14px;
  width: 100%;
  max-width: 720px;
  align-self: center;
  padding: 12px 4px;
}

.vi-skel__row {
  display: flex;
  gap: 10px;
  align-items: flex-end;
}

.vi-skel__row--out {
  justify-content: flex-end;
}

.vi-skel__ava {
  width: 30px;
  height: 30px;
  border-radius: 50%;
  flex-shrink: 0;
}

.vi-skel__bubble {
  height: 38px;
  border-radius: 18px;
}

.vi-skel__bubble--sm {
  width: 38%;
  height: 32px;
  border-bottom-left-radius: 6px;
}

.vi-skel__bubble--md {
  width: 54%;
}

.vi-skel__bubble--lg {
  width: 66%;
  height: 44px;
  border-bottom-right-radius: 6px;
}

.vi-skel__bubble--xl {
  width: 46%;
  height: 30px;
}

/* 3б. Скелетон настроек: карточки-каркасы */

.vi-skel--settings {
  display: flex;
  flex-direction: column;
  gap: 14px;
  max-width: 720px;
  width: 100%;
  margin: 0 auto;
  padding: 4px 0 24px;
}

.vi-skel__card {
  border-radius: 18px;
  border: 1px solid var(--border);
  background: var(--surface);
  padding: 16px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.vi-skel__profile {
  flex-direction: row;
  align-items: center;
  gap: 14px;
}

.vi-skel__profile .vi-skel__ava {
  width: 52px;
  height: 52px;
}

.vi-skel__line {
  height: 12px;
  border-radius: 6px;
}

.vi-skel__line--w40 {
  width: 40%;
}

.vi-skel__line--w60 {
  width: 60%;
}

.vi-skel__line--w80 {
  width: 80%;
}

.vi-skel__segrow {
  display: flex;
  gap: 8px;
}

.vi-skel__seg {
  flex: 1;
  height: 52px;
  border-radius: 12px;
}

/* 3в. Скелетон звонков: строки-каркасы */

.vi-skel--calls {
  display: flex;
  flex-direction: column;
  gap: 4px;
  padding: 8px 4px;
}

.vi-skel__callrow {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 10px 12px;
}

.vi-skel__callrow .vi-skel__ava {
  width: 44px;
  height: 44px;
}

.vi-skel__callrow .vi-skel__lines {
  display: flex;
  flex-direction: column;
  gap: 8px;
  flex: 1;
}

/* Скелетоны чисто декоративные */

.vi-skel--thread,
.vi-skel--settings,
.vi-skel--calls {
  pointer-events: none;
}

/* ---------- 4. Оффлайн-баннер ---------- */

.vi-offline {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  z-index: 1400;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  padding: calc(10px + var(--safe-top, env(safe-area-inset-top, 0px))) 16px 10px;
  background: var(--vi-banner-bg);
  color: var(--vi-banner-ink);
  border-bottom: 1px solid var(--vi-banner-line);
  box-shadow: 0 8px 28px rgba(4, 8, 16, 0.18);
  backdrop-filter: blur(10px) saturate(1.1);
  -webkit-backdrop-filter: blur(10px) saturate(1.1);
  font-size: 13px;
  font-weight: 500;
  letter-spacing: 0.01em;
  transform: translateY(-110%);
  transition: transform 0.3s ease;
  pointer-events: none;
}

.vi-offline[hidden] {
  display: none !important;
}

.vi-offline.is-show {
  transform: translateY(0);
}

.vi-offline__dot {
  width: 9px;
  height: 9px;
  border-radius: 50%;
  background: var(--vi-focus);
  flex-shrink: 0;
  animation: vi-ping 1.4s ease-out infinite;
}

@keyframes vi-ping {
  0% {
    box-shadow: 0 0 0 0 color-mix(in srgb, var(--vi-focus) 45%, transparent);
  }
  70% {
    box-shadow: 0 0 0 8px transparent;
  }
  100% {
    box-shadow: 0 0 0 0 transparent;
  }
}

/* ---------- 5. a11y: focus-visible кольца и контраст ---------- */

/* Восстановление колец там, где соседние слои их подавили outline:none
   (визуальные состояния hover сохраняются) */

.view--calls .call-row:focus-visible {
  outline: 2px solid var(--vi-focus);
  outline-offset: 2px;
  border-radius: 14px;
}

.vd-clip-card:focus-visible {
  outline: 2px solid rgba(107, 150, 255, 0.95);
  outline-offset: 3px;
}

.sheet__caption:focus-visible,
.feed-compose__input:focus-visible {
  outline: none;
  border-color: var(--vi-focus);
  box-shadow: 0 0 0 3px color-mix(in srgb, var(--vi-focus) 30%, transparent);
}

/* Кольца для собственных компонентов VI */

.vi-empty__btn:focus-visible {
  outline: 2px solid var(--vi-focus);
  outline-offset: 2px;
}

/* Контраст подсказок на пустых состояниях — не темнее канона 4.5:1 */
.va-empty__hint,
.calls-empty span,
.clips-empty p,
.feed-empty p,
.vi-empty__hint {
  color: var(--text-muted);
}

html[data-theme="dark"] .va-empty__hint,
html[data-theme="dark"] .calls-empty span,
html[data-theme="dark"] .clips-empty p,
html[data-theme="dark"] .feed-empty p,
html[data-theme="dark"] .vi-empty__hint {
  color: #9fb0cd;
}

/* ---------- 6. Мобайл 390 ---------- */

@media (max-width: 480px) {
  .vi-empty {
    padding: 28px 18px;
    max-width: 300px;
  }

  .vi-empty__ico {
    width: 56px;
    height: 56px;
    border-radius: 18px;
  }

  .vi-skel--thread {
    max-width: 100%;
  }

  .vi-skel__bubble--lg {
    width: 74%;
  }

  .vi-skel__bubble--md {
    width: 62%;
  }

  .vi-offline {
    font-size: 12.5px;
    padding-left: 12px;
    padding-right: 12px;
  }
}

/* ---------- 7. Reduced motion ---------- */

@media (prefers-reduced-motion: reduce) {
  .vi-skel,
  .vi-skel--thread,
  .vi-skel--settings,
  .vi-skel--calls {
    animation: none;
    background: var(--vi-skel-base);
  }

  .vi-offline {
    transition: none;
  }

  .vi-offline__dot {
    animation: none;
  }

  .vi-empty {
    animation: none;
  }
}
