/*
 * Посадочные страницы маршрутов для типов специалистов (/arquitectos/ и
 * следующие за ней) и собирающая их страница-хаб /soluciones/. Подключается
 * только на этих страницах (см. header.php и ffj_is_route_page()), поэтому
 * селекторы здесь могут быть общими — main, html.
 */

/*
 * У main в global.css стоит overflow: hidden — он режет горизонтальные вылеты,
 * но заодно делает main скролл-контейнером, и position: sticky внутри перестаёт
 * работать. clip режет так же, но скролл-контейнера не создаёт, и липкая строка
 * маршрута остаётся липкой.
 */
main {
    overflow: clip;
}

/*
 * Прокрутка к якорям — браузерная: клик по пункту меню плавно доводит до
 * секции, а scroll-margin-top ниже отводит её из-под шапки и липкой строки.
 */
html {
    scroll-behavior: smooth;
}

@media (prefers-reduced-motion: reduce) {
    html {
        scroll-behavior: auto;
    }
}

.route-page {
    color: #24262b;
}

/* Липкая навигация маршрута
   ------------------------------------------------------------------------ */

/*
 * Шапка сайта тоже липкая, поэтому строка маршрута прилипает не к нулю, а под
 * неё: --ffj-header-h — нижний край шапки в прилипшем состоянии, его держит
 * актуальным js/routes.js. Минус пиксель — перекрытие: при дробной высоте шапки
 * (а она дробная почти всегда) без него между полосами остаётся волосяной
 * просвет, сквозь который видно контент.
 */
/*
 * Разделительная линия снизу — внутренней тенью, а не border-bottom: бордюр
 * входил бы в высоту строки и сдвигал всё её содержимое на пиксель вверх.
 */
.route-nav {
    position: sticky;
    top: calc(var(--ffj-header-h, 0px) - 1px);
    z-index: 1030;
    background: #fff;
    box-shadow: inset 0 -1px 0 #eef1f4, 0 2px 6px rgba(13, 20, 49, .04);
}

/*
 * Высота строки задана явно, а пункты тянутся на всю её высоту (align-items:
 * stretch): подпись, ссылки и кнопка выравниваются по одной линии независимо от
 * метрик шрифта и от того, зарезервировал ли браузер место под горизонтальный
 * скроллбар списка. Красное подчёркивание при этом ложится ровно на нижний край.
 */
.route-nav__inner {
    align-items: stretch;
    display: flex;
    gap: 24px;
    height: 64px;
}

.route-nav__label {
    align-items: center;
    color: #24262b;
    display: flex;
    flex: 0 0 auto;
    font-size: 13px;
    font-weight: 700;
    letter-spacing: .06em;
    text-transform: uppercase;
    white-space: nowrap;
}

/* На узком экране пункты не переносятся, а прокручиваются: строка остаётся
   в одну линию, и красная кнопка всегда на своём месте справа.

   height: 100% обязателен: из-за overflow-x список — скролл-контейнер, а такой
   флекс-элемент браузер по align-items: stretch не растягивает и оставляет по
   высоте контента. Пункты тогда прижаты к верху строки, и текст в них стоит
   заметно выше подписи слева и кнопки справа. */
.route-nav__list {
    align-items: stretch;
    display: flex;
    flex: 1 1 auto;
    gap: 22px;
    height: 100%;
    list-style: none;
    margin: 0;
    overflow-x: auto;
    padding: 0;
    scrollbar-width: none;
}

.route-nav__item {
    display: flex;
}

.route-nav__list::-webkit-scrollbar {
    display: none;
}

/* Растворяющийся правый край — единственный признак того, что строку можно
   прокрутить. Класс ставит js/routes.js и только когда прокручивать есть что. */
.route-nav__list.is-scrollable {
    -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 28px), transparent);
    mask-image: linear-gradient(to right, #000 calc(100% - 28px), transparent);
}

/*
 * Подчёркивание активного пункта — абсолютным псевдоэлементом, а не бордюром:
 * бордюр входит в высоту ссылки, текст центрируется в остатке и встаёт выше
 * середины строки. Псевдоэлемент из потока выключен, поэтому текст центрируется
 * по всей высоте — ровно так же, как подпись слева и кнопка справа.
 */
.route-nav__link {
    align-items: center;
    color: #4a5073;
    display: flex;
    font-size: 14px;
    position: relative;
    white-space: nowrap;
}

.route-nav__link::after {
    bottom: 0;
    content: '';
    height: 2px;
    left: 0;
    position: absolute;
    right: 0;
}

.route-nav__link:hover,
.route-nav__link.is-active {
    color: var(--ffj-red-01);
}

.route-nav__link:hover::after,
.route-nav__link.is-active::after {
    background: var(--ffj-red-01);
}

.route-nav__cta {
    align-self: center;
    flex: 0 0 auto;
    white-space: nowrap;
}

/* Кнопка ведёт к последней секции, поэтому подсвечивается наравне с пунктами —
   но подчёркиванием её не отметить, отмечаем цветом. */
.route-nav__cta.is-active {
    background: var(--ffj-red-02);
}

/* Секции
   ------------------------------------------------------------------------ */

/* Секция после прокрутки к якорю должна встать под обеими липкими полосами, а
   не скрыться за ними. Оба слагаемых считает js/routes.js. */
.route-hero,
.route-section {
    scroll-margin-top: calc(var(--ffj-header-h, 0px) + var(--ffj-route-nav-h, 64px) + 12px);
}

.route-hero {
    background: #fff;
    padding: 40px 0 56px;
}

