/* comp-waves.css — волны А/Б/В (чипы дней, превью ссылок, плеер) и задумки #154 / #151 / #150.

   Часть css/components.css: файл был 107 КБ, и патч, несущий его целиком, вёз всё ради одного
   правила. Подключается из $cssParts в index.php — сразу за самим components.css и ДО
   надстроек-стилей (addons.css, rxmenu.css, convprev.css, scrollcalm.css), которые базу
   перекрывают.

   Рез только ХВОСТОВОЙ, и это не вкусовщина: части грузятся ПОСЛЕ components.css, поэтому
   вырезать секцию из середины значило бы опустить её ниже по каскаду — при равной силе
   селектора она начала бы выигрывать у того, что раньше выигрывало у неё. Здесь части идут
   строго теми же строками и в том же порядке, что в исходнике, поэтому итоговый каскад
   совпадает побайтово. Строки 843-1124.
*/
/* ==== Восстановление стилей волн А/Б (потеряны при перезаписи файла патчами Б4–Б7) + В1 ==== */
/* Строки ниже — то, что рисуют render.js/features.js для реакций (А1), подтверждения (А2),
   цитат ответа и прыжка (А3), костей (А5), пометок и архива (Б1), плашки пинов (Б2) — и поиск
   по сообщениям (В1). Держим одним блоком в хвосте: так их не потерять во второй раз, а каскад
   их и так ставит последними. */

/* Мини-цитата ответа в пузыре (А3): полоска слева, имя акцентом, сниппет серым. В своём
   (акцентном) пузыре цвета белые — акцент на акценте не читался бы. */
