Дата публикации
8 Января 2020
Дата изменения
8 Января 2020
Уникальных просмотров
1.721

Оглавление

Фреймворк Materialize предоставляет неплохой эффект для кнопок. При нажатии на кнопку, в месте нажатия образуется некая волна. Если кликнуть на центр кнопки, волны расходятся быстрее, если кликать на край — немного медленнее.

Потребовалось реализовать нечто похожее, но само собой без подключение фреймворка. В интернете нашел несколько интересных решений, есть даже на чистом CSS. Но больше всего меня заинтересовал вариант написанный на чистом JavaScript, с применением небольшой CSS анимации. Разобрался в нем и решил разместить у себя на сайте. 

JavaScript код

Для начала напишем небольшой JS код:

// Ищем все кнопки
const buttons = document.getElementsByClassName('btn');
for (let i = 0; i < buttons.length; i++) {
    buttons[i].addEventListener('click', function (e) {
        // При нажатии на кнопку, внутри создаем элемент span, который и будет волной
        const wave = document.createElement('span'),
            // Получаем размеры и координаты элемента в месте клика относительно viewport
            waveOffset = this.getBoundingClientRect();

        // Вычисляем координаты вычитанием координат элемента из координат документа
        const waveY = e.pageY - waveOffset.top,
            waveX = e.pageX - waveOffset.left;

        // Полученные координаты записываем в стили тегу span
        wave.style.top = waveY + 'px',
            wave.style.left = waveX + 'px',
            wave.style.background = this.getAttribute('data-button-background');

        // Внутри кнопки по клику создаем span с координатами, которые формируются в зависимости от того, куда кликнем
        this.appendChild(wave);

        // Удаляем созданный тег span после 1.5 секунд
        setTimeout(function () {
            wave.parentNode.removeChild(wave);
        }, 1500);
    });
}

Как и всегда, я проставил много комментариев. Но если тезисно — данный код находит все кнопки по классу .btn, далее при клике внутри кнопки создается элемент span, который будет создавать тот самый эффект волн как в Material Design / Materialize фреймворке.

При клике на элемент, скрипт вычисляет его координаты, вычитает их из координат документа (не путать с координатами браузера) и полученные координаты заносит в инлайновые стили top и left. Некая динамическая генерация волн.

Прописываем CSS стили

Динамическое определение волн есть. Но их еще нужно анимировать. Напишем несколько стилей и анимацию с помощью кейфреймов:

.btn {
    position: relative;
    overflow: hidden;
    z-index: 1;
}

.btn span {
    position: absolute;
    height: 12px;
    width: 12px;
    border-radius: 100%;
    background: #FFFFFF;
    animation: buttonWave 1.6s;
}

@keyframes buttonWave {
    0% {
        opacity: 0.2;
        transform: scale(1);
    }
    100% {
        opacity: 0;
        transform: scale(40);
    }
}

Анимацию волн можно регулировать в @keyframes buttonWave.

В одном из решений в интернете подсмотрел возможность задавать цвет волн с помощью дата атрибута:

<button class="btn btn-default" data-button-background="#323479">Button 1</button>
<button class="btn btn-default" data-button-background="#cb2e77">Button 2</button>
<button class="btn btn-default">Button 3</button>

Прозрачность цвета волн регулируется в @keyframes buttonWave, через параметр opacity. Но этот дата-атрибут можно просто не заполнять, скрипт ругаться не будет.

Результат и исходники

Благодарность автору

Если по какой-либо причине вы хотите поблагодарить автора данного ресурса, вы можете это сделать одним из удобных для вас способов ниже.

Один из самых популярных способов поблагодарить автора, воспользоваться сервисом Яндекс.Деньги.

Время работы: 0,1126 s
Время запросов: 0,1126 s
Количество запросов: 28
Источник: cache