.route-hero__title {
    color: #24262b;
    font-size: 2.5rem;
    font-weight: 700;
    line-height: 1.15;
    margin-bottom: 20px;
}

.route-hero__text {
    font-size: 1.0625rem;
    line-height: 1.6;
    margin-bottom: 28px;
    max-width: 520px;
}

/* Кто ведёт проект — приписка под подзаголовком. Мельче и тише его: это не
   второе обещание первого экрана, а уточнение к первому. */
.route-hero__note {
    color: #4a5073;
    font-size: .9375rem;
    line-height: 1.6;
    margin-bottom: 28px;
    margin-top: -12px;
    max-width: 520px;
}

.route-hero__actions {
    display: flex;
    flex-wrap: wrap;
    gap: 12px;
}

/* Третье действие первого экрана: не кнопка, а ссылка — рядом с двумя кнопками
   третья читалась бы как равная им по весу. */
.route-hero__link {
    color: var(--ffj-red-01);
    display: inline-block;
    font-size: .9375rem;
    font-weight: 700;
    margin-top: 18px;
}

.route-hero__link:hover {
    color: var(--ffj-red-02);
}

.route-hero__link i {
    font-size: .75rem;
    margin-left: 6px;
    transition: transform .2s ease;
}

.route-hero__link:hover i {
    transform: translateX(4px);
}

.route-hero__media {
    position: relative;
}

.route-hero__media img {
    border-radius: 14px;
    display: block;
    height: 420px;
    object-fit: cover;
    width: 100%;
}

.route-section {
    padding: 56px 0;
}

.route-section--grey {
    background: var(--ffj-grey-02);
}

.route-section__title {
    color: #24262b;
    font-size: 1.875rem;
    font-weight: 700;
    line-height: 1.25;
    margin-bottom: 14px;
}

.route-section__lead {
    color: #4a5073;
    font-size: 1.0625rem;
    line-height: 1.6;
    margin-bottom: 28px;
    max-width: 720px;
}

.route-section__more {
    margin-top: 28px;
}

/*
 * Иллюстрация в колонке рядом с текстом блока. Кадры узлов приходят от KMEW
 * маленькими, поэтому размер задаёт сам файл: width: auto оставляет натуральную
 * величину, а max-width ужимает кадр, только если колонка уже него. Растянутый
 * такой снимок превращается в кашу.
 */
.route-section__media {
    border-radius: 14px;
    display: block;
    height: auto;
    max-width: 100%;
    width: auto;
}

/* Абзац под блоком: он относится к обеим половинам ряда сразу, поэтому стоит
   под ними, а не внутри одной карточки. */
.route-section__note {
    color: #4a5073;
    font-size: .9375rem;
    line-height: 1.6;
    margin-top: 24px;
    max-width: 860px;
}

/* Карточки: дизайны, серии, проекты
   ------------------------------------------------------------------------ */

.route-cards {
    display: grid;
    gap: 24px;
}

.route-cards--2 {
    grid-template-columns: repeat(2, minmax(0, 1fr));
}

.route-cards--3 {
    grid-template-columns: repeat(3, minmax(0, 1fr));
}

.route-cards--4 {
    grid-template-columns: repeat(4, minmax(0, 1fr));
}

/*
 * Пять колонок — под блок имитаций на маршруте архитектора: пять фактур должны
 * читаться как один ряд, иначе пятая карточка уезжает на вторую строку и набор
 * перестаёт выглядеть законченным.
 */
.route-cards--5 {
    grid-template-columns: repeat(5, minmax(0, 1fr));
}

.route-card {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    color: inherit;
    display: flex;
    flex-direction: column;
    overflow: hidden;
    transition: box-shadow .25s ease, transform .25s ease;
}

.route-card:hover {
    box-shadow: 0 12px 28px rgba(13, 20, 49, .1);
    color: inherit;
    transform: translateY(-2px);
}

.route-card__media {
    background: var(--ffj-grey-02);
    display: block;
}

.route-card__media img {
    display: block;
    height: 200px;
    object-fit: cover;
    width: 100%;
}

.route-cards--2 .route-card__media img {
    height: 240px;
}

.route-card__body {
    display: flex;
    flex: 1 1 auto;
    flex-direction: column;
    gap: 6px;
    padding: 18px 20px 20px;
}

.route-card__title {
    color: #24262b;
    font-size: 1.0625rem;
    font-weight: 700;
}

.route-card__title--upper {
    letter-spacing: .03em;
    text-transform: uppercase;
}

.route-card__meta {
    color: var(--ffj-red-01);
    font-size: .875rem;
    font-weight: 600;
}

.route-card__text {
    color: #4a5073;
    font-size: .875rem;
    line-height: 1.5;
}

.route-card__link {
    color: var(--ffj-red-01);
    font-size: .875rem;
    font-weight: 700;
    margin-top: auto;
    padding-top: 10px;
}

.route-card__link i {
    font-size: .75rem;
    margin-left: 6px;
    transition: transform .2s ease;
}

.route-card:hover .route-card__link i,
.route-doc:hover .route-card__link i,
.route-tile:hover .route-card__link i,
.route-compare__item:hover .route-card__link i {
    transform: translateX(4px);
}

/* Плитки с иконкой: роли на «Soluciones», быстрые входы на маршрутах
   ------------------------------------------------------------------------ */

/*
 * Два входа в решения рядом: по роли и по типу проекта. Списки разной длины
 * (четыре роли и пять типологий), поэтому столбцы не выравниваются по низу —
 * каждый заканчивается там, где заканчивается его набор.
 */
.route-groups {
    display: grid;
    gap: 24px;
    grid-template-columns: repeat(2, minmax(0, 1fr));
}

