/* ============================================================
   TnP Brand System — Stage 2.5 «Cinematic» (Brand Guide v3.0)
   Канонические токены + ambient color system + слой совместимости.
   Подключается ПОСЛЕ /fonts/fonts.css на всех новых страницах.
   ============================================================ */

/* ---- Houdini @property: анимируемые кастом-свойства ---- */
@property --glow-hue     { syntax: '<number>';     initial-value: 239;  inherits: true; }
@property --glow-alpha   { syntax: '<number>';     initial-value: 0.12; inherits: true; }
@property --ambient-hue  { syntax: '<number>';     initial-value: 239;  inherits: true; }
@property --ambient-sat  { syntax: '<percentage>'; initial-value: 84%;  inherits: true; }
@property --ambient-light{ syntax: '<percentage>'; initial-value: 67%;  inherits: true; }

:root {
    /* Бренд */
    --primary: #6366f1;
    --primary-hover: #4f46e5;
    --primary-glow: rgba(99, 102, 241, 0.4);
    --secondary: #8b5cf6;
    --bg: #000000;
    --surface: #0a0a0a;
    --surface-2: #111111;
    --surface-3: #1a1a1a;
    --text: #f0f0f0;
    --text-muted: #999999;
    --text-dim: #555555;
    --glass-bg: rgba(255, 255, 255, 0.06);
    --glass-border: rgba(255, 255, 255, 0.1);
    --glass-hover: rgba(255, 255, 255, 0.12);
    --success: #10b981;
    --warning: #f59e0b;
    --danger: #ef4444;
    --info: #6366f1;
    --imdb: #f5c518;
    --tomato: #fa320a;
    --metacritic: #66cc33;

    /* День/ночь: меняется ТОЛЬКО интенсивность свечения */
    --glow-intensity: 0.3;
    --overlay-tint: rgba(99, 102, 241, 0.06);

    /* Ambient Color System: Element = Context×0.70 + Brand×0.30 */
    --ambient-hue: 239;
    --ambient-sat: 84%;
    --ambient-light: 67%;
    --synergy-glow: hsla(var(--ambient-hue), var(--ambient-sat), var(--ambient-light), calc(var(--glow-intensity) * 0.5));
    --synergy-glow-strong: hsla(var(--ambient-hue), var(--ambient-sat), var(--ambient-light), var(--glow-intensity));

    /* Типографика */
    --font-ui: 'Inter', -apple-system, BlinkMacSystemFont, sans-serif;
    --font-display: 'Playfair Display', Georgia, serif;
    --font-mono: 'JetBrains Mono', 'Fira Code', ui-monospace, monospace;

    /* ---- Слой совместимости (legacy-переменные dashboard.js / setup.js) ---- */
    --primary-color: var(--primary);
    --secondary-color: var(--secondary);
    --accent-color: var(--primary-hover);
    --accent: var(--success);
    --dark-bg: var(--bg);
    --dark-card: var(--surface-2);
    --dark-card-hover: var(--surface-3);
    --dark-hover: var(--surface-3);
    --card-bg: var(--surface-2);
    --bg-primary: var(--bg);
    --bg-secondary: var(--surface);
    --text-primary: var(--text);
    --text-secondary: var(--text-muted);
    --border-color: var(--glass-border);
    --border: var(--glass-border);
    --gradient: linear-gradient(135deg, var(--primary) 0%, var(--secondary) 100%);
    --gradient-dark: linear-gradient(135deg, #0a0a0a 0%, #1a1a1a 100%);
}

/* Ночь (21:00–06:00, класс вешает theme-switcher.js): glow сильнее, палитра та же */
:root.night-theme {
    --glow-intensity: 0.6;
    --overlay-tint: rgba(30, 27, 75, 0.12);
}

/* ---- База ---- */
* { margin: 0; padding: 0; box-sizing: border-box; }

body {
    font-family: var(--font-ui);
    background: var(--bg);
    color: var(--text);
    line-height: 1.6;
    -webkit-font-smoothing: antialiased;
}

a { color: inherit; text-decoration: none; }
button { font-family: inherit; cursor: pointer; }
:focus-visible { outline: 2px solid var(--primary); outline-offset: 2px; }

::-webkit-scrollbar { width: 8px; height: 6px; }
::-webkit-scrollbar-track { background: transparent; }
::-webkit-scrollbar-thumb { background: #333; border-radius: 4px; }
::-webkit-scrollbar-thumb:hover { background: #444; }

/* ---- Иконки (SVG-спрайт /img/icons.svg) ---- */
.icon {
    width: 1.15em; height: 1.15em;
    vertical-align: -0.2em;
    fill: none;
    stroke: currentColor;
    stroke-width: 2;
    stroke-linecap: round;
    stroke-linejoin: round;
    flex-shrink: 0;
}
.icon-sm { width: 0.9em; height: 0.9em; }
.icon-lg { width: 1.6em; height: 1.6em; }
.icon-fill { fill: currentColor; stroke: none; }

/* ---- Лого ---- */
.tnp-logo {
    display: inline-flex; align-items: center; gap: 12px;
    font-weight: 800; font-size: 1.5rem; letter-spacing: -1px;
    color: var(--primary); transition: all 0.3s;
}
.tnp-logo:hover { transform: scale(1.05); filter: drop-shadow(0 0 12px var(--primary-glow)); }

/* ---- Стекло ---- */
.glass {
    background: var(--glass-bg);
    border: 1px solid var(--glass-border);
    backdrop-filter: blur(10px);
    -webkit-backdrop-filter: blur(10px);
    border-radius: 12px;
}
.glass-elevated {
    background: rgba(255, 255, 255, 0.1);
    border: 1px solid rgba(255, 255, 255, 0.2);
    backdrop-filter: blur(20px);
    -webkit-backdrop-filter: blur(20px);
    border-radius: 16px;
    box-shadow: 0 20px 60px rgba(0, 0, 0, 0.4);
}
/* Liquid glass: блик по верхней кромке на hover */
.glass-specular { position: relative; overflow: hidden; }
.glass-specular::before {
    content: ''; position: absolute; top: 0; left: 15%; right: 15%; height: 1px;
    background: linear-gradient(90deg, transparent, rgba(255,255,255,0.25), transparent);
    opacity: 0; transition: opacity 0.4s;
}
.glass-specular:hover::before { opacity: 1; }

/* ---- Кнопки ---- */
.btn {
    display: inline-flex; align-items: center; justify-content: center; gap: 8px;
    padding: 12px 28px; border-radius: 8px; border: none;
    font-size: 14px; font-weight: 600; letter-spacing: 0.4px;
    transition: all 0.3s; text-align: center;
}
.btn-primary {
    background: var(--primary); color: #fff;
    box-shadow: 0 8px 24px rgba(99, 102, 241, 0.3);
}
.btn-primary:hover {
    background: var(--primary-hover); transform: translateY(-2px);
    box-shadow: 0 12px 32px rgba(99, 102, 241, 0.4);
}
.btn-glass {
    background: var(--glass-bg); color: var(--text);
    border: 1px solid var(--glass-border);
    backdrop-filter: blur(10px); -webkit-backdrop-filter: blur(10px);
}
.btn-glass:hover {
    background: var(--glass-hover); transform: translateY(-2px);
    border-color: rgba(255, 255, 255, 0.25);
    box-shadow: 0 10px 26px rgba(0,0,0,0.4), 0 0 18px rgba(99,102,241, calc(var(--glow-intensity) * 0.6));
}
.btn-ghost { background: transparent; color: var(--text-muted); border: 1px solid var(--glass-border); }
.btn-ghost:hover { color: var(--text); border-color: rgba(255,255,255,0.25); }
.btn-danger { background: rgba(239,68,68,0.12); color: var(--danger); border: 1px solid rgba(239,68,68,0.3); }
.btn-danger:hover { background: rgba(239,68,68,0.2); }
.btn:disabled { opacity: 0.5; cursor: not-allowed; transform: none !important; }

/* ---- Заголовки секций ---- */
.section-title {
    font-family: var(--font-display); font-size: 28px; font-weight: 400;
    border-left: 4px solid var(--primary); padding-left: 15px;
    text-shadow: 0 0 20px rgba(99, 102, 241, calc(var(--glow-intensity) * 0.7));
}

/* Трёхслойный synergy-текст */
.text-synergy {
    color: #fff;
    text-shadow: 0 0 20px rgba(99, 102, 241, var(--glow-intensity)), 0 2px 8px rgba(0, 0, 0, 0.5);
}

/* Микро-лейблы */
.micro-label {
    font-size: 11px; text-transform: uppercase; letter-spacing: 1.5px;
    color: var(--text-dim); font-weight: 500;
}

/* ---- Постер-карточка ---- */
.poster-card {
    flex: 0 0 185px; aspect-ratio: 2 / 3;
    border-radius: 8px; position: relative;
    background: var(--surface-2); cursor: pointer;
    scroll-snap-align: start;
    transition: transform 0.3s, box-shadow 0.3s;
    /* ⛔ НЕ повертати `overflow: hidden`. Сяйво палітри малюють шари
       ::before/::after ПОЗАДУ картки (див. .has-palette нижче) — вони мусять
       виходити за її межі. Заокруглення кутів тепер тримають самі діти
       (img + .poster-overlay мають власний border-radius). */
}
/* ⚠️ `.qa-hover` — QA-двiйник :hover. Скриншот не має курсора, тому стенд
   _hover-all.html не міг би показати сяйво взагалі: воно живе на :hover.
   Замість дублювання правил у стенді (де копія завжди відстає від прода)
   стенд просто вішає цей клас. Будь-яке нове :hover-правило картки має
   отримати тут двiйник, інакше стенд знову почне брехати. */
/* ⚠️ `:hover` винесений у медіа-блок наприкiнцi файлу — на тач-екранi вiн
   ЛИПНЕ пiсля дотику й ефект лишається ввiмкненим без пальця. Тут — лише
   клас-двiйник для QA-стендiв. */
.poster-card.qa-hover {
    transform: scale(1.06); z-index: 2;
    /* ⚠️ Без чорної drop-тіні (`0 12px 30px rgba(0,0,0,.5)`): зі зсувом униз
       вона лягала на НИЖНЮ частину картки й глушила її. Підняття читається
       через scale + свічення, тінь для цього не потрібна. */
    box-shadow: 0 0 26px var(--synergy-glow-strong);
}
/* Картці з палітрою нейтральне сяйво не потрібне — і, головне, воно давало
   б рівно той самий обрізаний по кромці кант, від якого ми пішли. */
.poster-card.has-palette.qa-hover { box-shadow: none; }
.poster-card img {
    width: 100%; height: 100%; object-fit: cover;
    /* власне заокруглення — картка більше не обрізає дітей (overflow знято) */
    border-radius: inherit;
    position: relative; z-index: 1;
    transition: transform 0.5s;
}
/* ⛔ НЕ масштабувати саме зображення на hover.
   `scale(1.05)` роздував картинку до 342px у картці 326px: вона з'їжджала
   на 8px УГОРУ (зрізало верхні написи постера — напр. «Потяг до Пусана»)
   і на 8px УНИЗ, де .poster-card{overflow:hidden} показував чужий шматок
   кадру смугою під текстом. Замір: усі 36 карток мали imgTop = -8px.
   Підняття картки вже дає сам scale(1.06) на .poster-card — цього досить. */

/* ---- Палітра кліпу (--card-grad / --card-accent) ----
   Колір працює як СВІТЛО НАВКОЛО картки, а не як шар на постері: постер
   непрозорий і все одно накриває фон картки, тому фарбувати треба назовні.
   Постійне м'яке сяйво + помітніше на hover. */
.poster-card.has-palette {
    background: var(--card-grad, var(--surface-2));
    /* ⛔ У СПОКОЇ сяйва НЕМАЄ — картка виглядає як чистий постер.
       Колір палітри показуємо ТІЛЬКИ при наведенні (див. :hover нижче). */
    transition: transform 0.3s;
}
/* ─── Сяйво палітри: РОЗМИТИЙ ШАР ПОЗАДУ КАРТКИ, не box-shadow ───────────
   ⛔ `box-shadow` тут не працює за визначенням: зовнішня тінь ОБРІЗАЄТЬСЯ по
   border-box, тому альфа стрибком іде з 0 (під карткою) на максимум одразу
   за кромкою. Око читає цей стрибок як обведення — той самий «різкий контур»,
   який не лікувався ані двома кільцями, ані п'ятьма (26/52/88/135/190px):
   розбиття на кільця гладшає СЕРЕДИНУ спаду, але не саму межу.
   Тут замість тіні — два прямокутники ПОЗАДУ постера з `filter: blur()`.
   Вони не обрізаються: гаусіана йде НАСКРІЗЬ через кромку, її пік лишається
   під непрозорим постером, а назовні виходить уже плавний хвіст. Розриву
   немає в принципі, тому яскравість біля картки можна тримати високою.

   Два шари, обидва з inset:0 (край збігається з карткою → на кромці рівно
   половина піку):
     ::after  — ядро, вузьке й насичене (blur 26px, opacity .95);
     ::before — розчинення, широке (blur 92px, opacity .60).
   Замiряна дистанцiя згасання ≈180px вiд кромки (профiль по вертикалi над
   карткою, монотонний спад без сходинок). Змiниш blur — перемiряй профiль i
   звiр з padding `.row-scroll` (190px), iнакше overflow:auto зрiже хвiст i
   рiзкий контур повернеться вже на межi обрiзки.
   Сума двох гладких кривих гладка — сходинки взятись нізвідки. */
.poster-card.has-palette::before,
.poster-card.has-palette::after {
    content: ''; position: absolute; inset: 0; z-index: 0;
    border-radius: inherit; pointer-events: none;
    opacity: 0; transition: opacity 0.35s ease;
}
/* Широке розчинення. ⚠️ Домішка білого лишається: навіть після переходу
   палітри на постер (див. tnp_content_pipeline.extract_palette) трапляються
   темні акценти, а чистий темний колір дав би не підсвітку, а бруд. */
.poster-card.has-palette::before {
    background: color-mix(in srgb, var(--card-accent, #6366f1) 86%, #fff);
    filter: blur(92px);
}
/* Насичене ядро біля кромки */
.poster-card.has-palette::after {
    background: color-mix(in srgb, var(--card-accent, #6366f1) 92%, #fff);
    filter: blur(26px);
}
.poster-card.has-palette.qa-hover::before { opacity: 0.60; }
.poster-card.has-palette.qa-hover::after  { opacity: 0.95; }

/* ⛔ Смужку знизу («підпис» домінантним кольором) ПРИБРАНО 2026-08-15.
   Дві причини:
   1) палітра знімається з кадру трейлера, а кадри часто темні (14 із 35
      акцентів мають яскравість < 30/255) — замість кольорового підпису
      виходила темна лінія по нижньому краю картки;
   2) це місце належить ПРОГРЕСУ ПЕРЕГЛЯДУ: у ЛК той самий слот зайнято
      `.cinema-card-progress` (теж bottom:0, height:3px) — див.
      dashboard-v5.css. Дві різні смуги в одному місці плутали б.
   Не повертати сюди декор: слот зарезервовано під % перегляду. */

/* ---- Рейтинг-чипы — СТРОГО единый размер (IMDb / 🍅 / Metacritic / MAL) ---- */
.rating-imdb, .rating-tomato, .rating-meta, .rating-mal {
    display: inline-flex; align-items: center; gap: 2px;
    height: 20px; padding: 0 4px; border-radius: 4px;
    /* ⚠️ Розмiр пiдiбраний ПIД ШИРИНУ КАРТКИ, не «на око». Три чiпи в рядок
       (IMDb + 🍅 + Metacritic) при 11px/5px давали 170px проти 153px чистої
       ширини картки (185 − 2×16 паддiнга оверлея) — третiй чiп рiзало, i на
       постерi було видно «Ⓜ 6» замiсть «Ⓜ 64». Мiняєш кегль/паддiнг —
       перемiряй суму на _hover-all.html, вона мусить лишатись < 153. */
    font-size: 10px; font-weight: 700; line-height: 1;
    vertical-align: middle; box-sizing: border-box;
    border: 0;  /* сброс — чтобы border не менял высоту одного из чипов */
    white-space: nowrap;   /* чип не рветься всередині */
}
/* MyAnimeList — синій бейдж (для аніме). Бренд-колір MAL #2E51A2 */
.rating-mal { background: #2e51a2; color: #fff; }
.rating-imdb  { background: var(--imdb); color: #000; }
/* Помідор: чистий емодзі 🍅 (без тіней/обводки — за бажанням оператора) */
.rating-tomato{ background: var(--tomato); color: #fff; }
.rating-tomato .tomato-emoji { font-size: 12px; line-height: 1; }
/* Metacritic — фірмовий знак (жовта «m» в жовтому колі) на ЧОРНОМУ чіпі.
   Іконка — суцільний жовтий диск. Симетричний padding (як у базового
   правила 0 7px) + іконка 16px у 20px чіпі: 2px повітря згори/знизу, та сама
   вертикальна маса, що в IMDb/🍅. НЕ ставити padding-left/великі 19px —
   збивало вирівнювання (диск ліз до краю, чіп виглядав важчим за сусідів). */
.rating-meta { background: #000; color: #fff; }
/* ⚠️ Диск 16px у чипі 20px висоти лишає всього по 2px згори/знизу — при
   вужчому padding (0 5px) круглий значок візуально зрізало по краях.
   14px тримає диск цілим і не міняє висоту чипа. */
.rating-meta .icon {
    width: 13px; height: 13px; stroke: none; flex-shrink: 0;
    margin-left: -1px;  /* оптичний зсув: круглий диск здається зміщеним праворуч */
}
.rating-imdb .icon {
    width: 15px; height: 15px; stroke: none; flex-shrink: 0;
}

/* ---- Горизонтальный ряд с fade-краем ---- */
.row-wrap { position: relative; }
/* ⛔ Fade-край праворуч ПРИБРАНО (2026-09-09). Це та сама «тiнь зi зламаними
   градiєнтами», яку оператор бачив i на ПК, i на Андроїдi.
   Шар був `right:0; width:80px; linear-gradient(to left, var(--bg), transparent)`
   — тобто НЕПРОЗОРА чорнота по правому краю ряду. Вiн мав сенс, поки фон
   сторiнки був голий `--bg`: розчиняв обрiзану картку в тон сторiнки.
   Зламали його двi мої ж правки:
   1) пiд рядами тепер кольорова заливка кадру (`#hero-spill`), а не чорне —
      градiєнт у `--bg` малює по нiй чужу чорну пляму;
   2) ряд поїхав до кромки ЕКРАНА (`margin-inline: -60px`), а `::after`
      лишився на кромцi `.row-wrap` — на 60px усерединi. Через це чорнота
      обривалась СХОДИНКОЮ посеред заливки: замiр по фону мiж рядами
      49 → 0 на 1130-1215px i стрибок назад на 49 рiвно на 1220px = права
      кромка `.row-wrap`.
   Плюс `.row-wrap` вищий за картку (в ньому запас 190px пiд сяйво), тому
   смуга йшла наскрiзь через промiжки мiж рядами й читалась суцiльною.
   Повертати не треба: «є ще контент» показують стрiлки (у миші) i сама
   обрiзана картка (у пальця). Захочеш повернути — тiльки прозорий градiєнт
   на кромцi ЕКРАНА, нiколи не в `--bg`. */
.row-scroll {
    display: flex; gap: 16px; overflow-x: auto;
    scroll-snap-type: x proximity; padding-bottom: 8px;
    -webkit-overflow-scrolling: touch;
}
.row-scroll::-webkit-scrollbar { height: 6px; }

/* ---- Точки карусели ---- */
.carousel-dot {
    width: 10px; height: 10px; border-radius: 50%;
    border: 2px solid rgba(255, 255, 255, 0.5); background: transparent;
    transition: all 0.3s; padding: 0; margin: 0;
    box-sizing: border-box; flex: 0 0 auto; appearance: none; -webkit-appearance: none;
}
.carousel-dot.active {
    background: var(--primary); border-color: var(--primary);
    transform: scale(1.3); box-shadow: 0 0 10px var(--primary-glow);
}

/* ---- Skeleton loading ---- */
.skeleton {
    background: linear-gradient(90deg, #111 25%, #1a1a1a 50%, #111 75%);
    background-size: 200% 100%;
    animation: shimmer 1.5s infinite;
    border-radius: 8px;
}
@keyframes shimmer { 0% { background-position: 200% 0; } 100% { background-position: -200% 0; } }

/* ---- Провайдер/сервис-пиллы ---- */
.prov-pill {
    display: inline-block; padding: 2px 8px; border-radius: 4px;
    font-size: 10px; font-weight: 800; letter-spacing: 0.5px;
}
.prov-rd { background: rgba(16, 185, 129, 0.15); color: var(--success); }
.prov-tb { background: rgba(245, 158, 11, 0.15); color: var(--warning); }
.prov-ad { background: rgba(139, 92, 246, 0.15); color: var(--secondary); }

/* ---- Формы ---- */
.field {
    width: 100%; padding: 13px 16px; border-radius: 10px;
    background: rgba(255, 255, 255, 0.05); border: 1px solid var(--glass-border);
    color: var(--text); font-size: 15px; font-family: var(--font-ui);
    transition: border-color 0.3s, box-shadow 0.3s;
}
.field::placeholder { color: var(--text-dim); }
.field:focus {
    outline: none; border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(99, 102, 241, 0.15);
}

/* ---- Модалка ---- */
.modal-backdrop {
    position: fixed; inset: 0; z-index: 1000;
    background: rgba(0, 0, 0, 0.85);
    backdrop-filter: blur(6px); -webkit-backdrop-filter: blur(6px);
    display: flex; align-items: center; justify-content: center; padding: 20px;
}
.modal-card {
    background: rgba(17, 17, 17, 0.95);
    border: 1px solid rgba(255, 255, 255, 0.15);
    border-radius: 16px; box-shadow: 0 20px 60px rgba(0, 0, 0, 0.5);
    max-width: 560px; width: 100%; max-height: 90vh; overflow-y: auto;
    padding: 28px;
}

/* ---- Анимации появления ---- */
@keyframes fadeUp { from { opacity: 0; transform: translateY(24px); } to { opacity: 1; transform: none; } }
.reveal { animation: fadeUp 0.6s ease both; }
@supports (animation-timeline: view()) {
    .reveal {
        animation: fadeUp linear both;
        animation-timeline: view();
        animation-range: entry 0% entry 30%;
    }
}

@keyframes heroBreath { 0%, 100% { --glow-alpha: 0.08; } 50% { --glow-alpha: 0.18; } }

/* ---- Доступность ---- */
@media (prefers-reduced-motion: reduce) {
    *, *::before, *::after {
        animation-duration: 0.01ms !important;
        animation-iteration-count: 1 !important;
        transition-duration: 0.01ms !important;
        scroll-behavior: auto !important;
    }
}


/* ═══ Картка: ефекти наведення — ТIЛЬКИ для миші ═══════════════════════════
   Дзеркало правил вище, але на `:hover`. Роздiлення потрiбне тому, що на
   тач-екранi `:hover` липкий: Android лишає його на елементi пiсля дотику,
   тож масштаб i сяйво палiтри висiли б на картцi без пальця. `.qa-hover`
   лишається зовнi блоку — стенди мусять працювати й у headless.
   ⚠️ Нове `:hover`-правило картки додавати В ОБИДВА мiсця: сюди i двiйником
   `.qa-hover` вище, iнакше QA-стенд почне брехати. */
@media (hover: hover) and (pointer: fine) {
    .poster-card:hover {
        transform: scale(1.06); z-index: 2;
        box-shadow: 0 0 26px var(--synergy-glow-strong);
    }
    .poster-card.has-palette:hover { box-shadow: none; }
    .poster-card.has-palette:hover::before { opacity: 0.60; }
    .poster-card.has-palette:hover::after  { opacity: 0.95; }
}
