← Назад к шаблонам На главную
UI-компоненты

Сравнение пакетов услуг

Блок для сравнения тарифов, услуг или подписок. Пользователь выбирает два пакета, а интерфейс подсвечивает различия и помогает быстрее принять решение.

Сложность: Сложная HTML CSS JavaScript comparison table dynamic filters pricing UI responsive layout
Сравнение пакетов

Разница между тарифами видна сразу

Пользователь выбирает два пакета, а блок подсвечивает отличия по цене, возможностям и условиям.

Параметр Расширенный Комплексный
Стоимость 14 500 ₽ 22 000 ₽
Встречи 4 8
Поддержка после встречи 7 дней 30 дней
Отчёт Краткий Подробный
Приоритет Обычный Высокий

Комплексный пакет подходит, если важны сопровождение, подробный отчёт и больше встреч.

<section class="compare-lab">
    <div class="compare-lab__head">
        <span class="compare-lab__badge">Сравнение пакетов</span>
        <h2>Разница между тарифами видна сразу</h2>
        <p>
            Пользователь выбирает два пакета, а блок подсвечивает отличия по цене,
            возможностям и условиям.
        </p>
    </div>

    <div class="compare-lab__selectors">
        <label>
            Первый пакет
            <select class="compare-select" data-side="left">
                <option value="start">Базовый</option>
                <option value="pro" selected>Расширенный</option>
                <option value="max">Комплексный</option>
            </select>
        </label>

        <label>
            Второй пакет
            <select class="compare-select" data-side="right">
                <option value="start">Базовый</option>
                <option value="pro">Расширенный</option>
                <option value="max" selected>Комплексный</option>
            </select>
        </label>
    </div>

    <div class="compare-table">
        <div class="compare-table__row compare-table__row--head">
            <span>Параметр</span>
            <strong class="compare-left-title">Расширенный</strong>
            <strong class="compare-right-title">Комплексный</strong>
        </div>

        <div class="compare-table__row" data-feature="price">
            <span>Стоимость</span>
            <strong class="compare-left-value">14 500 ₽</strong>
            <strong class="compare-right-value">22 000 ₽</strong>
        </div>

        <div class="compare-table__row" data-feature="meetings">
            <span>Встречи</span>
            <strong class="compare-left-value">4</strong>
            <strong class="compare-right-value">8</strong>
        </div>

        <div class="compare-table__row" data-feature="support">
            <span>Поддержка после встречи</span>
            <strong class="compare-left-value">7 дней</strong>
            <strong class="compare-right-value">30 дней</strong>
        </div>

        <div class="compare-table__row" data-feature="report">
            <span>Отчёт</span>
            <strong class="compare-left-value">Краткий</strong>
            <strong class="compare-right-value">Подробный</strong>
        </div>

        <div class="compare-table__row" data-feature="priority">
            <span>Приоритет</span>
            <strong class="compare-left-value">Обычный</strong>
            <strong class="compare-right-value">Высокий</strong>
        </div>
    </div>

    <div class="compare-lab__result">
        <p class="compare-result-text">
            Комплексный пакет подходит, если важны сопровождение, подробный отчёт и больше встреч.
        </p>
        <button type="button">Выбрать подходящий пакет</button>
    </div>