/*
 * Каждый набор — на своей подложке. Плитки в обоих столбцах одинаковые, и без
 * подложки десять строк читаются как один длинный список, а не как два входа
 * на выбор; линии в зазоре для этого мало, а панель видно с любого расстояния.
 *
 * Подложка светлее плиток не бывает, поэтому секция под блоком должна быть
 * белой: на сером фоне панель пропадёт (см. front-page.php — там у секции
 * поэтому нет bg-grey).
 */
.route-group {
    background: var(--ffj-grey-02);
    border-radius: 16px;
    padding: 22px;
}

/*
 * Граница плитки внутри панели: на сером #eef1f4 почти не видно, и карточки
 * теряют края. Тот же цвет, что у прочих границ темы, на полтона темнее.
 */
.route-group .route-tile {
    border-color: #e7ecf2;
}

/* Подпись столбца — метка, а не заголовок раздела: над блоком уже есть свой. */
.route-group__title {
    color: var(--ffj-red-01);
    font-size: 12px;
    font-weight: 700;
    letter-spacing: .08em;
    margin: 0 0 16px;
    text-transform: uppercase;
}

.route-tiles {
    display: grid;
    gap: 24px;
    grid-template-columns: repeat(4, minmax(0, 1fr));
}

/*
 * Столбиком, в половину ширины. Плитка разворачивается в строку: иконка слева
 * от текста, а не над ним — вертикальной она заняла бы вдвое больше высоты, и
 * пять типологий уехали бы далеко ниже четырёх ролей.
 */
.route-tiles--stack {
    gap: 12px;
    grid-template-columns: minmax(0, 1fr);
}

.route-tiles--stack .route-tile {
    align-items: flex-start;
    flex-direction: row;
    gap: 16px;
    padding: 16px 18px;
}

.route-tiles--stack .route-tile__icon {
    font-size: 1.125rem;
    height: 44px;
    margin-bottom: 0;
    width: 44px;
}

/*
 * Обёртка текста нужна только строке: без неё название, обещание и ссылка стали
 * бы соседями иконки в том же ряду. В вертикальной плитке она ничего не меняет
 * — это та же колонка, что и сама плитка.
 */
.route-tile__body {
    display: flex;
    flex: 1 1 auto;
    flex-direction: column;
    min-width: 0;
}

/*
 * Плитка — не обложка, а иконка и две строки, поэтому в отличие от .route-card
 * медиа-блока у неё нет и всё содержимое лежит в общем padding. Модификаторы:
 * --accent — красная круглая иконка вместо серой квадратной,
 * --soon    — плитка без ссылки (маршрут ещё не опубликован).
 */
.route-tile {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    color: inherit;
    display: flex;
    flex-direction: column;
    padding: 22px;
    transition: border-color .25s ease, box-shadow .25s ease, transform .25s ease;
}

/*
 * :not(.route-tile--soon) — маршрут без опубликованной страницы выводится тем же
 * <a>, но без href: это уже не ссылка, и отзываться на наведение ей нечем.
 */
.route-tile:not(.route-tile--soon):hover {
    border-color: var(--ffj-red-01);
    box-shadow: 0 12px 28px rgba(13, 20, 49, .1);
    color: inherit;
    transform: translateY(-2px);
}

.route-tile__icon {
    align-items: center;
    background: var(--ffj-grey-02);
    border-radius: 12px;
    color: #4a5073;
    display: flex;
    flex: 0 0 auto;
    font-size: 1.375rem;
    height: 64px;
    justify-content: center;
    margin-bottom: 16px;
    transition: background-color .25s ease, color .25s ease;
    width: 64px;
}

.route-tile:not(.route-tile--soon):hover .route-tile__icon {
    background: var(--ffj-red-01);
    color: #fff;
}

/*
 * Быстрые входы маршрута: та же плитка, но иконка сразу красная и круглая.
 * Цвет здесь несёт смысл: серая квадратная плитка ведёт в раздел, красная
 * круглая — конкретное действие монтажника.
 *
 * :not(.route-tile--soon) — не ради «скоро», а ради веса: без него правило выше
 * оказывается специфичнее и на наведении гасит красный обратно.
 */
.route-tile--accent .route-tile__icon {
    background: var(--ffj-red-01);
    border-radius: 50%;
    color: #fff;
}

.route-tile--accent:not(.route-tile--soon):hover .route-tile__icon {
    background: var(--ffj-red-02);
    color: #fff;
}

/*
 * Тег на месте иконки (узлы на маршруте монтажника). Плитка — флекс-колонка,
 * поэтому без align-self тег растягивается на всю её ширину и перестаёт быть
 * тегом. Отступ снизу — тот же, что у иконки, чтобы заголовок стоял на месте.
 */
.route-tile > .route-tag {
    align-self: flex-start;
    margin-bottom: 14px;
}

.route-tile__title {
    color: #24262b;
    font-size: 1.0625rem;
    font-weight: 700;
}

/*
 * Обещание маршрута — между «кому» и «что внутри». Тон темнее, чем у списка
 * ниже: это фраза, которую читают, а summary — перечисление, которое сканируют.
 */
.route-tile__lead {
    color: #4a5073;
    font-size: .9375rem;
    line-height: 1.45;
    margin-top: 8px;
}

.route-tile__meta {
    color: #8a90a8;
    font-size: .8125rem;
    line-height: 1.5;
    margin-top: 6px;
}

/*
 * Пометка на месте ссылки: margin-top: auto прижимает её к низу так же, как
 * .route-card__link в готовых карточках, — ряд остаётся ровным независимо от
 * того, сколько маршрутов уже открыто.
 */