.mreply{display:block;width:100%;text-align:left;border:none;background:rgba(127,127,127,.10);border-left:3px solid var(--accent);border-radius:8px;padding:4px 9px;margin:0 0 5px;cursor:pointer;font-size:12.5px;line-height:1.35;font-family:inherit}
.mmine .mreply{background:rgba(255,255,255,.16);border-left-color:rgba(255,255,255,.8)}
.mreply-who{display:block;font-weight:600;color:var(--accent)}
.mmine .mreply-who{color:#fff}
.mreply-snip{display:block;color:var(--text2);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.mmine .mreply-snip{color:rgba(255,255,255,.85)}
.mreply-del{font-style:italic;color:var(--text2)}
.mmine .mreply-del{color:rgba(255,255,255,.8)}
.mreply:disabled{cursor:default}

/* Вспышка при прыжке к сообщению (А3): короткий ореол акцентом, класс временный. */
@keyframes flashPulse{0%{box-shadow:0 0 0 0 color-mix(in oklch, var(--accent), transparent 25%)}45%{box-shadow:0 0 0 7px color-mix(in oklch, var(--accent), transparent 55%)}100%{box-shadow:0 0 0 11px transparent}}
.flash{animation:flashPulse 1.2s ease}

/* Кнопка «к новым» после прыжка вглубь истории (А3). Якорь — сама панель переписки.
   Центрируется полями, а НЕ translateX(-50%): fadeUp анимирует transform и на 0.2s ЗАТИРАЛ им
   центрирование — кнопка выезжала правее середины и прыгала влево, когда анимация кончалась.
   Высота больше не число: композер стал многострочным и растёт, поэтому всё, что висит над ним,
   едет от его живой высоты (--composer-h публикует autoGrowInput; запасное 66px — однострочный). */
#chatpane{position:relative}
.jump-down{position:absolute;left:0;right:0;margin-inline:auto;width:fit-content;bottom:calc(var(--composer-h, 66px) + 20px);z-index:7;border:1px solid var(--border);background:var(--panel2);color:var(--text);border-radius:18px;padding:8px 14px;font-size:13px;cursor:pointer;box-shadow:0 8px 24px rgba(0,0,0,.14);backdrop-filter:blur(var(--blur));-webkit-backdrop-filter:blur(var(--blur));animation:fadeUp .2s ease}
.jump-down:hover{color:var(--accent)}

/* Кнопка «вниз, к последнему» (задумка #157). Своя, а не текстовая пилюля «к новым»: у неё одно
   дело и нет слов, поэтому — квадратик-суперэллипс размером с кнопки композера (форму даёт
   corner-shape из tokens.css, тот же, что у пузырей и кнопок; радиус — общий --bub-radius).
   Полупрозрачная и на размытии, как панели вокруг: обои сквозь неё видно, но стрелку — тоже.
   Стоит чуть выше соседки (+30 против +20): она перекрывает меньше последней строки переписки.
   Показываются они по очереди (см. scrollDownBtnSync), поэтому разная высота глаз не режет. */
.scroll-down{position:absolute;left:0;right:0;margin-inline:auto;width:38px;height:38px;bottom:calc(var(--composer-h, 66px) + 30px);z-index:7;display:flex;align-items:center;justify-content:center;border:1px solid var(--border);border-radius:var(--bub-radius,14px);background:color-mix(in oklch, var(--panel2), transparent 30%);backdrop-filter:blur(var(--blur)) saturate(1.4);-webkit-backdrop-filter:blur(var(--blur)) saturate(1.4);color:var(--text2);font-size:16px;line-height:1;cursor:pointer;box-shadow:0 6px 18px rgba(0,0,0,.12);animation:scrollDownIn .18s ease;transition:color .15s ease,background .15s ease,box-shadow .15s ease,transform .12s ease}
.scroll-down:hover{color:var(--accent);background:color-mix(in oklch, var(--panel2), transparent 12%);box-shadow:0 8px 22px rgba(0,0,0,.16)}
.scroll-down:active{transform:translateY(1px) scale(.94)}
@keyframes scrollDownIn{from{opacity:0;transform:translateY(8px) scale(.9)}to{opacity:1;transform:none}}

/* Значение интерактивного эмодзи (А5): крупная грань под броском. */
.dice-val{font-size:15px;font-weight:700;color:var(--text2);text-align:center;margin-top:2px}

/* Список диалогов (Б1): скрепка пина и ручная точка «непрочитанное» (без числа). */
.row-pin{font-size:12px;opacity:.7;flex-shrink:0}
.unread-dot{width:9px;height:9px;border-radius:50%;background:var(--accent);flex-shrink:0}

/* Архивная секция над списком (Б1): свёрнутая строка «Архив N», тап раскрывает. */
.archive-head{display:flex;align-items:center;gap:8px;padding:9px 12px;margin:2px 8px;border-radius:12px;cursor:pointer;color:var(--text2);font-size:13.5px;user-select:none}
.archive-head:hover{background:var(--hover)}
.arch-ic{font-size:14px}
.arch-label{flex:1;font-weight:600}
.arch-count{background:var(--hover);border-radius:10px;padding:1px 8px;font-size:12px}
.arch-chev{font-size:11px}
.archive-list{border-bottom:1px solid var(--border);margin:0 0 4px;padding-bottom:4px}

/* Плашка закреплённых под шапкой (Б2): последний пин, счётчик листает, ✕ открепляет. */
#pin-bar{align-items:center;gap:10px;padding:6px 12px;background:var(--panel);backdrop-filter:blur(var(--blur)) saturate(1.4);-webkit-backdrop-filter:blur(var(--blur)) saturate(1.4);border-bottom:1px solid var(--border);cursor:pointer;z-index:3}
#pin-bar .pin-body{flex:1;min-width:0;border-left:3px solid var(--accent);padding-left:9px}
#pin-who{font-size:12px;font-weight:600;color:var(--accent)}
#pin-snip{font-size:12.5px;color:var(--text2);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
#pin-count{border:none;background:var(--hover);color:var(--text2);border-radius:11px;min-width:34px;height:24px;font-size:12px;cursor:pointer;padding:0 8px;flex-shrink:0}
#pin-count:hover{color:var(--accent)}
.pin-x{border:none;background:transparent;color:var(--text2);font-size:14px;cursor:pointer;padding:4px 6px;border-radius:8px;flex-shrink:0}
.pin-x:hover{color:var(--accent);background:var(--hover)}
body:not(.inchat) #pin-bar{display:none !important}

/* Общий лист подтверждения (А2): доборы поверх модальных классов. */
.confirm-text{font-size:13.5px;color:var(--text2);margin:10px 0 14px;line-height:1.45}
.modal-actions button.danger{background:var(--danger)}

/* Поиск по сообщениям (В1): поле на месте заголовка — геометрия шапки не дёргается. */
#msg-search{display:none;flex:1;min-width:0;align-items:center;gap:7px;padding:0 10px 0 12px;height:38px;border-radius:18px;background:var(--hover)}
#chathead.searching .peer-head,#chathead.searching #closeness-badge,#chathead.searching #head-search-btn{display:none}
#chathead.searching #msg-search{display:flex}
#msg-search input{flex:1;min-width:0;border:none;background:transparent;outline:none;font-size:14px}
#msg-search-count{flex-shrink:0;font-size:12px;color:var(--text2);white-space:nowrap}
.ms-btn{flex-shrink:0;border:none;background:transparent;color:var(--text2);cursor:pointer;padding:4px 5px;border-radius:8px;display:flex;align-items:center;justify-content:center}
.ms-btn:hover{color:var(--accent);background:var(--hover)}
.ms-btn:disabled{opacity:.3;cursor:default}
.ms-btn:disabled:hover{color:var(--text2);background:transparent}
#head-search-btn{border:none;background:transparent;color:var(--text2);cursor:pointer;width:38px;height:38px;display:flex;align-items:center;justify-content:center;border-radius:50%;flex-shrink:0;padding:0}
#head-search-btn:hover{color:var(--accent);background:var(--hover)}

/* Телефон: пин-бар — стеклянной карточкой под пилюлями шапки (шапка там absolute и лежит
   поверх ленты); поиск и лупа — тем же стеклом, что остальные сегменты. */
@media(max-width:760px){
  #pin-bar{position:absolute;top:70px;left:9px;right:9px;z-index:7;border:1px solid var(--border);border-radius:16px;box-shadow:0 8px 24px rgba(0,0,0,.08)}
  #msg-search{height:54px;border-radius:24px;padding:0 12px;background:var(--panel)}
  /* Лупа теперь ВНУТРИ стеклянной пилюли имени (задумка #75) — своим стеклом ей быть не нужно:
     обычная кнопка в потоке пилюли, чуть крупнее десктопной под палец. */
  #head-search-btn{width:40px;height:40px;border-radius:50%}
}

/* ==== Волна В, п. В2: чипы дней + календарь; п. В1: секция «Сообщения» в поиске списка ==== */

/* Чип дня между рядами. position:sticky даёт «плавающую» текущую дату при скролле ДАРОМ:
   чип держится у верха, пока следующий его не вытеснит — ровно телеграмное поведение,
   без единого обработчика скролла. */
.day-chip{position:sticky;top:8px;z-index:5;display:flex;justify-content:center;margin:18px 0 14px;pointer-events:none;opacity:0;transition:opacity .22s ease}
.day-chip button{pointer-events:none;border:none;background:var(--panel2);backdrop-filter:blur(var(--blur)) saturate(1.4);-webkit-backdrop-filter:blur(var(--blur)) saturate(1.4);color:var(--text2);border-radius:14px;padding:5px 13px;font-size:12px;font-weight:600;cursor:pointer;box-shadow:0 4px 14px rgba(0,0,0,.14)}
#messages.day-scrolling .day-chip{opacity:1}
#messages.day-scrolling .day-chip button{pointer-events:auto}
.day-chip button:hover{color:var(--accent)}
/* Кнопка даты — в фирменном супер-эллипсе (задумка #194). Селектор нарочно тяжелее самого
   правила выше: внутри ленты corner-shape гасит `#messages *{corner-shape:round}` из layout.css
   (правило проекта — суперэллипс в ленте несут только избранные силуэты), и одного класса тут не
   хватило бы. `#messages .day-chip button` — id + класс + тег против одного id, поэтому выигрывает
   независимо от порядка файлов, а round у прочей мелочи ленты остаётся нетронутым.
   Радиус не трогаем: 14px при высоте чипа ~27px — углы уже смыкаются, и суперэллипс превращает
   пилюлю ровно в ту форму, что у пузырей и кнопок приложения. Чипов на экране один-два, цена
   формы ничтожна — тот же довод, по которому её оставили пузырю и аватарке. */
#messages .day-chip button{corner-shape:superellipse(2.6)}

/* Календарь прыжка к дате: сетка месяца без библиотек. */
.cal-sheet{max-width:320px;width:100%}
.cal-head{display:flex;align-items:center;justify-content:space-between;margin-bottom:10px}
.cal-title{font-weight:700;font-size:15px}
.cal-nav{border:none;background:var(--hover);color:var(--text2);width:32px;height:32px;border-radius:10px;font-size:16px;cursor:pointer}
.cal-nav:hover{color:var(--accent)}
.cal-grid{display:grid;grid-template-columns:repeat(7,1fr);gap:4px}
.cal-wd{margin-bottom:4px}
.cal-wd span{text-align:center;font-size:11px;color:var(--text2);font-weight:600}
.cal-day{border:none;background:transparent;color:var(--text2);opacity:.35;height:34px;border-radius:10px;font-size:13px}
.cal-day.has{opacity:1;color:var(--text);background:var(--hover);cursor:pointer;font-weight:600}
.cal-day.has:hover{background:var(--accent-soft);color:var(--accent)}

/* Секция «Сообщения» в поиске списка (В1, вторая половина). */
#global-msgs{border-top:1px solid var(--border);margin-top:6px;padding:4px 6px 8px}
.gm-row{display:flex;align-items:center;gap:11px;width:100%;text-align:left;border:none;background:transparent;padding:8px 8px;border-radius:14px;cursor:pointer}
.gm-row:hover{background:var(--hover)}
.gm-body{flex:1;min-width:0}
.gm-top{display:flex;align-items:baseline;gap:8px}
.gm-name{font-weight:600;font-size:14px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;flex:1}
.gm-date{font-size:11.5px;color:var(--text2);flex-shrink:0}
.gm-snip{font-size:13px;color:var(--text2);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;margin-top:1px}
.gm-more{display:block;width:100%;border:none;background:transparent;color:var(--accent);font-size:13px;font-weight:600;padding:8px;cursor:pointer;border-radius:12px}
.gm-more:hover{background:var(--hover)}

@media(max-width:760px){
  /* Шапка переписки на телефоне — стекло ПОВЕРХ ленты: чип держится ниже её пилюль, с зазором,
     чтобы плавающая плашка не касалась стекла шапки (#74). */
  .day-chip{top:76px}
}

/* ==== Волна В, п. В3: карточка превью ссылки ==== */
.link-prev{display:flex;flex-direction:column;gap:2px;width:100%;text-align:left;border:none;cursor:pointer;margin-top:6px;padding:7px 10px 8px 12px;border-radius:10px;background:var(--hover);border-left:3px solid var(--accent)}
.link-prev:hover{filter:brightness(1.04)}
.lp-site{font-size:11.5px;font-weight:600;color:var(--text2)}
.lp-title{font-size:13.5px;font-weight:700;color:var(--text);line-height:1.25}
.lp-descr{font-size:12.5px;color:var(--text2);line-height:1.35;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}
/* В своём (зелёном) пузыре карточка белёсая, полоска и текст — белые полутона. */
.mmine .link-prev{background:rgba(255,255,255,.16);border-left-color:rgba(255,255,255,.75)}
.mmine .lp-site{color:rgba(255,255,255,.75)}
.mmine .lp-title{color:#fff}
.mmine .lp-descr{color:rgba(255,255,255,.82)}

/* ==== Волна В, п. В4: плеер — скорость, мини-плеер, PiP ==== */
.rate-btn{border:1px solid var(--border);background:var(--panel-solid,var(--panel));color:var(--text2);border-radius:11px;padding:3px 8px;font-size:11.5px;font-weight:700;cursor:pointer;line-height:1.2;flex-shrink:0}
.rate-btn:hover{color:var(--accent);border-color:var(--accent)}
.voicebubble .rate-btn{align-self:center}   /* #104: убран лишний margin-left:8px поверх gap:10px плеера */
/* В своём (зелёном) пузыре кнопка — белыми полутонами, как карточка превью. */
.mmine .voicebubble .rate-btn{background:rgba(255,255,255,.16);border-color:rgba(255,255,255,.4);color:#fff}

#mini-player{display:flex;align-items:center;gap:9px;margin:0 10px 6px;padding:7px 10px;border:1px solid var(--border);border-radius:14px;background:var(--panel);backdrop-filter:blur(var(--blur)) saturate(1.4);-webkit-backdrop-filter:blur(var(--blur)) saturate(1.4);box-shadow:0 3px 10px rgba(0,0,0,.06)}
#mpl-toggle,#mpl-close{border:none;background:transparent;color:var(--text);font-size:14px;cursor:pointer;width:28px;height:28px;border-radius:9px;flex-shrink:0}
#mpl-toggle:hover,#mpl-close:hover{background:var(--hover)}
#mpl-close{color:var(--text2)}
.mpl-mid{flex:1;min-width:0}
#mpl-label{font-size:12.5px;font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.mpl-bar{height:3px;border-radius:2px;background:var(--hover);margin-top:4px;overflow:hidden}
.mpl-bar i{display:block;height:100%;width:0%;background:var(--accent);border-radius:2px;transition:width .2s linear}

/* Инструменты лайтбокса: скорость и PiP в углу, поверх видео. */
.lb-tools{position:absolute;top:14px;left:14px;display:flex;gap:8px;z-index:3}
.lb-tool{background:rgba(20,20,24,.55);border:1px solid rgba(255,255,255,.25);color:#fff;backdrop-filter:blur(8px);-webkit-backdrop-filter:blur(8px)}
.lb-tool:hover{color:#fff;border-color:#fff}
.pip-btn{border-radius:11px;padding:3px 8px;cursor:pointer;display:flex;align-items:center}


/* ── Кластер жестов (#63/#65/#67): индикатор свайпа-ответа, десктоп-кнопка, выкл. выделения ── */
#swipe-hint{position:fixed;z-index:60;display:none;pointer-events:none;filter:drop-shadow(0 4px 10px rgba(0,0,0,.18))}
#swipe-hint .sh-track{fill:var(--panel2);stroke:var(--border);stroke-width:2}
#swipe-hint .sh-prog{fill:none;stroke:var(--accent);stroke-width:2.4;transform:rotate(-90deg);transform-origin:22px 22px}
#swipe-hint .sh-ic{stroke:var(--accent)}
#swipe-hint.ready .sh-track{fill:var(--accent)}
#swipe-hint.ready .sh-ic,#swipe-hint.ready .sh-prog{stroke:#fff}

#hover-reply{position:fixed;z-index:38;display:none;width:30px;height:30px;align-items:center;justify-content:center;border-radius:50%;border:1px solid var(--border);background:var(--panel2);color:var(--text2);cursor:pointer;box-shadow:0 4px 12px rgba(0,0,0,.12);padding:0}
#hover-reply:hover{color:var(--accent);border-color:var(--accent)}

@media(max-width:760px){
  /* #65: на телефоне не выделяем текст зажимом и не показываем callout — копия только через меню
     (тап по пузырю → «Копировать текст»). Ссылки/медиа/спойлеры остаются кликабельными. */
  .msgbubble,.mtext,.mtext-rich{-webkit-user-select:none;user-select:none;-webkit-touch-callout:none}
}


/* ── #66: множественный выбор (лонг-пресс → выбрать; тап переключает; панель сверху) ── */
body.select-mode .mrow{cursor:pointer}
.mrow.selected{background:color-mix(in srgb, var(--accent) 13%, transparent);border-radius:12px}

#select-bar{position:fixed;top:0;left:0;right:0;z-index:44;display:none;align-items:center;gap:8px;padding:calc(9px + env(safe-area-inset-top)) 10px 9px;background:var(--panel);backdrop-filter:blur(var(--blur)) saturate(1.4);-webkit-backdrop-filter:blur(var(--blur)) saturate(1.4);border-bottom:1px solid var(--border);box-shadow:0 4px 14px rgba(0,0,0,.08)}
#select-bar .sb-x,#select-bar .sb-act{width:40px;height:40px;flex-shrink:0;border:none;background:transparent;border-radius:50%;cursor:pointer;color:var(--text);display:flex;align-items:center;justify-content:center;font-size:19px}
#select-bar .sb-x:hover,#select-bar .sb-act:hover{background:var(--hover)}
#select-bar .sb-count{font-weight:700;font-size:15px;white-space:nowrap}
#select-bar .sb-sp{flex:1}
#select-bar .sb-act.danger{color:var(--danger)}
#select-bar .sb-act.disabled{opacity:.35;pointer-events:none}

/* ── #60: скелетоны при открытии диалога (мгновенный каркас до загрузки истории) ── */
.skeletons{padding:2px 0}
.sk-row{display:flex;margin:0 0 10px;padding:0 2px}
.sk-row.sk-mine{justify-content:flex-end}
.sk-bub{height:32px;border-radius:16px;max-width:80%;background-color:var(--hover);background-image:linear-gradient(100deg,transparent 18%,color-mix(in srgb,var(--text2) 10%,transparent) 46%,color-mix(in srgb,var(--text2) 10%,transparent) 54%,transparent 82%);background-size:220% 100%;background-repeat:no-repeat;animation:sk-shimmer 1.25s ease-in-out infinite}
.sk-row.sk-mine .sk-bub{background-color:var(--accent-soft)}
.sk-media,.sk-sticker,.sk-btn{background-color:var(--hover);background-image:linear-gradient(100deg,transparent 18%,color-mix(in srgb,var(--text2) 10%,transparent) 46%,color-mix(in srgb,var(--text2) 10%,transparent) 54%,transparent 82%);background-size:220% 100%;background-repeat:no-repeat;animation:sk-shimmer 1.25s ease-in-out infinite}
.sk-media{width:58%;max-width:230px;height:150px;border-radius:16px}
.sk-sticker{width:92px;height:92px;border-radius:16px}
.sk-btns{display:flex;gap:6px;flex-wrap:wrap;max-width:82%}
.sk-btn{height:30px;border-radius:10px}
.sk-row.sk-post{justify-content:flex-start}
.sk-post .sk-bub{max-width:96%}
.skeletons.sk-channel .sk-media{width:88%;max-width:none;height:180px}
.skeletons.sk-channel .sk-row{margin-bottom:14px}
@keyframes sk-shimmer{0%{background-position:180% 0}100%{background-position:-80% 0}}

/* ============ Задумки #154 / #151 / #150: цитата ответа, подпись под кадром, углы ============ */

/* ---- #154: цитата ответа вне текстового пузыря ---- */
/* У медиа, стикера, кости, опроса и коллажа пузыря нет — их цитата стоит прямо в .mcontent, на
   обоях. Значит подложка ей нужна своя: правила .mreply выше рассчитаны на фон пузыря, и у
   исходящих там белое по белому — на обоях это была бы невидимая строка. */
.mcontent > .mreply{max-width:min(280px,100%);margin-bottom:5px;background:var(--bubble-in);box-shadow:0 1px 1.5px rgba(0,0,0,.04)}
.mmine .mcontent > .mreply{background:var(--bubble-in);border-left-color:var(--accent)}
.mcontent > .mreply .mreply-who,.mmine .mcontent > .mreply .mreply-who{color:var(--accent)}
.mcontent > .mreply .mreply-snip,.mmine .mcontent > .mreply .mreply-snip{color:var(--text2)}
.mcontent > .mreply .mreply-del,.mmine .mcontent > .mreply .mreply-del{color:var(--text2)}
/* Ширину цитата берёт по содержимому под ней: над коллажем — створ сетки, над стикером/костью
   она иначе разъехалась бы шире самого стикера. */
.mcontent:has(> .album-grid) > .mreply{max-width:min(78vw,340px)}
.mcontent:has(> .sticker) > .mreply{max-width:min(220px,100%)}

/* ---- #151: подпись сообщения без заднего фона ---- */
/* Было: .media-caption — это только цвет и margin-top, то есть текст лежит прямо на обоях и на
   пёстром фоне читается через раз. Стало: кадр и подпись сшиты в один пузырь — кадру обнуляются
   нижние углы, подпись получает фон пузыря и его нижние скругления.
   Ширину подпись берёт ту же, что кадр: иначе длинная строка растянула бы .mcontent и подпись
   оказалась бы шире фотографии. Кружок (.round) из сшивки исключён — он не пузырь. */
.mcontent > .media-frame:not(.round):has(+ .media-caption){border-bottom-left-radius:0;border-bottom-right-radius:0}
.mcontent > .media-frame:not(.round) + .media-caption{width:min(280px,100%);max-width:280px;margin-top:0;padding:7px 11px 8px;background:var(--bubble-in);color:var(--text);border-radius:0 0 var(--bub-radius,14px) var(--bub-radius,14px);box-shadow:0 1px 1.5px rgba(0,0,0,.04)}
.mthem .mcontent > .media-frame:not(.round) + .media-caption{border-bottom-left-radius:6px}
.mmine .mcontent > .media-frame:not(.round) + .media-caption{background:var(--bubble-out);color:#fff;border-bottom-right-radius:6px}

/* Подписи коллажа — тем же приёмом: контейнер .album-caps становится подножием пузыря. */
.mcontent > .album-grid:has(+ .album-caps:not(:empty)){border-bottom-left-radius:0;border-bottom-right-radius:0}
.mcontent > .album-caps:not(:empty){width:min(78vw,340px);margin-top:0;padding:7px 11px 8px;background:var(--bubble-in);border-radius:0 0 var(--bub-radius,14px) var(--bub-radius,14px);box-shadow:0 1px 1.5px rgba(0,0,0,.04)}
.mmine .mcontent > .album-caps:not(:empty){background:var(--bubble-out)}
.mmine .mcontent > .album-caps > .media-caption{color:#fff}
.mrow[data-album] .mcontent > .album-caps:not(:empty){border-bottom-left-radius:18px;border-bottom-right-radius:18px}
.mrow[data-album].mthem .mcontent > .album-caps:not(:empty){border-bottom-left-radius:8px}
.mrow[data-album].mmine .mcontent > .album-caps:not(:empty){border-bottom-right-radius:8px}

/* Подпись к файлу шла отдельной строкой под карточкой — тот же случай, тот же приём. */
.mcontent > .msgbubble:has(+ .media-caption){border-bottom-left-radius:0;border-bottom-right-radius:0}
.mcontent > .msgbubble + .media-caption{margin-top:0;padding:0 12px 8px;background:var(--bubble-in);color:var(--text);border-radius:0 0 var(--bub-radius,14px) var(--bub-radius,14px)}
.mthem .mcontent > .msgbubble + .media-caption{border-bottom-left-radius:6px}
.mmine .mcontent > .msgbubble + .media-caption{background:var(--bubble-out);color:#fff;border-bottom-right-radius:6px}

/* Пресет «терминал» (бот-стили выше) красил подпись сам — под новой подложкой он бы потерялся,
   потому что правила сшивки идут ниже по файлу и при равной силе выигрывают. Возвращаем ему
   и цвет, и фон: подпись должна остаться частью терминального пузыря, а не белой заплатой. */
.bot-style-terminal .mthem .mcontent > .media-caption{background:#101418;color:#8fe3a8}

/* ---- #150: грязные углы под изображениями (диагноз-кандидат, ключ не закрыт) ---- */
/* В tokens.css у ВСЕХ элементов corner-shape:superellipse(2.6), а внутри .media-frame живёт
   композитный слой — .media-blur с filter:blur(14px) и transform:scale(1.15). Обрезка
   overflow:hidden достаётся такому слою круглым скруглением, а суперэллипс «полнее»: между
   круглым краем слоя и суперэллиптическим краем рамки открывается серп, и в нём видна подложка
   рамки — а она почти чёрная (#0c0d10). Отсюда и «грязные углы».
   Лечим с двух сторон. Дети скругляются САМИ (border-radius:inherit; corner-shape у них тот же,
   значит форма совпадает с рамкой до пикселя) — обрезка родителя перестаёт быть единственной
   защитой. И подложка больше не чёрная: под кадром всегда лежит .media-blur (постер или тёмный
   градиент .dark), показывать подложке нечего, а если серп где-то и останется — он будет цвета
   обоев, а не сажи. Клетки коллажа квадратные, им наследовать нечего. */
.media-frame{background:transparent}
.media-blur,.media-img,.media-vid{border-radius:inherit}
.album-cell .media-blur,.album-cell .media-img,.album-cell .media-vid{border-radius:0!important}