</section>
.compare-lab {
    padding: 46px;
    border-radius: 28px;
    overflow: hidden;
    background:
        radial-gradient(circle at 12% 18%, rgba(59, 130, 246, 0.30), transparent 32%),
        radial-gradient(circle at 88% 82%, rgba(236, 72, 153, 0.18), transparent 34%),
        linear-gradient(135deg, #020617, #0f172a);
}

.compare-lab__head {
    max-width: 860px;
    margin-bottom: 34px;
}

.compare-lab__badge {
    display: inline-flex;
    margin-bottom: 16px;
    padding: 8px 13px;
    border-radius: 999px;
    color: #bfdbfe;
    background: rgba(59, 130, 246, 0.16);
    border: 1px solid rgba(96, 165, 250, 0.45);
    font-size: 13px;
}

.compare-lab__head h2 {
    margin: 0 0 16px;
    color: #ffffff;
    font-size: clamp(32px, 5vw, 56px);
    line-height: 1.02;
    letter-spacing: -0.05em;
}

.compare-lab__head p {
    color: #cbd5e1;
    font-size: 17px;
    line-height: 1.7;
}

.compare-lab__selectors {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 18px;
    margin-bottom: 22px;
}

.compare-lab__selectors label {
    display: grid;
    gap: 8px;
    color: #dbeafe;
    font-size: 14px;
}

.compare-select {
    border: 1px solid #334155;
    border-radius: 16px;
    padding: 13px 14px;
    color: #ffffff;
    background: #020617;
    outline: none;
}

.compare-table,
.compare-lab__result {
    border: 1px solid rgba(148, 163, 184, 0.28);
    border-radius: 26px;
    background: rgba(15, 23, 42, 0.78);
    box-shadow: 0 28px 80px rgba(2, 6, 23, 0.5);
}

.compare-table {
    overflow: hidden;
}

.compare-table__row {
    display: grid;
    grid-template-columns: 1fr 1fr 1fr;
    gap: 14px;
    align-items: center;
    padding: 18px;
    border-bottom: 1px solid #334155;
    transition: 0.25s;
}

.compare-table__row:last-child {
    border-bottom: 0;
}

.compare-table__row--head {
    background: rgba(59, 130, 246, 0.12);
}

.compare-table__row span {
    color: #94a3b8;
}

.compare-table__row strong {
    color: #ffffff;
}

.compare-table__row.is-different {
    background: rgba(34, 197, 94, 0.08);
}

.compare-table__row.is-different strong:last-child {
    color: #86efac;
}

.compare-lab__result {
    display: flex;
    justify-content: space-between;
    gap: 18px;
    align-items: center;
    margin-top: 22px;
    padding: 22px;
}

.compare-lab__result p {
    margin: 0;
    color: #cbd5e1;
    line-height: 1.7;
}

.compare-lab__result button {
    flex: 0 0 auto;
    border: 0;
    border-radius: 16px;
    padding: 15px 18px;
    color: #ffffff;
    background: linear-gradient(135deg, #16a34a, #2563eb);
    cursor: pointer;
    transition: 0.25s;
}

.compare-lab__result button:hover {
    transform: translateY(-2px);
}

.compare-table.is-updated {
    animation: comparePulse 0.28s ease;
}

@keyframes comparePulse {
    from {
        opacity: 0.75;
        transform: scale(0.99);
    }

    to {
        opacity: 1;
        transform: scale(1);
    }
}

@media (max-width: 720px) {
    .compare-lab {
        padding: 26px 18px;
    }

    .compare-lab__selectors,
    .compare-table__row {
        grid-template-columns: 1fr;
    }

    .compare-lab__result {
        align-items: stretch;
        flex-direction: column;
    }

    .compare-lab__result button {
        width: 100%;
    }
}
const compareData = {
    start: {
        title: "Базовый",
        price: "8 500 ₽",
        meetings: "2",
        support: "3 дня",
        report: "Мини",
        priority: "Обычный"
    },
    pro: {
        title: "Расширенный",
        price: "14 500 ₽",
        meetings: "4",
        support: "7 дней",
        report: "Краткий",
        priority: "Обычный"
    },
    max: {
        title: "Комплексный",
        price: "22 000 ₽",
        meetings: "8",
        support: "30 дней",
        report: "Подробный",
        priority: "Высокий"
    }
};

const compareSelects = document.querySelectorAll(".compare-select");
const compareTable = document.querySelector(".compare-table");
const compareLeftTitle = document.querySelector(".compare-left-title");
const compareRightTitle = document.querySelector(".compare-right-title");
const compareResultText = document.querySelector(".compare-result-text");

function updateCompare() {
    const leftKey = document.querySelector('[data-side="left"]').value;
    const rightKey = document.querySelector('[data-side="right"]').value;
    const left = compareData[leftKey];
    const right = compareData[rightKey];

    compareTable.classList.remove("is-updated");
    void compareTable.offsetWidth;
    compareTable.classList.add("is-updated");

    compareLeftTitle.textContent = left.title;
    compareRightTitle.textContent = right.title;

    document.querySelectorAll(".compare-table__row[data-feature]").forEach(function (row) {
        const feature = row.dataset.feature;
        const values = row.querySelectorAll("strong");

        values[0].textContent = left[feature];
        values[1].textContent = right[feature];

        row.classList.toggle("is-different", left[feature] !== right[feature]);
    });

    if (leftKey === rightKey) {
        compareResultText.textContent = "Вы выбрали одинаковые пакеты. Для сравнения выберите разные варианты.";
    } else {
        compareResultText.textContent = right.title + " пакет выгоднее, если важны расширенные возможности и сопровождение.";
    }
}

compareSelects.forEach(function (select) {
    select.addEventListener("change", updateCompare);
});

updateCompare();
🚀 Рассчитать проект