.route-tile__note {
    color: #b6bacb;
    font-size: .875rem;
    font-weight: 700;
    margin-top: auto;
    padding-top: 10px;
}

/* Ряд кнопок вне первого экрана — те же правила, что у .route-hero__actions. */
.route-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 12px;
}

/* Документация
   ------------------------------------------------------------------------ */

.route-tag {
    background: var(--ffj-red-01);
    border-radius: 4px;
    color: #fff;
    display: inline-block;
    font-size: 11px;
    font-weight: 700;
    letter-spacing: .06em;
    line-height: 1;
    padding: 6px 8px;
    text-transform: uppercase;
    white-space: nowrap;
}

/*
 * Колонка узкая: в диапазоне 992–1199px она сжимается до ~290px, поэтому кегль
 * списка и тега заметно мельче основного текста страницы — иначе длинные
 * подписи вроде «Solicitar la información disponible» ломаются надвое.
 */
.route-aside {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    height: 100%;
    padding: 16px;
}

.route-aside__title {
    color: #24262b;
    font-size: 1.125rem;
    font-weight: 700;
}

.route-aside__note {
    color: #8a90a8;
    font-size: .6875rem;
    margin-bottom: 16px;
}

/* Префикс .route-page здесь не для порядка, а ради веса: в global.css есть
   `.article ul li` и `.article p` с font-size: 1rem, и без префикса они
   перебивают правила ниже — список карточки съезжал обратно на 16px. */
.route-page .route-aside__list {
    list-style: none;
    margin: 0 0 20px;
    padding: 0;
}

.route-page .route-aside__list li {
    align-items: center;
    border-top: 1px solid #eef1f4;
    display: flex;
    font-size: 0.8rem;
    gap: 6px;
    padding: 9px 0;
}

.route-page .route-aside__list li:first-child {
    border-top: none;
}

/* min-width, а не фиксированная ширина: колонка тегов ровная на текущих
   подписях, но более длинный перевод растянет тег, а не вылезет за него. */
.route-page .route-aside__list .route-tag {
    flex: 0 0 auto;
    font-size: 10px;
    letter-spacing: .02em;
    min-width: 70px;
    padding: 5px 4px;
    text-align: center;
}

.route-docs {
    display: grid;
    gap: 20px;
    grid-template-columns: repeat(3, minmax(0, 1fr));
}

.route-doc {
    align-items: flex-start;
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    color: inherit;
    display: flex;
    flex-direction: column;
    gap: 8px;
    padding: 22px;
    transition: box-shadow .25s ease, transform .25s ease;
}

.route-doc:hover {
    box-shadow: 0 12px 28px rgba(13, 20, 49, .1);
    color: inherit;
    transform: translateY(-2px);
}

.route-doc__title {
    color: #24262b;
    font-size: 1.0625rem;
    font-weight: 700;
}

.route-doc__text {
    color: #4a5073;
    font-size: .875rem;
}

/* Система монтажа: схема узла и шаги 01-06
   ------------------------------------------------------------------------ */

/* Схема слева, шаги справа: колонки равные, потому что схема без подписей
   рядом не читается, а шаги без схемы — просто список. */
.route-system {
    display: grid;
    gap: 40px;
    grid-template-columns: repeat(2, minmax(0, 1fr));
}

/* Пара равных карточек: преимущество и оговорка к нему. */
.route-duo {
    display: grid;
    gap: 24px;
    grid-template-columns: repeat(2, minmax(0, 1fr));
}

/*
 * Ряд «карточка и кадр» вместо двух равных карточек. Колонка кадра ограничена
 * натуральной шириной фотографии узла (348px): на половине ряда её пришлось бы
 * растягивать почти вдвое, и от снимка осталась бы каша. По высоте кадр идёт
 * вровень с карточкой рядом, подрезаясь по cover.
 */
.route-duo--media {
    grid-template-columns: minmax(0, 1fr) minmax(0, 348px);
}

.route-duo__media {
    border-radius: 14px;
    display: block;
    height: 100%;
    max-width: 348px;
    object-fit: cover;
    width: 100%;
}

.route-scheme {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    padding: 24px;
}

/* Схема тянется по ширине колонки. В файле она заметно шире, чем выводится,
   поэтому на ретине остаётся резкой. */
.route-scheme img {
    display: block;
    height: auto;
    width: 100%;
}

/* Три разреза подконструкции под схемой. Рисунки разных пропорций и на белом
   фоне, поэтому вписываются в одинаковую карточку целиком: подрезать разрез
   нельзя, он и есть содержание. */
.route-shots {
    display: grid;
    gap: 24px;
    grid-template-columns: repeat(3, minmax(0, 1fr));
    margin-top: 40px;
}

.route-shots__item {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    margin: 0;
    padding: 20px;
}

/* Два кадра вместо трёх: одно и то же место реза, сделанное разным инструментом.
   Колонок здесь всегда две, поэтому кадр шире и выше, чем в ряду из трёх. */
.route-shots--2 {
    grid-template-columns: repeat(2, minmax(0, 1fr));
}

/*
 * Здесь кадр заполняет карточку целиком (cover), а не вписывается в неё: это
 * не разрез, а фактура панели, и она одинаковая по всей высоте — обрезать её
 * нечем, а вписанная она давала бы узкую полосу в белом поле.
 */
.route-shots--2 .route-shots__item img {
    height: 420px;
    object-fit: cover;
}

/* Подпись под кадром: без неё две тёмные фактуры читаются как один и тот же
   кадр, и разница в кромке — то, ради чего пара и стоит на странице, — теряется. */
.route-shots__note {
    color: #4a5073;
    font-size: .9375rem;
    line-height: 1.5;
    margin-top: 16px;
}

.route-shots__item img {
    display: block;
    height: 300px;
    object-fit: contain;
    width: 100%;
}

/* Кадр, который открывается в лайтбоксе. Курсор — единственное, чем карточка
   про это говорит, и это обычный курсор ссылки: кадр по клику не приближается,
   а открывается отдельным окном, как и всё остальное на маршруте. Ссылка
   блочная, иначе под кадром осталась бы полоса от строчной высоты. */
.route-shots__link {
    cursor: pointer;
    display: block;
}

/*
 * Один чертёж во всю ширину ряда. Общая высота ряда ему не подходит: лист
 * читают по размерам и подписям у линий, и в полосе высотой с фотографию они
 * превращаются в точки. Поэтому лист идёт своей высотой, а разглядывают его в
 * лайтбоксе — там он открывается целиком.
 */
.route-shots--1 {
    grid-template-columns: minmax(0, 1fr);
}

.route-shots--1 .route-shots__item img {
    height: auto;
}

/* Ролик десятиминутный и весит десятки мегабайт, поэтому грузится только по
   кнопке: до нажатия страница тянет один постер. */
.route-video {
    margin-top: 40px;
}

.route-video video {
    background: #24262b;
    border-radius: 14px;
    display: block;
    height: auto;
    width: 100%;
}

/*
 * Два ролика в ряд: съёмка реза и разбор дефекта от пыли — их смотрят вместе,
 * один за другим.
 *
 * Кадры у роликов разной пропорции, поэтому оба живут в прямоугольнике второго
 * (768:540) — иначе низ у плееров не сходится. Растянут при этом только кадр
 * первого ролика: он вписывается в высоту (contain, обрезать нечего), а поля
 * сверху и снизу закрывает та же тёмная подложка, что стоит под плеером.
 * Пропорция второго — потому что у него внизу идут субтитры, и ужимать его в
 * чужую рамку значило бы мельчить их ещё сильнее.
 */
.route-videos {
    display: grid;
    gap: 24px;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    margin-top: 40px;
}

.route-videos .route-video {
    margin-top: 0;
}

.route-videos video {
    aspect-ratio: 768 / 540;
    object-fit: contain;
}

/*
 * Шаги идут строго друг за другом, и говорит об этом только вертикальная линия
 * между номерами. Она рисуется псевдоэлементом от каждого шага вниз, у
 * последнего гасится — иначе линия висела бы хвостом под шестым номером.
 */
.route-step {
    display: grid;
    gap: 2px 18px;
    grid-template-columns: 44px minmax(0, 1fr);
    padding-bottom: 22px;
    position: relative;
}

.route-step:last-child {
    padding-bottom: 0;
}

.route-step::before {
    background: #eef1f4;
    bottom: 0;
    content: '';
    left: 21px;
    position: absolute;
    top: 44px;
    width: 2px;
}

.route-step:last-child::before {
    display: none;
}

/* Номер занимает обе строки текста, а подпись и пояснение прижаты к его
   середине — так номер читается как метка пары, а не первой строки. */
.route-step__num {
    align-items: center;
    background: var(--ffj-red-01);
    border-radius: 50%;
    color: #fff;
    display: flex;
    font-size: .8125rem;
    font-weight: 700;
    grid-row: span 2;
    height: 44px;
    justify-content: center;
    width: 44px;
}

.route-step__title {
    align-self: end;
    color: #24262b;
    font-weight: 700;
}

.route-step__text {
    align-self: start;
    color: #4a5073;
    font-size: .875rem;
}

/* Отметки: что даёт сухой монтаж и что проверить перед сдачей
   ------------------------------------------------------------------------ */

/* Префикс .route-page — ради веса: .article ul li в global.css перебивает
   кегль и отступы списка (та же причина, что у .route-aside__list выше). */
/* Ширина ограничена так же, как у списка помощи: строка в одну фразу на всю
   ширину контейнера читается тяжело. В карточке блока «в обра» ограничение ни
   на что не влияет — там колонка и так уже. */
.route-page .route-checks {
    list-style: none;
    margin: 0;
    max-width: 860px;
    padding: 0;
}

.route-page .route-checks li {
    border-top: 1px solid #eef1f4;
    font-size: .9375rem;
    padding: 11px 0 11px 30px;
    position: relative;
}

.route-page .route-checks li:first-child {
    border-top: none;
}

/* Галочка — символом в псевдоэлементе, а не иконкой Font Awesome: kit подменяет
   <i> на <svg> уже после отрисовки, и строка на этом прыгает. */
.route-page .route-checks li::before {
    color: var(--ffj-green-01);
    content: '\2713';
    font-weight: 700;
    left: 4px;
    line-height: inherit;
    position: absolute;
    top: 11px;
}

/* Белая плашка без ссылки: колонки блока «в обра» и всё, что нужно просто
   показать карточкой на сером фоне. */
.route-panel {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    height: 100%;
    padding: 26px;
}

.route-panel__eyebrow {
    color: var(--ffj-red-01);
    font-size: 1.125rem;
    font-weight: 700;
    letter-spacing: .04em;
}

.route-panel__title {
    color: #24262b;
    font-size: 1.125rem;
    font-weight: 700;
    margin-bottom: 16px;
}

.route-page .route-panel p {
    color: #4a5073;
    font-size: .9375rem;
    margin-bottom: 0;
}

/* Сравнение серий
   ------------------------------------------------------------------------ */

/*
 * Таблица под карточками серий: одни и те же характеристики у обеих серий
 * рядом. Плашка белая, потому что блок серий стоит на сером фоне; overflow
 * скрыт, чтобы серая шапка таблицы не вылезала из скругления.
 */
.route-specs {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    margin-top: 24px;
    overflow: hidden;
}

/*
 * table-layout: fixed — иначе ширину колонок задаёт самая длинная строка
 * («Característica diferencial»), и колонки серий получаются разными.
 */
.route-specs__table {
    border-collapse: collapse;
    margin: 0;
    table-layout: fixed;
    width: 100%;
}

.route-specs__table th,
.route-specs__table td {
    font-size: .875rem;
    line-height: 1.5;
    padding: 14px 20px;
    text-align: left;
    vertical-align: top;
}

/* Шапка — названия серий. Первая ячейка пустая: это угол таблицы. */
.route-specs__table thead th {
    background: var(--ffj-grey-02);
    color: #24262b;
    font-weight: 700;
    letter-spacing: .03em;
    text-transform: uppercase;
}

/* Ширина задаётся только шапке: при fixed остальные колонки делят остаток. */
.route-specs__table thead th:first-child {
    width: 26%;
}

.route-specs__table tbody th {
    color: #24262b;
    font-weight: 700;
}

.route-specs__table tbody td {
    color: #4a5073;
}

.route-specs__table tbody tr + tr > * {
    border-top: 1px solid #eef1f4;
}

/*
 * Строка «с чего начать» — единственная развёрнутая: подводка, условия
 * списком и ссылка в каталог своей серии.
 */
.route-specs__lead {
    color: #24262b;
    display: block;
    font-weight: 700;
}

/* Префикс .route-page — ради веса: .article ul li в global.css перебивает
   кегль и отступы списка (та же причина, что у .route-aside__list). */
.route-page .route-specs__list {
    list-style: none;
    margin: 8px 0 0;
    padding: 0;
}

.route-page .route-specs__list li {
    font-size: .875rem;
    line-height: 1.5;
    padding: 3px 0 3px 16px;
    position: relative;
}

.route-page .route-specs__list li::before {
    background: var(--ffj-red-01);
    border-radius: 50%;
    content: '';
    height: 5px;
    left: 0;
    position: absolute;
    top: 12px;
    width: 5px;
}

.route-specs__link {
    color: var(--ffj-red-01);
    display: inline-block;
    font-size: .8125rem;
    font-weight: 700;
    letter-spacing: .03em;
    margin-top: 12px;
    text-transform: uppercase;
}

.route-specs__link:hover {
    color: var(--ffj-red-02);
}

.route-specs__link i {
    font-size: .6875rem;
    margin-left: 6px;
    transition: transform .2s ease;
}

.route-specs__link:hover i {
    transform: translateX(4px);
}

/* Сравнения
   ------------------------------------------------------------------------ */

.route-compare {
    display: grid;
    gap: 16px;
    max-width: 860px;
}

.route-compare__item {
    align-items: center;
    background: #fff;
    border: 1px solid #eef1f4;
    border-left: 4px solid var(--ffj-red-01);
    border-radius: 10px;
    color: inherit;
    display: flex;
    gap: 20px;
    justify-content: space-between;
    padding: 20px 24px;
    transition: box-shadow .25s ease;
}

.route-compare__item:hover {
    box-shadow: 0 12px 28px rgba(13, 20, 49, .1);
    color: inherit;
}

.route-compare__title {
    color: #24262b;
    display: block;
    font-weight: 700;
}

.route-compare__text {
    color: #4a5073;
    display: block;
    font-size: .875rem;
    margin-top: 4px;
}

.route-compare .route-card__link {
    flex: 0 0 auto;
    margin-top: 0;
    padding-top: 0;
}

/* Поддержка проекта
   ------------------------------------------------------------------------ */

/*
 * Пункты помощи — списком, а не плиткой: в плитку они встают рваным рядом, как
 * только их число перестаёт делиться на колонки, а списком читаются как
 * перечисление того, чем здесь помогают, — что и есть смысл блока.
 */
.route-support {
    display: grid;
    max-width: 860px;
}

.route-support__item {
    align-items: baseline;
    border-top: 1px solid #eef1f4;
    display: grid;
    gap: 4px 24px;
    grid-template-columns: minmax(0, 260px) minmax(0, 1fr);
    padding: 14px 0 14px 22px;
    position: relative;
}

.route-support__item:first-child {
    border-top: none;
}

.route-support__item::before {
    background: var(--ffj-red-01);
    border-radius: 50%;
    content: '';
    height: 10px;
    left: 0;
    position: absolute;
    top: 21px;
    width: 10px;
}

.route-support__title {
    color: #24262b;
    font-weight: 700;
}

.route-support__text {
    color: #4a5073;
    font-size: .875rem;
}

/* Списки и форма
   ------------------------------------------------------------------------ */

.route-page .route-list {
    list-style: none;
    margin: 0 0 24px;
    padding: 0;
}

.route-page .route-list li {
    font-size: .9375rem;
    padding: 6px 0 6px 20px;
    position: relative;
}

.route-page .route-list li::before {
    background: var(--ffj-red-01);
    border-radius: 50%;
    content: '';
    height: 6px;
    left: 0;
    position: absolute;
    top: 15px;
    width: 6px;
}

.route-form__promise {
    color: var(--ffj-red-01);
    font-weight: 700;
    margin-bottom: 8px;
}

.route-privacy {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    color: #8a90a8;
    font-size: .8125rem;
    padding: 20px 22px;
}

.route-privacy__title {
    color: var(--ffj-red-01);
    font-size: 11px;
    font-weight: 700;
    letter-spacing: .06em;
    margin-bottom: 8px;
    text-transform: uppercase;
}

.route-page .route-privacy p {
    margin-bottom: 8px;
}

.route-form {
    background: #fff;
    border: 1px solid #eef1f4;
    border-radius: 14px;
    padding: 28px;
}

/*
 * Форма переиспользует оформление полей общей формы сайта (.wrap-bottom-form /
 * .plans-form), но не её подложку: там голубой градиент и фотография, которые
 * в белой карточке лезут поверх полей. Гасим ровно то же, что уже гасит для
 * себя модалка в ux.css, — фон обёртки, её внутренние отступы и фото в :before.
 */
.route-form.wrap-bottom-form {
    background: #fff;
}

.route-form.wrap-bottom-form form {
    padding: 0;
}

.route-form.wrap-bottom-form form:before {
    display: none;
}

/*
 * Поля в две колонки. Пар полей восемь, и в один столбец форма уезжает намного
 * ниже левой колонки блока. Сетка вешается на .fields — обёртку полей из самой
 * формы; согласие, кнопка и ответ формы лежат снаружи неё и остаются во всю
 * ширину сами по себе. Contact Form 7 оборачивает каждое поле в <p>, поэтому
 * колонками управляют сами абзацы и разметку формы под них править не нужно.
 */
.route-form.wrap-bottom-form form .fields {
    display: grid;
    gap: 0 20px;
    grid-template-columns: repeat(2, minmax(0, 1fr));
}

/*
 * Во всю ширину — то, что не пара соседнему полю: выбор «что нужно», вложение
 * и комментарий. Опознаём по содержимому абзаца, чтобы не заводить в форме
 * служебных классов.
 */
.route-form.wrap-bottom-form form .fields > p:has(.wpcf7-checkbox),
.route-form.wrap-bottom-form form .fields > p:has(input[type="file"]),
.route-form.wrap-bottom-form form .fields > p:has(textarea) {
    grid-column: 1 / -1;
}

/* В колонке ограничение общей формы в 400px только мешает: поле уже колонки. */
.route-form.wrap-bottom-form form input.wpcf7-form-control:not(.wpcf7-submit),
.route-form.wrap-bottom-form form select.wpcf7-form-control,
.route-form.wrap-bottom-form form textarea.wpcf7-form-control,
.route-form.wrap-bottom-form form .form-control {
    max-width: 100%;
}

/*
 * Подпись группы полей. У группы галочек своего <label> быть не может: внутри
 * уже по <label> на каждую плашку, а вкладывать label в label нельзя.
 */
.route-form.wrap-bottom-form form .form-label {
    color: var(--ffj-blue-02);
    display: block;
    font-size: 13px;
    font-weight: 600;
    letter-spacing: .02em;
    margin-bottom: 6px;
}

/*
 * «¿Qué necesita?» — ряд плашек, а не столбик галочек: отмечают обычно
 * несколько, и в столбик они занимают пол-формы.
 */
.route-form.wrap-bottom-form form .wpcf7-checkbox {
    display: flex;
    flex-wrap: wrap;
    gap: 10px;
}

/*
 * Ширина плашки — по её подписи, лишние переносятся на следующую строку.
 * Делить ряд поровну (flex: 1 1 0) нельзя: варианты заводят в самой форме
 * Contact Form 7, их число и длина меняются без правки темы, и на восьми
 * вариантах каждой доставалось меньше, чем её самое длинное слово, — подписи
 * вылезали за рамку и налезали на соседей.
 */
.route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item {
    flex: 0 1 auto;
    margin: 0;
    max-width: 100%;
    min-width: 0;
}

.route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item label {
    align-items: center;
    background: #fff;
    border: 1px solid #d9e2ea;
    border-radius: 8px;
    color: #24262b;
    cursor: pointer;
    display: flex;
    font-size: 14px;
    font-weight: 600;
    justify-content: center;
    margin: 0;
    padding: 11px 12px;
    text-align: center;
    transition: border-color .15s ease, background-color .15s ease;
}

.route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item label:hover {
    border-color: var(--ffj-red-01);
}

/*
 * Сам квадратик галочки в плашке лишний — выбор виден по рамке. Убираем его с
 * глаз, но не из потока фокуса: :focus-visible ниже рисует обводку на плашке,
 * иначе с клавиатуры выбор был бы вслепую.
 */
.route-form.wrap-bottom-form form .wpcf7-checkbox input[type="checkbox"] {
    height: 1px;
    margin: 0;
    opacity: 0;
    position: absolute;
    width: 1px;
}

.route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item label:has(input:checked) {
    background: #fff5f4;
    border-color: var(--ffj-red-01);
    box-shadow: inset 0 0 0 1px var(--ffj-red-01);
    color: var(--ffj-red-01);
}

.route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item label:has(input:focus-visible) {
    outline: 2px solid var(--ffj-red-01);
    outline-offset: 2px;
}

/* Отправка — во всю ширину формы: это единственное действие блока. */
.route-form.wrap-bottom-form form .wpcf7-submit {
    width: 100%;
}

.route-form__title {
    color: #24262b;
    font-size: 1.125rem;
    font-weight: 700;
    margin-bottom: 20px;
}

/* Адаптив
   ------------------------------------------------------------------------ */

@media (max-width: 1199.98px) {
    /*
     * :not(--stack) — столбик остаётся столбиком на любой ширине: он и так уже
     * в половину контейнера, вторая колонка внутри него не поместилась бы.
     */
    .route-cards--4,
    .route-tiles:not(.route-tiles--stack) {
        grid-template-columns: repeat(2, minmax(0, 1fr));
    }

    /* Пять карточек в ряд перестают помещаться раньше остальных сеток. */
    .route-cards--5 {
        grid-template-columns: repeat(3, minmax(0, 1fr));
    }
}


@media (max-width: 991.98px) {
    .route-nav__label {
        display: none;
    }

    .route-hero__title {
        font-size: 2rem;
    }

    .route-hero__media img {
        height: 320px;
        margin-top: 28px;
    }

    .route-cards--2,
    .route-cards--3,
    .route-cards--5,
    .route-docs,
    .route-shots {
        grid-template-columns: repeat(2, minmax(0, 1fr));
    }

    /* Колонка стала вдвое шире, разрезу такая высота уже не нужна. */
    .route-shots__item img {
        height: 260px;
    }

    .route-shots--2 .route-shots__item img {
        height: 360px;
    }

    /* Два набора рядом перестают помещаться: сначала роли, потом типологии. */
    .route-groups {
        grid-template-columns: minmax(0, 1fr);
    }

    .route-system,
    .route-duo {
        grid-template-columns: minmax(0, 1fr);
    }

    /* Две равные карточки здесь уже не помещаются, а «карточка и кадр» ещё
       помещается: колонка кадра узкая. Правило повторяет базовое, потому что
       строкой выше .route-duo сворачивает и его. */
    .route-duo--media {
        grid-template-columns: minmax(0, 1fr) minmax(0, 348px);
    }

    .route-aside {
        margin-top: 24px;
    }

    /* Колонки развернулись в столбик, и кадр встал вплотную к списку над ним:
       у колонок Bootstrap вертикального отступа нет. */
    .route-section__media {
        margin-top: 24px;
    }
}

@media (max-width: 767.98px) {
    .route-duo--media {
        grid-template-columns: minmax(0, 1fr);
    }

    /* Половина телефонного экрана — это кадр шириной с ладонь: субтитры в нём
       уже не прочитать, поэтому ролики расходятся друг под друга. Ровнять их
       по высоте больше незачем: они стоят не рядом, а один под другим, и общая
       рамка только добавила бы первому полосы сверху и снизу. */
    .route-videos {
        grid-template-columns: minmax(0, 1fr);
    }

    .route-videos video {
        aspect-ratio: auto;
    }

    .route-duo__media {
        height: auto;
    }

    .route-form.wrap-bottom-form form .fields {
        grid-template-columns: minmax(0, 1fr);
    }

    .route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item {
        flex: 1 1 45%;
    }

    .route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item label {
        min-width: 0;
    }

    /*
     * Три колонки с абзацами текста на телефоне не читаются, поэтому строка
     * разворачивается в блок: сверху характеристика, под ней значения, каждое
     * подписано названием серии — саму шапку таблицы здесь показывать негде.
     */
    .route-specs__table,
    .route-specs__table tbody,
    .route-specs__table tbody tr,
    .route-specs__table tbody th,
    .route-specs__table tbody td {
        display: block;
        width: auto;
    }

    .route-specs__table thead {
        display: none;
    }

    .route-specs__table tbody tr {
        padding: 8px 0;
    }

    .route-specs__table tbody tr + tr {
        border-top: 1px solid #eef1f4;
    }

    .route-specs__table tbody tr + tr > * {
        border-top: none;
    }

    .route-specs__table tbody th {
        padding-bottom: 2px;
    }

    .route-specs__table tbody td {
        padding-bottom: 6px;
        padding-top: 6px;
    }

    .route-specs__table tbody td::before {
        color: var(--ffj-red-01);
        content: attr(data-label);
        display: block;
        font-size: 11px;
        font-weight: 700;
        letter-spacing: .06em;
        margin-bottom: 2px;
        text-transform: uppercase;
    }

    .route-nav__inner {
        gap: 14px;
        height: 56px;
    }

    .route-nav__link {
        font-size: 13px;
    }

    .route-nav__cta {
        font-size: 13px;
        padding: 8px 14px;
    }

    .route-hero {
        padding: 28px 0 40px;
    }

    .route-hero__title {
        font-size: 1.75rem;
    }

    .route-section {
        padding: 40px 0;
    }

    .route-section__title {
        font-size: 1.5rem;
    }

    .route-hero__actions .btn,
    .route-actions .btn {
        flex: 1 1 100%;
    }
}

@media (max-width: 575.98px) {
    /*
     * На самом узком экране половина ряда уже уже самой длинной подписи
     * («Documentación»), поэтому плашки снова расходятся по содержимому и
     * растягиваются по своей строке: длинной достаётся строка целиком.
     */
    .route-form.wrap-bottom-form form .wpcf7-checkbox .wpcf7-list-item {
        flex: 1 1 auto;
    }

    .route-cards--2,
    .route-cards--3,
    .route-cards--4,
    .route-cards--5,
    .route-tiles,
    .route-docs,
    .route-shots {
        grid-template-columns: minmax(0, 1fr);
    }

    .route-shots__item img {
        height: 320px;
    }

    .route-shots--2 .route-shots__item img {
        height: 320px;
    }

    /*
     * Отступы контейнера, панели и плитки складываются, и на узком экране текст
     * остаётся в колодце. Панель отдаёт свою половину плиткам.
     */
    .route-group {
        padding: 16px;
    }

    .route-compare__item {
        align-items: flex-start;
        flex-direction: column;
        gap: 12px;
    }

    .route-support__item {
        grid-template-columns: minmax(0, 1fr);
    }

    .route-form {
        padding: 20px;
    }
}
